unity shader reflect

改編自《cg教程--可編程實時圖形學權威指南》上的demo。

本文的目的不在於教你如何實現反射效果,而是在於讓你學會遷移cg、hlsl、glsl到unity中[unity shader 資料很少,但是前面哪幾種還是相對較多的 ]

反射向量計算公式 R=I-2N(N*I) 備註N*I是點乘   I入射光線,N法向量

函數實現:
float3 reflect(float3 I,float3 N)
{
  return I-2.0*N*dot(N,I);
}

Shader "CG shader Reflect"{
     Properties {      
                  environmentMap("Environment Map", Cube) = "" {}
                  reflectivity("reflectivity1", float) =1 //反射係數  決定反射強度
                  decalMap("decalMap", 2D) = "white" {}
                }
                SubShader{
                      Pass{
                           CGPROGRAM
                           #pragma vertex vert //頂點編程入口
                           #pragma fragment frag //片段編程入口
                           #include "UnityCG.cginc" //注意引入
                           struct VertInput{  //在UnityCG中有定義 可以參考appdata_base、appdata_tan、appdata_full
                               float4 position:POSITION;
                               float2 texCoordw:TEXCOORD0;
                               float3 normal1:NORMAL;
                           };
                           struct VertOutput{
                               float4 oPosition:SV_POSITION;
                               float2 oTexCoord:TEXCOORD0;
                               float3 R:TEXCOORD1;
                           };
                           // uniform 類型的參數 需要在Properties裏面定義
                           uniform samplerCUBE environmentMap;
                           uniform float reflectivity;
                           uniform sampler2D decalMap;
                           VertOutput vert(VertInput input)
                           {
                               VertOutput o;
                               o.oPosition=mul(UNITY_MATRIX_MVP,input.position);//UNITY_MATRIX_MVP變量, 就是對應圖形中的模型視圖投影矩陣(ModelViewProj),unity中規定 必須這麼寫
                               o.oTexCoord=input.texCoordw;
                               float3 positionW=mul(_Object2World,input.position).xyz;//_Object2World 模型矩陣,把本地座標轉到世界座標
                               float3 N=mul((float3x3)_Object2World,input.normal1);
                               N=normalize(N);
                               float3 I=positionW-_WorldSpaceCameraPos;//計算入射光線,需要在世界座標系中計算。_WorldSpaceCameraPos視點在世界座標的位置
                               o.R=reflect(I,N);//計算反射光線 reflect系統自帶函數
                               return o;
                           }
                           
                           float4 frag(VertOutput output):COLOR
                           {
                               float4 reflectionColor=texCUBE(environmentMap,output.R);
                               float4 decalColor=tex2D(decalMap,output.oTexCoord);
                               float4 color1=lerp(decalColor,reflectionColor,reflectivity);
                               return color1;
                           }
                           ENDCG
                    }
            }
}

上例代碼出現的_Object2World,_WorldSpaceCameraPos 莫名奇妙的參數,來自UnityCG.cginc文件,在對cg、hlsl、glsl進行移植的時候,特殊參數需要參考UnityCG.cginc文件的定義。

附unity shader 學習資料:http://en.wikibooks.org/wiki/Cg_Programming/Unity
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章