Shader导论:
Shader(着色器):是一种短小的程序片段,是用于告诉图形硬件如何计算和输出图像过去由汇编语言编写【Shader是可编程图形管线的算法片段】
Shader的主要分类为:Vertex Shader(顶点着色)和Fragment Shader(片段着色)
渲染管线:
渲染管线也称为渲染流水线,是显示芯片内部处理图形信号相互独立的并行处理单元.一个流水线是一序列可以并行和按照固定顺序进行的阶 段.每个阶段都从它的前一阶段接收输入,然后把输出发给随后的阶段. 就像一个在同一时间内,不同阶段不同的汽车一起制造的装配线,传统 的图形硬件流水线以流水的方式处理大量的顶点,几何图元和片段.
Shader实际上就是一小段程序,它负责将输入的顶点数据以指定的方 式和输入的贴图或者颜色等组合起来,然后输出.绘图单元可以根据这 个输出来将图像绘制到屏幕上.输入的贴图或颜色等,加上对应的 Shader,以及对Shader的特定的参数设置,将这些内容打包存储到一起 得到的就是一个Material(材质).之后我们便可以将材质赋予三维物 体来进行渲染(输出)了.
Shader是图形可编程方案的程序片段
渲染管线是一种计算机从数据到最终图形成像的描述
三大主流的高级编程语言:
Shader Language的发展方向是设计出在便捷性方面可以和C++/JAVA 相比较的高级语言,赋予程序员灵活而方便的编程方式,并尽可能的控 制渲染过程,同时利用图形硬件的并行性,提高算法的效率.
目前Shader Language有三种语言:基于OpenGL的OpenGL Shading Language,简称GLSL.基于DirectX的High Level Shading Language 简称HLSL.还有NVIDIA公司的C for Graphic简称Cg语言.
Cg语言(C for Graphics)是为GPU编程设计的高级着色器 语言,由NVIDIA公司开发。Cg极力保留C语言的大部分语义, 并让开发者从硬件细节中解脱出来,Cg同时也有一个高级语 言的其他好处,如代码的易重用性,可读性得到提高,编译器代码优化。
Shader的基本结构
三种着色器:表面着色器、顶点片段着色器、固定管线着色器
Shader:
//固定管线着色器,从语法上说是最简单的着色器
//虽然功能有限,但在3中着色器中运行速度是最快的,几乎在所有硬件上都能运行
//结构:由 Properties、SubShader、FallBack组成
Shader "CustomLearn/First"{ Properties{ // 属性的语法规则:_Name("DisplayName",Type)=defaultValue // 1、_Name是属性的名字,简单说就是变量名,在之后的整个shader // 代码中一直通过该名字来获得该属性的内容 // 2、DisplayName:将显示在Unity材质编辑器中的名称 // 3、Type:属性的类型,类型可以有以下 // 1)Color-颜色,有RGBA(红绿蓝和透明)四个两来定义取值0-1之间 // 2) 2D——表示一个2的幂次方大小的贴图,这样贴图将在采样后背后被转化 // 为对应模型的UV的每个像素的颜色最终被显示出来 // UVMaping:作用是将一个2D贴图上的点映射到3D模型上,是3D渲染中最常见的一种顶点处理手段 // 3)Rect - 表示的是一个非2的幂次方大小的贴图 // 4)Cube - 即Cube map texture(立方体为例),即六张带有联系 // 的2D贴图的组合,主要用来做一些反射效果,比如说天空盒 // 5)Range - 一个介于最大值和最小值之间的浮点数,这个值可以用来在 // 材质球的设置面板进行设置,一般用于调整shader某些特定的参数,比如透明度 // 6)Float - 任意的一个浮点数 // 7)Vector - 表示一个四维数,格式为(x,y,z,w) _Color("Main Color",color)=(1,0.5,0.5,1) } SubShader{ //SubShader:子着色器,可以有一个或者多个,在实际运行平台当中 //到底执行那个子着色器,是由运行的平台所决定的 //子着色器:是Shader代码的主体,每个子着色器包含一个或者多个Pass通道, //每个Pass都会渲染一次当前shader所作用的对象,在计算着色器时,平台会优先选用 //要使用的子着色器,然后运行Pass通道,会得到一个输出的结果,最后将结构渲染在界面上 Pass{ //Pass通道:控制被渲染对象的几何体,除了表面着色器以外,其他两种着色器的SubShader下一定要有Pass通道 //pass通道语法规则 //{{Name and Tags}[RendererSetup][TextureSetup]} //1、Name and Tags:可以定义Pass通道和任意数量的标签,如果为Pass通道命名后,可以在别的着色器中使用该名字(标签)来重用它 //2、标签的作用可以用来向渲染管线说明Pass的意图 //3、RenderSetup:渲染设置是用来固定功能管线着色器中,可以设置图形硬件的各种状态 // 可用的设置命令为: // 1)Material{}:材质:定义一个使用顶点着色器光照管线的材质 // 2)Lighting:光照:取值为On或off // 3)Cull:裁剪,设置裁剪模式,有Back,Front、Off // Cull Back:表示不绘制北里观察者的几何面 // Cull Front:表示不绘制面向观察者的几何面,用于由内而外的对象 // Cull Off:显示所有面,用于特殊效果 //4、ZTest:深度测试,模式包括:Less、Greater、LEqual、GEqual、Equal、NotEqual、Always // 深度测试:当场景中有多个物体需要绘制,这些物体之间通常会存在遮挡的关系,离观察者比较远 // 的会因为近处物体的遮挡而不可见,或者只有近处可见。这是如果绘制不可见的物体没 // 有太大意义,所以深度检测可以简化复杂场景的绘制,确保只有场景内最靠近表面的 // 物体参与绘制 //5、ZWrite:深度缓存写入,取值为On或Off; // ZWrite On/Off:用于将要绘制的对象写入深度缓存区中,默认情况下是开启的,如果要 // 绘制一个纯色的物体,可以将这个选项打开,如果要绘制半透明效果,关闭深度缓存 //6、Fog():雾效,设置雾效的参数,用于控制雾效的相关渲染 // 雾化的原理:通过混合已经生成的像素的颜色,和基于到镜头的距离来确定最终的颜色。 // 雾化不会改变已经混合的像素的透明度值,只是改变了RGB值,我们可以在Unity工程中设置 //7、Alpha Test:设置Alpha测试,模式包括:Less、Greater、LEqual、GEqual、Equal、NotEqual、Always、Nerver // AlphaTest:表示的是阻止像素被渲染到屏幕的最后机会,在最终渲染出的颜色被计算出来之后, // 可以选择通过颜色的透明度值和一个固定值比较,如果比较的结果失败(这里是否失败 // 取决于上面设置的测试类型:大于、小于。。。)像素就不会被写到显示的输出中 //8、Bleed:Alpha混合 //9、Color:颜色,设置顶点光照关闭时设置的颜色值 //10、ColorMask:颜色通道,当值为0时,关闭所有的颜色通道的渲染,取值为RGB|A|0|或者RGB任意组合 //11、Offset Factor/Units:表示两个参数来定义深度偏移 // Factor:表示z轴缩放的最大斜率的值 // units:表示可分辨的最小深度缓冲区的值 //12、SepatareSpecular:高光颜色,取值为On或Off //13、ColorMaterial:颜色集,当计算定点光照时使用每个顶点的颜色 //4、TextureSetup:贴图设置的选项: // 1)Combine:将两种颜色进行混合,可以是上次SetTexture的处理结果,(previous、constant、primary、Texture中的一种) // 2)constantColor:设置一个常量的颜色值 // 3)matriax:设置矩阵纹理坐标进行变换 Material{ Diffuse[_Color] } //灯光打开 Lighting On //剔除关闭【Cull Front 剔除正面,不会绘制面向观察者的几何体】 Cull Off } } //如果用户所用的SubShader都失败了,为了在计算机上能够呈现设定的渲染效果, //0一般会使用FallBack,FallBack是Unity自己预制的Shader实现, //一般可以在所有显卡上运行,Shaderde的备胎,类似Default语句 FallBack "Diffuse" } //固定管线着色器 Shader "CustomLearn/Second"{ Properties{ // 主颜色 _Color("Main color",color) = (1,1,1,0.5) //高光 _SpecColor("Spec color",color) = (1,1,1,1) //自发光 _Emission("Emission",color) = (0,0,0,0) //太阳光 _Shiness("Shiness",Range(0,1)) = 0.7 //主纹理 _MainTex("MainTexture",2D) = "white"{} } SubShader{ Tags{"Queue"="Transparent" "IgnoreProjector"="true" "ForceNoShadowCasting"="True"} //tags:表示输出的是什么,如果输出的是非透明的物体,写在Opaque中,如果想渲染半透明或者透明的物体写在Transparent中 //其他的一些标签还包括: //IgnoreProjector=True:表示不被Project投影影响 //ForceNoShadowCasting=True:表示不产生阴影 //"Queue"="XXX":表示指定的渲染队列 //Queue的值可以有: //Background - 最早被调用的渲染,用来渲染天空盒或者北京 //Geometry - 这是默认值,用来渲染非透明的物体 //AlphaTest - 用来渲染经过Alpha Test 渲染过的像素 //Transparent:从后往前的顺序渲染透明的物体 //Overlay:用来渲染叠加效果,是渲染的最后阶段使用 //上述设置的Queue中的渲染效果,实际上是一组定义的整数 //Background=1000,Geometry=2000,AlphaTest=2450,Transpartent=3000,Overlay=4000 //也可以指定渲染队列为:"Queue"="Transparent+100",表示当前渲染内容在渲染完透明物体之后, //在Overlay之前 //透明度的混合 Blend srcAlpha OneMinusSrcAlpha Pass{ Material{ //漫反射颜色 Diffuse[_Color] //环境光颜色 Ambient[_SpecColor] //太阳光的光泽度,值在0-1之间 SHininess[_Shiness] } //开启灯光 Lighting On //开启顶点光照的平行高光颜色 SeparateSpecular On //设置纹理 SetTexture[_MainTex]{ //设置纹理的颜色 constantColor[_Color] //混合效果 //纹理*原色的两倍,纹理*常量颜色值 Combine texture*primary DOUBLE,texture*constant } } } FallBack "Diffuse" }