Need help with a simple threshold surface shader

Hi,

I’m new to Unity and writing shaders, so I bumped into a roadblock while trying to do a seemingly simple thing. I want to apply 2 different textures to an object depending on the local height of the pixel. So let’s say for the first half I want an object to be some color and the second half another.

Shader "Custom/Snow3"
{
    Properties {
        _Color ("Color", Color) = (1,0,0,1)
        _MainTex ("Albedo (RGB)", 2D) = "white" {}
    }
    SubShader {
        Tags { "RenderType"="Opaque" }
        LOD 200
       
        CGPROGRAM
        #pragma surface surf Lambert vertex:vert

        #pragma target 3.0

        sampler2D _MainTex;

        struct Input
        {
            float2 uv_MainTex;
            float4 objectSpacePos;
        };

        fixed4 _Color;

        void vert(inout appdata_full v, out Input o) {
            UNITY_INITIALIZE_OUTPUT(Input, o);
            o.objectSpacePos = v.vertex;
        }

        void surf(Input IN, inout SurfaceOutput o) {
            float ```heightGradient``` = (IN.objectSpacePos.y + 1) * 0.5;
            //fixed4 c = tex2D(_MainTex, IN.uv_MainTex) * heightGradient;
            fixed4 c = tex2D(_MainTex, IN.uv_MainTex) * heightGradient * _Color;
            if(heightGradient > 3) {
                c = c + (0, 1, 1, 1);
            }
            o.Albedo = c.rgb;
            o.Alpha = c.a;
        }
        ENDCG
    }
    FallBack "Diffuse"
}

I have this code and it does almost what I want but by my understanding heightGradient should be in the range of <0, 1> since object space is in the range of <-1, 1>. Yet the code above (heightGradient > 3) produces the following result:


Is there something wrong with my mesh?

Your assumptions all seem correct for what should be happening, assuming you are correct about the mesh’s local dimensions. One thing I would wonder about is if your mesh is scaled or if its pivot is moved up in world space, and if changing the scale or object’s position has any effect. If so that probably means the mesh is being batched, either dynamically or more likely statically. Static batching pre-transforms the mesh into world space, so you loose any local space information. You either need to disable static batching for this mesh, or bake the data you want into the vertex data, like the vertex color or an unused UV component.

If moving or scaling the game object has no affect, then I suspect your mesh’s pivot isn’t centered.