上图提供两种方式溶解显示
上面一排是根据现实的图案红色通道也就是r值进行溶解
下面一排提供额外的溶解纹理
可以通过简单更改呈现多种溶解图案
代码仓库 gitee
b站账号:https://space.bilibili.com/374230437
interface IMapPath {
map: string;
dissolve?: string;
}
export class Dissolve {
material: ShaderMaterial | MeshStandardMaterial;
mesh: Mesh<BufferGeometry, typeof this.material>;
constructor(private mapPaths: IMapPath, private gui: ThreeHelper["gui"]) {
this.material = this.CustomMaterial();
this.mesh = new Mesh(new IcosahedronGeometry(3, 5), this.material);
// this.mesh = new Mesh(new SphereGeometry(3, 36, 36), this.material);
// this.mesh = new Mesh(new BoxGeometry(3, 3, 3), this.material);
gui?.add(<any>this.material.uniforms.iProgress, "value", 0, 1);
this.mesh.onAfterRender = () => {
(this.material as ShaderMaterial).uniforms.iProgress.value += 0.01;
};
}
CustomMaterial(): ShaderMaterial {
const material = new ShaderMaterial({
transparent: true,
uniforms: {
iTime: { value: 0 },
iProgress: { value: 0 },
map: {
value: new TextureLoader().load(this.mapPaths.map),
},
dissolveMap: {
value:
this.mapPaths.dissolve &&
new TextureLoader().load(this.mapPaths.dissolve),
},
},
vertexShader: `
varying vec2 vUv;
void main() {
vUv = uv;
vec4 modelViewPosition = modelViewMatrix * vec4(position, 1.0);
gl_Position = projectionMatrix * modelViewPosition;
}`,
fragmentShader: `
uniform float iTime;
varying vec2 vUv;
uniform float iProgress;
uniform sampler2D map;
uniform sampler2D dissolveMap;
void main( ) {
vec3 diffuse = texture(map,vUv).rgb;
${
this.mapPaths.dissolve
? "vec3 dissolve = texture(dissolveMap,vUv).rgb;"
: "vec3 dissolve = diffuse;"
}
float t = iProgress;
float edge_width = mix(0.0,0.5, t);
float edge = smoothstep(dissolve.r - edge_width, dissolve.r, t);
vec4 edgeColor = vec4(0.6,0.2,0.1, 1.0);
diffuse += edgeColor.rgb * (1.0 - edge);
gl_FragColor = vec4(diffuse,edge);
}
`,
});
return material;
}
}