fix some bugs on macos and improve presentation queue

This commit is contained in:
Greg Wells
2025-07-01 16:15:43 -04:00
parent 4c7fe77db3
commit 504603e5ac
11 changed files with 41 additions and 36 deletions

View File

@@ -100,9 +100,8 @@ gnReturnCode createMetalGraphicsPipeline(gnGraphicsPipeline graphicsPipeline, gn
}
MTLDepthStencilDescriptor* depthStencilDesc = [[MTLDepthStencilDescriptor alloc] init];
depthStencilDesc.depthWriteEnabled = info.depthStencil.depthWriteEnable,
depthStencilDesc.depthCompareFunction = info.depthStencil.depthWriteEnable,
depthStencilDesc.depthCompareFunction = mtlGrypnCompareOperation(info.depthStencil.operation),
depthStencilDesc.depthWriteEnabled = info.depthStencil.depthWriteEnable;
depthStencilDesc.depthCompareFunction = MTLCompareFunctionLess;
graphicsPipeline->graphicsPipeline->depthState = [device->outputDevice->device newDepthStencilStateWithDescriptor:depthStencilDesc];

View File

@@ -8,19 +8,15 @@ gnReturnCode metalPresent(gnOutputDeviceHandle device, gnPresentInfo info) {
for (int i =0 ; i < info.presentationQueueCount; i++) {
info.presentationQueues[i]->info.surface->windowSurface->layer.device = device->outputDevice->device;
id<CAMetalDrawable> drawable = [info.presentationQueues[i]->info.surface->windowSurface->layer nextDrawable];
if (drawable == nil) {
return GN_FAILED_TO_CREATE_FRAMEBUFFER;
}
if (drawable == nil) return GN_FAILED_TO_CREATE_FRAMEBUFFER;
__block gnPresentationQueue presentationQueue = info.presentationQueues[i];
__block uint32_t imageIndex = info.imageIndices[i];
id<MTLCommandBuffer> commandBuffer = [device->outputDevice->transferQueue commandBuffer];
MTLRenderPassDescriptor* passDesc = [MTLRenderPassDescriptor renderPassDescriptor];
passDesc.colorAttachments[0].texture = drawable.texture;
passDesc.colorAttachments[0].loadAction = MTLLoadActionClear;
passDesc.colorAttachments[0].storeAction = MTLStoreActionStore;
passDesc.colorAttachments[0].clearColor = MTLClearColorMake(1.0f, 0, 0, 1.0f);
id<MTLRenderCommandEncoder> render = [commandBuffer renderCommandEncoderWithDescriptor:passDesc];
[render endEncoding];
[commandBuffer addCompletedHandler:^(id<MTLCommandBuffer> buffer) {
uint32_tArrayListAdd(&presentationQueue->presentationQueue->avaliableTextures, imageIndex);
}];
id<MTLBlitCommandEncoder> blit = [commandBuffer blitCommandEncoder];

View File

@@ -2,11 +2,12 @@
#import <Metal/Metal.h>
#include "presentation_queue/gryphn_presentation_queue.h"
typedef struct gnPlatformPresentationQueue_t {
int textureCount;
id<MTLTexture>* textures;
typedef id<MTLTexture> metalTexture;
GN_ARRAY_LIST(metalTexture);
uint32_t currentImage;
typedef struct gnPlatformPresentationQueue_t {
metalTextureArrayList textures;
uint32_tArrayList avaliableTextures;
} gnPlatformPresentationQueue;
gnReturnCode createMetalPresentationQueue(gnPresentationQueueHandle presentationQueue, const gnDevice device, gnPresentationQueueInfo presentationInfo);

View File

@@ -25,23 +25,22 @@ gnReturnCode createMetalPresentationQueue(gnPresentationQueueHandle presentation
MTLPixelFormat convertedFormat = mtlGryphnFormatToMetalFormat(presentationInfo.format.format);
CGColorSpaceRef convertedColorSpace = mtlGryphnColorSpaceToMetalColorSpace(presentationInfo.format.colorSpace);
presentationQueue->presentationQueue->textureCount = presentationInfo.minImageCount;
presentationQueue->presentationQueue->textures = malloc(sizeof(id<MTLTexture>) * presentationInfo.minImageCount);
MTLTextureDescriptor* textureDescriptor = [[MTLTextureDescriptor alloc] init];
textureDescriptor.pixelFormat = convertedFormat;
textureDescriptor.width = presentationInfo.imageSize.x;
textureDescriptor.height = presentationInfo.imageSize.y;
textureDescriptor.usage = MTLTextureUsageRenderTarget;
textureDescriptor.usage = MTLTextureUsageRenderTarget | MTLTextureUsageShaderRead;
textureDescriptor.textureType = MTLTextureType2D;
presentationQueue->imageCount = presentationInfo.minImageCount;
presentationQueue->images = malloc(sizeof(gnTexture) * presentationInfo.minImageCount);
presentationQueue->presentationQueue->textures = metalTextureArrayListCreate();
for (int i = 0; i < presentationInfo.minImageCount; i++) {
presentationQueue->presentationQueue->textures[i] = [device->outputDevice->device newTextureWithDescriptor:textureDescriptor];
presentationQueue->images[i] = malloc(sizeof(struct gnTexture_t));
presentationQueue->images[i]->texture = malloc(sizeof(gnPlatformTexture));
presentationQueue->images[i]->texture->texture = presentationQueue->presentationQueue->textures[i];
presentationQueue->images[i]->texture->texture = [device->outputDevice->device newTextureWithDescriptor:textureDescriptor];
metalTextureArrayListAdd(&presentationQueue->presentationQueue->textures, presentationQueue->images[i]->texture->texture);
uint32_tArrayListAdd(&presentationQueue->presentationQueue->avaliableTextures, i);
}
return GN_SUCCESS;
@@ -49,16 +48,17 @@ gnReturnCode createMetalPresentationQueue(gnPresentationQueueHandle presentation
gnReturnCode getMetalPresentQueueImage(gnPresentationQueueHandle presentationQueue, uint64_t timeout, gnSemaphore semaphore, uint32_t* imageIndex) {
semaphore->semaphore->eventTriggered = gnFalse;
*imageIndex = presentationQueue->presentationQueue->currentImage;
presentationQueue->presentationQueue->currentImage++;
presentationQueue->presentationQueue->currentImage %= presentationQueue->imageCount;
while (presentationQueue->presentationQueue->avaliableTextures.count == 0) {}
*imageIndex = presentationQueue->presentationQueue->avaliableTextures.data[0];
uint32_tArrayListPopHead(&presentationQueue->presentationQueue->avaliableTextures);
semaphore->semaphore->eventTriggered = gnTrue;
return GN_SUCCESS;
}
void destroyMetalPresentationQueue(gnPresentationQueueHandle presentationQueue) {
for (int i = 0; i < presentationQueue->imageCount; i++) {
[presentationQueue->presentationQueue->textures[i] release];
}
free(presentationQueue->presentationQueue->avaliableTextures.data);
presentationQueue->presentationQueue->avaliableTextures.count = 0;
for (int i = 0; i < presentationQueue->imageCount; i++)
[presentationQueue->images[i]->texture->texture release];
free(presentationQueue->presentationQueue);
}

View File

@@ -137,8 +137,6 @@ gnReturnCode createMetalShaderModule(gnShaderModule module, gnDevice device, gnS
return GN_FAILED_TO_FIND_ENTRY_POINT;
}
printf("%s", result);
NSString* functionName = [NSString stringWithCString:name encoding:NSUTF8StringEncoding];
module->shaderModule->function = [shaderLib newFunctionWithName:functionName];

View File

@@ -15,8 +15,8 @@ gnReturnCode metalSubmit(gnOutputDevice device, gnSubmitInfo info) {
for (int c = 0; c < semsToSignalCount; c++) {
semsToSignal[c]->semaphore->eventTriggered = gnTrue;
}
}];
fenceToSignal->signaled = gnTrue;
}];
[commandBuffer commit];
}

View File

@@ -27,7 +27,6 @@ gnSurfaceDetails getMetalSurfaceDetails(
surfaceDetails.minImageCount = 2;
surfaceDetails.maxImageCount = 3;
CGSize size = windowSurface->windowSurface->layer.drawableSize;
printf("Size: %f %f\n", size.width, size.height);
surfaceDetails.minImageSize = surfaceDetails.maxImageSize = surfaceDetails.currentSize = (gnUInt2){size.width, size.height};
return surfaceDetails;
}

View File

@@ -8,6 +8,7 @@ gnReturnCode createMetalTexture(gnTexture texture, gnDevice device, const gnText
textureDescriptor.pixelFormat = mtlGryphnFormatToMetalFormat(info.format);
textureDescriptor.width = info.width;
textureDescriptor.height = info.height;
texture->texture->texture = [device->outputDevice->device newTextureWithDescriptor:textureDescriptor];
[textureDescriptor release];
return GN_SUCCESS;

View File

@@ -15,6 +15,7 @@ typedef void MTKView;
// MTKView* gnCreateMTKView(NSWindow* window);
// void gnWindowSetMTKView(NSWindow* window, MTKView* view);
CAMetalLayer* gnCreateCAMetalLayer(NSWindow* window);
void gnResizeCAMetalLayer(NSWindow* window);
// CAMetalLayer* gnGetCAMetalLayer(NSWindow* window);
// void gnAttachMetalLayer(NSWindow* window, CAMetalLayer* layer);

View File

@@ -24,12 +24,22 @@ CAMetalLayer* gnCreateCAMetalLayer(NSWindow* window) {
[view setLayer:layer];
[view setWantsLayer:YES];
CGSize viewSize = view.bounds.size;
CGFloat scale = view.window.screen.backingScaleFactor;
CGFloat scale = window.screen.backingScaleFactor;
layer.drawableSize = CGSizeMake(viewSize.width * scale,
viewSize.height * scale);
return layer;
}
void gnResizeCAMetalLayer(NSWindow* window) {
CAMetalLayer* layer = (CAMetalLayer*)window.contentView.layer;
CGSize viewSize = window.contentView.bounds.size;
CGFloat scale = window.screen.backingScaleFactor;
layer.drawableSize = CGSizeMake(viewSize.width * scale,
viewSize.height * scale);
}
// CAMetalLayer* gnGetCAMetalLayer(NSWindow* window) {
// return (CAMetalLayer*)window.contentView.layer;
// }