unityShader r

What is a shader?

Shader, the Chinese translation is shader, is a relatively short program fragment used to tell the graphics hardware how to calculate and output images. In the past, it was written in assembly language and now it can also be written in high-level language. In one sentence: A shader is an algorithm fragment of a programmable graphics pipeline.
It is mainly divided into two categories, Vertex Shader and Fragment Shader.

What is the rendering pipeline?

The rendering pipeline, also called the rendering pipeline, is an independent parallel processing unit inside the display chip that processes graphics signals. A pipeline is a sequence of stages that can be executed in parallel and in a fixed order. Each stage receives input from its previous stage and sends output to subsequent stages. Like an assembly line where different cars are built at different stages at the same time, traditional graphics hardware pipelines process large numbers of vertices, primitives, and fragments in a streamlined fashion.

CPU stage: 3D enable or game -> call openGL and other interfaces

GPU stage: vertex shader (graphics transformation operation, lighting operation, etc.) fragment shader (calculate what color each pixel on the screen should be)

The relationship between shaders, materials and textures

A shader is actually a small program that is responsible for combining the input vertex data with the input texture or color in a specified way, and then outputs it. The drawing unit can draw images to the screen based on this output. The input texture or color, etc., plus the corresponding shader, and specific parameter settings for the shader are packaged and stored together, and the result is a Material. After that, we can assign the material to the three-dimensional object for rendering (output). The material is like the product
ultimately used by the engine , the shader is like the processing method used to produce this product , and the texture is the raw material .

The three mainstream programming languages ​​​​of shader 

Shader language currently has three main languages: OpenGL Shading Language based on OpenGL, referred to as GLSL, High Level Shading Language based on DirectX, referred to as HLSL, and NVIDIA's C for Graphic language referred to as Cg language.

GLSL(OpenGL Shading Language,)

The development of openGL has always been in a relatively slow situation. Every time the version is improved, few new technologies are added, and most of them are just modifications and improvements to some of them. In July 1992, SGI released version 1.0 of OpenGL, and then jointly developed the Windows NT version of OpenGL with Microsoft, allowing some large-scale 3D graphics processing software that originally had to be run on high-end graphics workstations to be able to run on microcomputers. use. In 1995, version 1.1 of openGL was launched. This version had many performance improvements over 1.0 and added some new features. These include improved printer support, inclusion of OpenGL calls in enhanced metafiles, new features for vertex arrays, improved transfer speed of vertex positions, normals, colors, color indices, texture coordinates, polygon edge markers, and the introduction of new texture features etc. OpenGL1.5 has added "OpenGLShading Language" , which is the core of "OpenGL 2.0" and is used for extended functions of shading objects, vertex shading and fragment shading technology.

HLSL DirectX-based (High Level Shading Language)

DirectX enhances 3D graphics and sound effects and provides designers with a common hardware driver standard, eliminating the need for game developers to write different drivers for each brand of hardware. It also reduces the complexity of installing and setting up hardware for users. Literally speaking, Direct means direct, and the X behind it represents many meanings. From this point of view, it can be seen that the emergence of DirectX is to provide direct services for many software.

cg (C for Graphic)

GLSL and HLSL are based on the OpenGL and Direct3D interfaces respectively. The two cannot be mixed. In fact, OpenGL and Direct3D have always been enemies and have been fighting for a long time. OpenGL has accumulated a huge user base during its long-term development, and these users will choose GLSL to learn. GLSL inherited the good portability of OpenGL and once dominated operating systems such as Unix. But GLSL's syntax is unique. Microsoft's HLSL has poor portability and can be said to be the only one on the Windows platform. This has largely restricted the promotion and development of HLSL. However, HLSL's use in the field of DX games is deeply rooted in the hearts of the people.

Cg is a graphics processor programming language that can be widely supported by OpenGL and Direct3D. The Cg language is not the same level of language as OpenGL and DirectX, but the upper layer of OpenGL and DirectX. That is, the Cg program runs on the basis of the standard vertex and pixel shading of OpenGL and DirectX.

The basic structure of ShaderLab

shader“name”{

        [Properties]

        SubShaders

        [FallBack]

}

properties: properties in unity material

subshaders: the main code for GPU programming. There can be multiple subshaders. When the current subshader is not suitable for this GPU, it will go to the next shader.

Fallback: Ensure that when all shaders are unsuitable, you can fall back to the simpler shader.

Fixed rendering pipeline (fixed functions shader1)

Shader "folder/filename"{

    properties{
        _Color("Main Color",color) = (1,1,1,1) //主颜色
        _Ambient("Ambient",color)=(0.3,0.3,0.3,0.3,0.3)//环境光 0.3是为了让环境光不是全白,否则看不出光照效果
        _Specular("Specular",color) = (1,1,1,1)//高光
        _Shininess("Shininess",range(0,8)) = 4 //高光度范围0-8 默认为4 
        _Emission("Emission",color)=(1,1,1,1)
        
    }

    SubShader{
        pass{
            //color[_Color] 中括号代表放入的是一个变量,这样会导致三维物体在任何方位显示的都是同一个颜色
            //要解决次问题
            material{
                diffuse[_Color]//漫反射 要配合光照不然物体是全黑的
                ambient[_Ambient]//环境光
                specular[_Specular]//高光 需要配合sepratespecular使用
                shininess[_Shininess] //用来描述specular这个高光的大小(光滑程度)
                emission[]//自发光
            }
            lingting on //打开光照 物体才可以被看见
            sepratespecular on //镜面高光
        }
        
    }

}

Fixed rendering pipeline (fixed functions shader2)

Shader "folder/filename"{

    properties{
        _Color("Main Color",color) = (1,1,1,1) //主颜色
        _Ambient("Ambient",color)=(0.3,0.3,0.3,0.3,0.3)//环境光 0.3是为了让环境光不是全白,否则看不出光照效果
        _Specular("Specular",color) = (1,1,1,1)//高光
        _Shininess("Shininess",range(0,8)) = 4 //高光度范围0-8 默认为4 
        _Emission("Emission",color)=(1,1,1,1)
        _Constant("Constant",color) = (1,1,1,0.3)
        _MainTex("MainTex",2d) = "" // 设置贴图
        _SecondTex("SecondTex",2d) = ""
        
    }

    SubShader{
        Tags{"queue"="Transparent"}//不使用的话由于Shader计算顺序原因而达不到前面的物体透明
        pass{
            Blend srcAlpha oneMinusSrcAlpha //设置透明

            //color[_Color] 中括号代表放入的是一个变量,这样会导致三维物体在任何方位显示的都是同一个颜色
            //要解决次问题
            material{
                diffuse[_Color]//漫反射 要配合光照不然物体是全黑的
                ambient[_Ambient]//环境光
                specular[_Specular]//高光 需要配合sepratespecular使用
                shininess[_Shininess] //用来描述specular这个高光的大小(光滑程度)
                emission[]//自发光
            }
            lingting on //打开光照 物体才可以被看见
            sepratespecular on //镜面高光


            settexture[_MainTex]{//设置贴图
                combine texture * primary double //此时两个值都是0-1的浮点数,相乘就会变得更小所以图像显示就会变暗 
// primary是先前代码的参数值
//为了解决此问题需要为combine的结果double 或 quad
            settexture[_SecondTex]{//设置贴图
                constantColor[_Constant]//设置贴图alpha值
                combine texture * previous double,texture * constant  //primary不会计算前一张贴图的值,如果想让两张贴图相混合,需要用previous
        }
        
    }

}

Surface Shader

SurfaceOutput

Input

Lighting

Shadow

Shader "Custom/3"
{
    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
        // Physically based Standard lighting model, and enable shadows on all light types
        #pragma surface surf Standard fullforwardshadows
        //编译指令 按照surface关键词来编译 surf函数名称 光照模型

        // Use shader model 3.0 target, to get nicer looking lighting
        #pragma target 3.0//使用的硬件功能,越高则越高级

        

        struct Input
        {
            float2 uv_MainTex;//纹理坐标
        };
        sampler2D _MainTex; // 声明properties在CG中,2d对应sampler2D 
        half _Glossiness; range对应half
        half _Metallic;
        fixed4 _Color; // color对应fixed4

        // 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)
//SurfaceOutputStandard 是一个输入输出结构体 
        {
            // Albedo comes from a texture tinted by color
            fixed4 c = tex2D (_MainTex, IN.uv_MainTex) * _Color;
            o.Albedo = c.rgb;//输出结构体的rgb值
            // Metallic and smoothness come from slider variables
            o.Metallic = _Metallic;
            o.Smoothness = _Glossiness;
            o.Alpha = c.a;//输出结构体的alpha值
        }
        ENDCG
    }
    FallBack "Diffuse"
}

Guess you like

Origin blog.csdn.net/helongss/article/details/132968216