So I'm rendering a mesh to a render texture for an outline effect. In the HDRP pipeline UnityObjectToClipPos doesn't seem to work because when I try to merge the everything back together the outline is not in the correct position. Any ideas on how I render this mesh with the correct matrices?


Shader "Hidden/Shader/FlatRender"
        _Color ("Color", Color) = (1,1,1,1)
        Tags { "RenderType"="Opaque" }
        LOD 100

            #pragma vertex vert
            #pragma fragment frag

            #include "UnityCG.cginc"

            struct appdata
                float4 vertex : POSITION;

            struct v2f
                float4 vertex : SV_POSITION;

            float4 _Color;

            v2f vert (appdata v)
                v2f o;
                o.vertex = UnityObjectToClipPos(v.vertex);
                return o;

            fixed4 frag (v2f i) : SV_Target
                return _Color;

Outline Post Processing

using System;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.Experimental.Rendering;
using UnityEngine.Rendering.HighDefinition;

[Serializable, VolumeComponentMenu("Post-processing/Custom/JumpFloodOutline")]
public sealed class JumpFloodOutline : CustomPostProcessVolumeComponent, IPostProcessComponent
    [Tooltip("Controls the thickness of the outline")]
    public ClampedFloatParameter Thickness = new ClampedFloatParameter(4.0f,0.0f,50.0f);
    [Tooltip("Outline color")]
    public ColorParameter OutlineColor = new ColorParameter(Color.white,true,true,true);

    private Material m_FlatRender;
    //private Material m_BlurRender;
    private Material m_MergeOutline;
    private int silhouetteBufferID = Shader.PropertyToID("_SilhouetteBuffer");
    private int inputTextureID = Shader.PropertyToID("_InputTexture");
    private int colorID = Shader.PropertyToID("_Color");

    public bool IsActive()
        return m_FlatRender != null && OutlineObjects.Count > 0 && Thickness.value > 0f && OutlineColor.value.a > 0.0f;
    // Do not forget to add this post process in the Custom Post Process Orders list (Project Settings > HDRP Default Settings).
    public override CustomPostProcessInjectionPoint injectionPoint => CustomPostProcessInjectionPoint.BeforeTAA;

    const string kBlurShader = "Hidden/Shader/Blur";
    const string kFlatShader = "Hidden/Shader/FlatRender";
    const string kMergeShader = "Hidden/Shader/MergeOutline";

    public static List<OutlineObject> OutlineObjects = new List<OutlineObject>(); 

    private Material LoadMaterial(string shaderName)
        var shader = Shader.Find(shaderName);
        if (shader != null)
            return new Material(shader);
            Debug.LogError($"Unable to find shader '{shaderName}'. Post Process Volume JumpFloodOutline is unable to load.");
            return null;

    public override void Setup()
        m_FlatRender = LoadMaterial(kFlatShader);
        m_MergeOutline = LoadMaterial(kMergeShader);

    public override void Render(CommandBuffer cmd, HDCamera camera, RTHandle source, RTHandle destination)
        if(camera.camera.name == "SceneCamera")
            cmd.CopyTexture(source, destination);
            RenderTextureDescriptor silhouetteRTD = new RenderTextureDescriptor()
            dimension = TextureDimension.Tex2D,
            width = camera.actualWidth,
            height = camera.actualHeight,

            depthBufferBits = 8,
            volumeDepth = 1,
            msaaSamples = (int)MSAASamples.None,

            useMipMap = false,
            autoGenerateMips = false,
            colorFormat = RenderTextureFormat.ARGB32
        RenderTexture silhouetteTexture = RenderTexture.GetTemporary(silhouetteRTD);

        cmd.ClearRenderTarget(false, true, Color.clear);

        m_FlatRender.SetColor(colorID, OutlineColor.value);
        for (int i = 0; i < OutlineObjects.Count; i++)
            var obj = OutlineObjects[i];
            if (GeometryUtility.TestPlanesAABB(camera.frustum.planes, obj.Renderer.bounds))
                cmd.DrawRenderer(obj.Renderer, m_FlatRender);

        m_MergeOutline.SetTexture("_InputTexture", source);
        m_MergeOutline.SetTexture("_OutlineTexture", silhouetteTexture);
        HDUtils.DrawFullScreen(cmd, m_MergeOutline, destination);

    public override void Cleanup()

Example image of issue

enter image description here


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.