2016-04-10 6 views
1

私はシェイダーを書くのが初めてで、私は練習用シェイダーに取り組んでいます。シェーダの目的は、オブジェクトが見えないように透明なピクセルを生成するための「通常の」パスと、「ジオメトリ」パスが元の色と同じ場所に再描画される各三角形を取得することです。したがって、私は出力が元のオブジェクトだと思っていますが、黒です。しかし、私のジオメトリパスは私が見ることができる任意の出力を生成していないようだ。CG/Unity:オブジェクトを複製するための玩具シェーダ

enter image description here

ここで私は現在、シェーダのために持っているコードです。

Shader "Outlined/Silhouette2" { 
    Properties 
    { 
     _Color("Color", Color) = (0,0,0,1) 
     _MainColor("Main Color", Color) = (1,1,1,1) 
     _Thickness("Thickness", float) = 4 
     _MainTex("Main Texture", 2D) = "white" {} 
    } 
    SubShader 
    { 

     Tags{ "Queue" = "Geometry" "IgnoreProjector" = "True" "RenderType" = "Transparent" } 
     Blend SrcAlpha OneMinusSrcAlpha 
     Cull Back 
     ZTest always 
     Pass 
     { 
      Stencil{ 
       Ref 1 
       Comp always 
       Pass replace 
      } 

      CGPROGRAM 
      #pragma vertex vert 
      #pragma fragment frag 
      #pragma multi_compile_fog 

      #include "UnityCG.cginc" 

      struct v2g 
      { 
       float4 pos : SV_POSITION; 
       float2 uv : TEXCOORD0; 
       float3 viewT : TANGENT; 
       float3 normals : NORMAL; 
      }; 

      struct g2f 
      { 
       float4 pos : SV_POSITION; 
       float2 uv : TEXCOORD0; 
       float3 viewT : TANGENT; 
       float3 normals : NORMAL; 
      }; 

      float4 _LightColor0; 
      sampler2D _MainTex; 
      float4 _MainColor; 

      v2g vert(appdata_base v) 
      { 
       v2g OUT; 
       OUT.pos = mul(UNITY_MATRIX_MVP, v.vertex); 
       OUT.uv = v.texcoord; 
       OUT.normals = v.normal; 
       OUT.viewT = ObjSpaceViewDir(v.vertex); 

       return OUT; 
      } 

      half4 frag(g2f IN) : COLOR 
      { 
       //this renders nothing, if you want the base mesh and color 
       //fill this in with a standard fragment shader calculation 

       float4 texColor = tex2D(_MainTex, IN.uv); 
       float3 normal = mul(float4(IN.normals, 0.0), _Object2World).xyz; 
       float3 normalDirection = normalize(normal); 
       float3 lightDirection = normalize(_WorldSpaceLightPos0.xyz * -1); 
       float3 diffuse = _LightColor0.rgb * _MainColor.rgb * max(0.0, dot(normalDirection, lightDirection)); 

       texColor = float4(diffuse,1) * texColor; 

       // 
       //return texColor; 
       return float4(0, 0, 0, 0); 
      } 
      ENDCG 
     } 

     Pass 
     { 
      Stencil{ 
       Ref 0 
       Comp equal 
      } 

      CGPROGRAM 
      #include "UnityCG.cginc" 
      #pragma target 4.0 
      #pragma vertex vert 
      #pragma geometry geom 
      #pragma fragment frag 


      half4 _Color; 
      float _Thickness; 

      struct v2g 
      { 
       float4 pos : SV_POSITION; 
       float2 uv : TEXCOORD0; 
       float4 local_pos: TEXCOORD1; 
       float3 viewT : TANGENT; 
       float3 normals : NORMAL; 
      }; 

      struct g2f 
      { 
       float4 pos : SV_POSITION; 
       float2 uv : TEXCOORD0; 
       float3 viewT : TANGENT; 
       float3 normals : NORMAL; 
      }; 

      v2g vert(appdata_base v) 
      { 
       v2g OUT; 
       OUT.pos = mul(UNITY_MATRIX_MVP, v.vertex); 
       OUT.local_pos = v.vertex; 

       OUT.uv = v.texcoord; 
       OUT.normals = v.normal; 
       OUT.viewT = ObjSpaceViewDir(v.vertex); 

       return OUT; 
      } 

      [maxvertexcount(12)] 
      void geom(triangle v2g IN[3], inout TriangleStream<g2f> triStream) 
      { 
       g2f OUT; 
       OUT.pos = IN[0].pos; 
       OUT.uv = IN[0].uv; 
       OUT.viewT = IN[0].viewT; 
       OUT.normals = IN[0].normals; 
       triStream.Append(OUT); 

       OUT.pos = IN[1].pos; 
       OUT.uv = IN[1].uv; 
       OUT.viewT = IN[1].viewT; 
       OUT.normals = IN[1].normals; 
       triStream.Append(OUT); 

       OUT.pos = IN[2].pos; 
       OUT.uv = IN[2].uv; 
       OUT.viewT = IN[2].viewT; 
       OUT.normals = IN[2].normals; 
       triStream.Append(OUT); 
      } 

      half4 frag(g2f IN) : COLOR 
      { 
       _Color.a = 1; 
       return _Color; 
      } 
      ENDCG 

     } 
    } 
    FallBack "Diffuse" 
} 

私がやっているすべては私が与えられてきた同じ三角形を取って、私は私が表示されることは何も起こさないために間違っていることができたかわからないんだけど三角形ストリームに追加されているので。誰がなぜこれが起こっているのか知っていますか?

答えて

1

ジオメトリシェイダーの三角形の3つの頂点に給餌した後に triStrem.RestartStrip();と呼ぶことはありません。

これは、特定の三角形ストリップが終了したことをストリームに通知し、新しい三角形ストリップが開始されます。これをしないと、ストリームに渡された各(単一の)頂点は、三角形のストリップパターンを使用して、既存の三角形ストリップに追加されます:https://en.wikipedia.org/wiki/Triangle_strip

私はジオシェイダーにはかなり新しいので、これがあなたの問題であるかどうかわからない、私はRestartStrip関数が各geomerty-shaderの最後で自動的に呼び出されるとは思わないが、これをテストしていない。むしろ、あなたがmaxvertexcountに達したときに自動的に呼び出されると思います。 1つの三角形については、maxvertexcountを3に設定します。今は12に設定しません。 (私は助けようと思っていたので、どんなシェーダの回答でもうまくいきませんでした)

+0

私は実際にこれを本当に感謝します。ジオメトリシェーダなしで、私が望む効果を得るために別の方向に移動することを選択したので、これが修正されるかどうかはわかりませんが、それは三角に関する情報の非常に重要な部分であり、私はそれを覚えています将来は。 – Valevalorin

+0

はそのオプションに対処していませんが、最終目標が「出力は元のオブジェクトだと思っていますが、黒です」としています。フラグメントシェーダーからfloat4(0,0,0,1)(黒)を出力するだけではどうですか? – Glurth

+0

当時、シェイダーに2回目の「パス」を追加するだけで別のイメージを生成できることに気付きませんでした。私は、追加イメージを作成するためにジオメトリシェーダを明示的に作成しなければならないと考えました。 – Valevalorin

関連する問題