info.g *= 0.995;
/* move the vertex along the velocity */
info.r += info.g;
gl_FragColor = info;
}
‘);
this.normalShader = new GL.Shader(vertexShader, ‘
uniform sampler2D texture;
uniform vec2 delta;
varying vec2 coord;
void main() {
/* get vertex info */
vec4 info = texture2D(texture, coord);
/* update the normal */
vec3 dx = vec3(delta.x, texture2D(texture, vec2(coord.x + delta.x, coord.y)).r – info.r, 0.0);
vec3 dy = vec3(0.0, texture2D(texture, vec2(coord.x, coord.y + delta.y)).r – info.r, delta.y);
info.ba = normalize(cross(dy, dx)).xz;
gl_FragColor = info;
}
‘);
this.sphereShader = new GL.Shader(vertexShader, ‘
uniform sampler2D texture;
uniform vec3 oldCenter;
uniform vec3 newCenter;
uniform float radius;
varying vec2 coord;
float volumeInSphere(vec3 center) {
vec3 toCenter = vec3(coord.x * 2.0 – 1.0, 0.0, coord.y * 2.0 – 1.0) – center;
float t = length(toCenter) / radius;
float dy = exp(-pow(t * 1.5, 6.0));
float ymin = min(0.0, center.y – dy);









