UnityのStandard Surface Shaderを使うと3Dモデルを半透明で表示することが出来ます。ただ、モデルの形状が複雑な場合には、裏面のポリゴンが見えて汚い表示になってしまうことがあります。
そこで、隠面は表示せず、手前側の面のみ半透明で表示するシェーダを作ってみました。左が綺麗な半透明シェーダを使ったドラゴン、右がStandard Surface Shaderを使って半透明にしたドラゴンです。
Standard Surface Shaderではドラゴン裏側の羽まで見えてしまっていますね。
これを解決する方法を紹介していきます。目次は次のとおりです。
半透明でモデルをきれいに表示する方法
綺麗に表示する方法を考える前に、なぜモデルを半透明で表示すると汚く表示されるのかを考えてみましょう。
Unityのサイトによると・・・
Usually semitransparent shaders do not write into the depth buffer. However, this can create draw order problems, especially with complex non-convex meshes. If you want to fade in & out meshes like that, then using a shader that fills in the depth buffer before rendering transparency might be useful.
Unity - Manual: ShaderLab: Culling & Depth Testing
どうやらコレが原因のようです。半透明モデルを描画する際にデプスバッファ(Zバッファ)への書き込みを行わないため、後から裏面を描画すると上書きされてしまうのですね。
これを解決するため、先にデプスバッファにモデルのZ値(デプス値)のみを書き込みます。この時モデルは描画しません。
これでモデルを表示する場所のZ値だけ正しく更新されます。続けて、そのZ値を参照しながらモデルを描画します。デプス値は正しく設定されているので、Zテストにより裏面は描画されないことになります。
分かってしまえば、超簡単ですね!では早速シェーダを作ってみましょう。
半透明シェーダプログラム作る
プロジェクトウインドウで右クリックし、Create→Shader→Standard Surface Shaderを選択してください。名前はSemiTransparent.shaderにしました。
いま作ったシェーダファイルを右クリックし、Create→Materialを選択してください。これでSemiTransparent用のマテリアルが作成できました。
今回はSurface Shaderを使ってモデルを綺麗に半透明表示するシェーダを作ってみます。SemiTransparent.shaderを開いて次のプログラムを入力してください。
Shader "SemiTransparent" { Properties { _Color ("Color", Color) = (1,1,1,1) _MainTex ("Albedo (RGB)", 2D) = "white" {} } SubShader { Tags { "RenderType"="Transparent" "Queue"="Transparent"} LOD 200 Pass{ ZWrite ON ColorMask 0 } CGPROGRAM #pragma surface surf Standard fullforwardshadows alpha:fade #pragma target 3.0 sampler2D _MainTex; struct Input { float2 uv_MainTex; }; fixed4 _Color; void surf (Input IN, inout SurfaceOutputStandard o) { fixed4 c = tex2D (_MainTex, IN.uv_MainTex) * _Color; o.Albedo = c.rgb; o.Metallic = 0; o.Smoothness = 0; o.Alpha = c.a; } ENDCG } FallBack "Diffuse" }
このシェーダでは2パスでモデルを描画しています。1パス目では「ColorMask 0」を指定することでモデルは描画せずZバッファ(デプスバッファ)にのみ書き込んでいます。
2パス目で通常通りモデルを描画しています。先にZバッファに値を書き込んでいるため、裏面のモデルはZテストに失敗し描画されません。
実行結果
シェーダが作成できたら、マテリアルをモデルにアタッチしてみましょう。プロジェクトウィンドウからマテリアルをドラッグ&ドロップします。
モデルのインスペクタからマテリアルのColorのアルファ値を操作することで、モデルの透明度を変化させることができます。
きれいに半透明のモデルが表示されたら成功です!