I wrote the following shader which purpose is to force draw a mesh over the rest, regardless z-depth :

Shader "Custom/AlwaysOnTop"
        Tags { "Queue"="Overlay" "RenderType"="Overlay" }
        ZTest Always

        #pragma surface surf Lambert

        struct Input 
            float4 color : COLOR;

        void surf (Input IN, inout SurfaceOutput o)
            o.Albedo = 1;
    Fallback "Diffuse"

It works great, however transparent objects still get draw over it. Setting the queue as Overlay should have solved the problem.

enter image description here

  • White = AlwaysOnTop shader
  • Green = Transparent diffuse
  • Blue = Diffuse

The left face of the white cube should be white, no tinted in green.


2 Answers 2


If you want something overlaying everything the easiest way is to create a second camera with identical settings and position to the first except for:

  • A higher depth. (it's the camera render order, to render after the first camera.)
  • Clear flags set to depth only, this will render everything on top.
  • Culling mask set only to the object layer you want to render.
  • Remove the same layer from the 1st camera's culling mask.
  • Remove the audio listeners, UI rendering, and other extra components from the 2nd camera.

see: https://docs.unity3d.com/Manual/Layers.html

Easiest way to move them together is to make the 2nd camera a child of the 1st. If you change the camera's FOV or other effects you'll need to add a small script to copy the values over.

This is a method that works with Unity 4 as well (and more likely to work with future versions too).


Your material may have too low Render Queue value. Sometimes the material overrides the value it gets from the shader. Try setting it for example to 5000 or so, and see which values work for you. Too low value will render transparent objects after your overlayed object.


You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .