WebGL 中的透明纹理行为 [英] Transparent textures behaviour in WebGL

查看:41
本文介绍了WebGL 中的透明纹理行为的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

环境:WebGL、Chrome.使用透明 png 作为模型的纹理时,我有以下行为:

Environment: WebGL, Chrome. I have the following behavior when using transparent png's as textures for models:

  1. 图像 A - 树将建筑物隐藏在它后面,我看到了世界框纹理.它也会隐藏自己(后面的分支不可见)
  2. 同时 - 图像 B - 工作正常,窗口是透明的,我看到后面是什么

A:B:

两张截图都是在同一场景中同时从不同的相机位置制作的.纹理由相同的算法生成.

Both screenshots were made on same the scene at the same time from different camera positions. Textures are produced by the same algorithm.

我无法理解窗口和分支透明度之间的区别.我的主要问题是 - 如何修复树枝以便不隐藏它们后面的物体?着色器代码为:

I can't understand what's the difference between window and branches transparency. My main question is - how to fix the branches so as to not hide the objects behind them? Shader code is:

gl_FragColor = vec4(textureColor.rgb * vLightWeighting, textureColor.a);

我玩过启用/禁用混合和depth_test,有时会得到想要的结果,但不确定这是否是做事的正确方法.

I played with enable/disable blending and depth_test, sometimes getting the desired results, but not sure if it's the proper way to do things.

推荐答案

您遇到了深度缓冲问题,这与您的着色器或混合模式无关.

You're running into depth buffer issues, it has nothing to do with your shader or blend modes.

发生的情况是,您渲染透明几何体的顺序会影响您在其后面渲染的能力.这是因为深度缓冲区没有透明或不透明的概念.结果,即使它们在视觉上对场景没有贡献,这些透明像素无论如何都会将自己写入深度缓冲区,之后您在它们后面绘制的任何像素都将被丢弃,因为它们不可见".但是,如果您先在透明对象后面绘制几何图形,它会正确显示,因为它会在透明深度设置到位以丢弃它之前写入框架.

What's happening is that the order that you render your transparent geometry in is affecting your ability to render behind it. This is because the depth buffer has no concept of transparent or non-transparent. As a result, even though they don't visually contribute to the scene those transparent pixels write themselves into the depth buffer anyway, and after that any pixels that you draw behind them will be discard because they're "not visible". If you drew the geometry behind the transparent object first, though, it would show correctly because it gets written into the frame before the transparent depth is put in place to discard it.

即使是大型商业游戏引擎在某种程度上仍然难以解决这个问题,所以不要因为它造成一些混乱而感到难过.:)

This is something that even large commercial game engines still struggle with to some degree, so don't feel bad about it causing some confusion. :)

这个问题没有完美的解决方案",但它真正归结为试图像这样构建你的场景:

There's no "perfect solution" to this problem, but what it really boils down to is trying to structure your scene like so:

  1. 渲染按状态(着色器/纹理/等)排序的任何不透明几何体
  2. 接下来渲染任何透明几何体.如果可能的话,按深度对它们进行排序,以便您首先绘制离相机最远的那个.

简单地通过标记透明的几何体位并在其他所有事情之后渲染它们,您将解决此问题的 90%,但对于重叠的透明对象,问题可能仍然存在.这对您来说可能不是问题,具体取决于您的场景,但如果它仍然导致伪影,您需要在绘制之前按深度对透明对象进行排序.

Simply by flagging the bits of geometry that are transparent and rendering them after everything else you'll solve 90% of this problem, but the issue may still remain for overlapping transparent objects. That may not be an issue for you, depending on your scene, but if it's still causing artifacts you'll need to sort transparent objects by depth before you draw.

这篇关于WebGL 中的透明纹理行为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