axmol/cocos/renderer/backend/metal/RenderTargetMTL.mm

203 lines
8.0 KiB
Plaintext
Raw Normal View History

#include "RenderTargetMTL.h"
#include "UtilsMTL.h"
CC_BACKEND_BEGIN
2021-12-28 11:05:34 +08:00
static MTLLoadAction getLoadAction(const RenderPassDescriptor& params,
TargetBufferFlags buffer) {
const auto clearFlags = (TargetBufferFlags) params.flags.clear;
const auto discardStartFlags = params.flags.discardStart;
2021-12-28 11:05:34 +08:00
if (bitmask::any(clearFlags, buffer)) {
return MTLLoadActionClear;
2021-12-28 11:05:34 +08:00
} else if (bitmask::any(discardStartFlags, buffer)) {
return MTLLoadActionDontCare;
}
return MTLLoadActionLoad;
}
2021-12-28 11:05:34 +08:00
static MTLStoreAction getStoreAction(const RenderPassDescriptor& params,
TargetBufferFlags buffer) {
const auto discardEndFlags = params.flags.discardEnd;
2021-12-28 11:05:34 +08:00
if (bitmask::any(discardEndFlags, buffer)) {
return MTLStoreActionDontCare;
}
return MTLStoreActionStore;
}
2021-12-28 11:05:34 +08:00
RenderTargetMTL::RenderTargetMTL(bool defaultRenderTarget) : RenderTarget(defaultRenderTarget)
{
}
RenderTargetMTL::~RenderTargetMTL()
{
}
2021-12-28 11:05:34 +08:00
void RenderTargetMTL::bindFrameBuffer() const
{
}
2021-12-28 11:05:34 +08:00
void RenderTargetMTL::unbindFrameBuffer() const
{
}
void RenderTargetMTL::setColorAttachment(ColorAttachment attachment)
{
RenderTarget::setColorAttachment(attachment);
2021-12-28 11:05:34 +08:00
}
void RenderTargetMTL::setDepthAttachment(TextureBackend* attachment, int level)
{
RenderTarget::setDepthAttachment(attachment, level);
2021-12-28 11:05:34 +08:00
}
void RenderTargetMTL::setStencilAttachment(TextureBackend* attachment, int level)
{
RenderTarget::setStencilAttachment(attachment, level);
2021-12-28 11:05:34 +08:00
}
2021-12-28 11:05:34 +08:00
void RenderTargetMTL::applyRenderPassAttachments(const RenderPassDescriptor& params, MTLRenderPassDescriptor* descriptor) const
{
// const auto discardFlags = params.flags.discardEnd;
auto clearFlags = params.flags.clear;
2021-12-28 11:05:34 +08:00
for (size_t i = 0; i < MAX_COLOR_ATTCHMENT; i++) {
auto attachment = getColorAttachment(i);
2021-12-28 11:05:34 +08:00
if (!attachment) {
continue;
}
2021-12-28 11:05:34 +08:00
const auto MRTColorFlag = getMRTColorFlag(i);
2021-12-28 11:05:34 +08:00
descriptor.colorAttachments[i].texture = attachment.texture;
2021-12-28 11:05:34 +08:00
descriptor.colorAttachments[i].level = attachment.level;
// descriptor.colorAttachments[i].slice = attachment.layer;
2021-12-28 11:05:34 +08:00
descriptor.colorAttachments[i].loadAction = getLoadAction(params, MRTColorFlag);
descriptor.colorAttachments[i].storeAction = getStoreAction(params,MRTColorFlag);
if(bitmask::any(clearFlags, MRTColorFlag))
descriptor.colorAttachments[i].clearColor = MTLClearColorMake(
params.clearColorValue[0], params.clearColorValue[1], params.clearColorValue[2], params.clearColorValue[3]);
#if 0
if (multisampledColor[i]) {
// We're rendering into our temporary MSAA texture and doing an automatic resolve.
// We should not be attempting to load anything into the MSAA texture.
assert(descriptor.colorAttachments[i].loadAction != MTLLoadActionLoad);
descriptor.colorAttachments[i].texture = multisampledColor[i];
descriptor.colorAttachments[i].level = 0;
descriptor.colorAttachments[i].slice = 0;
const bool discard = any(discardFlags & getMRTColorFlag(i));
if (!discard) {
descriptor.colorAttachments[i].resolveTexture = attachment.texture;
descriptor.colorAttachments[i].resolveLevel = attachment.level;
descriptor.colorAttachments[i].resolveSlice = attachment.layer;
descriptor.colorAttachments[i].storeAction = MTLStoreActionMultisampleResolve;
}
}
#endif
}
2021-12-28 11:05:34 +08:00
// Sets descriptor depth and stencil params, should match RenderTargetMTL::chooseAttachmentFormat
2021-12-28 11:05:34 +08:00
if(bitmask::any(this->_flags, RenderTargetFlag::DEPTH_AND_STENCIL)) {
auto depthAttachment = getDepthAttachment();
2021-12-28 11:05:34 +08:00
if(depthAttachment){
descriptor.depthAttachment.texture = depthAttachment.texture;
2021-12-28 11:05:34 +08:00
descriptor.depthAttachment.level = depthAttachment.level;
// descriptor.depthAttachment.slice = depthAttachment.layer;
2021-12-28 11:05:34 +08:00
descriptor.depthAttachment.loadAction = getLoadAction(params, TargetBufferFlags::DEPTH);
descriptor.depthAttachment.storeAction = getStoreAction(params, TargetBufferFlags::DEPTH);
2021-12-28 11:05:34 +08:00
if(bitmask::any(clearFlags, TargetBufferFlags::DEPTH))
descriptor.depthAttachment.clearDepth = params.clearDepthValue;
}
2021-12-28 11:05:34 +08:00
auto stencilAttachment = getStencilAttachment();
2021-12-28 11:05:34 +08:00
if(stencilAttachment) {
descriptor.stencilAttachment.texture = stencilAttachment.texture;
2021-12-28 11:05:34 +08:00
descriptor.stencilAttachment.level = stencilAttachment.level;
// descriptor.stencilAttachment.slice = depthAttachment.layer;
2021-12-28 11:05:34 +08:00
descriptor.stencilAttachment.loadAction = getLoadAction(params, TargetBufferFlags::STENCIL);
descriptor.stencilAttachment.storeAction = getStoreAction(params, TargetBufferFlags::STENCIL);
2021-12-28 11:05:34 +08:00
if(bitmask::any(clearFlags, TargetBufferFlags::STENCIL))
descriptor.stencilAttachment.clearStencil = params.clearStencilValue;
}
}
2021-12-28 11:05:34 +08:00
#if 0
if (multisampledDepth) {
// We're rendering into our temporary MSAA texture and doing an automatic resolve.
// We should not be attempting to load anything into the MSAA texture.
assert(descriptor.depthAttachment.loadAction != MTLLoadActionLoad);
descriptor.depthAttachment.texture = multisampledDepth;
descriptor.depthAttachment.level = 0;
descriptor.depthAttachment.slice = 0;
const bool discard = any(discardFlags & TargetBufferFlags::DEPTH);
if (!discard) {
descriptor.depthAttachment.resolveTexture = depthAttachment.texture;
descriptor.depthAttachment.resolveLevel = depthAttachment.level;
descriptor.depthAttachment.resolveSlice = depthAttachment.layer;
descriptor.depthAttachment.storeAction = MTLStoreActionMultisampleResolve;
}
}
#endif
}
RenderTargetMTL::Attachment RenderTargetMTL::getColorAttachment(int index) const
{
2021-12-28 11:05:34 +08:00
if(isDefaultRenderTarget() && index == 0)
return {DeviceMTL::getCurrentDrawable().texture, 0};
auto& rb = this->_color[index];
2021-12-28 11:05:34 +08:00
return RenderTargetMTL::Attachment{static_cast<bool>(rb) ? (id<MTLTexture>)(rb.texture->getHandler()) : nil, rb.level};
}
RenderTargetMTL::Attachment RenderTargetMTL::getDepthAttachment() const
{
2021-12-28 11:05:34 +08:00
if(isDefaultRenderTarget())
return {UtilsMTL::getDefaultDepthStencilTexture(), 0};
auto& rb = this->_depth;
return RenderTargetMTL::Attachment{!!rb ? (id<MTLTexture>)(rb.texture->getHandler()) : nil, rb.level};
}
RenderTargetMTL::Attachment RenderTargetMTL::getStencilAttachment() const
{
2021-12-28 11:05:34 +08:00
if(isDefaultRenderTarget())
return RenderTargetMTL::Attachment{UtilsMTL::getDefaultDepthStencilTexture(), 0};
auto& rb = this->_stencil;
return RenderTargetMTL::Attachment{!!rb ? (id<MTLTexture>)(rb.texture->getHandler()) : nil, rb.level};
}
PixelFormat RenderTargetMTL::getColorAttachmentPixelFormat(int index) const
{
// !!!important
// the default framebuffer pixel format is: MTLPixelFormatBGRA8Unorm
2021-12-28 11:05:34 +08:00
if(isDefaultRenderTarget() && index == 0)
return PixelFormat::BGRA8;
auto& rb = this->_color[index];
return rb ? rb.texture->getTextureFormat() : PixelFormat::NONE;
}
PixelFormat RenderTargetMTL::getDepthAttachmentPixelFormat() const
2021-12-28 11:05:34 +08:00
{ // FIXME: adxe only support D24S8
if(bitmask::any(_flags, TargetBufferFlags::DEPTH_AND_STENCIL)) {
if(isDefaultRenderTarget() || !_depth)
return PixelFormat::D24S8;
return _depth.texture->getTextureFormat();
}
return PixelFormat::NONE;
}
PixelFormat RenderTargetMTL::getStencilAttachmentPixelFormat() const
2021-12-28 11:05:34 +08:00
{ // FIXME: adxe only support D24S8
if(bitmask::any(_flags, TargetBufferFlags::DEPTH_AND_STENCIL)) {
if(isDefaultRenderTarget() || !_stencil)
return PixelFormat::D24S8;
return _stencil.texture->getTextureFormat();
}
return PixelFormat::NONE;
}
CC_BACKEND_END