Update DeviceManager

This commit is contained in:
2021-07-21 01:59:11 +02:00
parent cfbf31cb77
commit 58f2efb360
6 changed files with 100 additions and 43 deletions

View File

@@ -29,8 +29,8 @@ namespace openVulkanoCpp::Vulkan
CreateDevice(); CreateDevice();
swapChain.Init(device, surface, window); swapChain.Init(device.get(), surface, window);
swapChainRenderPass.Init(device, &swapChain); swapChainRenderPass.Init(device.get(), &swapChain);
pipeline.Init(device->device); pipeline.Init(device->device);
@@ -75,10 +75,11 @@ namespace openVulkanoCpp::Vulkan
void Context::CreateDevice() void Context::CreateDevice()
{ {
const std::vector<std::string> neededExtensions = { VK_KHR_SWAPCHAIN_EXTENSION_NAME };
deviceManager.Init(instance); deviceManager.Init(instance);
device = deviceManager.GetCompatibleDevice({ VK_KHR_SWAPCHAIN_EXTENSION_NAME }); device = deviceManager.GetCompatibleDevice(neededExtensions);
device->PrepareDevice({ VK_KHR_SWAPCHAIN_EXTENSION_NAME }, surface); device->PrepareDevice(neededExtensions, surface);
dynamicDispatch.init(instance, &vkGetInstanceProcAddr, device->device, &vkGetDeviceProcAddr); dynamicDispatch.init(instance, &vkGetInstanceProcAddr, device->device, &vkGetDeviceProcAddr);
Logger::RENDER->info("Found device: {0}", device->GetDeviceName());; Logger::RENDER->info("Found device: {0}", device->GetDeviceName());
} }
} }

View File

@@ -30,7 +30,7 @@ namespace openVulkanoCpp
vk::Instance instance; // Vulkan instance vk::Instance instance; // Vulkan instance
vk::DispatchLoaderDynamic dynamicDispatch; // for access to features not available in statically linked Vulkan lib vk::DispatchLoaderDynamic dynamicDispatch; // for access to features not available in statically linked Vulkan lib
vk::SurfaceKHR surface; // Vulkan surface to display framebuffer on vk::SurfaceKHR surface; // Vulkan surface to display framebuffer on
Device* device = nullptr; std::shared_ptr<Device> device;
SwapChain swapChain; SwapChain swapChain;
RenderPass swapChainRenderPass; RenderPass swapChainRenderPass;
IVulkanWindow* window = nullptr; IVulkanWindow* window = nullptr;

View File

@@ -126,7 +126,7 @@ namespace openVulkanoCpp::Vulkan
queueFamilyProperties = physicalDevice.getQueueFamilyProperties(); queueFamilyProperties = physicalDevice.getQueueFamilyProperties();
properties = physicalDevice.getProperties(); properties = physicalDevice.getProperties();
features = physicalDevice.getFeatures(); features = physicalDevice.getFeatures();
for (auto& ext : physicalDevice.enumerateDeviceExtensionProperties()) { supportedExtensions.insert(ext.extensionName); } for (auto& ext : physicalDevice.enumerateDeviceExtensionProperties()) { supportedExtensions.insert(ext.extensionName.data()); }
// Query device memory properties // Query device memory properties
memoryProperties = physicalDevice.getMemoryProperties(); memoryProperties = physicalDevice.getMemoryProperties();

View File

