#ifndef __OPENGL_COMPOSITE_H__ #define __OPENGL_COMPOSITE_H__ #include #include #include #include #include #include #include #include #include "GLExtensions.h" #include "RuntimeCoordinator.h" #include "RuntimeHost.h" #include "RuntimeSnapshotProvider.h" #include "RuntimeStore.h" #include #include #include #include #include #include #include #include #include class RenderEngine; class RuntimeServices; class ShaderBuildQueue; class VideoBackend; class OpenGLComposite { public: OpenGLComposite(HWND hWnd, HDC hDC, HGLRC hRC); ~OpenGLComposite(); bool InitDeckLink(); bool InitVideoIO(); bool Start(); bool Stop(); bool ReloadShader(bool preserveFeedbackState = false); std::string GetRuntimeStateJson() const; bool AddLayer(const std::string& shaderId, std::string& error); bool RemoveLayer(const std::string& layerId, std::string& error); bool MoveLayer(const std::string& layerId, int direction, std::string& error); bool MoveLayerToIndex(const std::string& layerId, std::size_t targetIndex, std::string& error); bool SetLayerBypass(const std::string& layerId, bool bypassed, std::string& error); bool SetLayerShader(const std::string& layerId, const std::string& shaderId, std::string& error); bool UpdateLayerParameterJson(const std::string& layerId, const std::string& parameterId, const std::string& valueJson, std::string& error); bool UpdateLayerParameterByControlKeyJson(const std::string& layerKey, const std::string& parameterKey, const std::string& valueJson, std::string& error); bool ResetLayerParameters(const std::string& layerId, std::string& error); bool SaveStackPreset(const std::string& presetName, std::string& error); bool LoadStackPreset(const std::string& presetName, std::string& error); bool RequestScreenshot(std::string& error); unsigned short GetControlServerPort() const; unsigned short GetOscPort() const; std::string GetOscBindAddress() const; std::string GetControlUrl() const; std::string GetDocsUrl() const; std::string GetOscAddress() const; void resizeGL(WORD width, WORD height); void paintGL(bool force = false); private: void resizeWindow(int width, int height); bool CheckOpenGLExtensions(); void PublishVideoIOStatus(const std::string& statusMessage); struct OscOverlayState { std::string layerKey; std::string parameterKey; JsonValue targetValue; ShaderParameterValue currentValue; bool hasCurrentValue = false; std::chrono::steady_clock::time_point lastUpdatedTime; std::chrono::steady_clock::time_point lastAppliedTime; uint64_t generation = 0; uint64_t pendingCommitGeneration = 0; bool commitQueued = false; }; HWND hGLWnd; HDC hGLDC; HGLRC hGLRC; CRITICAL_SECTION pMutex; std::unique_ptr mRuntimeHost; std::unique_ptr mRuntimeStore; std::unique_ptr mRuntimeCoordinator; std::unique_ptr mRuntimeSnapshotProvider; std::unique_ptr mRenderEngine; std::unique_ptr mShaderBuildQueue; std::unique_ptr mRuntimeServices; std::unique_ptr mVideoBackend; std::map mOscOverlayStates; std::atomic mUseCommittedLayerStates; std::atomic mScreenshotRequested; bool InitOpenGLState(); void renderEffect(); bool ProcessRuntimePollResults(); void RequestShaderBuild(); bool ApplyRuntimeCoordinatorResult(const RuntimeCoordinatorResult& result, std::string* error = nullptr); void ApplyRuntimeCoordinatorRenderReset(RuntimeCoordinatorRenderResetScope resetScope); void ProcessScreenshotRequest(); std::filesystem::path BuildScreenshotPath() const; void broadcastRuntimeState(); }; #endif // __OPENGL_COMPOSITE_H__