是否有可能在Three.js中的同一面上将多个纹理叠加在一起,以便在webGL中加速alpha加速?
将纹理(或应该)应用于同一个面,以便底部纹理(纹理1)没有alpha通道,并且上面的纹理在下面的图像示例中以纹理2的方式进行alpha通道。
这种混合可以使用HTML5 Canvas作为前置步骤来实现,但由于纹理位图可能很大,我更喜欢跳过Canvas混合操作。
我通过创建网格的副本并对每个网格应用一个纹理进行测试,并使其他网格透明并移动了一点,这几乎成功,但有一些闪烁,因为对象不能完全在同一位置,纹理之间有一些空间,这不是正确的效果。他们看起来应该像是混合在一起。 Photoshop(如下图所示)。
答案 0 :(得分:58)
使用ShaderMaterial并将两个纹理设置为制服,然后在着色器中混合它们。
我做了这个例子:http://abstract-algorithm.com/three_sh/这真的应该足够了。
所以,你制作ShaderMaterial:
var vertShader = document.getElementById('vertex_shh').innerHTML;
var fragShader = document.getElementById('fragment_shh').innerHTML;
var attributes = {}; // custom attributes
var uniforms = { // custom uniforms (your textures)
tOne: { type: "t", value: THREE.ImageUtils.loadTexture( "cover.png" ) },
tSec: { type: "t", value: THREE.ImageUtils.loadTexture( "grass.jpg" ) }
};
var material_shh = new THREE.ShaderMaterial({
uniforms: uniforms,
attributes: attributes,
vertexShader: vertShader,
fragmentShader: fragShader
});
使用该材质创建网格:
var me = new THREE.Mesh( new THREE.CubeGeometry(80,80,80), material_shh );
您可以放置最简单的顶点着色器:
varying vec2 vUv;
void main()
{
vUv = uv;
vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );
gl_Position = projectionMatrix * mvPosition;
}
实际进行混合的片段着色器:
#ifdef GL_ES
precision highp float;
#endif
uniform sampler2D tOne;
uniform sampler2D tSec;
varying vec2 vUv;
void main(void)
{
vec3 c;
vec4 Ca = texture2D(tOne, vUv);
vec4 Cb = texture2D(tSec, vUv);
c = Ca.rgb * Ca.a + Cb.rgb * Cb.a * (1.0 - Ca.a); // blending equation
gl_FragColor= vec4(c, 1.0);
}
如果你需要混合更多的纹理,你可以使用相同的方程进行多次混合。
所以这是结果: