using System; using System.Runtime.InteropServices; using UnityEngine; using UnityEngine.Experimental.Rendering; namespace FidelityFX.FrameGen { public static class FrameInterpolation { public static FrameInterpolationContext CreateContext(Vector2Int displaySize, Vector2Int maxRenderSize, FrameInterpolationShaders shaders, GraphicsFormat backBufferFormat, InitializationFlags flags = 0) { if (SystemInfo.usesReversedZBuffer) flags |= InitializationFlags.EnableDepthInverted; else flags &= ~InitializationFlags.EnableDepthInverted; var contextDescription = new ContextDescription { flags = flags, maxRenderSize = maxRenderSize, displaySize = displaySize, backBufferFormat = backBufferFormat, shaders = shaders, }; Debug.Log($"Setting up Frame Interpolation with render size: {maxRenderSize.x}x{maxRenderSize.y}, display size: {displaySize.x}x{displaySize.y}, backbuffer format: {backBufferFormat}, flags: {flags}"); var context = new FrameInterpolationContext(); context.Create(contextDescription); return context; } public struct ContextDescription { public InitializationFlags flags; public Vector2Int maxRenderSize; public Vector2Int displaySize; public GraphicsFormat backBufferFormat; public FrameInterpolationShaders shaders; } public struct PrepareDescription { public DispatchFlags flags; public Vector2Int renderSize; public Vector2 jitterOffset; public Vector2 motionVectorScale; public float frameTimeDelta; public float cameraNear; public float cameraFar; public float viewSpaceToMetersFactor; public float cameraFovAngleVertical; public ResourceView depth; public ResourceView motionVectors; public ulong frameID; } public struct DispatchDescription { public DispatchFlags flags; public Vector2Int displaySize; public Vector2Int renderSize; public ResourceView currentBackBuffer; public ResourceView currentBackBuffer_HUDLess; // Optional public ResourceView output; public RectInt interpolationRect; public ResourceView opticalFlowVector; public ResourceView opticalFlowSceneChangeDetection; public Vector2Int opticalFlowBufferSize; public Vector2 opticalFlowScale; public int opticalFlowBlockSize; public float cameraNear; public float cameraFar; public float cameraFovAngleVertical; public float viewSpaceToMetersFactor; public float frameTimeDelta; public bool reset; public BackbufferTransferFunction backbufferTransferFunction; public Vector2 minMaxLuminance; public ulong frameID; public ResourceView InterpolationSource { get { if (currentBackBuffer_HUDLess.IsValid) return currentBackBuffer_HUDLess; return currentBackBuffer; } } } [Flags] public enum InitializationFlags { EnableDepthInverted = 1 << 0, EnableDepthInfinite = 1 << 1, EnableHDRColorInput = 1 << 3, EnableDisplayResolutionMotionVectors = 1 << 4, EnableJitterMotionVectors = 1 << 5, EnableAsyncSupport = 1 << 6, } [Flags] public enum DispatchFlags { DrawDebugTearLines = 1 << 0, DrawDebugResetIndicators = 1 << 1, DrawDebugView = 1 << 2, } [Serializable, StructLayout(LayoutKind.Sequential)] internal struct Constants { public Vector2Int renderSize; public Vector2Int displaySize; public Vector2 displaySizeRcp; public float cameraNear; public float cameraFar; public Vector2Int upscalerTargetSize; public int mode; public int reset; public Vector4 deviceToViewDepth; public float deltaTime; public int HUDLessAttachedFactor; public Vector2 unused; public Vector2 opticalFlowScale; public int opticalFlowBlockSize; public uint dispatchFlags; public Vector2Int maxRenderSize; public int opticalFlowHalfResMode; public int numInstances; public Vector2Int interpolationRectBase; public Vector2Int interpolationRectSize; public Vector3 debugBarColor; public uint backBufferTransferFunction; public Vector2 minMaxLuminance; public float tanHalfFOV; public float pad; public Vector2 jitter; public Vector2 motionVectorScale; } } }