Skip to content

Commit

Permalink
use surface to initialize swapchain
Browse files Browse the repository at this point in the history
  • Loading branch information
recp committed Oct 9, 2023
1 parent c0dc9ae commit cbda69c
Show file tree
Hide file tree
Showing 11 changed files with 143 additions and 53 deletions.
8 changes: 8 additions & 0 deletions include/gpu/api/swapchain.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,14 @@ extern "C" {
struct GPUApi;

typedef struct GPUApiSwapChain {
GPUSwapChain*
(*createSwapChain)(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
struct GPUSurface * __restrict surface,
GPUExtent2D size,
bool autoResize);

GPUSwapChain*
(*createSwapChainForView)(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
Expand Down
3 changes: 3 additions & 0 deletions include/gpu/geometric.h
Original file line number Diff line number Diff line change
Expand Up @@ -49,4 +49,7 @@ typedef struct GPURect2D {
GPUExtent2D extent;
} GPURect2D;

#ifdef __cplusplus
}
#endif
#endif /* gpu_geometry_h */
2 changes: 1 addition & 1 deletion include/gpu/gpu.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ extern "C" {
#endif

#include "common.h"
#include "geometry.h"
#include "geometric.h"

#include "pixelformat.h"
#include "device.h"
Expand Down
11 changes: 10 additions & 1 deletion include/gpu/swapchain.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,16 +21,17 @@ extern "C" {
#endif

#include "common.h"
#include "geometric.h"

struct GPUCommandQueue;
struct GPUSurface;

typedef struct GPUSwapChain {
void *_priv;
void *target; /* draw target */
float backingScaleFactor;
} GPUSwapChain;


typedef enum GPUWindowType {
GPU_WINDOW_TYPE_HWND,
GPU_WINDOW_TYPE_COREWINDOW,
Expand All @@ -42,6 +43,14 @@ typedef struct GPUWindowHandle {
void *ptr;
} GPUWindowHandle;

GPU_EXPORT
GPUSwapChain*
GPUCreateSwapChain(GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
struct GPUSurface * __restrict surface,
GPUExtent2D size,
bool autoResize);

GPU_EXPORT
GPUSwapChain*
GPUCreateSwapChainForView(GPUDevice * __restrict device,
Expand Down
15 changes: 15 additions & 0 deletions src/api/swapchain.c
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,21 @@

#include "../common.h"

GPU_EXPORT
GPUSwapChain*
GPUCreateSwapChain(GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
struct GPUSurface * __restrict surface,
GPUExtent2D size,
bool autoResize) {
GPUApi *api;

if (!(api = gpuActiveGPUApi()))
return NULL;

return api->swapchain.createSwapChain(api, device, cmdQue, surface, size, autoResize);
}

GPU_EXPORT
GPUSwapChain*
GPUCreateSwapChainForView(GPUDevice * __restrict device,
Expand Down
7 changes: 6 additions & 1 deletion src/backend/dx12/impl/surface.c
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,12 @@ dx12_createSurface(GPUApi * __restrict api,
float scale) {
GPUSurface *surface;

return NULL;
surface = calloc(1, sizeof(*surface));
surface->_priv = nativeHandle;
surface->type = type;
surface->scale = scale;

return surface;
}

GPU_HIDE
Expand Down
46 changes: 25 additions & 21 deletions src/backend/dx12/impl/swapchain.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,15 +18,12 @@

GPU_HIDE
GPUSwapChain*
dx12_createSwapChainForView(GPUApi * __restrict api,
GPUDevice * __restrict device,
GPUCommandQueue * __restrict cmdQue,
void * __restrict viewHandle,
GPUWindowType viewHandleType,
float backingScaleFactor,
uint32_t width,
uint32_t height,
bool autoResize) {
dx12_createSwapChain(GPUApi * __restrict api,
GPUDevice * __restrict device,
GPUCommandQueue * __restrict cmdQue,
GPUSurface * __restrict surface,
GPUExtent2D size,
bool autoResize) {
GPUSwapChain *swapChain;
ID3D12Device *d3dDevice;
ID3D12CommandQueue *cmdQueDX12;
Expand All @@ -46,8 +43,8 @@ dx12_createSwapChainForView(GPUApi * __restrict api,

swapChainDX12 = NULL;
swapChainDesc.BufferCount = FrameCount;
swapChainDesc.Width = width;
swapChainDesc.Height = height;
swapChainDesc.Width = size.width;
swapChainDesc.Height = size.height;
swapChainDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
swapChainDesc.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_DISCARD;
Expand All @@ -58,24 +55,26 @@ dx12_createSwapChainForView(GPUApi * __restrict api,
cmdQueDX12 = cmdQue->priv;
dxgiFactory = dx12api->dxgiFactory;

switch (viewHandleType) {
case GPU_WINDOW_TYPE_COREWINDOW:
switch (surface->type) {
case GPU_SURFACE_WINDOWS_COREWINDOW:
DXCHECK(dxgiFactory->lpVtbl->CreateSwapChainForCoreWindow(dxgiFactory,
(IUnknown *)cmdQueDX12,
viewHandle,
surface->_priv,
&swapChainDesc,
NULL,
&swapChain1));
break;
case GPU_WINDOW_TYPE_HWND:
case GPU_SURFACE_WINDOWS_HWND:
DXCHECK(dxgiFactory->lpVtbl->CreateSwapChainForHwnd(dxgiFactory,
(IUnknown *)cmdQueDX12,
viewHandle,
surface->_priv,
&swapChainDesc,
NULL,
NULL,
&swapChain1));
DXCHECK(dxgiFactory->lpVtbl->MakeWindowAssociation(dxgiFactory, viewHandle, DXGI_MWA_NO_ALT_ENTER));
DXCHECK(dxgiFactory->lpVtbl->MakeWindowAssociation(dxgiFactory,
surface->_priv,
DXGI_MWA_NO_ALT_ENTER));
break;
default:
/* TODO: ? */
Expand All @@ -85,22 +84,27 @@ dx12_createSwapChainForView(GPUApi * __restrict api,
hr = swapChain1->lpVtbl->QueryInterface(swapChain1, &IID_IDXGISwapChain3, (void**)&swapChain3);
swapChain1->lpVtbl->Release(swapChain1);


swapChainDX12 = calloc(1, sizeof(*swapChainDX12));
frameIndex = swapChain3->lpVtbl->GetCurrentBackBufferIndex(swapChain3);

// Create Descriptor Heap for Render Target Views
rtvHeapDesc.NumDescriptors = FrameCount;
rtvHeapDesc.Type = D3D12_DESCRIPTOR_HEAP_TYPE_RTV;
DXCHECK(d3dDevice->lpVtbl->CreateDescriptorHeap(d3dDevice, &rtvHeapDesc, &IID_ID3D12DescriptorHeap, (void **)&rtvHeap));
DXCHECK(d3dDevice->lpVtbl->CreateDescriptorHeap(d3dDevice,
&rtvHeapDesc,
&IID_ID3D12DescriptorHeap,
(void **)&rtvHeap));

// Create Render Target Views for each back buffer
p_rtvHandle = rtvHeap->lpVtbl->GetCPUDescriptorHandleForHeapStart(rtvHeap, &rtvHandle);
rtvDescriptorSize = d3dDevice->lpVtbl->GetDescriptorHandleIncrementSize(d3dDevice, D3D12_DESCRIPTOR_HEAP_TYPE_RTV);

for (i = 0; i < FrameCount; i++) {
frame = &swapChainDX12->frames[i];
DXCHECK(swapChain3->lpVtbl->GetBuffer(swapChain3, i, &IID_ID3D12Resource, (void **)&frame->renderTarget));
DXCHECK(swapChain3->lpVtbl->GetBuffer(swapChain3,
i,
&IID_ID3D12Resource,
(void **)&frame->renderTarget));

d3dDevice->lpVtbl->CreateRenderTargetView(d3dDevice, frame->renderTarget, NULL, rtvHandle);
rtvHandle.ptr += rtvDescriptorSize;
Expand Down Expand Up @@ -151,5 +155,5 @@ dx12_createSwapChainForView(GPUApi * __restrict api,
GPU_HIDE
void
dx12_initSwapChain(GPUApiSwapChain* apiSwapChain) {
apiSwapChain->createSwapChainForView = dx12_createSwapChainForView;
apiSwapChain->createSwapChain = dx12_createSwapChain;
}
7 changes: 6 additions & 1 deletion src/backend/mt/impl/surface.c
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,12 @@ mt_createSurface(GPUApi * __restrict api,
float scale) {
GPUSurface *surface;

return NULL;
surface = calloc(1, sizeof(*surface));
surface->_priv = nativeHandle;
surface->type = type;
surface->scale = scale;

return surface;
}

GPU_HIDE
Expand Down
93 changes: 65 additions & 28 deletions src/backend/mt/impl/swapchain.m
Original file line number Diff line number Diff line change
Expand Up @@ -107,50 +107,51 @@ - (void)dealloc {
}
}

GPU_HIDE
GPUSwapChain*
mt_createSwapChainForView(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
void * __restrict viewHandle,
GPUWindowType viewHandleType,
float backingScaleFactor,
uint32_t width,
uint32_t height,
bool autoResize) {
mt_createSwapChain(GPUApi * __restrict api,
GPUDevice * __restrict device,
GPUCommandQueue * __restrict cmdQue,
GPUSurface * __restrict surface,
GPUExtent2D size,
bool autoResize) {
GPUSwapChain *swapChain;
GPUSwapChainMetal *swapChainMtl;
GPUSwapChainObjc *objc;

swapChain = calloc(1, sizeof(*swapChain));
swapChainMtl = calloc(1, sizeof(*swapChainMtl));
swapChainMtl->layer = [CAMetalLayer layer];
swapChainMtl->layer.bounds = CGRectMake(0, 0, width, height);
swapChainMtl->layer.bounds = CGRectMake(0, 0, size.width, size.height);
swapChainMtl->layer.device = device->priv;
// swapChainMtl->layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
swapChainMtl->layer.opaque = YES;
swapChainMtl->layer.contentsScale = backingScaleFactor;
swapChainMtl->layer.contentsScale = surface->scale;
swapChainMtl->layer.contentsGravity = kCAGravityResizeAspectFill;
swapChain->_priv = swapChainMtl;
swapChain->backingScaleFactor = backingScaleFactor;
swapChain->backingScaleFactor = surface->scale;
swapChainMtl->objc = [GPUSwapChainObjc new];

objc = swapChainMtl->objc;
objc->swapChainMtl = swapChainMtl;
objc->backingScaleFactor = backingScaleFactor;
objc->backingScaleFactor = surface->scale;

mt_swapChainAttachToView(swapChain, viewHandle, autoResize, true);
mt_swapChainAttachToView(swapChain, surface->_priv, autoResize, true);

return swapChain;
}

GPU_HIDE
GPUSwapChain*
mt_createSwapChainForLayer(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
float backingScaleFactor,
uint32_t width,
uint32_t height,
bool autoResize) {
mt_createSwapChainForView(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
void * __restrict viewHandle,
GPUWindowType viewHandleType,
float backingScaleFactor,
uint32_t width,
uint32_t height,
bool autoResize) {
GPUSwapChain *swapChain;
GPUSwapChainMetal *swapChainMtl;
GPUSwapChainObjc *objc;
Expand All @@ -172,17 +173,20 @@ - (void)dealloc {
objc->swapChainMtl = swapChainMtl;
objc->backingScaleFactor = backingScaleFactor;

mt_swapChainAttachToView(swapChain, viewHandle, autoResize, true);

return swapChain;
}

GPU_HIDE
GPUSwapChain*
mt_createSwapChain(GPUApi * __restrict api,
GPUDevice * __restrict device,
GPUCommandQueue * __restrict cmdQue,
float backingScaleFactor,
float width,
float height) {
mt_createSwapChainForLayer(struct GPUApi * __restrict api,
struct GPUDevice * __restrict device,
struct GPUCommandQueue * __restrict cmdQue,
float backingScaleFactor,
uint32_t width,
uint32_t height,
bool autoResize) {
GPUSwapChain *swapChain;
GPUSwapChainMetal *swapChainMtl;
GPUSwapChainObjc *objc;
Expand All @@ -192,7 +196,7 @@ - (void)dealloc {
swapChainMtl->layer = [CAMetalLayer layer];
swapChainMtl->layer.bounds = CGRectMake(0, 0, width, height);
swapChainMtl->layer.device = device->priv;
// swapChainMtl->layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
// swapChainMtl->layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
swapChainMtl->layer.opaque = YES;
swapChainMtl->layer.contentsScale = backingScaleFactor;
swapChainMtl->layer.contentsGravity = kCAGravityResizeAspectFill;
Expand All @@ -207,9 +211,42 @@ - (void)dealloc {
return swapChain;
}

//GPU_HIDE
//GPUSwapChain*
//mt_createSwapChain(GPUApi * __restrict api,
// GPUDevice * __restrict device,
// GPUCommandQueue * __restrict cmdQue,
// float backingScaleFactor,
// float width,
// float height) {
// GPUSwapChain *swapChain;
// GPUSwapChainMetal *swapChainMtl;
// GPUSwapChainObjc *objc;
//
// swapChain = calloc(1, sizeof(*swapChain));
// swapChainMtl = calloc(1, sizeof(*swapChainMtl));
// swapChainMtl->layer = [CAMetalLayer layer];
// swapChainMtl->layer.bounds = CGRectMake(0, 0, width, height);
// swapChainMtl->layer.device = device->priv;
//// swapChainMtl->layer.pixelFormat = MTLPixelFormatBGRA8Unorm;
// swapChainMtl->layer.opaque = YES;
// swapChainMtl->layer.contentsScale = backingScaleFactor;
// swapChainMtl->layer.contentsGravity = kCAGravityResizeAspectFill;
// swapChain->_priv = swapChainMtl;
// swapChain->backingScaleFactor = backingScaleFactor;
// swapChainMtl->objc = [GPUSwapChainObjc new];
//
// objc = swapChainMtl->objc;
// objc->swapChainMtl = swapChainMtl;
// objc->backingScaleFactor = backingScaleFactor;
//
// return swapChain;
//}

GPU_HIDE
void
mt_initSwapChain(GPUApiSwapChain *api) {
api->createSwapChain = mt_createSwapChain;
api->createSwapChainForView = mt_createSwapChainForView;
api->createSwapChainForLayer = mt_createSwapChainForLayer;
api->attachToLayer = mt_swapChainAttachToLayer;
Expand Down
1 change: 1 addition & 0 deletions win/gpu/gpu.vcxproj
Original file line number Diff line number Diff line change
Expand Up @@ -230,6 +230,7 @@
<ClInclude Include="..\..\include\gpu\device.h" />
<ClInclude Include="..\..\include\gpu\feature.h" />
<ClInclude Include="..\..\include\gpu\frame.h" />
<ClInclude Include="..\..\include\gpu\geometric.h" />
<ClInclude Include="..\..\include\gpu\gpu.h" />
<ClInclude Include="..\..\include\gpu\instance.h" />
<ClInclude Include="..\..\include\gpu\library.h" />
Expand Down
3 changes: 3 additions & 0 deletions win/gpu/gpu.vcxproj.filters
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,9 @@
<ClInclude Include="..\..\include\gpu\surface.h">
<Filter>include\gpu</Filter>
</ClInclude>
<ClInclude Include="..\..\include\gpu\geometric.h">
<Filter>include\gpu</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\..\src\win\dllmain.c">
Expand Down

0 comments on commit cbda69c

Please sign in to comment.