[UnityShaderCookbook 读书笔记] [01] Unity Shader 基础

来源:互联网 发布:php 菜鸟教程 编辑:程序博客网 时间:2024/05/19 19:40

创建 Shader


一个好的Shader总是从一个基本的 diffuse 光照模型开始
因此,我们从 Diffuse 入手开始写 Shader ~

Shader 中的 Diffuse 部分描述从一个表面上向各个方向反射的光

在Unity中创建 Shader 并打开
得到了一个 Unity 的 Shader 模板

Shader "HineNotes/CookbookCh_01/BasicDiffuse" {     Properties {          _MainTex ("Base (RGB)", 2D) = "white" {}     }     SubShader {          Tags { "RenderType"="Opaque" }          LOD 200          CGPROGRAM          #pragma surface surf Lambert          sampler2D _MainTex;          struct Input {               float2 uv_MainTex;          };          void surf (Input IN, inout SurfaceOutput o) {               half4 c = tex2D (_MainTex, IN.uv_MainTex);               o.Albedo = c.rgb;               o.Alpha = c.a;          }          ENDCG     }     FallBack "Diffuse"}

其中 Shader 关键字后的字符串 “Cookbook_01/BasicDiffuse”
为 Shader 名,利用 / 可以为 Shader 设置分级菜单

新建一个 Material, 也起名 BasicDiffuse 把这个Shader赋给它
再把这个 Material 赋给模型,得到的效果就是这样~
BasicDiffuse 效果
这是一个 Surface Shader, Unity 为我们做了很多幕后工作
随着我们深入学习,对于其背后的 Cg 语言,以及 Unity 如何处理背后的底层 GPU 任务,会有更多的了解

有关 Unity 内置的 Cg 函数,参考 Unity安装目录\Editor\Data\CGIncludes
目前值得我们关注的有
UnityCG.cginc, Lighting.cginc, UnityShaderVariables.cginc
我们当前的这个 Shader 用到了这些文件


为 Shader 添加属性


选中刚刚的 BasicDiffuse 材质,在 Inspector 面板中,我们可以看到 Shader 属性 Base (RGB)
这里写图片描述

也就是 BasicDiffuse 中的这一段

Properties {     _MainTex ("Base (RGB)", 2D) = "white" {}}

定义属性的语法为
Properties { Property [Property …] }

而通常的写法为
_name (“display name”, type) = “defaulttexture” {}

name 为属性名,在Unity中属性名通常以下划线 _开始,display name 为该属性在 Inspector 面板中显示的名字,type 表示属性的类型(具体见下面的表格)赋值符号后面的字符串是默认值,根据不同属性类型来提供,而最后的大括号中则是可选的选项

属性类型 描述 Range (min, max) 在 Inspector 面板中创建一个滑条,在最大最小值之间滑动,接受 float 参数 Color 在 Inspector 面板中创建一个颜色面板,可以打开拾色器,获取颜色 float4 = (float,float,float,float) 2D 在 Inspector 面板中创建一个贴图面板,允许用户为 Shader 指定贴图对于 2D 和 Cube 类型,默认值可以使用空字符串”“,或“white”,”black”,”gray”,”bump” 3D 在 Inspector 面板中创建一个贴图面板,允许用户为 Shader 指定3D贴图 Rect 在 Inspector 面板中创建一个不以2的整数幂为大小的贴图 Cube 在 Inspector 面板中创建一个 cube map 面板,允许用户为 Shader 指定 cube map Float 在 Inspector 面板中创建一个 float 值输入框,但没有滑条 Int 在 Inspector 面板中创建一个 int 值输入框 Vector 在 Inspector 面板中创建一组4个 float 值输入框,可以用来传入方向和颜色

将初始 Shader 的标题改为
“HineNotes/CookbookCh_01/UseOfProperties”

其中的属性段改为

Properties {     _Slider ("Slider", Range(0, 10)) = 5     _Float ("Float", Float) = 1.0     _Int ("Int", Int) = 1     _Color ("Clolr", Color) = ( 0.262, 0.612, 1.0, 1.0)     _Vector ("Vector", Vector) = (1.0, 1.0, 1.0, 1.0)     _TwoD("2D", 2D) = "" {}     _Cube("Cube", Cube) = "" {}     _ThreeD("3D", 3D) = "" {}     _MainTex ("Base (RGB)", 2D) = "white" {} }

存储后切换到 Unity, Unity 会对更改后的 Shder 自动进行编译,我们可以在 Inspector 中看到属性效果
这里写图片描述
Base( RGB ) 上方就是我们刚刚新添加的属性
对于 Property 部分的介绍,可以参考 Unity 官方文档
http://docs.unity3d.com/Manual/SL-Properties.html


使用 Shader 的属性


想要在 SubShader 块中使用属性,我们需要在其中创建与 Properties 块中同名的属性
将 CGPROGRAM 段修改为

CGPROGRAM#pragma surface surf Lambertfloat4 _Color;float _Slider;struct Input {     float2 uv_MainTex;};void surf (Input IN, inout SurfaceOutput o) {     float4 c;     c = pow(_Color, _Slider);     o.Albedo = c.rgb;     o.Alpha = c.a;}ENDCG

即可得到由 _Color 和 _Slider 两个属性共同控制的 Shader
其中 _Color 控制漫反射颜色,_Slider 控制强度
最终的 UseOfProperties Shader 如下

Shader "HineNotes/CookbookCh_01/UseOfProperties" {     Properties {          _Slider ("Slider", Range(0, 10)) = 5          _Float ("Float", Float) = 1.0          _Int ("Int", Int) = 1          _Color ("Clolr", Color) = ( 0.262, 0.612, 1.0, 1.0)          _Vector ("Vector", Vector) = (1.0, 1.0, 1.0, 1.0)          _TwoD("2D", 2D) = "" {}          _Cube("Cube", Cube) = "" {}          _ThreeD("3D", 3D) = "" {}          _MainTex ("Base (RGB)", 2D) = "white" {}     }     SubShader {       Tags { "RenderType"="Opaque" }       LOD 200          CGPROGRAM          #pragma surface surf Lambert          float4 _Color;          float _Slider;          struct Input {               float2 uv_MainTex;          };          void surf (Input IN, inout SurfaceOutput o) {               float4 c;               c = pow(_Color, _Slider);               o.Albedo = c.rgb;               o.Alpha = c.a;          }          ENDCG     }     FallBack "Diffuse"}

其中 pow(arg1, arg2) 函数是 Cg 语言内置的函数,提供指数运算
关于更多 Cg 内置函数,参考
http://http.developer.nvidia.com/CgTutorial/cg_tutorial_appendix_e.html

经过调整颜色的材质如下
这里写图片描述

2 0
原创粉丝点击