Unity Shader片段著色器使用基礎(chǔ)詳解
一、Unity Shader基礎(chǔ)
1、創(chuàng)建和使用Shader
在Unity中Shader一般由兩種用途:
- 指定給材質(zhì),用于物理渲染;
- 指定給腳本,用于圖像處理,比如后期處理(Post Processing);
2、Unity渲染管線Shader的編寫方式
- 頂點-片段著色器(Vertex and Fragment Shader);
- 表面著色器(Surface Shader);
- 固定函數(shù)著色器(Fixed Function Shader,目前逐漸被拋棄);
二、CG語法基礎(chǔ)
1、編譯指令
CG常用的編譯指令:

(1) 編譯目標(biāo)等級
CG代碼編譯到不同的Shader Models中,要適應(yīng)對應(yīng)的GPU平臺,否則會出現(xiàn)一些Shader在GPU上無法運行。
聲明編譯目標(biāo)的級別#pragma target name也可以使用#pragma require feature指令直接聲明某個特定的功能。
#pragma target 3.5 //目標(biāo)等級3.5 #pragma require geometry tessellation //需要幾何體細(xì)分功能
(2) 渲染平臺
Unity具有跨平臺的特性,它支持很多渲染API,例如Direct3D、Opengl。默認(rèn)情況下,Unity會為所有支持的平臺編譯一份Shader程序,但需要指定編譯某些平臺或不編譯某些平臺。

使用示例:
#pragma only_renderers d3d11 //目標(biāo)只編譯Direct3D 11/12 平臺 #pragma exclude_renderers glcore //不編譯 OpenGL 3.x/4.x
2、著色器函數(shù)
一個基本的Shader示例:
Shader "Custom/Simplest Shader"
{
SubShader
{
Pass
{
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
void vert (in float4 vertex : POSITION,
out float4 position : SV_POSITION)
{
position = UnityObjectToClipPos(vertex);
}
void frag (in float4 vertex : SV_POSITION,
out fixed4 color : SV_TARGET)
{
color = fixed4(1, 0, 0, 1);
}
ENDCG
}
}
}在Shader中,頂點-片元著色器主要通過頂點函數(shù)和片元函數(shù)來實現(xiàn)的。
(1) 無返回值函數(shù)
上述Shader中的頂點函數(shù)和片元函數(shù)使用的是無返回值的函數(shù),通過out關(guān)鍵字將變量輸出。
語法結(jié)構(gòu)如下:
void name(in 參數(shù),out 參數(shù))
{
//函數(shù)體
}void:函數(shù)以void開頭,表示返回值為空;
name:定義函數(shù)名稱;
in:輸入?yún)?shù),語法為:in+數(shù)據(jù)類型+名稱,一個函數(shù)可以有多個輸入,關(guān)鍵詞 in 可省略。
out:輸出參數(shù),語法為:out+數(shù)據(jù)類型+名稱,一個函數(shù)可以有多個輸出。
(2) 有返回值的函數(shù)
語法結(jié)構(gòu)如下:
type name(in 參數(shù))
{
//函數(shù)體
return 返回值;
}3、語義
CG語言編寫著色器函數(shù)時,函數(shù)的輸入?yún)?shù)和輸出參數(shù)都需要填充一個語義(Semantic)來表示它們要傳遞的數(shù)據(jù)信息。
語義可以執(zhí)行大量繁瑣的操作,使用戶能夠避免直接于GPU底層進(jìn)行交流。
參數(shù)后被冒號隔開并且全部大寫的關(guān)鍵詞就是語義。
(1) 頂點這著色器的輸入語義
頂點數(shù)據(jù)是以輸入?yún)?shù)的方式傳遞給頂點函數(shù)的,每一個輸入的參數(shù)都需要填充一個語義,用于表示所傳遞的數(shù)據(jù)。

注意:
當(dāng)頂點信息包含的元素少于頂點著色器輸入所需要的元素時,缺少的部分會被0填充, w分量會被1填充; 如:輸入語義TEXCOOED0被聲明為float4類型,那么頂點著色器最終獲取到的數(shù)據(jù)為 ( x , y , 0 , 1 ) (x,y,0,1) (x,y,0,1)
(2) 頂點這著色器輸出和片元著色器輸入語義
在整個渲染流水線中,頂點著色器最重要的的一項人物就是需要輸出頂點在裁剪空間中的坐標(biāo),這樣GPU就可以知道頂點在屏幕上的柵格化位置以及深度值。在頂點函數(shù)中這個輸出參數(shù)值需要使用float4類型的SV_POSITION語義填充。
頂點著色器產(chǎn)生的輸出值將會在三角形便利階段經(jīng)過插值計算,最終作為像素值輸入到片元著色器。
換句話說,頂點著色器的輸出就是片元著色器的輸入。

片元著色器會自動獲取頂點著色器輸出的裁切空間頂點坐標(biāo),所以片元函數(shù)輸入的SV_POSITION可以省略。
注意:
與頂點函數(shù)的輸入語義不同,TEXCOORDn不再特指模型的UV坐標(biāo),COLORn也不在特指頂點顏色。它們使用范圍更廣,可以用于聲明任何符合要求的數(shù)據(jù)。
(3) 片元著色器輸出語義
片元著色器通常只會輸出一個fixed4類型的顏色信息,輸出的值會存儲到渲染目標(biāo)(Render Target),輸出參數(shù)使用SV_TARGET語義進(jìn)行填充。
到此這篇關(guān)于Unity Shader片段著色器使用基礎(chǔ)詳解的文章就介紹到這了,更多相關(guān)Unity Shader片段著色器內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
C#結(jié)束Excel進(jìn)程的步驟教學(xué)
在本篇文章里小編給大家分享了關(guān)于C#結(jié)束Excel進(jìn)程的步驟教學(xué)內(nèi)容,有興趣的朋友們學(xué)習(xí)下。2019-01-01
c# socket心跳超時檢測的思路(適用于超大量TCP連接情況下)
這篇文章主要介紹了c# socket心跳超時檢測的思路(適用于超大量TCP連接情況下),幫助大家更好的理解和學(xué)習(xí)使用c#,感興趣的朋友可以了解下2021-03-03
C#復(fù)雜XML反序列化為實體對象兩種方式小結(jié)
本文主要介紹了C#復(fù)雜XML反序列化為實體對象兩種方式,主要介紹如何把通過接口獲取到的Xml數(shù)據(jù)轉(zhuǎn)換成(反序列化)我們想要的實體對象,感興趣的可以一起來了解一下2022-04-04
C# 使用HttpClient上傳文件并附帶其他參數(shù)的步驟
這篇文章主要介紹了C# 使用HttpClient上傳文件并附帶其他參數(shù)的步驟,幫助大家更好的理解和使用c#,感興趣的朋友可以了解下2020-12-12
Winform實現(xiàn)調(diào)用asp.net數(shù)據(jù)接口實例
這篇文章主要介紹了Winform實現(xiàn)調(diào)用asp.net數(shù)據(jù)接口的方法,以實例的形式講述了數(shù)據(jù)接口及反射辨別響應(yīng)的實現(xiàn)方法,具有一定的參考借鑒價值,需要的朋友可以參考下2014-10-10

