美文网首页Shader编程
Unity Shader 入门(一) SurfaceShade

Unity Shader 入门(一) SurfaceShade

作者: xzhuan | 来源:发表于2020-11-23 17:22 被阅读0次

    xzhuan原创稿件,转载请注明出处!

    //-------------------------------【Unity右键路径】-----------------------------------------
    Shader "Custom/MySurfaceShader"
    {
       //-------------------------------【Shader属性】-----------------------------------------
       Properties
       {
           // Color :颜色 Inspector面板里会有一个选取颜色的picker
           // Range :某范围内的浮点数 Inspector面板里会出现一个Slider
           // 2D :   2D纹理
           // Rect : 创建非2次方边长的纹理
           // Cube : 创建Cube Map,也是一种纹理
           // Float :浮点数,和Range的区别就是Range是一个范围内的数,Float是单个数
           // Vector:向量 定义一个四元素的容器
           _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
       {
           //----------------------------【标签】---------------------------  
           //Queque 渲染顺序       BackGround/Geometry
           //RenderType 渲染类型   Opaque不透明/Transparent透明
           Tags { "RenderType"="Opaque" }
           //Level of Detail
           LOD 200
    
           //CG程序 开始
           CGPROGRAM
           // Physically based Standard lighting model, and enable shadows on all light types
           //说明是surface shader,可以换成Vertex或Fragment,surf是表面处理函数,在代码段的下面就有一个surf函数。Standard fullforwardshadows是光照模型函数。
           #pragma surface surf Standard fullforwardshadows
    
           // Use shader model 3.0 target, to get nicer looking lighting
           //设置编译目标Shader model的版本
           #pragma target 3.0
    
           //在surf函数的上面,将properties里的变量用相同的名称定义一遍。还有一个Input结构体,这是输入结构
           sampler2D _MainTex;
    
           struct Input
           {
               float2 uv_MainTex;
           };
    
           half _Glossiness;
           half _Metallic;
           fixed4 _Color;
    
           // Add instancing support for this shader. You need to check 'Enable Instancing' on materials that use the shader.
           // See https://docs.unity3d.com/Manual/GPUInstancing.html for more information about instancing.
           // #pragma instancing_options assumeuniformscaling
           UNITY_INSTANCING_BUFFER_START(Props)
           // put more per-instance properties here
           UNITY_INSTANCING_BUFFER_END(Props)
    
           void surf (Input IN, inout SurfaceOutputStandard o)
           {
               // Albedo comes from a texture tinted by color
               //先定义了一个4元的定点数c,tex2D是纹理采样函数,第一个参数是纹理,第二个参数是uv坐标,函数的返回值乘以颜色
               fixed4 c = tex2D (_MainTex, IN.uv_MainTex) * _Color;
               //o这个变量就是着色器会输出的变量,也就是存储着我们眼睛会看到的效果的变量
               //后面的语句的意思就是将各个值赋给o里的不同值。rgb就是RGB颜色,Albedo是反射值,Metalic是金属值,Smoothness是光滑值,Alpha是透明通道
               o.Albedo = c.rgb;
               // Metallic and smoothness come from slider variables
               o.Metallic = _Metallic;
               o.Smoothness = _Glossiness;
               o.Alpha = c.a;
           }
           //CG程序 结束
           ENDCG
       }
    
       //备胎: 表示前面的着色程序显卡不支持的时候就用默认的“Diffuse”
       FallBack "Diffuse"
    }
    

    CG数据结构 类型

    CG支持7种数据类型:
    float 32位浮点数
    half 16位浮点数
    int 32位整型数
    fixed 12位定点数
    bool 布尔数据
    sampler 纹理对象的句柄,公有sampler, sampler1D, sampler2D, sampler3D, samplerCUBE, 和 samplerRECT 六种
    string 字符,其实没有必要在CG中用到字符
    向量类型 float2就是2元的float类型的向量,fixed4就是4元的fixed类型的向量
    向量最长不超过4元
    此外,CG还支持矩阵数据类型,比如:
    float2×4 matrix; // 表示2×4阶矩阵,包含8个float类型数据

    surface shader的输入输出结构:
    输入结构就是存储输入的信息,输出结构就是存储要输出的信息,也就是我们的眼睛会看见的效果。
    struct Input
    {
    float2 uv_MainTex;
    }
    纹理坐标必须命名为“uv”+"纹理名称",uv_MainTex就是名为_MainTex的纹理的uv坐标。

    surface shader的默认的几种输出结构如下,输出结构也是可以自定义的。
    struct SurfaceOutput
    {
    fixed3 Albedo; // 漫反射颜色
    fixed3 Normal; // 切线空间法线,如果赋值的话
    fixed3 Emission; // 自发光颜色
    half Specular; // 高光强度,范围是0-1
    fixed Gloss; // specular intensity
    fixed Alpha; // 透明度
    };
    struct SurfaceOutputStandard
    {
    fixed3 Albedo; // 基础 (漫反射或镜面反射) 颜色
    fixed3 Normal; // 切线空间法线,如果赋值的话
    half3 Emission; // 自发光颜色
    half Metallic; // 0=非金属, 1=金属
    half Smoothness; // 0=粗糙, 1=光滑
    half Occlusion; // 遮挡(默认1)
    fixed Alpha; // 透明度
    };
    struct SurfaceOutputStandardSpecular
    {
    fixed3 Albedo; // 漫反射颜色
    fixed3 Specular; // 镜面反射颜色
    fixed3 Normal; // 切线空间法线,如果赋值的话
    half3 Emission; // 自发光颜色
    half Smoothness; // 0=粗糙, 1=光滑
    half Occlusion; // 遮挡(默认1)
    fixed Alpha; // 透明度
    };

    那么定义变量的时候怎么知道该用哪种类型呢?

    1. 精度够用就好
    2. 颜色和单位向量,使用fixed
    3. 其他情况,尽量使用half(即范围在[-6万, +6万]内、精确到小数点后3.3位);否则才使用float。

    相关文章

      网友评论

        本文标题:Unity Shader 入门(一) SurfaceShade

        本文链接:https://www.haomeiwen.com/subject/fmdviktx.html