UnityShader3實(shí)現(xiàn)彩光效果
本文實(shí)例為大家分享了UnityShader3實(shí)現(xiàn)彩光效果展示的具體代碼,供大家參考,具體內(nèi)容如下
參考鏈接: 【OpenGL】Shader實(shí)例分析(八)- 彩色光圈
效果圖:
這里我把它分三部分實(shí)現(xiàn):1.彩色 2.光圈 3.動(dòng)畫
1.先實(shí)現(xiàn)彩色效果。分析一下那張彩色圖,它是以中心為原點(diǎn)的,然后顏色分為三部分,如下圖。當(dāng)角度為90度時(shí),藍(lán)色最多;當(dāng)角度為-150度時(shí),紅色最多;當(dāng)角度為-30度時(shí),綠色最多。然后其他地方就是三色混合。
Shader "Custom/Colors"
{
 Properties
 {
 _AngleRange ("AngleRange", Range(60, 120)) = 60
 }
 SubShader
 {
 Pass
 {
 CGPROGRAM
 #pragma vertex vert
 #pragma fragment frag
 #include "UnityCG.cginc"
 
 #define PI 3.142
 
 struct appdata
 {
 float4 vertex : POSITION;
 };
 
 struct v2f
 { 
 float4 vertex : SV_POSITION;
 float4 scrPos : TEXCOORD0;
 };
 
 half _AngleRange;
 
 v2f vert (appdata v)
 {
 v2f o;
 o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);
 o.scrPos = ComputeScreenPos(o.vertex);
 
 return o;
 }
 
 fixed4 frag (v2f i) : SV_Target
 {
 //范圍在(0, 1) 
 float2 wcoord = i.scrPos.xy / i.scrPos.w; 
 //映射到(-1, 1),即屏幕中心為(0, 0) 
 wcoord = wcoord * 2 - 1; 
 //atan2(y, x):反正切,y/x的反正切范圍在[-π, π]內(nèi) 
 float radian = atan2(wcoord.y, wcoord.x); 
 //1度(°)=0.017弧度(rad)
 //1弧度(rad)=57.29578度(°)
 float angle = radian * 57.3;
 //映射到(0, 360)
 if(angle < 0) angle = 360 + angle;
 
 fixed b = 1 - saturate(abs(angle - 90) / _AngleRange);
 fixed g;
 if(angle > 180) g = 1 - saturate(abs(angle - 330) / _AngleRange); 
 else g = 1 - saturate((angle + 30) / _AngleRange);
 fixed r = 1 - saturate(abs(angle - 210) / _AngleRange);
 
 return fixed4(r, g, b, 1);
 }
 ENDCG
 }
 }
}
2.先說(shuō)一下1 / (xxx)這個(gè)式子的強(qiáng)大,它實(shí)現(xiàn)的效果,往往會(huì)帶有光暈效果。其中第六個(gè)就是我們想要實(shí)現(xiàn)的光圈效果。
Shader "Custom/Test"
{
 Properties
 {
 _Value ("Value", Range(1, 50)) = 1
 }
 SubShader
 {
 Pass
 {
 CGPROGRAM
 #pragma vertex vert
 #pragma fragment frag
 #include "UnityCG.cginc"
 
 struct appdata
 {
 float4 vertex : POSITION;
 float2 uv : TEXCOORD0;
 };
 
 struct v2f
 { 
 float4 vertex : SV_POSITION;
 float2 uv : TEXCOORD0;
 };
 
 half _Value;
 
 v2f vert (appdata v)
 {
 v2f o;
 o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);
 o.uv = v.uv;
 return o;
 }
 
 fixed4 frag (v2f i) : SV_Target
 {
 //映射到(-1, 1),使其中心點(diǎn)為原點(diǎn)
 float2 uv = i.uv * 2 - float2(1, 1);
 float v;
 
 //v = 1 / abs(_Value * uv.y);//1
 //v = 1 / abs(_Value * (uv.y + uv.x));//2
 //v = 1 / abs(_Value * (uv.y + 2 * uv.x));//3
 //v = 1 / abs(_Value * (abs(uv.y) + abs(uv.x)));//4
 //v = 1 / abs(_Value * length(uv));//5
 //v = 1 / abs(_Value * abs(length(uv) - 0.5));//6
 v = 1 / abs(_Value * abs(uv.x / uv.y));//7 x越小y越大,則越亮
 
 return fixed4(v, v, v, 1);
 }
 ENDCG
 }
 }
}
3.動(dòng)畫。這里我做的效果是基于角度的光線間隔效果,首先當(dāng)然就是計(jì)算角度了,間隔的實(shí)現(xiàn)就是fmod和step的使用。
Shader "Custom/Test"
{
 Properties
 {
 _Width ("Width", Range(30, 90)) = 45
 }
 SubShader
 {
 Pass
 {
 CGPROGRAM
 #pragma vertex vert
 #pragma fragment frag
 #include "UnityCG.cginc"
 
 struct appdata
 {
 float4 vertex : POSITION;
 float2 uv : TEXCOORD0;
 };
 
 struct v2f
 { 
 float4 vertex : SV_POSITION;
 float2 uv : TEXCOORD0;
 };
 
 half _Width;
 
 v2f vert (appdata v)
 {
 v2f o;
 o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);
 o.uv = v.uv;
 return o;
 }
 
 fixed4 frag (v2f i) : SV_Target
 {
 //映射到(-1, 1),使其中心點(diǎn)為原點(diǎn)
 float2 uv = i.uv * 2 - float2(1, 1);
 
 float a = atan2(uv.y, uv.x);
 a *= 57.3;
 if(a < 0) a += 360;
 
 float b = fmod(a + _Time.y * 20, _Width);
 b = step(0.5 * _Width, b);
 
 return fixed4(b, b, b, 1);
 }
 ENDCG
 }
 }
}
>
4.最后當(dāng)然就是將它們?nèi)嘣谝黄鹆恕?/p>
Shader "Custom/Colors"
{
 Properties
 {
 _AngleRange ("AngleRange", Range(60, 120)) = 60
 _Width ("Width", Range(30, 90)) = 45 
 }
 SubShader
 {
 Pass
 {
 CGPROGRAM
 #pragma vertex vert
 #pragma fragment frag
 #include "UnityCG.cginc"
 
 #define PI 3.142
 
 struct appdata
 {
 float4 vertex : POSITION;
 float2 uv : TEXCOORD0;
 };
 
 struct v2f
 { 
 float4 vertex : SV_POSITION;
 float4 scrPos : TEXCOORD0;
 float2 uv : TEXCOORD1;
 };
 
 half _AngleRange;
 half _Width; 
 
 v2f vert (appdata v)
 {
 v2f o;
 o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);
 o.scrPos = ComputeScreenPos(o.vertex);
 o.uv = v.uv; 
 
 return o;
 }
 
 fixed4 frag (v2f i) : SV_Target
 {
 //1.彩色
 
 //范圍在(0, 1) 
 float2 wcoord = i.scrPos.xy / i.scrPos.w; 
 //映射到(-1, 1),即屏幕中心為(0, 0) 
 wcoord = wcoord * 2 - 1; 
 //atan2(y, x):反正切,y/x的反正切范圍在[-π, π]內(nèi) 
 float radian = atan2(wcoord.y, wcoord.x); 
 //1度(°)=0.017弧度(rad)
 //1弧度(rad)=57.29578度(°)
 float angle = radian * 57.3;
 //映射到(0, 360)
 if(angle < 0) angle = 360 + angle;
 
 fixed b = 1 - saturate(abs(angle - 90) / _AngleRange);
 fixed g;
 if(angle > 180) g = 1 - saturate(abs(angle - 330) / _AngleRange); 
 else g = 1 - saturate((angle + 30) / _AngleRange);
 fixed r = 1 - saturate(abs(angle - 210) / _AngleRange);
 
 //2.光圈
 
 //映射到(-1, 1),使其中心點(diǎn)為原點(diǎn) 
 float2 uv = i.uv * 2 - float2(1, 1); 
 float v = 1 / abs(30 * abs(length(uv) - 0.3));
 
 //3.轉(zhuǎn)動(dòng)
 
 float a = atan2(uv.y, uv.x); 
 a *= 57.3; 
 if(a < 0) a += 360; 
 
 float aa = fmod(a + _Time.y * 20, _Width); 
 aa = step(0.5 * _Width, aa); 
 
 //////////////////////
 //////////////////////
 if(length(uv) < 0.3) return fixed4(0, 0, 0, 1);
 return fixed4(r, g, b, 1) * aa + fixed4(v, v, v, 1);
 }
 ENDCG
 }
 }
}
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持我們。
欄 目:C#教程
下一篇:Unity3D使用GL實(shí)現(xiàn)圖案解鎖功能
本文標(biāo)題:UnityShader3實(shí)現(xiàn)彩光效果
本文地址:http://www.jygsgssxh.com/a1/C_jiaocheng/4846.html
您可能感興趣的文章
- 01-10C#實(shí)現(xiàn)txt定位指定行完整實(shí)例
 - 01-10WinForm實(shí)現(xiàn)仿視頻播放器左下角滾動(dòng)新聞效果的方法
 - 01-10C#實(shí)現(xiàn)清空回收站的方法
 - 01-10C#實(shí)現(xiàn)讀取注冊(cè)表監(jiān)控當(dāng)前操作系統(tǒng)已安裝軟件變化的方法
 - 01-10C#實(shí)現(xiàn)多線程下載文件的方法
 - 01-10C#實(shí)現(xiàn)Winform中打開網(wǎng)頁(yè)頁(yè)面的方法
 - 01-10C#實(shí)現(xiàn)遠(yuǎn)程關(guān)閉計(jì)算機(jī)或重啟計(jì)算機(jī)的方法
 - 01-10C#自定義簽名章實(shí)現(xiàn)方法
 - 01-10C#文件斷點(diǎn)續(xù)傳實(shí)現(xiàn)方法
 - 01-10winform實(shí)現(xiàn)創(chuàng)建最前端窗體的方法
 


