简体   繁体   中英

Explanation of WebGL code - why does it work that way

I'm trying to make a lightbulb that glows a little and then it becomes less intense. Also at the edges to be a little bit dimmer. I found the a code, that I think creates the effect I want to create, but I don't seem to understand it very well. Here's the code:

mat2 rotate2d(float angle){
return mat2(cos(angle),-sin(angle),
            sin(angle),cos(angle));
    }

float variation(vec2 v1, vec2 v2, float strength, float speed) {
    return sin(
        dot(normalize(v1), normalize(v2)) * strength + iGlobalTime * speed
    ) / 100.0;
}

vec3 paintCircle (vec2 uv, vec2 center, float rad, float width) {

    vec2 diff = center-uv;
    float len = length(diff);

    len += variation(diff, vec2(0.0, 1.0), 5.0, 2.0);
    len -= variation(diff, vec2(1.0, 0.0), 5.0, 2.0);

    float circle = smoothstep(rad-width, rad, len) - smoothstep(rad, rad+width, len);
    return vec3(circle);
}


void mainImage( out vec4 fragColor, in vec2 fragCoord )
{
    vec2 uv = fragCoord.xy / iResolution.xy;
    uv.x *= 1.5;
    uv.x -= 0.25;

    vec3 color;
    float radius = 0.35;
    vec2 center = vec2(0.5);


    //paint color circle
    color = paintCircle(uv, center, radius, 0.1);

    //color with gradient
    vec2 v = rotate2d(iGlobalTime) * uv;
    color *= vec3(v.x, v.y, 0.7-v.y*v.x);

    //paint white circle
    color += paintCircle(uv, center, radius, 0.01);


    fragColor = vec4(color, 1.0);
}

I don't understand why we need the dot product of the normalized vectors and how it's chosen exacly:

len += variation(diff, vec2(0.0, 1.0), 5.0, 2.0);
len -= variation(diff, vec2(1.0, 0.0), 5.0, 2.0);

I mean - why is there first adding, then subtraction? Then why is that:

vec2 uv = fragCoord.xy / iResolution.xy;
uv.x *= 1.5;
uv.x -= 0.25;

and how does this vec2 v = rotate2d(iGlobalTime) * uv; color *= vec3(vx, vy, 0.7-vy*vx); vec2 v = rotate2d(iGlobalTime) * uv; color *= vec3(vx, vy, 0.7-vy*vx);

make the color gradient? Here's a link of the code if someone prefers watching it there and what it does: https://www.shadertoy.com/view/ltBXRc . I'm obviously not very good at geometry. If someone could help me, I'd appreciate it :)

If we wanted to draw a perfect circle, we would simply plot all points lying a certain distance from the center of the scene. Speaking procedurally, we would start from the center, pick any random direction, go some distance r in that direction, and plot a point. Then return to the center, pick some other direction, go the same distance r , and plot another point. And so on, until we have a smooth circle: r = 1

To plot a distorted circle we can vary the distance r depending on the direction we're facing. If we express the direction as an angle in radians ( theta ), then r will be some function of that angle. What function exactly? Let's try something simple first: r = theta

Not quiet what we want, it should be more like a circle (r = 1), but with a bit of waviness (r = 1 + waviness). The simplest wavy function is sin(x) . Let's try to add it: r = 1 + 0.1 * sin(5 * theta)

By changing the numbers we can manipulate the amplitude and the frequency of the waves. But there's too much symmetry, to break it we need something more complex than a sine wave.

How about this monster sin(5 * sin(x)) - sin(5 * cos(x))

Let's add it to the circle r = 1 + 0.1 * sin(5 * sin(theta)) - 0.1 * sin(5 * cos(theta))

Looks pretty good to me.

The shader performs exactly this distortion, but in a different manner. Taking a dot product with a standard basis vector simply gives you the X or Y coordinate of the vector. We can rewrite that bit as:

len += 0.02 * sin(normalize(diff).y * 5.0 + 2.0 * iGlobalTime);
len -= 0.02 * sin(normalize(diff).x * 5.0 + 2.0 * iGlobalTime);

X and Y coordinates of a normalized vector are just sin and cos of an angle represented by that vector. So, normalize(diff).y gives you the sine of an angle, and normalize(diff).x gives you the cosine.

Hopefully this clears things up a bit.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM