😸

Unityシェーダー超入門①シェーダーの中身

2023/03/20に公開

新規作成したシェーダーの中身を言語化してみた

結構時間が掛かった、あれってなんだっけとかこれってどういう意味だっけとか…
分かった風に書いてるけど大体調べてます。改めて再復習する良い機会だった!
次は簡単なシェーダーを作るまでの流れを書いて見ようと思います!

UnlitShader
//Shaderの名前
//※ファイル名と一致してなくてもいいけど一致させた方がいいとおもう。
//スラッシュで区切られているのはインスペクター上の階層構造
Shader "Unlit/NewUnlitShader"
{   
    //マテリアルのインスペクターに設定したい変数の記述
    Properties
    {   
        //_(アンダーバー)を付けるのが習慣らしい、理由は知らない…
        //変数名("インスペクター上の表記名", 変数の型) = "初期値"
        //float4みたいな複数の変数型だと(0,1,1,0)みたいな感じの記述になる。
        //実現したい内容によって選択する型も変わるので良く使いそうな物は見ておいた方が良さげ
        _MainTex ("Texture", 2D) = "white" {}
    }

    //シェーダーの中身の記述
    //ハードウェアやらに合わせて複数かき分けが出来る模様
    SubShader
    {   
        //シェーダーの設定
        //Opqaueは不透明。半透明なども指定が出来る
        Tags { "RenderType"="Opaque" }
        //Level of Detail 
        //カメラとの距離で処理分岐をさせたい場合の閾値、必要ない場合は削除をしてもいい
        LOD 100
        //Passは一つの描画出力の工程
        //複数作れる、その場合上から順番に処理がされる
        Pass
        {
            //CGPROGRAM以下がHLSLであるという定義
            //要はここからがシェーダーの中身って感じ。
            //HLSLはシェーダー言語のこと
            CGPROGRAM
            //#pragmaそのものはコンパイラに対して命令する記述で様々な種類があるよ
            //vertが関数vertex(頂点)シェーダーだよという記述
            #pragma vertex vert
            //fragが関数fragment(フラグメント)シェーダーだよという記述
            #pragma fragment frag
            //フォグの処理に対するシェーダーバリアントの記述
            //処理の有無によるシェーダーを自動生成してくれている
            #pragma multi_compile_fog
            //includeは外部のライブリ参照
            //cginc/hlsl/glslincの拡張子が読み込める
            //UnityCG.cgincはUnity側で予め関数が用意されているライブラリ
            //自分で作ったライブラリも読み込めるので
	    よく使いそうな処理はまとめておくといいかもしれない。
            #include "UnityCG.cginc"

            //シェーダーを設定してるモデルから受け取る値の設定
            struct appdata
            {
                //セマンティクス
                //頂点シェーダーでの引数設定
                //頂点座標
                float4 vertex : POSITION;
                //UV座標
                float2 uv : TEXCOORD0;
            };
            //vertex to fragmentの略
            //頂点シェーダーからフラグメントシェーダーへの値の引き渡し
            struct v2f
            {   
                //UV座標
                float2 uv : TEXCOORD0;
                //フォグ
                UNITY_FOG_COORDS(1)
                //位置情報
                float4 vertex : SV_POSITION;
            };

            //プロパティで宣言した型と同じ宣言
            sampler2D _MainTex;
            //STはタイリングとオフセットの表記するための宣言
            float4 _MainTex_ST;

            //vertex(頂点)シェーダー
            //頂点情報を元に色々する
            v2f vert (appdata v) //appdataで指定した情報を使う
            {
                //戻り値
                v2f o;
                //UnityCG.cgincで定義されてる関数
                //3D空間においてのスクリーン上のでの座標変換を行う関数
                o.vertex = UnityObjectToClipPos(v.vertex);
                //UnityCG.cgincで定義されてる関数
                //テクスチャのUV値の計算を行う関数
                o.uv = TRANSFORM_TEX(v.uv, _MainTex);
                //UnityCG.cgincで定義されてる関数
                //フォグの処理
                UNITY_TRANSFER_FOG(o,o.vertex);
                return o;
            }

            //fragment(フラグメント)シェーダー
            //Vertex(頂点)シェーダの戻り値を利用して色々する
            fixed4 frag (v2f i) : SV_Target
            {
                //tex2D関数
                //UV座標からテクスチャ上のピクセルの色を計算して返す
                fixed4 col = tex2D(_MainTex, i.uv);
                //UnityCG.cgincで定義されてる関数
                //フォグの処理
                UNITY_APPLY_FOG(i.fogCoord, col);
                return col;
            }
            //ここまでがシェーダーの記述
            ENDCG
        }
    }
}

Discussion