@@ -47,7 +47,7 @@ namespace openVulkanoCpp
[[nodiscard]] std::string GetDeviceName() const [[nodiscard]] std::string GetDeviceName() const
{ {
return properties.deviceName; return properties.deviceName.data();
} }
void PrepareDevice(const vk::ArrayProxy<const std::string>& requestedExtensions, const vk::SurfaceKHR& surface); void PrepareDevice(const vk::ArrayProxy<const std::string>& requestedExtensions, const vk::SurfaceKHR& surface);
@@ -75,7 +75,7 @@ namespace openVulkanoCpp
void ExecuteNow(const std::function<void(const vk::CommandBuffer& commandBuffer)>& function) const; void ExecuteNow(const std::function<void(const vk::CommandBuffer& commandBuffer)>& function) const;
vk::ShaderModule CreateShaderModule(const std::string& filename) const; [[nodiscard]] vk::ShaderModule CreateShaderModule(const std::string& filename) const;
vk::ShaderModule CreateShaderModule(vk::ShaderModuleCreateInfo& createInfo) const; vk::ShaderModule CreateShaderModule(vk::ShaderModuleCreateInfo& createInfo) const;

View File

@@ -0,0 +1,58 @@
/*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
*/
#include "DeviceManager.hpp"
#include "Device.hpp"
#include <stdexcept>
namespace openVulkanoCpp::Vulkan
{
void DeviceManager::Init(const vk::Instance& instance)
{
if (!devices.empty()) Close();
for (auto& physicalDevice: instance.enumeratePhysicalDevices())
{
devices.push_back(std::make_shared<Device>(physicalDevice));
}
}
std::shared_ptr<Device> DeviceManager::GetCompatibleDevice(const vk::ArrayProxy<const std::string>& deviceExtensions)
{
for (const auto& device: devices)
{
if (device->IsExtensionAvailable(deviceExtensions)) return device;
}
throw std::runtime_error("No device with required extensions found!\n" + ProduceMissingDeviceCompatibilityReport(deviceExtensions));
}
std::string DeviceManager::ProduceMissingDeviceCompatibilityReport(const vk::ArrayProxy<const std::string>& deviceExtensions)
{
std::stringstream ss;
ss << "Requested Extensions: [";
bool first = true;
for (const std::string& ext : deviceExtensions)
{
ss << ' ' << ext;
if (first) first = false;
else ss << ',';
}
ss << " ]\nAvailable Devices: [\n";
for (const auto& device: devices)
{
ss << '\t' << device->GetDeviceName() << ": [";
first = true;
for (const std::string& ext : device->GetExtensions())
{
ss << ' ' << ext;
if (first) first = false;
else ss << ',';
}
ss << " ]\n";
}
ss << ']';
return ss.str();
}
}

View File

@@ -1,44 +1,42 @@
/*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at https://mozilla.org/MPL/2.0/.
*/
#pragma once #pragma once
#include <stdexcept>
#include <memory>
#include <vector> #include <vector>
#include "Base/ICloseable.hpp" #include <vulkan/vulkan.hpp>
#include "Device.hpp"
namespace openVulkanoCpp namespace openVulkanoCpp::Vulkan
{ {
namespace Vulkan class Device;
class DeviceManager final
{ {
std::vector<std::shared_ptr<Device>> devices;
class DeviceManager : virtual public ICloseable public:
DeviceManager() = default;
DeviceManager(const vk::Instance& instance)
{ {
std::vector<Device> devices; Init(instance);
public: }
void Init(const vk::Instance& instance)
{
devices = std::vector<Device>();
for (auto& physicalDevice : instance.enumeratePhysicalDevices())
{
devices.emplace_back(physicalDevice);
}
}
Device* GetCompatibleDevice(const std::vector<std::string>& deviceExtensions) ~DeviceManager() = default;
{
for (auto& device : devices)
{
if (device.IsExtensionAvailable(deviceExtensions)) return &device;
}
throw std::runtime_error("No device with required extensions found!");
}
void Close() override void Init(const vk::Instance& instance);
{
for (auto& device : devices) std::shared_ptr<Device> GetCompatibleDevice(const vk::ArrayProxy<const std::string>& deviceExtensions);
{
device.Close(); std::string ProduceMissingDeviceCompatibilityReport(const vk::ArrayProxy<const std::string>& deviceExtensions);
}
devices.clear(); void Close()
} {
}; devices.clear();
} }
};
} }