正确渲染纹理的透明区域

我正在渲染一个包含部分透明纹理的分支网格的树。

如果我使用AlphaTestEffect来渲染它,并将ReferenceAlpha设置为低,我会得到这个。

在这里输入图像描述

我想用BasicEffect渲染树,但是,这是我得到的结果。 BlendState被设置为NonPremultiplied。

我甚至不知道我在看什么。 看起来最近的分支的透明区域覆盖了它后面的那个(而不是树干)。 如果我将DepthState设置为DepthRead,那么所有的分支都是乱序的。

究竟是什么问题呢?

在这里输入图像描述

问题是你不要在这里排列你的多边形,因此不能正确使用alpha混合。 解决这个问题的常用方法是:

  • Alphatesting:丢弃低于某个alpha阈值的像素,以便获得适当的Z缓冲,Z丢弃。 从近距离看,这个结果是硬边缘。
  • 阿尔法覆盖:你必须建立一个混合状态,支持这种技术。 它基于多重采样抗锯齿,因此当您将其打开到更高级别时,您可以获得更好的结果。
  • 两遍渲染:首先渲染alphatesting的所有东西以获得正确的sorting,然后在第二遍渲染中渲染所有与alpha混合和Z缓冲写入closures的东西,但丢弃高于某个alpha级别的像素。 这样你只渲染透明几何的平滑轮廓,这会让你sorting错误,但用户不会识别它(可能)。

也有一些先进的技术(顺序独立的透明度),由于其性能饥饿性质,它们并不真正用于实时应用程序。

如果您正在使用渲染目标而不是直接渲染到屏幕上,请确保使用渲染目标的最完整的构造函数重载来构建它,以便您可以指示它创建深度缓冲区。

除此之外,你应该把你的De​​pthStencilState设置为默认不读取,因为这意味着你的分支只能进行深度testing,而不是已经在深度缓冲区中,而不是对自己。

BlendState应该设置为AlphaBlend。 这是我认为唯一的select,支持半透明纹理。 NonPreMultiplied只能用于没有使用XNA内容管道导入的内容。

请注意,JánosTuránszki是正确的,我只是在这里列出了如何在XNA中完成。