拆分纹理的 R、G 和 B 通道 - 对三通道中的一部分应用线性过滤。js/WebGL/Shaders

Split up R, G and B channels of texture – apply linear filtering to a subset of them in Three.js/WebGL/Shaders

我正在使用从服务器检索的高度纹理。它对 RGB 通道内每个像素的整体高度值进行编码。要获得每个像素的高度值,R 通道乘以 65536.0,G 乘以 256.0,然后 height = R + G + B.

由于这种分裂,RG 存在不连续性(参见下面的 G 通道图像,其中 100% 白色区域与 100% 黑色区域)它们需要,因为另一部分(R 或 B)接管了。这就是为什么我不能线性过滤纹理。但是,我想对 B 通道进行线性过滤,因为它包含最高的 frequencies/smallest 高度偏差 - 以获得光滑的表面。

是否可以在内部拆分纹理(例如,在着色器中,但我不介意发生这种情况的位置),以便只有它的 B 通道被线性过滤,而 R, B 频道留在最近的邻居?在所有组件再次添加在一起之前?如果是这样,如何以有效的方式做到这一点?

WebGL 纹理过滤适用于整个纹理,而不是每个单独的通道。但是你可以做的是 clone the texture,并在着色器中分别对它们进行采样。

var texture2 = texture1.clone();
texture1.magFilter = THREE.NearestFilter;
texture2.magFilter = THREE.LinearFilter; // This is the default

然后在你的着色器中:

vec2 sampleRG = texture2D(texture1, vUv).rg;
float sampleB = texture2D(texture2, vUv).b;

这有点额外开销,但您的 GPU 无法处理。

请注意,我一直看到每个通道的值范围是 0 到 255,而不是 256。您确定不想乘以 255 吗?