#define PI 3.14159265358979323
#define T .05
//#define ZOOM 200.
#define ZOOM (0.35*iResolution.y)

#define tt ((iTime)/3.)


#define hue(a) (.6 + .6*cos(2.*PI*a + vec3(0,-2.*PI/3.,2.*PI/3.)))
#define cmul(z1, z2) (mat2(z1, -z1.y, z1.x)*z2)
#define cdiv(z1, z2) (z1*mat2(z2, -z2.y, z2.x)/dot(z2, z2))
#define clog(z) vec2(0.5*log(dot(z,z)), atan(z.y, z.x))

vec2 cexp(vec2 z, vec2 c)
{
    float argz, m, a;
    float lnz = dot(z,z);
    
    if (lnz == 0.) return vec2(0., 0.);
    else {
        lnz = 0.5*log(lnz);
        argz = atan(z.y, z.x);
        
        m = exp(c.x*lnz - c.y*argz);
        a = c.x*argz + c.y*lnz;
        
        return m*vec2(cos(a), sin(a));
    }
}


vec3 hrgb(vec2 w)
{
    
    float m = length(w);
    float a = (PI + atan(w.y, w.x))/(2.0*PI);
    
    m = log(1. + 100.*m);

    float mm = fract(m);
    float p = fract(mod(a, 1.0/16.0));

    vec3 c;

    c.r =  0.5 - 0.5*sin(2.0*PI*a - PI/2.0);
    c.g = (0.5 + 0.5*sin(2.0*PI*a*1.5 - PI/2.0)) * float(a < 0.66);
    c.b = (0.5 + 0.5*sin(2.0*PI*a*1.5 + PI/2.0)) * float(a > 0.33);
    
    //c = 0.5*(c + hue(a));
    
    c -= 0.3*mm + 2.*p;
    
    
    //if (//length(w) + T/2. > 1. &&
     //   (fract(w.x) < T || fract(-w.x) < T ||
      //   fract(w.y) < T || fract(-w.y) < T)) c -= 0.4;
    
    return c;
}

vec2 f(vec2 z, int n)
{
    vec2 w;

    //w = cexp( vec2(exp(1.), 0.), z );
    
    //w = z - vec2(0.5, 0.);
    //w = cdiv( w, (z - vec2(-0.35,-0.35)) );
    //w = cdiv( w, (z - vec2(-0.35, 0.35)) );
    
    //w = cmul( (z - vec2(-0.35,-0.35)),
    //          (z - vec2(-0.35, 0.35)) );
    //w = cdiv( w, (z - vec2(0.5, 0.)));
    
    w = z;//vec2(0., 0.);
    
    for (int i=0; i<n; i++) {
        w = cmul(w, w);
        //w = cexp(w, vec2(2., 0.));
        w += vec2(0.35, 0.0);
    }
    
    w = cexp(w, vec2(1. + fract(tt), 0.));
    w += vec2(0.35, 0.0)*fract(tt);
    
    return w;
}

void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
    vec2 z, w, w1, w2, w3, w4;
    int n = 5;
    
    z = fragCoord - iResolution.xy/2.;

    //if (iMouse.xy != vec2(0., 0.)) //to center at origin
    //    z -= iMouse.xy - iResolution.xy/2.;
    
    
    z /= ZOOM;
    z -= vec2(0., 0.);
    w = f(z, int(1. + tt)%20);
    fragColor = vec4(hrgb(w), 1.0);
    
    /*
    z -= vec2(0.5, 0.)*ZOOM;
    
    w  = f( z/ZOOM, n );
    w1 = f( (z + vec2(-.25,-.25))/ZOOM, n );
    w2 = f( (z + vec2(-.25, .25))/ZOOM, n );
    w3 = f( (z + vec2( .25,-.25))/ZOOM, n );
    w4 = f( (z + vec2( .25, .25))/ZOOM, n );
    
    
    fragColor = vec4(0.2*(hrgb(w) +
                          hrgb(w1) + hrgb(w2) + 
                          hrgb(w3) + hrgb(w4)), 1.0);*/
}
