在函数distSigned
中,我假设为l.p != vec2(0)
。如果不是这种情况,则可能很难发现bug,从而破坏了整个着色器。有什么方法可以验证这一点,如果参数无效,则抛出运行时错误?这将使调试变得容易得多。我知道GLSL没有像Java那样的throw
,但是也许有某种黑客手段?
struct parallel {
vec2 p;
vec2 d;
};
struct pt {vec2 v;};
float distSigned(pt p, parallel l) {
vec2 l2o = fromOrigo(l);
float d = length(l2o);
return dot(p.v, l2o/d) - d;
}
编辑:我看了一下GLSL规范并发现了:
“必须为词法或语言返回编译时错误 语法错误的着色器。其他错误在编译时或链接时报告为 指示。”
我猜这意味着GLSL没有运行时错误?如果是这样,也许我可以自行实现异常?是否有某种设计模式?
答案 0 :(得分:3)
向谁抛出运行时错误 ?什么时候扔?会引发多少个着色器调用,接收代码将如何接收它们?
只要GPU围绕着色器,着色器就会执行,而不是在运行绘制调用时执行。因此,此类错误将被“抛出”的时间可能在“您发出抽签通知时”到任意未来的任何时间。那么您将如何接收它们?谁来接收?
此外,您正在执行多个着色器调用;每个顶点和每个片段都有各自的调用。因此,每个顶点和栅格化的片段都可能“抛出”某种运行时错误。对于大小和复杂性的场景,可能有数百万个这样的错误。您将如何处理?
否,如果要调试着色器,则需要专用的工具,或者需要执行与printf调试等效的着色器。也就是说,将场景降低到可以减少的最低复杂度,然后根据某种错误情况是通过一种方法还是另一种方法来写输出值。
答案 1 :(得分:1)
错误像素实现,Webgl2:
//:ES2_AA2_MAC_DEB: My debug macro, true if positive.
//: pix_err: PIXel ERRor ( Stores Hex Error Code )
//: pix_fra: PIXel FRAgment ( fragment color )
#if( ES2_AA2_MAC_DEB > 0 ) //:///////////////////////////://
//:ASSIGN_TO_ZERO_AT_TOP_OF_FUNCTION!!!!!!!!!!!!!!!!!!!!
uint pix_err =( 0x00000000 );
#endif //:///////////////////////////////////////////////://
//: ...Later when you want to error check....
#if( ES2_AA2_MAC_DEB > 0 ) //:///////////////////////////://
if( Ax1-Ax0+uint(1) != ES2_zoo_wid ||
Ay1-Ay0+uint(1) != ES2_zoo_hig ){
//: The first error encountered puts program ://
//: into invalid state, so we want to make sure ://
//: we never override the first error tripped. ://
//: So always guard with comparison to ://
//: 0x00000000 before setting to the error color.://
if( uint(0x00000000) == pix_err ){
pix_err=( uint(0xFF9000FF) );
};;
};;
#endif //:///////////////////////////////////////////////://
... Do more code.......................................
... DONT TRY TO EXIT EARLY if error is tripped ........
... that will just turn your code into spaghetti ......
#if( ES2_AA2_MAC_DEB > 0 ) //://////////////////////////://
if( uint(0x000000) != pix_err ){
#define F_F uint(0xFF)" //://////////////////////://
pix_fra=( vec4( //://///////////////////////////://
float( ( pix_err >> 24 ) & F_F ) / 255.0
,float( ( pix_err >> 16 ) & F_F ) / 255.0
,float( ( pix_err >> 8 ) & F_F ) / 255.0
,float( ( pix_err >> 0 ) & F_F ) / 255.0
));; //://///////////////////////////////////////://
#undef F_F //://////////////////////////////////://
};;
#endif //:///////////////////////////////////////////////://
//: Now in debug mode, you can color sample the pixel ://
//: and type in the hex code to find the exact error. ://
//: Might not be helpful for minor edge cases, but ://
//: should be very helpful for gross mistakes in ://
//: your programming logic. ://
return( pix_fra );