diff --git a/CMSceneGraph b/CMSceneGraph index cf93f6e0..ea88b9fa 160000 --- a/CMSceneGraph +++ b/CMSceneGraph @@ -1 +1 @@ -Subproject commit cf93f6e0910d96ffd8dd840209f6e65f162e1cd9 +Subproject commit ea88b9fa13b816293530be9232f9ce5a529944ae diff --git a/CMUtil b/CMUtil index 8ce98c85..be9122db 160000 --- a/CMUtil +++ b/CMUtil @@ -1 +1 @@ -Subproject commit 8ce98c85a397921277cd19a91993b6724bf1d391 +Subproject commit be9122db80512d3c046fe68b3b9948dd2078dec7 diff --git a/inc/hgl/graph/VK.h b/inc/hgl/graph/VK.h index 6ab2e453..f0afc2fe 100644 --- a/inc/hgl/graph/VK.h +++ b/inc/hgl/graph/VK.h @@ -62,6 +62,14 @@ class IndexBuffer; class GPUCmdBuffer; class RenderCmdBuffer; class TextureCmdBuffer; + +enum class RenderPassTypeBy +{ + Simple=0, + Normal, + Verbose +};// + class RenderPass; class GPUFence; class GPUSemaphore; diff --git a/inc/hgl/graph/VKDevice.h b/inc/hgl/graph/VKDevice.h index 03469b20..eb1e30a5 100644 --- a/inc/hgl/graph/VKDevice.h +++ b/inc/hgl/graph/VKDevice.h @@ -211,12 +211,17 @@ public: //Command Buffer 相关 RenderCmdBuffer * CreateRenderCommandBuffer(); TextureCmdBuffer *CreateTextureCommandBuffer(); +private: + RenderPass * CreateRenderPass( const List &desc_list, const List &subpass, const List &dependency, - const RenderbufferInfo *); + const RenderbufferInfo *, + const RenderPassTypeBy &type_by=RenderPassTypeBy::Verbose); - RenderPass * CreateRenderPass( const RenderbufferInfo *); +public: + + RenderPass * AcquireRenderPass( const RenderbufferInfo *,const RenderPassTypeBy &type_by=RenderPassTypeBy::Normal); GPUFence * CreateFence(bool); GPUSemaphore * CreateGPUSemaphore(); @@ -232,14 +237,13 @@ public: bool SubmitTexture (const VkCommandBuffer *cmd_bufs,const uint32_t count=1); ///<提交纹理处理到队列 - RenderTarget *CreateRenderTarget( Framebuffer *,const uint32_t fence_count=1); - + RenderTarget *CreateRenderTarget( const FramebufferInfo *fbi,RenderPass *,const uint32_t fence_count=1); RenderTarget *CreateRenderTarget( const FramebufferInfo *fbi,const uint32_t fence_count=1); public: - Pipeline *CreatePipeline(const InlinePipeline &,const Material *,const RenderTarget *); Pipeline *CreatePipeline( PipelineData *, const Material *,const RenderTarget *); + Pipeline *CreatePipeline(const InlinePipeline &,const Material *,const RenderTarget *); public: diff --git a/inc/hgl/graph/VKPipeline.h b/inc/hgl/graph/VKPipeline.h index c449805a..4d011d56 100644 --- a/inc/hgl/graph/VKPipeline.h +++ b/inc/hgl/graph/VKPipeline.h @@ -14,10 +14,23 @@ class Pipeline bool alpha_test; bool alpha_blend; + +private: + + friend class GPUDevice; + + Pipeline(VkDevice dev,VkPipeline p,PipelineData *pd) + { + device=dev; + pipeline=p; + data=pd; + + alpha_test=false; + alpha_blend=false; + } public: - Pipeline(VkDevice dev,VkPipeline p,PipelineData *pd):device(dev),pipeline(p),data(pd){} virtual ~Pipeline(); operator VkPipeline(){return pipeline;} diff --git a/src/GUI/ThemeEngine.cpp b/src/GUI/ThemeEngine.cpp index 6454284c..6e6d2f9f 100644 --- a/src/GUI/ThemeEngine.cpp +++ b/src/GUI/ThemeEngine.cpp @@ -49,7 +49,7 @@ namespace hgl RenderTarget *rt=CreateRenderTarget(size.x,size.y,format); if(!rt)return(false); - + ThemeForm *tf=CreateForm(f,rt); form_list.Add(f,tf); diff --git a/src/SceneGraph/CMakeLists.txt b/src/SceneGraph/CMakeLists.txt index 7d8bfd8d..d62d4da8 100644 --- a/src/SceneGraph/CMakeLists.txt +++ b/src/SceneGraph/CMakeLists.txt @@ -119,6 +119,7 @@ SET(VK_DEVICE_SOURCE ${SG_INCLUDE_PATH}/VKDevice.h Vulkan/VKDeviceImage.cpp Vulkan/VKDeviceTexture.cpp Vulkan/VKDeviceMaterial.cpp + Vulkan/VKDevicePipeline.cpp Vulkan/VKDeviceFramebuffer.cpp Vulkan/VKDeviceSwapchain.cpp Vulkan/VKDeviceRenderPass.cpp diff --git a/src/SceneGraph/Vulkan/VKDeviceRenderPass.cpp b/src/SceneGraph/Vulkan/VKDeviceRenderPass.cpp index 92d629aa..7391368c 100644 --- a/src/SceneGraph/Vulkan/VKDeviceRenderPass.cpp +++ b/src/SceneGraph/Vulkan/VKDeviceRenderPass.cpp @@ -234,14 +234,14 @@ namespace delete hash; } - static Map RenderPassList; + static Map RenderPassListByVerbose; } -RenderPass *GPUDevice::CreateRenderPass(const RenderpassTypeBy &type_by, - const List &desc_list, +RenderPass *GPUDevice::CreateRenderPass(const List &desc_list, const List &subpass, const List &dependency, - const RenderbufferInfo *rbi) + const RenderbufferInfo *rbi, + const RenderPassTypeBy &type_by) { for(const VkFormat cf:rbi->GetColorFormatList()) { @@ -269,15 +269,17 @@ RenderPass *GPUDevice::CreateRenderPass(const RenderpassTypeBy &type_by, rp_info.pSubpasses = subpass.GetData(); rp_info.dependencyCount = dependency.GetCount(); rp_info.pDependencies = dependency.GetData(); - + RenderPassHASHCode code; + RenderPass *rp=nullptr; - HashRenderPass(&code,rp_info); + if(type_by==RenderPassTypeBy::Verbose) + { + HashRenderPass(&code,rp_info); - RenderPass *rp; - - if(RenderPassList.Get(code,rp)) - return rp; + if(RenderPassListByVerbose.Get(code,rp)) + return rp; + } VkRenderPass render_pass; @@ -286,17 +288,47 @@ RenderPass *GPUDevice::CreateRenderPass(const RenderpassTypeBy &type_by, rp=new RenderPass(attr->device,render_pass,rbi->GetColorFormatList(),depth_format); - RenderPassList.Add(code,rp); + if(type_by==RenderPassTypeBy::Verbose) + RenderPassListByVerbose.Add(code,rp); return rp; } -RenderPass *GPUDevice::CreateRenderPass(const RenderpassTypeBy &type_by,const RenderbufferInfo *rbi) +namespace +{ + void HashRenderPass(RenderPassHASHCode *code,const RenderbufferInfo *rbi) + { + util::Hash *hash=util::CreateSHA1LEHash(); + + hash->Init(); + + for(const VkFormat &fmt:rbi->GetColorFormatList()) + hash->Write(fmt); + + hash->Final(&code); + delete hash; + } + + static Map RenderPassListByNormal; +}//namespace + +RenderPass *GPUDevice::AcquireRenderPass(const RenderbufferInfo *rbi,const RenderPassTypeBy &type_by) { for(const VkFormat &fmt:rbi->GetColorFormatList()) if(!attr->physical_device->IsColorAttachmentOptimal(fmt)) return(nullptr); + RenderPassHASHCode code; + RenderPass *rp=nullptr; + + if(type_by==RenderPassTypeBy::Normal) + { + HashRenderPass(&code,rbi); + + if(RenderPassListByNormal.Get(code,rp)) + return rp; + } + List color_ref_list; VkAttachmentReference depth_ref; List atta_desc_list; @@ -323,6 +355,11 @@ RenderPass *GPUDevice::CreateRenderPass(const RenderpassTypeBy &type_by,const Re CreateSubpassDependency(subpass_dependency_list,2); - return CreateRenderPass(type_by,atta_desc_list,subpass_desc_list,subpass_dependency_list,rbi); + rp=CreateRenderPass(atta_desc_list,subpass_desc_list,subpass_dependency_list,rbi,type_by); + + if(type_by==RenderPassTypeBy::Normal) + RenderPassListByNormal.Add(code,rp); + + return rp; } VK_NAMESPACE_END diff --git a/src/SceneGraph/Vulkan/VKDeviceRenderTarget.cpp b/src/SceneGraph/Vulkan/VKDeviceRenderTarget.cpp index a5133aac..f77d7ac6 100644 --- a/src/SceneGraph/Vulkan/VKDeviceRenderTarget.cpp +++ b/src/SceneGraph/Vulkan/VKDeviceRenderTarget.cpp @@ -1,17 +1,9 @@ #include VK_NAMESPACE_BEGIN -RenderTarget *GPUDevice::CreateRenderTarget(Framebuffer *fb,const uint32_t fence_count) -{ - return(new RenderTarget(this,fb,fence_count)); -} - -RenderTarget *GPUDevice::CreateRenderTarget(const FramebufferInfo *fbi,const uint32_t fence_count) +RenderTarget *GPUDevice::CreateRenderTarget(const FramebufferInfo *fbi,RenderPass *rp,const uint32_t fence_count) { if(!fbi)return(nullptr); - - RenderPass *rp=CreateRenderPass(RenderpassTypeBy::Format,fbi); //Renderpass内部会验证格式,所以不需要自己处理 - if(!rp)return(nullptr); const uint32_t color_count=fbi->GetColorCount(); @@ -51,7 +43,17 @@ RenderTarget *GPUDevice::CreateRenderTarget(const FramebufferInfo *fbi,const uin } SAFE_CLEAR(depth_texture); - delete rp; return nullptr; } + +RenderTarget *GPUDevice::CreateRenderTarget(const FramebufferInfo *fbi,const uint32_t fence_count) +{ + if(!fbi)return(nullptr); + + RenderPass *rp=AcquireRenderPass(fbi,RenderPassTypeBy::Normal); + + if(!rp)return(nullptr); + + return CreateRenderTarget(fbi,rp,fence_count); +} VK_NAMESPACE_END \ No newline at end of file diff --git a/src/SceneGraph/Vulkan/VKSwapchainRenderTarget.cpp b/src/SceneGraph/Vulkan/VKSwapchainRenderTarget.cpp index 08b35c27..9088e50a 100644 --- a/src/SceneGraph/Vulkan/VKSwapchainRenderTarget.cpp +++ b/src/SceneGraph/Vulkan/VKSwapchainRenderTarget.cpp @@ -3,19 +3,24 @@ #include VK_NAMESPACE_BEGIN -struct SwapchainFormatHash +namespace { - union + struct SwapchainFormatHash { - struct + union { - uint32 color; - uint32 depth; - }; + struct + { + uint32_t color; + uint32_t depth; + }; - uint64 hash; - }; -};// + uint64 hashcode; + }; + };// + + static Map RenderpassListBySimple; +}//namespace SwapchainRenderTarget::SwapchainRenderTarget(GPUDevice *dev,Swapchain *sc):RenderTarget(dev,nullptr,sc->GetImageCount()) { @@ -31,9 +36,21 @@ SwapchainRenderTarget::SwapchainRenderTarget(GPUDevice *dev,Swapchain *sc):Rende Texture2D **sc_color=swapchain->GetColorTextures(); Texture2D *sc_depth=swapchain->GetDepthTexture(); - SwapchainRenderbufferInfo rbi((*sc_color)->GetFormat(),sc_depth->GetFormat()); + { + SwapchainFormatHash sfh; + + sfh.color=(*sc_color)->GetFormat(); + sfh.depth=sc_depth->GetFormat(); - this->render_pass=device->CreateRenderPass(RenderpassTypeBy::Simple,&rbi); + if(!RenderpassListBySimple.Get(sfh.hashcode,this->render_pass)) + { + SwapchainRenderbufferInfo rbi((*sc_color)->GetFormat(),sc_depth->GetFormat()); + + this->render_pass=device->AcquireRenderPass(&rbi,RenderPassTypeBy::Simple); + + RenderpassListBySimple.Add(sfh.hashcode,this->render_pass); + } + } swap_chain_count=swapchain->GetImageCount();