diff --git a/dgVoodooAPI/Bin/Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/Release/dgVoodooAPI.dll deleted file mode 100644 index d7d79f1..0000000 Binary files a/dgVoodooAPI/Bin/Release/dgVoodooAPI.dll and /dev/null differ diff --git a/dgVoodooAPI/Bin/Spec Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/Spec Release/dgVoodooAPI.dll deleted file mode 100644 index dcb5eec..0000000 Binary files a/dgVoodooAPI/Bin/Spec Release/dgVoodooAPI.dll and /dev/null differ diff --git a/dgVoodooAPI/Bin/x64/Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/x64/Release/dgVoodooAPI.dll new file mode 100644 index 0000000..0b4012c Binary files /dev/null and b/dgVoodooAPI/Bin/x64/Release/dgVoodooAPI.dll differ diff --git a/dgVoodooAPI/Bin/x64/Spec Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/x64/Spec Release/dgVoodooAPI.dll new file mode 100644 index 0000000..0c6d3ac Binary files /dev/null and b/dgVoodooAPI/Bin/x64/Spec Release/dgVoodooAPI.dll differ diff --git a/dgVoodooAPI/Bin/x86/Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/x86/Release/dgVoodooAPI.dll new file mode 100644 index 0000000..f82c938 Binary files /dev/null and b/dgVoodooAPI/Bin/x86/Release/dgVoodooAPI.dll differ diff --git a/dgVoodooAPI/Bin/x86/Spec Release/dgVoodooAPI.dll b/dgVoodooAPI/Bin/x86/Spec Release/dgVoodooAPI.dll new file mode 100644 index 0000000..2b1543c Binary files /dev/null and b/dgVoodooAPI/Bin/x86/Spec Release/dgVoodooAPI.dll differ diff --git a/dgVoodooAPI/Doc/dgVoodooAPI.chm b/dgVoodooAPI/Doc/dgVoodooAPI.chm index bdab889..0c85bda 100644 Binary files a/dgVoodooAPI/Doc/dgVoodooAPI.chm and b/dgVoodooAPI/Doc/dgVoodooAPI.chm differ diff --git a/dgVoodooAPI/Inc/APIControl.hpp b/dgVoodooAPI/Inc/APIControl.hpp new file mode 100644 index 0000000..31f96b1 --- /dev/null +++ b/dgVoodooAPI/Inc/APIControl.hpp @@ -0,0 +1,56 @@ +// ***************************************************************************** +// File: APIControl.hpp +// +// Description: Functions and structures for controlling dgVoodoo +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef APICONTROL_HPP +#define APICONTROL_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "APITypes.h" + +// --- Defines ----------------------------------------------------------------- + +#define IMPORT /*_declspec(dllimport)*/ _stdcall + +// --- Predeclarations --------------------------------------------------------- + +namespace dgVoodoo { + +// --- APIControl -------------------------------------------------------------- + +// --- Objects + +struct APIControl +{ + struct Debug + { + bool enableGlideVisualDebug; + bool enableDDrawVisualDebug; + bool enableD3DVisualDebug; + }; + + Debug debug; + + void* internalHandle; +}; + +// --- Functions + +typedef APIControl* (IMPORT *DGAPIGetAPIControlPtrType) (); +typedef bool (IMPORT *DGAPIReleaseAPIControlPtrType) (APIControl* pCtrl); + +extern "C" { + + APIControl* DGAPIGetAPIControlPtr (); + bool DGAPIReleaseAPIControlPtr (APIControl* pCtrl); +} + +} // namespace dgVoodoo + +#endif // !APICONTROL_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/ICPLDDI.hpp b/dgVoodooAPI/Inc/APIDll/ICPLDDI.hpp similarity index 100% rename from dgVoodooAPI/Inc/ICPLDDI.hpp rename to dgVoodooAPI/Inc/APIDll/ICPLDDI.hpp diff --git a/dgVoodooAPI/Inc/IMainFactory.hpp b/dgVoodooAPI/Inc/APIDll/IMainFactory.hpp similarity index 100% rename from dgVoodooAPI/Inc/IMainFactory.hpp rename to dgVoodooAPI/Inc/APIDll/IMainFactory.hpp diff --git a/dgVoodooAPI/Inc/Addon/AddonDefs.hpp b/dgVoodooAPI/Inc/Addon/AddonDefs.hpp new file mode 100644 index 0000000..b71c4c8 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/AddonDefs.hpp @@ -0,0 +1,55 @@ +// ***************************************************************************** +// File: AddonDefs.hpp +// +// Description: Main dgVoodoo addon header +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ADDONDEFS_HPP +#define ADDONDEFS_HPP + +// --- Includes ---------------------------------------------------------------- + +#include +#include "APITypes.h" + +// --- Defines ----------------------------------------------------------------- + +#define DEFINE_ADDON_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8) \ + EXTERN_C const GUID FAR name + +// --- Interface GUIDs + +DEFINE_ADDON_GUID (IID_D3DObserver, 0x1ad8ea63, 0x72c4, 0x4219, 0xbf, 0xf3, 0x88, 0x87, 0x98, 0xc6, 0xb7, 0xc0); +DEFINE_ADDON_GUID (IID_D3DDeviceObserver, 0x80b505f3, 0x9b00, 0x428e, 0x92, 0x7, 0xcb, 0x60, 0x9, 0x58, 0xec, 0xe1); +DEFINE_ADDON_GUID (IID_D3DResourceObserver, 0xd5010988, 0x96b2, 0x4158, 0xa9, 0xd4, 0x9, 0x45, 0xaa, 0xaf, 0x24, 0xb3); + +DEFINE_ADDON_GUID (IID_D3D12RootObserver, 0x68801515, 0xfec7, 0x43d2, 0xae, 0xc4, 0x21, 0xa8, 0xab, 0x9a, 0x6c, 0x62); + +// --- Predeclarations --------------------------------------------------------- + +// --- Addon interfaces + +namespace dgVoodoo { + +class IAddonMainCallback; + +class ID3DObserver; +class ID3DDeviceObserver; +class ID3DResourceObserver; + +class ID3D12RootObserver; + +}; + +// --- TypeDefs ---------------------------------------------------------------- + +// --- Mandatory functions to be implemented in the addon + +typedef bool API_EXPORT (*AddonInitType) (dgVoodoo::IAddonMainCallback* pAddonMain); +typedef void API_EXPORT (*AddonExitType) (); + + +#endif // ADDONDEFS_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/IAddonMainCallback.hpp b/dgVoodooAPI/Inc/Addon/IAddonMainCallback.hpp new file mode 100644 index 0000000..923966f --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/IAddonMainCallback.hpp @@ -0,0 +1,53 @@ +// ***************************************************************************** +// File: IAddonMain.hpp +// +// Description: Main callback interface for dgVoodoo add-ons +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef IADDONMAIN_HPP +#define IADDONMAIN_HPP + +// --- Includes ---------------------------------------------------------------- + +#include +#include "..\APIDebugObj.hpp" +#include "..\IIniParser.hpp" + +namespace dgVoodoo { + +// --- IAddonMain -------------------------------------------------------------- + +class IAddonMainCallback +{ +public: + // --- Query + + virtual UInt32 GetVersion () const = 0; + + // --- Interface registering + + virtual bool RegisterForCallback (REFIID iid, void* pCallbackObject) = 0; + virtual void UnregisterForCallback (REFIID iid, void* pCallbackObject) = 0; + + // --- Factoring + + virtual IIniParser* CreateIniParser (const APIDebugObj* pDebugObj = NULL) = 0; + + virtual UInt32 RSSizeOfResource (HMODULE hModule, LPCTSTR name, LPCTSTR type) = 0; + virtual bool RSLoadResource (HMODULE hModule, LPCTSTR name, LPCTSTR type, BYTE* dst) = 0; + virtual const BYTE* RSLoadResource (HMODULE hModule, LPCTSTR name, LPCTSTR type) = 0; + + // --- Debug + + virtual void IssueInfo (const APIDebugObj* pDebugObj, const char* pInfoMessage, ...) = 0; + virtual void IssueWarning (const APIDebugObj* pDebugObj, const char* pWarningMessage, ...) = 0; + virtual void IssueError (const APIDebugObj* pDebugObj, const char* pErrorMessage, ...) = 0; +}; + + +} // namespace dgVoodoo + +#endif // !IADDONMAIN_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3D.hpp b/dgVoodooAPI/Inc/Addon/ID3D.hpp new file mode 100644 index 0000000..85ff53a --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3D.hpp @@ -0,0 +1,37 @@ +// ***************************************************************************** +// File: ID3D.hpp +// +// Description: Interface for D3D objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3D_HPP +#define ID3D_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "..\APITypes.h" + +namespace dgVoodoo { + +// --- ID3D -------------------------------------------------------------------- + +class ID3D +{ +public: + enum ObjectType + { + OT_D3D = 0, + OT_D3D8, + OT_D3D9 + }; + + virtual ObjectType GetObjectType () const = 0; +}; + + +} // namespace dgVoodoo + +#endif // !ID3D_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3D12Root.hpp b/dgVoodooAPI/Inc/Addon/ID3D12Root.hpp new file mode 100644 index 0000000..5747789 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3D12Root.hpp @@ -0,0 +1,287 @@ +// ***************************************************************************** +// File: ID3D12Root.hpp +// +// Description: Interface for D3D12 Root +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3D12ROOT_HPP +#define ID3D12ROOT_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "..\APITypes.h" +#include "D3D12.h" + +//namespace dgVoodoo { + +// --- Predeclarations --------------------------------------------------------- + +class ID3D12ResourceDescAllocator; +class ID3D12GraphicsCommandListAuto; +class ID3D12ResourceDescRingBuffer; +class ID3D12Buffer; +class ID3D12HeapPageAllocator; +class ID3D12Swapchain; + +// --- ID3D12Root -------------------------------------------------------------- + +class ID3D12Root +{ +public: + + struct SwapchainData + { + SIZE imageSize; + SIZE imagePresentationSize; + DXGI_FORMAT format; + SIZE maxOverriddenInputTextureSize; + }; + + + struct GraphicsPLDesc + { + ID3D12RootSignature* pRootSignature; + ID3DBlob* pVS; + ID3DBlob* pPS; + ID3DBlob* pDS; + ID3DBlob* pHS; + ID3DBlob* pGS; + D3D12_STREAM_OUTPUT_DESC* pStreamOutput; + D3D12_BLEND_DESC* pBlendState; + UINT SampleMask; + D3D12_RASTERIZER_DESC* pRasterizerState; + D3D12_DEPTH_STENCIL_DESC* pDepthStencilState; + D3D12_INPUT_LAYOUT_DESC* pInputLayout; + D3D12_INDEX_BUFFER_STRIP_CUT_VALUE IBStripCutValue; + D3D12_PRIMITIVE_TOPOLOGY_TYPE PrimitiveTopologyType; + UINT NumRenderTargets; + DXGI_FORMAT RTVFormats[8]; + DXGI_FORMAT DSVFormat; + DXGI_SAMPLE_DESC SampleDesc; + UINT NodeMask; + D3D12_PIPELINE_STATE_FLAGS Flags; + }; + + struct ComputePLDesc + { + ID3D12RootSignature* pRootSignature; + ID3DBlob* pCS; + UINT NodeMask; + D3D12_PIPELINE_STATE_FLAGS Flags; + }; + + struct SwapchainProxyTextureData + { + ID3D12Resource* pTexture; + UINT texState; + D3D12_CPU_DESCRIPTOR_HANDLE srvHandle; + D3D12_CPU_DESCRIPTOR_HANDLE rtvHandle; + DXGI_FORMAT rtvFormat; + }; + + enum DynamicAllocator + { + DA_RingAllocator = 0, + DA_ConstBufferPageHeapAllocator, + DA_VertexBufferPageHeapAllocator, + DA_IndexBufferPageHeapAllocator, + DA_UploadBufferPageHeapAllocator, + DA_ReadbackBufferPageHeapAllocator + }; + +public: + // Factoring related methods + + virtual ID3D12Device* GetDevice (UInt32 adapterID) = 0; + + virtual ID3D12RootSignature* SerializeAndCreateRootSignature (UInt32 adapterID, D3D_ROOT_SIGNATURE_VERSION Version, + const D3D12_ROOT_SIGNATURE_DESC* pRootSignatureDesc, + ID3DBlob** ppErrorBlob) = 0; + + virtual ID3DBlob* CreateD3DBlob (UIntPtr dataSize, const void* pInitialData) = 0; + + virtual ID3D12ResourceDescAllocator* GetCBV_SRV_UAV_DescAllocator (UInt32 adapterID) = 0; + virtual ID3D12ResourceDescAllocator* GetRTV_DescAllocator (UInt32 adapterID) = 0; + virtual ID3D12ResourceDescAllocator* GetDSV_DescAllocator (UInt32 adapterID) = 0; + virtual ID3D12ResourceDescAllocator* GetSampler_DescAllocator (UInt32 adapterID) = 0; + + virtual ID3D12GraphicsCommandListAuto* GetGraphicsCommandListAuto (UInt32 adapterID) = 0; + virtual ID3D12GraphicsCommandListAuto* GetCopyCommandListAuto (UInt32 adapterID) = 0; + + virtual ID3D12HeapPageAllocator* GetHeapPageAllocator (UInt32 adapterID, DynamicAllocator allocator) = 0; + + virtual ID3D12ResourceDescRingBuffer* GetCBV_SRV_UAV_RingBuffer (UInt32 adapterID) = 0; + virtual ID3D12ResourceDescRingBuffer* CreateResourceDescRingBuffer (UInt32 adapterID, D3D12_DESCRIPTOR_HEAP_TYPE heapType, + UINT numDescriptors, D3D12_DESCRIPTOR_HEAP_FLAGS heapFlags) = 0; + + virtual ID3D12Buffer* CreateStaticBuffer (UInt32 adapterID, UInt32 bufferSize, D3D12_HEAP_TYPE heapType, D3D12_HEAP_FLAGS heapFlags) = 0; + virtual ID3D12Buffer* CreateDynamicBuffer (UInt32 adapterID, UInt32 bufferSize, DynamicAllocator allocatorType) = 0; + + // Swapchains + + virtual SwapchainData GetSwapchainData (ID3D12Swapchain* pSwapchain) = 0; + virtual UInt32 GetMaxNumberOfProxyTextures (UInt32 adapterID) = 0; + virtual bool GetProxyTexture (ID3D12Swapchain* pSwapchain, UInt32 idx, SwapchainProxyTextureData* pOutData) = 0; + + // Resource tracking + + virtual bool RTEnableTrackingUnkownResources (bool enable) = 0; + virtual bool RTResourceDestroyed (ID3D12Resource* pResource, bool waitForCompletion = true) = 0; + virtual bool RTObjectDestroyed (void* pObject, bool waitForCompletion = true) = 0; + + // Pipeline object caches + + virtual D3D12_DEPTH_STENCIL_DESC* PLCacheGetDepthStencilDesc (UInt32 adapterID, const D3D12_DEPTH_STENCIL_DESC& desc) = 0; + virtual D3D12_BLEND_DESC* PLCacheGetBlend4Desc (UInt32 adapterID, const D3D12_BLEND_DESC& desc) = 0; // only the first 4 RT's are taken into account... sorry about that + virtual D3D12_RASTERIZER_DESC* PLCacheGetRasterizerDesc (UInt32 adapterID, const D3D12_RASTERIZER_DESC& desc) = 0; + virtual D3D12_INPUT_LAYOUT_DESC* PLCacheGetInputLayoutDesc (UInt32 adapterID, UInt32 numOfElements, const D3D12_INPUT_ELEMENT_DESC* pElements) = 0; + virtual ID3D12PipelineState* PLCacheGetGraphicsPipeline (UInt32 adapterID, const GraphicsPLDesc& desc) = 0; + virtual ID3D12PipelineState* PLCacheGetComputePipeline (UInt32 adapterID, const ComputePLDesc& desc) = 0; + + // Graphics pipeline state notification methods + + virtual void GPLRootSignatureReleased (UInt32 adapterID, ID3D12RootSignature* pRootSignature) = 0; + virtual void GPLShaderReleased (UInt32 adapterID, ID3DBlob* pShader) = 0; + virtual void GPLStreamOutputReleased (UInt32 adapterID, D3D12_STREAM_OUTPUT_DESC* pStreamOutput) = 0; + virtual void GPLBlendStateReleased (UInt32 adapterID, D3D12_BLEND_DESC* pBlendState) = 0; + virtual void GPLRasterizerStateReleased (UInt32 adapterID, D3D12_RASTERIZER_DESC* pRasterizerState) = 0; + virtual void GPLDepthStencilStateReleased (UInt32 adapterID, D3D12_DEPTH_STENCIL_DESC* pDepthStencilState) = 0; + virtual void GPLInputLayoutReleased (UInt32 adapterID, D3D12_INPUT_LAYOUT_DESC* pInputLayout) = 0; + + // Compute pipeline state notification methods + + virtual void CPLRootSignatureReleased (UInt32 adapterID, ID3D12RootSignature* pRootSignature) = 0; + virtual void CPLShaderReleased (UInt32 adapterID, ID3DBlob* pShader) = 0; +}; + + +// --- ID3D12ResourceDescAllocator --------------------------------------------- + +class ID3D12ResourceDescAllocator +{ +public: + virtual UInt32 AllocDescriptorGroup (UInt32 numOfContinuousDescriptors) = 0; + virtual void DeallocDescriptorGroup (UInt32 handle, UInt32 numOfContinuousDescriptors, + ID3D12Fence* pFence = NULL, UINT64 fenceValue = 0) = 0; + + virtual UInt32 GetSubGroupHandle (UInt32 handle, UInt32 descIndex) = 0; + + virtual D3D12_GPU_DESCRIPTOR_HANDLE GetGPUDescHandle (UInt32 handle, UInt32 descIndex = 0) = 0; + virtual D3D12_CPU_DESCRIPTOR_HANDLE GetCPUDescHandle (UInt32 handle, UInt32 descIndex = 0) = 0; + + virtual ID3D12DescriptorHeap* GetDescriptorHeap (UInt32 handle) = 0; +}; + + +// --- ID3D12ResourceDescRingBuffer -------------------------------------------- + +class ID3D12ResourceDescRingBuffer +{ +public: + struct AllocData + { + D3D12_GPU_DESCRIPTOR_HANDLE gpuDescHandle; + D3D12_CPU_DESCRIPTOR_HANDLE cpuDescHandle; + ID3D12DescriptorHeap* pHeap; + UInt32 incrementSize; + }; + + virtual bool Alloc (UInt32 numOfDescriptors, ID3D12Fence* pFence, UINT64 fenceValue, AllocData& allocData) = 0; + + virtual void Release () = 0; +}; + +// --- ID3D12Buffer ------------------------------------------------------------ + +class ID3D12Buffer +{ +public: + enum LockType + { + LT_Default = 0, // Wait for GPU (static buffer) + LT_NoOverwrite, // Nooverwrite - No wait for GPU (dynamic buffer) + LT_Discard // Discard - No wait for GPU (dynamic buffer) + }; + + struct LockData + { + UInt64 gpuAddress; + void* ptr; + ID3D12Resource* pBuffer; + }; + + virtual bool HasAddressChanged () const = 0; + virtual void ClearAddressChangedFlag () = 0; + virtual bool GetAndClearAddressChangedBit (UInt32 idx) = 0; + + virtual LockData Lock (LockType lockType, ID3D12Fence* pFence = NULL, UInt64 fenceValue = 0) = 0; + virtual void Unlock () = 0; + + virtual void Release () = 0; +}; + +// --- ID3D12GraphicsCommandListAuto ------------------------------------------- + +class ID3D12GraphicsCommandListAuto +{ +public: + virtual ID3D12GraphicsCommandList* GetCommandListInterface () = 0; + + virtual bool IsCurrentId (void* id) = 0; + virtual bool ChangeId (void* newId) = 0; + + virtual UINT64 GetFenceValue () const = 0; + + virtual bool AFlush (bool waitForCompletion = false) = 0; + virtual void AFlushLock () = 0; + virtual void AFlushUnlock (bool forceFlush = false) = 0; + virtual UINT64 AGetLastFlushFenceValue () const = 0; + virtual ID3D12Fence* AGetFence () const = 0; + + virtual bool HIUpdateSubBuffer (ID3D12Resource* pMADBuffer, ID3D12HeapPageAllocator* pAllocator, + UInt32 begin, UInt32 end, const void* pSrcData, bool setToUnmappedState = false) = 0; + + virtual bool HIUpdateSubTexture (ID3D12Resource* pMADTexture, UInt32 dstSubResIdx, + ID3D12HeapPageAllocator* pAllocator, const D3D12_BOX& dstBox, + const void* pSrcData, UInt32 srcPitch, UInt32 srcDepth) = 0; +}; + +// --- Helpers ----------------------------------------------------------------- + +struct D3D12RSPARAMETER: public D3D12_ROOT_PARAMETER +{ + D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE _ParameterType, UINT NumDescriptorRanges, const D3D12_DESCRIPTOR_RANGE* pDescriptorRanges, + D3D12_SHADER_VISIBILITY _ShaderVisibility) + { + ParameterType = _ParameterType; + DescriptorTable.NumDescriptorRanges = NumDescriptorRanges; + DescriptorTable.pDescriptorRanges = pDescriptorRanges; + ShaderVisibility = _ShaderVisibility; + } + + D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE _ParameterType, UINT ShaderRegister, UINT RegisterSpace, UINT Num32BitValues, + D3D12_SHADER_VISIBILITY _ShaderVisibility) + { + ParameterType = _ParameterType; + Constants.ShaderRegister = ShaderRegister; + Constants.RegisterSpace = RegisterSpace; + Constants.Num32BitValues = Num32BitValues; + ShaderVisibility = _ShaderVisibility; + } + + D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE _ParameterType, UINT ShaderRegister, UINT RegisterSpace, + D3D12_SHADER_VISIBILITY _ShaderVisibility) + { + ParameterType = _ParameterType; + Descriptor.ShaderRegister = ShaderRegister; + Descriptor.RegisterSpace = RegisterSpace; + ShaderVisibility = _ShaderVisibility; + } +}; + +//} // namespace dgVoodoo + +#endif // !ID3D12ROOT_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3D12RootObserver.hpp b/dgVoodooAPI/Inc/Addon/ID3D12RootObserver.hpp new file mode 100644 index 0000000..87852f1 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3D12RootObserver.hpp @@ -0,0 +1,82 @@ +// ***************************************************************************** +// File: ID3D12RootObserver.hpp +// +// Description: Callback interface for observing D3D12 Root +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3D12ROOTOBSERVER_HPP +#define ID3D12ROOTOBSERVER_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "ID3D12Root.hpp" + +namespace dgVoodoo { + +// --- ID3D12RootObserver ------------------------------------------------------ + +class ID3D12RootObserver +{ +public: + + struct SwapchainDrawingTarget + { + RECT dstRect; + ID3D12Resource* pDstTexture; + D3D12_CPU_DESCRIPTOR_HANDLE rtvCPUHandle; + UINT dstTextureState; + }; + + + struct PresentBeginContextInput + { + ID3D12Swapchain* pSwapchain; + SwapchainDrawingTarget drawingTarget; + + RECT srcRect; + ID3D12Resource* pSrcTexture; + D3D12_CPU_DESCRIPTOR_HANDLE srvCPUHandle; + UINT srcTextureState; + }; + + + struct PresentBeginContextOutput + { + ID3D12Resource* pOutputTexture; + D3D12_CPU_DESCRIPTOR_HANDLE outputTexSRVCPUHandle; + UINT outputTextureExpectedState; + }; + + + struct PresentEndContextInput + { + ID3D12Swapchain* pSwapchain; + SwapchainDrawingTarget drawingTarget; + }; + + +public: + + // --- Factoring + + virtual bool D3D12RootCreated (HMODULE hD3D12Dll, ID3D12Root* pD3D12Root) = 0; + virtual void D3D12RootReleased (const ID3D12Root* pD3D12Root) = 0; + + virtual bool D3D12BeginUsingAdapter (UInt32 adapterID) = 0; + virtual void D3D12EndUsingAdapter (UInt32 adapterID) = 0; + + virtual void D3D12SwapchainCreated (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) = 0; + virtual void D3D12SwapchainChanged (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) = 0; + virtual void D3D12SwapchainReleased (UInt32 adapterID, ID3D12Swapchain* pSwapchain) = 0; + + virtual bool D3D12SwapchainPresentBegin (UInt32 adapterID, const PresentBeginContextInput& iCtx, PresentBeginContextOutput& oCtx) = 0; + virtual void D3D12SwapchainPresentEnd (UInt32 adapterID, const PresentEndContextInput& iCtx) = 0; +}; + + +} // namespace dgVoodoo + +#endif // !ID3D12ROOTOBSERVER_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3DDevice.hpp b/dgVoodooAPI/Inc/Addon/ID3DDevice.hpp new file mode 100644 index 0000000..894c634 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3DDevice.hpp @@ -0,0 +1,37 @@ +// ***************************************************************************** +// File: ID3DDevice.hpp +// +// Description: Interface for D3DDevice objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3DDEVICE_HPP +#define ID3DDEVICE_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "..\APITypes.h" + +namespace dgVoodoo { + +// --- ID3DDevice -------------------------------------------------------------- + +class ID3DDevice +{ +public: + enum ObjectType + { + OT_Direct3DDevice = 0, + OT_Direct3D8Device, + OT_Direct3D9Device + }; + + virtual ObjectType GetObjectType () const = 0; +}; + + +} // namespace dgVoodoo + +#endif // !ID3DDEVICE_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3DDeviceObserver.hpp b/dgVoodooAPI/Inc/Addon/ID3DDeviceObserver.hpp new file mode 100644 index 0000000..f36c277 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3DDeviceObserver.hpp @@ -0,0 +1,35 @@ +// ***************************************************************************** +// File: ID3DDeviceObserver.hpp +// +// Description: Callback interface for observing D3DDevice objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3DDEVICEOBSERVER_HPP +#define ID3DDEVICEOBSERVER_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "ID3DDevice.hpp" + +namespace dgVoodoo { + +// --- ID3DDeviceObserver ------------------------------------------------------ + +class ID3DDeviceObserver +{ +public: + + // --- Factoring + + virtual bool D3DDeviceObjectCreated (ID3DDevice* pD3DDevice) = 0; + virtual void D3DDeviceObjectReleased (const ID3DDevice* pD3DDevice) = 0; + +}; + + +} // namespace dgVoodoo + +#endif // !ID3DDEVICEOBSERVER_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3DObserver.hpp b/dgVoodooAPI/Inc/Addon/ID3DObserver.hpp new file mode 100644 index 0000000..4e45082 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3DObserver.hpp @@ -0,0 +1,35 @@ +// ***************************************************************************** +// File: ID3DObserver.hpp +// +// Description: Callback interface for observing D3D objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3DOBSERVER_HPP +#define ID3DOBSERVER_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "ID3D.hpp" + +namespace dgVoodoo { + +// --- ID3DObserver ------------------------------------------------------------ + +class ID3DObserver +{ +public: + + // --- Factoring + + virtual bool D3DObjectCreated (ID3D* pD3D) = 0; + virtual void D3DObjectReleased (const ID3D* pD3D) = 0; + +}; + + +} // namespace dgVoodoo + +#endif // !ID3DOBSERVER_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3DResource.hpp b/dgVoodooAPI/Inc/Addon/ID3DResource.hpp new file mode 100644 index 0000000..9a8b234 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3DResource.hpp @@ -0,0 +1,98 @@ +// ***************************************************************************** +// File: ID3DResource.hpp +// +// Description: Interface for D3DResource objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3DRESOURCE_HPP +#define ID3DRESOURCE_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "..\APITypes.h" + +namespace dgVoodoo { + +// --- ID3DResource ------------------------------------------------------------ + +class ID3DResource +{ +public: + enum Type + { + Texture = 0, + CubeTexture, + VolumeTexture + }; + + enum Format + { + // Plain surface and texture formats + P8 = 0, + RGB565, + XRGB555, + ARGB1555, + ARGB4444, + XRGB8888, + ARGB8888, + L8, + A8, + A8L8, + V8U8, + L6V5U5, + L8V8U8, + Q8W8V8U8, + + DXTC1, + DXTC2, + DXTC3, + DXTC4, + DXTC5, + UYVY, + YUY2, + ARGB2101010, + L16, + R16G16, + U16V16, + R16G16B16A16, + R16F, + R16G16F, + R16G16B16A16F, + R32F, + R32G32F, + R32G32B32A32F, + BC4, + BC5, + + // Z-buffer formats + Z16, + Z24, + Z24S8, + Z24X4S4, + Z32, + DFZ16, + DFZ24S8, + INTZ24S8 + }; + + + struct Desc + { + UInt32 width; + UInt32 height; + UInt32 depth; + UInt32 mipMapNum; + Format format; + }; + + virtual Type ARGetType () const = 0; + virtual Desc ARGetDesc () const = 0; +}; + + +} // namespace dgVoodoo + +#endif // !ID3DRESOURCE_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/Addon/ID3DResourceObserver.hpp b/dgVoodooAPI/Inc/Addon/ID3DResourceObserver.hpp new file mode 100644 index 0000000..2b0a318 --- /dev/null +++ b/dgVoodooAPI/Inc/Addon/ID3DResourceObserver.hpp @@ -0,0 +1,44 @@ +// ***************************************************************************** +// File: ID3DResourceObserver.hpp +// +// Description: Callback interface for observing D3D resource objects +// +// Contact person: DG +// +// ***************************************************************************** + +#ifndef ID3DRESOURCEOBSERVER_HPP +#define ID3DRESOURCEOBSERVER_HPP + +// --- Includes ---------------------------------------------------------------- + +#include "..\APITypes.h" +#include "ID3D.hpp" +#include "ID3DResource.hpp" + +namespace dgVoodoo { + + +// --- ID3DObserver ------------------------------------------------------------ + +class ID3DResourceObserver +{ +public: + + // --- Factoring + + virtual bool TextureCreated (ID3D* pD3D, ID3DResource* pTexture) = 0; + virtual bool CubeTextureCreated (ID3D* pD3D, ID3DResource* pTexture) = 0; + virtual bool VolumeTextureCreated (ID3D* pD3D, ID3DResource* pTexture) = 0; + + virtual void TextureReleased (ID3D* pD3D, const ID3DResource* pTexture) = 0; + virtual void CubeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture) = 0; + virtual void VolumeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture) = 0; + + // --- Content manipulation +}; + + +} // namespace dgVoodoo + +#endif // !ID3DRESOURCEOBSERVER_HPP \ No newline at end of file diff --git a/dgVoodooAPI/Inc/dgVoodooConfig.hpp b/dgVoodooAPI/Inc/dgVoodooConfig.hpp index 0c9ac0f..c962a76 100644 --- a/dgVoodooAPI/Inc/dgVoodooConfig.hpp +++ b/dgVoodooAPI/Inc/dgVoodooConfig.hpp @@ -204,6 +204,16 @@ struct ConfigGeneralExt }; + enum SystemHookFlags + { + SHF_None = 0x0, + SHF_GDI = 0x1, + SHF_Cursor = 0x2, + + SHF_All = 0x3 + }; + + UInt32 desktopResWidth; UInt32 desktopResHeight; UInt32 desktopRefRateNumerator; @@ -224,8 +234,8 @@ struct ConfigGeneralExt PresentationModel presentationModel; UInt32 fpsLimitNumerator; UInt32 fpsLimitDenominator; + UInt32 systemHookFlags; bool freeMouse; - bool enableGDIHooking; ConfigGeneralExt (): desktopResWidth (0), @@ -248,8 +258,8 @@ struct ConfigGeneralExt presentationModel (PM_Automatic), fpsLimitNumerator (0), fpsLimitDenominator (0), - freeMouse (false), - enableGDIHooking (false) + systemHookFlags (SHF_None), + freeMouse (false) { } }; @@ -411,7 +421,7 @@ struct ConfigDirectX bool appControlledScreenState; bool disableAltEnter; bool watermark; - bool linearBltStretch; + bool bilinear2DOperations; bool applyPhongShading; bool forceVSync; bool disableMipmapping; @@ -431,7 +441,7 @@ struct ConfigDirectX appControlledScreenState (true), disableAltEnter (true), watermark (true), - linearBltStretch (false), + bilinear2DOperations (false), applyPhongShading (false), forceVSync (false), disableMipmapping (false), diff --git a/dgVoodooAPI/Lib/arm64/dgVoodooAPI.lib b/dgVoodooAPI/Lib/arm64/dgVoodooAPI.lib new file mode 100644 index 0000000..061a822 Binary files /dev/null and b/dgVoodooAPI/Lib/arm64/dgVoodooAPI.lib differ diff --git a/dgVoodooAPI/Lib/arm64/dgVoodooAddon.lib b/dgVoodooAPI/Lib/arm64/dgVoodooAddon.lib new file mode 100644 index 0000000..1b4f172 Binary files /dev/null and b/dgVoodooAPI/Lib/arm64/dgVoodooAddon.lib differ diff --git a/dgVoodooAPI/Lib/arm64ec/dgVoodooAddon.lib b/dgVoodooAPI/Lib/arm64ec/dgVoodooAddon.lib new file mode 100644 index 0000000..70c5915 Binary files /dev/null and b/dgVoodooAPI/Lib/arm64ec/dgVoodooAddon.lib differ diff --git a/dgVoodooAPI/Lib/x64/dgVoodooAPI.lib b/dgVoodooAPI/Lib/x64/dgVoodooAPI.lib new file mode 100644 index 0000000..7c52f48 Binary files /dev/null and b/dgVoodooAPI/Lib/x64/dgVoodooAPI.lib differ diff --git a/dgVoodooAPI/Lib/x64/dgVoodooAddon.lib b/dgVoodooAPI/Lib/x64/dgVoodooAddon.lib new file mode 100644 index 0000000..604a772 Binary files /dev/null and b/dgVoodooAPI/Lib/x64/dgVoodooAddon.lib differ diff --git a/dgVoodooAPI/Lib/dgVoodooAPI.lib b/dgVoodooAPI/Lib/x86/dgVoodooAPI.lib similarity index 74% rename from dgVoodooAPI/Lib/dgVoodooAPI.lib rename to dgVoodooAPI/Lib/x86/dgVoodooAPI.lib index 1f0a38c..cd5408a 100644 Binary files a/dgVoodooAPI/Lib/dgVoodooAPI.lib and b/dgVoodooAPI/Lib/x86/dgVoodooAPI.lib differ diff --git a/dgVoodooAPI/Lib/x86/dgVoodooAddon.lib b/dgVoodooAPI/Lib/x86/dgVoodooAddon.lib new file mode 100644 index 0000000..08e0380 Binary files /dev/null and b/dgVoodooAPI/Lib/x86/dgVoodooAddon.lib differ diff --git a/dgVoodooAPI/SampleApp/SampleApp.sln b/dgVoodooAPI/SampleApp/SampleApp.sln deleted file mode 100644 index fe1213e..0000000 --- a/dgVoodooAPI/SampleApp/SampleApp.sln +++ /dev/null @@ -1,22 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 14 -VisualStudioVersion = 14.0.25420.1 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "SampleApp", "SampleApp.vcxproj", "{CD7EACA5-A639-4264-9F8D-5044F8489A15}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|x86 = Debug|x86 - Release|x86 = Release|x86 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x86.ActiveCfg = Debug|Win32 - {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x86.Build.0 = Debug|Win32 - {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x86.ActiveCfg = Release|Win32 - {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x86.Build.0 = Release|Win32 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection -EndGlobal diff --git a/dgVoodooAPI/SampleApp/SampleApp.cpp b/dgVoodooAPI/Samples/API Library/APILibrary.cpp similarity index 98% rename from dgVoodooAPI/SampleApp/SampleApp.cpp rename to dgVoodooAPI/Samples/API Library/APILibrary.cpp index 95d6041..45f21a4 100644 --- a/dgVoodooAPI/SampleApp/SampleApp.cpp +++ b/dgVoodooAPI/Samples/API Library/APILibrary.cpp @@ -1,7 +1,7 @@ -// SampleApp.cpp : Defines the entry point for the console application. +// APILibrary.cpp : Defines the entry point for the console application. // -#include "IMainFactory.hpp" +#include ".\APIDll\IMainFactory.hpp" #include "IIniParser.hpp" #include "IAPIDataStream.hpp" #include "APIDebugObj.hpp" diff --git a/dgVoodooAPI/SampleApp/SampleApp.vcxproj b/dgVoodooAPI/Samples/API Library/APILibrary.vcxproj similarity index 58% rename from dgVoodooAPI/SampleApp/SampleApp.vcxproj rename to dgVoodooAPI/Samples/API Library/APILibrary.vcxproj index 9d1819c..ef495db 100644 --- a/dgVoodooAPI/SampleApp/SampleApp.vcxproj +++ b/dgVoodooAPI/Samples/API Library/APILibrary.vcxproj @@ -1,171 +1,260 @@ - - - - - Debug - Win32 - - - Release - Win32 - - - Debug - x64 - - - Release - x64 - - - - {CD7EACA5-A639-4264-9F8D-5044F8489A15} - Win32Proj - SampleApp - 10.0.17763.0 - - - - Application - true - v141 - Unicode - - - Application - false - v141 - true - Unicode - - - Application - true - v141 - Unicode - - - Application - false - v141 - true - Unicode - - - - - - - - - - - - - - - - - - - - - true - - - true - - - false - - - false - - - - - - Level3 - Disabled - WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions) - true - $(SolutionDir)\..\Inc\ - - - Console - true - $(SolutionDir)\..\Lib\ - dgVoodooAPI.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies) - - - - - - - Level3 - Disabled - _DEBUG;_CONSOLE;%(PreprocessorDefinitions) - true - - - Console - true - - - - - Level3 - - - MaxSpeed - true - true - WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions) - true - $(SolutionDir)\..\Inc\ - - - Console - true - true - true - $(SolutionDir)\..\Lib\ - dgVoodooAPI.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies) - - - - - Level3 - - - MaxSpeed - true - true - NDEBUG;_CONSOLE;%(PreprocessorDefinitions) - true - - - Console - true - true - true - - - - - - - - - - - - - - - - - - - + + + + + Debug + ARM64 + + + Debug + Win32 + + + Release + ARM64 + + + Release + Win32 + + + Debug + x64 + + + Release + x64 + + + + {CD7EACA5-A639-4264-9F8D-5044F8489A15} + Win32Proj + SampleApp + 10.0 + + + + Application + true + v143 + Unicode + + + Application + false + v143 + true + Unicode + + + Application + true + v143 + Unicode + + + Application + true + v143 + Unicode + + + Application + false + v143 + true + Unicode + + + Application + false + v143 + true + Unicode + + + + + + + + + + + + + + + + + + + + + + + + + + + true + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + true + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + true + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + false + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + false + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + false + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + + + + Level3 + Disabled + WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + $(SolutionDir)\..\Lib\x86\ + dgVoodooAPI.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies) + + + + + + + Level3 + Disabled + _DEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + $(SolutionDir)\..\Lib\x64\ + dgVoodooAPI.lib;$(CoreLibraryDependencies);%(AdditionalDependencies) + + + + + + + Level3 + Disabled + _DEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + $(SolutionDir)\..\Lib\arm64\ + dgVoodooAPI.lib;$(CoreLibraryDependencies);%(AdditionalDependencies) + + + + + Level3 + + + MaxSpeed + true + true + WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + true + true + $(SolutionDir)\..\Lib\x86\ + dgVoodooAPI.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies) + + + + + Level3 + + + MaxSpeed + true + true + NDEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + true + true + $(SolutionDir)\..\Lib\x64\ + dgVoodooAPI.lib;$(CoreLibraryDependencies);%(AdditionalDependencies) + + + + + Level3 + + + MaxSpeed + true + true + NDEBUG;_CONSOLE;%(PreprocessorDefinitions) + true + $(SolutionDir)\..\Inc\ + + + Console + true + true + true + $(SolutionDir)\..\Lib\arm64\ + dgVoodooAPI.lib;$(CoreLibraryDependencies);%(AdditionalDependencies) + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/dgVoodooAPI/Samples/API Library/APILibrary.vcxproj.filters b/dgVoodooAPI/Samples/API Library/APILibrary.vcxproj.filters new file mode 100644 index 0000000..aaf3a10 --- /dev/null +++ b/dgVoodooAPI/Samples/API Library/APILibrary.vcxproj.filters @@ -0,0 +1,45 @@ + + + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + + + {275425d7-3480-433c-b4e7-79331c6f595a} + + + {4a85f66c-422e-48cf-9442-7f86f97911a1} + + + + + Source Files + + + \ No newline at end of file diff --git a/dgVoodooAPI/SampleApp/ReadMe.txt b/dgVoodooAPI/Samples/API Library/ReadMe.txt similarity index 100% rename from dgVoodooAPI/SampleApp/ReadMe.txt rename to dgVoodooAPI/Samples/API Library/ReadMe.txt diff --git a/dgVoodooAPI/SampleApp/TestFiles/INIPropertySet.ini b/dgVoodooAPI/Samples/API Library/TestFiles/INIPropertySet.ini similarity index 77% rename from dgVoodooAPI/SampleApp/TestFiles/INIPropertySet.ini rename to dgVoodooAPI/Samples/API Library/TestFiles/INIPropertySet.ini index 8741c5b..6658b34 100644 --- a/dgVoodooAPI/SampleApp/TestFiles/INIPropertySet.ini +++ b/dgVoodooAPI/Samples/API Library/TestFiles/INIPropertySet.ini @@ -1,10 +1,10 @@ -Color1 = BLUE - -[Geometry] -Shapes1 = rectangle, triangle -Shapes2 = "rotated rectangle" circle -Shapes3 = - -[Topology] [] - +Color1 = BLUE + +[Geometry] +Shapes1 = rectangle, triangle +Shapes2 = "rotated rectangle" circle +Shapes3 = + +[Topology] [] + Color2 = red R:255 G:0 B:0 \ No newline at end of file diff --git a/dgVoodooAPI/SampleApp/TestFiles/TestConfig.conf b/dgVoodooAPI/Samples/API Library/TestFiles/TestConfig.conf similarity index 100% rename from dgVoodooAPI/SampleApp/TestFiles/TestConfig.conf rename to dgVoodooAPI/Samples/API Library/TestFiles/TestConfig.conf diff --git a/dgVoodooAPI/Samples/Bin/ARM64/Release/APILibrary.exe b/dgVoodooAPI/Samples/Bin/ARM64/Release/APILibrary.exe new file mode 100644 index 0000000..dc464cb Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/ARM64/Release/APILibrary.exe differ diff --git a/dgVoodooAPI/Samples/Bin/ARM64/Release/SampleAddon.dll b/dgVoodooAPI/Samples/Bin/ARM64/Release/SampleAddon.dll new file mode 100644 index 0000000..8f9f0a3 Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/ARM64/Release/SampleAddon.dll differ diff --git a/dgVoodooAPI/Samples/Bin/ARM64EC/Release/SampleAddon.dll b/dgVoodooAPI/Samples/Bin/ARM64EC/Release/SampleAddon.dll new file mode 100644 index 0000000..dc53c22 Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/ARM64EC/Release/SampleAddon.dll differ diff --git a/dgVoodooAPI/Samples/Bin/Win32/Release/APILibrary.exe b/dgVoodooAPI/Samples/Bin/Win32/Release/APILibrary.exe new file mode 100644 index 0000000..05eca8e Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/Win32/Release/APILibrary.exe differ diff --git a/dgVoodooAPI/Samples/Bin/Win32/Release/SampleAddon.dll b/dgVoodooAPI/Samples/Bin/Win32/Release/SampleAddon.dll new file mode 100644 index 0000000..003c89a Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/Win32/Release/SampleAddon.dll differ diff --git a/dgVoodooAPI/Samples/Bin/x64/Release/APILibrary.exe b/dgVoodooAPI/Samples/Bin/x64/Release/APILibrary.exe new file mode 100644 index 0000000..6279849 Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/x64/Release/APILibrary.exe differ diff --git a/dgVoodooAPI/Samples/Bin/x64/Release/SampleAddon.dll b/dgVoodooAPI/Samples/Bin/x64/Release/SampleAddon.dll new file mode 100644 index 0000000..e29ed48 Binary files /dev/null and b/dgVoodooAPI/Samples/Bin/x64/Release/SampleAddon.dll differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.cpp b/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.cpp new file mode 100644 index 0000000..54a761b --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.cpp @@ -0,0 +1,131 @@ +// ***************************************************************************** +// File: AddonMain.cpp +// +// Description: Main host object for addon implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "AddonMain.hpp" + +// --- Namespaces -------------------------------------------------------------- + +using namespace dgVoodoo; + +// --- AddonMain --------------------------------------------------------------- + +AddonMain::AddonMain (HINSTANCE hDll, IAddonMainCallback* pAddonMainCB): + APIDebugObj (APIDebugObj::EnableInfo, APIDebugObj::EnableWarning, APIDebugObj::EnableError, + "[dgVoodoo Sample Addon] ", 0, NULL), + hDll (hDll), + pAddonMainCB (pAddonMainCB), + pINIParser (NULL), + texturer (*this), + presenter (*this) +{ +} + + +bool AddonMain::ILoadAndValidateINIFile () +{ + bool valid = true; + + if (pINIParser->Parse ("SampleAddon.ini", dgVoodoo::IIniParser::LowerCase)) { + + for (UInt32 i = 0; valid && i < pINIParser->GetNumberOfSections (); i++) { + const char* pName = pINIParser->GetSectionName (i); + + if (pName == NULL) { + + if (pINIParser->GetNumberOfProperties (i) != 0) { + valid = false; + } + + } else if (strcmp (pName, "presenter") == 0) { + + presenter.SetINISectionIdx (i); + + } else if (strcmp (pName, "texturer") == 0) { + } else { + valid = false; + } + } + } + + return valid; +} + + +AddonMain::~AddonMain () +{ + Exit (); +} + + +bool AddonMain::Init () +{ + pINIParser = pAddonMainCB->CreateIniParser (); + + if (pINIParser != NULL) { + + if (ILoadAndValidateINIFile ()) { + + if (texturer.Init ()) { + + if (presenter.Init ()) { + + UInt32 version = pAddonMainCB->GetVersion (); + + pAddonMainCB->IssueInfo (this, "Sample addon init succeeded for dgVoodoo version %d.%d%d\n", + (version >> 8) & 0xF, (version >> 4) & 0xF, (version >> 0) & 0xF); + + return true; + } + texturer.Exit (); + } + } + pINIParser->Release (); + pINIParser = NULL; + } + + return false; +} + + +void AddonMain::Exit () +{ + if (pINIParser != NULL) { + + presenter.Exit (); + texturer.Exit (); + pINIParser->Release (); + } + pAddonMainCB->IssueInfo (this, "Sample addon exited.\n"); +} + + +// --- Functions --------------------------------------------------------------- + +AddonMain* CreateAddonMain (HINSTANCE hDll, dgVoodoo::IAddonMainCallback* pAddonMainCB) +{ + AddonMain* pAddonMain = new AddonMain (hDll, pAddonMainCB); + if (pAddonMain != NULL) { + + if (pAddonMain->Init ()) { + return pAddonMain; + } + + delete pAddonMain; + } + + return NULL; +} + + +void DeleteAddonMain (AddonMain* pAddonMain) +{ + delete pAddonMain; +} \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.hpp b/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.hpp new file mode 100644 index 0000000..1dc1ae1 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/AddonMain.hpp @@ -0,0 +1,51 @@ +// ***************************************************************************** +// File: AddonMain.hpp +// +// Description: Main host object for addon implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "Public\IIniParser.hpp" +#include "Public\APIDebugObj.hpp" + +#include "Public\Addon\AddonDefs.hpp" +#include "Public\Addon\IAddonMainCallback.hpp" + +#include "Presenter.hpp" +#include "Texturer.hpp" + +// --- Namespaces -------------------------------------------------------------- + +using namespace dgVoodoo; + +// --- Predeclarations --------------------------------------------------------- + +// --- AddonMain --------------------------------------------------------------- + +class AddonMain: public APIDebugObj +{ +friend class Texturer; +friend class Presenter; + +protected: + HINSTANCE hDll; + IAddonMainCallback* pAddonMainCB; + IIniParser* pINIParser; + + Texturer texturer; + Presenter presenter; + +protected: + bool ILoadAndValidateINIFile (); + +public: + AddonMain (HINSTANCE hDll, IAddonMainCallback* pAddonMainCB); + ~AddonMain (); + + bool Init (); + void Exit (); +}; \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Credits.txt b/dgVoodooAPI/Samples/D3D12 Addon/Credits.txt new file mode 100644 index 0000000..0e150e5 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Credits.txt @@ -0,0 +1,3 @@ +PNG file: + +https://www.pngwing.com/en/free-png-bbull \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/DirtyGlass.png b/dgVoodooAPI/Samples/D3D12 Addon/DirtyGlass.png new file mode 100644 index 0000000..9d5e930 Binary files /dev/null and b/dgVoodooAPI/Samples/D3D12 Addon/DirtyGlass.png differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.cpp b/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.cpp new file mode 100644 index 0000000..c1abb7f --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.cpp @@ -0,0 +1,86 @@ +// ***************************************************************************** +// File: ImageLoader.cpp +// +// Description: General image loader functionality for dgVoodooAddon +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "Wincodec.h" +#include "ImageLoader.hpp" + +// --- Namespaces -------------------------------------------------------------- + +// --- Predeclarations --------------------------------------------------------- + +class AddonMain; + +// --- Presenter --------------------------------------------------------------- + +bool ImageLoader::LoadImageA (LPCSTR pFileName, ImageData& outImageData) +{ + WCHAR wFilename[MAX_PATH]; + + if (MultiByteToWideChar (CP_ACP, 0, pFileName, -1, wFilename, MAX_PATH) > 0) { + + return LoadImageW (wFilename, outImageData); + } + return false; +} + + +bool ImageLoader::LoadImageW (LPCWSTR pFileName, ImageData& outImageData) +{ + memset (&outImageData, 0, sizeof (outImageData)); + + CoInitialize (NULL); + + IWICImagingFactory* pFactory = NULL; + HRESULT hr = CoCreateInstance (CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARGS (&pFactory)); + if (SUCCEEDED (hr)) { + + IWICBitmapDecoder* pDecoder = NULL; + hr = pFactory->CreateDecoderFromFilename (pFileName, NULL, GENERIC_READ, WICDecodeMetadataCacheOnDemand, &pDecoder); + if (SUCCEEDED (hr)) { + + IWICBitmapFrameDecode* pFrameDecode = NULL; + hr = pDecoder->GetFrame (0, &pFrameDecode); + if (SUCCEEDED (hr)) { + + WICPixelFormatGUID pfGUID; + hr = pFrameDecode->GetPixelFormat (&pfGUID); + if (SUCCEEDED (hr) && pfGUID == GUID_WICPixelFormat32bppBGRA) { + + UINT width = 0; + UINT height = 0; + hr = pFrameDecode->GetSize (&width, &height); + if (SUCCEEDED (hr)) { + + const UINT pixelBPP = 4; + BYTE* pBitmap = new BYTE[width * height * pixelBPP]; + if (pBitmap != NULL) { + hr = pFrameDecode->CopyPixels (NULL, width * pixelBPP, width * height * pixelBPP, pBitmap); + if (SUCCEEDED (hr)) { + outImageData.pBitmap = pBitmap; + outImageData.width = width; + outImageData.height = height; + outImageData.stride = width * pixelBPP; + outImageData.pixelBPP = pixelBPP; + } else { + delete[] pBitmap; + } + } + } + } + pFrameDecode->Release (); + } + pDecoder->Release (); + } + pFactory->Release (); + } + + return outImageData.pBitmap != NULL; +} \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.hpp b/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.hpp new file mode 100644 index 0000000..6ce77fa --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/ImageLoader.hpp @@ -0,0 +1,41 @@ +// ***************************************************************************** +// File: ImageLoader.hpp +// +// Description: General image loader functionality for dgVoodooAddon +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "Wincodec.h" + +// --- Namespaces -------------------------------------------------------------- + +//using namespace dgVoodoo; + +// --- Predeclarations --------------------------------------------------------- + +class AddonMain; + +// --- ImageLoader ------------------------------------------------------------- + +class ImageLoader +{ +public: + struct ImageData + { + BYTE* pBitmap; + UINT width; + UINT height; + UINT stride; + UINT pixelBPP; + }; + +public: + + static bool LoadImageA (LPCSTR pFileName, ImageData& outImageData); + static bool LoadImageW (LPCWSTR pFileName, ImageData& outImageData); + +}; \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Main.cpp b/dgVoodooAPI/Samples/D3D12 Addon/Main.cpp new file mode 100644 index 0000000..a547541 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Main.cpp @@ -0,0 +1,81 @@ +// ***************************************************************************** +// File: Main.cpp +// +// Description: Main file of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include +#include + +#include "Public\Addon\AddonDefs.hpp" +#include "Public\Addon\IAddonMainCallback.hpp" + +// --- Defines ----------------------------------------------------------------- + +// --- Namespaces -------------------------------------------------------------- + +using namespace dgVoodoo; + +// --- Predeclarations --------------------------------------------------------- + +class AddonMain; + +// --- Externs ----------------------------------------------------------------- + +extern AddonMain* CreateAddonMain (HINSTANCE hDll, dgVoodoo::IAddonMainCallback* pAddonMainCB); +extern void DeleteAddonMain (AddonMain* pAddonMain); + +// --- Variables --------------------------------------------------------------- + +HINSTANCE hDll = NULL; +AddonMain* pAddonMain = NULL; + +// --- Dll Main ---------------------------------------------------------------- + +BOOL WINAPI DllMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) +{ + switch (fdwReason) { + case DLL_PROCESS_ATTACH: + + hDll = hinstDLL; + break; + + case DLL_PROCESS_DETACH: + break; + } + return TRUE; +} + + +int APIENTRY _tWinMain (HINSTANCE hInstance, + HINSTANCE hPrevInstance, + LPTSTR lpCmdLine, + int nCmdShow) +{ + return 1; +} + +// --- Addon functions --------------------------------------------------------- + +extern "C" { + + bool API_EXPORT AddOnInit (dgVoodoo::IAddonMainCallback* pAddonMainCB) + { + pAddonMain = CreateAddonMain (hDll, pAddonMainCB); + + return pAddonMain != NULL; + } + + + void API_EXPORT AddOnExit () + { + DeleteAddonMain (pAddonMain); + pAddonMain = NULL; + } + +} // extern "C" \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Presenter.cpp b/dgVoodooAPI/Samples/D3D12 Addon/Presenter.cpp new file mode 100644 index 0000000..e92b33c --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Presenter.cpp @@ -0,0 +1,774 @@ +// ***************************************************************************** +// File: Presenter.cpp +// +// Description: D3D12 presentation hook implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "AddonMain.hpp" +#include "Resource.h" + +// --- Defines ----------------------------------------------------------------- + +#define DEFAULT_GLASSIMAGEPATH "GlassImage.png" +#define DEFAULT_SEPIACOLOR 0x40F1AE72 + +#define VBUFFER_VERTEXCNT 256 + +// --- Presenter --------------------------------------------------------------- + +const D3D12_BLEND_DESC Presenter::defaultBlendDesc = +{ + FALSE, FALSE, + // RT0 + { FALSE, FALSE, D3D12_BLEND_ONE, D3D12_BLEND_ZERO, D3D12_BLEND_OP_ADD, D3D12_BLEND_ONE, D3D12_BLEND_ZERO, D3D12_BLEND_OP_ADD, D3D12_LOGIC_OP_CLEAR, 0xF } +}; + + +const D3D12_RASTERIZER_DESC Presenter::defaultRasterizerDesc = +{ + D3D12_FILL_MODE_SOLID, D3D12_CULL_MODE_NONE, FALSE, 0, 0.0f, 0.0f, TRUE, FALSE, FALSE, 0, D3D12_CONSERVATIVE_RASTERIZATION_MODE_OFF +}; + + +const D3D12_DEPTH_STENCIL_DESC Presenter::defaultDepthStencilDesc = +{ + FALSE, D3D12_DEPTH_WRITE_MASK_ALL, D3D12_COMPARISON_FUNC_ALWAYS, FALSE, 0xFF, 0xFF, + { D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP}, + { D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP, D3D12_STENCIL_OP_KEEP} +}; + + +const D3D12_INPUT_ELEMENT_DESC Presenter::deaultInputLayout[] = +{ + {"POSITION", 0, DXGI_FORMAT_R32G32_FLOAT, 0, D3D12_APPEND_ALIGNED_ELEMENT, D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0}, + {"TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, D3D12_APPEND_ALIGNED_ELEMENT, D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, 0} +}; + + +Presenter::Presenter (AddonMain& main): + main (main), + pD3D12Root (NULL), + pVSQuad (NULL), + pPSGlass (NULL), + sectionIdx (0), + pGlassFilePath (NULL), + sepiaColor (0x0) +{ + memset (&glassImage, 0, sizeof (glassImage)); + memset (&rootPSConstBuffer, 0, sizeof (rootPSConstBuffer)); +} + + +Presenter::~Presenter () +{ + Exit (); +} + + +Presenter::AdapterData::AdapterData (): + pDevice (NULL), + pRootSignature (NULL), + pSRVDescAllocator (NULL), + pGlassTexture (NULL), + hGlassTexSRV (-1), + glassTexState (D3D12_RESOURCE_STATE_COMMON), + pPSO (NULL), + pVertexBuffer (NULL), + vbPos (0) +{ + memset (&graphicsPipeline, 0, sizeof (graphicsPipeline)); +} + + +void Presenter::ITakeLock () +{ + EnterCriticalSection (&lock); +} + + +void Presenter::IReleaseLock () +{ + LeaveCriticalSection (&lock); +} + + +// D3D12 observer functions can get called simultaneously with different adapterID's in extreme cases +// We don't want to read/write the main 'adapters' container concurrently by any chance so guard it by a lock + +Presenter::AdapterData& Presenter::GetAdapterRef (UInt32 adapterID) +{ + ITakeLock (); + + AdapterData& adapterData = adapters[adapterID]; + + IReleaseLock (); + + return adapterData; +} + + +void Presenter::EraseAdapter (UInt32 adapterID) +{ + ITakeLock (); + + adapters.erase (adapterID); + + IReleaseLock (); +} + + +bool Presenter::IParsePresenterINISection () +{ + pGlassFilePath = DEFAULT_GLASSIMAGEPATH; + sepiaColor = DEFAULT_SEPIACOLOR; + + bool succeeded = true; + + for (UInt32 i = 0; succeeded && i < main.pINIParser->GetNumberOfProperties (sectionIdx); i++) { + const char* pName = main.pINIParser->GetPropertyName (sectionIdx, i); + + if (strcmp (pName, "glassimage") == 0) { + if (main.pINIParser->GetNumberOfSubProperties (sectionIdx, i) == 0) { + if (main.pINIParser->GetNumberOfPropertyValues (sectionIdx, i) == 1) { + + pGlassFilePath = main.pINIParser->GetPropertyValueAsString (sectionIdx, i, 0); + + } else { + // empty value + succeeded = (main.pINIParser->GetNumberOfPropertyValues (sectionIdx, i) == 0); + } + } else { + succeeded = false; + } + + } else if (strcmp (pName, "sepiacolor") == 0) { + + if (main.pINIParser->GetNumberOfSubProperties (sectionIdx, i) == 0) { + if (main.pINIParser->GetNumberOfPropertyValues (sectionIdx, i) == 1) { + + Int32 value = 0; + succeeded = main.pINIParser->GetPropertyValueAsInt (sectionIdx, i, 0, value); + sepiaColor = value; + + } else { + // empty value + succeeded = (main.pINIParser->GetNumberOfPropertyValues (sectionIdx, i) == 0); + } + } else { + succeeded = false; + } + + } else { + succeeded = false; + } + } + + return succeeded; +} + + +bool Presenter::ILoadShaders () +{ + UInt32 size = main.pAddonMainCB->RSSizeOfResource (main.hDll, MAKEINTRESOURCE (IDR_VSQUAD_5_1), L"RT_CUSTOM"); + const BYTE* pData = main.pAddonMainCB->RSLoadResource (main.hDll, MAKEINTRESOURCE (IDR_VSQUAD_5_1), L"RT_CUSTOM"); + if (pData != NULL) { + + pVSQuad = pD3D12Root->CreateD3DBlob (size, pData); + delete[] pData; + if (pVSQuad != NULL) { + + size = main.pAddonMainCB->RSSizeOfResource (main.hDll, MAKEINTRESOURCE (IDR_PSGLASS_5_1), L"RT_CUSTOM"); + pData = main.pAddonMainCB->RSLoadResource (main.hDll, MAKEINTRESOURCE (IDR_PSGLASS_5_1), L"RT_CUSTOM"); + + if (pData != NULL) { + pPSGlass = pD3D12Root->CreateD3DBlob (size, pData); + delete[] pData; + + if (pPSGlass != NULL) { + + return true; + } + } + + pVSQuad->Release (); + } + } + return false; +} + + +bool Presenter::ICreateRootSignature (AdapterData& adapter) +{ + // SRV array descriptor - just for demonstration purposes: SRV range[3..4] in space 1 + const static D3D12_DESCRIPTOR_RANGE textureView = + { + D3D12_DESCRIPTOR_RANGE_TYPE_SRV, + 2, 3, 1, 0 + }; + + const static D3D12_ROOT_PARAMETER rootEntries[] = + { + // SRV table address for texture views + D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE, 1, &textureView, D3D12_SHADER_VISIBILITY_PIXEL), + + // Inline constant buffer with 4 32bit entries (RootPSConstBuffer): CBV range[0..0], space 2 + D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE_32BIT_CONSTANTS, 0, 2, 4, D3D12_SHADER_VISIBILITY_PIXEL) + + //D3D12RSPARAMETER (D3D12_ROOT_PARAMETER_TYPE_CBV, 2U, 0U, (D3D12_SHADER_VISIBILITY) (D3D12_SHADER_VISIBILITY_ALL)), + }; + + // Static samplers + const static D3D12_STATIC_SAMPLER_DESC staticSamplers[] = + { + // point sampler (s0) + { + D3D12_FILTER_MIN_MAG_MIP_POINT, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, + 0.0f, 1, D3D12_COMPARISON_FUNC_ALWAYS, D3D12_STATIC_BORDER_COLOR_TRANSPARENT_BLACK, 0, D3D12_FLOAT32_MAX, 0, 0, + D3D12_SHADER_VISIBILITY_PIXEL + }, + + // bilinear sampler (s1) + { + D3D12_FILTER_MIN_MAG_MIP_LINEAR, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, D3D12_TEXTURE_ADDRESS_MODE_CLAMP, + 0.0f, 1, D3D12_COMPARISON_FUNC_ALWAYS, D3D12_STATIC_BORDER_COLOR_TRANSPARENT_BLACK, 0, D3D12_FLOAT32_MAX, 1, 0, + D3D12_SHADER_VISIBILITY_PIXEL + }, + }; + + const static D3D12_ROOT_SIGNATURE_DESC rootSignature = + { + 2, rootEntries, 2, staticSamplers, + D3D12_ROOT_SIGNATURE_FLAG_ALLOW_INPUT_ASSEMBLER_INPUT_LAYOUT | + D3D12_ROOT_SIGNATURE_FLAG_DENY_HULL_SHADER_ROOT_ACCESS | + D3D12_ROOT_SIGNATURE_FLAG_DENY_DOMAIN_SHADER_ROOT_ACCESS | + D3D12_ROOT_SIGNATURE_FLAG_DENY_GEOMETRY_SHADER_ROOT_ACCESS + }; + + adapter.pRootSignature = pD3D12Root->SerializeAndCreateRootSignature (adapter.adapterID, D3D_ROOT_SIGNATURE_VERSION_1, &rootSignature, NULL); + + return adapter.pRootSignature != NULL; +} + + +void Presenter::IReleaseRootSignature (AdapterData& adapter) +{ + // Let's tell dgVoodoo's caching infrastructure that we are about to release our + // root signature object so remove all internal entries associated with it + pD3D12Root->GPLRootSignatureReleased (adapter.adapterID, adapter.pRootSignature); + + adapter.pRootSignature->Release(); + adapter.pRootSignature = NULL; +} + + +bool Presenter::ICreateGlassTexture (AdapterData& adapter) +{ + // Create a very basic 2D texture resource (1 mipmap level, format BGRA8888) in the default type heap (video memory) + // with allocated physical video memory pages (committed resource) + D3D12_HEAP_PROPERTIES heapProp = + { + D3D12_HEAP_TYPE_DEFAULT, D3D12_CPU_PAGE_PROPERTY_UNKNOWN, D3D12_MEMORY_POOL_UNKNOWN, 0x0, 0x0 + }; + D3D12_RESOURCE_DESC desc = + { + D3D12_RESOURCE_DIMENSION_TEXTURE2D, D3D12_DEFAULT_RESOURCE_PLACEMENT_ALIGNMENT, glassImage.width, glassImage.height, 1, 1, + DXGI_FORMAT_B8G8R8A8_TYPELESS, { 1, 0 }, D3D12_TEXTURE_LAYOUT_UNKNOWN, D3D12_RESOURCE_FLAG_NONE + }; + + HRESULT hr = adapter.pDevice->CreateCommittedResource (&heapProp, D3D12_HEAP_FLAG_NONE, &desc, D3D12_RESOURCE_STATE_COMMON, + NULL, __uuidof(ID3D12Resource), (void**) &adapter.pGlassTexture); + if (SUCCEEDED (hr)) { + + // Let's allocate a shader resource view (SRV) entry for it in a CPU-only visible descriptor array through an allocator + adapter.hGlassTexSRV = adapter.pSRVDescAllocator->AllocDescriptorGroup (1); + if (adapter.hGlassTexSRV != -1) { + + ID3D12GraphicsCommandListAuto* pCmdListAuto = pD3D12Root->GetCopyCommandListAuto (adapter.adapterID); + ID3D12GraphicsCommandList* pCmdList = pCmdListAuto->GetCommandListInterface (); + + // Lock the command list for flush to make sure all the commands below will be written into it as a continuous block + pCmdListAuto->AFlushLock (); + + // A helper method to upload data into a texture subresource - this provides basically the same functionality as UpdateSubResource in D3D11 + // Give it the destination resource, the dst box, the source data user ptr, src memory layout and a memory page allocator and let it generate + // the proper commands into the cmd list; this is an upload operation so use the "upload" page allocator + D3D12_BOX dstBox = { 0, 0, 0, glassImage.width, glassImage.height, 1 }; + bool succeeded = pCmdListAuto->HIUpdateSubTexture (adapter.pGlassTexture, 0, pD3D12Root->GetHeapPageAllocator (adapter.adapterID, ID3D12Root::DA_UploadBufferPageHeapAllocator), + dstBox, glassImage.pBitmap, glassImage.stride, glassImage.stride * glassImage.height); + + if (succeeded) { + // The upload method leaves our texture in copy-dest state so let's transition it back to common state for + // later usage in the graphics pipeline + adapter.glassTexState = D3D12_RESOURCE_STATE_COMMON; + D3D12_RESOURCE_BARRIER barrier = { D3D12_RESOURCE_BARRIER_TYPE_TRANSITION, D3D12_RESOURCE_BARRIER_FLAG_NONE }; + barrier.Transition.pResource = adapter.pGlassTexture; + barrier.Transition.Subresource = 0; + barrier.Transition.StateBefore = D3D12_RESOURCE_STATE_COPY_DEST; + barrier.Transition.StateAfter = D3D12_RESOURCE_STATE_COMMON; + pCmdList->ResourceBarrier (1, &barrier); + } + + // Unlock the command list for flush and force a flush operation if the uploader method was successful (the GPU begins to work here) + pCmdListAuto->AFlushUnlock (succeeded); + + if (succeeded) { + + // Fill our SRV entry with a view describing a 2D texture with unorm BGRA8888 format, unswizzled components and all mipmap levels addressable + // This entry will be copied into a GPU-visible descriptor entry during generating the actual rendering commands + D3D12_SHADER_RESOURCE_VIEW_DESC srvDesc = + { + DXGI_FORMAT_B8G8R8A8_UNORM, D3D12_SRV_DIMENSION_TEXTURE2D, D3D12_DEFAULT_SHADER_4_COMPONENT_MAPPING + }; + srvDesc.Texture2D.MipLevels = -1; + srvDesc.Texture2D.MostDetailedMip = 0; + srvDesc.Texture2D.PlaneSlice = 0; + srvDesc.Texture2D.ResourceMinLODClamp = 0.0f; + adapter.pDevice->CreateShaderResourceView (adapter.pGlassTexture, &srvDesc, adapter.pSRVDescAllocator->GetCPUDescHandle (adapter.hGlassTexSRV)); + + return true; + } + // Release the SRV entry + adapter.pSRVDescAllocator->DeallocDescriptorGroup (adapter.hGlassTexSRV, 1); + adapter.hGlassTexSRV = 0; + } + + // Release the texture - no synchronization notifications are needed here because actually nothing happened with it + adapter.pGlassTexture->Release (); + adapter.pGlassTexture = NULL; + } + + return false; +} + + +void Presenter::IReleaseGlassTexture (AdapterData& adapter) +{ + // Let's tell dgVoodoo's object/resource tracking system that we are about to + // release the glass texture so remove it from their entries and wait for GPU completion if needed + pD3D12Root->RTResourceDestroyed (adapter.pGlassTexture, true); + + adapter.pSRVDescAllocator->DeallocDescriptorGroup (adapter.hGlassTexSRV, 1); + adapter.pGlassTexture->Release (); + adapter.pGlassTexture = NULL; +} + + +void Presenter::ICleanUpAdapter (AdapterData& adapter) +{ + // Make sure to clear our "ownership" of the auto command lists + { + ID3D12GraphicsCommandListAuto* pCmdListAuto = pD3D12Root->GetCopyCommandListAuto (adapter.adapterID); + if (pCmdListAuto->IsCurrentId (this)) { + pCmdListAuto->ChangeId (NULL); + } + } + { + ID3D12GraphicsCommandListAuto* pCmdListAuto = pD3D12Root->GetGraphicsCommandListAuto (adapter.adapterID); + if (pCmdListAuto->IsCurrentId (this)) { + pCmdListAuto->ChangeId (NULL); + } + } + + IReleaseRootSignature (adapter); + IReleaseGlassTexture (adapter); + + adapter.pVertexBuffer->Release (); +} + + +void Presenter::IAddTransitionBarrier (ID3D12Resource* pResource, UINT stateBefore, UINT stateAfter, D3D12_RESOURCE_BARRIER* pBarriers, UInt32 numBarriers) +{ + // Helper method to store a simple transition barrier for the 0th subresource of the incoming resource + + pBarriers[numBarriers].Type = D3D12_RESOURCE_BARRIER_TYPE_TRANSITION; + pBarriers[numBarriers].Flags = D3D12_RESOURCE_BARRIER_FLAG_NONE; + + pBarriers[numBarriers].Transition.pResource = pResource; + pBarriers[numBarriers].Transition.Subresource = 0; + pBarriers[numBarriers].Transition.StateBefore = (D3D12_RESOURCE_STATES) stateBefore; + pBarriers[numBarriers].Transition.StateAfter = (D3D12_RESOURCE_STATES) stateAfter; +} + + +// --- ID3D12RootObserver callbacks + +bool Presenter::D3D12RootCreated (HMODULE /*hD3D12Dll*/, ID3D12Root* _pD3D12Root) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D12 root object (%p) is created.\n", _pD3D12Root); + + if (ImageLoader::LoadImageA (pGlassFilePath, glassImage)) { + + pD3D12Root = _pD3D12Root; + + if (ILoadShaders ()) { + + rootPSConstBuffer.sepiaColorR = ((sepiaColor >> 16) & 0xFF) / 255.0f; + rootPSConstBuffer.sepiaColorG = ((sepiaColor >> 8) & 0xFF) / 255.0f; + rootPSConstBuffer.sepiaColorB = ((sepiaColor >> 0) & 0xFF) / 255.0f; + rootPSConstBuffer.colorIntensity = ((sepiaColor >> 24) & 0xFF) / 255.0f; + + return true; + } + + delete[] glassImage.pBitmap; + memset (&glassImage, 0, sizeof (glassImage)); + + pD3D12Root = NULL; + } + + return false; +} + + +void Presenter::D3D12RootReleased (const ID3D12Root* _pD3D12Root) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D12 root object (%p) is released.\n", _pD3D12Root); + + delete[] glassImage.pBitmap; + memset (&glassImage, 0, sizeof (glassImage)); + + pD3D12Root = NULL; +} + + +bool Presenter::D3D12BeginUsingAdapter (UInt32 adapterID) +{ + // In extreme cases D3D12 observer methods can get called concurrently with different adapter ID's + // Make sure that we won't modify concurrently the main 'adapters' container by any chance + ITakeLock (); + + AdapterData data; + adapters.insert (std::make_pair (adapterID, data)); + + IReleaseLock (); + + main.pAddonMainCB->IssueInfo (&main, "A new D3D12 adapter (%d) and its objects are initialized on root object (%p). Using ID3D12Device (%p)\n", adapterID, pD3D12Root, data.pDevice); + + AdapterData& adapter = adapters[adapterID]; + adapter.adapterID = adapterID; + adapter.pDevice = pD3D12Root->GetDevice (adapterID); + + if (ICreateRootSignature (adapter)) { + + adapter.pSRVDescAllocator = pD3D12Root->GetCBV_SRV_UAV_DescAllocator (adapterID); + + if (ICreateGlassTexture (adapter)) { + + adapter.vbPos = 0; + adapter.pVertexBuffer = pD3D12Root->CreateDynamicBuffer (adapterID, VBUFFER_VERTEXCNT * sizeof (Vertex), ID3D12Root::DA_VertexBufferPageHeapAllocator); + if (adapter.pVertexBuffer != NULL) { + + adapter.graphicsPipeline.pRootSignature = adapter.pRootSignature; + adapter.graphicsPipeline.pVS = pVSQuad; + adapter.graphicsPipeline.pPS = pPSGlass; + adapter.graphicsPipeline.pBlendState = pD3D12Root->PLCacheGetBlend4Desc (adapterID, defaultBlendDesc); + adapter.graphicsPipeline.SampleMask = 0xFFFFFFFF; + adapter.graphicsPipeline.pRasterizerState = pD3D12Root->PLCacheGetRasterizerDesc (adapterID, defaultRasterizerDesc); + adapter.graphicsPipeline.pDepthStencilState = pD3D12Root->PLCacheGetDepthStencilDesc (adapterID, defaultDepthStencilDesc); + adapter.graphicsPipeline.pInputLayout = pD3D12Root->PLCacheGetInputLayoutDesc (adapterID, 2, deaultInputLayout); + adapter.graphicsPipeline.IBStripCutValue = D3D12_INDEX_BUFFER_STRIP_CUT_VALUE_DISABLED; + adapter.graphicsPipeline.PrimitiveTopologyType = D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE; + adapter.graphicsPipeline.NumRenderTargets = 1; + adapter.graphicsPipeline.DSVFormat = DXGI_FORMAT_UNKNOWN; + adapter.graphicsPipeline.RTVFormats[0] = DXGI_FORMAT_UNKNOWN; + adapter.graphicsPipeline.SampleDesc = { 1, 0 }; + adapter.graphicsPipeline.NodeMask = 0; + adapter.graphicsPipeline.Flags = D3D12_PIPELINE_STATE_FLAG_NONE; + + return true; + } + IReleaseGlassTexture (adapter); + } + IReleaseRootSignature (adapter); + } + + EraseAdapter (adapterID); + + return false; +} + + +void Presenter::D3D12EndUsingAdapter (UInt32 adapterID) +{ + ICleanUpAdapter (GetAdapterRef (adapterID)); + + EraseAdapter (adapterID); + + main.pAddonMainCB->IssueInfo (&main, "D3D12 adapter (%d) and its objects are released on root object (%p).\n", adapterID, pD3D12Root); +} + + +void Presenter::D3D12SwapchainCreated (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) +{ + // Just put it into our entries and don't do anything else + + AdapterData& adapter = GetAdapterRef (adapterID); + + SwapchainEntry entry = { pSwapchain, swapchainData }; + adapter.swapchains.insert (std::make_pair (pSwapchain, entry)); +} + + +void Presenter::D3D12SwapchainChanged (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) +{ + // Just update the data in our entries and do nothing more + + AdapterData& adapter = GetAdapterRef (adapterID); + + SwapchainEntry entry = { pSwapchain, swapchainData }; + adapter.swapchains[pSwapchain] = entry; +} + + +void Presenter::D3D12SwapchainReleased (UInt32 adapterID, ID3D12Swapchain* pSwapchain) +{ + // Just remove it from our entries + + AdapterData& adapter = GetAdapterRef (adapterID); + + adapter.swapchains.erase (pSwapchain); +} + + +bool Presenter::D3D12SwapchainPresentBegin (UInt32 adapterID, const PresentBeginContextInput& iCtx, PresentBeginContextOutput& oCtx) +{ + bool succeeded = false; + + AdapterData& adapter = GetAdapterRef (adapterID); + + // Get a render target - we don't do up/downscaling in this hook so we won't give back a texture factored on our own, but instead always draw into + // a proxy texure associated with the swapchain or into the swapchain directly. That's why we don't care about 'output texture expected state' + // as well here and set it to invalid -1. Expected state is what dgVoodoo transitions it into after the presentation so we know what state + // our texture is in when next time have to do sg with it. + oCtx.pOutputTexture = NULL; + oCtx.outputTexSRVCPUHandle = { NULL }; + oCtx.outputTextureExpectedState = -1; + + D3D12_CPU_DESCRIPTOR_HANDLE rtvCPUHandle = { 0 }; + UINT renderTargetState = 0; + DXGI_FORMAT rtvFormat = adapter.swapchains[iCtx.pSwapchain].properties.format; + RECT dstRect = { 0, 0, 0, 0 }; + { + // If dgVoodoo + // - gives us a possible direct destination texture to draw into + // - and the dimensions of the source texture rect matches the dimensions of the destination texture rect (the presentation size) + // then use that destination texture as the render target. It's a performance optimization. + + // If the dimensions of the src/dst rects mismatch then it means an image scaling which we hand off to dgVoodoo by drawing into a matching size + // proxy texture instead. + + if (iCtx.drawingTarget.pDstTexture != NULL && + (iCtx.srcRect.right - iCtx.srcRect.left) == (iCtx.drawingTarget.dstRect.right - iCtx.drawingTarget.dstRect.left) && + (iCtx.srcRect.bottom - iCtx.srcRect.top) == (iCtx.drawingTarget.dstRect.bottom - iCtx.drawingTarget.dstRect.top) ) { + + oCtx.pOutputTexture = iCtx.drawingTarget.pDstTexture; + rtvCPUHandle = iCtx.drawingTarget.rtvCPUHandle; + renderTargetState = iCtx.drawingTarget.dstTextureState; + dstRect = iCtx.drawingTarget.dstRect; + + } else { + + // A swapchain can always have at least 2 proxy textures. We have to check out if the incoming source texture is not a proxy texture already, + // so we pick up either the 0th or the 1st of the proxy textures. + ID3D12Root::SwapchainProxyTextureData ptData; + for (UInt32 i = 0; i < 2; i++) { + pD3D12Root->GetProxyTexture (iCtx.pSwapchain, i, &ptData); + oCtx.pOutputTexture = ptData.pTexture; + oCtx.outputTexSRVCPUHandle = ptData.srvHandle; + + if (ptData.pTexture != iCtx.pSrcTexture) { + // When we draw into a proxy texture then we could simply negligate the source and destination rects + // and update the full texture instead because dgVoodoo will only present the source rect anyway, + // but we can save some GPU resources this way, so this is a performance optimization + rtvCPUHandle = ptData.rtvHandle; + dstRect = iCtx.srcRect; + renderTargetState = ptData.texState; + break; + } + } + } + } + + // If we couldn't pick up a render target for any reason (demonstration purpose) + // then it's an error case so return with NULL output texture and let dgVoodoo ignore our hook + if (oCtx.pOutputTexture != NULL) { + + + ID3D12GraphicsCommandListAuto* pCmdListAuto = pD3D12Root->GetGraphicsCommandListAuto (adapterID); + + // This (vertex) buffer access pattern must be familiar: if 4 new vertices still fit into it then just append them to the end of the stream or allocate a new + // physical buffer instead and zero the stream position + ID3D12Buffer::LockData lData = adapter.pVertexBuffer->Lock ((adapter.vbPos + 4) <= VBUFFER_VERTEXCNT ? ID3D12Buffer::LT_NoOverwrite : ID3D12Buffer::LT_Discard, + pCmdListAuto->AGetFence (), pCmdListAuto->GetFenceValue ()); + + if (lData.ptr != NULL) { + + // Alloc room for 2 entries in the GPU-visible SRV descriptor ring buffer + ID3D12ResourceDescRingBuffer* pSRVRingBuffer = pD3D12Root->GetCBV_SRV_UAV_RingBuffer (adapterID); + ID3D12ResourceDescRingBuffer::AllocData rdData; + if (pSRVRingBuffer->Alloc (2, pCmdListAuto->AGetFence (), pCmdListAuto->GetFenceValue (), rdData)) { + + if ((adapter.vbPos + 4) > VBUFFER_VERTEXCNT) { + adapter.vbPos = 0; + } + + D3D12_RESOURCE_DESC srcDesc = iCtx.pSrcTexture->GetDesc (); + float srcWidth = (float) srcDesc.Width; + float srcHeight = (float) srcDesc.Height; + + // Texture coordinates for the incoming src rect + float tuLeft = (iCtx.srcRect.left / srcWidth); + float tvTop = (iCtx.srcRect.top / srcHeight); + float tuRight = (iCtx.srcRect.right / srcWidth); + float tvBottom = (iCtx.srcRect.bottom / srcHeight); + + // Make ptr volatile to avoid compiling optimizations resulting in reading video memory + // ("and dword ptr [eax], 0" and the likes) + volatile Vertex* pVertex = ((Vertex*) lData.ptr) + adapter.vbPos; + pVertex[0].pX = -1.0f; pVertex[0].pY = 1.0f; pVertex[0].tU = tuLeft; pVertex[0].tV = tvTop; + pVertex[1].pX = -1.0f; pVertex[1].pY = -1.0f; pVertex[1].tU = tuLeft; pVertex[1].tV = tvBottom; + pVertex[2].pX = 1.0f; pVertex[2].pY = 1.0f; pVertex[2].tU = tuRight; pVertex[2].tV = tvTop; + pVertex[3].pX = 1.0f; pVertex[3].pY = -1.0f; pVertex[3].tU = tuRight; pVertex[3].tV = tvBottom; + + // A 2 element array containing 2 separate one-length SRV descriptor ranges; the incoming texture and our glass texture + // The SRV range allocated by the ring buffer allocator is one range with 2 elements where our 2 source descriptors will be copied to + D3D12_CPU_DESCRIPTOR_HANDLE textureSRVs[] = + { + iCtx.srvCPUHandle, adapter.pSRVDescAllocator->GetCPUDescHandle (adapter.hGlassTexSRV) + }; + const static UINT textureSRVrangeSizes[] = { 1, 1 }; + const static UINT srvRingBufferRangeSize = 2; + adapter.pDevice->CopyDescriptors (1, &rdData.cpuDescHandle, &srvRingBufferRangeSize, 2, textureSRVs, textureSRVrangeSizes, D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV); + + // The "current state" of the command list must potentially be completely updated because either somebody else has written into it or it + // got flushed since the last time we wrote into it + // (Actually, this will always be the case in this hook method; it is just a demonstration how to decide between a full/partial state update) + bool forceUpdate = pCmdListAuto->ChangeId (this); + + pCmdListAuto->AFlushLock (); + ID3D12GraphicsCommandList* pCmdList = pCmdListAuto->GetCommandListInterface (); + + if (forceUpdate) { + pCmdList->SetGraphicsRootSignature (adapter.pRootSignature); + } + + bool updatePSO = forceUpdate; + // Get a pipeline object from the cache with the new render target format if needed + // (it's set to DXGI_FORMAT_UNKNOWN by default so it will always happen for the first time) + if (adapter.graphicsPipeline.RTVFormats[0] != rtvFormat) { + adapter.graphicsPipeline.RTVFormats[0] = rtvFormat; + + adapter.pPSO = pD3D12Root->PLCacheGetGraphicsPipeline (adapterID, adapter.graphicsPipeline); + updatePSO = true; + } + + if (updatePSO) { + pCmdList->SetPipelineState (adapter.pPSO); + } + + // Handle resource transition barriers + { + D3D12_RESOURCE_BARRIER barriers[4]; + UInt32 numBarriers = 0; + + // If the glass texture is not in a pixel shader source state then let's transition it into that + if ((adapter.glassTexState & D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE) == 0) { + IAddTransitionBarrier (adapter.pGlassTexture, adapter.glassTexState, D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE, barriers, numBarriers++); + adapter.glassTexState = D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE; + } + // If the incoming texture is not in a pixel shader source state + if ((iCtx.srcTextureState & D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE) == 0) { + IAddTransitionBarrier (iCtx.pSrcTexture, iCtx.srcTextureState, D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE, barriers, numBarriers++); + } + // If the dst texture is not in rendertarget state + if ((renderTargetState & D3D12_RESOURCE_STATE_RENDER_TARGET) == 0) { + IAddTransitionBarrier (oCtx.pOutputTexture, renderTargetState, D3D12_RESOURCE_STATE_RENDER_TARGET, barriers, numBarriers++); + } + if (numBarriers != 0) { + pCmdList->ResourceBarrier (numBarriers, barriers); + } + } + + if (forceUpdate) { + pCmdList->IASetPrimitiveTopology (D3D_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP); + // Update our tiny root-inline constant buffer + pCmdList->SetGraphicsRoot32BitConstants (1, 4, &rootPSConstBuffer, 0); + } + + // The things below can change independently on the cmd list state so we must always have to update them unconditionally + // The auto cmd list itself filters out a lot of redundant calls so it's not a big problem anyway + + // The allocator of the vertex buffer can return a new video memory location when locking with discarding + D3D12_VERTEX_BUFFER_VIEW vbView[] = + { + lData.gpuAddress, VBUFFER_VERTEXCNT * sizeof (Vertex), sizeof (Vertex) + }; + pCmdList->IASetVertexBuffers (0, 1, vbView); + + // The descriptor ring buffer allocator can return an address in a physical heap other than the latest one + pCmdList->SetDescriptorHeaps (1, &rdData.pHeap); + pCmdList->SetGraphicsRootDescriptorTable (0, rdData.gpuDescHandle); + + // Even the render target and the destination rects can change depending on the current state of dgVoodoo swapchain + pCmdList->OMSetRenderTargets (1, &rtvCPUHandle, TRUE, NULL); + pCmdList->RSSetScissorRects (1, &dstRect); + D3D12_VIEWPORT vp = { (FLOAT) dstRect.left, (FLOAT) dstRect.top, + (FLOAT) (dstRect.right - dstRect.left), + (FLOAT) (dstRect.bottom - dstRect.top), + 0.0f, 1.0f }; + pCmdList->RSSetViewports (1, &vp); + pCmdList->DrawInstanced (4, 1, adapter.vbPos, 0); + adapter.vbPos += 4; + + // We do not force a flush here because it's unneeded. Commiting short command lists to execution degrades performance anyway. + // Let dgVoodoo continue writing into the command list and handle the flush scenario. + pCmdListAuto->AFlushUnlock (); + + // If everything happened as expected then we can tell dgVoodoo to take the result of this hook method into account + // Otherwise, if we don't reach this point then just return false to tell the opposite + succeeded = true; + } + + // Make sure to 'unlock' the vertex buffer because subsequent Lock calls in a locked state will return with unsuccesful allocation + adapter.pVertexBuffer->Unlock (); + } + } + return succeeded; +} + + +void Presenter::D3D12SwapchainPresentEnd (UInt32 /*adapterID*/, const PresentEndContextInput& iCtx) +{ + // The source image has been drawn into the swapchain and set to the expected resource state (if it was required) and that's the point + // where this callback gets called + // We get a valid non-NULL destination texture in iCtx.drawingTarget and could draw something extra into the swapchain (like some overlay data) here + // but we do not draw anything in this sample +} + + +bool Presenter::Init () +{ + if (IParsePresenterINISection ()) { + if (main.pAddonMainCB->RegisterForCallback (IID_D3D12RootObserver, static_cast (this))) { + + InitializeCriticalSection (&lock); + return true; + } + } + + return false; +} + + +void Presenter::Exit () +{ + DeleteCriticalSection (&lock); + main.pAddonMainCB->UnregisterForCallback (IID_D3D12RootObserver, static_cast (this)); +} + + diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Presenter.hpp b/dgVoodooAPI/Samples/D3D12 Addon/Presenter.hpp new file mode 100644 index 0000000..801c0ba --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Presenter.hpp @@ -0,0 +1,138 @@ +// ***************************************************************************** +// File: Presenter.hpp +// +// Description: D3D12 presentation hook implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "Public\Addon\ID3D12RootObserver.hpp" +#include "ImageLoader.hpp" +#include + +// --- Namespaces -------------------------------------------------------------- + +using namespace dgVoodoo; + +// --- Predeclarations --------------------------------------------------------- + +class AddonMain; + +// --- Presenter --------------------------------------------------------------- + +class Presenter: public ID3D12RootObserver +{ +protected: + struct SwapchainEntry + { + // Here we could cache our resources associated with particular swapchains + // But there are no own-factored resources in this sample addon so this structure is empty + // and serves only demonstration purposes + ID3D12Swapchain* pSwapchain; + ID3D12Root::SwapchainData properties; + }; + + struct AdapterData + { + UInt32 adapterID; + + ID3D12Device* pDevice; + ID3D12RootSignature* pRootSignature; + ID3D12ResourceDescAllocator* pSRVDescAllocator; + + ID3D12Resource* pGlassTexture; + UInt32 hGlassTexSRV; + D3D12_RESOURCE_STATES glassTexState; + + ID3D12Root::GraphicsPLDesc graphicsPipeline; + ID3D12PipelineState* pPSO; + ID3D12Buffer* pVertexBuffer; + UInt32 vbPos; + + std::unordered_map swapchains; + + AdapterData (); + }; + + struct Vertex + { + float pX, pY; + float tU, tV; + }; + + struct RootPSConstBuffer + { + float sepiaColorR; + float sepiaColorG; + float sepiaColorB; + float colorIntensity; + }; + +protected: + AddonMain& main; + ID3D12Root* pD3D12Root; + CRITICAL_SECTION lock; + std::unordered_map adapters; + + ImageLoader::ImageData glassImage; + ID3DBlob* pVSQuad; + ID3DBlob* pPSGlass; + RootPSConstBuffer rootPSConstBuffer; + + UInt32 sectionIdx; + const char* pGlassFilePath; + UInt32 sepiaColor; + + const static D3D12_BLEND_DESC defaultBlendDesc; + const static D3D12_RASTERIZER_DESC defaultRasterizerDesc; + const static D3D12_DEPTH_STENCIL_DESC defaultDepthStencilDesc; + const static D3D12_INPUT_ELEMENT_DESC deaultInputLayout[]; + +protected: + void ITakeLock (); + void IReleaseLock (); + + AdapterData& GetAdapterRef (UInt32 adapterID); + void EraseAdapter (UInt32 adapterID); + + bool IParsePresenterINISection (); + + bool ILoadShaders (); + bool ICreateRootSignature (AdapterData& adapter); + void IReleaseRootSignature (AdapterData& adapter); + bool ICreateGlassTexture (AdapterData& adapter); + void IReleaseGlassTexture (AdapterData& adapter); + + void ICleanUpAdapter (AdapterData& adapter); + + void IAddTransitionBarrier (ID3D12Resource* pResource, UINT stateBefore, UINT stateAfter, D3D12_RESOURCE_BARRIER* pBarriers, UInt32 numBarriers); + +protected: + + // --- ID3D12RootObserver callbacks + + virtual bool D3D12RootCreated (HMODULE hD3D12Dll, ID3D12Root* pD3D12Root) override; + virtual void D3D12RootReleased (const ID3D12Root* pD3D12Root) override; + + virtual bool D3D12BeginUsingAdapter (UInt32 adapterID) override; + virtual void D3D12EndUsingAdapter (UInt32 adapterID) override; + + virtual void D3D12SwapchainCreated (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) override; + virtual void D3D12SwapchainChanged (UInt32 adapterID, ID3D12Swapchain* pSwapchain, const ID3D12Root::SwapchainData& swapchainData) override; + virtual void D3D12SwapchainReleased (UInt32 adapterID, ID3D12Swapchain* pSwapchain) override; + + virtual bool D3D12SwapchainPresentBegin (UInt32 adapterID, const PresentBeginContextInput& iCtx, PresentBeginContextOutput& oCtx) override; + virtual void D3D12SwapchainPresentEnd (UInt32 adapterID, const PresentEndContextInput& iCtx) override; + +public: + Presenter (AddonMain& main); + ~Presenter (); + + bool Init (); + void Exit (); + + void SetINISectionIdx (UInt32 idx) { sectionIdx = idx; } +}; \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Resource.h b/dgVoodooAPI/Samples/D3D12 Addon/Resource.h new file mode 100644 index 0000000..7c904fa Binary files /dev/null and b/dgVoodooAPI/Samples/D3D12 Addon/Resource.h differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Resource.rc b/dgVoodooAPI/Samples/D3D12 Addon/Resource.rc new file mode 100644 index 0000000..c0cd557 Binary files /dev/null and b/dgVoodooAPI/Samples/D3D12 Addon/Resource.rc differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.ini b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.ini new file mode 100644 index 0000000..273ca22 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.ini @@ -0,0 +1,16 @@ +; +; INI file for Sample addon +; + +[Presenter] + +; GlassImage: The path of the glass image texture - if no value is specified then the default 'DirtyGlass.png' will be used +; SepiaColor: A 32 bit ARGB value, "A" specifies the intensity of the original image color, "RGB" specifies the sepia color +; If no value is specified then the default will be used + +GlassImage = DirtyGlass.png +SepiaColor = 0x40F1AE72 + +[Texturer] + +; nothing here diff --git a/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj new file mode 100644 index 0000000..81ca1d7 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj @@ -0,0 +1,616 @@ + + + + + Debug + ARM64 + + + Debug + ARM64EC + + + Debug + Win32 + + + Debug + x64 + + + Release + ARM64 + + + Release + ARM64EC + + + Release + Win32 + + + Release + x64 + + + Spec Release + ARM64 + + + Spec Release + ARM64EC + + + Spec Release + Win32 + + + Spec Release + x64 + + + + + + + + + + + + + + + + + + + + + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B} + Direct3D + 10.0 + SampleAddon + + + + DynamicLibrary + true + Unicode + v143 + + + DynamicLibrary + true + Unicode + v143 + + + DynamicLibrary + true + Unicode + v143 + + + DynamicLibrary + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + DynamicLibrary + false + true + Unicode + v143 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + $(SolutionDir)\Bin\$(Platform)\$(Configuration)\ + $(SolutionDir)\Bin\$(ProjectName)\$(Platform)\$(Configuration)\ + + + + Level3 + Disabled + $(SolutionDir)\..\Inc\ + + + NotUsing + /Zc:threadSafeInit- /D_APIDLL %(AdditionalOptions) + + + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + $(SolutionDir)\..\Lib\x86\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + + + + + + + + Level3 + Disabled + $(SolutionDir)\..\Inc\ + + + NotUsing + /Zc:threadSafeInit- /D_APIDLL %(AdditionalOptions) + + + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + $(SolutionDir)\..\Lib\arm64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + + + + + + + + Level3 + Disabled + $(SolutionDir)\..\Inc\ + + + NotUsing + /Zc:threadSafeInit- /D_APIDLL %(AdditionalOptions) + + + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + $(SolutionDir)\..\Lib\x64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + + + + + + + + Level3 + Disabled + $(SolutionDir)\..\Inc\ + + + NotUsing + /Zc:threadSafeInit- /D_APIDLL %(AdditionalOptions) + + + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + $(SolutionDir)\..\Lib\arm64ec\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\x86\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\arm64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\x64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\arm64ec\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_SPEC /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\x86\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_SPEC /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\arm64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_SPEC /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\x64\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + + + + + + Level3 + MaxSpeed + true + true + $(SolutionDir)\..\Inc\ + Size + false + false + MultiThreaded + false + + + /Zc:threadSafeInit- /D_APIDLL /D_SPEC /D_NO_CRT_STDIO_INLINE /D _CRT_SECURE_NO_WARNINGS %(AdditionalOptions) + + + NotUsing + _WINDLL;BUILD_AS_DLL;%(PreprocessorDefinitions) + + + true + true + true + $(SolutionDir)\..\Lib\arm64ec\ + $(OutDir)$(TargetName)$(TargetExt) + dgVoodooAddon.lib;dxguid.lib;kernel32.lib;user32.lib;gdi32.lib;%(AdditionalDependencies) + false + false + + + 1 + + + + + + \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj.filters b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj.filters new file mode 100644 index 0000000..b0315ac --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/SampleAddon.vcxproj.filters @@ -0,0 +1,53 @@ + + + + + {83ab2fbb-6f6a-43cc-8a01-251d7ac36e42} + + + {fd3639d3-d580-463c-87e1-0d9f83ead4e1} + + + {a0fab181-8327-4625-8501-52c15fa03b61} + + + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + Header Files + + + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + Source Files + + + + + Resource Files + + + \ No newline at end of file diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Shaders/Make.bat b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/Make.bat new file mode 100644 index 0000000..152d54f --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/Make.bat @@ -0,0 +1,2 @@ +fxc /Tvs_5_1 /Qstrip_reflect /Qstrip_debug /FoVSQuad.vso VSQuad.hlsl +fxc /Tps_5_1 /Qstrip_reflect /Qstrip_debug /FoPSGlass.pso PSGlass.hlsl diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.hlsl b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.hlsl new file mode 100644 index 0000000..d7c057d --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.hlsl @@ -0,0 +1,52 @@ +// ***************************************************************************** +// File: PSGlass.hlsl +// +// Description: Pixel shader used for drawing the glassified quad +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Input signature --------------------------------------------------------- + +struct INPUT +{ + float4 pos : SV_POSITION; + float2 srcTexUV : TEXCOORD0; +}; + +// --- Output signature -------------------------------------------------------- + +struct OUTPUT +{ + float4 color0 : SV_TARGET0; +}; + +// --- Resources --------------------------------------------------------------- + +SamplerState samplerPt : register (s0); +SamplerState samplerBi : register (s1); +Texture2D textures[2] : register (t3, space1); + +cbuffer RootPSConstBuffer : register (b0, space2) +{ + float3 sepiaColor; + float colorIntensity; +} + +// --- Shader code ------------------------------------------------------------- + +OUTPUT main (INPUT i) +{ + const float3 bwFactors = float3 (0.3125f, 0.5f, 0.1875f); + OUTPUT o; + + float4 t1 = textures[1].Sample (samplerBi, i.srcTexUV); + float4 t0 = textures[0].Sample (samplerPt, i.srcTexUV); + + t0.rgb = lerp (dot (t0.rgb, bwFactors), t0.rgb, colorIntensity) * sepiaColor; + + o.color0 = lerp (t0, t1, t1.a); + + return o; +} diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.pso b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.pso new file mode 100644 index 0000000..0f86328 Binary files /dev/null and b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/PSGlass.pso differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.hlsl b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.hlsl new file mode 100644 index 0000000..5903d45 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.hlsl @@ -0,0 +1,37 @@ +// ***************************************************************************** +// File: VSQuad.hlsl +// +// Description: Vertex shader used for drawing the textured quad +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Input signature --------------------------------------------------------- + +struct INPUT +{ + float2 pos : POSITION0; + float2 srcTexUV : TEXCOORD0; +}; + +// --- Output signature -------------------------------------------------------- + +struct OUTPUT +{ + float4 pos : SV_POSITION; + float2 srcTexUV : TEXCOORD0; +}; + +// --- Resources --------------------------------------------------------------- + +// --- Shader code ------------------------------------------------------------- + +OUTPUT main (INPUT i) +{ + OUTPUT o; + o.pos = float4 (i.pos, 0.0f, 1.0f); + o.srcTexUV = i.srcTexUV; + + return o; +} diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.vso b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.vso new file mode 100644 index 0000000..8387bd1 Binary files /dev/null and b/dgVoodooAPI/Samples/D3D12 Addon/Shaders/VSQuad.vso differ diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Texturer.cpp b/dgVoodooAPI/Samples/D3D12 Addon/Texturer.cpp new file mode 100644 index 0000000..7cce963 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Texturer.cpp @@ -0,0 +1,155 @@ +// ***************************************************************************** +// File: Texturer.cpp +// +// Description: Texturer implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "AddonMain.hpp" + +// --- Texturer ---------------------------------------------------------------- + +Texturer::Texturer (AddonMain& main): + main (main) +{ +} + + +Texturer::~Texturer () +{ + Exit (); +} + +// --- Statics + +const char* Texturer::formatIdxToStr[] = { + + "P8", "RGB565", "XRGB555", "ARGB1555", "ARGB4444", "XRGB8888", "ARGB8888", "L8", "A8", "A8L8", "V8U8", "L6V5U5", "L8V8U8", + "Q8W8V8U8", "DXTC1", "DXTC2", "DXTC3", "DXTC4", "DXTC5", "UYVY", "YUY2", "ARGB2101010", "L16", "R16G16", "U16V16", "R16G16B16A16", + "R16F", "R16G16F", "R16G16B16A16F", "R32F", "R32G32F", "R32G32B32A32F", "BC4", "BC5", + "Z16", "Z24", "Z24S8", "Z24X4S4", "Z32" +}; + + +// --- ID3DObserver callbacks + +bool Texturer::D3DObjectCreated (ID3D* pD3D) +{ + ID3D::ObjectType type = pD3D->GetObjectType (); + + const static char* pObjectTypeStrs[] = { "Direct3D (DirectDraw)", "Direct3D8", "Direct3D9" }; + + main.pAddonMainCB->IssueInfo (&main, "D3D object (%p) is created. Object type is %s.\n", pD3D, pObjectTypeStrs[type]); + + return true; +} + + +void Texturer::D3DObjectReleased (const ID3D* pD3D) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D object (%p) is released.\n", pD3D); +} + + +// --- ID3DDeviceObserver callbacks + +bool Texturer::D3DDeviceObjectCreated (ID3DDevice* pD3DDevice) +{ + ID3DDevice::ObjectType type = pD3DDevice->GetObjectType (); + + const static char* pObjectTypeStrs[] = { "Direct3DDevice", "Direct3D8Device", "Direct3D9Device" }; + + main.pAddonMainCB->IssueInfo (&main, "D3DDevice object (%p) is created. Object type is %s.\n", pD3DDevice, pObjectTypeStrs[type]); + + return true; +} + + +void Texturer::D3DDeviceObjectReleased (const ID3DDevice* pD3DDevice) +{ + main.pAddonMainCB->IssueInfo (&main, "D3DDevice object (%p) is released.\n", pD3DDevice); +} + +// --- ID3DResourceObserver callbacks + +bool Texturer::TextureCreated (ID3D* pD3D, ID3DResource* pTexture) +{ + { + ID3DResource::Desc desc = pTexture->ARGetDesc (); + main.pAddonMainCB->IssueInfo (&main, "D3D Texture (%p) is created. D3D = %p, width = %d, height = %d, mipmaplevels = %d, format = %s\n", + pTexture, pD3D, desc.width, desc.height, desc.mipMapNum, formatIdxToStr[desc.format]); + } + + return true; +} + +bool Texturer::CubeTextureCreated (ID3D* pD3D, ID3DResource* pTexture) +{ + { + ID3DResource::Desc desc = pTexture->ARGetDesc (); + main.pAddonMainCB->IssueInfo (&main, "D3D Cube Texture (%p) is created. D3D = %p, width = %d, height = %d, mipmaplevels = %d, format = %s\n", + pTexture, pD3D, desc.width, desc.height, desc.mipMapNum, formatIdxToStr[desc.format]); + } + + return true; +} + + +bool Texturer::VolumeTextureCreated (ID3D* pD3D, ID3DResource* pTexture) +{ + { + ID3DResource::Desc desc = pTexture->ARGetDesc (); + main.pAddonMainCB->IssueInfo (&main, "D3D Volume Texture (%p) is created. D3D = %p, width = %d, height = %d, depth = %d, mipmaplevels = %d, format = %s (unhooked resource)\n", + pTexture, pD3D, desc.width, desc.height, desc.depth, desc.mipMapNum, formatIdxToStr[desc.format]); + } + + return true; +} + + +void Texturer::TextureReleased (ID3D* pD3D, const ID3DResource* pTexture) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D Texture (%p) is released. D3D = %p\n", pTexture, pD3D); +} + + +void Texturer::CubeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D Cube Texture (%p) is released. D3D = %p\n", pTexture, pD3D); +} + + +void Texturer::VolumeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture) +{ + main.pAddonMainCB->IssueInfo (&main, "D3D Volume Texture (%p) is released. D3D = %p\n", pTexture, pD3D); +} + +// --- + +bool Texturer::Init () +{ + if (main.pAddonMainCB->RegisterForCallback (IID_D3DObserver, static_cast (this))) { + if (main.pAddonMainCB->RegisterForCallback (IID_D3DDeviceObserver, static_cast (this))) { + if (main.pAddonMainCB->RegisterForCallback(IID_D3DResourceObserver, static_cast (this))) { + + return true; + } + main.pAddonMainCB->UnregisterForCallback (IID_D3DDeviceObserver, static_cast (this)); + } + main.pAddonMainCB->UnregisterForCallback (IID_D3DObserver, static_cast (this)); + } + + return false; +} + + +void Texturer::Exit () +{ + main.pAddonMainCB->UnregisterForCallback (IID_D3DResourceObserver, static_cast (this)); + main.pAddonMainCB->UnregisterForCallback (IID_D3DDeviceObserver, static_cast (this)); + main.pAddonMainCB->UnregisterForCallback (IID_D3DObserver, static_cast (this)); +} diff --git a/dgVoodooAPI/Samples/D3D12 Addon/Texturer.hpp b/dgVoodooAPI/Samples/D3D12 Addon/Texturer.hpp new file mode 100644 index 0000000..229e809 --- /dev/null +++ b/dgVoodooAPI/Samples/D3D12 Addon/Texturer.hpp @@ -0,0 +1,65 @@ +// ***************************************************************************** +// File: Texturer.hpp +// +// Description: Texturer implementation of dgVoodoo Addon DLL +// +// Contact person: DG +// +// ***************************************************************************** + +// --- Includes ---------------------------------------------------------------- + +#include "Public\Addon\ID3DObserver.hpp" +#include "Public\Addon\ID3DDeviceObserver.hpp" +#include "Public\Addon\ID3DResourceObserver.hpp" + +// --- Namespaces -------------------------------------------------------------- + +using namespace dgVoodoo; + +// --- Predeclarations --------------------------------------------------------- + +class AddonMain; + +// --- Texturer ---------------------------------------------------------------- + +class Texturer: public ID3DObserver, + public ID3DDeviceObserver, + public ID3DResourceObserver +{ +protected: + + static const char* formatIdxToStr[]; + +protected: + AddonMain& main; + +protected: + + // --- ID3DObserver callbacks + + virtual bool D3DObjectCreated (ID3D* pD3D) override; + virtual void D3DObjectReleased (const ID3D* pD3D) override; + + // --- ID3DDeviceObserver callbacks + + virtual bool D3DDeviceObjectCreated (ID3DDevice* pD3DDevice); + virtual void D3DDeviceObjectReleased (const ID3DDevice* pD3DDevice); + + // --- ID3DResourceObserver callbacks + + virtual bool TextureCreated (ID3D* pD3D, ID3DResource* pTexture); + virtual bool CubeTextureCreated (ID3D* pD3D, ID3DResource* pTexture); + virtual bool VolumeTextureCreated (ID3D* pD3D, ID3DResource* pTexture); + + virtual void TextureReleased (ID3D* pD3D, const ID3DResource* pTexture); + virtual void CubeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture); + virtual void VolumeTextureReleased (ID3D* pD3D, const ID3DResource* pTexture); + +public: + Texturer (AddonMain& main); + ~Texturer (); + + bool Init (); + void Exit (); +}; \ No newline at end of file diff --git a/dgVoodooAPI/Samples/Samples.sln b/dgVoodooAPI/Samples/Samples.sln new file mode 100644 index 0000000..76b70d5 --- /dev/null +++ b/dgVoodooAPI/Samples/Samples.sln @@ -0,0 +1,81 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio Version 17 +VisualStudioVersion = 17.4.33122.133 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "SampleAddon", "D3D12 Addon\SampleAddon.vcxproj", "{9B08A494-4E40-4A58-BE34-A2ECC47AB22B}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "APILibrary", "API Library\APILibrary.vcxproj", "{CD7EACA5-A639-4264-9F8D-5044F8489A15}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|ARM64 = Debug|ARM64 + Debug|ARM64EC = Debug|ARM64EC + Debug|x64 = Debug|x64 + Debug|x86 = Debug|x86 + Release|ARM64 = Release|ARM64 + Release|ARM64EC = Release|ARM64EC + Release|x64 = Release|x64 + Release|x86 = Release|x86 + Spec Release|ARM64 = Spec Release|ARM64 + Spec Release|ARM64EC = Spec Release|ARM64EC + Spec Release|x64 = Spec Release|x64 + Spec Release|x86 = Spec Release|x86 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|ARM64.ActiveCfg = Debug|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|ARM64.Build.0 = Debug|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|ARM64EC.ActiveCfg = Debug|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|ARM64EC.Build.0 = Debug|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|x64.ActiveCfg = Debug|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|x64.Build.0 = Debug|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|x86.ActiveCfg = Debug|Win32 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Debug|x86.Build.0 = Debug|Win32 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|ARM64.ActiveCfg = Release|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|ARM64.Build.0 = Release|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|ARM64EC.ActiveCfg = Release|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|ARM64EC.Build.0 = Release|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|x64.ActiveCfg = Release|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|x64.Build.0 = Release|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|x86.ActiveCfg = Release|Win32 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Release|x86.Build.0 = Release|Win32 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|ARM64.ActiveCfg = Spec Release|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|ARM64.Build.0 = Spec Release|ARM64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|ARM64EC.ActiveCfg = Spec Release|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|ARM64EC.Build.0 = Spec Release|ARM64EC + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|x64.ActiveCfg = Spec Release|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|x64.Build.0 = Spec Release|x64 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|x86.ActiveCfg = Spec Release|Win32 + {9B08A494-4E40-4A58-BE34-A2ECC47AB22B}.Spec Release|x86.Build.0 = Spec Release|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|ARM64.ActiveCfg = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|ARM64.Build.0 = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|ARM64EC.ActiveCfg = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|ARM64EC.Build.0 = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x64.ActiveCfg = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x64.Build.0 = Debug|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x86.ActiveCfg = Debug|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Debug|x86.Build.0 = Debug|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|ARM64.ActiveCfg = Release|ARM64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|ARM64.Build.0 = Release|ARM64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|ARM64EC.ActiveCfg = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|ARM64EC.Build.0 = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x64.ActiveCfg = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x64.Build.0 = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x86.ActiveCfg = Release|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Release|x86.Build.0 = Release|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|ARM64.ActiveCfg = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|ARM64.Build.0 = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|ARM64EC.ActiveCfg = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|ARM64EC.Build.0 = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|x64.ActiveCfg = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|x64.Build.0 = Release|x64 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|x86.ActiveCfg = Release|Win32 + {CD7EACA5-A639-4264-9F8D-5044F8489A15}.Spec Release|x86.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {40C569D8-BEAA-4C3F-A60F-A6E51F90B653} + EndGlobalSection +EndGlobal