Directx 多重纹理-3D纹理两层之间的插值

Directx 多重纹理-3D纹理两层之间的插值,directx,textures,hlsl,texture-mapping,volume-rendering,Directx,Textures,Hlsl,Texture Mapping,Volume Rendering,我正在尝试使用3D纹理实现地形纹理,3D纹理由几层材质组成,并在材质之间进行平滑混合 也许我的插图能更好地解释这一点: 想象一下,每种颜色都是一种凉爽的地形纹理,如草、石头等。 我想将它们适当地混合,但使用当前的方法,除了我想显示的纹理之外,我还获得了请求之间的所有纹理(这似乎是合乎逻辑的,因为正如我所读到的,3D纹理被视为三维数组,而不是纹理柱)。 当前(显然是愚蠢的)方法很简单,就像饼图一样(“当前”结果是使用点插值渲染的,所需结果是手绘的): 顶点: 顶点1:Position=Vecto

我正在尝试使用3D纹理实现地形纹理,3D纹理由几层材质组成,并在材质之间进行平滑混合

也许我的插图能更好地解释这一点:

想象一下,每种颜色都是一种凉爽的地形纹理,如草、石头等。
我想将它们适当地混合,但使用当前的方法,除了我想显示的纹理之外,我还获得了请求之间的所有纹理(这似乎是合乎逻辑的,因为正如我所读到的,3D纹理被视为三维数组,而不是纹理柱)。
当前(显然是愚蠢的)方法很简单,就像饼图一样(“当前”结果是使用点插值渲染的,所需结果是手绘的):

顶点:
顶点1:Position=Vector3.Zero,UVW=Vector3.Zero

顶点2:Position=Vector3(0,1,0),UVW=Vector3(0,1,0.75f)

顶点3:Position=Vector3(0,0,1),UVW=Vector3(1,0,1)

如您所见,三角形的第一个顶点使用第一种材质(红色一种),第二个顶点使用第三种材质(蓝色一种),第三个顶点使用最后第四种材质(黄色一种)。

这是如何在像素着色器中完成的(UVW直接传递,无需更改):
float3 texColor=tex3D(ColorTextureSampler,input.UVW)
返回float4(texColor,1)
我选择的原因是我的地形结构。使用行进立方体从体素(每个体素包含材质ID)生成地形。每个顶点都是“焊接”的,因为网格非常大,我不想让每个三角形都是单独的(但如果无法使用连接的顶点解决问题,我仍然可以这样做)。
我最近有了一个想法,在每个顶点中存储三角形其他两个顶点的材质id及其混合因子(我会有一个float2 UV对,float3表示材质id,float3表示每个材质id的混合因子),但我看不到任何方法可以在不将网格分解为单个三角形的情况下实现这一点。
任何帮助都将不胜感激。我的目标是使用C#和Direct3D 9 API的SlimDX。感谢阅读。

注:如果我在本文中犯了一些错误,我很抱歉,英语不是我的母语。

可能,您的

彩色纹理采样器使用(
D3DTEXF\u POINT
)。使用
D3DTEXF_线性
D3DTEXF_各向异性
来实现所需的插值效果。 我对SlimDX 9不是很熟悉,但你已经有了这个想法

顺便说一句,很好的例子=)

更新1 结果在您的评论下面似乎适合您的代码。 看起来要想得到想要的效果,你们必须改变整体的方法。 对于您来说,这不是一个完整的解决方案,但我们是如何在普通3D地形中实现这一点的:

  • 每个顶点有1对(u,v)纹理坐标
  • 您有n个纹理要采样到(T1、T2、T3、…、Tn),这些纹理表示不同的地形层:沙、草、岩石等
  • 您总共有n个遮罩纹理通道,这些通道存储每个纹理T在其通道中的混合系数:
    R
    通道为T1保存alpha,
    G
    通道为T2,
    B
    为T3。。。等等
  • 在像素着色器中,您可以像往常一样对层纹理进行采样,并获得颜色值
    float4 val1、val2、val3
  • 然后为相应的混合系数采样遮罩纹理,并获得
    float blend1、blend2、blend3,…
  • 然后应用某种混合算法,例如简单线性插值:
例如,如果你的T1是一块草,你的地图中间有一个大的草地,你会在中间挥动一个大的红色场。< /P> 该算法有点慢,因为纹理采样较多,但实现简单,视觉效果好且最灵活。您不仅可以使用遮罩作为混合系数,还可以使用任何值:例如高度(在山峰中采集更多的雪,在山中采集岩石,在低地采集泥土),坡度(在陡坡上采集岩石,在平地上采集草),甚至是固定值,等等,或者混合所有这些值。此外,您还可以改变混合:使用内置的
lerp
或更复杂的东西(警告!这个例子很愚蠢):

float4 terrainColor=val1*val2*blend1+val2*val3*blend2
Terracincolor=饱和(Terracincolor)

玩混合算法是这个游戏中最有趣的部分。你可以在谷歌找到很多技术

不确定,但希望有帮助!
快乐编码!=)

谢谢你的回答:)不幸的是,几乎没有什么改变-我只是得到了相同的图像,但平滑,正如你从中看到的。哇,很棒的更新。似乎我还没有明确说明我的地形由“块”(体素)组成,基于高度的方法不能使用,因为我希望用户通过添加其他材质来编辑地形。但纹理掩蔽似乎很有趣,也许我会尝试它来实现飞溅效果。我希望在ps_3_0中有足够的纹理采样器,我将研究它。谢谢,它变得更清晰了,我会让你知道我的进展:)我通过混合你和我的方法做到了这一点。我没有使用不同的采样器,而是将我的纹理打包成一个3D纹理(就像我以前做的那样),并通过我在问题中描述的因素将它们混合。它给了我一个简单平滑的纹理,我期待着使用您描述的“纹理遮罩”使材质之间的过渡更具吸引力:)
float4 terrainColor = lerp( val1, val2, blend1 );
terrainColor = lerp( terrainColor, val3, blend2);
terrainColor = lerp( terrainColor, ..., blendN );