这里只做记录用,不进行详细的讲解。
Shader "Custom/SurfaceShader" { Properties { _Color ("Color", Color) = (1,1,1,1) _MainTex ("Albedo (RGB)", 2D) = "white" {} _Glossiness ("Smoothness", Range(0,1)) = 0.5 _Metallic ("Metallic", Range(0,1)) = 0.0 } SubShader { Tags { "RenderType"="Opaque" } LOD 200 CGPROGRAM //SurfaceOutputStandard 结构体定义在这个cginc文件内 #include "UnityPBSLighting.cginc" //-----------------------------重要内容 #pragma surface surf PBSLighting vertex:vert finalcolor:final fullforwardshadows #pragma target 3.0 sampler2D _MainTex; //自定义 struct Input { float4 vertColor; float2 uv_MainTex; }; half _Glossiness; half _Metallic; fixed4 _Color; //自定义的定点处理方法 void vert(inout appdata_full v,out Input o) { //这句话必须要有,用来对o进行初始化 UNITY_INITIALIZE_OUTPUT(Input,o); o.vertColor = v.color; } UNITY_INSTANCING_CBUFFER_START(Props) UNITY_INSTANCING_CBUFFER_END //自定义的啥啥啥 void surf (Input IN, inout SurfaceOutputStandard o) { } //自定义的光照方法 inline half4 LightingPBSLighting (SurfaceOutputStandard s, half3 viewDir, fixed atten) { return float4(1,1,0,0); } //自定义的最终处理方法 void final(Input IN, SurfaceOutputStandard o,inout fixed4 color) { } ENDCG } FallBack "Diffuse" }
如果要看SurfaceShader的详细讲解,可以看这个帖子:
【Unity Shaders】初探Surface Shader背后的机制
不同的是,冯同学的这篇帖子时间比较久了,用的是SurfaceOutput,unity有了物理渲染以后,就成了SurfaceOutputStandard,旧版的这个结构体是定义在Lighting.cginc文件里,新版的是定义在UnityPBSLighting.cginc文件中。所以,如果使用了自定义的光照方法,但是又要使用SurfaceOutputStandard结构体,就需要对这个文件设置引用。当然也可以自定义一个结构体。
还有关于冯同学说的四个方法两个结构体,并不准确,与UnlitShader 一样 vertex方法的传入参数也可以自定义。
SurfaceShader在编译时,还是转换成了UnlitShader,前者与后者的对应关系为:
vertex <=> vertex
(surf+lighting+finalcolor)<=> fragment
可以通过转换后的代码去验证一下。