You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

136 lines
8.4 KiB

using UnityEngine;
using UnityEngine.Experimental.Rendering;
namespace FidelityFX.OpticalFlow
{
internal class OpticalFlowResources
{
public readonly RenderTexture[] OpticalFlowInput = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel1 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel2 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel3 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel4 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel5 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowInputLevel6 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel0 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel1 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel2 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel3 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel4 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel5 = new RenderTexture[2];
public readonly RenderTexture[] OpticalFlowLevel6 = new RenderTexture[2];
public RenderTexture OpticalFlowSCDHistogram;
public RenderTexture OpticalFlowSCDPreviousHistogram;
public RenderTexture OpticalFlowSCDTemp;
public void Create(OpticalFlow.ContextDescription contextDescription)
{
Vector2Int opticalFlowInputTextureSize = contextDescription.resolution;
const int minBlockSize = 8;
Vector2Int opticalFlowTextureSize = OpticalFlow.GetOpticalFlowTextureSize(contextDescription.resolution, minBlockSize);
Vector2Int opticalFlowLevel1TextureSize = NextLevelSize(opticalFlowTextureSize);
Vector2Int opticalFlowLevel2TextureSize = NextLevelSize(opticalFlowLevel1TextureSize);
Vector2Int opticalFlowLevel3TextureSize = NextLevelSize(opticalFlowLevel2TextureSize);
Vector2Int opticalFlowLevel4TextureSize = NextLevelSize(opticalFlowLevel3TextureSize);
Vector2Int opticalFlowLevel5TextureSize = NextLevelSize(opticalFlowLevel4TextureSize);
Vector2Int opticalFlowLevel6TextureSize = NextLevelSize(opticalFlowLevel5TextureSize);
Vector2Int opticalFlowHistogramTextureSize = OpticalFlow.GetOpticalFlowHistogramSize(0);
Vector2Int globalMotionSearchMaxDispatchSize = OpticalFlow.GetGlobalMotionSearchDispatchSize(0);
int globalMotionSearchTextureWidth = 4 + (globalMotionSearchMaxDispatchSize.x * globalMotionSearchMaxDispatchSize.y);
CreateDoubleBufferedResource(OpticalFlowInput, "OPTICALFLOW_OpticalFlowInput", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel1, "OPTICALFLOW_OpticalFlowInputLevel1-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel2, "OPTICALFLOW_OpticalFlowInputLevel2-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel3, "OPTICALFLOW_OpticalFlowInputLevel3-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel4, "OPTICALFLOW_OpticalFlowInputLevel4-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel5, "OPTICALFLOW_OpticalFlowInputLevel5-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
opticalFlowInputTextureSize = new Vector2Int(opticalFlowInputTextureSize.x >> 1, opticalFlowInputTextureSize.y >> 1);
CreateDoubleBufferedResource(OpticalFlowInputLevel6, "OPTICALFLOW_OpticalFlowInputLevel6-", opticalFlowInputTextureSize, GraphicsFormat.R8_UInt);
CreateDoubleBufferedResource(OpticalFlowLevel0, "OPTICALFLOW_OpticalFlow", opticalFlowTextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel1, "OPTICALFLOW_OpticalFlowLevel1-", opticalFlowLevel1TextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel2, "OPTICALFLOW_OpticalFlowLevel2-", opticalFlowLevel2TextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel3, "OPTICALFLOW_OpticalFlowLevel3-", opticalFlowLevel3TextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel4, "OPTICALFLOW_OpticalFlowLevel4-", opticalFlowLevel4TextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel5, "OPTICALFLOW_OpticalFlowLevel5-", opticalFlowLevel5TextureSize, GraphicsFormat.R16G16_SInt);
CreateDoubleBufferedResource(OpticalFlowLevel6, "OPTICALFLOW_OpticalFlowLevel6-", opticalFlowLevel6TextureSize, GraphicsFormat.R16G16_SInt);
OpticalFlowSCDHistogram = CreateResource("OPTICALFLOW_OpticalFlowSCDHistogram", new Vector2Int(OpticalFlow.GetSCDHistogramTextureWidth(), 1), GraphicsFormat.R32_UInt);
OpticalFlowSCDPreviousHistogram = CreateResource("OPTICALFLOW_OpticalFlowSCDPreviousHistogram", new Vector2Int(OpticalFlow.GetSCDHistogramTextureWidth(), 1), GraphicsFormat.R32_SFloat);
OpticalFlowSCDTemp = CreateResource("OPTICALFLOW_OpticalFlowSCDTemp", new Vector2Int(3, 1), GraphicsFormat.R32_UInt);
}
public void Destroy()
{
DestroyResource(ref OpticalFlowSCDTemp);
DestroyResource(ref OpticalFlowSCDPreviousHistogram);
DestroyResource(ref OpticalFlowSCDHistogram);
DestroyResource(OpticalFlowLevel6);
DestroyResource(OpticalFlowLevel5);
DestroyResource(OpticalFlowLevel4);
DestroyResource(OpticalFlowLevel3);
DestroyResource(OpticalFlowLevel2);
DestroyResource(OpticalFlowLevel1);
DestroyResource(OpticalFlowLevel0);
DestroyResource(OpticalFlowInputLevel6);
DestroyResource(OpticalFlowInputLevel5);
DestroyResource(OpticalFlowInputLevel4);
DestroyResource(OpticalFlowInputLevel3);
DestroyResource(OpticalFlowInputLevel2);
DestroyResource(OpticalFlowInputLevel1);
DestroyResource(OpticalFlowInput);
}
private static Vector2Int NextLevelSize(Vector2Int size)
{
return new Vector2Int(AlignUp(size.x, 2) / 2, AlignUp(size.y, 2) / 2);
}
private static int AlignUp(int x, int y)
{
return (x + (y - 1)) & ~(y - 1);
}
private static RenderTexture CreateResource(string name, Vector2Int size, GraphicsFormat format)
{
var rt = new RenderTexture(size.x, size.y, 0, format) { name = name, enableRandomWrite = true };
rt.Create();
return rt;
}
private static void CreateDoubleBufferedResource(RenderTexture[] resource, string name, Vector2Int size, GraphicsFormat format)
{
for (int i = 0; i < 2; ++i)
{
resource[i] = new RenderTexture(size.x, size.y, 0, format) { name = name + (i + 1), enableRandomWrite = true };
resource[i].Create();
}
}
private static void DestroyResource(ref RenderTexture resource)
{
if (resource == null)
return;
resource.Release();
resource = null;
}
private static void DestroyResource(RenderTexture[] resource)
{
for (int i = 0; i < resource.Length; ++i)
DestroyResource(ref resource[i]);
}
}
}