three.js伽马校正和自定义着色器

时间:2014-02-07 14:26:44

标签: three.js webgl

我不太确定THREE.js如何在内部处理伽马校正。 似乎要启用它,您唯一需要做的就是在渲染器对象上设置以下标志:

gammaInput = true; gammaOutput = true;

但是,当您编写自己的自定义着色器并从纹理中获取颜色时,是否仍需将颜色转换为线性空间,或者THREE.js在将纹理上传到GPU之前对其进行转换(当设置gammaInput时)真的)?

同样,在确定着色器中的最终颜色时,是否必须将其转换为gamma空间,或者是否存在THREE.js自动应用的后期处理效果(当gammaOutput设置为true时)?

感谢

2 个答案:

答案 0 :(得分:1)

Three.js不会在上传到GPU之前将纹理映射到另一个空间。一切都使用块在着色器中就地完成。

要将输入值转换为线性:

作为示例,看看Three.js如何处理map属性here。您基本上会看到以下行:

texelColor = mapTexelToLinear( texelColor );

mapTexelToLinear基本上是在WebGLProgram.js file中创建的。

您明白了。

总而言之,您基本上可以在着色器的顶部包含this chunk

#include <encodings_pars_fragment>

然后,您需要根据纹理所在的空间对纹理像素进行解码。例如,使用sRGB纹理的示例:

vec4 color = sRGBToLinear(texel);

要输出经过伽玛校正的值:

您还需要在着色器的顶部包含encodings_pars_fragment

#include <encodings_pars_fragment>

然后,您需要包括自动修改碎片颜色的块。看看this line

通过在自定义着色器的末尾包含块encodings_fragment,它将根据您在THREE.WebGLRenderer上使用的参数自动映射片段。

要了解其工作原理,您可以查看encodings chunk,其中仅包含:

gl_FragColor = linearToOutputTexel( gl_FragColor );

然后您可以看一下WebGLProgram.js file,以了解linearToOutputText函数的工作方式。基本上与texel解码的方式相同。

希望这很有用!

答案 1 :(得分:-1)

虽然我相信https://github.com/mrdoob/three.js/issues/1488回答了您的第一个问题,但您的第二个问题仍然没有答案。

我发现了

renderer.gammaOutput = true;

在为材质使用自定义着色器时不执行任何操作。您可以通过启用gammaOutput并将gammaFactor设置为极值来进行测试。内置材质对此做出了响应,但是您的自定义着色器却没有。

是的,在这种情况下,您需要自己处理伽玛,方法是修改输出颜色,或者在线性空间中完成所有渲染后添加后期处理步骤。