more seperation
This commit is contained in:
@@ -104,6 +104,8 @@ set(APP_SOURCES
|
|||||||
"${APP_DIR}/runtime/RuntimeHost.h"
|
"${APP_DIR}/runtime/RuntimeHost.h"
|
||||||
"${APP_DIR}/runtime/HealthTelemetry.cpp"
|
"${APP_DIR}/runtime/HealthTelemetry.cpp"
|
||||||
"${APP_DIR}/runtime/HealthTelemetry.h"
|
"${APP_DIR}/runtime/HealthTelemetry.h"
|
||||||
|
"${APP_DIR}/runtime/RuntimeCoordinator.cpp"
|
||||||
|
"${APP_DIR}/runtime/RuntimeCoordinator.h"
|
||||||
"${APP_DIR}/runtime/RuntimeSnapshotProvider.cpp"
|
"${APP_DIR}/runtime/RuntimeSnapshotProvider.cpp"
|
||||||
"${APP_DIR}/runtime/RuntimeSnapshotProvider.h"
|
"${APP_DIR}/runtime/RuntimeSnapshotProvider.h"
|
||||||
"${APP_DIR}/runtime/RuntimeClock.cpp"
|
"${APP_DIR}/runtime/RuntimeClock.cpp"
|
||||||
|
|||||||
@@ -1,28 +0,0 @@
|
|||||||
|
|
||||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
|
||||||
# Visual Studio 2013
|
|
||||||
VisualStudioVersion = 12.0.21005.1
|
|
||||||
MinimumVisualStudioVersion = 10.0.40219.1
|
|
||||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "LoopThroughWithOpenGLCompositing", "LoopThroughWithOpenGLCompositing.vcxproj", "{92C79085-CA51-4008-95DB-5403D2E19885}"
|
|
||||||
EndProject
|
|
||||||
Global
|
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
|
||||||
Debug|Win32 = Debug|Win32
|
|
||||||
Debug|x64 = Debug|x64
|
|
||||||
Release|Win32 = Release|Win32
|
|
||||||
Release|x64 = Release|x64
|
|
||||||
EndGlobalSection
|
|
||||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Debug|Win32.ActiveCfg = Debug|Win32
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Debug|Win32.Build.0 = Debug|Win32
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Debug|x64.ActiveCfg = Debug|x64
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Debug|x64.Build.0 = Debug|x64
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Release|Win32.ActiveCfg = Release|Win32
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Release|Win32.Build.0 = Release|Win32
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Release|x64.ActiveCfg = Release|x64
|
|
||||||
{92C79085-CA51-4008-95DB-5403D2E19885}.Release|x64.Build.0 = Release|x64
|
|
||||||
EndGlobalSection
|
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
|
||||||
HideSolutionNode = FALSE
|
|
||||||
EndGlobalSection
|
|
||||||
EndGlobal
|
|
||||||
@@ -1,299 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
|
||||||
<ItemGroup Label="ProjectConfigurations">
|
|
||||||
<ProjectConfiguration Include="Debug|Win32">
|
|
||||||
<Configuration>Debug</Configuration>
|
|
||||||
<Platform>Win32</Platform>
|
|
||||||
</ProjectConfiguration>
|
|
||||||
<ProjectConfiguration Include="Debug|x64">
|
|
||||||
<Configuration>Debug</Configuration>
|
|
||||||
<Platform>x64</Platform>
|
|
||||||
</ProjectConfiguration>
|
|
||||||
<ProjectConfiguration Include="Release|Win32">
|
|
||||||
<Configuration>Release</Configuration>
|
|
||||||
<Platform>Win32</Platform>
|
|
||||||
</ProjectConfiguration>
|
|
||||||
<ProjectConfiguration Include="Release|x64">
|
|
||||||
<Configuration>Release</Configuration>
|
|
||||||
<Platform>x64</Platform>
|
|
||||||
</ProjectConfiguration>
|
|
||||||
</ItemGroup>
|
|
||||||
<PropertyGroup Label="Globals">
|
|
||||||
<ProjectGuid>{92C79085-CA51-4008-95DB-5403D2E19885}</ProjectGuid>
|
|
||||||
<RootNamespace>LoopThroughWithOpenGLCompositing</RootNamespace>
|
|
||||||
<Keyword>Win32Proj</Keyword>
|
|
||||||
<WindowsTargetPlatformVersion>10.0.26100.0</WindowsTargetPlatformVersion>
|
|
||||||
</PropertyGroup>
|
|
||||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
|
||||||
<ConfigurationType>Application</ConfigurationType>
|
|
||||||
<PlatformToolset>v143</PlatformToolset>
|
|
||||||
<CharacterSet>MultiByte</CharacterSet>
|
|
||||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
|
||||||
<ConfigurationType>Application</ConfigurationType>
|
|
||||||
<PlatformToolset>v143</PlatformToolset>
|
|
||||||
<CharacterSet>MultiByte</CharacterSet>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
|
|
||||||
<ConfigurationType>Application</ConfigurationType>
|
|
||||||
<PlatformToolset>v143</PlatformToolset>
|
|
||||||
<CharacterSet>MultiByte</CharacterSet>
|
|
||||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
|
|
||||||
<ConfigurationType>Application</ConfigurationType>
|
|
||||||
<PlatformToolset>v143</PlatformToolset>
|
|
||||||
<CharacterSet>MultiByte</CharacterSet>
|
|
||||||
</PropertyGroup>
|
|
||||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
|
||||||
<ImportGroup Label="ExtensionSettings">
|
|
||||||
</ImportGroup>
|
|
||||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">
|
|
||||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
|
||||||
</ImportGroup>
|
|
||||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">
|
|
||||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
|
||||||
</ImportGroup>
|
|
||||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
|
|
||||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
|
||||||
</ImportGroup>
|
|
||||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
|
|
||||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
|
||||||
</ImportGroup>
|
|
||||||
<PropertyGroup Label="UserMacros" />
|
|
||||||
<PropertyGroup>
|
|
||||||
<_ProjectFileVersion>12.0.21005.1</_ProjectFileVersion>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
|
||||||
<OutDir>$(SolutionDir)$(Configuration)\</OutDir>
|
|
||||||
<IntDir>$(Configuration)\</IntDir>
|
|
||||||
<LinkIncremental>true</LinkIncremental>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
|
||||||
<OutDir>$(SolutionDir)$(Platform)\$(Configuration)\</OutDir>
|
|
||||||
<IntDir>$(Platform)\$(Configuration)\</IntDir>
|
|
||||||
<LinkIncremental>true</LinkIncremental>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
|
||||||
<OutDir>$(SolutionDir)$(Configuration)\</OutDir>
|
|
||||||
<IntDir>$(Configuration)\</IntDir>
|
|
||||||
<LinkIncremental>false</LinkIncremental>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
|
||||||
<OutDir>$(SolutionDir)$(Platform)\$(Configuration)\</OutDir>
|
|
||||||
<IntDir>$(Platform)\$(Configuration)\</IntDir>
|
|
||||||
<LinkIncremental>false</LinkIncremental>
|
|
||||||
</PropertyGroup>
|
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
|
||||||
<ClCompile>
|
|
||||||
<Optimization>Disabled</Optimization>
|
|
||||||
<AdditionalIncludeDirectories>.;control;gl;gl\pipeline;gl\renderer;gl\shader;platform;runtime;shader;videoio;videoio\decklink;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
|
||||||
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
|
||||||
<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
|
|
||||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
|
||||||
<PrecompiledHeader />
|
|
||||||
<WarningLevel>Level3</WarningLevel>
|
|
||||||
<DebugInformationFormat>EditAndContinue</DebugInformationFormat>
|
|
||||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
|
||||||
</ClCompile>
|
|
||||||
<Link>
|
|
||||||
<AdditionalDependencies>opengl32.lib;Glu32.lib;Ws2_32.lib;Crypt32.lib;Advapi32.lib;Gdiplus.lib;Ole32.lib;Windowscodecs.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
|
||||||
<SubSystem>Windows</SubSystem>
|
|
||||||
<TargetMachine>MachineX86</TargetMachine>
|
|
||||||
</Link>
|
|
||||||
</ItemDefinitionGroup>
|
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
|
||||||
<Midl>
|
|
||||||
<TargetEnvironment>X64</TargetEnvironment>
|
|
||||||
</Midl>
|
|
||||||
<ClCompile>
|
|
||||||
<Optimization>Disabled</Optimization>
|
|
||||||
<AdditionalIncludeDirectories>.;control;gl;gl\pipeline;gl\renderer;gl\shader;platform;runtime;shader;videoio;videoio\decklink;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
|
||||||
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
|
||||||
<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
|
|
||||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
|
||||||
<PrecompiledHeader />
|
|
||||||
<WarningLevel>Level3</WarningLevel>
|
|
||||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
|
||||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
|
||||||
</ClCompile>
|
|
||||||
<Link>
|
|
||||||
<AdditionalDependencies>opengl32.lib;Glu32.lib;Ws2_32.lib;Crypt32.lib;Advapi32.lib;Gdiplus.lib;Ole32.lib;Windowscodecs.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
|
||||||
<SubSystem>Windows</SubSystem>
|
|
||||||
<TargetMachine>MachineX64</TargetMachine>
|
|
||||||
</Link>
|
|
||||||
</ItemDefinitionGroup>
|
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
|
||||||
<ClCompile>
|
|
||||||
<Optimization>MaxSpeed</Optimization>
|
|
||||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
|
||||||
<AdditionalIncludeDirectories>.;control;gl;gl\pipeline;gl\renderer;gl\shader;platform;runtime;shader;videoio;videoio\decklink;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
|
||||||
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
|
||||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
|
||||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
|
||||||
<PrecompiledHeader />
|
|
||||||
<WarningLevel>Level3</WarningLevel>
|
|
||||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
|
||||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
|
||||||
</ClCompile>
|
|
||||||
<Link>
|
|
||||||
<AdditionalDependencies>opengl32.lib;Glu32.lib;Ws2_32.lib;Crypt32.lib;Advapi32.lib;Gdiplus.lib;Ole32.lib;Windowscodecs.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
|
||||||
<SubSystem>Windows</SubSystem>
|
|
||||||
<OptimizeReferences>true</OptimizeReferences>
|
|
||||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
|
||||||
<TargetMachine>MachineX86</TargetMachine>
|
|
||||||
</Link>
|
|
||||||
</ItemDefinitionGroup>
|
|
||||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
|
||||||
<Midl>
|
|
||||||
<TargetEnvironment>X64</TargetEnvironment>
|
|
||||||
</Midl>
|
|
||||||
<ClCompile>
|
|
||||||
<Optimization>MaxSpeed</Optimization>
|
|
||||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
|
||||||
<AdditionalIncludeDirectories>.;control;gl;gl\pipeline;gl\renderer;gl\shader;platform;runtime;shader;videoio;videoio\decklink;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
|
||||||
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
|
||||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
|
||||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
|
||||||
<PrecompiledHeader />
|
|
||||||
<WarningLevel>Level3</WarningLevel>
|
|
||||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
|
||||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
|
||||||
</ClCompile>
|
|
||||||
<Link>
|
|
||||||
<AdditionalDependencies>opengl32.lib;Glu32.lib;Ws2_32.lib;Crypt32.lib;Advapi32.lib;Gdiplus.lib;Ole32.lib;Windowscodecs.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
|
||||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
|
||||||
<SubSystem>Windows</SubSystem>
|
|
||||||
<OptimizeReferences>true</OptimizeReferences>
|
|
||||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
|
||||||
<TargetMachine>MachineX64</TargetMachine>
|
|
||||||
</Link>
|
|
||||||
</ItemDefinitionGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ClCompile Include="control\ControlServer.cpp" />
|
|
||||||
<ClCompile Include="control\ControlServices.cpp" />
|
|
||||||
<ClCompile Include="control\OscServer.cpp" />
|
|
||||||
<ClCompile Include="control\RuntimeControlBridge.cpp" />
|
|
||||||
<ClCompile Include="control\RuntimeServices.cpp" />
|
|
||||||
<ClCompile Include="gl\renderer\GLExtensions.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\GlobalParamsBuffer.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\GlShaderSources.cpp" />
|
|
||||||
<ClCompile Include="LoopThroughWithOpenGLCompositing.cpp" />
|
|
||||||
<ClCompile Include="gl\OpenGLComposite.cpp" />
|
|
||||||
<ClCompile Include="gl\OpenGLCompositeRuntimeControls.cpp" />
|
|
||||||
<ClCompile Include="gl\RenderEngine.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLRenderPass.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLRenderPipeline.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\ShaderFeedbackBuffers.cpp" />
|
|
||||||
<ClCompile Include="gl\renderer\OpenGLRenderer.cpp" />
|
|
||||||
<ClCompile Include="gl\renderer\RenderTargetPool.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLVideoIOBridge.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\OpenGLShaderPrograms.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\PngScreenshotWriter.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\ShaderProgramCompiler.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\ShaderBuildQueue.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\ShaderTextureBindings.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\TextRasterizer.cpp" />
|
|
||||||
<ClCompile Include="gl\shader\TextureAssetLoader.cpp" />
|
|
||||||
<ClCompile Include="gl\pipeline\TemporalHistoryBuffers.cpp" />
|
|
||||||
<ClCompile Include="stdafx.cpp">
|
|
||||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
|
|
||||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>
|
|
||||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>
|
|
||||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|x64'">Create</PrecompiledHeader>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkAPI_i.c" />
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkDisplayMode.cpp" />
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkFrameTransfer.cpp" />
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkSession.cpp" />
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkVideoIOFormat.cpp" />
|
|
||||||
<ClCompile Include="runtime\HealthTelemetry.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeClock.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeHost.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeJson.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeParameterUtils.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeSnapshotProvider.cpp" />
|
|
||||||
<ClCompile Include="runtime\RuntimeStore.cpp" />
|
|
||||||
<ClCompile Include="shader\ShaderCompiler.cpp" />
|
|
||||||
<ClCompile Include="shader\ShaderPackageRegistry.cpp" />
|
|
||||||
<ClCompile Include="videoio\VideoBackend.cpp" />
|
|
||||||
<ClCompile Include="videoio\VideoIOFormat.cpp" />
|
|
||||||
<ClCompile Include="videoio\VideoPlayoutScheduler.cpp" />
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ClInclude Include="control\ControlServer.h" />
|
|
||||||
<ClInclude Include="control\ControlServices.h" />
|
|
||||||
<ClInclude Include="control\OscServer.h" />
|
|
||||||
<ClInclude Include="control\RuntimeControlBridge.h" />
|
|
||||||
<ClInclude Include="control\RuntimeServices.h" />
|
|
||||||
<ClInclude Include="gl\renderer\GLExtensions.h" />
|
|
||||||
<ClInclude Include="gl\shader\GlobalParamsBuffer.h" />
|
|
||||||
<ClInclude Include="gl\renderer\GlRenderConstants.h" />
|
|
||||||
<ClInclude Include="gl\renderer\GlScopedObjects.h" />
|
|
||||||
<ClInclude Include="gl\shader\GlShaderSources.h" />
|
|
||||||
<ClInclude Include="LoopThroughWithOpenGLCompositing.h" />
|
|
||||||
<ClInclude Include="gl\OpenGLComposite.h" />
|
|
||||||
<ClInclude Include="gl\RenderEngine.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLRenderPass.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLRenderPipeline.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\RenderPassDescriptor.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\ShaderFeedbackBuffers.h" />
|
|
||||||
<ClInclude Include="gl\renderer\OpenGLRenderer.h" />
|
|
||||||
<ClInclude Include="gl\renderer\RenderTargetPool.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLVideoIOBridge.h" />
|
|
||||||
<ClInclude Include="gl\shader\OpenGLShaderPrograms.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\PngScreenshotWriter.h" />
|
|
||||||
<ClInclude Include="gl\shader\ShaderProgramCompiler.h" />
|
|
||||||
<ClInclude Include="gl\shader\ShaderBuildQueue.h" />
|
|
||||||
<ClInclude Include="gl\shader\ShaderTextureBindings.h" />
|
|
||||||
<ClInclude Include="gl\shader\Std140Buffer.h" />
|
|
||||||
<ClInclude Include="gl\shader\TextRasterizer.h" />
|
|
||||||
<ClInclude Include="gl\shader\TextureAssetLoader.h" />
|
|
||||||
<ClInclude Include="gl\pipeline\TemporalHistoryBuffers.h" />
|
|
||||||
<ClInclude Include="platform\NativeHandles.h" />
|
|
||||||
<ClInclude Include="platform\NativeSockets.h" />
|
|
||||||
<ClInclude Include="resource.h" />
|
|
||||||
<ClInclude Include="runtime\HealthTelemetry.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeClock.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeHost.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeJson.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeParameterUtils.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeSnapshotProvider.h" />
|
|
||||||
<ClInclude Include="runtime\RuntimeStore.h" />
|
|
||||||
<ClInclude Include="shader\ShaderCompiler.h" />
|
|
||||||
<ClInclude Include="shader\ShaderPackageRegistry.h" />
|
|
||||||
<ClInclude Include="shader\ShaderTypes.h" />
|
|
||||||
<ClInclude Include="stdafx.h" />
|
|
||||||
<ClInclude Include="targetver.h" />
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkAPI_h.h" />
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkDisplayMode.h" />
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkFrameTransfer.h" />
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkSession.h" />
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkVideoIOFormat.h" />
|
|
||||||
<ClInclude Include="videoio\VideoBackend.h" />
|
|
||||||
<ClInclude Include="videoio\VideoIOFormat.h" />
|
|
||||||
<ClInclude Include="videoio\VideoIOTypes.h" />
|
|
||||||
<ClInclude Include="videoio\VideoPlayoutScheduler.h" />
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<Image Include="LoopThroughWithOpenGLCompositing.ico" />
|
|
||||||
<Image Include="small.ico" />
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<None Include="video_effect.slang" />
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ResourceCompile Include="LoopThroughWithOpenGLCompositing.rc" />
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<Midl Include="..\..\3rdParty\Blackmagic DeckLink SDK 16.0\Win\include\DeckLinkAPI.idl" />
|
|
||||||
</ItemGroup>
|
|
||||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
|
||||||
<ImportGroup Label="ExtensionTargets">
|
|
||||||
</ImportGroup>
|
|
||||||
</Project>
|
|
||||||
@@ -1,338 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
|
||||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
|
||||||
<ItemGroup>
|
|
||||||
<Filter Include="Source Files">
|
|
||||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
|
||||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
|
||||||
</Filter>
|
|
||||||
<Filter Include="Header Files">
|
|
||||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
|
||||||
<Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
|
||||||
</Filter>
|
|
||||||
<Filter Include="Resource Files">
|
|
||||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
|
||||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav</Extensions>
|
|
||||||
</Filter>
|
|
||||||
<Filter Include="DeckLink API">
|
|
||||||
<UniqueIdentifier>{1eab21d6-58f8-49e0-929b-8a4482e04756}</UniqueIdentifier>
|
|
||||||
</Filter>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ClCompile Include="control\ControlServer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="control\ControlServices.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="control\OscServer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="control\RuntimeControlBridge.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\renderer\GLExtensions.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\GlobalParamsBuffer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\GlShaderSources.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="LoopThroughWithOpenGLCompositing.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\OpenGLComposite.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\OpenGLCompositeRuntimeControls.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\RenderEngine.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLRenderPass.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLRenderPipeline.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\ShaderFeedbackBuffers.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\renderer\OpenGLRenderer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\renderer\RenderTargetPool.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\OpenGLShaderPrograms.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\PngScreenshotWriter.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\ShaderProgramCompiler.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\ShaderBuildQueue.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\ShaderTextureBindings.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\TextRasterizer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\shader\TextureAssetLoader.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\TemporalHistoryBuffers.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="gl\pipeline\OpenGLVideoIOBridge.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="stdafx.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkAPI_i.c">
|
|
||||||
<Filter>DeckLink API</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="control\RuntimeServices.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkDisplayMode.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkFrameTransfer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkSession.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\decklink\DeckLinkVideoIOFormat.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\HealthTelemetry.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeClock.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeHost.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeJson.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeParameterUtils.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeSnapshotProvider.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="runtime\RuntimeStore.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="shader\ShaderCompiler.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="shader\ShaderPackageRegistry.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\VideoBackend.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\VideoIOFormat.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="videoio\VideoPlayoutScheduler.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ClInclude Include="control\ControlServer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="control\ControlServices.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="control\OscServer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="control\RuntimeControlBridge.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\renderer\GLExtensions.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\GlobalParamsBuffer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\renderer\GlRenderConstants.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\renderer\GlScopedObjects.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\GlShaderSources.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="LoopThroughWithOpenGLCompositing.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\OpenGLComposite.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\RenderEngine.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLRenderPass.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLRenderPipeline.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\RenderPassDescriptor.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\ShaderFeedbackBuffers.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\renderer\OpenGLRenderer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\renderer\RenderTargetPool.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\OpenGLShaderPrograms.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\PngScreenshotWriter.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\ShaderProgramCompiler.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\ShaderBuildQueue.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\ShaderTextureBindings.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\Std140Buffer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\TextRasterizer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\shader\TextureAssetLoader.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\TemporalHistoryBuffers.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="gl\pipeline\OpenGLVideoIOBridge.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="platform\NativeHandles.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="platform\NativeSockets.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="resource.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\HealthTelemetry.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeHost.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeJson.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeParameterUtils.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeSnapshotProvider.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeStore.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="shader\ShaderCompiler.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="shader\ShaderPackageRegistry.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="shader\ShaderTypes.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="stdafx.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="targetver.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="control\RuntimeServices.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkSession.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkVideoIOFormat.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkAPI_h.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkDisplayMode.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\decklink\DeckLinkFrameTransfer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\VideoBackend.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="runtime\RuntimeClock.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\VideoIOFormat.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\VideoIOTypes.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="videoio\VideoPlayoutScheduler.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<Image Include="LoopThroughWithOpenGLCompositing.ico">
|
|
||||||
<Filter>Resource Files</Filter>
|
|
||||||
</Image>
|
|
||||||
<Image Include="small.ico">
|
|
||||||
<Filter>Resource Files</Filter>
|
|
||||||
</Image>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<ResourceCompile Include="LoopThroughWithOpenGLCompositing.rc">
|
|
||||||
<Filter>Resource Files</Filter>
|
|
||||||
</ResourceCompile>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<Midl Include="..\..\include\DeckLinkAPI.idl">
|
|
||||||
<Filter>DeckLink API</Filter>
|
|
||||||
</Midl>
|
|
||||||
</ItemGroup>
|
|
||||||
<ItemGroup>
|
|
||||||
<None Include="video_effect.slang">
|
|
||||||
<Filter>Resource Files</Filter>
|
|
||||||
</None>
|
|
||||||
</ItemGroup>
|
|
||||||
</Project>
|
|
||||||
@@ -101,9 +101,10 @@ OpenGLComposite::OpenGLComposite(HWND hWnd, HDC hDC, HGLRC hRC) :
|
|||||||
mRuntimeHost = std::make_unique<RuntimeHost>();
|
mRuntimeHost = std::make_unique<RuntimeHost>();
|
||||||
mRuntimeStore = std::make_unique<RuntimeStore>(*mRuntimeHost);
|
mRuntimeStore = std::make_unique<RuntimeStore>(*mRuntimeHost);
|
||||||
mRuntimeSnapshotProvider = std::make_unique<RuntimeSnapshotProvider>(*mRuntimeHost);
|
mRuntimeSnapshotProvider = std::make_unique<RuntimeSnapshotProvider>(*mRuntimeHost);
|
||||||
|
mRuntimeCoordinator = std::make_unique<RuntimeCoordinator>(*mRuntimeStore);
|
||||||
mRenderEngine = std::make_unique<RenderEngine>(
|
mRenderEngine = std::make_unique<RenderEngine>(
|
||||||
*mRuntimeHost,
|
|
||||||
*mRuntimeSnapshotProvider,
|
*mRuntimeSnapshotProvider,
|
||||||
|
mRuntimeHost->GetHealthTelemetry(),
|
||||||
pMutex,
|
pMutex,
|
||||||
hGLDC,
|
hGLDC,
|
||||||
hGLRC,
|
hGLRC,
|
||||||
@@ -202,7 +203,11 @@ bool OpenGLComposite::InitVideoIO()
|
|||||||
}
|
}
|
||||||
if (!mVideoBackend->HasInputDevice() && mRuntimeHost)
|
if (!mVideoBackend->HasInputDevice() && mRuntimeHost)
|
||||||
{
|
{
|
||||||
mRuntimeHost->SetSignalStatus(false, mVideoBackend->InputFrameWidth(), mVideoBackend->InputFrameHeight(), mVideoBackend->InputDisplayModeName());
|
mRuntimeHost->GetHealthTelemetry().ReportSignalStatus(
|
||||||
|
false,
|
||||||
|
mVideoBackend->InputFrameWidth(),
|
||||||
|
mVideoBackend->InputFrameHeight(),
|
||||||
|
mVideoBackend->InputDisplayModeName());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mVideoBackend->ConfigureOutput(videoModes.output, mRuntimeStore && mRuntimeStore->IsExternalKeyingConfigured(), initFailureReason))
|
if (!mVideoBackend->ConfigureOutput(videoModes.output, mRuntimeStore && mRuntimeStore->IsExternalKeyingConfigured(), initFailureReason))
|
||||||
@@ -227,27 +232,15 @@ void OpenGLComposite::paintGL(bool force)
|
|||||||
{
|
{
|
||||||
if (IsIconic(hGLWnd))
|
if (IsIconic(hGLWnd))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
const unsigned previewFps = mRuntimeStore ? mRuntimeStore->GetConfiguredPreviewFps() : 30u;
|
|
||||||
if (previewFps == 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
const auto now = std::chrono::steady_clock::now();
|
|
||||||
const auto minimumInterval = std::chrono::microseconds(1000000 / (previewFps == 0 ? 1u : previewFps));
|
|
||||||
if (mLastPreviewPresentTime != std::chrono::steady_clock::time_point() &&
|
|
||||||
now - mLastPreviewPresentTime < minimumInterval)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mRenderEngine->TryPresentToWindow(mVideoBackend->OutputFrameWidth(), mVideoBackend->OutputFrameHeight()))
|
const unsigned previewFps = mRuntimeStore ? mRuntimeStore->GetConfiguredPreviewFps() : 30u;
|
||||||
|
if (!mRenderEngine->TryPresentPreview(force, previewFps, mVideoBackend->OutputFrameWidth(), mVideoBackend->OutputFrameHeight()))
|
||||||
{
|
{
|
||||||
ValidateRect(hGLWnd, NULL);
|
ValidateRect(hGLWnd, NULL);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
mLastPreviewPresentTime = std::chrono::steady_clock::now();
|
|
||||||
ValidateRect(hGLWnd, NULL);
|
ValidateRect(hGLWnd, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -336,7 +329,7 @@ bool OpenGLComposite::InitOpenGLState()
|
|||||||
MessageBoxA(NULL, compilerErrorMessage, "OpenGL shader failed to load or compile", MB_OK);
|
MessageBoxA(NULL, compilerErrorMessage, "OpenGL shader failed to load or compile", MB_OK);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
mCachedLayerRenderStates = mRenderEngine->CommittedLayerStates();
|
mRuntimeStore->SetCompileStatus(true, "Shader layers compiled successfully.");
|
||||||
mUseCommittedLayerStates = false;
|
mUseCommittedLayerStates = false;
|
||||||
|
|
||||||
mRenderEngine->ResetTemporalHistoryState();
|
mRenderEngine->ResetTemporalHistoryState();
|
||||||
@@ -367,15 +360,8 @@ bool OpenGLComposite::Stop()
|
|||||||
|
|
||||||
bool OpenGLComposite::ReloadShader(bool preserveFeedbackState)
|
bool OpenGLComposite::ReloadShader(bool preserveFeedbackState)
|
||||||
{
|
{
|
||||||
mPreserveFeedbackOnNextShaderBuild = preserveFeedbackState;
|
return mRuntimeCoordinator &&
|
||||||
if (mRuntimeHost)
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->RequestShaderReload(preserveFeedbackState));
|
||||||
{
|
|
||||||
mRuntimeStore->SetCompileStatus(true, "Shader rebuild queued.");
|
|
||||||
mRuntimeStore->ClearReloadRequest();
|
|
||||||
}
|
|
||||||
RequestShaderBuild();
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::RequestScreenshot(std::string& error)
|
bool OpenGLComposite::RequestScreenshot(std::string& error)
|
||||||
@@ -442,7 +428,7 @@ void OpenGLComposite::renderEffect()
|
|||||||
|
|
||||||
const auto applyOscOverlays = [&](std::vector<RuntimeRenderState>& states, bool allowCommit)
|
const auto applyOscOverlays = [&](std::vector<RuntimeRenderState>& states, bool allowCommit)
|
||||||
{
|
{
|
||||||
if (states.empty() || mOscOverlayStates.empty() || !mRuntimeHost)
|
if (states.empty() || mOscOverlayStates.empty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
const double smoothing = ClampOscAlpha(mRuntimeStore ? mRuntimeStore->GetConfiguredOscSmoothing() : 0.0);
|
const double smoothing = ClampOscAlpha(mRuntimeStore ? mRuntimeStore->GetConfiguredOscSmoothing() : 0.0);
|
||||||
@@ -576,66 +562,12 @@ void OpenGLComposite::renderEffect()
|
|||||||
|
|
||||||
const bool hasInputSource = mVideoBackend->HasInputSource();
|
const bool hasInputSource = mVideoBackend->HasInputSource();
|
||||||
std::vector<RuntimeRenderState> layerStates;
|
std::vector<RuntimeRenderState> layerStates;
|
||||||
if (mUseCommittedLayerStates)
|
mRenderEngine->ResolveRenderLayerStates(
|
||||||
{
|
mUseCommittedLayerStates.load(),
|
||||||
layerStates = mRenderEngine->CommittedLayerStates();
|
mVideoBackend->InputFrameWidth(),
|
||||||
applyOscOverlays(layerStates, false);
|
mVideoBackend->InputFrameHeight(),
|
||||||
if (mRuntimeSnapshotProvider)
|
applyOscOverlays,
|
||||||
mRuntimeSnapshotProvider->RefreshDynamicRenderStateFields(layerStates);
|
layerStates);
|
||||||
}
|
|
||||||
else if (mRuntimeSnapshotProvider)
|
|
||||||
{
|
|
||||||
const unsigned renderWidth = mVideoBackend->InputFrameWidth();
|
|
||||||
const unsigned renderHeight = mVideoBackend->InputFrameHeight();
|
|
||||||
const RuntimeSnapshotVersions versions = mRuntimeSnapshotProvider->GetVersions();
|
|
||||||
const bool renderStateCacheValid =
|
|
||||||
!mCachedLayerRenderStates.empty() &&
|
|
||||||
mCachedRenderStateVersion == versions.renderStateVersion &&
|
|
||||||
mCachedRenderStateWidth == renderWidth &&
|
|
||||||
mCachedRenderStateHeight == renderHeight;
|
|
||||||
|
|
||||||
if (renderStateCacheValid)
|
|
||||||
{
|
|
||||||
RuntimeRenderStateSnapshot renderSnapshot;
|
|
||||||
renderSnapshot.outputWidth = renderWidth;
|
|
||||||
renderSnapshot.outputHeight = renderHeight;
|
|
||||||
renderSnapshot.versions.renderStateVersion = mCachedRenderStateVersion;
|
|
||||||
renderSnapshot.versions.parameterStateVersion = mCachedParameterStateVersion;
|
|
||||||
renderSnapshot.states = mCachedLayerRenderStates;
|
|
||||||
|
|
||||||
applyOscOverlays(renderSnapshot.states, true);
|
|
||||||
if (mCachedParameterStateVersion != versions.parameterStateVersion &&
|
|
||||||
mRuntimeSnapshotProvider->TryRefreshSnapshotParameters(renderSnapshot))
|
|
||||||
{
|
|
||||||
mCachedParameterStateVersion = renderSnapshot.versions.parameterStateVersion;
|
|
||||||
applyOscOverlays(renderSnapshot.states, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
mCachedLayerRenderStates = renderSnapshot.states;
|
|
||||||
layerStates = renderSnapshot.states;
|
|
||||||
mRuntimeSnapshotProvider->RefreshDynamicRenderStateFields(layerStates);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
RuntimeRenderStateSnapshot renderSnapshot;
|
|
||||||
if (mRuntimeSnapshotProvider->TryGetRenderStateSnapshot(renderWidth, renderHeight, renderSnapshot))
|
|
||||||
{
|
|
||||||
mCachedLayerRenderStates = renderSnapshot.states;
|
|
||||||
mCachedRenderStateVersion = renderSnapshot.versions.renderStateVersion;
|
|
||||||
mCachedParameterStateVersion = renderSnapshot.versions.parameterStateVersion;
|
|
||||||
mCachedRenderStateWidth = renderSnapshot.outputWidth;
|
|
||||||
mCachedRenderStateHeight = renderSnapshot.outputHeight;
|
|
||||||
applyOscOverlays(mCachedLayerRenderStates, true);
|
|
||||||
layerStates = mCachedLayerRenderStates;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
applyOscOverlays(mCachedLayerRenderStates, true);
|
|
||||||
layerStates = mCachedLayerRenderStates;
|
|
||||||
mRuntimeSnapshotProvider->RefreshDynamicRenderStateFields(layerStates);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
const unsigned historyCap = mRuntimeStore ? mRuntimeStore->GetConfiguredMaxTemporalHistoryFrames() : 0;
|
const unsigned historyCap = mRuntimeStore ? mRuntimeStore->GetConfiguredMaxTemporalHistoryFrames() : 0;
|
||||||
mRenderEngine->RenderLayerStack(
|
mRenderEngine->RenderLayerStack(
|
||||||
hasInputSource,
|
hasInputSource,
|
||||||
@@ -657,20 +589,9 @@ void OpenGLComposite::ProcessScreenshotRequest()
|
|||||||
if (width == 0 || height == 0)
|
if (width == 0 || height == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
std::vector<unsigned char> bottomUpPixels;
|
std::vector<unsigned char> topDownPixels;
|
||||||
if (!mRenderEngine->ReadOutputFrameRgba(width, height, bottomUpPixels))
|
if (!mRenderEngine->CaptureOutputFrameRgbaTopDown(width, height, topDownPixels))
|
||||||
return;
|
return;
|
||||||
std::vector<unsigned char> topDownPixels(bottomUpPixels.size());
|
|
||||||
|
|
||||||
const std::size_t rowBytes = static_cast<std::size_t>(width) * 4;
|
|
||||||
for (unsigned y = 0; y < height; ++y)
|
|
||||||
{
|
|
||||||
const unsigned sourceY = height - 1 - y;
|
|
||||||
std::copy(
|
|
||||||
bottomUpPixels.begin() + static_cast<std::ptrdiff_t>(sourceY * rowBytes),
|
|
||||||
bottomUpPixels.begin() + static_cast<std::ptrdiff_t>((sourceY + 1) * rowBytes),
|
|
||||||
topDownPixels.begin() + static_cast<std::ptrdiff_t>(y * rowBytes));
|
|
||||||
}
|
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -707,14 +628,13 @@ std::filesystem::path OpenGLComposite::BuildScreenshotPath() const
|
|||||||
|
|
||||||
bool OpenGLComposite::ProcessRuntimePollResults()
|
bool OpenGLComposite::ProcessRuntimePollResults()
|
||||||
{
|
{
|
||||||
if (!mRuntimeHost || !mRuntimeServices)
|
if (!mRuntimeServices)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
const RuntimePollEvents events = mRuntimeServices->ConsumePollEvents();
|
const RuntimePollEvents events = mRuntimeServices->ConsumePollEvents();
|
||||||
if (events.failed)
|
if (events.failed)
|
||||||
{
|
{
|
||||||
mRuntimeStore->SetCompileStatus(false, events.error);
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->HandleRuntimePollFailure(events.error));
|
||||||
broadcastRuntimeState();
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -728,29 +648,23 @@ bool OpenGLComposite::ProcessRuntimePollResults()
|
|||||||
return true;
|
return true;
|
||||||
|
|
||||||
char compilerErrorMessage[1024] = {};
|
char compilerErrorMessage[1024] = {};
|
||||||
if (!mRenderEngine->CommitPreparedLayerPrograms(readyBuild, mVideoBackend->InputFrameWidth(), mVideoBackend->InputFrameHeight(), sizeof(compilerErrorMessage), compilerErrorMessage))
|
if (!mRenderEngine->ApplyPreparedShaderBuild(
|
||||||
|
readyBuild,
|
||||||
|
mVideoBackend->InputFrameWidth(),
|
||||||
|
mVideoBackend->InputFrameHeight(),
|
||||||
|
mRuntimeCoordinator && mRuntimeCoordinator->PreserveFeedbackOnNextShaderBuild(),
|
||||||
|
sizeof(compilerErrorMessage),
|
||||||
|
compilerErrorMessage))
|
||||||
{
|
{
|
||||||
mRuntimeStore->SetCompileStatus(false, compilerErrorMessage);
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->HandlePreparedShaderBuildFailure(compilerErrorMessage));
|
||||||
mUseCommittedLayerStates = true;
|
|
||||||
mPreserveFeedbackOnNextShaderBuild = false;
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
mUseCommittedLayerStates = false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->HandlePreparedShaderBuildSuccess());
|
||||||
mCachedLayerRenderStates = mRenderEngine->CommittedLayerStates();
|
|
||||||
mRenderEngine->ResetTemporalHistoryState();
|
|
||||||
if (!mPreserveFeedbackOnNextShaderBuild)
|
|
||||||
mRenderEngine->ResetShaderFeedbackState();
|
|
||||||
mPreserveFeedbackOnNextShaderBuild = false;
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
mRuntimeStore->SetCompileStatus(true, "Shader rebuild queued.");
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->HandleRuntimeReloadRequest());
|
||||||
mPreserveFeedbackOnNextShaderBuild = false;
|
|
||||||
RequestShaderBuild();
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -759,24 +673,81 @@ void OpenGLComposite::RequestShaderBuild()
|
|||||||
if (!mShaderBuildQueue || !mVideoBackend)
|
if (!mShaderBuildQueue || !mVideoBackend)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
mUseCommittedLayerStates = true;
|
|
||||||
if (mRuntimeHost)
|
|
||||||
mRuntimeStore->ClearReloadRequest();
|
|
||||||
mShaderBuildQueue->RequestBuild(mVideoBackend->InputFrameWidth(), mVideoBackend->InputFrameHeight());
|
mShaderBuildQueue->RequestBuild(mVideoBackend->InputFrameWidth(), mVideoBackend->InputFrameHeight());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool OpenGLComposite::ApplyRuntimeCoordinatorResult(const RuntimeCoordinatorResult& result, std::string* error)
|
||||||
|
{
|
||||||
|
if (!result.accepted)
|
||||||
|
{
|
||||||
|
if (error)
|
||||||
|
*error = result.errorMessage;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result.compileStatusChanged && mRuntimeStore)
|
||||||
|
mRuntimeStore->SetCompileStatus(result.compileStatusSucceeded, result.compileStatusMessage);
|
||||||
|
|
||||||
|
if (result.clearReloadRequest && mRuntimeStore)
|
||||||
|
mRuntimeStore->ClearReloadRequest();
|
||||||
|
|
||||||
|
switch (result.committedStateMode)
|
||||||
|
{
|
||||||
|
case RuntimeCoordinatorCommittedStateMode::UseCommittedStates:
|
||||||
|
mUseCommittedLayerStates = true;
|
||||||
|
break;
|
||||||
|
case RuntimeCoordinatorCommittedStateMode::UseLiveSnapshots:
|
||||||
|
mUseCommittedLayerStates = false;
|
||||||
|
break;
|
||||||
|
case RuntimeCoordinatorCommittedStateMode::Unchanged:
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result.clearTransientOscState)
|
||||||
|
{
|
||||||
|
mOscOverlayStates.clear();
|
||||||
|
if (mRuntimeServices)
|
||||||
|
mRuntimeServices->ClearOscState();
|
||||||
|
}
|
||||||
|
|
||||||
|
ApplyRuntimeCoordinatorRenderReset(result.renderResetScope);
|
||||||
|
|
||||||
|
if (result.shaderBuildRequested)
|
||||||
|
RequestShaderBuild();
|
||||||
|
|
||||||
|
if (result.runtimeStateBroadcastRequired)
|
||||||
|
broadcastRuntimeState();
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void OpenGLComposite::ApplyRuntimeCoordinatorRenderReset(RuntimeCoordinatorRenderResetScope resetScope)
|
||||||
|
{
|
||||||
|
if (!mRenderEngine)
|
||||||
|
return;
|
||||||
|
|
||||||
|
switch (resetScope)
|
||||||
|
{
|
||||||
|
case RuntimeCoordinatorRenderResetScope::TemporalHistoryOnly:
|
||||||
|
mRenderEngine->ResetTemporalHistoryState();
|
||||||
|
break;
|
||||||
|
case RuntimeCoordinatorRenderResetScope::TemporalHistoryAndFeedback:
|
||||||
|
mRenderEngine->ResetTemporalHistoryState();
|
||||||
|
mRenderEngine->ResetShaderFeedbackState();
|
||||||
|
break;
|
||||||
|
case RuntimeCoordinatorRenderResetScope::None:
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void OpenGLComposite::broadcastRuntimeState()
|
void OpenGLComposite::broadcastRuntimeState()
|
||||||
{
|
{
|
||||||
if (mRuntimeServices)
|
if (mRuntimeServices)
|
||||||
mRuntimeServices->BroadcastState();
|
mRuntimeServices->BroadcastState();
|
||||||
}
|
}
|
||||||
|
|
||||||
void OpenGLComposite::resetTemporalHistoryState()
|
|
||||||
{
|
|
||||||
mRenderEngine->ResetTemporalHistoryState();
|
|
||||||
mRenderEngine->ResetShaderFeedbackState();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool OpenGLComposite::CheckOpenGLExtensions()
|
bool OpenGLComposite::CheckOpenGLExtensions()
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -12,6 +12,7 @@
|
|||||||
#include <comutil.h>
|
#include <comutil.h>
|
||||||
|
|
||||||
#include "GLExtensions.h"
|
#include "GLExtensions.h"
|
||||||
|
#include "RuntimeCoordinator.h"
|
||||||
#include "RuntimeHost.h"
|
#include "RuntimeHost.h"
|
||||||
#include "RuntimeSnapshotProvider.h"
|
#include "RuntimeSnapshotProvider.h"
|
||||||
#include "RuntimeStore.h"
|
#include "RuntimeStore.h"
|
||||||
@@ -91,30 +92,25 @@ private:
|
|||||||
|
|
||||||
std::unique_ptr<RuntimeHost> mRuntimeHost;
|
std::unique_ptr<RuntimeHost> mRuntimeHost;
|
||||||
std::unique_ptr<RuntimeStore> mRuntimeStore;
|
std::unique_ptr<RuntimeStore> mRuntimeStore;
|
||||||
|
std::unique_ptr<RuntimeCoordinator> mRuntimeCoordinator;
|
||||||
std::unique_ptr<RuntimeSnapshotProvider> mRuntimeSnapshotProvider;
|
std::unique_ptr<RuntimeSnapshotProvider> mRuntimeSnapshotProvider;
|
||||||
std::unique_ptr<RenderEngine> mRenderEngine;
|
std::unique_ptr<RenderEngine> mRenderEngine;
|
||||||
std::unique_ptr<ShaderBuildQueue> mShaderBuildQueue;
|
std::unique_ptr<ShaderBuildQueue> mShaderBuildQueue;
|
||||||
std::unique_ptr<RuntimeServices> mRuntimeServices;
|
std::unique_ptr<RuntimeServices> mRuntimeServices;
|
||||||
std::unique_ptr<VideoBackend> mVideoBackend;
|
std::unique_ptr<VideoBackend> mVideoBackend;
|
||||||
std::vector<RuntimeRenderState> mCachedLayerRenderStates;
|
|
||||||
uint64_t mCachedRenderStateVersion = 0;
|
|
||||||
uint64_t mCachedParameterStateVersion = 0;
|
|
||||||
unsigned mCachedRenderStateWidth = 0;
|
|
||||||
unsigned mCachedRenderStateHeight = 0;
|
|
||||||
std::map<std::string, OscOverlayState> mOscOverlayStates;
|
std::map<std::string, OscOverlayState> mOscOverlayStates;
|
||||||
std::atomic<bool> mUseCommittedLayerStates;
|
std::atomic<bool> mUseCommittedLayerStates;
|
||||||
std::atomic<bool> mScreenshotRequested;
|
std::atomic<bool> mScreenshotRequested;
|
||||||
std::chrono::steady_clock::time_point mLastPreviewPresentTime;
|
|
||||||
bool mPreserveFeedbackOnNextShaderBuild = false;
|
|
||||||
|
|
||||||
bool InitOpenGLState();
|
bool InitOpenGLState();
|
||||||
void renderEffect();
|
void renderEffect();
|
||||||
bool ProcessRuntimePollResults();
|
bool ProcessRuntimePollResults();
|
||||||
void RequestShaderBuild();
|
void RequestShaderBuild();
|
||||||
|
bool ApplyRuntimeCoordinatorResult(const RuntimeCoordinatorResult& result, std::string* error = nullptr);
|
||||||
|
void ApplyRuntimeCoordinatorRenderReset(RuntimeCoordinatorRenderResetScope resetScope);
|
||||||
void ProcessScreenshotRequest();
|
void ProcessScreenshotRequest();
|
||||||
std::filesystem::path BuildScreenshotPath() const;
|
std::filesystem::path BuildScreenshotPath() const;
|
||||||
void broadcastRuntimeState();
|
void broadcastRuntimeState();
|
||||||
void resetTemporalHistoryState();
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // __OPENGL_COMPOSITE_H__
|
#endif // __OPENGL_COMPOSITE_H__
|
||||||
|
|||||||
@@ -38,62 +38,38 @@ std::string OpenGLComposite::GetOscAddress() const
|
|||||||
|
|
||||||
bool OpenGLComposite::AddLayer(const std::string& shaderId, std::string& error)
|
bool OpenGLComposite::AddLayer(const std::string& shaderId, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->CreateStoredLayer(shaderId, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->AddLayer(shaderId), &error);
|
||||||
|
|
||||||
ReloadShader(true);
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::RemoveLayer(const std::string& layerId, std::string& error)
|
bool OpenGLComposite::RemoveLayer(const std::string& layerId, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->DeleteStoredLayer(layerId, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->RemoveLayer(layerId), &error);
|
||||||
|
|
||||||
ReloadShader(true);
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::MoveLayer(const std::string& layerId, int direction, std::string& error)
|
bool OpenGLComposite::MoveLayer(const std::string& layerId, int direction, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->MoveStoredLayer(layerId, direction, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->MoveLayer(layerId, direction), &error);
|
||||||
|
|
||||||
ReloadShader(true);
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::MoveLayerToIndex(const std::string& layerId, std::size_t targetIndex, std::string& error)
|
bool OpenGLComposite::MoveLayerToIndex(const std::string& layerId, std::size_t targetIndex, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->MoveStoredLayerToIndex(layerId, targetIndex, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->MoveLayerToIndex(layerId, targetIndex), &error);
|
||||||
|
|
||||||
ReloadShader(true);
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::SetLayerBypass(const std::string& layerId, bool bypassed, std::string& error)
|
bool OpenGLComposite::SetLayerBypass(const std::string& layerId, bool bypassed, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->SetStoredLayerBypassState(layerId, bypassed, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->SetLayerBypass(layerId, bypassed), &error);
|
||||||
|
|
||||||
ReloadShader();
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::SetLayerShader(const std::string& layerId, const std::string& shaderId, std::string& error)
|
bool OpenGLComposite::SetLayerShader(const std::string& layerId, const std::string& shaderId, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->SetStoredLayerShaderSelection(layerId, shaderId, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->SetLayerShader(layerId, shaderId), &error);
|
||||||
|
|
||||||
ReloadShader();
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::UpdateLayerParameterJson(const std::string& layerId, const std::string& parameterId, const std::string& valueJson, std::string& error)
|
bool OpenGLComposite::UpdateLayerParameterJson(const std::string& layerId, const std::string& parameterId, const std::string& valueJson, std::string& error)
|
||||||
@@ -102,11 +78,8 @@ bool OpenGLComposite::UpdateLayerParameterJson(const std::string& layerId, const
|
|||||||
if (!ParseJson(valueJson, parsedValue, error))
|
if (!ParseJson(valueJson, parsedValue, error))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (!mRuntimeStore->SetStoredParameterValue(layerId, parameterId, parsedValue, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->UpdateLayerParameter(layerId, parameterId, parsedValue), &error);
|
||||||
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::UpdateLayerParameterByControlKeyJson(const std::string& layerKey, const std::string& parameterKey, const std::string& valueJson, std::string& error)
|
bool OpenGLComposite::UpdateLayerParameterByControlKeyJson(const std::string& layerKey, const std::string& parameterKey, const std::string& valueJson, std::string& error)
|
||||||
@@ -115,42 +88,24 @@ bool OpenGLComposite::UpdateLayerParameterByControlKeyJson(const std::string& la
|
|||||||
if (!ParseJson(valueJson, parsedValue, error))
|
if (!ParseJson(valueJson, parsedValue, error))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (!mRuntimeStore->SetStoredParameterValueByControlKey(layerKey, parameterKey, parsedValue, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->UpdateLayerParameterByControlKey(layerKey, parameterKey, parsedValue), &error);
|
||||||
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::ResetLayerParameters(const std::string& layerId, std::string& error)
|
bool OpenGLComposite::ResetLayerParameters(const std::string& layerId, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->ResetStoredLayerParameterValues(layerId, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->ResetLayerParameters(layerId), &error);
|
||||||
|
|
||||||
mOscOverlayStates.clear();
|
|
||||||
if (mRuntimeServices)
|
|
||||||
mRuntimeServices->ClearOscState();
|
|
||||||
resetTemporalHistoryState();
|
|
||||||
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::SaveStackPreset(const std::string& presetName, std::string& error)
|
bool OpenGLComposite::SaveStackPreset(const std::string& presetName, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->SaveStackPresetSnapshot(presetName, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->SaveStackPreset(presetName), &error);
|
||||||
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool OpenGLComposite::LoadStackPreset(const std::string& presetName, std::string& error)
|
bool OpenGLComposite::LoadStackPreset(const std::string& presetName, std::string& error)
|
||||||
{
|
{
|
||||||
if (!mRuntimeStore->LoadStackPresetSnapshot(presetName, error))
|
return mRuntimeCoordinator &&
|
||||||
return false;
|
ApplyRuntimeCoordinatorResult(mRuntimeCoordinator->LoadStackPreset(presetName), &error);
|
||||||
|
|
||||||
ReloadShader();
|
|
||||||
broadcastRuntimeState();
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,9 +2,12 @@
|
|||||||
|
|
||||||
#include <gl/gl.h>
|
#include <gl/gl.h>
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
#include <cstddef>
|
||||||
|
|
||||||
RenderEngine::RenderEngine(
|
RenderEngine::RenderEngine(
|
||||||
RuntimeHost& runtimeHost,
|
|
||||||
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
||||||
|
HealthTelemetry& healthTelemetry,
|
||||||
CRITICAL_SECTION& mutex,
|
CRITICAL_SECTION& mutex,
|
||||||
HDC hdc,
|
HDC hdc,
|
||||||
HGLRC hglrc,
|
HGLRC hglrc,
|
||||||
@@ -13,8 +16,9 @@ RenderEngine::RenderEngine(
|
|||||||
PreviewPaintCallback previewPaint) :
|
PreviewPaintCallback previewPaint) :
|
||||||
mRenderer(),
|
mRenderer(),
|
||||||
mRenderPass(mRenderer),
|
mRenderPass(mRenderer),
|
||||||
mRenderPipeline(mRenderer, runtimeHost, std::move(renderEffect), std::move(screenshotReady), std::move(previewPaint)),
|
mRenderPipeline(mRenderer, runtimeSnapshotProvider, healthTelemetry, std::move(renderEffect), std::move(screenshotReady), std::move(previewPaint)),
|
||||||
mShaderPrograms(mRenderer, runtimeHost, runtimeSnapshotProvider),
|
mShaderPrograms(mRenderer, runtimeSnapshotProvider),
|
||||||
|
mRuntimeSnapshotProvider(runtimeSnapshotProvider),
|
||||||
mMutex(mutex),
|
mMutex(mutex),
|
||||||
mHdc(hdc),
|
mHdc(hdc),
|
||||||
mHglrc(hglrc)
|
mHglrc(hglrc)
|
||||||
@@ -65,6 +69,28 @@ bool RenderEngine::CommitPreparedLayerPrograms(const PreparedShaderBuild& prepar
|
|||||||
return mShaderPrograms.CommitPreparedLayerPrograms(preparedBuild, inputFrameWidth, inputFrameHeight, errorMessageSize, errorMessage);
|
return mShaderPrograms.CommitPreparedLayerPrograms(preparedBuild, inputFrameWidth, inputFrameHeight, errorMessageSize, errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RenderEngine::ApplyPreparedShaderBuild(
|
||||||
|
const PreparedShaderBuild& preparedBuild,
|
||||||
|
unsigned inputFrameWidth,
|
||||||
|
unsigned inputFrameHeight,
|
||||||
|
bool preserveFeedbackState,
|
||||||
|
int errorMessageSize,
|
||||||
|
char* errorMessage)
|
||||||
|
{
|
||||||
|
if (!CommitPreparedLayerPrograms(preparedBuild, inputFrameWidth, inputFrameHeight, errorMessageSize, errorMessage))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
mCachedLayerRenderStates = mShaderPrograms.CommittedLayerStates();
|
||||||
|
mCachedRenderStateVersion = preparedBuild.renderSnapshot.versions.renderStateVersion;
|
||||||
|
mCachedParameterStateVersion = preparedBuild.renderSnapshot.versions.parameterStateVersion;
|
||||||
|
mCachedRenderStateWidth = preparedBuild.renderSnapshot.outputWidth;
|
||||||
|
mCachedRenderStateHeight = preparedBuild.renderSnapshot.outputHeight;
|
||||||
|
ResetTemporalHistoryState();
|
||||||
|
if (!preserveFeedbackState)
|
||||||
|
ResetShaderFeedbackState();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
const std::vector<RuntimeRenderState>& RenderEngine::CommittedLayerStates() const
|
const std::vector<RuntimeRenderState>& RenderEngine::CommittedLayerStates() const
|
||||||
{
|
{
|
||||||
return mShaderPrograms.CommittedLayerStates();
|
return mShaderPrograms.CommittedLayerStates();
|
||||||
@@ -85,12 +111,27 @@ void RenderEngine::ResizeView(int width, int height)
|
|||||||
mRenderer.ResizeView(width, height);
|
mRenderer.ResizeView(width, height);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool RenderEngine::TryPresentToWindow(unsigned outputFrameWidth, unsigned outputFrameHeight)
|
bool RenderEngine::TryPresentPreview(bool force, unsigned previewFps, unsigned outputFrameWidth, unsigned outputFrameHeight)
|
||||||
{
|
{
|
||||||
|
if (!force)
|
||||||
|
{
|
||||||
|
if (previewFps == 0)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
const auto now = std::chrono::steady_clock::now();
|
||||||
|
const auto minimumInterval = std::chrono::microseconds(1000000 / (previewFps == 0 ? 1u : previewFps));
|
||||||
|
if (mLastPreviewPresentTime != std::chrono::steady_clock::time_point() &&
|
||||||
|
now - mLastPreviewPresentTime < minimumInterval)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (!TryEnterCriticalSection(&mMutex))
|
if (!TryEnterCriticalSection(&mMutex))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
mRenderer.PresentToWindow(mHdc, outputFrameWidth, outputFrameHeight);
|
mRenderer.PresentToWindow(mHdc, outputFrameWidth, outputFrameHeight);
|
||||||
|
mLastPreviewPresentTime = std::chrono::steady_clock::now();
|
||||||
LeaveCriticalSection(&mMutex);
|
LeaveCriticalSection(&mMutex);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -133,6 +174,76 @@ bool RenderEngine::RenderOutputFrame(const RenderPipelineFrameContext& context,
|
|||||||
return rendered;
|
return rendered;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RenderEngine::ResolveRenderLayerStates(
|
||||||
|
bool useCommittedLayerStates,
|
||||||
|
unsigned renderWidth,
|
||||||
|
unsigned renderHeight,
|
||||||
|
OverlayApplier overlayApplier,
|
||||||
|
std::vector<RuntimeRenderState>& layerStates)
|
||||||
|
{
|
||||||
|
layerStates.clear();
|
||||||
|
if (useCommittedLayerStates)
|
||||||
|
{
|
||||||
|
layerStates = mShaderPrograms.CommittedLayerStates();
|
||||||
|
if (overlayApplier)
|
||||||
|
overlayApplier(layerStates, false);
|
||||||
|
mRuntimeSnapshotProvider.RefreshDynamicRenderStateFields(layerStates);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
const RuntimeSnapshotVersions versions = mRuntimeSnapshotProvider.GetVersions();
|
||||||
|
const bool renderStateCacheValid =
|
||||||
|
!mCachedLayerRenderStates.empty() &&
|
||||||
|
mCachedRenderStateVersion == versions.renderStateVersion &&
|
||||||
|
mCachedRenderStateWidth == renderWidth &&
|
||||||
|
mCachedRenderStateHeight == renderHeight;
|
||||||
|
|
||||||
|
if (renderStateCacheValid)
|
||||||
|
{
|
||||||
|
RuntimeRenderStateSnapshot renderSnapshot;
|
||||||
|
renderSnapshot.outputWidth = renderWidth;
|
||||||
|
renderSnapshot.outputHeight = renderHeight;
|
||||||
|
renderSnapshot.versions.renderStateVersion = mCachedRenderStateVersion;
|
||||||
|
renderSnapshot.versions.parameterStateVersion = mCachedParameterStateVersion;
|
||||||
|
renderSnapshot.states = mCachedLayerRenderStates;
|
||||||
|
|
||||||
|
if (overlayApplier)
|
||||||
|
overlayApplier(renderSnapshot.states, true);
|
||||||
|
if (mCachedParameterStateVersion != versions.parameterStateVersion &&
|
||||||
|
mRuntimeSnapshotProvider.TryRefreshSnapshotParameters(renderSnapshot))
|
||||||
|
{
|
||||||
|
mCachedParameterStateVersion = renderSnapshot.versions.parameterStateVersion;
|
||||||
|
if (overlayApplier)
|
||||||
|
overlayApplier(renderSnapshot.states, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
mCachedLayerRenderStates = renderSnapshot.states;
|
||||||
|
layerStates = renderSnapshot.states;
|
||||||
|
mRuntimeSnapshotProvider.RefreshDynamicRenderStateFields(layerStates);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeRenderStateSnapshot renderSnapshot;
|
||||||
|
if (mRuntimeSnapshotProvider.TryGetRenderStateSnapshot(renderWidth, renderHeight, renderSnapshot))
|
||||||
|
{
|
||||||
|
mCachedLayerRenderStates = renderSnapshot.states;
|
||||||
|
mCachedRenderStateVersion = renderSnapshot.versions.renderStateVersion;
|
||||||
|
mCachedParameterStateVersion = renderSnapshot.versions.parameterStateVersion;
|
||||||
|
mCachedRenderStateWidth = renderSnapshot.outputWidth;
|
||||||
|
mCachedRenderStateHeight = renderSnapshot.outputHeight;
|
||||||
|
if (overlayApplier)
|
||||||
|
overlayApplier(mCachedLayerRenderStates, true);
|
||||||
|
layerStates = mCachedLayerRenderStates;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (overlayApplier)
|
||||||
|
overlayApplier(mCachedLayerRenderStates, true);
|
||||||
|
layerStates = mCachedLayerRenderStates;
|
||||||
|
mRuntimeSnapshotProvider.RefreshDynamicRenderStateFields(layerStates);
|
||||||
|
return !layerStates.empty();
|
||||||
|
}
|
||||||
|
|
||||||
void RenderEngine::RenderLayerStack(
|
void RenderEngine::RenderLayerStack(
|
||||||
bool hasInputSource,
|
bool hasInputSource,
|
||||||
const std::vector<RuntimeRenderState>& layerStates,
|
const std::vector<RuntimeRenderState>& layerStates,
|
||||||
@@ -178,3 +289,23 @@ bool RenderEngine::ReadOutputFrameRgba(unsigned width, unsigned height, std::vec
|
|||||||
LeaveCriticalSection(&mMutex);
|
LeaveCriticalSection(&mMutex);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RenderEngine::CaptureOutputFrameRgbaTopDown(unsigned width, unsigned height, std::vector<unsigned char>& topDownPixels)
|
||||||
|
{
|
||||||
|
std::vector<unsigned char> bottomUpPixels;
|
||||||
|
if (!ReadOutputFrameRgba(width, height, bottomUpPixels))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
topDownPixels.resize(bottomUpPixels.size());
|
||||||
|
const std::size_t rowBytes = static_cast<std::size_t>(width) * 4;
|
||||||
|
for (unsigned y = 0; y < height; ++y)
|
||||||
|
{
|
||||||
|
const unsigned sourceY = height - 1 - y;
|
||||||
|
std::copy(
|
||||||
|
bottomUpPixels.begin() + static_cast<std::ptrdiff_t>(sourceY * rowBytes),
|
||||||
|
bottomUpPixels.begin() + static_cast<std::ptrdiff_t>((sourceY + 1) * rowBytes),
|
||||||
|
topDownPixels.begin() + static_cast<std::ptrdiff_t>(y * rowBytes));
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|||||||
@@ -4,11 +4,13 @@
|
|||||||
#include "OpenGLRenderPipeline.h"
|
#include "OpenGLRenderPipeline.h"
|
||||||
#include "OpenGLRenderer.h"
|
#include "OpenGLRenderer.h"
|
||||||
#include "OpenGLShaderPrograms.h"
|
#include "OpenGLShaderPrograms.h"
|
||||||
#include "RuntimeHost.h"
|
#include "HealthTelemetry.h"
|
||||||
#include "RuntimeSnapshotProvider.h"
|
#include "RuntimeSnapshotProvider.h"
|
||||||
|
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
|
|
||||||
|
#include <cstdint>
|
||||||
|
#include <chrono>
|
||||||
#include <functional>
|
#include <functional>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
@@ -19,10 +21,11 @@ public:
|
|||||||
using RenderEffectCallback = std::function<void()>;
|
using RenderEffectCallback = std::function<void()>;
|
||||||
using ScreenshotCallback = std::function<void()>;
|
using ScreenshotCallback = std::function<void()>;
|
||||||
using PreviewPaintCallback = std::function<void()>;
|
using PreviewPaintCallback = std::function<void()>;
|
||||||
|
using OverlayApplier = std::function<void(std::vector<RuntimeRenderState>& states, bool allowCommit)>;
|
||||||
|
|
||||||
RenderEngine(
|
RenderEngine(
|
||||||
RuntimeHost& runtimeHost,
|
|
||||||
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
||||||
|
HealthTelemetry& healthTelemetry,
|
||||||
CRITICAL_SECTION& mutex,
|
CRITICAL_SECTION& mutex,
|
||||||
HDC hdc,
|
HDC hdc,
|
||||||
HGLRC hglrc,
|
HGLRC hglrc,
|
||||||
@@ -43,14 +46,27 @@ public:
|
|||||||
std::string& error);
|
std::string& error);
|
||||||
bool CompileLayerPrograms(unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
bool CompileLayerPrograms(unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
||||||
bool CommitPreparedLayerPrograms(const PreparedShaderBuild& preparedBuild, unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
bool CommitPreparedLayerPrograms(const PreparedShaderBuild& preparedBuild, unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
||||||
|
bool ApplyPreparedShaderBuild(
|
||||||
|
const PreparedShaderBuild& preparedBuild,
|
||||||
|
unsigned inputFrameWidth,
|
||||||
|
unsigned inputFrameHeight,
|
||||||
|
bool preserveFeedbackState,
|
||||||
|
int errorMessageSize,
|
||||||
|
char* errorMessage);
|
||||||
|
|
||||||
const std::vector<RuntimeRenderState>& CommittedLayerStates() const;
|
const std::vector<RuntimeRenderState>& CommittedLayerStates() const;
|
||||||
void ResetTemporalHistoryState();
|
void ResetTemporalHistoryState();
|
||||||
void ResetShaderFeedbackState();
|
void ResetShaderFeedbackState();
|
||||||
void ResizeView(int width, int height);
|
void ResizeView(int width, int height);
|
||||||
bool TryPresentToWindow(unsigned outputFrameWidth, unsigned outputFrameHeight);
|
bool TryPresentPreview(bool force, unsigned previewFps, unsigned outputFrameWidth, unsigned outputFrameHeight);
|
||||||
bool TryUploadInputFrame(const VideoIOFrame& inputFrame, const VideoIOState& videoState);
|
bool TryUploadInputFrame(const VideoIOFrame& inputFrame, const VideoIOState& videoState);
|
||||||
bool RenderOutputFrame(const RenderPipelineFrameContext& context, VideoIOOutputFrame& outputFrame);
|
bool RenderOutputFrame(const RenderPipelineFrameContext& context, VideoIOOutputFrame& outputFrame);
|
||||||
|
bool ResolveRenderLayerStates(
|
||||||
|
bool useCommittedLayerStates,
|
||||||
|
unsigned renderWidth,
|
||||||
|
unsigned renderHeight,
|
||||||
|
OverlayApplier overlayApplier,
|
||||||
|
std::vector<RuntimeRenderState>& layerStates);
|
||||||
void RenderLayerStack(
|
void RenderLayerStack(
|
||||||
bool hasInputSource,
|
bool hasInputSource,
|
||||||
const std::vector<RuntimeRenderState>& layerStates,
|
const std::vector<RuntimeRenderState>& layerStates,
|
||||||
@@ -60,13 +76,21 @@ public:
|
|||||||
VideoIOPixelFormat inputPixelFormat,
|
VideoIOPixelFormat inputPixelFormat,
|
||||||
unsigned historyCap);
|
unsigned historyCap);
|
||||||
bool ReadOutputFrameRgba(unsigned width, unsigned height, std::vector<unsigned char>& bottomUpPixels);
|
bool ReadOutputFrameRgba(unsigned width, unsigned height, std::vector<unsigned char>& bottomUpPixels);
|
||||||
|
bool CaptureOutputFrameRgbaTopDown(unsigned width, unsigned height, std::vector<unsigned char>& topDownPixels);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
OpenGLRenderer mRenderer;
|
OpenGLRenderer mRenderer;
|
||||||
OpenGLRenderPass mRenderPass;
|
OpenGLRenderPass mRenderPass;
|
||||||
OpenGLRenderPipeline mRenderPipeline;
|
OpenGLRenderPipeline mRenderPipeline;
|
||||||
OpenGLShaderPrograms mShaderPrograms;
|
OpenGLShaderPrograms mShaderPrograms;
|
||||||
|
RuntimeSnapshotProvider& mRuntimeSnapshotProvider;
|
||||||
CRITICAL_SECTION& mMutex;
|
CRITICAL_SECTION& mMutex;
|
||||||
HDC mHdc;
|
HDC mHdc;
|
||||||
HGLRC mHglrc;
|
HGLRC mHglrc;
|
||||||
|
std::vector<RuntimeRenderState> mCachedLayerRenderStates;
|
||||||
|
uint64_t mCachedRenderStateVersion = 0;
|
||||||
|
uint64_t mCachedParameterStateVersion = 0;
|
||||||
|
unsigned mCachedRenderStateWidth = 0;
|
||||||
|
unsigned mCachedRenderStateHeight = 0;
|
||||||
|
std::chrono::steady_clock::time_point mLastPreviewPresentTime;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,7 +1,8 @@
|
|||||||
#include "OpenGLRenderPipeline.h"
|
#include "OpenGLRenderPipeline.h"
|
||||||
|
|
||||||
|
#include "HealthTelemetry.h"
|
||||||
#include "OpenGLRenderer.h"
|
#include "OpenGLRenderer.h"
|
||||||
#include "RuntimeHost.h"
|
#include "RuntimeSnapshotProvider.h"
|
||||||
#include "VideoIOFormat.h"
|
#include "VideoIOFormat.h"
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
@@ -11,12 +12,14 @@
|
|||||||
|
|
||||||
OpenGLRenderPipeline::OpenGLRenderPipeline(
|
OpenGLRenderPipeline::OpenGLRenderPipeline(
|
||||||
OpenGLRenderer& renderer,
|
OpenGLRenderer& renderer,
|
||||||
RuntimeHost& runtimeHost,
|
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
||||||
|
HealthTelemetry& healthTelemetry,
|
||||||
RenderEffectCallback renderEffect,
|
RenderEffectCallback renderEffect,
|
||||||
OutputReadyCallback outputReady,
|
OutputReadyCallback outputReady,
|
||||||
PaintCallback paint) :
|
PaintCallback paint) :
|
||||||
mRenderer(renderer),
|
mRenderer(renderer),
|
||||||
mRuntimeHost(runtimeHost),
|
mRuntimeSnapshotProvider(runtimeSnapshotProvider),
|
||||||
|
mHealthTelemetry(healthTelemetry),
|
||||||
mRenderEffect(renderEffect),
|
mRenderEffect(renderEffect),
|
||||||
mOutputReady(outputReady),
|
mOutputReady(outputReady),
|
||||||
mPaint(paint)
|
mPaint(paint)
|
||||||
@@ -47,8 +50,8 @@ bool OpenGLRenderPipeline::RenderFrame(const RenderPipelineFrameContext& context
|
|||||||
|
|
||||||
const auto renderEndTime = std::chrono::steady_clock::now();
|
const auto renderEndTime = std::chrono::steady_clock::now();
|
||||||
const double renderMilliseconds = std::chrono::duration_cast<std::chrono::duration<double, std::milli>>(renderEndTime - renderStartTime).count();
|
const double renderMilliseconds = std::chrono::duration_cast<std::chrono::duration<double, std::milli>>(renderEndTime - renderStartTime).count();
|
||||||
mRuntimeHost.GetHealthTelemetry().TryRecordPerformanceStats(state.frameBudgetMilliseconds, renderMilliseconds);
|
mHealthTelemetry.TryRecordPerformanceStats(state.frameBudgetMilliseconds, renderMilliseconds);
|
||||||
mRuntimeHost.TryAdvanceFrame();
|
mRuntimeSnapshotProvider.TryAdvanceFrame();
|
||||||
|
|
||||||
ReadOutputFrame(state, outputFrame);
|
ReadOutputFrame(state, outputFrame);
|
||||||
if (mPaint)
|
if (mPaint)
|
||||||
|
|||||||
@@ -8,7 +8,8 @@
|
|||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
class OpenGLRenderer;
|
class OpenGLRenderer;
|
||||||
class RuntimeHost;
|
class HealthTelemetry;
|
||||||
|
class RuntimeSnapshotProvider;
|
||||||
|
|
||||||
struct RenderPipelineFrameContext
|
struct RenderPipelineFrameContext
|
||||||
{
|
{
|
||||||
@@ -25,7 +26,8 @@ public:
|
|||||||
|
|
||||||
OpenGLRenderPipeline(
|
OpenGLRenderPipeline(
|
||||||
OpenGLRenderer& renderer,
|
OpenGLRenderer& renderer,
|
||||||
RuntimeHost& runtimeHost,
|
RuntimeSnapshotProvider& runtimeSnapshotProvider,
|
||||||
|
HealthTelemetry& healthTelemetry,
|
||||||
RenderEffectCallback renderEffect,
|
RenderEffectCallback renderEffect,
|
||||||
OutputReadyCallback outputReady,
|
OutputReadyCallback outputReady,
|
||||||
PaintCallback paint);
|
PaintCallback paint);
|
||||||
@@ -53,7 +55,8 @@ private:
|
|||||||
void ReadOutputFrame(const VideoIOState& state, VideoIOOutputFrame& outputFrame);
|
void ReadOutputFrame(const VideoIOState& state, VideoIOOutputFrame& outputFrame);
|
||||||
|
|
||||||
OpenGLRenderer& mRenderer;
|
OpenGLRenderer& mRenderer;
|
||||||
RuntimeHost& mRuntimeHost;
|
RuntimeSnapshotProvider& mRuntimeSnapshotProvider;
|
||||||
|
HealthTelemetry& mHealthTelemetry;
|
||||||
RenderEffectCallback mRenderEffect;
|
RenderEffectCallback mRenderEffect;
|
||||||
OutputReadyCallback mOutputReady;
|
OutputReadyCallback mOutputReady;
|
||||||
PaintCallback mPaint;
|
PaintCallback mPaint;
|
||||||
|
|||||||
@@ -1,81 +1,25 @@
|
|||||||
#include "OpenGLVideoIOBridge.h"
|
#include "OpenGLVideoIOBridge.h"
|
||||||
|
|
||||||
#include "HealthTelemetry.h"
|
|
||||||
#include "RenderEngine.h"
|
#include "RenderEngine.h"
|
||||||
|
|
||||||
#include <chrono>
|
OpenGLVideoIOBridge::OpenGLVideoIOBridge(RenderEngine& renderEngine) :
|
||||||
|
mRenderEngine(renderEngine)
|
||||||
OpenGLVideoIOBridge::OpenGLVideoIOBridge(
|
|
||||||
VideoIODevice& videoIO,
|
|
||||||
RenderEngine& renderEngine,
|
|
||||||
HealthTelemetry& healthTelemetry) :
|
|
||||||
mVideoIO(videoIO),
|
|
||||||
mRenderEngine(renderEngine),
|
|
||||||
mHealthTelemetry(healthTelemetry)
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void OpenGLVideoIOBridge::RecordFramePacing(VideoIOCompletionResult completionResult)
|
void OpenGLVideoIOBridge::UploadInputFrame(const VideoIOFrame& inputFrame, const VideoIOState& state)
|
||||||
{
|
{
|
||||||
const auto now = std::chrono::steady_clock::now();
|
|
||||||
if (mLastPlayoutCompletionTime != std::chrono::steady_clock::time_point())
|
|
||||||
{
|
|
||||||
mCompletionIntervalMilliseconds = std::chrono::duration_cast<std::chrono::duration<double, std::milli>>(now - mLastPlayoutCompletionTime).count();
|
|
||||||
if (mSmoothedCompletionIntervalMilliseconds <= 0.0)
|
|
||||||
mSmoothedCompletionIntervalMilliseconds = mCompletionIntervalMilliseconds;
|
|
||||||
else
|
|
||||||
mSmoothedCompletionIntervalMilliseconds = mSmoothedCompletionIntervalMilliseconds * 0.9 + mCompletionIntervalMilliseconds * 0.1;
|
|
||||||
if (mCompletionIntervalMilliseconds > mMaxCompletionIntervalMilliseconds)
|
|
||||||
mMaxCompletionIntervalMilliseconds = mCompletionIntervalMilliseconds;
|
|
||||||
}
|
|
||||||
mLastPlayoutCompletionTime = now;
|
|
||||||
|
|
||||||
if (completionResult == VideoIOCompletionResult::DisplayedLate)
|
|
||||||
++mLateFrameCount;
|
|
||||||
else if (completionResult == VideoIOCompletionResult::Dropped)
|
|
||||||
++mDroppedFrameCount;
|
|
||||||
else if (completionResult == VideoIOCompletionResult::Flushed)
|
|
||||||
++mFlushedFrameCount;
|
|
||||||
|
|
||||||
mHealthTelemetry.TryRecordFramePacingStats(
|
|
||||||
mCompletionIntervalMilliseconds,
|
|
||||||
mSmoothedCompletionIntervalMilliseconds,
|
|
||||||
mMaxCompletionIntervalMilliseconds,
|
|
||||||
mLateFrameCount,
|
|
||||||
mDroppedFrameCount,
|
|
||||||
mFlushedFrameCount);
|
|
||||||
}
|
|
||||||
|
|
||||||
void OpenGLVideoIOBridge::VideoFrameArrived(const VideoIOFrame& inputFrame)
|
|
||||||
{
|
|
||||||
const VideoIOState& state = mVideoIO.State();
|
|
||||||
mHealthTelemetry.TryReportSignalStatus(!inputFrame.hasNoInputSource, state.inputFrameSize.width, state.inputFrameSize.height, state.inputDisplayModeName);
|
|
||||||
|
|
||||||
if (inputFrame.hasNoInputSource || inputFrame.bytes == nullptr)
|
if (inputFrame.hasNoInputSource || inputFrame.bytes == nullptr)
|
||||||
return; // don't transfer texture when there's no input
|
return; // don't transfer texture when there's no input
|
||||||
|
|
||||||
mRenderEngine.TryUploadInputFrame(inputFrame, state);
|
mRenderEngine.TryUploadInputFrame(inputFrame, state);
|
||||||
}
|
}
|
||||||
|
|
||||||
void OpenGLVideoIOBridge::PlayoutFrameCompleted(const VideoIOCompletion& completion)
|
void OpenGLVideoIOBridge::RenderScheduledFrame(const VideoIOState& state, const VideoIOCompletion& completion, VideoIOOutputFrame& outputFrame)
|
||||||
{
|
{
|
||||||
RecordFramePacing(completion.result);
|
|
||||||
|
|
||||||
VideoIOOutputFrame outputFrame;
|
|
||||||
if (!mVideoIO.BeginOutputFrame(outputFrame))
|
|
||||||
return;
|
|
||||||
const VideoIOState& state = mVideoIO.State();
|
|
||||||
RenderPipelineFrameContext frameContext;
|
RenderPipelineFrameContext frameContext;
|
||||||
frameContext.videoState = state;
|
frameContext.videoState = state;
|
||||||
frameContext.completion = completion;
|
frameContext.completion = completion;
|
||||||
|
|
||||||
mRenderEngine.RenderOutputFrame(frameContext, outputFrame);
|
mRenderEngine.RenderOutputFrame(frameContext, outputFrame);
|
||||||
|
|
||||||
mVideoIO.EndOutputFrame(outputFrame);
|
|
||||||
|
|
||||||
mVideoIO.AccountForCompletionResult(completion.result);
|
|
||||||
|
|
||||||
// Schedule the next frame for playout after the GL bridge is released so
|
|
||||||
// input uploads are not blocked by non-GL output bookkeeping.
|
|
||||||
mVideoIO.ScheduleOutputFrame(outputFrame);
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,34 +2,16 @@
|
|||||||
|
|
||||||
#include "OpenGLRenderPipeline.h"
|
#include "OpenGLRenderPipeline.h"
|
||||||
|
|
||||||
#include <chrono>
|
|
||||||
#include <cstdint>
|
|
||||||
|
|
||||||
class HealthTelemetry;
|
|
||||||
class RenderEngine;
|
class RenderEngine;
|
||||||
|
|
||||||
class OpenGLVideoIOBridge
|
class OpenGLVideoIOBridge
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
OpenGLVideoIOBridge(
|
explicit OpenGLVideoIOBridge(RenderEngine& renderEngine);
|
||||||
VideoIODevice& videoIO,
|
|
||||||
RenderEngine& renderEngine,
|
|
||||||
HealthTelemetry& healthTelemetry);
|
|
||||||
|
|
||||||
void VideoFrameArrived(const VideoIOFrame& inputFrame);
|
void UploadInputFrame(const VideoIOFrame& inputFrame, const VideoIOState& state);
|
||||||
void PlayoutFrameCompleted(const VideoIOCompletion& completion);
|
void RenderScheduledFrame(const VideoIOState& state, const VideoIOCompletion& completion, VideoIOOutputFrame& outputFrame);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void RecordFramePacing(VideoIOCompletionResult completionResult);
|
|
||||||
|
|
||||||
VideoIODevice& mVideoIO;
|
|
||||||
RenderEngine& mRenderEngine;
|
RenderEngine& mRenderEngine;
|
||||||
HealthTelemetry& mHealthTelemetry;
|
|
||||||
std::chrono::steady_clock::time_point mLastPlayoutCompletionTime;
|
|
||||||
double mCompletionIntervalMilliseconds = 0.0;
|
|
||||||
double mSmoothedCompletionIntervalMilliseconds = 0.0;
|
|
||||||
double mMaxCompletionIntervalMilliseconds = 0.0;
|
|
||||||
uint64_t mLateFrameCount = 0;
|
|
||||||
uint64_t mDroppedFrameCount = 0;
|
|
||||||
uint64_t mFlushedFrameCount = 0;
|
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -29,12 +29,11 @@ std::size_t RequiredTemporaryRenderTargets(const std::vector<OpenGLRenderer::Lay
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
OpenGLShaderPrograms::OpenGLShaderPrograms(OpenGLRenderer& renderer, RuntimeHost& runtimeHost, RuntimeSnapshotProvider& runtimeSnapshotProvider) :
|
OpenGLShaderPrograms::OpenGLShaderPrograms(OpenGLRenderer& renderer, RuntimeSnapshotProvider& runtimeSnapshotProvider) :
|
||||||
mRenderer(renderer),
|
mRenderer(renderer),
|
||||||
mRuntimeHost(runtimeHost),
|
|
||||||
mRuntimeSnapshotProvider(runtimeSnapshotProvider),
|
mRuntimeSnapshotProvider(runtimeSnapshotProvider),
|
||||||
mGlobalParamsBuffer(renderer),
|
mGlobalParamsBuffer(renderer),
|
||||||
mCompiler(renderer, runtimeHost, mTextureBindings)
|
mCompiler(renderer, runtimeSnapshotProvider, mTextureBindings)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -44,7 +43,7 @@ bool OpenGLShaderPrograms::CompileLayerPrograms(unsigned inputFrameWidth, unsign
|
|||||||
mRuntimeSnapshotProvider.GetRenderStateSnapshot(inputFrameWidth, inputFrameHeight);
|
mRuntimeSnapshotProvider.GetRenderStateSnapshot(inputFrameWidth, inputFrameHeight);
|
||||||
const std::vector<RuntimeRenderState>& layerStates = renderSnapshot.states;
|
const std::vector<RuntimeRenderState>& layerStates = renderSnapshot.states;
|
||||||
std::string temporalError;
|
std::string temporalError;
|
||||||
const unsigned historyCap = mRuntimeHost.GetMaxTemporalHistoryFrames();
|
const unsigned historyCap = mRuntimeSnapshotProvider.GetMaxTemporalHistoryFrames();
|
||||||
if (!mRenderer.TemporalHistory().ValidateTextureUnitBudget(layerStates, historyCap, temporalError))
|
if (!mRenderer.TemporalHistory().ValidateTextureUnitBudget(layerStates, historyCap, temporalError))
|
||||||
{
|
{
|
||||||
CopyErrorMessage(temporalError, errorMessageSize, errorMessage);
|
CopyErrorMessage(temporalError, errorMessageSize, errorMessage);
|
||||||
@@ -92,9 +91,6 @@ bool OpenGLShaderPrograms::CompileLayerPrograms(unsigned inputFrameWidth, unsign
|
|||||||
mRenderer.ReplaceLayerPrograms(newPrograms);
|
mRenderer.ReplaceLayerPrograms(newPrograms);
|
||||||
mCommittedLayerStates = renderSnapshot.states;
|
mCommittedLayerStates = renderSnapshot.states;
|
||||||
|
|
||||||
mRuntimeHost.SetCompileStatus(true, "Shader layers compiled successfully.");
|
|
||||||
mRuntimeHost.ClearReloadRequest();
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -107,7 +103,7 @@ bool OpenGLShaderPrograms::CommitPreparedLayerPrograms(const PreparedShaderBuild
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string temporalError;
|
std::string temporalError;
|
||||||
const unsigned historyCap = mRuntimeHost.GetMaxTemporalHistoryFrames();
|
const unsigned historyCap = mRuntimeSnapshotProvider.GetMaxTemporalHistoryFrames();
|
||||||
if (!mRenderer.TemporalHistory().ValidateTextureUnitBudget(preparedBuild.renderSnapshot.states, historyCap, temporalError))
|
if (!mRenderer.TemporalHistory().ValidateTextureUnitBudget(preparedBuild.renderSnapshot.states, historyCap, temporalError))
|
||||||
{
|
{
|
||||||
CopyErrorMessage(temporalError, errorMessageSize, errorMessage);
|
CopyErrorMessage(temporalError, errorMessageSize, errorMessage);
|
||||||
@@ -155,9 +151,6 @@ bool OpenGLShaderPrograms::CommitPreparedLayerPrograms(const PreparedShaderBuild
|
|||||||
mRenderer.ReplaceLayerPrograms(newPrograms);
|
mRenderer.ReplaceLayerPrograms(newPrograms);
|
||||||
mCommittedLayerStates = preparedBuild.renderSnapshot.states;
|
mCommittedLayerStates = preparedBuild.renderSnapshot.states;
|
||||||
|
|
||||||
mRuntimeHost.SetCompileStatus(true, "Shader layers compiled successfully.");
|
|
||||||
mRuntimeHost.ClearReloadRequest();
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
#include "GlobalParamsBuffer.h"
|
#include "GlobalParamsBuffer.h"
|
||||||
#include "OpenGLRenderer.h"
|
#include "OpenGLRenderer.h"
|
||||||
#include "RuntimeHost.h"
|
|
||||||
#include "RuntimeSnapshotProvider.h"
|
#include "RuntimeSnapshotProvider.h"
|
||||||
#include "ShaderBuildQueue.h"
|
#include "ShaderBuildQueue.h"
|
||||||
#include "ShaderTypes.h"
|
#include "ShaderTypes.h"
|
||||||
@@ -16,7 +15,7 @@ class OpenGLShaderPrograms
|
|||||||
public:
|
public:
|
||||||
using LayerProgram = OpenGLRenderer::LayerProgram;
|
using LayerProgram = OpenGLRenderer::LayerProgram;
|
||||||
|
|
||||||
OpenGLShaderPrograms(OpenGLRenderer& renderer, RuntimeHost& runtimeHost, RuntimeSnapshotProvider& runtimeSnapshotProvider);
|
OpenGLShaderPrograms(OpenGLRenderer& renderer, RuntimeSnapshotProvider& runtimeSnapshotProvider);
|
||||||
|
|
||||||
bool CompileLayerPrograms(unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
bool CompileLayerPrograms(unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
||||||
bool CommitPreparedLayerPrograms(const PreparedShaderBuild& preparedBuild, unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
bool CommitPreparedLayerPrograms(const PreparedShaderBuild& preparedBuild, unsigned inputFrameWidth, unsigned inputFrameHeight, int errorMessageSize, char* errorMessage);
|
||||||
@@ -33,7 +32,6 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
OpenGLRenderer& mRenderer;
|
OpenGLRenderer& mRenderer;
|
||||||
RuntimeHost& mRuntimeHost;
|
|
||||||
RuntimeSnapshotProvider& mRuntimeSnapshotProvider;
|
RuntimeSnapshotProvider& mRuntimeSnapshotProvider;
|
||||||
ShaderTextureBindings mTextureBindings;
|
ShaderTextureBindings mTextureBindings;
|
||||||
GlobalParamsBuffer mGlobalParamsBuffer;
|
GlobalParamsBuffer mGlobalParamsBuffer;
|
||||||
|
|||||||
@@ -19,9 +19,9 @@ void CopyErrorMessage(const std::string& message, int errorMessageSize, char* er
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ShaderProgramCompiler::ShaderProgramCompiler(OpenGLRenderer& renderer, RuntimeHost& runtimeHost, ShaderTextureBindings& textureBindings) :
|
ShaderProgramCompiler::ShaderProgramCompiler(OpenGLRenderer& renderer, RuntimeSnapshotProvider& runtimeSnapshotProvider, ShaderTextureBindings& textureBindings) :
|
||||||
mRenderer(renderer),
|
mRenderer(renderer),
|
||||||
mRuntimeHost(runtimeHost),
|
mRuntimeSnapshotProvider(runtimeSnapshotProvider),
|
||||||
mTextureBindings(textureBindings)
|
mTextureBindings(textureBindings)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
@@ -31,7 +31,7 @@ bool ShaderProgramCompiler::CompileLayerProgram(const RuntimeRenderState& state,
|
|||||||
std::vector<ShaderPassBuildSource> passSources;
|
std::vector<ShaderPassBuildSource> passSources;
|
||||||
std::string loadError;
|
std::string loadError;
|
||||||
|
|
||||||
if (!mRuntimeHost.BuildLayerPassFragmentShaderSources(state.layerId, passSources, loadError))
|
if (!mRuntimeSnapshotProvider.BuildLayerPassFragmentShaderSources(state.layerId, passSources, loadError))
|
||||||
{
|
{
|
||||||
CopyErrorMessage(loadError, errorMessageSize, errorMessage);
|
CopyErrorMessage(loadError, errorMessageSize, errorMessage);
|
||||||
return false;
|
return false;
|
||||||
@@ -117,7 +117,7 @@ bool ShaderProgramCompiler::CompilePreparedLayerProgram(const RuntimeRenderState
|
|||||||
passProgram.passId = passSource.passId;
|
passProgram.passId = passSource.passId;
|
||||||
passProgram.inputNames = passSource.inputNames;
|
passProgram.inputNames = passSource.inputNames;
|
||||||
passProgram.outputName = passSource.outputName;
|
passProgram.outputName = passSource.outputName;
|
||||||
passProgram.shaderTextureBase = mTextureBindings.ResolveShaderTextureBase(state, mRuntimeHost.GetMaxTemporalHistoryFrames());
|
passProgram.shaderTextureBase = mTextureBindings.ResolveShaderTextureBase(state, mRuntimeSnapshotProvider.GetMaxTemporalHistoryFrames());
|
||||||
passProgram.textureBindings.swap(textureBindings);
|
passProgram.textureBindings.swap(textureBindings);
|
||||||
passProgram.textBindings.swap(textBindings);
|
passProgram.textBindings.swap(textBindings);
|
||||||
|
|
||||||
@@ -125,7 +125,7 @@ bool ShaderProgramCompiler::CompilePreparedLayerProgram(const RuntimeRenderState
|
|||||||
if (globalParamsIndex != GL_INVALID_INDEX)
|
if (globalParamsIndex != GL_INVALID_INDEX)
|
||||||
glUniformBlockBinding(newProgram.get(), globalParamsIndex, kGlobalParamsBindingPoint);
|
glUniformBlockBinding(newProgram.get(), globalParamsIndex, kGlobalParamsBindingPoint);
|
||||||
|
|
||||||
const unsigned historyCap = mRuntimeHost.GetMaxTemporalHistoryFrames();
|
const unsigned historyCap = mRuntimeSnapshotProvider.GetMaxTemporalHistoryFrames();
|
||||||
glUseProgram(newProgram.get());
|
glUseProgram(newProgram.get());
|
||||||
mTextureBindings.AssignLayerSamplerUniforms(newProgram.get(), state, passProgram, historyCap);
|
mTextureBindings.AssignLayerSamplerUniforms(newProgram.get(), state, passProgram, historyCap);
|
||||||
glUseProgram(0);
|
glUseProgram(0);
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "OpenGLRenderer.h"
|
#include "OpenGLRenderer.h"
|
||||||
#include "RuntimeHost.h"
|
#include "RuntimeSnapshotProvider.h"
|
||||||
#include "ShaderTextureBindings.h"
|
#include "ShaderTextureBindings.h"
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
@@ -13,7 +13,7 @@ public:
|
|||||||
using LayerProgram = OpenGLRenderer::LayerProgram;
|
using LayerProgram = OpenGLRenderer::LayerProgram;
|
||||||
using PassProgram = OpenGLRenderer::LayerProgram::PassProgram;
|
using PassProgram = OpenGLRenderer::LayerProgram::PassProgram;
|
||||||
|
|
||||||
ShaderProgramCompiler(OpenGLRenderer& renderer, RuntimeHost& runtimeHost, ShaderTextureBindings& textureBindings);
|
ShaderProgramCompiler(OpenGLRenderer& renderer, RuntimeSnapshotProvider& runtimeSnapshotProvider, ShaderTextureBindings& textureBindings);
|
||||||
|
|
||||||
bool CompileLayerProgram(const RuntimeRenderState& state, LayerProgram& layerProgram, int errorMessageSize, char* errorMessage);
|
bool CompileLayerProgram(const RuntimeRenderState& state, LayerProgram& layerProgram, int errorMessageSize, char* errorMessage);
|
||||||
bool CompilePreparedLayerProgram(const RuntimeRenderState& state, const std::vector<ShaderPassBuildSource>& passSources, LayerProgram& layerProgram, int errorMessageSize, char* errorMessage);
|
bool CompilePreparedLayerProgram(const RuntimeRenderState& state, const std::vector<ShaderPassBuildSource>& passSources, LayerProgram& layerProgram, int errorMessageSize, char* errorMessage);
|
||||||
@@ -22,6 +22,6 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
OpenGLRenderer& mRenderer;
|
OpenGLRenderer& mRenderer;
|
||||||
RuntimeHost& mRuntimeHost;
|
RuntimeSnapshotProvider& mRuntimeSnapshotProvider;
|
||||||
ShaderTextureBindings& mTextureBindings;
|
ShaderTextureBindings& mTextureBindings;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -0,0 +1,173 @@
|
|||||||
|
#include "RuntimeCoordinator.h"
|
||||||
|
|
||||||
|
#include "RuntimeStore.h"
|
||||||
|
|
||||||
|
RuntimeCoordinator::RuntimeCoordinator(RuntimeStore& runtimeStore) :
|
||||||
|
mRuntimeStore(runtimeStore)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::AddLayer(const std::string& shaderId)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.CreateStoredLayer(shaderId, error), error, true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::RemoveLayer(const std::string& layerId)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.DeleteStoredLayer(layerId, error), error, true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::MoveLayer(const std::string& layerId, int direction)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.MoveStoredLayer(layerId, direction, error), error, true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::MoveLayerToIndex(const std::string& layerId, std::size_t targetIndex)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.MoveStoredLayerToIndex(layerId, targetIndex, error), error, true, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::SetLayerBypass(const std::string& layerId, bool bypassed)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.SetStoredLayerBypassState(layerId, bypassed, error), error, true, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::SetLayerShader(const std::string& layerId, const std::string& shaderId)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.SetStoredLayerShaderSelection(layerId, shaderId, error), error, true, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::UpdateLayerParameter(const std::string& layerId, const std::string& parameterId, const JsonValue& newValue)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.SetStoredParameterValue(layerId, parameterId, newValue, error), error, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::UpdateLayerParameterByControlKey(const std::string& layerKey, const std::string& parameterKey, const JsonValue& newValue)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.SetStoredParameterValueByControlKey(layerKey, parameterKey, newValue, error), error, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::ResetLayerParameters(const std::string& layerId)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
RuntimeCoordinatorResult result = ApplyStoreMutation(mRuntimeStore.ResetStoredLayerParameterValues(layerId, error), error, false, false);
|
||||||
|
if (!result.accepted)
|
||||||
|
return result;
|
||||||
|
|
||||||
|
result.clearTransientOscState = true;
|
||||||
|
result.renderResetScope = RuntimeCoordinatorRenderResetScope::TemporalHistoryAndFeedback;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::SaveStackPreset(const std::string& presetName)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.SaveStackPresetSnapshot(presetName, error), error, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::LoadStackPreset(const std::string& presetName)
|
||||||
|
{
|
||||||
|
std::string error;
|
||||||
|
return ApplyStoreMutation(mRuntimeStore.LoadStackPresetSnapshot(presetName, error), error, true, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::RequestShaderReload(bool preserveFeedbackState)
|
||||||
|
{
|
||||||
|
return BuildQueuedReloadResult(preserveFeedbackState);
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::HandleRuntimePollFailure(const std::string& error)
|
||||||
|
{
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = true;
|
||||||
|
result.runtimeStateBroadcastRequired = true;
|
||||||
|
result.compileStatusChanged = true;
|
||||||
|
result.compileStatusSucceeded = false;
|
||||||
|
result.compileStatusMessage = error;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::HandlePreparedShaderBuildFailure(const std::string& error)
|
||||||
|
{
|
||||||
|
mPreserveFeedbackOnNextShaderBuild = false;
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = true;
|
||||||
|
result.runtimeStateBroadcastRequired = true;
|
||||||
|
result.compileStatusChanged = true;
|
||||||
|
result.compileStatusSucceeded = false;
|
||||||
|
result.compileStatusMessage = error;
|
||||||
|
result.committedStateMode = RuntimeCoordinatorCommittedStateMode::UseCommittedStates;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::HandlePreparedShaderBuildSuccess()
|
||||||
|
{
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = true;
|
||||||
|
result.runtimeStateBroadcastRequired = true;
|
||||||
|
result.compileStatusChanged = true;
|
||||||
|
result.compileStatusSucceeded = true;
|
||||||
|
result.compileStatusMessage = "Shader layers compiled successfully.";
|
||||||
|
result.committedStateMode = RuntimeCoordinatorCommittedStateMode::UseLiveSnapshots;
|
||||||
|
mPreserveFeedbackOnNextShaderBuild = false;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::HandleRuntimeReloadRequest()
|
||||||
|
{
|
||||||
|
return BuildQueuedReloadResult(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool RuntimeCoordinator::PreserveFeedbackOnNextShaderBuild() const
|
||||||
|
{
|
||||||
|
return mPreserveFeedbackOnNextShaderBuild;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::ApplyStoreMutation(bool succeeded, const std::string& errorMessage, bool reloadRequired, bool preserveFeedbackState)
|
||||||
|
{
|
||||||
|
if (!succeeded)
|
||||||
|
{
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = false;
|
||||||
|
result.errorMessage = errorMessage;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (reloadRequired)
|
||||||
|
return BuildQueuedReloadResult(preserveFeedbackState);
|
||||||
|
|
||||||
|
return BuildAcceptedNoReloadResult();
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::BuildQueuedReloadResult(bool preserveFeedbackState)
|
||||||
|
{
|
||||||
|
mPreserveFeedbackOnNextShaderBuild = preserveFeedbackState;
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = true;
|
||||||
|
result.runtimeStateBroadcastRequired = true;
|
||||||
|
result.shaderBuildRequested = true;
|
||||||
|
result.compileStatusChanged = true;
|
||||||
|
result.compileStatusSucceeded = true;
|
||||||
|
result.compileStatusMessage = "Shader rebuild queued.";
|
||||||
|
result.clearReloadRequest = true;
|
||||||
|
result.committedStateMode = RuntimeCoordinatorCommittedStateMode::UseCommittedStates;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RuntimeCoordinator::BuildAcceptedNoReloadResult() const
|
||||||
|
{
|
||||||
|
RuntimeCoordinatorResult result;
|
||||||
|
result.accepted = true;
|
||||||
|
result.runtimeStateBroadcastRequired = true;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
@@ -0,0 +1,70 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "RuntimeJson.h"
|
||||||
|
|
||||||
|
#include <cstddef>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
class RuntimeStore;
|
||||||
|
|
||||||
|
enum class RuntimeCoordinatorCommittedStateMode
|
||||||
|
{
|
||||||
|
Unchanged,
|
||||||
|
UseCommittedStates,
|
||||||
|
UseLiveSnapshots
|
||||||
|
};
|
||||||
|
|
||||||
|
enum class RuntimeCoordinatorRenderResetScope
|
||||||
|
{
|
||||||
|
None,
|
||||||
|
TemporalHistoryOnly,
|
||||||
|
TemporalHistoryAndFeedback
|
||||||
|
};
|
||||||
|
|
||||||
|
struct RuntimeCoordinatorResult
|
||||||
|
{
|
||||||
|
bool accepted = false;
|
||||||
|
bool runtimeStateBroadcastRequired = false;
|
||||||
|
bool shaderBuildRequested = false;
|
||||||
|
bool clearTransientOscState = false;
|
||||||
|
bool compileStatusChanged = false;
|
||||||
|
bool compileStatusSucceeded = false;
|
||||||
|
bool clearReloadRequest = false;
|
||||||
|
RuntimeCoordinatorCommittedStateMode committedStateMode = RuntimeCoordinatorCommittedStateMode::Unchanged;
|
||||||
|
RuntimeCoordinatorRenderResetScope renderResetScope = RuntimeCoordinatorRenderResetScope::None;
|
||||||
|
std::string compileStatusMessage;
|
||||||
|
std::string errorMessage;
|
||||||
|
};
|
||||||
|
|
||||||
|
class RuntimeCoordinator
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
explicit RuntimeCoordinator(RuntimeStore& runtimeStore);
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult AddLayer(const std::string& shaderId);
|
||||||
|
RuntimeCoordinatorResult RemoveLayer(const std::string& layerId);
|
||||||
|
RuntimeCoordinatorResult MoveLayer(const std::string& layerId, int direction);
|
||||||
|
RuntimeCoordinatorResult MoveLayerToIndex(const std::string& layerId, std::size_t targetIndex);
|
||||||
|
RuntimeCoordinatorResult SetLayerBypass(const std::string& layerId, bool bypassed);
|
||||||
|
RuntimeCoordinatorResult SetLayerShader(const std::string& layerId, const std::string& shaderId);
|
||||||
|
RuntimeCoordinatorResult UpdateLayerParameter(const std::string& layerId, const std::string& parameterId, const JsonValue& newValue);
|
||||||
|
RuntimeCoordinatorResult UpdateLayerParameterByControlKey(const std::string& layerKey, const std::string& parameterKey, const JsonValue& newValue);
|
||||||
|
RuntimeCoordinatorResult ResetLayerParameters(const std::string& layerId);
|
||||||
|
RuntimeCoordinatorResult SaveStackPreset(const std::string& presetName);
|
||||||
|
RuntimeCoordinatorResult LoadStackPreset(const std::string& presetName);
|
||||||
|
|
||||||
|
RuntimeCoordinatorResult RequestShaderReload(bool preserveFeedbackState = false);
|
||||||
|
RuntimeCoordinatorResult HandleRuntimePollFailure(const std::string& error);
|
||||||
|
RuntimeCoordinatorResult HandlePreparedShaderBuildFailure(const std::string& error);
|
||||||
|
RuntimeCoordinatorResult HandlePreparedShaderBuildSuccess();
|
||||||
|
RuntimeCoordinatorResult HandleRuntimeReloadRequest();
|
||||||
|
bool PreserveFeedbackOnNextShaderBuild() const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
RuntimeCoordinatorResult ApplyStoreMutation(bool succeeded, const std::string& errorMessage, bool reloadRequired, bool preserveFeedbackState);
|
||||||
|
RuntimeCoordinatorResult BuildQueuedReloadResult(bool preserveFeedbackState);
|
||||||
|
RuntimeCoordinatorResult BuildAcceptedNoReloadResult() const;
|
||||||
|
|
||||||
|
RuntimeStore& mRuntimeStore;
|
||||||
|
bool mPreserveFeedbackOnNextShaderBuild = false;
|
||||||
|
};
|
||||||
@@ -12,6 +12,11 @@ bool RuntimeSnapshotProvider::BuildLayerPassFragmentShaderSources(const std::str
|
|||||||
return mRuntimeHost.BuildLayerPassFragmentShaderSources(layerId, passSources, error);
|
return mRuntimeHost.BuildLayerPassFragmentShaderSources(layerId, passSources, error);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsigned RuntimeSnapshotProvider::GetMaxTemporalHistoryFrames() const
|
||||||
|
{
|
||||||
|
return mRuntimeHost.GetMaxTemporalHistoryFrames();
|
||||||
|
}
|
||||||
|
|
||||||
RuntimeSnapshotVersions RuntimeSnapshotProvider::GetVersions() const
|
RuntimeSnapshotVersions RuntimeSnapshotProvider::GetVersions() const
|
||||||
{
|
{
|
||||||
RuntimeSnapshotVersions versions;
|
RuntimeSnapshotVersions versions;
|
||||||
@@ -35,6 +40,16 @@ RuntimeRenderFrameContext RuntimeSnapshotProvider::GetFrameContext() const
|
|||||||
return frameContext;
|
return frameContext;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RuntimeSnapshotProvider::AdvanceFrame()
|
||||||
|
{
|
||||||
|
mRuntimeHost.AdvanceFrame();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool RuntimeSnapshotProvider::TryAdvanceFrame()
|
||||||
|
{
|
||||||
|
return mRuntimeHost.TryAdvanceFrame();
|
||||||
|
}
|
||||||
|
|
||||||
RuntimeRenderStateSnapshot RuntimeSnapshotProvider::GetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight) const
|
RuntimeRenderStateSnapshot RuntimeSnapshotProvider::GetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight) const
|
||||||
{
|
{
|
||||||
for (;;)
|
for (;;)
|
||||||
|
|||||||
@@ -35,8 +35,11 @@ public:
|
|||||||
explicit RuntimeSnapshotProvider(RuntimeHost& runtimeHost);
|
explicit RuntimeSnapshotProvider(RuntimeHost& runtimeHost);
|
||||||
|
|
||||||
bool BuildLayerPassFragmentShaderSources(const std::string& layerId, std::vector<ShaderPassBuildSource>& passSources, std::string& error) const;
|
bool BuildLayerPassFragmentShaderSources(const std::string& layerId, std::vector<ShaderPassBuildSource>& passSources, std::string& error) const;
|
||||||
|
unsigned GetMaxTemporalHistoryFrames() const;
|
||||||
RuntimeSnapshotVersions GetVersions() const;
|
RuntimeSnapshotVersions GetVersions() const;
|
||||||
RuntimeRenderFrameContext GetFrameContext() const;
|
RuntimeRenderFrameContext GetFrameContext() const;
|
||||||
|
void AdvanceFrame();
|
||||||
|
bool TryAdvanceFrame();
|
||||||
RuntimeRenderStateSnapshot GetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight) const;
|
RuntimeRenderStateSnapshot GetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight) const;
|
||||||
bool TryGetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight, RuntimeRenderStateSnapshot& snapshot) const;
|
bool TryGetRenderStateSnapshot(unsigned outputWidth, unsigned outputHeight, RuntimeRenderStateSnapshot& snapshot) const;
|
||||||
bool TryRefreshSnapshotParameters(RuntimeRenderStateSnapshot& snapshot) const;
|
bool TryRefreshSnapshotParameters(RuntimeRenderStateSnapshot& snapshot) const;
|
||||||
|
|||||||
@@ -2,12 +2,15 @@
|
|||||||
|
|
||||||
#include "DeckLinkSession.h"
|
#include "DeckLinkSession.h"
|
||||||
#include "OpenGLVideoIOBridge.h"
|
#include "OpenGLVideoIOBridge.h"
|
||||||
#include "RenderEngine.h"
|
|
||||||
#include "HealthTelemetry.h"
|
#include "HealthTelemetry.h"
|
||||||
|
#include "RenderEngine.h"
|
||||||
|
|
||||||
|
#include <chrono>
|
||||||
|
|
||||||
VideoBackend::VideoBackend(RenderEngine& renderEngine, HealthTelemetry& healthTelemetry) :
|
VideoBackend::VideoBackend(RenderEngine& renderEngine, HealthTelemetry& healthTelemetry) :
|
||||||
|
mHealthTelemetry(healthTelemetry),
|
||||||
mVideoIODevice(std::make_unique<DeckLinkSession>()),
|
mVideoIODevice(std::make_unique<DeckLinkSession>()),
|
||||||
mBridge(std::make_unique<OpenGLVideoIOBridge>(*mVideoIODevice, renderEngine, healthTelemetry))
|
mBridge(std::make_unique<OpenGLVideoIOBridge>(renderEngine))
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -35,7 +38,7 @@ bool VideoBackend::SelectPreferredFormats(const VideoFormatSelection& videoModes
|
|||||||
bool VideoBackend::ConfigureInput(const VideoFormat& inputVideoMode, std::string& error)
|
bool VideoBackend::ConfigureInput(const VideoFormat& inputVideoMode, std::string& error)
|
||||||
{
|
{
|
||||||
return mVideoIODevice->ConfigureInput(
|
return mVideoIODevice->ConfigureInput(
|
||||||
[this](const VideoIOFrame& frame) { mBridge->VideoFrameArrived(frame); },
|
[this](const VideoIOFrame& frame) { HandleInputFrame(frame); },
|
||||||
inputVideoMode,
|
inputVideoMode,
|
||||||
error);
|
error);
|
||||||
}
|
}
|
||||||
@@ -43,7 +46,7 @@ bool VideoBackend::ConfigureInput(const VideoFormat& inputVideoMode, std::string
|
|||||||
bool VideoBackend::ConfigureOutput(const VideoFormat& outputVideoMode, bool externalKeyingEnabled, std::string& error)
|
bool VideoBackend::ConfigureOutput(const VideoFormat& outputVideoMode, bool externalKeyingEnabled, std::string& error)
|
||||||
{
|
{
|
||||||
return mVideoIODevice->ConfigureOutput(
|
return mVideoIODevice->ConfigureOutput(
|
||||||
[this](const VideoIOCompletion& completion) { mBridge->PlayoutFrameCompleted(completion); },
|
[this](const VideoIOCompletion& completion) { HandleOutputFrameCompletion(completion); },
|
||||||
outputVideoMode,
|
outputVideoMode,
|
||||||
externalKeyingEnabled,
|
externalKeyingEnabled,
|
||||||
error);
|
error);
|
||||||
@@ -173,3 +176,63 @@ void VideoBackend::SetStatusMessage(const std::string& message)
|
|||||||
{
|
{
|
||||||
mVideoIODevice->SetStatusMessage(message);
|
mVideoIODevice->SetStatusMessage(message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void VideoBackend::HandleInputFrame(const VideoIOFrame& frame)
|
||||||
|
{
|
||||||
|
const VideoIOState& state = mVideoIODevice->State();
|
||||||
|
mHealthTelemetry.TryReportSignalStatus(!frame.hasNoInputSource, state.inputFrameSize.width, state.inputFrameSize.height, state.inputDisplayModeName);
|
||||||
|
|
||||||
|
if (mBridge)
|
||||||
|
mBridge->UploadInputFrame(frame, state);
|
||||||
|
}
|
||||||
|
|
||||||
|
void VideoBackend::HandleOutputFrameCompletion(const VideoIOCompletion& completion)
|
||||||
|
{
|
||||||
|
RecordFramePacing(completion.result);
|
||||||
|
|
||||||
|
VideoIOOutputFrame outputFrame;
|
||||||
|
if (!BeginOutputFrame(outputFrame))
|
||||||
|
return;
|
||||||
|
|
||||||
|
const VideoIOState& state = mVideoIODevice->State();
|
||||||
|
if (mBridge)
|
||||||
|
mBridge->RenderScheduledFrame(state, completion, outputFrame);
|
||||||
|
|
||||||
|
EndOutputFrame(outputFrame);
|
||||||
|
AccountForCompletionResult(completion.result);
|
||||||
|
|
||||||
|
// Schedule the next frame after render work is complete so device-side
|
||||||
|
// bookkeeping stays with the backend seam and the bridge stays render-only.
|
||||||
|
ScheduleOutputFrame(outputFrame);
|
||||||
|
}
|
||||||
|
|
||||||
|
void VideoBackend::RecordFramePacing(VideoIOCompletionResult completionResult)
|
||||||
|
{
|
||||||
|
const auto now = std::chrono::steady_clock::now();
|
||||||
|
if (mLastPlayoutCompletionTime != std::chrono::steady_clock::time_point())
|
||||||
|
{
|
||||||
|
mCompletionIntervalMilliseconds = std::chrono::duration_cast<std::chrono::duration<double, std::milli>>(now - mLastPlayoutCompletionTime).count();
|
||||||
|
if (mSmoothedCompletionIntervalMilliseconds <= 0.0)
|
||||||
|
mSmoothedCompletionIntervalMilliseconds = mCompletionIntervalMilliseconds;
|
||||||
|
else
|
||||||
|
mSmoothedCompletionIntervalMilliseconds = mSmoothedCompletionIntervalMilliseconds * 0.9 + mCompletionIntervalMilliseconds * 0.1;
|
||||||
|
if (mCompletionIntervalMilliseconds > mMaxCompletionIntervalMilliseconds)
|
||||||
|
mMaxCompletionIntervalMilliseconds = mCompletionIntervalMilliseconds;
|
||||||
|
}
|
||||||
|
mLastPlayoutCompletionTime = now;
|
||||||
|
|
||||||
|
if (completionResult == VideoIOCompletionResult::DisplayedLate)
|
||||||
|
++mLateFrameCount;
|
||||||
|
else if (completionResult == VideoIOCompletionResult::Dropped)
|
||||||
|
++mDroppedFrameCount;
|
||||||
|
else if (completionResult == VideoIOCompletionResult::Flushed)
|
||||||
|
++mFlushedFrameCount;
|
||||||
|
|
||||||
|
mHealthTelemetry.TryRecordFramePacingStats(
|
||||||
|
mCompletionIntervalMilliseconds,
|
||||||
|
mSmoothedCompletionIntervalMilliseconds,
|
||||||
|
mMaxCompletionIntervalMilliseconds,
|
||||||
|
mLateFrameCount,
|
||||||
|
mDroppedFrameCount,
|
||||||
|
mFlushedFrameCount);
|
||||||
|
}
|
||||||
|
|||||||
@@ -2,6 +2,8 @@
|
|||||||
|
|
||||||
#include "VideoIOTypes.h"
|
#include "VideoIOTypes.h"
|
||||||
|
|
||||||
|
#include <chrono>
|
||||||
|
#include <cstdint>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
@@ -50,6 +52,18 @@ public:
|
|||||||
void SetStatusMessage(const std::string& message);
|
void SetStatusMessage(const std::string& message);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
void HandleInputFrame(const VideoIOFrame& frame);
|
||||||
|
void HandleOutputFrameCompletion(const VideoIOCompletion& completion);
|
||||||
|
void RecordFramePacing(VideoIOCompletionResult completionResult);
|
||||||
|
|
||||||
|
HealthTelemetry& mHealthTelemetry;
|
||||||
std::unique_ptr<VideoIODevice> mVideoIODevice;
|
std::unique_ptr<VideoIODevice> mVideoIODevice;
|
||||||
std::unique_ptr<OpenGLVideoIOBridge> mBridge;
|
std::unique_ptr<OpenGLVideoIOBridge> mBridge;
|
||||||
|
std::chrono::steady_clock::time_point mLastPlayoutCompletionTime;
|
||||||
|
double mCompletionIntervalMilliseconds = 0.0;
|
||||||
|
double mSmoothedCompletionIntervalMilliseconds = 0.0;
|
||||||
|
double mMaxCompletionIntervalMilliseconds = 0.0;
|
||||||
|
uint64_t mLateFrameCount = 0;
|
||||||
|
uint64_t mDroppedFrameCount = 0;
|
||||||
|
uint64_t mFlushedFrameCount = 0;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -417,11 +417,21 @@ double DeckLinkSession::FrameBudgetMilliseconds() const
|
|||||||
return mScheduler.FrameBudgetMilliseconds();
|
return mScheduler.FrameBudgetMilliseconds();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool DeckLinkSession::BeginOutputFrame(VideoIOOutputFrame& frame)
|
bool DeckLinkSession::AcquireNextOutputVideoFrame(CComPtr<IDeckLinkMutableVideoFrame>& outputVideoFrame)
|
||||||
{
|
{
|
||||||
CComPtr<IDeckLinkMutableVideoFrame> outputVideoFrame = outputVideoFrameQueue.front();
|
if (outputVideoFrameQueue.empty())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
outputVideoFrame = outputVideoFrameQueue.front();
|
||||||
outputVideoFrameQueue.push_back(outputVideoFrame);
|
outputVideoFrameQueue.push_back(outputVideoFrame);
|
||||||
outputVideoFrameQueue.pop_front();
|
outputVideoFrameQueue.pop_front();
|
||||||
|
return outputVideoFrame != nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool DeckLinkSession::PopulateOutputFrame(IDeckLinkMutableVideoFrame* outputVideoFrame, VideoIOOutputFrame& frame)
|
||||||
|
{
|
||||||
|
if (outputVideoFrame == nullptr)
|
||||||
|
return false;
|
||||||
|
|
||||||
CComPtr<IDeckLinkVideoBuffer> outputVideoFrameBuffer;
|
CComPtr<IDeckLinkVideoBuffer> outputVideoFrameBuffer;
|
||||||
if (outputVideoFrame->QueryInterface(IID_IDeckLinkVideoBuffer, (void**)&outputVideoFrameBuffer) != S_OK)
|
if (outputVideoFrame->QueryInterface(IID_IDeckLinkVideoBuffer, (void**)&outputVideoFrameBuffer) != S_OK)
|
||||||
@@ -438,11 +448,44 @@ bool DeckLinkSession::BeginOutputFrame(VideoIOOutputFrame& frame)
|
|||||||
frame.width = mState.outputFrameSize.width;
|
frame.width = mState.outputFrameSize.width;
|
||||||
frame.height = mState.outputFrameSize.height;
|
frame.height = mState.outputFrameSize.height;
|
||||||
frame.pixelFormat = mState.outputPixelFormat;
|
frame.pixelFormat = mState.outputPixelFormat;
|
||||||
frame.nativeFrame = outputVideoFrame.p;
|
frame.nativeFrame = outputVideoFrame;
|
||||||
frame.nativeBuffer = outputVideoFrameBuffer.Detach();
|
frame.nativeBuffer = outputVideoFrameBuffer.Detach();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool DeckLinkSession::ScheduleFrame(IDeckLinkMutableVideoFrame* outputVideoFrame)
|
||||||
|
{
|
||||||
|
const VideoIOScheduleTime scheduleTime = mScheduler.NextScheduleTime();
|
||||||
|
return outputVideoFrame != nullptr &&
|
||||||
|
output->ScheduleVideoFrame(outputVideoFrame, scheduleTime.streamTime, scheduleTime.duration, scheduleTime.timeScale) == S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool DeckLinkSession::ScheduleBlackFrame(IDeckLinkMutableVideoFrame* outputVideoFrame)
|
||||||
|
{
|
||||||
|
if (outputVideoFrame == nullptr)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
CComPtr<IDeckLinkVideoBuffer> outputVideoFrameBuffer;
|
||||||
|
if (outputVideoFrame->QueryInterface(IID_IDeckLinkVideoBuffer, (void**)&outputVideoFrameBuffer) != S_OK)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (outputVideoFrameBuffer->StartAccess(bmdBufferAccessWrite) != S_OK)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
void* pFrame = nullptr;
|
||||||
|
outputVideoFrameBuffer->GetBytes((void**)&pFrame);
|
||||||
|
memset(pFrame, 0, outputVideoFrame->GetRowBytes() * mState.outputFrameSize.height);
|
||||||
|
|
||||||
|
outputVideoFrameBuffer->EndAccess(bmdBufferAccessWrite);
|
||||||
|
return ScheduleFrame(outputVideoFrame);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool DeckLinkSession::BeginOutputFrame(VideoIOOutputFrame& frame)
|
||||||
|
{
|
||||||
|
CComPtr<IDeckLinkMutableVideoFrame> outputVideoFrame;
|
||||||
|
return AcquireNextOutputVideoFrame(outputVideoFrame) && PopulateOutputFrame(outputVideoFrame, frame);
|
||||||
|
}
|
||||||
|
|
||||||
void DeckLinkSession::EndOutputFrame(VideoIOOutputFrame& frame)
|
void DeckLinkSession::EndOutputFrame(VideoIOOutputFrame& frame)
|
||||||
{
|
{
|
||||||
IDeckLinkVideoBuffer* outputVideoFrameBuffer = static_cast<IDeckLinkVideoBuffer*>(frame.nativeBuffer);
|
IDeckLinkVideoBuffer* outputVideoFrameBuffer = static_cast<IDeckLinkVideoBuffer*>(frame.nativeBuffer);
|
||||||
@@ -463,11 +506,7 @@ void DeckLinkSession::AccountForCompletionResult(VideoIOCompletionResult complet
|
|||||||
bool DeckLinkSession::ScheduleOutputFrame(const VideoIOOutputFrame& frame)
|
bool DeckLinkSession::ScheduleOutputFrame(const VideoIOOutputFrame& frame)
|
||||||
{
|
{
|
||||||
IDeckLinkMutableVideoFrame* outputVideoFrame = static_cast<IDeckLinkMutableVideoFrame*>(frame.nativeFrame);
|
IDeckLinkMutableVideoFrame* outputVideoFrame = static_cast<IDeckLinkMutableVideoFrame*>(frame.nativeFrame);
|
||||||
const VideoIOScheduleTime scheduleTime = mScheduler.NextScheduleTime();
|
return ScheduleFrame(outputVideoFrame);
|
||||||
if (outputVideoFrame == nullptr || output->ScheduleVideoFrame(outputVideoFrame, scheduleTime.streamTime, scheduleTime.duration, scheduleTime.timeScale) != S_OK)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool DeckLinkSession::Start()
|
bool DeckLinkSession::Start()
|
||||||
@@ -486,31 +525,13 @@ bool DeckLinkSession::Start()
|
|||||||
|
|
||||||
for (unsigned i = 0; i < kPrerollFrameCount; i++)
|
for (unsigned i = 0; i < kPrerollFrameCount; i++)
|
||||||
{
|
{
|
||||||
CComPtr<IDeckLinkMutableVideoFrame> outputVideoFrame = outputVideoFrameQueue.front();
|
CComPtr<IDeckLinkMutableVideoFrame> outputVideoFrame;
|
||||||
outputVideoFrameQueue.push_back(outputVideoFrame);
|
if (!AcquireNextOutputVideoFrame(outputVideoFrame))
|
||||||
outputVideoFrameQueue.pop_front();
|
|
||||||
|
|
||||||
CComPtr<IDeckLinkVideoBuffer> outputVideoFrameBuffer;
|
|
||||||
if (outputVideoFrame->QueryInterface(IID_IDeckLinkVideoBuffer, (void**)&outputVideoFrameBuffer) != S_OK)
|
|
||||||
{
|
{
|
||||||
MessageBoxA(NULL, "Could not query the preroll output frame buffer.", "DeckLink start failed", MB_OK | MB_ICONERROR);
|
MessageBoxA(NULL, "Could not acquire a preroll output frame.", "DeckLink start failed", MB_OK | MB_ICONERROR);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
if (!ScheduleBlackFrame(outputVideoFrame))
|
||||||
if (outputVideoFrameBuffer->StartAccess(bmdBufferAccessWrite) != S_OK)
|
|
||||||
{
|
|
||||||
MessageBoxA(NULL, "Could not write to the preroll output frame buffer.", "DeckLink start failed", MB_OK | MB_ICONERROR);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void* pFrame = nullptr;
|
|
||||||
outputVideoFrameBuffer->GetBytes((void**)&pFrame);
|
|
||||||
memset(pFrame, 0, outputVideoFrame->GetRowBytes() * mState.outputFrameSize.height);
|
|
||||||
|
|
||||||
outputVideoFrameBuffer->EndAccess(bmdBufferAccessWrite);
|
|
||||||
|
|
||||||
const VideoIOScheduleTime scheduleTime = mScheduler.NextScheduleTime();
|
|
||||||
if (output->ScheduleVideoFrame(outputVideoFrame, scheduleTime.streamTime, scheduleTime.duration, scheduleTime.timeScale) != S_OK)
|
|
||||||
{
|
{
|
||||||
MessageBoxA(NULL, "Could not schedule a preroll output frame.", "DeckLink start failed", MB_OK | MB_ICONERROR);
|
MessageBoxA(NULL, "Could not schedule a preroll output frame.", "DeckLink start failed", MB_OK | MB_ICONERROR);
|
||||||
return false;
|
return false;
|
||||||
@@ -599,23 +620,23 @@ void DeckLinkSession::HandlePlayoutFrameCompleted(IDeckLinkVideoFrame*, BMDOutpu
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
VideoIOCompletion completion;
|
VideoIOCompletion completion;
|
||||||
|
completion.result = TranslateCompletionResult(completionResult);
|
||||||
|
mOutputFrameCallback(completion);
|
||||||
|
}
|
||||||
|
|
||||||
|
VideoIOCompletionResult DeckLinkSession::TranslateCompletionResult(BMDOutputFrameCompletionResult completionResult)
|
||||||
|
{
|
||||||
switch (completionResult)
|
switch (completionResult)
|
||||||
{
|
{
|
||||||
case bmdOutputFrameDisplayedLate:
|
case bmdOutputFrameDisplayedLate:
|
||||||
completion.result = VideoIOCompletionResult::DisplayedLate;
|
return VideoIOCompletionResult::DisplayedLate;
|
||||||
break;
|
|
||||||
case bmdOutputFrameDropped:
|
case bmdOutputFrameDropped:
|
||||||
completion.result = VideoIOCompletionResult::Dropped;
|
return VideoIOCompletionResult::Dropped;
|
||||||
break;
|
|
||||||
case bmdOutputFrameFlushed:
|
case bmdOutputFrameFlushed:
|
||||||
completion.result = VideoIOCompletionResult::Flushed;
|
return VideoIOCompletionResult::Flushed;
|
||||||
break;
|
|
||||||
case bmdOutputFrameCompleted:
|
case bmdOutputFrameCompleted:
|
||||||
completion.result = VideoIOCompletionResult::Completed;
|
return VideoIOCompletionResult::Completed;
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
completion.result = VideoIOCompletionResult::Unknown;
|
return VideoIOCompletionResult::Unknown;
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
mOutputFrameCallback(completion);
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -66,6 +66,12 @@ public:
|
|||||||
void HandlePlayoutFrameCompleted(IDeckLinkVideoFrame* completedFrame, BMDOutputFrameCompletionResult completionResult);
|
void HandlePlayoutFrameCompleted(IDeckLinkVideoFrame* completedFrame, BMDOutputFrameCompletionResult completionResult);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
bool AcquireNextOutputVideoFrame(CComPtr<IDeckLinkMutableVideoFrame>& outputVideoFrame);
|
||||||
|
bool PopulateOutputFrame(IDeckLinkMutableVideoFrame* outputVideoFrame, VideoIOOutputFrame& frame);
|
||||||
|
bool ScheduleFrame(IDeckLinkMutableVideoFrame* outputVideoFrame);
|
||||||
|
bool ScheduleBlackFrame(IDeckLinkMutableVideoFrame* outputVideoFrame);
|
||||||
|
static VideoIOCompletionResult TranslateCompletionResult(BMDOutputFrameCompletionResult completionResult);
|
||||||
|
|
||||||
CComPtr<CaptureDelegate> captureDelegate;
|
CComPtr<CaptureDelegate> captureDelegate;
|
||||||
CComPtr<PlayoutDelegate> playoutDelegate;
|
CComPtr<PlayoutDelegate> playoutDelegate;
|
||||||
CComPtr<IDeckLinkInput> input;
|
CComPtr<IDeckLinkInput> input;
|
||||||
|
|||||||
Reference in New Issue
Block a user