C++着色器问题

标签 c++ directx shader

我正在使用 Nvidia CGDirect3D9 并且对以下代码有疑问。

它会编译,但不会“加载”(使用 cgLoadProgram 包装器)并且所导致的失败被简单地描述为 发生 D3D 失败

它是像素着色器的一部分,使用着色器模型设置为 3.0

有趣的是,此着色器在以下情况下加载良好:

1) 手动展开 while 语句(对许多 if { } 语句)。

2) 删除循环中带有 tex2D 函数的行。

3) 切换到着色器模型 2_X 并手动展开循环。


着色器代码的问题部分:

float2 tex = float2(1, 1);
float2 dtex = float2(0.01, 0.01);

float h = 1.0 - tex2D(height_texture1, tex);
float height = 1.00;

while ( h < height )
{
    height -= 0.1;
    tex += dtex;

    // Remove the next line and it works (not as expected,
    // of course)
    h = tex2D( height_texture1, tex );
}

如果有人知道为什么会发生这种情况,或者可以在非 CG 环境中测试类似的代码,或者可以以其他方式帮助我,我在等你;)

谢谢。

最佳答案

我认为您需要在纹理坐标上使用 ddx/ddy 来确定循环之前的梯度,然后使用 tex2D(sampler2D samp, float2 s, float2 dx, float2 dy)

GPU 总是渲染四边形而不是像素(即使在像素边界上——渲染后端会丢弃多余的像素)。这样做是因为它允许它始终计算屏幕空间纹理派生,即使您使用计算的纹理坐标也是如此。它只需要取像素中心值之间的差值。

但是,当像问题代码中那样使用动态分支时,这不起作用,因为各个像素的着色器处理器可能会在控制流中发生分歧。因此,您需要在程序流程发散之前通过 ddx/ddy 手动计算导数。

关于C++着色器问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4150918/

相关文章:

android - OpenGL ES 2.0 : How to Implement Simultaneous Multi-Color gl_FragColor?

c++ - 着色器输入布局无效

c++ - DirectX 使用多个渲染目标作为彼此的输入

visual-studio-2005 - 在 VS2005 中使用 Windows 7 和 DirectX SDK

c++ - 共享纹理应该在 D3DPOOL_DEFAULT 还是 D3DPOOL_MANAGED?

opengl - 如何通过质心计算的光实现平面着色?

c++ - OpenCV 的多项式朴素贝叶斯

c++ - 如何从 STL 容器中获取只能 move 的类型?

c++ - 在带有 C++ 子级列表的通用树中添加一个节点并查找两个给定节点之间的路径成本

c++ - 用于隐式转换的 gcc 警告标志