Correctly sorting transparent geometry can be difficult. It’s basically an unsolved problem in realtime computer graphics. There usually isn’t a single answer that can solve every case. Opaque objects don’t have this problem as they write to the Depth Buffer (ZWrite), which allows Depth Testing (ZTest) to occur to sort on a per-fragment/pixel basis. Unity also will render opaque objects closer to the camera first, so we don’t need to waste time rendering pixels behind others. But with the Transparent queue, shaders typically don’t write to the depth buffer and we have to render objects further away first, in order to achieve the correct Alpha Blending. Even if depth write was enabled, it still wouldn’t sort correctly when blending is involved. Quick tips : Always split Opaque and Transparent parts of a model into separate meshes (or at least separate sub-meshes) and apply separate materials. If your object doesn’t need partial transparency, consider using Opaque with Alpha Clipping instead. In HLSL, use clip(alpha - threshold) or if (alpha < threshold) discard; In Shader Graph, can find this in Graph Settings This could also be paired with Dithering to fake some transparency. For example, see this Shader Graph tutorial by Daniel Ilett In some cases, can swap to a different blend mode. Additive (Blend One One) and Multiplicative (i.e. Blend Zero SrcColor) blending modes in particular would produce the same results regardless of the order those objects are rendered in! Solutions to fixing common transparent sorting issues are listed below. Render Queue Transparent objects will sort based on their mesh origin. If you know that a particular transparent material should always appear behind / on top of others, you can use the Render Queue or Sorting Priority on the material to force the render order. Pre-sorting Mesh Triangle Order When rendering a mesh, the faces are rendered in order of their indices/triangles array. In cases where you don’t have intersecting geometry, it may be possible to pre-sort the triangles to force the draw order. This can be more performant than using the above method, but requires some setup in the modelling program. A mesh consisting of layered spheres. Left : The inner spheres are incorrectly rendering on top. Right : Sorting corrected by combining layers in specific order in Blender. It may vary in each 3D modelling program, but as you combine multiple meshes, the assumption is that the triangles are appended. Example in Blender : Separate each “layer” of triangles into separate objects. Select two layers - outer most layer first. I find it easiest to do this in the Outliner while holding Ctrl Combine/Join with Ctrl+J (while hovering over the 3D Viewport) Repeat steps 2 & 3 until each layer is collapsed down into a single mesh Blender Outliner, showing each layer being combined after repeating these steps. Note that using some Modifiers could change the triangle ordering. You would want to keep using Cull Back with this method. If you need back faces you’d need to duplicate the geometry will flipped faces/normals, and sort these triangles appropriately. May also need to untick the “Optimise Mesh : Polygon Order” on the model import in Unity. As this may reorganise the triangle order. Transparent Depth Prepass When you don’t want to see overlapping faces of the model through itself, we can use a prepass to write to the depth buffer only. When we then render our object normally it can ZTest against this. Left : Normal Render Right : Render with Prepass (Character from Kenney Animated Characters 2) For Built-in RP, can add a pass before your main one : 1 2 3 4 Pass { ZWrite On // Write to the Depth Buffer ColorMask 0 // Don't write to the Color Buffer } (Can find another example here : https://forum.unity.com/threads/transparent-depth-shader-good-for-ghosts.149511/) In other pipelines we can’t use multi-pass shaders, but you can instead use a separate shader/material with -1 on the Sorting Priority (or Render Queue). Can use the following code in a .shader file (Create → Unlit Shader) 1 2 3 4 5 6 7 8 9 10 Shader "Custom/DepthPrepass" { Properties { } SubShader { Tags { "Queue"="Transparent-1" } Pass { ZWrite On ColorMask 0 } } } Can then attach it as a second material on the Mesh Renderer. If the mesh already has multiple sub-meshes / materials, may be better to separate that part of the mesh and use another GameObject & MeshRenderer too. For URP, if you have many objects that need this prepass, then rather than using multiple materials / GameObjects, you can use the Render Objects feature. This allows us to re-render a particular Layer with an Override Material (using our DepthPrepass shader) But note that using this removes the ability to see any other transparent objects through the mesh. (Unless they are moved to the Before Rendering Transparents event too) OIT There are also methods to achieve Order Independent Transparency - But I’m not at all familiar with these. I think they’re quite expensive (either in terms of performance or memory), and Unity does not include any support for them so you’d need to implement this stuff yourself (or find an asset/package that handles it for you. This would require custom shaders too though, so not easy to implement)