Search Unity

  1. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

Clipping plane shader makes light moving

Discussion in 'Shaders' started by KarbenC, Feb 4, 2022.

  1. KarbenC

    KarbenC

    Joined:
    Dec 14, 2018
    Posts:
    12
    Hi,
    I found a shader that can cut objects with a plane, here it is :
    Code (CSharp):
    1. Shader "Custom/021_Clipping_Plane"{
    2.     //show values to edit in inspector
    3.     Properties{
    4.         _Color("Tint", Color) = (0, 0, 0, 1)
    5.         _MainTex("Texture", 2D) = "white" {}
    6.         _Smoothness("Smoothness", Range(0, 1)) = 0
    7.         _Metallic("Metalness", Range(0, 1)) = 0
    8.             //[HDR]_Emission("Emission", color) = (0,0,0)
    9.  
    10.             //[HDR]_CutoffColor("Cutoff Color", Color) = (1,0,0,0)
    11.     }
    12.  
    13.         SubShader{
    14.             //the material is completely non-transparent and is rendered at the same time as the other opaque geometry
    15.             Tags{ "RenderType" = "Opaque" "Queue" = "Geometry"}
    16.  
    17.             // render faces regardless if they point towards the camera or away from it
    18.             Cull Off
    19.             LOD 200
    20.  
    21.             CGPROGRAM
    22.             //the shader is a surface shader, meaning that it will be extended by unity in the background
    23.             //to have fancy lighting and other features
    24.             //our surface shader function is called surf and we use our custom lighting model
    25.             //fullforwardshadows makes sure unity adds the shadow passes the shader might need
    26.             //vertex:vert makes the shader use vert as a vertex shader function
    27.             #pragma surface surf Standard fullforwardshadows addshadow
    28.             #pragma target 3.0
    29.  
    30.             sampler2D _MainTex;
    31.             fixed4 _Color;
    32.  
    33.             half _Smoothness;
    34.             half _Metallic;
    35.             //half3 _Emission;
    36.  
    37.             float4 _Plane;
    38.  
    39.             //float4 _CutoffColor;
    40.  
    41.             //input struct which is automatically filled by unity
    42.             struct Input {
    43.                 float2 uv_MainTex;
    44.                 float3 worldPos;
    45.                 //float facing : VFACE;
    46.             };
    47.  
    48.             //the surface shader function which sets parameters the lighting function then uses
    49.             void surf(Input i, inout SurfaceOutputStandard o) {
    50.                 //calculate signed distance to plane
    51.                 float distance = dot(i.worldPos, _Plane.xyz);
    52.                 distance = distance + _Plane.w;
    53.                 //discard surface above plane
    54.                 clip(-distance);
    55.  
    56.                 //float facing = i.facing * 0.5 + 0.5;
    57.  
    58.                 //normal color stuff
    59.                 fixed4 col = tex2D(_MainTex, i.uv_MainTex);
    60.                 col *= _Color;
    61.                 o.Albedo = col.rgb;
    62.                 o.Metallic = _Metallic;
    63.                 o.Smoothness = _Smoothness;
    64.  
    65.                 //o.Emission = lerp(_CutoffColor, _Emission, facing);
    66.             }
    67.             ENDCG
    68.         }
    69.             FallBack "Standard" //fallback adds a shadow pass so we get shadows on other objects
    70.                 //FallBack "Diffuse"
    71.  
    72.  
    73. }
    To make it work i add a plane as child of the player.
    1.png
    And add this script on the plane :
    Code (CSharp):
    1. using UnityEngine;
    2.  
    3.  
    4. [ExecuteAlways]
    5. public class ClippingPlane : MonoBehaviour
    6. {
    7.     public bool canCut;
    8.     public GameObject[] objectsToRemove;
    9.  
    10.     //UI
    11.     public GameObject wait;
    12.     public GameObject dynamicCut;
    13.     public GameObject staticCut;
    14.  
    15.     //material we pass the values to
    16.     public GameObject player;
    17.     public Material[] mat;
    18.  
    19.     private void Start()
    20.     {
    21.         WaitCut();
    22.         player.GetComponent<PlayerXbox>().isFlying = false;
    23.     }
    24.     //execute every frame
    25.     public void Update()
    26.     {
    27.  
    28.         //create plane
    29.         Plane plane = new Plane(transform.up, transform.position);
    30.         //transfer values from plane to vector4
    31.         Vector4 planeRepresentation = new Vector4(plane.normal.x, plane.normal.y, plane.normal.z, plane.distance);
    32.         //pass vector to shader
    33.         foreach (Material mat in mat)
    34.         {
    35.             mat.SetVector("_Plane", planeRepresentation);
    36.         }
    37.  
    38.     }
    39.  
    40.     public void DisableObjects()
    41.     {
    42.         foreach (GameObject toRemove in objectsToRemove)
    43.         {
    44.             toRemove.SetActive(false);
    45.         }
    46.     }
    47.  
    48.     public void EnableRemovedObjects()
    49.     {
    50.         foreach (GameObject toRemove in objectsToRemove)
    51.         {
    52.             toRemove.SetActive(true);
    53.         }
    54.     }
    55.  
    56.     public void Cut()
    57.     {
    58.         if (canCut == true)
    59.         {
    60.             gameObject.transform.localPosition = new Vector3(0, 0, 3.5f);
    61.             DisableObjects();
    62.             player.GetComponent<PlayerXbox>().isFlying = true;
    63.             player.GetComponent<PlayerXbox>().canFly = false;
    64.             player.GetComponent<PlayerXbox>().NoGround();
    65.  
    66.             wait.SetActive(false);
    67.             dynamicCut.SetActive(true);
    68.             staticCut.SetActive(false);
    69.         }
    70.     }
    71.  
    72.     public void FixCut()
    73.     {
    74.         if (canCut == true)
    75.         {
    76.             gameObject.SetActive(false);
    77.  
    78.             wait.SetActive(false);
    79.             dynamicCut.SetActive(false);
    80.             staticCut.SetActive(true);
    81.         }
    82.     }
    83.  
    84.     public void WaitCut()
    85.     {
    86.         if (canCut == true)
    87.         {
    88.             gameObject.SetActive(true);
    89.             gameObject.transform.localPosition = new Vector3(0, 0, -500f);
    90.             EnableRemovedObjects();
    91.             player.GetComponent<PlayerXbox>().isFlying = true;
    92.             player.GetComponent<PlayerXbox>().canFly = true;
    93.  
    94.             wait.SetActive(true);
    95.             dynamicCut.SetActive(false);
    96.             staticCut.SetActive(false);
    97.         }
    98.     }
    99. }
    It works well for cutting :
    Player 4k_2022-02-04-08-34-18.jpg

    But it makes something weird, there is a light reflection following the player at his back :
    Player 4k_2022-02-04-08-23-43.jpg Player 4k_2022-02-04-08-24-35.jpg

    When i use the standard shader there is not this light following me so it comes from the cutting shader.

    So i tryied to combine the 2 shaders but i don't achieve it.

    Can you help me to understand what the problem is and to resolve it ?
    Thanks !
     
    Last edited: Feb 11, 2022
  2. bgolus

    bgolus

    Joined:
    Dec 7, 2012
    Posts:
    12,317
    This looks like you're using an orthographic camera in the last two images. I'm not entirely sure why you're not seeing the same issue with the Standard shader, but basically any specular lighting breaks fairly badly when using an orthographic projection.

    I would recommend not using an orthographic camera, or switching to a Surface Shader using Lambert shading (aka, diffuse only).
     
  3. KarbenC

    KarbenC

    Joined:
    Dec 14, 2018
    Posts:
    12
    Hi bgolus (the famous !)

    Yes i use the orthographic camera, i have to switch between the 2 types of camera...

    I try to reduce smoothness and yes it delete this bad effect. This works well, so i could change all textures smoothness parameter when switching cameras. That's a solution but a little complicated with lots of textures.

    So i tried to use Lambert with this line :
    Code (CSharp):
    1. #pragma surface surf Lambert
    I also tried to change the fallback to "Diffuse" or "VertexLit" but i still have the light reflection following my player.

    Here is the standard shader script :
    Code (CSharp):
    1. // Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)
    2.  
    3. Shader "Standard"
    4. {
    5.     Properties
    6.     {
    7.         _Color("Color", Color) = (1,1,1,1)
    8.         _MainTex("Albedo", 2D) = "white" {}
    9.  
    10.         _Cutoff("Alpha Cutoff", Range(0.0, 1.0)) = 0.5
    11.  
    12.         _Glossiness("Smoothness", Range(0.0, 1.0)) = 0.5
    13.         _GlossMapScale("Smoothness Scale", Range(0.0, 1.0)) = 1.0
    14.         [Enum(Metallic Alpha,0,Albedo Alpha,1)] _SmoothnessTextureChannel ("Smoothness texture channel", Float) = 0
    15.  
    16.         [Gamma] _Metallic("Metallic", Range(0.0, 1.0)) = 0.0
    17.         _MetallicGlossMap("Metallic", 2D) = "white" {}
    18.  
    19.         [ToggleOff] _SpecularHighlights("Specular Highlights", Float) = 1.0
    20.         [ToggleOff] _GlossyReflections("Glossy Reflections", Float) = 1.0
    21.  
    22.         _BumpScale("Scale", Float) = 1.0
    23.         [Normal] _BumpMap("Normal Map", 2D) = "bump" {}
    24.  
    25.         _Parallax ("Height Scale", Range (0.005, 0.08)) = 0.02
    26.         _ParallaxMap ("Height Map", 2D) = "black" {}
    27.  
    28.         _OcclusionStrength("Strength", Range(0.0, 1.0)) = 1.0
    29.         _OcclusionMap("Occlusion", 2D) = "white" {}
    30.  
    31.         _EmissionColor("Color", Color) = (0,0,0)
    32.         _EmissionMap("Emission", 2D) = "white" {}
    33.  
    34.         _DetailMask("Detail Mask", 2D) = "white" {}
    35.  
    36.         _DetailAlbedoMap("Detail Albedo x2", 2D) = "grey" {}
    37.         _DetailNormalMapScale("Scale", Float) = 1.0
    38.         [Normal] _DetailNormalMap("Normal Map", 2D) = "bump" {}
    39.  
    40.         [Enum(UV0,0,UV1,1)] _UVSec ("UV Set for secondary textures", Float) = 0
    41.  
    42.  
    43.         // Blending state
    44.         [HideInInspector] _Mode ("__mode", Float) = 0.0
    45.         [HideInInspector] _SrcBlend ("__src", Float) = 1.0
    46.         [HideInInspector] _DstBlend ("__dst", Float) = 0.0
    47.         [HideInInspector] _ZWrite ("__zw", Float) = 1.0
    48.     }
    49.  
    50.     CGINCLUDE
    51.         #define UNITY_SETUP_BRDF_INPUT MetallicSetup
    52.     ENDCG
    53.  
    54.     SubShader
    55.     {
    56.         Tags { "RenderType"="Opaque" "PerformanceChecks"="False" }
    57.         LOD 300
    58.  
    59.  
    60.         // ------------------------------------------------------------------
    61.         //  Base forward pass (directional light, emission, lightmaps, ...)
    62.         Pass
    63.         {
    64.             Name "FORWARD"
    65.             Tags { "LightMode" = "ForwardBase" }
    66.  
    67.             Blend [_SrcBlend] [_DstBlend]
    68.             ZWrite [_ZWrite]
    69.  
    70.             CGPROGRAM
    71.             #pragma target 3.0
    72.  
    73.             // -------------------------------------
    74.  
    75.             #pragma shader_feature _NORMALMAP
    76.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    77.             #pragma shader_feature _EMISSION
    78.             #pragma shader_feature_local _METALLICGLOSSMAP
    79.             #pragma shader_feature_local _DETAIL_MULX2
    80.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    81.             #pragma shader_feature_local _SPECULARHIGHLIGHTS_OFF
    82.             #pragma shader_feature_local _GLOSSYREFLECTIONS_OFF
    83.             #pragma shader_feature_local _PARALLAXMAP
    84.  
    85.             #pragma multi_compile_fwdbase
    86.             #pragma multi_compile_fog
    87.             #pragma multi_compile_instancing
    88.             // Uncomment the following line to enable dithering LOD crossfade. Note: there are more in the file to uncomment for other passes.
    89.             //#pragma multi_compile _ LOD_FADE_CROSSFADE
    90.  
    91.             #pragma vertex vertBase
    92.             #pragma fragment fragBase
    93.             #include "UnityStandardCoreForward.cginc"
    94.  
    95.             ENDCG
    96.         }
    97.         // ------------------------------------------------------------------
    98.         //  Additive forward pass (one light per pass)
    99.         Pass
    100.         {
    101.             Name "FORWARD_DELTA"
    102.             Tags { "LightMode" = "ForwardAdd" }
    103.             Blend [_SrcBlend] One
    104.             Fog { Color (0,0,0,0) } // in additive pass fog should be black
    105.             ZWrite Off
    106.             ZTest LEqual
    107.  
    108.             CGPROGRAM
    109.             #pragma target 3.0
    110.  
    111.             // -------------------------------------
    112.  
    113.  
    114.             #pragma shader_feature _NORMALMAP
    115.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    116.             #pragma shader_feature_local _METALLICGLOSSMAP
    117.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    118.             #pragma shader_feature_local _SPECULARHIGHLIGHTS_OFF
    119.             #pragma shader_feature_local _DETAIL_MULX2
    120.             #pragma shader_feature_local _PARALLAXMAP
    121.  
    122.             #pragma multi_compile_fwdadd_fullshadows
    123.             #pragma multi_compile_fog
    124.             // Uncomment the following line to enable dithering LOD crossfade. Note: there are more in the file to uncomment for other passes.
    125.             //#pragma multi_compile _ LOD_FADE_CROSSFADE
    126.  
    127.             #pragma vertex vertAdd
    128.             #pragma fragment fragAdd
    129.             #include "UnityStandardCoreForward.cginc"
    130.  
    131.             ENDCG
    132.         }
    133.         // ------------------------------------------------------------------
    134.         //  Shadow rendering pass
    135.         Pass {
    136.             Name "ShadowCaster"
    137.             Tags { "LightMode" = "ShadowCaster" }
    138.  
    139.             ZWrite On ZTest LEqual
    140.  
    141.             CGPROGRAM
    142.             #pragma target 3.0
    143.  
    144.             // -------------------------------------
    145.  
    146.  
    147.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    148.             #pragma shader_feature_local _METALLICGLOSSMAP
    149.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    150.             #pragma shader_feature_local _PARALLAXMAP
    151.             #pragma multi_compile_shadowcaster
    152.             #pragma multi_compile_instancing
    153.             // Uncomment the following line to enable dithering LOD crossfade. Note: there are more in the file to uncomment for other passes.
    154.             //#pragma multi_compile _ LOD_FADE_CROSSFADE
    155.  
    156.             #pragma vertex vertShadowCaster
    157.             #pragma fragment fragShadowCaster
    158.  
    159.             #include "UnityStandardShadow.cginc"
    160.  
    161.             ENDCG
    162.         }
    163.         // ------------------------------------------------------------------
    164.         //  Deferred pass
    165.         Pass
    166.         {
    167.             Name "DEFERRED"
    168.             Tags { "LightMode" = "Deferred" }
    169.  
    170.             CGPROGRAM
    171.             #pragma target 3.0
    172.             #pragma exclude_renderers nomrt
    173.  
    174.  
    175.             // -------------------------------------
    176.  
    177.             #pragma shader_feature _NORMALMAP
    178.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    179.             #pragma shader_feature _EMISSION
    180.             #pragma shader_feature_local _METALLICGLOSSMAP
    181.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    182.             #pragma shader_feature_local _SPECULARHIGHLIGHTS_OFF
    183.             #pragma shader_feature_local _DETAIL_MULX2
    184.             #pragma shader_feature_local _PARALLAXMAP
    185.  
    186.             #pragma multi_compile_prepassfinal
    187.             #pragma multi_compile_instancing
    188.             // Uncomment the following line to enable dithering LOD crossfade. Note: there are more in the file to uncomment for other passes.
    189.             //#pragma multi_compile _ LOD_FADE_CROSSFADE
    190.  
    191.             #pragma vertex vertDeferred
    192.             #pragma fragment fragDeferred
    193.  
    194.             #include "UnityStandardCore.cginc"
    195.  
    196.             ENDCG
    197.         }
    198.  
    199.         // ------------------------------------------------------------------
    200.         // Extracts information for lightmapping, GI (emission, albedo, ...)
    201.         // This pass it not used during regular rendering.
    202.         Pass
    203.         {
    204.             Name "META"
    205.             Tags { "LightMode"="Meta" }
    206.  
    207.             Cull Off
    208.  
    209.             CGPROGRAM
    210.             #pragma vertex vert_meta
    211.             #pragma fragment frag_meta
    212.  
    213.             #pragma shader_feature _EMISSION
    214.             #pragma shader_feature_local _METALLICGLOSSMAP
    215.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    216.             #pragma shader_feature_local _DETAIL_MULX2
    217.             #pragma shader_feature EDITOR_VISUALIZATION
    218.  
    219.             #include "UnityStandardMeta.cginc"
    220.             ENDCG
    221.         }
    222.     }
    223.  
    224.     SubShader
    225.     {
    226.         Tags { "RenderType"="Opaque" "PerformanceChecks"="False" }
    227.         LOD 150
    228.  
    229.         // ------------------------------------------------------------------
    230.         //  Base forward pass (directional light, emission, lightmaps, ...)
    231.         Pass
    232.         {
    233.             Name "FORWARD"
    234.             Tags { "LightMode" = "ForwardBase" }
    235.  
    236.             Blend [_SrcBlend] [_DstBlend]
    237.             ZWrite [_ZWrite]
    238.  
    239.             CGPROGRAM
    240.             #pragma target 2.0
    241.  
    242.             #pragma shader_feature _NORMALMAP
    243.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    244.             #pragma shader_feature _EMISSION
    245.             #pragma shader_feature_local _METALLICGLOSSMAP
    246.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    247.             #pragma shader_feature_local _SPECULARHIGHLIGHTS_OFF
    248.             #pragma shader_feature_local _GLOSSYREFLECTIONS_OFF
    249.             // SM2.0: NOT SUPPORTED shader_feature_local _DETAIL_MULX2
    250.             // SM2.0: NOT SUPPORTED shader_feature_local _PARALLAXMAP
    251.  
    252.             #pragma skip_variants SHADOWS_SOFT DIRLIGHTMAP_COMBINED
    253.  
    254.             #pragma multi_compile_fwdbase
    255.             #pragma multi_compile_fog
    256.  
    257.             #pragma vertex vertBase
    258.             #pragma fragment fragBase
    259.             #include "UnityStandardCoreForward.cginc"
    260.  
    261.             ENDCG
    262.         }
    263.         // ------------------------------------------------------------------
    264.         //  Additive forward pass (one light per pass)
    265.         Pass
    266.         {
    267.             Name "FORWARD_DELTA"
    268.             Tags { "LightMode" = "ForwardAdd" }
    269.             Blend [_SrcBlend] One
    270.             Fog { Color (0,0,0,0) } // in additive pass fog should be black
    271.             ZWrite Off
    272.             ZTest LEqual
    273.  
    274.             CGPROGRAM
    275.             #pragma target 2.0
    276.  
    277.             #pragma shader_feature _NORMALMAP
    278.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    279.             #pragma shader_feature_local _METALLICGLOSSMAP
    280.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    281.             #pragma shader_feature_local _SPECULARHIGHLIGHTS_OFF
    282.             #pragma shader_feature_local _DETAIL_MULX2
    283.             // SM2.0: NOT SUPPORTED shader_feature_local _PARALLAXMAP
    284.             #pragma skip_variants SHADOWS_SOFT
    285.  
    286.             #pragma multi_compile_fwdadd_fullshadows
    287.             #pragma multi_compile_fog
    288.  
    289.             #pragma vertex vertAdd
    290.             #pragma fragment fragAdd
    291.             #include "UnityStandardCoreForward.cginc"
    292.  
    293.             ENDCG
    294.         }
    295.         // ------------------------------------------------------------------
    296.         //  Shadow rendering pass
    297.         Pass {
    298.             Name "ShadowCaster"
    299.             Tags { "LightMode" = "ShadowCaster" }
    300.  
    301.             ZWrite On ZTest LEqual
    302.  
    303.             CGPROGRAM
    304.             #pragma target 2.0
    305.  
    306.             #pragma shader_feature_local _ _ALPHATEST_ON _ALPHABLEND_ON _ALPHAPREMULTIPLY_ON
    307.             #pragma shader_feature_local _METALLICGLOSSMAP
    308.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    309.             #pragma skip_variants SHADOWS_SOFT
    310.             #pragma multi_compile_shadowcaster
    311.  
    312.             #pragma vertex vertShadowCaster
    313.             #pragma fragment fragShadowCaster
    314.  
    315.             #include "UnityStandardShadow.cginc"
    316.  
    317.             ENDCG
    318.         }
    319.  
    320.         // ------------------------------------------------------------------
    321.         // Extracts information for lightmapping, GI (emission, albedo, ...)
    322.         // This pass it not used during regular rendering.
    323.         Pass
    324.         {
    325.             Name "META"
    326.             Tags { "LightMode"="Meta" }
    327.  
    328.             Cull Off
    329.  
    330.             CGPROGRAM
    331.             #pragma vertex vert_meta
    332.             #pragma fragment frag_meta
    333.  
    334.             #pragma shader_feature _EMISSION
    335.             #pragma shader_feature_local _METALLICGLOSSMAP
    336.             #pragma shader_feature_local _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A
    337.             #pragma shader_feature_local _DETAIL_MULX2
    338.             #pragma shader_feature EDITOR_VISUALIZATION
    339.  
    340.             #include "UnityStandardMeta.cginc"
    341.             ENDCG
    342.         }
    343.     }
    344.  
    345.  
    346.     FallBack "VertexLit"
    347.     CustomEditor "StandardShaderGUI"
    348. }
    349.  
    Can't we combine the clipping shader script into it ? There is no much lines in it.
     
  4. bgolus

    bgolus

    Joined:
    Dec 7, 2012
    Posts:
    12,317
    There isn't a lot of code in that file because it's all in external files that are being included. All told the Standard shader has a few thousand lines of shader code. To add clipping support would require making copies of and modify several of those files. Especially to make shadows support it.
     
  5. KarbenC

    KarbenC

    Joined:
    Dec 14, 2018
    Posts:
    12
    Ok, thanks for the explanation.
    I retry with the standard shader but in fact i still have the light reflection following the player (as you said there was no reason it doesn't do).
    So i just remove the smoothness of some materials...