do clears as load ops if possible

This commit is contained in:
Samuliak 2024-07-06 17:28:35 +02:00
parent 2a9da80ff5
commit 498c4daed8
2 changed files with 146 additions and 38 deletions

View file

@ -60,7 +60,7 @@ void RendererMTL::display() {
colorAttachment->setClearColor(MTL::ClearColor{0.0f, 0.0f, 0.0f, 1.0f});
colorAttachment->setStoreAction(MTL::StoreActionStore);
beginRenderPassIfNeeded(renderPassDescriptor, drawable->texture());
beginRenderPassIfNeeded(renderPassDescriptor, false, drawable->texture());
renderCommandEncoder->setRenderPipelineState(displayPipeline);
renderCommandEncoder->setFragmentSamplerState(nearestSampler, 0);
@ -73,6 +73,7 @@ void RendererMTL::display() {
auto topScreen = colorRenderTargetCache.findFromAddress(topScreenAddr);
if (topScreen) {
clearColor(nullptr, topScreen->get().texture);
renderCommandEncoder->setViewport(MTL::Viewport{0, 0, 400, 240, 0.0f, 1.0f});
renderCommandEncoder->setFragmentTexture(topScreen->get().texture, 0);
renderCommandEncoder->drawPrimitives(MTL::PrimitiveTypeTriangleStrip, NS::UInteger(0), NS::UInteger(4));
@ -86,6 +87,7 @@ void RendererMTL::display() {
auto bottomScreen = colorRenderTargetCache.findFromAddress(bottomScreenAddr);
if (bottomScreen) {
clearColor(nullptr, bottomScreen->get().texture);
renderCommandEncoder->setViewport(MTL::Viewport{40, 240, 320, 240, 0.0f, 1.0f});
renderCommandEncoder->setFragmentTexture(bottomScreen->get().texture, 0);
renderCommandEncoder->drawPrimitives(MTL::PrimitiveTypeTriangleStrip, NS::UInteger(0), NS::UInteger(4));
@ -264,14 +266,7 @@ void RendererMTL::clearBuffer(u32 startAddress, u32 endAddress, u32 value, u32 c
const float b = Helpers::getBits<8, 8>(value) / 255.0f;
const float a = (value & 0xff) / 255.0f;
MTL::RenderPassDescriptor* renderPassDescriptor = MTL::RenderPassDescriptor::alloc()->init();
MTL::RenderPassColorAttachmentDescriptor* colorAttachment = renderPassDescriptor->colorAttachments()->object(0);
colorAttachment->setTexture(color->get().texture);
colorAttachment->setClearColor(MTL::ClearColor(r, g, b, a));
colorAttachment->setLoadAction(MTL::LoadActionClear);
colorAttachment->setStoreAction(MTL::StoreActionStore);
beginRenderPassIfNeeded(renderPassDescriptor, color->get().texture);
colorClearOps.push_back({color->get().texture, r, g, b, a});
return;
}
@ -286,23 +281,13 @@ void RendererMTL::clearBuffer(u32 startAddress, u32 endAddress, u32 value, u32 c
depthVal = (value & 0xffffff) / 16777215.0f;
}
MTL::RenderPassDescriptor* renderPassDescriptor = MTL::RenderPassDescriptor::alloc()->init();
MTL::RenderPassDepthAttachmentDescriptor* depthAttachment = renderPassDescriptor->depthAttachment();
depthAttachment->setTexture(depth->get().texture);
depthAttachment->setClearDepth(depthVal);
depthAttachment->setLoadAction(MTL::LoadActionClear);
depthAttachment->setStoreAction(MTL::StoreActionStore);
depthClearOps.push_back({depth->get().texture, depthVal});
if (format == DepthFmt::Depth24Stencil8) {
MTL::RenderPassStencilAttachmentDescriptor* stencilAttachment = renderPassDescriptor->stencilAttachment();
stencilAttachment->setTexture(depth->get().texture);
stencilAttachment->setClearStencil((value >> 24) & 0xff);
stencilAttachment->setLoadAction(MTL::LoadActionClear);
stencilAttachment->setStoreAction(MTL::StoreActionStore);
const u8 stencilVal = value >> 24;
stencilClearOps.push_back({depth->get().texture, stencilVal});
}
beginRenderPassIfNeeded(renderPassDescriptor, nullptr, depth->get().texture);
return;
}
@ -321,6 +306,7 @@ void RendererMTL::displayTransfer(u32 inputAddr, u32 outputAddr, u32 inputSize,
u32 outputHeight = outputSize >> 16;
auto srcFramebuffer = getColorRenderTarget(inputAddr, inputFormat, inputWidth, outputHeight);
clearColor(nullptr, srcFramebuffer->texture);
Math::Rect<u32> srcRect = srcFramebuffer->getSubRect(inputAddr, outputWidth, outputHeight);
if (verticalFlip) {
@ -355,7 +341,7 @@ void RendererMTL::displayTransfer(u32 inputAddr, u32 outputAddr, u32 inputSize,
Metal::BlitPipelineHash hash{destFramebuffer->format, DepthFmt::Unknown1};
auto blitPipeline = blitPipelineCache.get(hash);
beginRenderPassIfNeeded(renderPassDescriptor, destFramebuffer->texture);
beginRenderPassIfNeeded(renderPassDescriptor, false, destFramebuffer->texture);
renderCommandEncoder->setRenderPipelineState(blitPipeline);
renderCommandEncoder->setFragmentTexture(srcFramebuffer->texture, 0);
renderCommandEncoder->setFragmentSamplerState(nearestSampler, 0);
@ -444,24 +430,17 @@ void RendererMTL::drawVertices(PICA::PrimType primType, std::span<const PICA::Ve
// -------- Render --------
MTL::RenderPassDescriptor* renderPassDescriptor = MTL::RenderPassDescriptor::alloc()->init();
MTL::RenderPassColorAttachmentDescriptor* colorAttachment = renderPassDescriptor->colorAttachments()->object(0);
colorAttachment->setTexture(colorRenderTarget->texture);
colorAttachment->setLoadAction(MTL::LoadActionLoad);
colorAttachment->setStoreAction(MTL::StoreActionStore);
bool doesClear = clearColor(renderPassDescriptor, colorRenderTarget->texture);
if (depthStencilRenderTarget) {
MTL::RenderPassDepthAttachmentDescriptor* depthAttachment = renderPassDescriptor->depthAttachment();
depthAttachment->setTexture(depthStencilRenderTarget->texture);
depthAttachment->setLoadAction(MTL::LoadActionLoad);
depthAttachment->setStoreAction(MTL::StoreActionStore);
if (clearDepth(renderPassDescriptor, depthStencilRenderTarget->texture))
doesClear = true;
if (depthStencilRenderTarget->format == DepthFmt::Depth24Stencil8) {
MTL::RenderPassStencilAttachmentDescriptor* stencilAttachment = renderPassDescriptor->stencilAttachment();
stencilAttachment->setTexture(depthStencilRenderTarget->texture);
stencilAttachment->setLoadAction(MTL::LoadActionLoad);
stencilAttachment->setStoreAction(MTL::StoreActionStore);
if (clearStencil(renderPassDescriptor, depthStencilRenderTarget->texture))
doesClear = true;
}
}
beginRenderPassIfNeeded(renderPassDescriptor, colorRenderTarget->texture, (depthStencilRenderTarget ? depthStencilRenderTarget->texture : nullptr));
beginRenderPassIfNeeded(renderPassDescriptor, doesClear, colorRenderTarget->texture, (depthStencilRenderTarget ? depthStencilRenderTarget->texture : nullptr));
// Update the LUT texture if necessary
if (gpu.lightingLUTDirty) {