Skip to content

Instantly share code, notes, and snippets.

@wonglok
Created July 29, 2020 04:39
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wonglok/3b9033a250926b52771e92c2cbcbbc35 to your computer and use it in GitHub Desktop.
Save wonglok/3b9033a250926b52771e92c2cbcbbc35 to your computer and use it in GitHub Desktop.
FastFlame by Wong Lok @wonglok831 on IG
// import { PlaneBufferGeometry } from 'three/build/three.module'
import { ShaderMaterial, PlaneBufferGeometry, Mesh } from 'three'
let glsl = v => v[0]
export class FastFlame {
constructor ({ onLoop, onResize, onClean, resX = 128, resY = 128 }) {
this.onLoop = onLoop
this.onClean = onClean
this.onResize = onResize
this.out = {}
this.works = []
this.addWork = v => this.works.push(v)
let displayMaterial = new ShaderMaterial({
transparent: true,
wireframe: true,
uniforms: {
textureOutput: { value: null },
textureSimulation: { value: null },
time: { value: null }
},
vertexShader: this.getDisplayVert(),
fragmentShader: this.getDisplayFrag()
})
this.onResize(() => {
let dpi = 1 / 1.5
let rect = {
width: resX,
height: resY
}
displayMaterial.defines.resolution = `vec2(${(rect.width * dpi).toFixed(1)},${(rect.height * dpi).toFixed(1)})`
})
// let makeGeo = () => {
// let getUVandPosition = () => {
// let newArr = []
// var na = 0
// let nn = resX * resY
// var idx = 0
// for (var j = 0; j < resY; j++) {
// for (var i = 0; i < resX; i++) {
// newArr[na + 0] = i / resX
// newArr[na + 1] = j / resY
// newArr[na + 2] = idx / nn
// na += 3
// idx++
// }
// }
// // console.log('total points', idx)
// return new Float32Array(newArr)
// }
// let makePosition = () => {
// let newArr = []
// var na = 0
// // let nn = resX * resY
// // var idx = 0
// for (var j = 0; j < resY; j++) {
// for (var i = 0; i < resX; i++) {
// newArr[na + 0] = ((i / resX) - 0.5) * 256
// newArr[na + 1] = ((j / resY) - 0.5) * 256
// newArr[na + 2] = 0
// na += 3
// // idx++
// }
// }
// // console.log('total points', idx)
// return new Float32Array(newArr)
// }
// var geometry = new BufferGeometry()
// geometry.setAttribute('position', new BufferAttribute(makePosition(), 3))
// geometry.setAttribute('uvv', new BufferAttribute(getUVandPosition(), 3))
// return geometry
// }
let geometry = new PlaneBufferGeometry(400, 400, resX / 4, resY / 4)
this.addWork(() => {
let time = window.performance.now() * 0.001
displayMaterial.uniforms.time.value = time * 0.43
})
this.onLoop(() => {
this.works.forEach((v) => { v() })
})
this.out.mesh = new Mesh(geometry, displayMaterial)
}
getDisplayVert () {
return glsl`
uniform float dpi;
varying vec4 posData;
// attribute vec3 uvv;
uniform float time;
const mat2 m = mat2( 0.80, 0.60, -0.60, 0.80 );
float noise( in vec2 p ) {
return sin(p.x)*sin(p.y);
}
float fbm4( vec2 p ) {
float f = 0.0;
f += 0.5000 * noise( p ); p = m * p * 2.02;
f += 0.2500 * noise( p ); p = m * p * 2.03;
f += 0.1250 * noise( p ); p = m * p * 2.01;
f += 0.0625 * noise( p );
return f / 0.9375;
}
float fbm6( vec2 p ) {
float f = 0.0;
f += 0.500000*(0.5+0.5*noise( p )); p = m*p*2.02;
f += 0.250000*(0.5+0.5*noise( p )); p = m*p*2.03;
f += 0.125000*(0.5+0.5*noise( p )); p = m*p*2.01;
f += 0.062500*(0.5+0.5*noise( p )); p = m*p*2.04;
f += 0.031250*(0.5+0.5*noise( p )); p = m*p*2.01;
f += 0.015625*(0.5+0.5*noise( p ));
return f/0.96875;
}
float pattern (vec2 p) {
float vout = fbm4( p + time + fbm6( p + fbm4( p + time )) );
return abs(vout);
}
void main (void) {
vec4 outputData = vec4(0.0);
float dynamo = 200.0 * (0.5 - 1.5 * pattern(uv.xy + cos(0.1 + time * 0.3)));
outputData.x = mix(position.x, dynamo, 0.9);
outputData.y = mix(position.y, dynamo, 0.05);
outputData.z = mix(position.z, dynamo, 0.05);
gl_Position = projectionMatrix * modelViewMatrix * vec4(outputData.xyz, 1.0);
posData = gl_Position;
gl_PointSize = 3.5;
}
`
}
getDisplayFrag () {
return glsl`
uniform float time;
// varying vec4 simData;
// varying vec4 outData;
varying vec4 posData;
const mat2 m = mat2( 0.80, 0.60, -0.60, 0.80 );
float noise( in vec2 p ) {
return sin(p.x)*sin(p.y);
}
float fbm4( vec2 p )
{
float f = 0.0;
f += 0.5000 * noise( p ); p = m * p * 2.02;
f += 0.2500 * noise( p ); p = m * p * 2.03;
f += 0.1250 * noise( p ); p = m * p * 2.01;
f += 0.0625 * noise( p );
return f / 0.9375;
}
float fbm6( vec2 p )
{
float f = 0.0;
f += 0.500000*(0.5+0.5*noise( p )); p = m*p*2.02;
f += 0.250000*(0.5+0.5*noise( p )); p = m*p*2.03;
f += 0.125000*(0.5+0.5*noise( p )); p = m*p*2.01;
f += 0.062500*(0.5+0.5*noise( p )); p = m*p*2.04;
f += 0.031250*(0.5+0.5*noise( p )); p = m*p*2.01;
f += 0.015625*(0.5+0.5*noise( p ));
return f/0.96875;
}
float pattern (vec2 p) {
float vout = fbm4( p + time + fbm6( p + fbm4( p + time )) );
return abs(vout);
}
void main (void) {
// vec2 pt = gl_FragCoord.xy / resolution.xy;
float rx = 0.9 - pattern((posData.xy / resolution.xy) + cos(0.1 + time * 0.3));
float ry = 0.9 - pattern((posData.xy / resolution.xy) + cos(0.2 + time * 0.3));
float rz = 0.9 - pattern((posData.xy / resolution.xy) + cos(0.3 + time * 0.3));
gl_FragColor = vec4(rx, ry, rz, 0.5);
// vec2 hpt = gl_PointCoord.xy - vec2(0.5, 0.5);
// if (length(hpt) < 0.5) {
// } else {
// discard;
// }
}
`
}
}
@wonglok
Copy link
Author

wonglok commented Jul 29, 2020

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment