feat(render): add meshlet rendering and ECS query ref API

Introduces meshlet-based rendering pipeline with new HLSL structures and push constant layouts. Refactors meshlet upload/cooking, updates RenderGraphContext for global/view/instance data, and enhances ECS QueryBuilder with ref returns and [UnscopedRef] for fluent chaining. Improves resource management and disposal patterns, updates D3D12 interop for compatibility, and refines test/app infrastructure. Includes dependency updates, bug fixes, and code cleanups.
This commit is contained in:
2026-03-25 20:27:46 +09:00
parent b729ca86f5
commit 447a4e6904
28 changed files with 407 additions and 165 deletions

View File

@@ -10,9 +10,9 @@ namespace Ghost.Graphics.D3D12;
/// <summary>
/// D3D12 implementation of command queue interface
/// </summary>
internal unsafe class D3D12CommandQueue : D3D12Object<ID3D12CommandQueue1>, ICommandQueue
internal unsafe class D3D12CommandQueue : D3D12Object<ID3D12CommandQueue>, ICommandQueue
{
private UniquePtr<ID3D12Fence1> _fence;
private UniquePtr<ID3D12Fence> _fence;
private readonly AutoResetEvent _fenceEvent;
private ulong _fenceValue;
@@ -22,7 +22,7 @@ internal unsafe class D3D12CommandQueue : D3D12Object<ID3D12CommandQueue1>, ICom
get;
}
private static ID3D12CommandQueue1* CreateCommandQueue(ID3D12Device14* device, CommandQueueType type)
private static ID3D12CommandQueue* CreateCommandQueue(ID3D12Device14* device, CommandQueueType type)
{
var queueDesc = new D3D12_COMMAND_QUEUE_DESC
{
@@ -31,7 +31,7 @@ internal unsafe class D3D12CommandQueue : D3D12Object<ID3D12CommandQueue1>, ICom
Flags = D3D12_COMMAND_QUEUE_FLAGS.D3D12_COMMAND_QUEUE_FLAG_NONE,
};
ID3D12CommandQueue1* pQueue = default;
ID3D12CommandQueue* pQueue = default;
ThrowIfFailed(device->CreateCommandQueue(&queueDesc, __uuidof(pQueue), (void**)&pQueue));
return pQueue;
}
@@ -43,7 +43,7 @@ internal unsafe class D3D12CommandQueue : D3D12Object<ID3D12CommandQueue1>, ICom
_fenceEvent = new AutoResetEvent(false);
_fenceValue = 0;
ID3D12Fence1* pFence = default;
ID3D12Fence* pFence = default;
ThrowIfFailed(device.NativeObject.Get()->CreateFence(0, D3D12_FENCE_FLAGS.D3D12_FENCE_FLAG_NONE, __uuidof(pFence), (void**)&pFence));
_fence.Attach(pFence);

View File

@@ -160,6 +160,16 @@ internal class D3D12GraphicsEngine : IGraphicsEngine
return;
}
while (_commandBufferReturnQueue.TryDequeue(out var entry))
{
entry.commandBuffer.Dispose();
}
while (_commandBufferPool.TryDequeue(out var cmd))
{
cmd.Dispose();
}
_resourceDatabase.ReleaseAllResourcesImmediately();
_resourceAllocator.Dispose();

View File

@@ -29,9 +29,9 @@ internal unsafe class D3D12RenderDevice : D3D12Object<ID3D12Device14>, IRenderDe
public SharedPtr<IDXGIFactory7> DXGIFactory => _dxgiFactory.Share();
public SharedPtr<IDXGIAdapter1> Adapter => _adapter.Share();
public SharedPtr<ID3D12CommandQueue1> NativeGraphicsQueue => _graphicsQueue.NativeObject;
public SharedPtr<ID3D12CommandQueue1> NativeComputeQueue => _computeQueue.NativeObject;
public SharedPtr<ID3D12CommandQueue1> NativeCopyQueue => _copyQueue.NativeObject;
public SharedPtr<ID3D12CommandQueue> NativeGraphicsQueue => _graphicsQueue.NativeObject;
public SharedPtr<ID3D12CommandQueue> NativeComputeQueue => _computeQueue.NativeObject;
public SharedPtr<ID3D12CommandQueue> NativeCopyQueue => _copyQueue.NativeObject;
public D3D12RenderDevice()
:base(CreateDevice(out var dxgiFactory, out var adapter))

View File

@@ -53,8 +53,9 @@ internal static unsafe class D3D12Utility
var ptr = uPtr.Get();
if (ptr != null)
{
Debug.Assert(ptr != other);
var refCount = ptr->Release();
Debug.Assert((refCount != 0) || (ptr != other));
Debug.Assert(refCount == 0);
}
uPtr = new UniquePtr<T>(other);
@@ -68,7 +69,7 @@ internal static unsafe class D3D12Utility
if (ptr != null)
{
var refCount = ptr->Release();
Debug.Assert(refCount != 0);
//Debug.Assert(refCount == 0);
}
}
@@ -433,7 +434,7 @@ internal static unsafe class D3D12Utility
{
var flags = D3D12_RESOURCE_FLAG_NONE;
if (usage.HasFlag(BufferUsage.Raw) || usage.HasFlag(BufferUsage.UnorderedAccess))
if (usage.HasFlag(BufferUsage.UnorderedAccess))
{
flags |= D3D12_RESOURCE_FLAG_ALLOW_UNORDERED_ACCESS;
}