GLSL:使用2D纹理模拟3D纹理

时间:2012-10-07 20:21:35

标签: opengl-es glsl textures 3d-texture

我想出了一些使用包含图块的大2D纹理来模拟3D纹理查找的代码。 3D纹理为128x128x64,大2D纹理为1024x1024,分为64个128x128的图块。

片段着色器中的查找代码如下所示:

#extension GL_EXT_gpu_shader4 : enable

varying float LightIntensity;
varying vec3 pos;

uniform sampler2D noisef;
vec4 flat_texture3D()
{
    vec3 p = pos;
    vec2 inimg = p.xy;

    int d = int(p.z*128.0);
    float ix = (d % 8); 
    float iy = (d / 8);
    vec2 oc = inimg + vec2(ix, iy);
    oc *= 0.125;

    return texture2D(noisef, oc);
}

void main (void)
{
    vec4 noisevec = flat_texture3D();
    gl_FragColor = noisevec;
}

平铺逻辑似乎工作正常,此代码只有一个问题。它看起来像这样:

what it looks like

体素层之间存在奇怪的1到2像素宽的条纹。 当d发生变化时,条纹就会出现在边框处 我一直在研究这个问题已经有2天了,但仍然不知道这里发生了什么。

1 个答案:

答案 0 :(得分:3)

这看起来像纹理过滤器问题。想一想:当你接近边界时,双线性滤波器会考虑相邻的纹素,在你的情况下:来自另一个“深度层”。

为避免这种情况,您可以夹住纹理坐标,使它们永远不会位于图块的矩形最外面的纹理中心之外(类似于GL_CLAMP_TO_EDGE,但基于每个图块)。但是你应该意识到使用mipmapping时问题会变得更糟。您还应该知道,目前您无法在z方向上进行过滤,就像真正的3D纹理一样。当然,您可以在着色器中手动模拟它。

但是真的:为什么不只是使用3D纹理? hw可以为你做所有这些,而且开销更少......