Last active
June 17, 2025 21:57
-
-
Save michael-sacco/4d13381cb3322a457a7993012147273a to your computer and use it in GitHub Desktop.
Unity Get Camera Motion Vectors in Custom Pass for Universal Render Pipeline (URP)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #ifndef GETCAMERAMOTIONVECTORS_INCLUDE | |
| #define GETCAMERAMOTIONVECTORS_INCLUDE | |
| #if defined(USING_STEREO_MATRICES) | |
| float4x4 _PrevViewProjMStereo[2]; | |
| #define _PrevViewProjM _PrevViewProjMStereo[unity_StereoEyeIndex] | |
| #define _ViewProjM unity_MatrixVP | |
| #else | |
| float4x4 _ViewProjM; | |
| float4x4 _PrevViewProjM; | |
| #endif | |
| void GetCameraMotionVectors_float(float4 UV, float3 positionOS, out float2 velocity) | |
| { | |
| velocity = 0; | |
| #ifndef SHADERGRAPH_PREVIEW | |
| float4 positionCS = TransformObjectToHClip(positionOS); | |
| float4 projPos = positionCS * 0.5; | |
| projPos.xy = projPos.xy + projPos.w; | |
| half depth = 0.0; | |
| #if UNITY_REVERSED_Z | |
| depth = 1.0; | |
| #endif | |
| float3 viewPos = ComputeViewSpacePosition(projPos.xy, depth, unity_CameraInvProjection); | |
| float3 viewDirectionTemp = mul(unity_CameraInvProjection, float4(UV.xy * 2 - 1, 0.0, -1)); | |
| float3 viewVector = mul(unity_CameraToWorld, float4(viewDirectionTemp, 0.0)); | |
| float3 rayDirection = viewVector / length(viewVector); | |
| float4 worldPos = float4(mul(unity_CameraToWorld, float4(viewPos, 1.0)).xyz, 1.0); | |
| float4 prevPos = worldPos; | |
| float4 prevClipPos = mul(_PrevViewProjM, prevPos); | |
| float4 curClipPos = mul(_ViewProjM, worldPos); | |
| float2 prevPosCS = prevClipPos.xy / prevClipPos.w; | |
| float2 curPosCS = curClipPos.xy / curClipPos.w; | |
| velocity = prevPosCS - curPosCS; | |
| #if UNITY_UV_STARTS_AT_TOP == 0 | |
| velocity.y = -velocity.y; | |
| #endif | |
| velocity.xy *= 0.5; | |
| #endif | |
| } | |
| #endif |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| using UnityEngine; | |
| using UnityEngine.Rendering; | |
| // Note: This form of assigning view projection matrices to shader has been removed from Altos. | |
| // Now we assign the view projection matrices directly to specific material in the Render Pass. | |
| public class WriteGpuVpToShader : MonoBehaviour | |
| { | |
| private Matrix4x4 gpuVPLast; | |
| private Camera cam; | |
| private void Start() | |
| { | |
| RenderPipelineManager.beginCameraRendering += OnBeginCameraRendering; | |
| cam = Camera.main; | |
| cam.depthTextureMode |= DepthTextureMode.MotionVectors; | |
| } | |
| void OnBeginCameraRendering(ScriptableRenderContext context, Camera camera) | |
| { | |
| var gpuProj = GL.GetGPUProjectionMatrix(cam.projectionMatrix, true); | |
| var gpuView = cam.worldToCameraMatrix; | |
| var gpuVP = gpuProj * gpuView; | |
| Shader.SetGlobalMatrix("_ViewProjM", gpuVP); | |
| if (gpuVPLast != null) | |
| Shader.SetGlobalMatrix("_PrevViewProjM", gpuVPLast); | |
| gpuVPLast = gpuVP; | |
| } | |
| void OnDestroy() | |
| { | |
| RenderPipelineManager.beginCameraRendering -= OnBeginCameraRendering; | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment