我需要调试一个GLSL程序,但我不知道如何输出中间结果。 是否有可能使用GLSL进行一些调试跟踪(如printf) ?
当前回答
你可以试试这个:https://github.com/msqrt/shader-printf,它是一个叫做“GLSL的简单打印功能”的实现。
You might also want to try ShaderToy, and maybe watch a video like this one (https://youtu.be/EBrAdahFtuo) from "The Art of Code" YouTube channel where you can see some of the techniques that work well for debugging and visualising. I can strongly recommend his channel as he writes some really good stuff and he also has a knack for presenting complex ideas in novel, highly engaging and and easy to digest formats (His Mandelbrot video is a superb example of exactly that : https://youtu.be/6IWXkV82oyY)
我希望没有人介意这个迟到的回复,但这个问题在谷歌搜索GLSL调试中排名很高,当然在9年里发生了很大变化:-)
PS:其他替代方案也可以是NVIDIA nSight和AMD ShaderAnalyzer,它们为着色器提供了一个完整的步进调试器。
其他回答
void main(){
float bug=0.0;
vec3 tile=texture2D(colMap, coords.st).xyz;
vec4 col=vec4(tile, 1.0);
if(something) bug=1.0;
col.x+=bug;
gl_FragColor=col;
}
GLSL沙盒已经相当方便我的着色器。
不是调试本身(被回答为不能调试),而是方便地快速查看输出中的更改。
对纹理进行离线渲染,并评估纹理的数据。 你可以通过google“render to texture”opengl找到相关代码 然后使用glReadPixels将输出读入数组并对其执行断言(因为在调试器中查看如此巨大的数组通常并不真正有用)。
此外,你可能想要禁用钳制输出值不是在0到1之间,这只支持浮点纹理。
我个人一度被调试着色器的问题所困扰。似乎没有一个好的方法-如果有人发现一个好的(并且没有过时/过时)调试器,请告诉我。
如果你想在屏幕上可视化一个值的变化,你可以使用类似于这个的热图函数(我用hlsl写的,但很容易适应glsl):
float4 HeatMapColor(float value, float minValue, float maxValue)
{
#define HEATMAP_COLORS_COUNT 6
float4 colors[HEATMAP_COLORS_COUNT] =
{
float4(0.32, 0.00, 0.32, 1.00),
float4(0.00, 0.00, 1.00, 1.00),
float4(0.00, 1.00, 0.00, 1.00),
float4(1.00, 1.00, 0.00, 1.00),
float4(1.00, 0.60, 0.00, 1.00),
float4(1.00, 0.00, 0.00, 1.00),
};
float ratio=(HEATMAP_COLORS_COUNT-1.0)*saturate((value-minValue)/(maxValue-minValue));
float indexMin=floor(ratio);
float indexMax=min(indexMin+1,HEATMAP_COLORS_COUNT-1);
return lerp(colors[indexMin], colors[indexMax], ratio-indexMin);
}
然后在像素着色器中输出如下内容:
return HeatMapColor(myValue, 0.00, 50.00);
并且可以了解它在像素之间的变化情况:
当然你可以使用任何你喜欢的颜色。
现有的答案都是好东西,但我想分享更多的小宝石,在调试棘手的精度问题在GLSL着色器有价值。对于以浮点数表示的非常大的int数,需要注意正确使用floor(n)和floor(n + 0.5)来实现round()为精确的int。然后,可以通过以下逻辑将字节组件打包到R、G和B输出值中,呈现一个精确int的浮点值。
// Break components out of 24 bit float with rounded int value
// scaledWOB = (offset >> 8) & 0xFFFF
float scaledWOB = floor(offset / 256.0);
// c2 = (scaledWOB >> 8) & 0xFF
float c2 = floor(scaledWOB / 256.0);
// c0 = offset - (scaledWOB << 8)
float c0 = offset - floor(scaledWOB * 256.0);
// c1 = scaledWOB - (c2 << 8)
float c1 = scaledWOB - floor(c2 * 256.0);
// Normalize to byte range
vec4 pix;
pix.r = c0 / 255.0;
pix.g = c1 / 255.0;
pix.b = c2 / 255.0;
pix.a = 1.0;
gl_FragColor = pix;
推荐文章
- 如何调试一个GLSL着色器?
- 漂亮地打印Java集合(toString不返回漂亮输出)
- 确定导致分段错误的代码行?
- 如何在GDB中打印c++向量的元素?
- 在Clojure中调试?
- 为什么Android工作室说“等待调试器”如果我不调试?
- 没有找到用于调试模式的此可执行文件的有效配置文件
- Visual Studio c++和Windows中的调试内存填充模式是什么?
- 为什么这个for循环在某些平台上退出,而在其他平台上不退出?
- 在OpenGL中如何将原语渲染为线框?
- 如何使gdb保存命令历史?
- 如何检查Flutter应用程序是否正在调试中运行?
- 如何设置断点在内联Javascript在谷歌Chrome?
- Chrome调试-打破下一个点击事件
- PHP -调试Curl