diff options
9 files changed, 738 insertions, 712 deletions
diff --git a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.cpp b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.cpp index 92f042a44..c0b8cdde8 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.cpp @@ -17,9 +17,10 @@ #include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> -#include <dali/internal/graphics/vulkan/vulkan-device.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-view-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h> +#include <dali/internal/graphics/vulkan/vulkan-device.h> #include <dali/integration-api/debug.h> @@ -30,55 +31,55 @@ extern Debug::Filter* gVulkanFilter; namespace Dali::Graphics::Vulkan { -FramebufferAttachment* FramebufferAttachment::NewColorAttachment(ImageView* imageView, +FramebufferAttachment* FramebufferAttachment::NewColorAttachment(ImageView* imageView, vk::ClearColorValue clearColorValue, - bool presentable ) + bool presentable) { - assert( imageView->GetImage()->GetUsageFlags() & vk::ImageUsageFlagBits::eColorAttachment ); + assert(imageView->GetImage()->GetUsageFlags() & vk::ImageUsageFlagBits::eColorAttachment); - auto attachment = new FramebufferAttachment( imageView, - clearColorValue, - AttachmentType::COLOR, - presentable ); + auto attachment = new FramebufferAttachment(imageView, + clearColorValue, + AttachmentType::COLOR, + presentable); return attachment; } FramebufferAttachment* FramebufferAttachment::NewDepthAttachment( - ImageView* imageView, - vk::ClearDepthStencilValue clearDepthStencilValue ) + ImageView* imageView, + vk::ClearDepthStencilValue clearDepthStencilValue) { - assert( imageView->GetImage()->GetUsageFlags() & vk::ImageUsageFlagBits::eDepthStencilAttachment ); + assert(imageView->GetImage()->GetUsageFlags() & vk::ImageUsageFlagBits::eDepthStencilAttachment); - auto attachment = new FramebufferAttachment( imageView, - clearDepthStencilValue, - AttachmentType::DEPTH_STENCIL, - false /* presentable */ ); + auto attachment = new FramebufferAttachment(imageView, + clearDepthStencilValue, + AttachmentType::DEPTH_STENCIL, + false /* presentable */); return attachment; } -FramebufferAttachment::FramebufferAttachment( ImageView* imageView, - vk::ClearValue clearColor, - AttachmentType type, - bool presentable ) -: mImageView( imageView ), - mClearValue( clearColor ), - mType( type ) +FramebufferAttachment::FramebufferAttachment(ImageView* imageView, + vk::ClearValue clearColor, + AttachmentType type, + bool presentable) +: mImageView(imageView), + mClearValue(clearColor), + mType(type) { auto image = imageView->GetImage(); auto sampleCountFlags = image->GetSampleCount(); - mDescription.setSamples( sampleCountFlags ); + mDescription.setSamples(sampleCountFlags); - mDescription.setLoadOp( vk::AttachmentLoadOp::eClear ); - mDescription.setStoreOp( vk::AttachmentStoreOp::eStore ); - mDescription.setStencilLoadOp( vk::AttachmentLoadOp::eClear ); - mDescription.setStencilStoreOp( vk::AttachmentStoreOp::eStore ); - mDescription.setFormat( image->GetFormat() ); - mDescription.setInitialLayout( vk::ImageLayout::eUndefined ); + mDescription.setLoadOp(vk::AttachmentLoadOp::eClear); + mDescription.setStoreOp(vk::AttachmentStoreOp::eStore); + mDescription.setStencilLoadOp(vk::AttachmentLoadOp::eClear); + mDescription.setStencilStoreOp(vk::AttachmentStoreOp::eStore); + mDescription.setFormat(image->GetFormat()); + mDescription.setInitialLayout(vk::ImageLayout::eUndefined); - if( type == AttachmentType::DEPTH_STENCIL ) + if(type == AttachmentType::DEPTH_STENCIL) { mDescription.finalLayout = vk::ImageLayout::eDepthStencilAttachmentOptimal; } @@ -113,24 +114,106 @@ bool FramebufferAttachment::IsValid() const return mImageView; } +// FramebufferImpl ------------------------------- -//FramebufferImpl ------------------------------- -FramebufferImpl::FramebufferImpl( Device& graphicsDevice, - const std::vector< FramebufferAttachment* >& colorAttachments, - FramebufferAttachment* depthAttachment, - vk::Framebuffer vkHandle, - vk::RenderPass renderPass, - uint32_t width, - uint32_t height, - bool externalRenderPass ) -: mGraphicsDevice( &graphicsDevice ), - mWidth( width ), - mHeight( height ), - mColorAttachments( colorAttachments ), - mDepthAttachment( depthAttachment ), - mFramebuffer( vkHandle ), - mRenderPass( renderPass ), - mExternalRenderPass( externalRenderPass ) +FramebufferImpl* FramebufferImpl::New( + Vulkan::Device& device, + RenderPassImpl* renderPass, + std::vector<FramebufferAttachment*>& attachments, + uint32_t width, + uint32_t height, + bool hasDepthAttachments, + bool takeRenderPassOwnership) +{ + std::vector<vk::ImageView> imageViewAttachments; + + std::transform(attachments.cbegin(), + attachments.cend(), + std::back_inserter(imageViewAttachments), + [&](FramebufferAttachment* entry) + { + return entry->GetImageView()->GetVkHandle(); + }); + + auto framebufferCreateInfo = vk::FramebufferCreateInfo{}.setRenderPass(renderPass->GetVkHandle()).setPAttachments(imageViewAttachments.data()).setLayers(1).setWidth(width).setHeight(height).setAttachmentCount(U32(attachments.size())); + + auto vkFramebuffer = VkAssert(device.GetLogicalDevice().createFramebuffer(framebufferCreateInfo, device.GetAllocator())); + + return new FramebufferImpl(device, + attachments, + vkFramebuffer, + renderPass->GetVkHandle(), + width, + height, + hasDepthAttachments, + takeRenderPassOwnership); +} + +FramebufferImpl* FramebufferImpl::New( + Vulkan::Device& device, + RenderPassImpl* renderPass, + const std::vector<FramebufferAttachment*>& colorAttachments, + FramebufferAttachment* depthAttachment, + uint32_t width, + uint32_t height) +{ + assert((!colorAttachments.empty() || depthAttachment) && "Cannot create framebuffer. Please provide at least one attachment"); + + auto colorAttachmentsValid = true; + for(auto& attachment : colorAttachments) + { + if(!attachment->IsValid()) + { + colorAttachmentsValid = false; + break; + } + } + + assert(colorAttachmentsValid && "Invalid color attachment! The attachment has no ImageView"); + + // Flag that indicates if the framebuffer has a depth attachment + auto hasDepth = false; + if(depthAttachment) + { + hasDepth = depthAttachment->IsValid(); + assert(hasDepth && "Invalid depth attachment! The attachment has no ImageView"); + } + + // This vector stores the attachments (vk::ImageViews) + auto attachments = std::vector<FramebufferAttachment*>{}; + + // Flag that indicates if the render pass is externally provided + bool renderPassTakeOwnership = false; + if(renderPass == nullptr) + { + renderPass = RenderPassImpl::New(device, colorAttachments, depthAttachment); + renderPassTakeOwnership = true; + } + attachments.reserve(colorAttachments.size()); + attachments.insert(attachments.begin(), colorAttachments.begin(), colorAttachments.end()); + if(hasDepth) + { + attachments.push_back(depthAttachment); + } + return FramebufferImpl::New(device, renderPass, attachments, width, height, hasDepth, renderPassTakeOwnership); +} + +FramebufferImpl::FramebufferImpl(Device& graphicsDevice, + const std::vector<FramebufferAttachment*>& attachments, + vk::Framebuffer vkHandle, + vk::RenderPass renderPass, + uint32_t width, + uint32_t height, + bool hasDepthAttachment, + bool takeRenderPassOwnership) +: mGraphicsDevice(&graphicsDevice), + mWidth(width), + mHeight(height), + mAttachments(attachments), + mFramebuffer(vkHandle), + mRenderPass(renderPass), + mHasDepthAttachment(hasDepthAttachment), + mRenderPassOwned(takeRenderPassOwnership) { } @@ -144,17 +227,18 @@ uint32_t FramebufferImpl::GetHeight() const return mHeight; } -FramebufferAttachment* FramebufferImpl::GetAttachment( AttachmentType type, uint32_t index ) const +FramebufferAttachment* FramebufferImpl::GetAttachment(AttachmentType type, uint32_t index) const { - switch( type ) + switch(type) { case AttachmentType::COLOR: { - return mColorAttachments[index]; + return mAttachments[index]; } case AttachmentType::DEPTH_STENCIL: { - return mDepthAttachment; + if(mHasDepthAttachment) + return mAttachments.back(); } case AttachmentType::INPUT: case AttachmentType::RESOLVE: @@ -166,21 +250,25 @@ FramebufferAttachment* FramebufferImpl::GetAttachment( AttachmentType type, uint return nullptr; } -std::vector< FramebufferAttachment* > FramebufferImpl::GetAttachments( AttachmentType type ) const +std::vector<FramebufferAttachment*> FramebufferImpl::GetAttachments(AttachmentType type) const { - auto retval = std::vector< FramebufferAttachment* >{}; - switch( type ) + auto retval = std::vector<FramebufferAttachment*>{}; + switch(type) { case AttachmentType::COLOR: { - retval.reserve( mColorAttachments.size() ); - retval.insert( retval.end(), mColorAttachments.begin(), mColorAttachments.end() ); + auto numColorAttachments = mHasDepthAttachment ? mAttachments.size() - 1 : mAttachments.size(); + retval.reserve(numColorAttachments); + retval.insert(retval.end(), mAttachments.begin(), mAttachments.begin() + numColorAttachments); break; } case AttachmentType::DEPTH_STENCIL: { - retval.reserve( 1 ); - retval.push_back( mDepthAttachment ); + if(mHasDepthAttachment) + { + retval.reserve(1); + retval.push_back(mAttachments.back()); + } break; } case AttachmentType::INPUT: @@ -194,17 +282,17 @@ std::vector< FramebufferAttachment* > FramebufferImpl::GetAttachments( Attachmen return retval; } -uint32_t FramebufferImpl::GetAttachmentCount( AttachmentType type ) const +uint32_t FramebufferImpl::GetAttachmentCount(AttachmentType type) const { - switch( type ) + switch(type) { case AttachmentType::COLOR: { - return U32( mColorAttachments.size() ); + return U32(mAttachments.size() - mHasDepthAttachment); } case AttachmentType::DEPTH_STENCIL: { - return mDepthAttachment->IsValid() ? 1u : 0u; + return mHasDepthAttachment; } case AttachmentType::INPUT: case AttachmentType::RESOLVE: @@ -225,53 +313,46 @@ vk::Framebuffer FramebufferImpl::GetVkHandle() const return mFramebuffer; } -std::vector< vk::ClearValue > FramebufferImpl::GetClearValues() const +std::vector<vk::ClearValue> FramebufferImpl::GetClearValues() const { - auto result = std::vector< vk::ClearValue >{}; + auto result = std::vector<vk::ClearValue>{}; - std::transform( mColorAttachments.begin(), // @todo & color clear enabled - mColorAttachments.end(), - std::back_inserter( result ), - []( FramebufferAttachment* attachment ) { - return attachment->GetClearValue(); - } ); - - if( mDepthAttachment && mDepthAttachment->IsValid() ) // @todo & depth clear enabled - { - result.push_back( mDepthAttachment->GetClearValue() ); - } + std::transform(mAttachments.begin(), // @todo & color clear enabled / depth clear enabled + mAttachments.end(), + std::back_inserter(result), + [](FramebufferAttachment* attachment) + { + return attachment->GetClearValue(); + }); return result; } bool FramebufferImpl::OnDestroy() { - auto device = mGraphicsDevice->GetLogicalDevice(); + auto device = mGraphicsDevice->GetLogicalDevice(); auto frameBuffer = mFramebuffer; - vk::RenderPass renderPass = mExternalRenderPass ? vk::RenderPass{} : mRenderPass; + vk::RenderPass renderPass = mRenderPassOwned ? mRenderPass : vk::RenderPass{}; auto allocator = &mGraphicsDevice->GetAllocator(); - mGraphicsDevice->DiscardResource( [ device, frameBuffer, renderPass, allocator ]() { - - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Invoking deleter function: framebuffer->%p\n", - static_cast< VkFramebuffer >(frameBuffer) ) - device.destroyFramebuffer( frameBuffer, allocator ); - - if( renderPass ) - { - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Invoking deleter function: render pass->%p\n", - static_cast< VkRenderPass >(renderPass) ) - device.destroyRenderPass( renderPass, allocator ); - } + mGraphicsDevice->DiscardResource([device, frameBuffer, renderPass, allocator]() + { + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Invoking deleter function: framebuffer->%p\n", static_cast<VkFramebuffer>(frameBuffer)) + device.destroyFramebuffer(frameBuffer, allocator); - } ); + if(renderPass) + { + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Invoking deleter function: render pass->%p\n", static_cast<VkRenderPass>(renderPass)) + device.destroyRenderPass(renderPass, allocator); + } + }); return false; } -} // Namespace Vulkan +} // namespace Dali::Graphics::Vulkan // Namespace Graphics diff --git a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h index fbee25a2e..e0ccee562 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h +++ b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h @@ -22,6 +22,7 @@ namespace Dali::Graphics::Vulkan { +class RenderPassImpl; enum class AttachmentType { @@ -38,17 +39,17 @@ class Device; class FramebufferAttachment : public VkManaged { public: - FramebufferAttachment(ImageView* imageView, + FramebufferAttachment(ImageView* imageView, vk::ClearValue clearColor, AttachmentType type, - bool presentable); + bool presentable); - static FramebufferAttachment* NewColorAttachment( ImageView* imageView, + static FramebufferAttachment* NewColorAttachment(ImageView* imageView, vk::ClearColorValue clearColorValue, - bool presentable ); + bool presentable); - static FramebufferAttachment* NewDepthAttachment( ImageView* imageView, - vk::ClearDepthStencilValue clearDepthStencilValue ); + static FramebufferAttachment* NewDepthAttachment(ImageView* imageView, + vk::ClearDepthStencilValue clearDepthStencilValue); [[nodiscard]] ImageView* GetImageView() const; @@ -63,10 +64,10 @@ public: private: FramebufferAttachment() = default; - ImageView* mImageView{nullptr}; + ImageView* mImageView{nullptr}; vk::AttachmentDescription mDescription; - vk::ClearValue mClearValue; - AttachmentType mType{AttachmentType::UNDEFINED}; + vk::ClearValue mClearValue; + AttachmentType mType{AttachmentType::UNDEFINED}; }; /** @@ -78,30 +79,47 @@ private: class FramebufferImpl : public VkManaged { public: - FramebufferImpl(Device& graphicsDevice, - const std::vector<FramebufferAttachment*>& colorAttachments, - FramebufferAttachment* depthAttachment, - vk::Framebuffer vkHandle, - vk::RenderPass renderPass, - uint32_t width, - uint32_t height, - bool externalRenderPass = false ); + static FramebufferImpl* New( + Vulkan::Device& device, + RenderPassImpl* renderPass, + std::vector<FramebufferAttachment*>& attachments, + uint32_t width, + uint32_t height, + bool hasDepthAttachment, + bool takeRenderPassOwnership); + + static FramebufferImpl* New( + Vulkan::Device& device, + RenderPassImpl* renderPass, + const std::vector<FramebufferAttachment*>& colorAttachments, + FramebufferAttachment* depthAttachment, + uint32_t width, + uint32_t height); + + FramebufferImpl(Device& graphicsDevice, + const std::vector<FramebufferAttachment*>& attachments, + vk::Framebuffer vkHandle, + vk::RenderPass renderPass, + uint32_t width, + uint32_t height, + bool hasDepthAttachment, + bool takeRenderPassOwnership); [[nodiscard]] uint32_t GetWidth() const; [[nodiscard]] uint32_t GetHeight() const; - [[nodiscard]] FramebufferAttachment* GetAttachment( AttachmentType type, uint32_t index ) const; + [[nodiscard]] FramebufferAttachment* GetAttachment(AttachmentType type, uint32_t index) const; - [[nodiscard]] std::vector<FramebufferAttachment*> GetAttachments( AttachmentType type ) const; + [[nodiscard]] std::vector<FramebufferAttachment*> GetAttachments(AttachmentType type) const; - [[nodiscard]] uint32_t GetAttachmentCount( AttachmentType type ) const; + [[nodiscard]] uint32_t GetAttachmentCount(AttachmentType type) const; [[nodiscard]] vk::RenderPass GetRenderPass() const; [[nodiscard]] vk::Framebuffer GetVkHandle() const; - [[nodiscard]] std::vector< vk::ClearValue > GetClearValues() const; + [[nodiscard]] std::vector<vk::ClearValue> GetClearValues() const; bool OnDestroy() override; @@ -111,14 +129,13 @@ private: uint32_t mWidth; uint32_t mHeight; - std::vector<FramebufferAttachment*> mColorAttachments; - FramebufferAttachment* mDepthAttachment; - vk::Framebuffer mFramebuffer; - vk::RenderPass mRenderPass; - bool mExternalRenderPass; + std::vector<FramebufferAttachment*> mAttachments; + vk::Framebuffer mFramebuffer; + vk::RenderPass mRenderPass; + bool mHasDepthAttachment{false}; + bool mRenderPassOwned{false}; }; } // Namespace Dali::Graphics::Vulkan - #endif // DALI_INTERNAL_GRAPHICS_VULKAN_FRAMEBUFFER_IMPL_H diff --git a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer.cpp b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer.cpp index 6498a5f76..a98e484d2 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-framebuffer.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-framebuffer.cpp @@ -17,15 +17,20 @@ #include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-render-pass.h> + namespace Dali { namespace Graphics { namespace Vulkan { - Framebuffer::Framebuffer(const FramebufferCreateInfo& createInfo, VulkanGraphicsController& controller) -: Resource(createInfo, controller) +: Resource(createInfo, controller), + mFramebufferImpl{nullptr} { // mController.AddFramebuffer(*this) } @@ -34,7 +39,29 @@ Framebuffer::~Framebuffer() = default; bool Framebuffer::InitializeResource() { - // @todo Create the framebuffer !! + /* + * Renderpass handling. + * We get passed VulkanRenderPass + * For actual framebuffer creation, we need at least the first VulkanRenderPass to have a VulkanRenderPassImpl created + * and for subsequent VulkanRenderPasses to be compatible with the first (and can be created on the fly) + */ + + // Create attachments + auto renderPass = static_cast<Vulkan::RenderPass*>(mCreateInfo.renderPasses[0]); + + auto renderPassImpl = renderPass->GetImpl(); // Only generate actual render pass if needed + if(!renderPassImpl) + { + renderPass->InitializeResource(); + } + + auto& device = mController.GetGraphicsDevice(); + std::vector<FramebufferAttachment*> colorAttachments; + FramebufferAttachment* depthStencilAttachment{nullptr}; + //@todo FINISH ME! (Needs texture -> image view bindings) + mFramebufferImpl = FramebufferImpl::New(device, renderPassImpl, colorAttachments, depthStencilAttachment, mCreateInfo.size.width, mCreateInfo.size.height); + + //@todo Store all the render passes here. Will be used later to generate compatible render pass impls. return true; } @@ -48,4 +75,4 @@ void Framebuffer::DiscardResource() } // namespace Vulkan } // namespace Graphics -} // namespace Dali
\ No newline at end of file +} // namespace Dali diff --git a/dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.cpp b/dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.cpp index abad4033f..3696eaa2e 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.cpp @@ -270,7 +270,11 @@ UniquePtr<Graphics::RenderPass> VulkanGraphicsController::CreateRenderPass(const // But, we want to create multiple render passes in Core on a scene's surface... // Now, renderPassCreateInfo contains renderTarget, so this implementation can decide to generate // surface's swapchain framebuffers based on this new renderpass. Though, should be explicit about it! - return NewObject<Vulkan::RenderPass>(renderPassCreateInfo, *this, std::move(oldRenderPass)); + auto renderPass = NewObject<Vulkan::RenderPass>(renderPassCreateInfo, *this, std::move(oldRenderPass)); + + //auto vkRenderPass = static_cast<Vulkan::RenderPass*>(renderPass.get()); + //vkRenderPass->InitializeResource(); // This may create an actual resource. + return renderPass; } UniquePtr<Graphics::Buffer> VulkanGraphicsController::CreateBuffer(const Graphics::BufferCreateInfo& bufferCreateInfo, UniquePtr<Graphics::Buffer>&& oldBuffer) diff --git a/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.cpp b/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.cpp index 5bdf2757a..2d3d40a6f 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.cpp @@ -19,8 +19,8 @@ #include <dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.h> #include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-image-view-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-image-view-impl.h> #include <dali/internal/graphics/vulkan/vulkan-device.h> #include <dali/integration-api/debug.h> @@ -31,137 +31,115 @@ extern Debug::Filter* gVulkanFilter; namespace Dali::Graphics::Vulkan { - -namespace { - +namespace +{ vk::RenderPass CreateCompatibleRenderPass( - Vulkan::Device& device, - const std::vector< FramebufferAttachment* >& colorAttachments, - FramebufferAttachment* depthAttachment, - std::vector< vk::ImageView >& attachments) + Vulkan::Device& device, + const std::vector<FramebufferAttachment*>& colorAttachments, + FramebufferAttachment* depthAttachment, + std::vector<vk::ImageView>& attachments) { auto hasDepth = false; - if( depthAttachment ) + if(depthAttachment) { hasDepth = depthAttachment->IsValid(); - assert( hasDepth && "Invalid depth attachment! The attachment has no ImageView" ); + assert(hasDepth && "Invalid depth attachment! The attachment has no ImageView"); } // The total number of attachments auto totalAttachmentCount = hasDepth ? colorAttachments.size() + 1 : colorAttachments.size(); attachments.clear(); - attachments.reserve( totalAttachmentCount ); + attachments.reserve(totalAttachmentCount); // This vector stores the attachment references - auto colorAttachmentReferences = std::vector< vk::AttachmentReference >{}; - colorAttachmentReferences.reserve( colorAttachments.size() ); + auto colorAttachmentReferences = std::vector<vk::AttachmentReference>{}; + colorAttachmentReferences.reserve(colorAttachments.size()); // This vector stores the attachment descriptions - auto attachmentDescriptions = std::vector< vk::AttachmentDescription >{}; - attachmentDescriptions.reserve( totalAttachmentCount ); + auto attachmentDescriptions = std::vector<vk::AttachmentDescription>{}; + attachmentDescriptions.reserve(totalAttachmentCount); // For each color attachment... - for( auto i = 0u; i < colorAttachments.size(); ++i ) + for(auto i = 0u; i < colorAttachments.size(); ++i) { // Get the image layout auto imageLayout = colorAttachments[i]->GetImageView()->GetImage()->GetImageLayout(); // If the layout is undefined... - if( imageLayout == vk::ImageLayout::eUndefined ) + if(imageLayout == vk::ImageLayout::eUndefined) { // Set it to color attachment optimal imageLayout = vk::ImageLayout::eColorAttachmentOptimal; } // Any other case should be invalid - assert( imageLayout == vk::ImageLayout::eColorAttachmentOptimal ); + assert(imageLayout == vk::ImageLayout::eColorAttachmentOptimal); // Add a reference and a descriptions and image views to their respective vectors - colorAttachmentReferences.push_back( vk::AttachmentReference{}.setLayout( imageLayout ) - .setAttachment( U32( i ) ) ); + colorAttachmentReferences.push_back(vk::AttachmentReference{}.setLayout(imageLayout).setAttachment(U32(i))); - attachmentDescriptions.push_back( colorAttachments[i]->GetDescription() ); + attachmentDescriptions.push_back(colorAttachments[i]->GetDescription()); - attachments.push_back( colorAttachments[i]->GetImageView()->GetVkHandle() ); + attachments.push_back(colorAttachments[i]->GetImageView()->GetVkHandle()); } - // Follow the exact same procedure as color attachments auto depthAttachmentReference = vk::AttachmentReference{}; - if( hasDepth ) + if(hasDepth) { auto imageLayout = depthAttachment->GetImageView()->GetImage()->GetImageLayout(); - if( imageLayout == vk::ImageLayout::eUndefined ) + if(imageLayout == vk::ImageLayout::eUndefined) { imageLayout = vk::ImageLayout::eDepthStencilAttachmentOptimal; } - assert( imageLayout == vk::ImageLayout::eDepthStencilAttachmentOptimal ); + assert(imageLayout == vk::ImageLayout::eDepthStencilAttachmentOptimal); - depthAttachmentReference.setLayout( imageLayout ); - depthAttachmentReference.setAttachment( U32( colorAttachmentReferences.size() ) ); + depthAttachmentReference.setLayout(imageLayout); + depthAttachmentReference.setAttachment(U32(colorAttachmentReferences.size())); - attachmentDescriptions.push_back( depthAttachment->GetDescription() ); + attachmentDescriptions.push_back(depthAttachment->GetDescription()); - attachments.push_back( depthAttachment->GetImageView()->GetVkHandle() ); + attachments.push_back(depthAttachment->GetImageView()->GetVkHandle()); } // Creating a single subpass per framebuffer auto subpassDesc = vk::SubpassDescription{}; - subpassDesc.setPipelineBindPoint( vk::PipelineBindPoint::eGraphics ); - subpassDesc.setColorAttachmentCount( U32( colorAttachments.size())); - if( hasDepth ) + subpassDesc.setPipelineBindPoint(vk::PipelineBindPoint::eGraphics); + subpassDesc.setColorAttachmentCount(U32(colorAttachments.size())); + if(hasDepth) { - subpassDesc.setPDepthStencilAttachment( &depthAttachmentReference ); + subpassDesc.setPDepthStencilAttachment(&depthAttachmentReference); } - subpassDesc.setPColorAttachments( colorAttachmentReferences.data() ); + subpassDesc.setPColorAttachments(colorAttachmentReferences.data()); // Creating 2 subpass dependencies using VK_SUBPASS_EXTERNAL to leverage the implicit image layout // transitions provided by the driver - std::array< vk::SubpassDependency, 2 > subpassDependencies{ - - vk::SubpassDependency{}.setSrcSubpass( VK_SUBPASS_EXTERNAL ) - .setDstSubpass( 0 ) - .setSrcStageMask( vk::PipelineStageFlagBits::eBottomOfPipe ) - .setDstStageMask( vk::PipelineStageFlagBits::eColorAttachmentOutput ) - .setSrcAccessMask( vk::AccessFlagBits::eMemoryRead ) - .setDstAccessMask( vk::AccessFlagBits::eColorAttachmentRead | - vk::AccessFlagBits::eColorAttachmentWrite ) - .setDependencyFlags( vk::DependencyFlagBits::eByRegion ), - - vk::SubpassDependency{}.setSrcSubpass( 0 ) - .setDstSubpass( VK_SUBPASS_EXTERNAL ) - .setSrcStageMask( vk::PipelineStageFlagBits::eColorAttachmentOutput ) - .setDstStageMask( vk::PipelineStageFlagBits::eBottomOfPipe ) - .setSrcAccessMask( vk::AccessFlagBits::eColorAttachmentRead | - vk::AccessFlagBits::eColorAttachmentWrite ) - .setDstAccessMask( vk::AccessFlagBits::eMemoryRead ) - .setDependencyFlags( vk::DependencyFlagBits::eByRegion ) + std::array<vk::SubpassDependency, 2> subpassDependencies{ + + vk::SubpassDependency{}.setSrcSubpass(VK_SUBPASS_EXTERNAL).setDstSubpass(0).setSrcStageMask(vk::PipelineStageFlagBits::eBottomOfPipe).setDstStageMask(vk::PipelineStageFlagBits::eColorAttachmentOutput).setSrcAccessMask(vk::AccessFlagBits::eMemoryRead).setDstAccessMask(vk::AccessFlagBits::eColorAttachmentRead | vk::AccessFlagBits::eColorAttachmentWrite).setDependencyFlags(vk::DependencyFlagBits::eByRegion), + + vk::SubpassDependency{}.setSrcSubpass(0).setDstSubpass(VK_SUBPASS_EXTERNAL).setSrcStageMask(vk::PipelineStageFlagBits::eColorAttachmentOutput).setDstStageMask(vk::PipelineStageFlagBits::eBottomOfPipe).setSrcAccessMask(vk::AccessFlagBits::eColorAttachmentRead | vk::AccessFlagBits::eColorAttachmentWrite).setDstAccessMask(vk::AccessFlagBits::eMemoryRead).setDependencyFlags(vk::DependencyFlagBits::eByRegion) }; // Create the render pass - auto renderPassCreateInfo = vk::RenderPassCreateInfo{}.setAttachmentCount( U32( attachmentDescriptions.size() ) ) - .setPAttachments( attachmentDescriptions.data() ) - .setPSubpasses( &subpassDesc ) - .setSubpassCount( 1 ) - .setPDependencies( subpassDependencies.data() ); + auto renderPassCreateInfo = vk::RenderPassCreateInfo{}.setAttachmentCount(U32(attachmentDescriptions.size())).setPAttachments(attachmentDescriptions.data()).setPSubpasses(&subpassDesc).setSubpassCount(1).setPDependencies(subpassDependencies.data()); - auto vkRenderPass = VkAssert(device.GetLogicalDevice().createRenderPass( renderPassCreateInfo, device.GetAllocator())); + auto vkRenderPass = VkAssert(device.GetLogicalDevice().createRenderPass(renderPassCreateInfo, device.GetAllocator())); return vkRenderPass; } } // namespace - -RenderPassImpl* RenderPassImpl::NewRenderPass( - Vulkan::Device& device, - const std::vector< FramebufferAttachment* >& colorAttachments, - FramebufferAttachment* depthAttachment) +RenderPassImpl* RenderPassImpl::New( + Vulkan::Device& device, + const std::vector<FramebufferAttachment*>& colorAttachments, + FramebufferAttachment* depthAttachment) { - std::vector< vk::ImageView > attachments{}; - auto vkRenderPass = CreateCompatibleRenderPass(device, colorAttachments, depthAttachment, attachments); + std::vector<vk::ImageView> attachments{}; + auto vkRenderPass = CreateCompatibleRenderPass(device, colorAttachments, depthAttachment, attachments); auto renderPass = new RenderPassImpl(device, vkRenderPass); renderPass->SetAttachments(attachments); @@ -174,11 +152,12 @@ RenderPassImpl::RenderPassImpl(Vulkan::Device& device, vk::RenderPass renderPass { } -RenderPassImpl::RenderPassImpl(const Graphics::RenderPassCreateInfo& createInfo, - VulkanGraphicsController& controller, - std::vector<FramebufferAttachment*>& colorAttachments, - FramebufferAttachment* depthAttachment) -: mGraphicsDevice(&controller.GetGraphicsDevice()) +RenderPassImpl::RenderPassImpl( + Vulkan::Device& device, + const Graphics::RenderPassCreateInfo& createInfo, + std::vector<FramebufferAttachment*>& colorAttachments, + FramebufferAttachment* depthAttachment) +: mGraphicsDevice(&device) { // @todo Do mostly as CreateCompatibleRenderPass above, but instead, get the attachment // descriptions from the createInfo passed in here. @@ -194,29 +173,29 @@ vk::RenderPass RenderPassImpl::GetVkHandle() bool RenderPassImpl::OnDestroy() { - if( mVkRenderPass ) + if(mVkRenderPass) { - auto device = mGraphicsDevice->GetLogicalDevice(); - auto allocator = &mGraphicsDevice->GetAllocator(); + auto device = mGraphicsDevice->GetLogicalDevice(); + auto allocator = &mGraphicsDevice->GetAllocator(); auto renderPass = mVkRenderPass; - mGraphicsDevice->DiscardResource( [ device, renderPass, allocator ]() { - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Invoking deleter function: swap chain->%p\n", - static_cast< VkRenderPass >(renderPass) ) - device.destroyRenderPass( renderPass, allocator ); - } ); + mGraphicsDevice->DiscardResource([device, renderPass, allocator]() + { + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Invoking deleter function: swap chain->%p\n", static_cast<VkRenderPass>(renderPass)) + device.destroyRenderPass(renderPass, allocator); }); mVkRenderPass = nullptr; } return false; } -std::vector< vk::ImageView >& RenderPassImpl::GetAttachments() +std::vector<vk::ImageView>& RenderPassImpl::GetAttachments() { return mAttachments; } -void RenderPassImpl::SetAttachments(std::vector< vk::ImageView >& attachments) +void RenderPassImpl::SetAttachments(std::vector<vk::ImageView>& attachments) { + // @todo Remove? How can we late bind attachments? Recreate the whole RP? mAttachments = std::move(attachments); } diff --git a/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h b/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h index 50d5c8814..58630a650 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h +++ b/dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h @@ -17,9 +17,9 @@ * limitations under the License. */ +#include <dali/graphics-api/graphics-render-pass-create-info.h> #include <dali/internal/graphics/vulkan-impl/vulkan-types.h> #include <dali/public-api/common/vector-wrapper.h> -#include <dali/graphics-api/graphics-render-pass-create-info.h> namespace Dali::Graphics::Vulkan { @@ -30,32 +30,30 @@ class RenderTarget; class RenderPassImpl final : public Dali::Graphics::Vulkan::VkManaged { public: - static RenderPassImpl* NewRenderPass( - Vulkan::Device& device, + static RenderPassImpl* New( + Vulkan::Device& device, const std::vector<FramebufferAttachment*>& colorAttachments, - FramebufferAttachment* depthAttachment); + FramebufferAttachment* depthAttachment); RenderPassImpl(Vulkan::Device& device, vk::RenderPass renderPass); - RenderPassImpl(const Graphics::RenderPassCreateInfo& createInfo, VulkanGraphicsController& controller, - std::vector<FramebufferAttachment*>& colorAttachments, FramebufferAttachment* depthAttachment); + RenderPassImpl(Vulkan::Device& device, const Graphics::RenderPassCreateInfo& createInfo, std::vector<FramebufferAttachment*>& colorAttachments, FramebufferAttachment* depthAttachment); ~RenderPassImpl() override; vk::RenderPass GetVkHandle(); - std::vector< vk::ImageView >& GetAttachments(); + std::vector<vk::ImageView>& GetAttachments(); - void SetAttachments(std::vector< vk::ImageView >& attachments); + void SetAttachments(std::vector<vk::ImageView>& attachments); bool OnDestroy() override; private: - Device* mGraphicsDevice; - vk::RenderPass mVkRenderPass; - std::vector< vk::ImageView > mAttachments{}; + Device* mGraphicsDevice; + vk::RenderPass mVkRenderPass; + std::vector<vk::ImageView> mAttachments{}; }; } // namespace Dali::Graphics::Vulkan - -#endif //DALI_INTERNAL_GRAPHICS_VULKAN_RENDER_PASS_IMPL_H +#endif // DALI_INTERNAL_GRAPHICS_VULKAN_RENDER_PASS_IMPL_H diff --git a/dali/internal/graphics/vulkan-impl/vulkan-render-pass.cpp b/dali/internal/graphics/vulkan-impl/vulkan-render-pass.cpp index 44947ce8d..b2f8fafa9 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-render-pass.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-render-pass.cpp @@ -14,14 +14,13 @@ * limitations under the License. */ - #include <dali/internal/graphics/vulkan-impl/vulkan-render-pass.h> #include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-graphics-controller.h> #include <dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-render-target.h> - namespace Dali::Graphics::Vulkan { RenderPass::RenderPass(const Graphics::RenderPassCreateInfo& createInfo, VulkanGraphicsController& controller) @@ -35,19 +34,30 @@ RenderPass::~RenderPass() = default; bool RenderPass::InitializeResource() { auto renderTarget = static_cast<RenderTarget*>(mCreateInfo.renderTarget); - auto framebuffer = renderTarget->GetFramebuffer(); - DALI_ASSERT_ALWAYS(framebuffer); - auto vkFramebuffer = framebuffer->GetImpl(); + auto framebuffer = renderTarget->GetFramebuffer(); + if(framebuffer) + { + auto vkFramebuffer = framebuffer->GetImpl(); - // Hmmm... VkFramebuffer needs a render pass... (or does it now?!) - // - // At any rate, we want to generate render passes for surface without generating fbos - // for surface swapchain images; then in RenderTarget initialization, auto-generate fbos - // against compatible render passes. So. - std::vector<FramebufferAttachment*> colorAttachments = vkFramebuffer->GetAttachments(AttachmentType::COLOR);; - std::vector<FramebufferAttachment*> depthAttachment = vkFramebuffer->GetAttachments(AttachmentType::DEPTH_STENCIL);; + // Note, Vulkan framebuffer can now be used with compatible render passes in vkBeginRenderPass. + // So we can create multiple render passes. - mRenderPassImpl = new RenderPassImpl(mCreateInfo, mController, colorAttachments, depthAttachment[0]); + std::vector<FramebufferAttachment*> colorAttachments = vkFramebuffer->GetAttachments(AttachmentType::COLOR); + ; + std::vector<FramebufferAttachment*> depthAttachment = vkFramebuffer->GetAttachments(AttachmentType::DEPTH_STENCIL); + ; + + mRenderPassImpl = new RenderPassImpl(mController.GetGraphicsDevice(), mCreateInfo, colorAttachments, depthAttachment[0]); + } + else + { + // RenderTarget must be a surface. + // Create a new render pass that's compatible with the surface's framebuffer. + // + // Does that mean it has to use the fbo's color attachment? YES. + // I.e. should we generate separate RenderPassImpls for each of the surface's framebuffers? + // GetImpl() then needs bufferIndex + } return true; } @@ -64,4 +74,4 @@ RenderPassImpl* RenderPass::GetImpl() return mRenderPassImpl; } -} +} // namespace Dali::Graphics::Vulkan diff --git a/dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.cpp b/dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.cpp index d1080b13d..d9f98f051 100644 --- a/dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.cpp +++ b/dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.cpp @@ -16,17 +16,17 @@ */ // INTERNAL INCLUDES -#include <dali/internal/graphics/vulkan/vulkan-device.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-surface-impl.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-fence-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-surface-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.h> +#include <dali/internal/graphics/vulkan/vulkan-device.h> #if 0 -#include <dali/internal/graphics/vulkan-impl/vulkan-image.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-debug.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-view.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-image.h> #include <dali/internal/graphics/vulkan-impl/vulkan-queue.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-debug.h> #endif #include <dali/integration-api/debug.h> @@ -37,7 +37,6 @@ extern Debug::Filter* gVulkanFilter; namespace Dali::Graphics::Vulkan { - namespace { const auto MAX_SWAPCHAIN_RESOURCE_BUFFERS = 2u; @@ -48,7 +47,7 @@ const auto MAX_SWAPCHAIN_RESOURCE_BUFFERS = 2u; */ struct SwapchainBuffer { - SwapchainBuffer( Device& _graphicsDevice ); + SwapchainBuffer(Device& _graphicsDevice); ~SwapchainBuffer(); @@ -68,10 +67,10 @@ struct SwapchainBuffer }; SwapchainBuffer::SwapchainBuffer(Device& graphicsDevice_) -: graphicsDevice( graphicsDevice_ ) +: graphicsDevice(graphicsDevice_) { - acquireNextImageSemaphore = graphicsDevice.GetLogicalDevice().createSemaphore( {}, graphicsDevice.GetAllocator() ).value; - submitSemaphore = graphicsDevice.GetLogicalDevice().createSemaphore( {}, graphicsDevice.GetAllocator() ).value; + acquireNextImageSemaphore = graphicsDevice.GetLogicalDevice().createSemaphore({}, graphicsDevice.GetAllocator()).value; + submitSemaphore = graphicsDevice.GetLogicalDevice().createSemaphore({}, graphicsDevice.GetAllocator()).value; endOfFrameFence = graphicsDevice.CreateFence({}); } @@ -81,18 +80,18 @@ SwapchainBuffer::~SwapchainBuffer() // swapchain dies so make sure semaphore are not in use anymore auto result = graphicsDevice.GetLogicalDevice().waitIdle(); assert(result == vk::Result::eSuccess); - graphicsDevice.GetLogicalDevice().destroySemaphore( acquireNextImageSemaphore, graphicsDevice.GetAllocator() ); - graphicsDevice.GetLogicalDevice().destroySemaphore( submitSemaphore, graphicsDevice.GetAllocator() ); + graphicsDevice.GetLogicalDevice().destroySemaphore(acquireNextImageSemaphore, graphicsDevice.GetAllocator()); + graphicsDevice.GetLogicalDevice().destroySemaphore(submitSemaphore, graphicsDevice.GetAllocator()); } Swapchain* Swapchain::NewSwapchain( - Device& device, - Queue& presentationQueue, - vk::SwapchainKHR oldSwapchain, - SurfaceImpl* surface, - vk::Format requestedFormat, + Device& device, + Queue& presentationQueue, + vk::SwapchainKHR oldSwapchain, + SurfaceImpl* surface, + vk::Format requestedFormat, vk::PresentModeKHR presentMode, - uint32_t bufferCount) + uint32_t bufferCount) { auto swapchain = new Swapchain(device, presentationQueue); swapchain->CreateVkSwapchain(oldSwapchain, surface, requestedFormat, presentMode, bufferCount); @@ -100,8 +99,8 @@ Swapchain* Swapchain::NewSwapchain( } Swapchain::Swapchain(Device& graphicsDevice, Queue& presentationQueue) -: mGraphicsDevice( graphicsDevice ), - mQueue( &presentationQueue ), +: mGraphicsDevice(graphicsDevice), + mQueue(&presentationQueue), mSwapchainKHR(nullptr), mIsValid(false) { @@ -110,14 +109,14 @@ Swapchain::Swapchain(Device& graphicsDevice, Queue& presentationQueue) Swapchain::~Swapchain() = default; void Swapchain::CreateVkSwapchain( - vk::SwapchainKHR oldSwapchain, - SurfaceImpl* surface, - vk::Format requestedFormat, + vk::SwapchainKHR oldSwapchain, + SurfaceImpl* surface, + vk::Format requestedFormat, vk::PresentModeKHR presentMode, - uint32_t bufferCount) + uint32_t bufferCount) { mSurface = surface; - vk::Format swapchainImageFormat{}; + vk::Format swapchainImageFormat{}; vk::ColorSpaceKHR swapchainColorSpace{}; surface->GetSupportedFormats(requestedFormat, swapchainImageFormat, swapchainColorSpace); @@ -131,16 +130,15 @@ void Swapchain::CreateVkSwapchain( auto compositeAlpha = vk::CompositeAlphaFlagBitsKHR{}; // Simply select the first composite alpha format available - auto compositeAlphaFlags = std::vector< vk::CompositeAlphaFlagBitsKHR >{ - vk::CompositeAlphaFlagBitsKHR::eOpaque, - vk::CompositeAlphaFlagBitsKHR::ePreMultiplied, - vk::CompositeAlphaFlagBitsKHR::ePostMultiplied, - vk::CompositeAlphaFlagBitsKHR::eInherit - }; - - for( const auto& compositeAlphaFlag : compositeAlphaFlags ) + auto compositeAlphaFlags = std::vector<vk::CompositeAlphaFlagBitsKHR>{ + vk::CompositeAlphaFlagBitsKHR::eOpaque, + vk::CompositeAlphaFlagBitsKHR::ePreMultiplied, + vk::CompositeAlphaFlagBitsKHR::ePostMultiplied, + vk::CompositeAlphaFlagBitsKHR::eInherit}; + + for(const auto& compositeAlphaFlag : compositeAlphaFlags) { - if( surfaceCapabilities.supportedCompositeAlpha & compositeAlphaFlag ) + if(surfaceCapabilities.supportedCompositeAlpha & compositeAlphaFlag) { compositeAlpha = compositeAlphaFlag; break; @@ -148,15 +146,15 @@ void Swapchain::CreateVkSwapchain( } // Determine the number of images - if (surfaceCapabilities.minImageCount > 0 && - bufferCount > surfaceCapabilities.minImageCount ) + if(surfaceCapabilities.minImageCount > 0 && + bufferCount > surfaceCapabilities.minImageCount) { - bufferCount = surfaceCapabilities.minImageCount; + bufferCount = surfaceCapabilities.minImageCount; } // Find the transformation of the surface vk::SurfaceTransformFlagBitsKHR preTransform; - if( surfaceCapabilities.supportedTransforms & vk::SurfaceTransformFlagBitsKHR::eIdentity ) + if(surfaceCapabilities.supportedTransforms & vk::SurfaceTransformFlagBitsKHR::eIdentity) { // We prefer a non-rotated transform preTransform = vk::SurfaceTransformFlagBitsKHR::eIdentity; @@ -167,13 +165,14 @@ void Swapchain::CreateVkSwapchain( } auto presentModes = surface->GetSurfacePresentModes(); - auto found = std::find_if( presentModes.begin(), - presentModes.end(), - [ & ]( vk::PresentModeKHR mode ) { - return presentMode == mode; - } ); - - if( found == presentModes.end() ) + auto found = std::find_if(presentModes.begin(), + presentModes.end(), + [&](vk::PresentModeKHR mode) + { + return presentMode == mode; + }); + + if(found == presentModes.end()) { // Requested present mode not supported. Default to FIFO. FIFO is always supported as per spec. presentMode = vk::PresentModeKHR::eFifo; @@ -181,55 +180,54 @@ void Swapchain::CreateVkSwapchain( // Creation settings have been determined. Fill in the create info struct. mSwapchainCreateInfoKHR - .setSurface( surface->GetVkHandle() ) - .setPreTransform( preTransform ) - .setPresentMode( presentMode ) - .setOldSwapchain( oldSwapchain ) - .setMinImageCount( bufferCount ) - .setImageUsage( vk::ImageUsageFlagBits::eColorAttachment ) - .setImageSharingMode( vk::SharingMode::eExclusive ) - .setImageArrayLayers( 1 ) - .setImageColorSpace( swapchainColorSpace ) - .setImageFormat( swapchainImageFormat ) - .setImageExtent( swapchainExtent ) - .setCompositeAlpha( compositeAlpha ) - .setClipped( static_cast<vk::Bool32>(true) ) - .setQueueFamilyIndexCount( 0 ) - .setPQueueFamilyIndices( nullptr ); + .setSurface(surface->GetVkHandle()) + .setPreTransform(preTransform) + .setPresentMode(presentMode) + .setOldSwapchain(oldSwapchain) + .setMinImageCount(bufferCount) + .setImageUsage(vk::ImageUsageFlagBits::eColorAttachment) + .setImageSharingMode(vk::SharingMode::eExclusive) + .setImageArrayLayers(1) + .setImageColorSpace(swapchainColorSpace) + .setImageFormat(swapchainImageFormat) + .setImageExtent(swapchainExtent) + .setCompositeAlpha(compositeAlpha) + .setClipped(static_cast<vk::Bool32>(true)) + .setQueueFamilyIndexCount(0) + .setPQueueFamilyIndices(nullptr); // Create the swap chain mSwapchainKHR = VkAssert(mGraphicsDevice.GetLogicalDevice().createSwapchainKHR(mSwapchainCreateInfoKHR, mGraphicsDevice.GetAllocator())); } - void Swapchain::CreateFramebuffers() { assert(mSwapchainKHR && "Needs a swapchain before creating framebuffers"); // pull images and create Framebuffers - auto images = VkAssert( mGraphicsDevice.GetLogicalDevice().getSwapchainImagesKHR( mSwapchainKHR ) ); + auto images = VkAssert(mGraphicsDevice.GetLogicalDevice().getSwapchainImagesKHR(mSwapchainKHR)); auto surfaceCapabilities = mSurface->GetCapabilities(); // number of images must match requested buffering mode - if( images.size() < surfaceCapabilities.minImageCount ) + if(images.size() < surfaceCapabilities.minImageCount) { - DALI_LOG_STREAM( gVulkanFilter, - Debug::General, - "Swapchain creation failed: Swapchain images are less than the requested amount" ); - mGraphicsDevice.GetLogicalDevice().destroySwapchainKHR( mSwapchainKHR ); + DALI_LOG_STREAM(gVulkanFilter, + Debug::General, + "Swapchain creation failed: Swapchain images are less than the requested amount"); + mGraphicsDevice.GetLogicalDevice().destroySwapchainKHR(mSwapchainKHR); mSwapchainKHR = nullptr; return; } mFramebuffers.clear(); - mFramebuffers.reserve( images.size() ); + mFramebuffers.reserve(images.size()); - auto clearColor = vk::ClearColorValue{}.setFloat32( { 1.0f, 0.0f, 1.0f, 1.0f } ); + auto clearColor = vk::ClearColorValue{}.setFloat32({1.0f, 0.0f, 1.0f, 1.0f}); // // CREATE FRAMEBUFFERS // - for( auto&& image : images ) + for(auto&& image : images) { auto colorImage = mGraphicsDevice.CreateImageFromExternal(image, mSwapchainCreateInfoKHR.imageFormat, @@ -238,15 +236,16 @@ void Swapchain::CreateFramebuffers() auto colorImageView = mGraphicsDevice.CreateImageView(colorImage); // A new color attachment for each framebuffer - auto colorAttachment = FramebufferAttachment::NewColorAttachment( colorImageView, - clearColor, - true ); // presentable - - mFramebuffers.push_back( - mGraphicsDevice.CreateFramebuffer( { colorAttachment }, - nullptr, - mSwapchainCreateInfoKHR.imageExtent.width, - mSwapchainCreateInfoKHR.imageExtent.height ) ); + auto colorAttachment = FramebufferAttachment::NewColorAttachment(colorImageView, + clearColor, + true); // presentable + + mFramebuffers.push_back(FramebufferImpl::New(mGraphicsDevice, + nullptr, + {colorAttachment}, + nullptr, + mSwapchainCreateInfoKHR.imageExtent.width, + mSwapchainCreateInfoKHR.imageExtent.height)); } mIsValid = true; } @@ -258,66 +257,65 @@ vk::SwapchainKHR Swapchain::GetVkHandle() const FramebufferImpl* Swapchain::GetCurrentFramebuffer() const { - return GetFramebuffer( mSwapchainImageIndex ); + return GetFramebuffer(mSwapchainImageIndex); } -FramebufferImpl* Swapchain::GetFramebuffer( uint32_t index ) const +FramebufferImpl* Swapchain::GetFramebuffer(uint32_t index) const { return mFramebuffers[index]; } -FramebufferImpl* Swapchain::AcquireNextFramebuffer( bool shouldCollectGarbageNow ) +FramebufferImpl* Swapchain::AcquireNextFramebuffer(bool shouldCollectGarbageNow) { // prevent from using invalid swapchain - if( !mIsValid ) + if(!mIsValid) { - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Attempt to present invalid/expired swapchain: %p\n", static_cast< VkSwapchainKHR >(mSwapchainKHR) ); + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Attempt to present invalid/expired swapchain: %p\n", static_cast<VkSwapchainKHR>(mSwapchainKHR)); return nullptr; } const auto& device = mGraphicsDevice.GetLogicalDevice(); // on swapchain first create sync primitives if not created yet - if( mSwapchainBuffers.empty() ) + if(mSwapchainBuffers.empty()) { - mSwapchainBuffers.resize( MAX_SWAPCHAIN_RESOURCE_BUFFERS ); - for( auto& buffer : mSwapchainBuffers ) + mSwapchainBuffers.resize(MAX_SWAPCHAIN_RESOURCE_BUFFERS); + for(auto& buffer : mSwapchainBuffers) { - buffer.reset( new SwapchainBuffer( mGraphicsDevice ) ); + buffer.reset(new SwapchainBuffer(mGraphicsDevice)); } } - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Swapchain Image Index ( BEFORE Acquire ) = %d", - int(mSwapchainImageIndex) ); + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Swapchain Image Index ( BEFORE Acquire ) = %d", int(mSwapchainImageIndex)); auto& swapchainBuffer = mSwapchainBuffers[mGraphicsDevice.GetCurrentBufferIndex()]; - auto result = device.acquireNextImageKHR(mSwapchainKHR, + auto result = device.acquireNextImageKHR(mSwapchainKHR, std::numeric_limits<uint64_t>::max(), swapchainBuffer->acquireNextImageSemaphore, - nullptr, &mSwapchainImageIndex ); + nullptr, + &mSwapchainImageIndex); - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Swapchain Image Index ( AFTER Acquire ) = %d", - int(mSwapchainImageIndex) ); + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Swapchain Image Index ( AFTER Acquire ) = %d", int(mSwapchainImageIndex)); // swapchain either not optimal or expired, returning nullptr and // setting validity to false - if( result != vk::Result::eSuccess ) + if(result != vk::Result::eSuccess) { mIsValid = false; - if ( result == vk::Result::eErrorOutOfDateKHR ) + if(result == vk::Result::eErrorOutOfDateKHR) { return nullptr; } else { - assert( mIsValid ); + assert(mIsValid); } } // First frames don't need waiting as they haven't been submitted // yet. Note, that waiting on the fence without resetting it may // cause a stall ( nvidia, ubuntu ) - if( mFrameCounter >= mSwapchainBuffers.size() ) + if(mFrameCounter >= mSwapchainBuffers.size()) { vk::Result result = swapchainBuffer->endOfFrameFence->GetStatus(); if(result == vk::Result::eNotReady) @@ -328,61 +326,60 @@ FramebufferImpl* Swapchain::AcquireNextFramebuffer( bool shouldCollectGarbageNow } else { - //mGraphicsDevice.DeviceWaitIdle(); // Do we care for first frame?! + mGraphicsDevice.DeviceWaitIdle(); } - //mGraphicsDevice.CollectGarbage(); + // mGraphicsDevice.CollectGarbage(); return mFramebuffers[mSwapchainImageIndex]; } - void Swapchain::Submit(CommandBufferImpl* commandBuffer) { auto& swapchainBuffer = mSwapchainBuffers[mGraphicsDevice.GetCurrentBufferIndex()]; swapchainBuffer->endOfFrameFence->Reset(); - mGraphicsDevice.Submit( *mQueue, - { Vulkan::SubmissionData{ - {swapchainBuffer->acquireNextImageSemaphore}, - {}, - {commandBuffer}, - {swapchainBuffer->submitSemaphore}}}, - nullptr/*swapchainBuffer->inFlightFence*/); //This fence could guard resetting the cmd buffer + mGraphicsDevice.Submit(*mQueue, + {Vulkan::SubmissionData{ + {swapchainBuffer->acquireNextImageSemaphore}, + {}, + {commandBuffer}, + {swapchainBuffer->submitSemaphore}}}, + nullptr /*swapchainBuffer->inFlightFence*/); // This fence could guard resetting the cmd buffer } void Swapchain::Present() { // prevent from using invalid swapchain - if( !mIsValid ) + if(!mIsValid) { return; } - auto& swapchainBuffer = mSwapchainBuffers[mGraphicsDevice.GetCurrentBufferIndex()]; + auto& swapchainBuffer = mSwapchainBuffers[mGraphicsDevice.GetCurrentBufferIndex()]; vk::PresentInfoKHR presentInfo{}; - vk::Result result; - presentInfo.setPImageIndices( &mSwapchainImageIndex ) - .setPResults( &result ) - .setPSwapchains( &mSwapchainKHR ) - .setSwapchainCount( 1 ) - .setPWaitSemaphores( &swapchainBuffer->submitSemaphore ) - .setWaitSemaphoreCount( 1 ); + vk::Result result; + presentInfo.setPImageIndices(&mSwapchainImageIndex) + .setPResults(&result) + .setPSwapchains(&mSwapchainKHR) + .setSwapchainCount(1) + .setPWaitSemaphores(&swapchainBuffer->submitSemaphore) + .setWaitSemaphoreCount(1); - mGraphicsDevice.Present( *mQueue, presentInfo ); + mGraphicsDevice.Present(*mQueue, presentInfo); // handle error - if( presentInfo.pResults[0] != vk::Result::eSuccess ) + if(presentInfo.pResults[0] != vk::Result::eSuccess) { // invalidate swapchain - if ( result == vk::Result::eErrorOutOfDateKHR ) + if(result == vk::Result::eErrorOutOfDateKHR) { mIsValid = false; } else { mIsValid = false; - assert( mIsValid ); + assert(mIsValid); } } @@ -391,17 +388,16 @@ void Swapchain::Present() bool Swapchain::OnDestroy() { - if( mSwapchainKHR ) + if(mSwapchainKHR) { - auto device = mGraphicsDevice.GetLogicalDevice(); + auto device = mGraphicsDevice.GetLogicalDevice(); auto swapchain = mSwapchainKHR; auto allocator = &mGraphicsDevice.GetAllocator(); - mGraphicsDevice.DiscardResource( [ device, swapchain, allocator ]() { - DALI_LOG_INFO( gVulkanFilter, Debug::General, "Invoking deleter function: swap chain->%p\n", - static_cast< VkSwapchainKHR >(swapchain) ) - device.destroySwapchainKHR( swapchain, allocator ); - } ); + mGraphicsDevice.DiscardResource([device, swapchain, allocator]() + { + DALI_LOG_INFO(gVulkanFilter, Debug::General, "Invoking deleter function: swap chain->%p\n", static_cast<VkSwapchainKHR>(swapchain)) + device.destroySwapchainKHR(swapchain, allocator); }); mSwapchainKHR = nullptr; } @@ -491,6 +487,4 @@ uint32_t Swapchain::GetImageCount() const return uint32_t(mFramebuffers.size()); } - - -} // namespace Dali::Graphics::Vulkan::Internal +} // namespace Dali::Graphics::Vulkan diff --git a/dali/internal/graphics/vulkan/vulkan-device.cpp b/dali/internal/graphics/vulkan/vulkan-device.cpp index 098238f4f..2eaf3f1c4 100644 --- a/dali/internal/graphics/vulkan/vulkan-device.cpp +++ b/dali/internal/graphics/vulkan/vulkan-device.cpp @@ -19,17 +19,17 @@ #include <dali/internal/graphics/vulkan/vulkan-device.h> // INTERNAL INCLUDES -#include <dali/internal/graphics/vulkan/vulkan-surface-factory.h> +#include <dali/integration-api/debug.h> #include <dali/internal/graphics/vulkan-impl/vulkan-command-buffer-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-command-pool-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-fence-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-framebuffer-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-impl.h> -#include <dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-image-view-impl.h> +#include <dali/internal/graphics/vulkan-impl/vulkan-render-pass-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-surface-impl.h> #include <dali/internal/graphics/vulkan-impl/vulkan-swapchain-impl.h> -#include <dali/integration-api/debug.h> +#include <dali/internal/graphics/vulkan/vulkan-surface-factory.h> #ifndef VK_KHR_XLIB_SURFACE_EXTENSION_NAME #define VK_KHR_XLIB_SURFACE_EXTENSION_NAME "VK_KHR_xlib_surface" @@ -54,19 +54,19 @@ namespace Dali::Graphics::Vulkan { class RenderPassImpl; -auto reqLayers = std::vector< const char* >{ - //"VK_LAYER_LUNARG_screenshot", // screenshot - //"VK_LAYER_LUNARG_parameter_validation", // parameter - //"VK_LAYER_LUNARG_vktrace", // vktrace ( requires vktrace connection ) - //"VK_LAYER_LUNARG_monitor", // monitor - //"VK_LAYER_LUNARG_swapchain", // swapchain - //"VK_LAYER_GOOGLE_threading", // threading - //"VK_LAYER_LUNARG_api_dump", // api - //"VK_LAYER_LUNARG_object_tracker", // objects - //"VK_LAYER_LUNARG_core_validation", // core - //"VK_LAYER_GOOGLE_unique_objects", // unique objects - //"VK_LAYER_LUNARG_standard_validation", // standard - // Don't add VK_LAYER_RENDERDOC_Capture, set ENABLE_VULKAN_RENDERDOC_CAPTURE=1 environment variable +auto reqLayers = std::vector<const char*>{ + //"VK_LAYER_LUNARG_screenshot", // screenshot + //"VK_LAYER_LUNARG_parameter_validation", // parameter + //"VK_LAYER_LUNARG_vktrace", // vktrace ( requires vktrace connection ) + //"VK_LAYER_LUNARG_monitor", // monitor + //"VK_LAYER_LUNARG_swapchain", // swapchain + //"VK_LAYER_GOOGLE_threading", // threading + //"VK_LAYER_LUNARG_api_dump", // api + //"VK_LAYER_LUNARG_object_tracker", // objects + //"VK_LAYER_LUNARG_core_validation", // core + //"VK_LAYER_GOOGLE_unique_objects", // unique objects + //"VK_LAYER_LUNARG_standard_validation", // standard + // Don't add VK_LAYER_RENDERDOC_Capture, set ENABLE_VULKAN_RENDERDOC_CAPTURE=1 environment variable }; Device::Device() @@ -81,13 +81,13 @@ Device::~Device() mSurfaceMap.clear(); - DALI_LOG_STREAM( gVulkanFilter, Debug::General, "DESTROYING GRAPHICS CONTEXT--------------------------------\n" ); + DALI_LOG_STREAM(gVulkanFilter, Debug::General, "DESTROYING GRAPHICS CONTEXT--------------------------------\n"); SwapBuffers(); // We are done with all resources (technically... . If not we will get a ton of validation layer errors) // Kill the Vulkan logical device - mLogicalDevice.destroy( mAllocator.get() ); + mLogicalDevice.destroy(mAllocator.get()); // Kill the Vulkan instance DestroyInstance(); @@ -97,22 +97,22 @@ Device::~Device() void Device::Create() { auto extensions = PrepareDefaultInstanceExtensions(); - auto layers = vk::enumerateInstanceLayerProperties(); + auto layers = vk::enumerateInstanceLayerProperties(); - std::vector< const char* > validationLayers; - for( auto&& reqLayer : reqLayers ) + std::vector<const char*> validationLayers; + for(auto&& reqLayer : reqLayers) { - for( auto&& prop : layers.value ) + for(auto&& prop : layers.value) { - DALI_LOG_STREAM( gVulkanFilter, Debug::General, prop.layerName ); - if( std::string( prop.layerName ) == reqLayer ) + DALI_LOG_STREAM(gVulkanFilter, Debug::General, prop.layerName); + if(std::string(prop.layerName) == reqLayer) { - validationLayers.push_back( reqLayer ); + validationLayers.push_back(reqLayer); } } } - CreateInstance( extensions, validationLayers ); + CreateInstance(extensions, validationLayers); PreparePhysicalDevice(); } @@ -121,20 +121,20 @@ void Device::CreateDevice() auto queueInfos = GetQueueCreateInfos(); { auto maxQueueCountPerFamily = 0u; - for( auto&& info : queueInfos ) + for(auto&& info : queueInfos) { - maxQueueCountPerFamily = std::max( info.queueCount, maxQueueCountPerFamily ); + maxQueueCountPerFamily = std::max(info.queueCount, maxQueueCountPerFamily); } - auto priorities = std::vector< float >( maxQueueCountPerFamily ); - std::fill( priorities.begin(), priorities.end(), 1.0f ); + auto priorities = std::vector<float>(maxQueueCountPerFamily); + std::fill(priorities.begin(), priorities.end(), 1.0f); - for( auto& info : queueInfos ) + for(auto& info : queueInfos) { - info.setPQueuePriorities( priorities.data() ); + info.setPQueuePriorities(priorities.data()); } - std::vector< const char* > extensions{ VK_KHR_SWAPCHAIN_EXTENSION_NAME }; + std::vector<const char*> extensions{VK_KHR_SWAPCHAIN_EXTENSION_NAME}; /** * @todo Check these exist before using them for native image: @@ -150,55 +150,55 @@ void Device::CreateDevice() vk::PhysicalDeviceFeatures featuresToEnable{}; - if( mPhysicalDeviceFeatures.fillModeNonSolid ) + if(mPhysicalDeviceFeatures.fillModeNonSolid) { featuresToEnable.fillModeNonSolid = VK_TRUE; } - if( mPhysicalDeviceFeatures.textureCompressionASTC_LDR ) + if(mPhysicalDeviceFeatures.textureCompressionASTC_LDR) { featuresToEnable.textureCompressionASTC_LDR = VK_TRUE; } - if( mPhysicalDeviceFeatures.textureCompressionETC2 ) + if(mPhysicalDeviceFeatures.textureCompressionETC2) { featuresToEnable.textureCompressionETC2 = VK_TRUE; } auto info = vk::DeviceCreateInfo{}; - info.setEnabledExtensionCount( U32( extensions.size() ) ) - .setPpEnabledExtensionNames( extensions.data() ) - .setPEnabledFeatures( &featuresToEnable ) - .setPQueueCreateInfos( queueInfos.data() ) - .setQueueCreateInfoCount( U32( queueInfos.size() ) ); + info.setEnabledExtensionCount(U32(extensions.size())) + .setPpEnabledExtensionNames(extensions.data()) + .setPEnabledFeatures(&featuresToEnable) + .setPQueueCreateInfos(queueInfos.data()) + .setQueueCreateInfoCount(U32(queueInfos.size())); - mLogicalDevice = VkAssert( mPhysicalDevice.createDevice( info, *mAllocator ) ); + mLogicalDevice = VkAssert(mPhysicalDevice.createDevice(info, *mAllocator)); } // create Queue objects - for( auto& queueInfo : queueInfos ) + for(auto& queueInfo : queueInfos) { - for( auto i = 0u; i < queueInfo.queueCount; ++i ) + for(auto i = 0u; i < queueInfo.queueCount; ++i) { - auto queue = mLogicalDevice.getQueue( queueInfo.queueFamilyIndex, i ); + auto queue = mLogicalDevice.getQueue(queueInfo.queueFamilyIndex, i); // based on family push queue instance into right array - auto flags = mQueueFamilyProperties[queueInfo.queueFamilyIndex].queueFlags; - auto queueWrapper = std::unique_ptr< Queue >( new Queue(queue, queueInfo.queueFamilyIndex, i, flags ) ); + auto flags = mQueueFamilyProperties[queueInfo.queueFamilyIndex].queueFlags; + auto queueWrapper = std::unique_ptr<Queue>(new Queue(queue, queueInfo.queueFamilyIndex, i, flags)); - if( flags & vk::QueueFlagBits::eGraphics ) + if(flags & vk::QueueFlagBits::eGraphics) { - mGraphicsQueues.emplace_back( queueWrapper.get() ); + mGraphicsQueues.emplace_back(queueWrapper.get()); } - if( flags & vk::QueueFlagBits::eTransfer ) + if(flags & vk::QueueFlagBits::eTransfer) { - mTransferQueues.emplace_back( queueWrapper.get() ); + mTransferQueues.emplace_back(queueWrapper.get()); } - if( flags & vk::QueueFlagBits::eCompute ) + if(flags & vk::QueueFlagBits::eCompute) { - mComputeQueues.emplace_back( queueWrapper.get() ); + mComputeQueues.emplace_back(queueWrapper.get()); } - mAllQueues.emplace_back( std::move( queueWrapper )); + mAllQueues.emplace_back(std::move(queueWrapper)); // todo: present queue } } @@ -210,48 +210,45 @@ void Device::CreateDevice() } Graphics::SurfaceId Device::CreateSurface( - Dali::Graphics::SurfaceFactory& surfaceFactory, - const Dali::Graphics::GraphicsCreateInfo& createInfo ) + Dali::Graphics::SurfaceFactory& surfaceFactory, + const Dali::Graphics::GraphicsCreateInfo& createInfo) { - auto vulkanSurfaceFactory = dynamic_cast<Dali::Graphics::Vulkan::SurfaceFactory*>( &surfaceFactory ); + auto vulkanSurfaceFactory = dynamic_cast<Dali::Graphics::Vulkan::SurfaceFactory*>(&surfaceFactory); - if( !vulkanSurfaceFactory ) + if(!vulkanSurfaceFactory) { return -1; // fail } // create surface from the factory - auto* surface = new SurfaceImpl( *this, vulkanSurfaceFactory->Create( mInstance, - mAllocator.get(), - mPhysicalDevice )); - if( !surface->GetVkHandle() ) + auto* surface = new SurfaceImpl(*this, vulkanSurfaceFactory->Create(mInstance, mAllocator.get(), mPhysicalDevice)); + if(!surface->GetVkHandle()) { return -1; } - VkBool32 supported( VK_FALSE ); - for( auto i = 0u; i < mQueueFamilyProperties.size(); ++i ) + VkBool32 supported(VK_FALSE); + for(auto i = 0u; i < mQueueFamilyProperties.size(); ++i) { - auto result = mPhysicalDevice.getSurfaceSupportKHR( i, surface->GetVkHandle(), &supported ); - if( result == vk::Result::eSuccess && supported ) + auto result = mPhysicalDevice.getSurfaceSupportKHR(i, surface->GetVkHandle(), &supported); + if(result == vk::Result::eSuccess && supported) { break; } } - assert( supported && "There is no queue family supporting presentation!"); + assert(supported && "There is no queue family supporting presentation!"); - surface->GetCapabilities() = VkAssert( mPhysicalDevice.getSurfaceCapabilitiesKHR( surface->GetVkHandle() ) ); + surface->GetCapabilities() = VkAssert(mPhysicalDevice.getSurfaceCapabilitiesKHR(surface->GetVkHandle())); // If width (and height) equals the special value 0xFFFFFFFF, the size of the surface will be set by the swapchain - if( surface->GetCapabilities().currentExtent.width == std::numeric_limits< uint32_t >::max() ) + if(surface->GetCapabilities().currentExtent.width == std::numeric_limits<uint32_t>::max()) { - surface->GetCapabilities().currentExtent.width = std::max( surface->GetCapabilities().minImageExtent.width, - std::min( surface->GetCapabilities().maxImageExtent.width, createInfo.surfaceWidth ) ); - - surface->GetCapabilities().currentExtent.height = std::max( surface->GetCapabilities().minImageExtent.height, - std::min( surface->GetCapabilities().maxImageExtent.height, createInfo.surfaceHeight ) ); + surface->GetCapabilities().currentExtent.width = std::max(surface->GetCapabilities().minImageExtent.width, + std::min(surface->GetCapabilities().maxImageExtent.width, createInfo.surfaceWidth)); + surface->GetCapabilities().currentExtent.height = std::max(surface->GetCapabilities().minImageExtent.height, + std::min(surface->GetCapabilities().maxImageExtent.height, createInfo.surfaceHeight)); } mSurfaceResized = false; @@ -259,10 +256,10 @@ Graphics::SurfaceId Device::CreateSurface( // map surface to SurfaceId auto surfaceId = ++mBaseSurfaceId; - mSurfaceMap[ surfaceId ] = SwapchainSurfacePair{ nullptr, surface }; + mSurfaceMap[surfaceId] = SwapchainSurfacePair{nullptr, surface}; - if( createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_OPTIMAL || - createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_STENCIL_OPTIMAL ) + if(createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_OPTIMAL || + createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_STENCIL_OPTIMAL) { mHasDepth = true; } @@ -271,7 +268,7 @@ Graphics::SurfaceId Device::CreateSurface( mHasDepth = false; } - if( createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_STENCIL_OPTIMAL ) + if(createInfo.depthStencilMode == Dali::Graphics::DepthStencilMode::DEPTH_STENCIL_OPTIMAL) { mHasStencil = true; } @@ -279,35 +276,35 @@ Graphics::SurfaceId Device::CreateSurface( return surfaceId; } -void Device::DestroySurface( Dali::Graphics::SurfaceId surfaceId ) +void Device::DestroySurface(Dali::Graphics::SurfaceId surfaceId) { - if( auto surface = GetSurface( surfaceId ) ) + if(auto surface = GetSurface(surfaceId)) { DeviceWaitIdle(); - auto swapchain = GetSwapchainForSurfaceId( surfaceId ); + auto swapchain = GetSwapchainForSurfaceId(surfaceId); swapchain->Destroy(); surface->Destroy(); } } -Swapchain* Device::CreateSwapchainForSurface( SurfaceImpl* surface ) +Swapchain* Device::CreateSwapchainForSurface(SurfaceImpl* surface) { DALI_ASSERT_DEBUG(surface && "Surface ptr must be allocated"); auto surfaceCapabilities = surface->GetCapabilities(); - //TODO: propagate the format and presentation mode to higher layers to allow for more control? - // @todo - for instance, Graphics::RenderTargetCreateInfo?! - Swapchain* swapchain = CreateSwapchain( surface, - vk::Format::eB8G8R8A8Unorm, - vk::PresentModeKHR::eFifo, - surfaceCapabilities.minImageCount, - nullptr ); + // TODO: propagate the format and presentation mode to higher layers to allow for more control? + // @todo - for instance, Graphics::RenderTargetCreateInfo?! + Swapchain* swapchain = CreateSwapchain(surface, + vk::Format::eB8G8R8A8Unorm, + vk::PresentModeKHR::eFifo, + surfaceCapabilities.minImageCount, + nullptr); // store swapchain in the correct pair - for( auto&& val : mSurfaceMap ) + for(auto&& val : mSurfaceMap) { - if( val.second.surface == surface ) + if(val.second.surface == surface) { val.second.swapchain = swapchain; break; @@ -317,23 +314,22 @@ Swapchain* Device::CreateSwapchainForSurface( SurfaceImpl* surface ) return swapchain; } - -Swapchain* Device::ReplaceSwapchainForSurface( SurfaceImpl* surface, Swapchain*&& oldSwapchain ) +Swapchain* Device::ReplaceSwapchainForSurface(SurfaceImpl* surface, Swapchain*&& oldSwapchain) { auto surfaceCapabilities = surface->GetCapabilities(); mSurfaceResized = false; - auto swapchain = CreateSwapchain( surface, - vk::Format::eB8G8R8A8Unorm, - vk::PresentModeKHR::eFifo, - surfaceCapabilities.minImageCount, - std::move(oldSwapchain) ); + auto swapchain = CreateSwapchain(surface, + vk::Format::eB8G8R8A8Unorm, + vk::PresentModeKHR::eFifo, + surfaceCapabilities.minImageCount, + std::move(oldSwapchain)); // store swapchain in the correct pair - for( auto&& val : mSurfaceMap ) + for(auto&& val : mSurfaceMap) { - if( val.second.surface == surface ) + if(val.second.surface == surface) { val.second.swapchain = swapchain; break; @@ -343,21 +339,19 @@ Swapchain* Device::ReplaceSwapchainForSurface( SurfaceImpl* surface, Swapchain*& return swapchain; } -Swapchain* Device::CreateSwapchain( SurfaceImpl* surface, - vk::Format requestedFormat, - vk::PresentModeKHR presentMode, - uint32_t bufferCount, - Swapchain*&& oldSwapchain ) +Swapchain* Device::CreateSwapchain(SurfaceImpl* surface, + vk::Format requestedFormat, + vk::PresentModeKHR presentMode, + uint32_t bufferCount, + Swapchain*&& oldSwapchain) { - auto newSwapchain = Swapchain::NewSwapchain( *this, GetPresentQueue(), - oldSwapchain?oldSwapchain->GetVkHandle():nullptr, - surface, requestedFormat, presentMode, bufferCount); + auto newSwapchain = Swapchain::NewSwapchain(*this, GetPresentQueue(), oldSwapchain ? oldSwapchain->GetVkHandle() : nullptr, surface, requestedFormat, presentMode, bufferCount); - if( oldSwapchain ) + if(oldSwapchain) { - for( auto&& i : mSurfaceMap ) + for(auto&& i : mSurfaceMap) { - if( i.second.swapchain == oldSwapchain ) + if(i.second.swapchain == oldSwapchain) { i.second.swapchain = nullptr; break; @@ -365,7 +359,7 @@ Swapchain* Device::CreateSwapchain( SurfaceImpl* surface, } } - if( oldSwapchain ) + if(oldSwapchain) { // prevent destroying the swapchain as it is handled automatically // during replacing the swapchain @@ -373,7 +367,7 @@ Swapchain* Device::CreateSwapchain( SurfaceImpl* surface, oldSwapchain->SetVkHandle(nullptr); oldSwapchain->Release(); - mLogicalDevice.destroySwapchainKHR( khr, *mAllocator ); + mLogicalDevice.destroySwapchainKHR(khr, *mAllocator); } // @todo: Only create framebuffers if no "external" render passes. @@ -381,15 +375,15 @@ Swapchain* Device::CreateSwapchain( SurfaceImpl* surface, return newSwapchain; } -vk::Result Device::Present( Queue& queue, vk::PresentInfoKHR presentInfo ) +vk::Result Device::Present(Queue& queue, vk::PresentInfoKHR presentInfo) { - auto lock( queue.Lock() ); - return queue.Present( presentInfo ); + auto lock(queue.Lock()); + return queue.Present(presentInfo); } -vk::Result Device::QueueWaitIdle( Queue& queue ) +vk::Result Device::QueueWaitIdle(Queue& queue) { - auto lock( queue.Lock() ); + auto lock(queue.Lock()); return queue.WaitIdle(); } @@ -398,26 +392,26 @@ vk::Result Device::DeviceWaitIdle() return mLogicalDevice.waitIdle(); } -const vk::AllocationCallbacks& Device::GetAllocator( const char* tag ) +const vk::AllocationCallbacks& Device::GetAllocator(const char* tag) { - if( mAllocator ) + if(mAllocator) { - //mAllocator->setPUserData( CreateMemoryAllocationTag( tag ) ); + // mAllocator->setPUserData( CreateMemoryAllocationTag( tag ) ); } return *mAllocator; } -Queue& Device::GetGraphicsQueue( uint32_t index ) const +Queue& Device::GetGraphicsQueue(uint32_t index) const { return *mGraphicsQueues[index]; } -Queue& Device::GetTransferQueue( uint32_t index ) const +Queue& Device::GetTransferQueue(uint32_t index) const { return *mTransferQueues[index]; } -Queue& Device::GetComputeQueue( uint32_t index ) const +Queue& Device::GetComputeQueue(uint32_t index) const { return *mComputeQueues[index]; } @@ -427,150 +421,83 @@ Queue& Device::GetPresentQueue() const return GetGraphicsQueue(0); } -void Device::DiscardResource( std::function< void() > deleter ) +void Device::DiscardResource(std::function<void()> deleter) { - //std::lock_guard< std::mutex > lock( mMutex ); - //mDiscardQueue[mCurrentBufferIndex].push_back( std::move( deleter ) ); + // std::lock_guard< std::mutex > lock( mMutex ); + // mDiscardQueue[mCurrentBufferIndex].push_back( std::move( deleter ) ); } -Fence* Device::CreateFence( const vk::FenceCreateInfo& fenceCreateInfo ) +Fence* Device::CreateFence(const vk::FenceCreateInfo& fenceCreateInfo) { vk::Fence vkFence; - VkAssert( mLogicalDevice.createFence( &fenceCreateInfo, mAllocator.get(), &vkFence ) ); + VkAssert(mLogicalDevice.createFence(&fenceCreateInfo, mAllocator.get(), &vkFence)); return new Fence(*this, vkFence); } -FramebufferImpl* Device::CreateFramebuffer(const std::vector< FramebufferAttachment* >& colorAttachments, - FramebufferAttachment* depthAttachment, - uint32_t width, - uint32_t height, - RenderPassImpl* externalRenderPass ) -{ - assert( ( !colorAttachments.empty() || depthAttachment ) - && "Cannot create framebuffer. Please provide at least one attachment" ); - - auto colorAttachmentsValid = true; - for( auto& attachment : colorAttachments ) - { - if( !attachment->IsValid() ) - { - colorAttachmentsValid = false; - break; - } - } - - assert( colorAttachmentsValid && "Invalid color attachment! The attachment has no ImageView" ); - - // Flag that indicates if the framebuffer has a depth attachment - auto hasDepth = false; - if( depthAttachment ) - { - hasDepth = depthAttachment->IsValid(); - assert( hasDepth && "Invalid depth attachment! The attachment has no ImageView" ); - } - - auto renderPass = externalRenderPass; - - // Flag that indicates if the render pass is externally provided - auto isRenderPassExternal = (externalRenderPass != nullptr); - - // This vector stores the attachments (vk::ImageViews) - auto attachments = std::vector< vk::ImageView >{}; - - // If no external render pass was provided, create one internally - if( !isRenderPassExternal ) - { - renderPass = RenderPassImpl::NewRenderPass( *this, colorAttachments, depthAttachment ); - attachments = renderPass->GetAttachments(); - } - - // Finally create the framebuffer - auto framebufferCreateInfo = vk::FramebufferCreateInfo{}.setRenderPass( renderPass->GetVkHandle() ) - .setPAttachments( attachments.data() ) - .setLayers( 1 ) - .setWidth( width ) - .setHeight( height ) - .setAttachmentCount( U32( attachments.size() ) ); - - auto framebuffer = VkAssert( mLogicalDevice.createFramebuffer( framebufferCreateInfo, mAllocator.get() ) ); - - return new FramebufferImpl( *this, - colorAttachments, - depthAttachment, - framebuffer, - renderPass->GetVkHandle(), - width, - height, - isRenderPassExternal ); -} - - - -Image* Device::CreateImageFromExternal( vk::Image externalImage, vk::Format imageFormat, vk::Extent2D extent ) +Image* Device::CreateImageFromExternal(vk::Image externalImage, vk::Format imageFormat, vk::Extent2D extent) { auto imageCreateInfo = vk::ImageCreateInfo{} - .setFormat( imageFormat ) - .setSamples( vk::SampleCountFlagBits::e1 ) - .setInitialLayout( vk::ImageLayout::eUndefined ) - .setSharingMode( vk::SharingMode::eExclusive ) - .setUsage( vk::ImageUsageFlagBits::eColorAttachment ) - .setExtent( { extent.width, extent.height, 1 } ) - .setArrayLayers( 1 ) - .setImageType( vk::ImageType::e2D ) - .setTiling( vk::ImageTiling::eOptimal ) - .setMipLevels( 1 ); - - return new Image( *this, imageCreateInfo, externalImage ); + .setFormat(imageFormat) + .setSamples(vk::SampleCountFlagBits::e1) + .setInitialLayout(vk::ImageLayout::eUndefined) + .setSharingMode(vk::SharingMode::eExclusive) + .setUsage(vk::ImageUsageFlagBits::eColorAttachment) + .setExtent({extent.width, extent.height, 1}) + .setArrayLayers(1) + .setImageType(vk::ImageType::e2D) + .setTiling(vk::ImageTiling::eOptimal) + .setMipLevels(1); + + return new Image(*this, imageCreateInfo, externalImage); return nullptr; } ImageView* Device::CreateImageView(const vk::ImageViewCreateFlags& flags, - const Image& image, - vk::ImageViewType viewType, - vk::Format format, - vk::ComponentMapping components, - vk::ImageSubresourceRange subresourceRange, - void* pNext ) + const Image& image, + vk::ImageViewType viewType, + vk::Format format, + vk::ComponentMapping components, + vk::ImageSubresourceRange subresourceRange, + void* pNext) { auto imageViewCreateInfo = vk::ImageViewCreateInfo{} - .setPNext( pNext ) - .setFlags( flags ) - .setImage( image.GetVkHandle() ) - .setViewType( viewType ) - .setFormat( format ) - .setComponents( components ) - .setSubresourceRange( std::move( subresourceRange ) ); + .setPNext(pNext) + .setFlags(flags) + .setImage(image.GetVkHandle()) + .setViewType(viewType) + .setFormat(format) + .setComponents(components) + .setSubresourceRange(std::move(subresourceRange)); - auto imageView = new ImageView( *this, &image, imageViewCreateInfo ); + auto imageView = new ImageView(*this, &image, imageViewCreateInfo); - VkAssert( mLogicalDevice.createImageView( &imageViewCreateInfo, &GetAllocator("IMAGEVIEW"), &imageView->mImageView ) ); + VkAssert(mLogicalDevice.createImageView(&imageViewCreateInfo, &GetAllocator("IMAGEVIEW"), &imageView->mImageView)); return imageView; } -ImageView* Device::CreateImageView( Image* image ) +ImageView* Device::CreateImageView(Image* image) { - vk::ComponentMapping componentsMapping = { vk::ComponentSwizzle::eR, - vk::ComponentSwizzle::eG, - vk::ComponentSwizzle::eB, - vk::ComponentSwizzle::eA }; - + vk::ComponentMapping componentsMapping = {vk::ComponentSwizzle::eR, + vk::ComponentSwizzle::eG, + vk::ComponentSwizzle::eB, + vk::ComponentSwizzle::eA}; auto subresourceRange = vk::ImageSubresourceRange{} - .setAspectMask( image->GetAspectFlags() ) - .setBaseArrayLayer( 0 ) - .setBaseMipLevel( 0 ) - .setLevelCount( image->GetMipLevelCount() ) - .setLayerCount( image->GetLayerCount() ); + .setAspectMask(image->GetAspectFlags()) + .setBaseArrayLayer(0) + .setBaseMipLevel(0) + .setLevelCount(image->GetMipLevelCount()) + .setLayerCount(image->GetLayerCount()); auto imageView = CreateImageView({}, *image, vk::ImageViewType::e2D, image->GetFormat(), componentsMapping, - subresourceRange ); + subresourceRange); return imageView; } @@ -578,26 +505,26 @@ ImageView* Device::CreateImageView( Image* image ) vk::Result Device::WaitForFence(Fence* fence, uint32_t timeout) { auto f = fence->GetVkHandle(); - return mLogicalDevice.waitForFences( 1, &f, VK_TRUE, timeout ); + return mLogicalDevice.waitForFences(1, &f, VK_TRUE, timeout); } // ------------------------------------------------------------------------------------------------------- // Getters------------------------------------------------------------------------------------------------ -SurfaceImpl* Device::GetSurface( Graphics::SurfaceId surfaceId ) +SurfaceImpl* Device::GetSurface(Graphics::SurfaceId surfaceId) { // Note, surface ID == 0 means main window - if( surfaceId == 0 ) + if(surfaceId == 0) { return mSurfaceMap.begin()->second.surface; } return mSurfaceMap[surfaceId].surface; } -Swapchain* Device::GetSwapchainForSurface( SurfaceImpl* surface ) +Swapchain* Device::GetSwapchainForSurface(SurfaceImpl* surface) { - for( auto&& val : mSurfaceMap ) + for(auto&& val : mSurfaceMap) { - if( val.second.surface == surface ) + if(val.second.surface == surface) { return val.second.swapchain; } @@ -605,13 +532,13 @@ Swapchain* Device::GetSwapchainForSurface( SurfaceImpl* surface ) return nullptr; } -Swapchain* Device::GetSwapchainForSurfaceId( Graphics::SurfaceId surfaceId ) +Swapchain* Device::GetSwapchainForSurfaceId(Graphics::SurfaceId surfaceId) { - if( surfaceId == 0 ) + if(surfaceId == 0) { return mSurfaceMap.begin() - ->second - .swapchain; + ->second + .swapchain; } return mSurfaceMap[surfaceId].swapchain; } @@ -638,18 +565,18 @@ Platform Device::GetDefaultPlatform() const #elif VK_USE_PLATFORM_XCB_KHR mPlatform = Platform::XCB; #elif VK_USE_PLATFORM_XLIB_KHR - mPlatform = Platform::XLIB; + mPlatform = Platform::XLIB; #else return mPlatform; #endif } -CommandPool* Device::GetCommandPool( std::thread::id threadId) +CommandPool* Device::GetCommandPool(std::thread::id threadId) { - CommandPool* commandPool=nullptr; + CommandPool* commandPool = nullptr; { std::lock_guard<std::mutex> lock{mMutex}; - commandPool = mCommandPools.find(threadId) == mCommandPools.end()?nullptr:mCommandPools[threadId]; + commandPool = mCommandPools.find(threadId) == mCommandPools.end() ? nullptr : mCommandPools[threadId]; } if(!commandPool) { @@ -664,20 +591,19 @@ CommandPool* Device::GetCommandPool( std::thread::id threadId) return commandPool; } -void Device::SurfaceResized( unsigned int width, unsigned int height ) +void Device::SurfaceResized(unsigned int width, unsigned int height) { // Get main window's surface // At first, check to empty about mSurfaceMap - if ( !mSurfaceMap.empty() ) + if(!mSurfaceMap.empty()) { auto surface = mSurfaceMap.begin()->second.surface; - if (surface) + if(surface) { auto surfaceCapabilities = surface->GetCapabilities(); - if ( surfaceCapabilities.currentExtent.width != width - || surfaceCapabilities.currentExtent.height != height ) + if(surfaceCapabilities.currentExtent.width != width || surfaceCapabilities.currentExtent.height != height) { - surface->UpdateSize( width, height ); + surface->UpdateSize(width, height); mSurfaceResized = true; } } @@ -686,7 +612,7 @@ void Device::SurfaceResized( unsigned int width, unsigned int height ) uint32_t Device::SwapBuffers() { - mCurrentBufferIndex = (mCurrentBufferIndex+1)&1; + mCurrentBufferIndex = (mCurrentBufferIndex + 1) & 1; return mCurrentBufferIndex; } @@ -695,53 +621,53 @@ uint32_t Device::GetCurrentBufferIndex() const return mCurrentBufferIndex; } -void Device::CreateInstance( const std::vector< const char* >& extensions, - const std::vector< const char* >& validationLayers ) +void Device::CreateInstance(const std::vector<const char*>& extensions, + const std::vector<const char*>& validationLayers) { auto info = vk::InstanceCreateInfo{}; - info.setEnabledExtensionCount( U32( extensions.size() ) ) - .setPpEnabledExtensionNames( extensions.data() ) - .setEnabledLayerCount( U32( validationLayers.size() ) ) - .setPpEnabledLayerNames( validationLayers.data() ); + info.setEnabledExtensionCount(U32(extensions.size())) + .setPpEnabledExtensionNames(extensions.data()) + .setEnabledLayerCount(U32(validationLayers.size())) + .setPpEnabledLayerNames(validationLayers.data()); - const char* log_level = std::getenv( "LOG_VULKAN" ); - int intValue = log_level ? std::atoi(log_level) : 0; - if ( !intValue ) + const char* log_level = std::getenv("LOG_VULKAN"); + int intValue = log_level ? std::atoi(log_level) : 0; + if(!intValue) { - info.setEnabledLayerCount( 0 ); + info.setEnabledLayerCount(0); } - mInstance = VkAssert( vk::createInstance( info, *mAllocator ) ); + mInstance = VkAssert(vk::createInstance(info, *mAllocator)); } void Device::DestroyInstance() { - if( mInstance ) + if(mInstance) { - mInstance.destroy( *mAllocator ); + mInstance.destroy(*mAllocator); mInstance = nullptr; } } void Device::PreparePhysicalDevice() { - auto devices = VkAssert( mInstance.enumeratePhysicalDevices() ); - assert( !devices.empty() && "No Vulkan supported device found!" ); + auto devices = VkAssert(mInstance.enumeratePhysicalDevices()); + assert(!devices.empty() && "No Vulkan supported device found!"); // if only one, pick first mPhysicalDevice = nullptr; - if( devices.size() == 1 ) + if(devices.size() == 1) { - mPhysicalDevice = devices[0]; + mPhysicalDevice = devices[0]; } else // otherwise look for one which is a graphics device { - for( auto& device : devices ) + for(auto& device : devices) { auto properties = device.getProperties(); - if( properties.deviceType == vk::PhysicalDeviceType::eDiscreteGpu || - properties.deviceType == vk::PhysicalDeviceType::eIntegratedGpu ) + if(properties.deviceType == vk::PhysicalDeviceType::eDiscreteGpu || + properties.deviceType == vk::PhysicalDeviceType::eIntegratedGpu) { auto queueFamilyProperties = device.getQueueFamilyProperties(); for(const auto& queueFamily : queueFamilyProperties) @@ -756,7 +682,7 @@ void Device::PreparePhysicalDevice() } } - assert( mPhysicalDevice && "No suitable Physical Device found!" ); + assert(mPhysicalDevice && "No suitable Physical Device found!"); GetPhysicalDeviceProperties(); GetQueueFamilyProperties(); @@ -764,9 +690,9 @@ void Device::PreparePhysicalDevice() void Device::GetPhysicalDeviceProperties() { - mPhysicalDeviceProperties = mPhysicalDevice.getProperties(); + mPhysicalDeviceProperties = mPhysicalDevice.getProperties(); mPhysicalDeviceMemoryProperties = mPhysicalDevice.getMemoryProperties(); - mPhysicalDeviceFeatures = mPhysicalDevice.getFeatures(); + mPhysicalDeviceFeatures = mPhysicalDevice.getFeatures(); } void Device::GetQueueFamilyProperties() @@ -774,16 +700,15 @@ void Device::GetQueueFamilyProperties() mQueueFamilyProperties = mPhysicalDevice.getQueueFamilyProperties(); } -std::vector< vk::DeviceQueueCreateInfo > Device::GetQueueCreateInfos() +std::vector<vk::DeviceQueueCreateInfo> Device::GetQueueCreateInfos() { - std::vector< vk::DeviceQueueCreateInfo > queueInfos{}; + std::vector<vk::DeviceQueueCreateInfo> queueInfos{}; constexpr uint8_t MAX_QUEUE_TYPES = 3; - // find suitable family for each type of queue - auto familyIndexTypes = std::array< uint32_t, MAX_QUEUE_TYPES >{}; - familyIndexTypes.fill( std::numeric_limits< uint32_t >::max() ); + auto familyIndexTypes = std::array<uint32_t, MAX_QUEUE_TYPES>{}; + familyIndexTypes.fill(std::numeric_limits<uint32_t>::max()); // Device auto& graphicsFamily = familyIndexTypes[0]; @@ -795,37 +720,35 @@ std::vector< vk::DeviceQueueCreateInfo > Device::GetQueueCreateInfos() auto& presentFamily = familyIndexTypes[2]; auto queueFamilyIndex = 0u; - for( auto& prop : mQueueFamilyProperties ) + for(auto& prop : mQueueFamilyProperties) { - if( ( prop.queueFlags & vk::QueueFlagBits::eGraphics ) && graphicsFamily == -1u ) + if((prop.queueFlags & vk::QueueFlagBits::eGraphics) && graphicsFamily == -1u) { graphicsFamily = queueFamilyIndex; - presentFamily = queueFamilyIndex; + presentFamily = queueFamilyIndex; } - if( ( prop.queueFlags & vk::QueueFlagBits::eTransfer ) && transferFamily == -1u ) + if((prop.queueFlags & vk::QueueFlagBits::eTransfer) && transferFamily == -1u) { transferFamily = queueFamilyIndex; } ++queueFamilyIndex; } - assert( graphicsFamily != std::numeric_limits< uint32_t >::max() - && "No queue family that supports graphics operations!" ); - assert( transferFamily != std::numeric_limits< uint32_t >::max() - && "No queue family that supports transfer operations!" ); + assert(graphicsFamily != std::numeric_limits<uint32_t>::max() && "No queue family that supports graphics operations!"); + assert(transferFamily != std::numeric_limits<uint32_t>::max() && "No queue family that supports transfer operations!"); // todo: we may require that the family must be same for all type of operations, it makes // easier to handle synchronisation related issues. // sort queues - std::sort( familyIndexTypes.begin(), familyIndexTypes.end() ); + std::sort(familyIndexTypes.begin(), familyIndexTypes.end()); // allocate all queues from graphics family - auto prevQueueFamilyIndex = std::numeric_limits< uint32_t >::max(); + auto prevQueueFamilyIndex = std::numeric_limits<uint32_t>::max(); - for( const auto& familyIndex : familyIndexTypes ) + for(const auto& familyIndex : familyIndexTypes) { - if( prevQueueFamilyIndex == familyIndex ) + if(prevQueueFamilyIndex == familyIndex) { continue; } @@ -836,61 +759,61 @@ std::vector< vk::DeviceQueueCreateInfo > Device::GetQueueCreateInfos() // note the priorities are not being set as local pointer will out of scope, this // will be fixed by the caller function auto info = vk::DeviceQueueCreateInfo{} - .setPQueuePriorities( nullptr ) - .setQueueCount( queueCount ) - .setQueueFamilyIndex( familyIndex ); - queueInfos.push_back( info ); + .setPQueuePriorities(nullptr) + .setQueueCount(queueCount) + .setQueueFamilyIndex(familyIndex); + queueInfos.push_back(info); prevQueueFamilyIndex = familyIndex; } return queueInfos; } -std::vector< const char* > Device::PrepareDefaultInstanceExtensions() +std::vector<const char*> Device::PrepareDefaultInstanceExtensions() { auto extensions = vk::enumerateInstanceExtensionProperties(); std::string extensionName; - bool xlibAvailable{ false }; - bool xcbAvailable{ false }; - bool waylandAvailable{ false }; + bool xlibAvailable{false}; + bool xcbAvailable{false}; + bool waylandAvailable{false}; - for( auto&& ext : extensions.value ) + for(auto&& ext : extensions.value) { extensionName = std::string(ext.extensionName); - if( extensionName == VK_KHR_XCB_SURFACE_EXTENSION_NAME ) + if(extensionName == VK_KHR_XCB_SURFACE_EXTENSION_NAME) { xcbAvailable = true; } - else if( extensionName == VK_KHR_XLIB_SURFACE_EXTENSION_NAME ) + else if(extensionName == VK_KHR_XLIB_SURFACE_EXTENSION_NAME) { xlibAvailable = true; } - else if( extensionName == VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME ) + else if(extensionName == VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME) { waylandAvailable = true; } } - std::vector< const char* > retval{}; + std::vector<const char*> retval{}; // depending on the platform validate extensions auto platform = GetDefaultPlatform(); - if( platform != Platform::UNDEFINED ) + if(platform != Platform::UNDEFINED) { - if( platform == Platform::XCB && xcbAvailable ) + if(platform == Platform::XCB && xcbAvailable) { - retval.push_back( VK_KHR_XCB_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_XCB_SURFACE_EXTENSION_NAME); } - else if( platform == Platform::XLIB && xlibAvailable ) + else if(platform == Platform::XLIB && xlibAvailable) { - retval.push_back( VK_KHR_XLIB_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_XLIB_SURFACE_EXTENSION_NAME); } - else if( platform == Platform::WAYLAND && waylandAvailable ) + else if(platform == Platform::WAYLAND && waylandAvailable) { - retval.push_back( VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME); /* For native image, check these exist first: * VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME * VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME @@ -899,20 +822,20 @@ std::vector< const char* > Device::PrepareDefaultInstanceExtensions() } else // try to determine the platform based on available extensions { - if( xcbAvailable ) + if(xcbAvailable) { mPlatform = Platform::XCB; - retval.push_back( VK_KHR_XCB_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_XCB_SURFACE_EXTENSION_NAME); } - else if( xlibAvailable ) + else if(xlibAvailable) { mPlatform = Platform::XLIB; - retval.push_back( VK_KHR_XLIB_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_XLIB_SURFACE_EXTENSION_NAME); } - else if( waylandAvailable ) + else if(waylandAvailable) { mPlatform = Platform::WAYLAND; - retval.push_back( VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME ); + retval.push_back(VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME); /* For native image, check these exist first: * VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME * VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME @@ -926,55 +849,48 @@ std::vector< const char* > Device::PrepareDefaultInstanceExtensions() } // other essential extensions - retval.push_back( VK_KHR_SURFACE_EXTENSION_NAME ); - retval.push_back( VK_EXT_DEBUG_REPORT_EXTENSION_NAME ); + retval.push_back(VK_KHR_SURFACE_EXTENSION_NAME); + retval.push_back(VK_EXT_DEBUG_REPORT_EXTENSION_NAME); return retval; } vk::Result Device::Submit(Queue& queue, const std::vector<SubmissionData>& submissionData, Fence* fence) { - auto lock( queue.Lock() ); + auto lock(queue.Lock()); - auto submitInfos = std::vector< vk::SubmitInfo >{}; - submitInfos.reserve( submissionData.size() ); - auto commandBufferHandles = std::vector< vk::CommandBuffer >{}; + auto submitInfos = std::vector<vk::SubmitInfo>{}; + submitInfos.reserve(submissionData.size()); + auto commandBufferHandles = std::vector<vk::CommandBuffer>{}; // prepare memory auto bufferSize = 0u; - for( auto& data : submissionData ) + for(auto& data : submissionData) { - bufferSize += uint32_t( data.commandBuffers.size() ); + bufferSize += uint32_t(data.commandBuffers.size()); } - commandBufferHandles.reserve( bufferSize ); + commandBufferHandles.reserve(bufferSize); // Transform SubmissionData to vk::SubmitInfo - for( const auto& subData : submissionData ) + for(const auto& subData : submissionData) { auto currentBufferIndex = commandBufferHandles.size(); - //Extract the command buffer handles - std::transform( subData.commandBuffers.cbegin(), + // Extract the command buffer handles + std::transform(subData.commandBuffers.cbegin(), subData.commandBuffers.cend(), - std::back_inserter( commandBufferHandles ), - [ & ]( CommandBufferImpl* entry ) { + std::back_inserter(commandBufferHandles), + [&](CommandBufferImpl* entry) + { return entry->GetVkHandle(); - } ); + }); - auto retval = vk::SubmitInfo().setWaitSemaphoreCount( U32( subData.waitSemaphores.size() ) ) - .setPWaitSemaphores( subData.waitSemaphores.data() ) - .setPWaitDstStageMask( &subData.waitDestinationStageMask ) - .setCommandBufferCount( U32( subData.commandBuffers.size() ) ) - .setPCommandBuffers( &commandBufferHandles[currentBufferIndex] ) - .setSignalSemaphoreCount( U32( subData.signalSemaphores.size() ) ) - .setPSignalSemaphores( subData.signalSemaphores.data() ); + auto retval = vk::SubmitInfo().setWaitSemaphoreCount(U32(subData.waitSemaphores.size())).setPWaitSemaphores(subData.waitSemaphores.data()).setPWaitDstStageMask(&subData.waitDestinationStageMask).setCommandBufferCount(U32(subData.commandBuffers.size())).setPCommandBuffers(&commandBufferHandles[currentBufferIndex]).setSignalSemaphoreCount(U32(subData.signalSemaphores.size())).setPSignalSemaphores(subData.signalSemaphores.data()); - submitInfos.push_back( retval ); + submitInfos.push_back(retval); } - return VkAssert( queue.Submit( submitInfos, fence) ); - - + return VkAssert(queue.Submit(submitInfos, fence)); } } // namespace Dali::Graphics::Vulkan |