1 | // Copyright (C) 2020 Klaralvdalens Datakonsult AB (KDAB). |
2 | // SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only |
3 | |
4 | #include "rhiresourcemanagers_p.h" |
5 | |
6 | QT_BEGIN_NAMESPACE |
7 | |
8 | namespace Qt3DRender { |
9 | |
10 | namespace Render { |
11 | |
12 | namespace Rhi { |
13 | |
14 | RHIResourceManagers::RHIResourceManagers() |
15 | : m_rhiBufferManager(new RHIBufferManager()), |
16 | m_rhiShaderManager(new RHIShaderManager()), |
17 | m_rhiTextureManager(new RHITextureManager()), |
18 | m_rhiRenderTargetManager(new RHIRenderTargetManager()), |
19 | m_rhiGraphicsPipelineManager(new RHIGraphicsPipelineManager()), |
20 | m_rhiComputePipelineManager(new RHIComputePipelineManager()) |
21 | { |
22 | } |
23 | |
24 | RHIResourceManagers::~RHIResourceManagers() |
25 | { |
26 | delete m_rhiTextureManager; |
27 | delete m_rhiShaderManager; |
28 | delete m_rhiBufferManager; |
29 | delete m_rhiRenderTargetManager; |
30 | delete m_rhiGraphicsPipelineManager; |
31 | delete m_rhiComputePipelineManager; |
32 | } |
33 | |
34 | void RHIResourceManagers::releaseAllResources() |
35 | { |
36 | auto releaseAll = [](auto *manager) noexcept { |
37 | // Release all resources reference by a key |
38 | manager->releaseAllResources(); |
39 | // Release remaining resources which were allocated manually but had no key |
40 | const auto handles = manager->activeHandles(); |
41 | for (const auto &handle : handles) { |
42 | manager->release(handle); |
43 | } |
44 | }; |
45 | |
46 | releaseAll(m_rhiTextureManager); |
47 | releaseAll(m_rhiBufferManager); |
48 | qDeleteAll(c: m_rhiShaderManager->takeActiveResources()); |
49 | releaseAll(m_rhiRenderTargetManager); |
50 | releaseAll(m_rhiGraphicsPipelineManager); |
51 | releaseAll(m_rhiComputePipelineManager); |
52 | } |
53 | |
54 | int RHIGraphicsPipelineManager::getIdForAttributeVec(const std::vector<AttributeInfo> &attributesInfo) |
55 | { |
56 | auto it = std::find(first: m_attributesInfo.begin(), |
57 | last: m_attributesInfo.end(), |
58 | val: attributesInfo); |
59 | if (it == m_attributesInfo.end()) { |
60 | m_attributesInfo.emplace_back(args: attributesInfo); |
61 | return int(m_attributesInfo.size()) - 1; |
62 | } |
63 | return std::distance(first: m_attributesInfo.begin(), last: it); |
64 | } |
65 | |
66 | int RHIGraphicsPipelineManager::getIdForRenderStates(const RenderStateSetPtr &stateSet) |
67 | { |
68 | if (!stateSet) |
69 | return -1; |
70 | const std::vector<StateVariant> &states = stateSet->states(); |
71 | auto it = std::find(first: m_renderStates.begin(), |
72 | last: m_renderStates.end(), |
73 | val: states); |
74 | if (it == m_renderStates.end()) { |
75 | m_renderStates.emplace_back(args: states); |
76 | return int(m_renderStates.size()) - 1; |
77 | } |
78 | return std::distance(first: m_renderStates.begin(), last: it); |
79 | } |
80 | |
81 | namespace { |
82 | |
83 | template<typename Manager> |
84 | void erasePipelinesReferencingShader(Manager *manager, const Qt3DCore::QNodeId &shaderId) |
85 | { |
86 | const auto handles = manager->activeHandles(); // copy |
87 | for (const auto &handle : handles) { |
88 | const auto &key = handle->key(); |
89 | if (key.shader == shaderId) |
90 | manager->releaseResource(key); |
91 | } |
92 | } |
93 | |
94 | template<typename Manager> |
95 | void erasePipelinesReferencingRenderTargetId(Manager *manager, const Qt3DCore::QNodeId &renderTargetId) |
96 | { |
97 | const auto handles = manager->activeHandles(); // copy |
98 | for (const auto &handle : handles) { |
99 | const auto &key = handle->key(); |
100 | if (key.renderTarget == renderTargetId) |
101 | manager->releaseResource(key); |
102 | } |
103 | } |
104 | |
105 | } // anonymous |
106 | |
107 | void RHIGraphicsPipelineManager::releasePipelinesReferencingShader(const Qt3DCore::QNodeId &shaderId) |
108 | { |
109 | erasePipelinesReferencingShader(manager: this, shaderId); |
110 | } |
111 | |
112 | void RHIGraphicsPipelineManager::releasePipelinesReferencingRenderTarget(const Qt3DCore::QNodeId &renderTargetId) |
113 | { |
114 | erasePipelinesReferencingRenderTargetId(manager: this, renderTargetId); |
115 | } |
116 | |
117 | void RHIComputePipelineManager::releasePipelinesReferencingShader(const Qt3DCore::QNodeId &shaderId) |
118 | { |
119 | erasePipelinesReferencingShader(manager: this, shaderId); |
120 | } |
121 | |
122 | } // Rhi |
123 | |
124 | } // Render |
125 | |
126 | } // Qt3DRender |
127 | |
128 | QT_END_NAMESPACE |
129 | |