diff --git a/openVulkanoCpp/AR/Provider/ArKit/ArSessionArKitInternal.mm b/openVulkanoCpp/AR/Provider/ArKit/ArSessionArKitInternal.mm index 9ab0568..0556893 100644 --- a/openVulkanoCpp/AR/Provider/ArKit/ArSessionArKitInternal.mm +++ b/openVulkanoCpp/AR/Provider/ArKit/ArSessionArKitInternal.mm @@ -110,7 +110,10 @@ namespace OpenVulkano::AR::ArKit void ArSessionArKitInternal::SetRenderer(IRenderer* renderer) { - m_textureCache.Init(renderer); + if (renderer) + m_textureCache.Init(renderer); + else + m_textureCache.Close(); } Scene::Texture* ArSessionArKitInternal::MakeTexture(ArFrame* frame) diff --git a/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.h b/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.h index d6817c3..7a4c226 100644 --- a/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.h +++ b/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.h @@ -6,6 +6,7 @@ #pragma once +#include "Base/ICloseable.hpp" #include "MetalBackedTexture.h" #import @@ -13,18 +14,21 @@ namespace OpenVulkano::Vulkan { - class MetalTextureCache + class Renderer; + + class MetalTextureCache : public ICloseable { CVMetalTextureCacheRef m_textureCache = nullptr; Vulkan::ResourceManager* m_resourceManager = nullptr; std::map m_mtlToVkTextureMap; + Renderer* m_renderer; public: ~MetalTextureCache() { if (m_resourceManager) Close(); } void Init(IRenderer* renderer); - void Close(); + void Close() override; Scene::Texture* Get(CVPixelBufferRef pixelBuffer, MTLPixelFormat pixelFormat); diff --git a/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.mm b/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.mm index 5b0e7aa..29a68d8 100644 --- a/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.mm +++ b/openVulkanoCpp/Vulkan/Metal/MetalTextureCache.mm @@ -13,21 +13,22 @@ namespace OpenVulkano::Vulkan { if (m_resourceManager) Close(); if (!renderer) return; - auto vkRenderer = dynamic_cast(renderer); - if (!vkRenderer) throw std::invalid_argument("The Metal Texture Cache only supports Vulkan renderer!"); + m_renderer = dynamic_cast(renderer); + if (!m_renderer) throw std::invalid_argument("The Metal Texture Cache only supports Vulkan renderer!"); // Setup texture cache VkExportMetalDeviceInfoEXT metalDeviceInfo {}; metalDeviceInfo.sType = VK_STRUCTURE_TYPE_EXPORT_METAL_DEVICE_INFO_EXT; metalDeviceInfo.pNext = nullptr; VkExportMetalObjectsInfoEXT exportInfo { VK_STRUCTURE_TYPE_EXPORT_METAL_OBJECTS_INFO_EXT, &metalDeviceInfo }; - VkDevice vkDevice = vkRenderer->GetContext().device->device; + VkDevice vkDevice = m_renderer->GetContext().device->device; vkExportMetalObjectsEXT(vkDevice, &exportInfo); CVReturn result = CVMetalTextureCacheCreate(nil, nil, metalDeviceInfo.mtlDevice, nil, &m_textureCache); if (result != kCVReturnSuccess) { Logger::AR->error("Failed to create metal texture cache! Status code: {}", result); } - m_resourceManager = &vkRenderer->GetResourceManager(); + m_resourceManager = &m_renderer->GetResourceManager(); + m_renderer->RegisterCloseable(this); } Scene::Texture* MetalTextureCache::Get(CVPixelBufferRef pixelBuffer, MTLPixelFormat pixelFormat) @@ -56,6 +57,8 @@ namespace OpenVulkano::Vulkan void MetalTextureCache::Close() { m_mtlToVkTextureMap.clear(); + m_renderer->UnregisterCloseable(this); + m_renderer = nullptr; m_resourceManager = nullptr; //TODO delete the texture cache object? m_textureCache = nullptr; diff --git a/openVulkanoCpp/Vulkan/Renderer.cpp b/openVulkanoCpp/Vulkan/Renderer.cpp index d05abed..1bae3df 100644 --- a/openVulkanoCpp/Vulkan/Renderer.cpp +++ b/openVulkanoCpp/Vulkan/Renderer.cpp @@ -79,6 +79,12 @@ namespace OpenVulkano::Vulkan { context.device->device.destroySemaphore(sema); } + while (!closeables.empty()) + { + ICloseable* closeable = closeables.back(); + closeables.pop_back(); + closeable->Close(); + } uiRenderer.Close(); resourceManager.Close(); commands.clear(); diff --git a/openVulkanoCpp/Vulkan/Renderer.hpp b/openVulkanoCpp/Vulkan/Renderer.hpp index 39e1d2d..2ff4d36 100644 --- a/openVulkanoCpp/Vulkan/Renderer.hpp +++ b/openVulkanoCpp/Vulkan/Renderer.hpp @@ -39,6 +39,7 @@ namespace OpenVulkano::Vulkan std::vector> commands; std::vector> submitBuffers; UiRenderer uiRenderer; + std::vector closeables; public: Renderer() = default; @@ -79,5 +80,9 @@ namespace OpenVulkano::Vulkan ResourceManager& GetResourceManager() { return resourceManager; } Context& GetContext() { return context; } + + void RegisterCloseable(ICloseable* closeable) { closeables.push_back(closeable); } + + void UnregisterCloseable(ICloseable* closeable) { Utils::Remove(closeables, closeable); } }; }