Preview
#ifdef GL_ES
precision highp float;
#endif
#extension GL_OES_standard_derivatives : enable
uniform float time;
uniform vec2 mouse;
uniform vec2 resolution;
vec2 rand2n(vec2 co, float sampleIndex) {
vec2 seed = co * (sampleIndex + 1.0);
seed+=vec2(-1,1);
return vec2(fract(sin(dot(seed.xy ,vec2(12.9898,78.233))) * 43758.5453),
fract(cos(dot(seed.xy ,vec2(4.898,7.23))) * 23421.631));
}
vec2 circleInvert(vec2 pos, vec3 circle){
return ((pos - circle.xy) * circle.z * circle.z)/(length(pos - circle.xy) * length(pos - circle.xy) ) + circle.xy;
}
mat2 getRotationMat2(float angleRadians){
return mat2(cos(angleRadians), -sin(angleRadians),
sin(angleRadians), cos(angleRadians));
}
const mat2 UNI_MAT = mat2(1, 0, 0, 1);
const float PI = 3.1415926535;
const float PI_2 = 3.1415926535/2.;
const float PI_4 = 3.1415926535/4.;
const float R = 100. * sqrt(2.) / 2.;
vec3 c1 = vec3(100, 0, 0);
vec3 c3 = vec3(-100, 0, 0);
vec3 c2 = vec3(0, 100, 0);
vec3 c4 = vec3(0, -100, 0);
vec3 c5 = vec3(0);
// control point and rotation matrix of l1
float l1Angle = PI_4;
vec2 l1p = vec2(500, 0);
mat2 l1m;
mat2 l1mInv;
// control point and rotation matrix of l1
float l2Angle = PI + PI_4;
vec2 l2p = vec2(-800, 0);
mat2 l2m;
mat2 l2mInv;
float l3Angle = PI + PI_4;
vec2 l3p = vec2(-1500, 0);
mat2 l3m;
mat2 l3mInv;
float l4Angle = PI_2 + PI_4;
vec2 l4p = vec2(0, -1500);
mat2 l4m;
mat2 l4mInv;
bool enableL1 = false;
bool enableL2 = false;
bool enableL3 = false;
bool enableL4 = false;
const int MAX_ITERATIONS = 35;
float IIS(vec2 pos){
float loopNum = 0.;
bool cont = false;
for(int i = 0 ; i < MAX_ITERATIONS ; i++){
cont = false;
if(length(pos - c1.xy) < c1.z){
pos = circleInvert(pos, c1);
cont = true;
loopNum++;
}else if(length(pos - c2.xy) < c2.z){
pos = circleInvert(pos, c2);
cont = true;
loopNum++;
}else if(length(pos - c3.xy) < c3.z){
pos = circleInvert(pos, c3);
cont = true;
loopNum++;
}else if(length(pos - c4.xy) < c4.z){
pos = circleInvert(pos, c4);
cont = true;
loopNum++;
}else if(length(pos - c5.xy) < c5.z){
pos = circleInvert(pos, c5);
cont = true;
loopNum++;
}
if(enableL1){
pos -= l1p;
pos = l1mInv * pos;
if(pos.x > 0.){
pos.x *= -1.;
loopNum++;
cont = true;
}
pos = l1m * pos;
pos += l1p;
}
if(enableL2){
pos -= l2p;
pos = l2mInv * pos;
if(pos.x > 0.){
pos.x *= -1.;
loopNum++;
cont = true;
}
pos = l2m * pos;
pos += l2p;
}
if(enableL3){
pos -= l3p;
pos = l3mInv * pos;
if(pos.x > 0.){
pos.x *= -1.;
loopNum++;
cont = true;
}
pos = l3m * pos;
pos += l3p;
}
if(enableL4){
pos -= l4p;
pos = l4mInv * pos;
if(pos.x > 0.){
pos.x *= -1.;
loopNum++;
cont = true;
}
pos = l4m * pos;
pos += l4p;
}
if(cont == false) break;
}
return loopNum;
}
vec3 hsv2rgb(vec3 c)
{
vec4 K = vec4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
vec3 p = abs(fract(c.xxx + K.xyz) * 6.0 - K.www);
return c.z * mix(K.xxx, clamp(p - K.xxx, 0.0, 1.0), c.y);
}
//w: start time
//s: duration
float scene(in float t, in float w, in float s){
return clamp(t - w, 0.0, s) / s;
}
float expEzingIn(float t){
return pow( 2., 13. * (t - 1.) );
}
float expEzingOut(float t) {
return -pow( 2., -10. * t) + 1.;
}
float circEzingInOut(float t){
t /= .5;
if (t < 1.) return -.5 * (sqrt(1. - t*t) - 1.);
t -= 2.;
return .5 * (sqrt(1. - t*t) + 1.);
}
float circEzingIn(float t){
return - (sqrt(1. - t*t) - 1.);
}
float ezing(in float t){
//return pow( 2., 13. * (t - 1.) );
//return t;
//return t * t * t;
//return t * t * (3.0 - 2.0 * t);
//return sin(t * radians(90.0));
//return 1.0 - pow(cos(t * radians(90.0)), 0.5);
return pow(sin(t * radians(90.0)), 0.2);
}
const float DISPLAY_GAMMA_COEFF = 1. / 2.2;
vec3 gammaCorrect(vec3 rgb) {
return vec3((min(pow(rgb.r, DISPLAY_GAMMA_COEFF), 1.)),
(min(pow(rgb.g, DISPLAY_GAMMA_COEFF), 1.)),
(min(pow(rgb.b, DISPLAY_GAMMA_COEFF), 1.)));
}
const float SAMPLE_NUM = 20.;
void main(){
vec3 sum = vec3(0);
float t = mod(time, 22.);
float ratio = resolution.x / resolution.y / 2.0;
enableL1 = enableL2 = enableL3 = enableL4 = false;
float start = 1.5;
c1.z = mix(0., R, expEzingIn(scene(t, start, 1.)));
c2.z = mix(0., R, expEzingIn(scene(t, start + .1, 1.)));
c3.z = mix(0., R, expEzingIn(scene(t, start + .3, 1.)));
c4.z = mix(0., R, expEzingIn(scene(t, start + .5, 1.)));
float rotationStart = start + 1.7;
float scaleFactor = 150.;
float theta = mix(0., 2. * PI + PI_4, circEzingInOut(scene(t, rotationStart, 1.)));
scaleFactor += mix(0., 800., circEzingInOut(scene(t, rotationStart, 1.)));
//1.8---3.
l1p.x = mix(1500., 200., expEzingIn(scene(t, rotationStart, 1.)));
l2p.x = mix(-1500., -200., expEzingIn(scene(t, rotationStart, 1.5)));
enableL1 = t > rotationStart + .5;
enableL2 = t > rotationStart + .5;
float lineStart = rotationStart + 1.5;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, lineStart, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, lineStart, 1.)));
float lpRotateAngle1 = mix(0., PI_2, circEzingInOut(scene(t, lineStart, 1.)));
l3p.x = mix(-1500., -200., expEzingIn(scene(t, lineStart, 1.)));
enableL3 = t > lineStart;
float rotateStart2 = lineStart + 1.1;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart2, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart2, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart2, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart2, 1.)));
l4p.y = mix(-1500., -200., expEzingIn(scene(t, rotateStart2, 1.)));
enableL4 = t > rotateStart2;
float rotateStart3 = rotateStart2 + 1.1;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart3, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart3, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart3, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart3, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart3, 1.)));
float lpRotateAngle2 = mix(0., PI_2, circEzingInOut(scene(t, rotateStart3, 1.)));
float rotateStart4 = rotateStart3 + 1.3;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart4, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart4, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart4, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart4, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart4, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart4, 1.)));
scaleFactor += mix(0., -600., circEzingInOut(scene(t, rotateStart4, 1.)));
float rotateStart5 = rotateStart4 + 1.1;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart5, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart5, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart5, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart5, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart5, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart5, 1.)));
float rotateStart6 = rotateStart5 + 1.3;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart6, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart6, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart6, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart6, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart6, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart6, 1.)));
float rotateStart7 = rotateStart6 + 1.3;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart7, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart7, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart7, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart7, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart7, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart7, 1.)));
float rotateStart8 = rotateStart7 + 1.3;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart8, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart8, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart8, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart8, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart8, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart8, 1.)));
float rotateStart9 = rotateStart8 + 1.3;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart9, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart9, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart9, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart9, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart9, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart9, 1.)));
float rotateStart10 = rotateStart9 + 1.2;
l1Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart10, 1.)));
l2Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart10, 1.)));
l3Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart10, 1.)));
l4Angle += mix(0., PI_2 , circEzingInOut(scene(t, rotateStart10, 1.)));
lpRotateAngle1 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart10, 1.)));
lpRotateAngle2 += mix(0., PI_2, circEzingInOut(scene(t, rotateStart10, 1.)));
float circleStart = rotateStart5;
float deformR = 100.;
c1.z += mix(0., deformR, expEzingOut(scene(t, rotateStart5, 1.)));
c1.z += mix(0., -deformR, expEzingOut(scene(t, rotateStart6, 1.)));
//c2.z += mix(0., deformR, expEzingOut(scene(t, circleStart+.5, 1.)));
//c2.z += mix(0., -deformR, expEzingOut(scene(t, circleStart+.5 +1., 1.)));
c3.z += mix(0., deformR, expEzingOut(scene(t, rotateStart6, 1.)));
c3.z += mix(0., -deformR, expEzingOut(scene(t, rotateStart7, 1.)));
//c4.z += mix(0., deformR, expEzingOut(scene(t, circleStart+1.5, 1.)));
//c4.z += mix(0., -deformR, expEzingOut(scene(t, circleStart+1.5+1., 1.)));
c5.z += mix(0., 50., circEzingInOut(scene(t, rotateStart7, 1.)));
scaleFactor += mix(0., -300., circEzingInOut(scene(t, rotateStart7, 1.)));
scaleFactor /= mix(1., 4., circEzingInOut(scene(t, rotateStart8, 1.)));
scaleFactor /= mix(1., 4., circEzingInOut(scene(t, rotateStart9, 1.)));
scaleFactor /= mix(1., 4., circEzingInOut(scene(t, rotateStart10, 1.)));
float endingStart = rotateStart10 + 1.3;
if(t >= endingStart){
float rotateStart11 = endingStart;
l1Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart11, 1.)));
l2Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart11, 1.)));
l3Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart11, 1.)));
l4Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart11, 1.)));
lpRotateAngle1 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart11, 1.)));
lpRotateAngle2 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart11, 1.)));
float rotateStart12 = rotateStart11 + 1.3;
l1Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart12, 1.)));
l2Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart12, 1.)));
l3Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart12, 1.)));
l4Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart12, 1.)));
lpRotateAngle1 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart12, 1.)));
lpRotateAngle2 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart12, 1.)));
float rotateStart13 = rotateStart12+1.3;
l1Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart13, 1.)));
l2Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart13, 1.)));
l3Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart13, 1.)));
l4Angle -= mix(0., PI_2 , circEzingInOut(scene(t, rotateStart13, 1.)));
lpRotateAngle1 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart13, 1.)));
lpRotateAngle2 -= mix(0., PI_2, circEzingInOut(scene(t, rotateStart13, 1.)));
float endingTime = 1.;
c5.z = mix(50., 0., circEzingInOut(scene(t, rotateStart12, endingTime)));
l1p.x = mix(200., 5000., circEzingIn(scene(t, rotateStart13, endingTime)));
l2p.x = mix(-200., -5000., circEzingIn(scene(t, rotateStart13, endingTime)));
l3p.y = mix(0., -5000., circEzingIn(scene(t, rotateStart13, endingTime)));
l4p.y = mix(-200., -5000., circEzingIn(scene(t, rotateStart13, endingTime)));
c1.z = mix(R, 0., circEzingInOut(scene(t, rotateStart13, endingTime)));
c2.z = mix(R, 0., circEzingInOut(scene(t, rotateStart13, endingTime)));
c3.z = mix(R, 0., circEzingInOut(scene(t, rotateStart13, endingTime)));
c4.z = mix(R, 0., circEzingInOut(scene(t, rotateStart13, endingTime)));
theta += mix(0., -PI_2, circEzingInOut(scene(t, rotateStart13, 1.)));
scaleFactor *= mix(1., 650., circEzingInOut(scene(t, endingStart, 1.)));
}
mat2 lpRotate1 = getRotationMat2(lpRotateAngle1);
l1m = getRotationMat2(l1Angle);
l1mInv = getRotationMat2(-l1Angle);
l2m = getRotationMat2(l2Angle);
l2mInv = getRotationMat2(-l2Angle);
l3m = getRotationMat2(l3Angle);
l3mInv = getRotationMat2(-l3Angle);
l4m = getRotationMat2(l4Angle);
l4mInv = getRotationMat2(-l4Angle);
l1p = lpRotate1 * l1p;
l2p = lpRotate1 * l2p;
l3p = lpRotate1 * l3p;
mat2 lpRotate2 = getRotationMat2(lpRotateAngle2);
l4p = lpRotate2 * l4p;
mat2 m = getRotationMat2(theta);
for(float i = 0. ; i < SAMPLE_NUM ; i++){
vec2 position = ( (gl_FragCoord.xy + rand2n(gl_FragCoord.xy, i)) / resolution.yy ) - vec2(ratio, 0.5);
position = position * scaleFactor;
position = m * position;
float loopNum = IIS(position);
if(loopNum > 0.){
sum += hsv2rgb(vec3(0.01 + 0.05 * (loopNum-1.),1.0,1.0));
}
}
gl_FragColor = vec4(gammaCorrect(sum/SAMPLE_NUM), 1.);
}