我们可以在单个gl.drawElements()调用中绘制多个纹理吗?

时间:2014-05-31 01:39:26

标签: opengl-es opengl-es-2.0 webgl

在WebGL中,我们可以在单个gl.drawElements()调用中绘制多个纹理吗?如果是的话怎么样?

gl.TEXTURE0gl.TEXTURE31有什么用处,我的意思是,当使用多个纹理单位时会出现什么情况?

我试图在单个drawElements()调用中为每一面绘制一个具有6种不同纹理的立方体。可能吗?是的,怎么样?

2 个答案:

答案 0 :(得分:1)

多个纹理单元用于多重纹理,例如当您将污垢和草纹理混合在一起以制作脏草时。看这个例子:

http://www.clockworkcoders.com/oglsl/tutorial8.htm

对于你所谈论的内容(完全独立的纹理),使用纹理图集可能更有意义(特别是在嵌入式系统上)。见第3.9.4节:

http://imgtec.eetrend.com/sites/imgtec.eetrend.com/files/download/201402/1462-2116-powervrdexingnengjianyi.pdf

答案 1 :(得分:1)

要使用多个纹理,可以将不同的纹理绑定到不同的纹理单元,并使用着色器中的多个采样器引用它们

这是一个使用2个纹理的着色器

 uniform sampler2D u_texture1;
 uniform sampler2D u_texture2;
 varying vec2 vtexcoords1;
 varying vec2 vtexcoords2;

 void main() {
   vec4 color1 = texture2D(u_texture1, v_texcoords1);
   vec4 color2 = texture2D(u_texture2, v_texcoords2);
   gl_FragColor = color1 * color2;  // multiply the colors.
 }

然后,您需要将2个纹理绑定到2个纹理单元

 // bind a texture to texture unit0
 gl.activeTexture(gl.TEXTURE0);
 gl.bindTexture(gl.TEXTURE_2D, someTexture);

 // bind a texture to texture unit1
 gl.activeTexture(gl.TEXTURE1);
 gl.bindTexture(gl.TEXTURE_2D, someOtherTexture);

你需要告诉着色器使用哪个纹理单元

 // -- at init time
 var texture1location = gl.getUniformLocation(program, "u_texture1");
 var texture2location = gl.getUniformLocation(program, "u_texture2");

 // -- at draw time

 // tell the shader to use texture units 0 and 1
 gl.uniform1i(texture1location, 0);
 gl.uniform1i(texture2location, 1);

但是,这通常不是如何用6幅图像纹理立方体。大多数游戏通过将所有6个图像放在单个纹理(see end of this article)中来构造具有6个图像的立方体。大多数3D建模程序通过不制作立方体而将6个图像放在立方体上,而是制作6个平面,每个平面对齐以制作立方体的面。换句话说,6个单独的平面模型而不是一个立方体模型。这样它就变得简单了。您只需使用绘制1个纹理的着色器,并在绘制立方体的每个平面时使用不同的纹理。

在游戏风格案例中,1个立方体+ 1个纹理,带有6个图像。这很快,因为只有1次平局调用。在3D建模包中,它有6个平面,每个平面有1个纹理(总共6个),所以6个绘制调用,但它很灵活,因为每个平面可以使用不同的图像,而不必构建包含所有6个图像的新纹理。

您选择哪种方式取决于您。