着色器

简介

着色器是在图形处理器上运行的独特程序.它们用于指定如何获取网格数据(顶点位置、颜色、法线等等)然后把它们绘制到屏幕上.着色器并不像普通程序那样处理信息,因为它们经过了优化,可以在图形处理器上运行.其结果是,着色器在运行后不会保留数据;它们把最后一种颜色输出到屏幕上,然后继续.因此,无法访问着色器上次运行时的颜色输出.

Godot使用一种与GLSL非常相似的着色语言,增加了一些功能,但灵活性稍差.这样做的原因是Godot集成了内置功能,使编写复杂着色器变得更加容易.Godot将用户编写的着色器代码封装在自己的代码中.这样,Godot就可以处理很多用户无需担心的底层内容,它能够解析着色器代码,并使用它来影响渲染管道.对于更高级的着色器,您可以使用render_mode关闭此功能.

这个文档为您提供了一些特定于Godot的着色器的信息.有关Godot中着色语言的详细信息,请参见 Godot着色语言文档.

着色器类型

Godot着色语言必须指定着色器的用途,而不是提供通用配置给所有用途(2D、3D、粒子). 不同的类型支持不同的渲染模式,内置变量,和处理函数.

所有着色器都需要在第一行指定其类型,格式如下:

shader_type spatial;

有效的类型有:

有关每种着色类型的详细信息,参见相应的参考文档.

渲染模式

不同的着色器类型支持不同的渲染模式.它们是可选的,但如果指定,则必须位于 shader_type 之后.渲染模式被用于改变内置功能的处理方式.一个比较常见的用法是,通过使用渲染模式 unshaded 来跳过内置的光照处理函数.

渲染模式在着色器类型下面指定:

shader_type spatial;
render_mode unshaded, cull_disabled;

每种着色器类型都有不同的渲染模式列表.有关渲染模式的完整列表,请参阅每种着色器类型的文档.

处理器函数

根据着色器的类型,不同的处理器功能可以被选择性地重写.对于 "spatial" 和 "canvas_item" ,可以覆盖 vertexfragmentlight .对于 "particles" ,只有 vertex 可以被覆盖.

顶点处理器

在 "spatial" 和 "canvas_item" 着色器中,每一个顶点都要调用一次 vertex 处理函数.对于 "particles" 着色器,它对每个粒子都调用一次.

``vertex``函数用于修改每个顶点的信息,这些信息将被传递给片段函数.它也可以用来建立变量,这些变量将通过使用variings(见其他文档)被发送到片段函数.

默认情况下,Godot将获取您的顶点信息,并相应地对其进行转换以便绘制.如果这是不可用的,您可以使用渲染模式转换数据;查看 :ref:`空间着色器文档 <doc_spatial_shader>`来获得这个示例.

片段处理器

fragment 处理函数用于设置每个像素的Godot材质参数.该代码在对象或基本单元绘制的每个可见像素上运行.它只在 "spatial" 和 "canvas_item" 着色器中可用.

分段函数的标准用法是设置用于计算光照的材质属性.例如,你可以设置"粗糙度"、"边缘"或"传递"的值,可以告诉光照功能,以及光照对这个片段的响应.这使得控制复杂的着色管道成为可能,而无需用户编写太多代码.如果你不需要这个内置功能,可以忽略它,编写自己的光照处理函数,Godot会优化它.例如,如果你不给"边缘"设定一个值,Godot将不计算边缘照明.编译期间,Godot检查是否使用了"边缘";如果没有,它将删除所有对应的代码.因此,您不会将计算力浪费在不使用的效果上.

光处理器

light 处理也是按像素运行的,但也为每一个影响物体的光线而运行(如果没有光线影响物体,则不运行).它作为一个函数存在于 "fragment" 处理内部,通常在 "fragment" 函数中设置的材质属性上运行.

light 处理在2D中的工作方式与在3D中的工作方式不同;关于它在每一种情况下的工作方式的描述,请分别参阅它们的文档, CanvasItem shadersSpatial shaders .