閱讀排行
- 1C語(yǔ)言 while語(yǔ)句的用法詳解
 - 2java 實(shí)現(xiàn)簡(jiǎn)單圣誕樹的示例代碼(圣誕
 - 3利用C語(yǔ)言實(shí)現(xiàn)“百馬百擔(dān)”問(wèn)題方法
 - 4C語(yǔ)言中計(jì)算正弦的相關(guān)函數(shù)總結(jié)
 - 5c語(yǔ)言計(jì)算三角形面積代碼
 - 6什么是 WSH(腳本宿主)的詳細(xì)解釋
 - 7C++ 中隨機(jī)函數(shù)random函數(shù)的使用方法
 - 8正則表達(dá)式匹配各種特殊字符
 - 9C語(yǔ)言十進(jìn)制轉(zhuǎn)二進(jìn)制代碼實(shí)例
 - 10C語(yǔ)言查找數(shù)組里數(shù)字重復(fù)次數(shù)的方法
 
本欄相關(guān)
- 01-10C#通過(guò)反射獲取當(dāng)前工程中所有窗體并
 - 01-10關(guān)于ASP網(wǎng)頁(yè)無(wú)法打開的解決方案
 - 01-10WinForm限制窗體不能移到屏幕外的方法
 - 01-10WinForm繪制圓角的方法
 - 01-10C#實(shí)現(xiàn)txt定位指定行完整實(shí)例
 - 01-10WinForm實(shí)現(xiàn)仿視頻播放器左下角滾動(dòng)新
 - 01-10C#停止線程的方法
 - 01-10C#實(shí)現(xiàn)清空回收站的方法
 - 01-10C#通過(guò)重寫Panel改變邊框顏色與寬度的
 - 01-10C#實(shí)現(xiàn)讀取注冊(cè)表監(jiān)控當(dāng)前操作系統(tǒng)已
 
隨機(jī)閱讀
- 01-10SublimeText編譯C開發(fā)環(huán)境設(shè)置
 - 01-10使用C語(yǔ)言求解撲克牌的順子及n個(gè)骰子
 - 08-05dedecms(織夢(mèng))副欄目數(shù)量限制代碼修改
 - 04-02jquery與jsp,用jquery
 - 01-11ajax實(shí)現(xiàn)頁(yè)面的局部加載
 - 08-05DEDE織夢(mèng)data目錄下的sessions文件夾有什
 - 08-05織夢(mèng)dedecms什么時(shí)候用欄目交叉功能?
 - 01-10delphi制作wav文件的方法
 - 01-11Mac OSX 打開原生自帶讀寫NTFS功能(圖文
 - 01-10C#中split用法實(shí)例總結(jié)
 


