mirror of
https://github.com/charles-lunarg/vk-bootstrap.git
synced 2024-11-25 16:24:35 +00:00
Move Result & Error out of the detail namespace
Since its a part of the public interface, it means applications using vk-bootstrap will inevitably need to use the types in error handling paths.
This commit is contained in:
parent
789a24edb7
commit
ab52ad97a8
@ -469,14 +469,14 @@ const char* to_string(SwapchainError err) {
|
||||
}
|
||||
}
|
||||
|
||||
detail::Result<SystemInfo> SystemInfo::get_system_info() {
|
||||
Result<SystemInfo> SystemInfo::get_system_info() {
|
||||
if (!detail::vulkan_functions().init_vulkan_funcs(nullptr)) {
|
||||
return make_error_code(InstanceError::vulkan_unavailable);
|
||||
}
|
||||
return SystemInfo();
|
||||
}
|
||||
|
||||
detail::Result<SystemInfo> SystemInfo::get_system_info(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcAddr) {
|
||||
Result<SystemInfo> SystemInfo::get_system_info(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcAddr) {
|
||||
// Using externally provided function pointers, assume the loader is available
|
||||
if (!detail::vulkan_functions().init_vulkan_funcs(fp_vkGetInstanceProcAddr)) {
|
||||
return make_error_code(InstanceError::vulkan_unavailable);
|
||||
@ -554,7 +554,7 @@ InstanceBuilder::InstanceBuilder(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcA
|
||||
}
|
||||
InstanceBuilder::InstanceBuilder() {}
|
||||
|
||||
detail::Result<Instance> InstanceBuilder::build() const {
|
||||
Result<Instance> InstanceBuilder::build() const {
|
||||
|
||||
auto sys_info_ret = SystemInfo::get_system_info(info.fp_vkGetInstanceProcAddr);
|
||||
if (!sys_info_ret) return sys_info_ret.error();
|
||||
@ -719,7 +719,7 @@ detail::Result<Instance> InstanceBuilder::build() const {
|
||||
Instance instance;
|
||||
VkResult res =
|
||||
detail::vulkan_functions().fp_vkCreateInstance(&instance_create_info, info.allocation_callbacks, &instance.instance);
|
||||
if (res != VK_SUCCESS) return detail::Result<Instance>(InstanceError::failed_create_instance, res);
|
||||
if (res != VK_SUCCESS) return Result<Instance>(InstanceError::failed_create_instance, res);
|
||||
|
||||
detail::vulkan_functions().init_instance_funcs(instance.instance);
|
||||
|
||||
@ -732,7 +732,7 @@ detail::Result<Instance> InstanceBuilder::build() const {
|
||||
&instance.debug_messenger,
|
||||
info.allocation_callbacks);
|
||||
if (res != VK_SUCCESS) {
|
||||
return detail::Result<Instance>(InstanceError::failed_create_debug_messenger, res);
|
||||
return Result<Instance>(InstanceError::failed_create_debug_messenger, res);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1162,7 +1162,7 @@ PhysicalDeviceSelector::PhysicalDeviceSelector(Instance const& instance, VkSurfa
|
||||
criteria.desired_version = instance.api_version;
|
||||
}
|
||||
|
||||
detail::Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_impl(DeviceSelectionMode selection) const {
|
||||
Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_impl(DeviceSelectionMode selection) const {
|
||||
#if !defined(NDEBUG)
|
||||
// Validation
|
||||
for (const auto& node : criteria.extended_features_chain) {
|
||||
@ -1177,7 +1177,7 @@ detail::Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_impl(
|
||||
|
||||
if (criteria.require_present && !criteria.defer_surface_initialization) {
|
||||
if (instance_info.surface == VK_NULL_HANDLE)
|
||||
return detail::Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_surface_provided };
|
||||
return Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_surface_provided };
|
||||
}
|
||||
|
||||
// Get the VkPhysicalDevice handles on the system
|
||||
@ -1186,11 +1186,10 @@ detail::Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_impl(
|
||||
auto vk_physical_devices_ret = detail::get_vector<VkPhysicalDevice>(
|
||||
vk_physical_devices, detail::vulkan_functions().fp_vkEnumeratePhysicalDevices, instance_info.instance);
|
||||
if (vk_physical_devices_ret != VK_SUCCESS) {
|
||||
return detail::Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::failed_enumerate_physical_devices,
|
||||
vk_physical_devices_ret };
|
||||
return Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::failed_enumerate_physical_devices, vk_physical_devices_ret };
|
||||
}
|
||||
if (vk_physical_devices.size() == 0) {
|
||||
return detail::Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_physical_devices_found };
|
||||
return Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_physical_devices_found };
|
||||
}
|
||||
|
||||
auto fill_out_phys_dev_with_criteria = [&](PhysicalDevice& phys_dev) {
|
||||
@ -1248,32 +1247,32 @@ detail::Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_impl(
|
||||
return physical_devices;
|
||||
}
|
||||
|
||||
detail::Result<PhysicalDevice> PhysicalDeviceSelector::select(DeviceSelectionMode selection) const {
|
||||
Result<PhysicalDevice> PhysicalDeviceSelector::select(DeviceSelectionMode selection) const {
|
||||
auto const selected_devices = select_impl(selection);
|
||||
|
||||
if (!selected_devices) return detail::Result<PhysicalDevice>{ selected_devices.error() };
|
||||
if (!selected_devices) return Result<PhysicalDevice>{ selected_devices.error() };
|
||||
if (selected_devices.value().size() == 0) {
|
||||
return detail::Result<PhysicalDevice>{ PhysicalDeviceError::no_suitable_device };
|
||||
return Result<PhysicalDevice>{ PhysicalDeviceError::no_suitable_device };
|
||||
}
|
||||
|
||||
return selected_devices.value().at(0);
|
||||
}
|
||||
|
||||
// Return all devices which are considered suitable - intended for applications which want to let the user pick the physical device
|
||||
detail::Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_devices(DeviceSelectionMode selection) const {
|
||||
Result<std::vector<PhysicalDevice>> PhysicalDeviceSelector::select_devices(DeviceSelectionMode selection) const {
|
||||
auto const selected_devices = select_impl(selection);
|
||||
if (!selected_devices) return detail::Result<std::vector<PhysicalDevice>>{ selected_devices.error() };
|
||||
if (!selected_devices) return Result<std::vector<PhysicalDevice>>{ selected_devices.error() };
|
||||
if (selected_devices.value().size() == 0) {
|
||||
return detail::Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_suitable_device };
|
||||
return Result<std::vector<PhysicalDevice>>{ PhysicalDeviceError::no_suitable_device };
|
||||
}
|
||||
return selected_devices.value();
|
||||
}
|
||||
|
||||
detail::Result<std::vector<std::string>> PhysicalDeviceSelector::select_device_names(DeviceSelectionMode selection) const {
|
||||
Result<std::vector<std::string>> PhysicalDeviceSelector::select_device_names(DeviceSelectionMode selection) const {
|
||||
auto const selected_devices = select_impl(selection);
|
||||
if (!selected_devices) return detail::Result<std::vector<std::string>>{ selected_devices.error() };
|
||||
if (!selected_devices) return Result<std::vector<std::string>>{ selected_devices.error() };
|
||||
if (selected_devices.value().size() == 0) {
|
||||
return detail::Result<std::vector<std::string>>{ PhysicalDeviceError::no_suitable_device };
|
||||
return Result<std::vector<std::string>>{ PhysicalDeviceError::no_suitable_device };
|
||||
}
|
||||
std::vector<std::string> names;
|
||||
for (const auto& pd : selected_devices.value()) {
|
||||
@ -1410,61 +1409,55 @@ PhysicalDevice::operator VkPhysicalDevice() const { return this->physical_device
|
||||
|
||||
// ---- Queues ---- //
|
||||
|
||||
detail::Result<uint32_t> Device::get_queue_index(QueueType type) const {
|
||||
Result<uint32_t> Device::get_queue_index(QueueType type) const {
|
||||
uint32_t index = detail::QUEUE_INDEX_MAX_VALUE;
|
||||
switch (type) {
|
||||
case QueueType::present:
|
||||
index = detail::get_present_queue_index(physical_device.physical_device, surface, queue_families);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::present_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::present_unavailable };
|
||||
break;
|
||||
case QueueType::graphics:
|
||||
index = detail::get_first_queue_index(queue_families, VK_QUEUE_GRAPHICS_BIT);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::graphics_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::graphics_unavailable };
|
||||
break;
|
||||
case QueueType::compute:
|
||||
index = detail::get_separate_queue_index(queue_families, VK_QUEUE_COMPUTE_BIT, VK_QUEUE_TRANSFER_BIT);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::compute_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::compute_unavailable };
|
||||
break;
|
||||
case QueueType::transfer:
|
||||
index = detail::get_separate_queue_index(queue_families, VK_QUEUE_TRANSFER_BIT, VK_QUEUE_COMPUTE_BIT);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::transfer_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::transfer_unavailable };
|
||||
break;
|
||||
default:
|
||||
return detail::Result<uint32_t>{ QueueError::invalid_queue_family_index };
|
||||
return Result<uint32_t>{ QueueError::invalid_queue_family_index };
|
||||
}
|
||||
return index;
|
||||
}
|
||||
detail::Result<uint32_t> Device::get_dedicated_queue_index(QueueType type) const {
|
||||
Result<uint32_t> Device::get_dedicated_queue_index(QueueType type) const {
|
||||
uint32_t index = detail::QUEUE_INDEX_MAX_VALUE;
|
||||
switch (type) {
|
||||
case QueueType::compute:
|
||||
index = detail::get_dedicated_queue_index(queue_families, VK_QUEUE_COMPUTE_BIT, VK_QUEUE_TRANSFER_BIT);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::compute_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::compute_unavailable };
|
||||
break;
|
||||
case QueueType::transfer:
|
||||
index = detail::get_dedicated_queue_index(queue_families, VK_QUEUE_TRANSFER_BIT, VK_QUEUE_COMPUTE_BIT);
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE)
|
||||
return detail::Result<uint32_t>{ QueueError::transfer_unavailable };
|
||||
if (index == detail::QUEUE_INDEX_MAX_VALUE) return Result<uint32_t>{ QueueError::transfer_unavailable };
|
||||
break;
|
||||
default:
|
||||
return detail::Result<uint32_t>{ QueueError::invalid_queue_family_index };
|
||||
return Result<uint32_t>{ QueueError::invalid_queue_family_index };
|
||||
}
|
||||
return index;
|
||||
}
|
||||
|
||||
detail::Result<VkQueue> Device::get_queue(QueueType type) const {
|
||||
Result<VkQueue> Device::get_queue(QueueType type) const {
|
||||
auto index = get_queue_index(type);
|
||||
if (!index.has_value()) return { index.error() };
|
||||
VkQueue out_queue;
|
||||
internal_table.fp_vkGetDeviceQueue(device, index.value(), 0, &out_queue);
|
||||
return out_queue;
|
||||
}
|
||||
detail::Result<VkQueue> Device::get_dedicated_queue(QueueType type) const {
|
||||
Result<VkQueue> Device::get_dedicated_queue(QueueType type) const {
|
||||
auto index = get_dedicated_queue_index(type);
|
||||
if (!index.has_value()) return { index.error() };
|
||||
VkQueue out_queue;
|
||||
@ -1491,7 +1484,7 @@ void destroy_device(Device device) {
|
||||
|
||||
DeviceBuilder::DeviceBuilder(PhysicalDevice phys_device) { physical_device = phys_device; }
|
||||
|
||||
detail::Result<Device> DeviceBuilder::build() const {
|
||||
Result<Device> DeviceBuilder::build() const {
|
||||
|
||||
std::vector<CustomQueueDescription> queue_descriptions;
|
||||
queue_descriptions.insert(queue_descriptions.end(), info.queue_descriptions.begin(), info.queue_descriptions.end());
|
||||
@ -1760,9 +1753,9 @@ SwapchainBuilder::SwapchainBuilder(VkPhysicalDevice const physical_device,
|
||||
info.present_queue_index = detail::get_present_queue_index(physical_device, surface, queue_families);
|
||||
}
|
||||
}
|
||||
detail::Result<Swapchain> SwapchainBuilder::build() const {
|
||||
Result<Swapchain> SwapchainBuilder::build() const {
|
||||
if (info.surface == VK_NULL_HANDLE) {
|
||||
return detail::Error{ SwapchainError::surface_handle_not_provided };
|
||||
return Error{ SwapchainError::surface_handle_not_provided };
|
||||
}
|
||||
|
||||
auto desired_formats = info.desired_formats;
|
||||
@ -1772,7 +1765,7 @@ detail::Result<Swapchain> SwapchainBuilder::build() const {
|
||||
|
||||
auto surface_support_ret = detail::query_surface_support_details(info.physical_device, info.surface);
|
||||
if (!surface_support_ret.has_value())
|
||||
return detail::Error{ SwapchainError::failed_query_surface_support_details, surface_support_ret.vk_result() };
|
||||
return Error{ SwapchainError::failed_query_surface_support_details, surface_support_ret.vk_result() };
|
||||
auto surface_support = surface_support_ret.value();
|
||||
|
||||
uint32_t image_count = info.min_image_count;
|
||||
@ -1848,7 +1841,7 @@ detail::Result<Swapchain> SwapchainBuilder::build() const {
|
||||
auto res = swapchain_create_proc(info.device, &swapchain_create_info, info.allocation_callbacks, &swapchain.swapchain);
|
||||
|
||||
if (res != VK_SUCCESS) {
|
||||
return detail::Error{ SwapchainError::failed_create_swapchain, res };
|
||||
return Error{ SwapchainError::failed_create_swapchain, res };
|
||||
}
|
||||
swapchain.device = info.device;
|
||||
swapchain.image_format = surface_format.format;
|
||||
@ -1862,7 +1855,7 @@ detail::Result<Swapchain> SwapchainBuilder::build() const {
|
||||
info.device, swapchain.internal_table.fp_vkDestroySwapchainKHR, "vkDestroySwapchainKHR");
|
||||
auto images = swapchain.get_images();
|
||||
if (!images) {
|
||||
return detail::Error{ SwapchainError::failed_get_swapchain_images };
|
||||
return Error{ SwapchainError::failed_get_swapchain_images };
|
||||
}
|
||||
swapchain.requested_min_image_count = image_count;
|
||||
swapchain.present_mode = present_mode;
|
||||
@ -1870,18 +1863,18 @@ detail::Result<Swapchain> SwapchainBuilder::build() const {
|
||||
swapchain.allocation_callbacks = info.allocation_callbacks;
|
||||
return swapchain;
|
||||
}
|
||||
detail::Result<std::vector<VkImage>> Swapchain::get_images() {
|
||||
Result<std::vector<VkImage>> Swapchain::get_images() {
|
||||
std::vector<VkImage> swapchain_images;
|
||||
|
||||
auto swapchain_images_ret =
|
||||
detail::get_vector<VkImage>(swapchain_images, internal_table.fp_vkGetSwapchainImagesKHR, device, swapchain);
|
||||
if (swapchain_images_ret != VK_SUCCESS) {
|
||||
return detail::Error{ SwapchainError::failed_get_swapchain_images, swapchain_images_ret };
|
||||
return Error{ SwapchainError::failed_get_swapchain_images, swapchain_images_ret };
|
||||
}
|
||||
return swapchain_images;
|
||||
}
|
||||
detail::Result<std::vector<VkImageView>> Swapchain::get_image_views() { return get_image_views(nullptr); }
|
||||
detail::Result<std::vector<VkImageView>> Swapchain::get_image_views(const void* pNext) {
|
||||
Result<std::vector<VkImageView>> Swapchain::get_image_views() { return get_image_views(nullptr); }
|
||||
Result<std::vector<VkImageView>> Swapchain::get_image_views(const void* pNext) {
|
||||
const auto swapchain_images_ret = get_images();
|
||||
if (!swapchain_images_ret) return swapchain_images_ret.error();
|
||||
const auto swapchain_images = swapchain_images_ret.value();
|
||||
@ -1904,9 +1897,8 @@ detail::Result<std::vector<VkImageView>> Swapchain::get_image_views(const void*
|
||||
createInfo.subresourceRange.levelCount = 1;
|
||||
createInfo.subresourceRange.baseArrayLayer = 0;
|
||||
createInfo.subresourceRange.layerCount = 1;
|
||||
|
||||
VkResult res = internal_table.fp_vkCreateImageView(device, &createInfo, allocation_callbacks, &views[i]);
|
||||
if (res != VK_SUCCESS) return detail::Error{ SwapchainError::failed_create_swapchain_image_views, res };
|
||||
if (res != VK_SUCCESS) return Error{ SwapchainError::failed_create_swapchain_image_views, res };
|
||||
}
|
||||
return views;
|
||||
}
|
||||
|
@ -52,8 +52,6 @@
|
||||
|
||||
namespace vkb {
|
||||
|
||||
namespace detail {
|
||||
|
||||
struct Error {
|
||||
std::error_code type;
|
||||
VkResult vk_result = VK_SUCCESS; // optional error value if a vulkan call failed
|
||||
@ -61,75 +59,76 @@ struct Error {
|
||||
|
||||
template <typename T> class Result {
|
||||
public:
|
||||
Result(const T& value) : m_value{ value }, m_init{ true } {}
|
||||
Result(T&& value) : m_value{ std::move(value) }, m_init{ true } {}
|
||||
Result(const T& value) noexcept : m_value{ value }, m_init{ true } {}
|
||||
Result(T&& value) noexcept : m_value{ std::move(value) }, m_init{ true } {}
|
||||
|
||||
Result(Error error) : m_error{ error }, m_init{ false } {}
|
||||
Result(Error error) noexcept : m_error{ error }, m_init{ false } {}
|
||||
|
||||
Result(std::error_code error_code, VkResult result = VK_SUCCESS) : m_error{ error_code, result }, m_init{ false } {}
|
||||
Result(std::error_code error_code, VkResult result = VK_SUCCESS) noexcept
|
||||
: m_error{ error_code, result }, m_init{ false } {}
|
||||
|
||||
~Result() { destroy(); }
|
||||
Result(Result const& expected) : m_init(expected.m_init) {
|
||||
~Result() noexcept { destroy(); }
|
||||
Result(Result const& expected) noexcept : m_init(expected.m_init) {
|
||||
if (m_init)
|
||||
new (&m_value) T{ expected.m_value };
|
||||
else
|
||||
m_error = expected.m_error;
|
||||
}
|
||||
Result& operator=(Result const& result) {
|
||||
Result& operator=(Result const& result) noexcept {
|
||||
m_init = result.m_init;
|
||||
if (m_init)
|
||||
new (&m_value) T{ result.m_value };
|
||||
else
|
||||
m_error = result.m_error;
|
||||
}
|
||||
Result(Result&& expected) : m_init(expected.m_init) {
|
||||
Result(Result&& expected) noexcept : m_init(expected.m_init) {
|
||||
if (m_init)
|
||||
new (&m_value) T{ std::move(expected.m_value) };
|
||||
else
|
||||
m_error = std::move(expected.m_error);
|
||||
expected.destroy();
|
||||
}
|
||||
Result& operator=(Result&& result) {
|
||||
Result& operator=(Result&& result) noexcept {
|
||||
m_init = result.m_init;
|
||||
if (m_init)
|
||||
new (&m_value) T{ std::move(result.m_value) };
|
||||
else
|
||||
m_error = std::move(result.m_error);
|
||||
}
|
||||
Result& operator=(const T& expect) {
|
||||
Result& operator=(const T& expect) noexcept {
|
||||
destroy();
|
||||
m_init = true;
|
||||
new (&m_value) T{ expect };
|
||||
return *this;
|
||||
}
|
||||
Result& operator=(T&& expect) {
|
||||
Result& operator=(T&& expect) noexcept {
|
||||
destroy();
|
||||
m_init = true;
|
||||
new (&m_value) T{ std::move(expect) };
|
||||
return *this;
|
||||
}
|
||||
Result& operator=(const Error& error) {
|
||||
Result& operator=(const Error& error) noexcept {
|
||||
destroy();
|
||||
m_init = false;
|
||||
m_error = error;
|
||||
return *this;
|
||||
}
|
||||
Result& operator=(Error&& error) {
|
||||
Result& operator=(Error&& error) noexcept {
|
||||
destroy();
|
||||
m_init = false;
|
||||
m_error = error;
|
||||
return *this;
|
||||
}
|
||||
// clang-format off
|
||||
const T* operator-> () const { assert (m_init); return &m_value; }
|
||||
T* operator-> () { assert (m_init); return &m_value; }
|
||||
const T& operator* () const& { assert (m_init); return m_value; }
|
||||
T& operator* () & { assert (m_init); return m_value; }
|
||||
T&& operator* () && { assert (m_init); return std::move (m_value); }
|
||||
const T& value () const& { assert (m_init); return m_value; }
|
||||
T& value () & { assert (m_init); return m_value; }
|
||||
const T&& value () const&& { assert (m_init); return std::move (m_value); }
|
||||
T&& value () && { assert (m_init); return std::move (m_value); }
|
||||
const T* operator-> () const noexcept { assert (m_init); return &m_value; }
|
||||
T* operator-> () noexcept { assert (m_init); return &m_value; }
|
||||
const T& operator* () const& noexcept { assert (m_init); return m_value; }
|
||||
T& operator* () & noexcept { assert (m_init); return m_value; }
|
||||
T&& operator* () && noexcept { assert (m_init); return std::move (m_value); }
|
||||
const T& value () const& noexcept { assert (m_init); return m_value; }
|
||||
T& value () & noexcept { assert (m_init); return m_value; }
|
||||
const T&& value () const&& noexcept { assert (m_init); return std::move (m_value); }
|
||||
T&& value () && noexcept { assert (m_init); return std::move (m_value); }
|
||||
|
||||
// std::error_code associated with the error
|
||||
std::error_code error() const { assert (!m_init); return m_error.type; }
|
||||
@ -139,6 +138,11 @@ template <typename T> class Result {
|
||||
Error full_error() const { assert (!m_init); return m_error; }
|
||||
// clang-format on
|
||||
|
||||
// check if the result has an error that matches a specific error case
|
||||
template <typename E> bool matches_error(E error_enum_value) const {
|
||||
return !m_init && static_cast<E>(m_error.type.value()) == error_enum_value;
|
||||
}
|
||||
|
||||
bool has_value() const { return m_init; }
|
||||
explicit operator bool() const { return m_init; }
|
||||
|
||||
@ -153,6 +157,7 @@ template <typename T> class Result {
|
||||
bool m_init;
|
||||
};
|
||||
|
||||
namespace detail {
|
||||
struct GenericFeaturesPNextNode {
|
||||
|
||||
static const uint32_t field_capacity = 256;
|
||||
@ -234,8 +239,8 @@ struct SystemInfo {
|
||||
|
||||
public:
|
||||
// Use get_system_info to create a SystemInfo struct. This is because loading vulkan could fail.
|
||||
static detail::Result<SystemInfo> get_system_info();
|
||||
static detail::Result<SystemInfo> get_system_info(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcAddr);
|
||||
static Result<SystemInfo> get_system_info();
|
||||
static Result<SystemInfo> get_system_info(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcAddr);
|
||||
|
||||
// Returns true if a layer is available
|
||||
bool is_layer_available(const char* layer_name) const;
|
||||
@ -321,7 +326,7 @@ class InstanceBuilder {
|
||||
explicit InstanceBuilder(PFN_vkGetInstanceProcAddr fp_vkGetInstanceProcAddr);
|
||||
|
||||
// Create a VkInstance. Return an error if it failed.
|
||||
detail::Result<Instance> build() const;
|
||||
Result<Instance> build() const;
|
||||
|
||||
// Sets the name of the application. Defaults to "" if none is provided.
|
||||
InstanceBuilder& set_app_name(const char* app_name);
|
||||
@ -526,14 +531,14 @@ class PhysicalDeviceSelector {
|
||||
|
||||
// Return the first device which is suitable
|
||||
// use the `selection` parameter to configure if partially
|
||||
detail::Result<PhysicalDevice> select(DeviceSelectionMode selection = DeviceSelectionMode::partially_and_fully_suitable) const;
|
||||
Result<PhysicalDevice> select(DeviceSelectionMode selection = DeviceSelectionMode::partially_and_fully_suitable) const;
|
||||
|
||||
// Return all devices which are considered suitable - intended for applications which want to let the user pick the physical device
|
||||
detail::Result<std::vector<PhysicalDevice>> select_devices(
|
||||
Result<std::vector<PhysicalDevice>> select_devices(
|
||||
DeviceSelectionMode selection = DeviceSelectionMode::partially_and_fully_suitable) const;
|
||||
|
||||
// Return the names of all devices which are considered suitable - intended for applications which want to let the user pick the physical device
|
||||
detail::Result<std::vector<std::string>> select_device_names(
|
||||
Result<std::vector<std::string>> select_device_names(
|
||||
DeviceSelectionMode selection = DeviceSelectionMode::partially_and_fully_suitable) const;
|
||||
|
||||
// Set the surface in which the physical device should render to.
|
||||
@ -661,7 +666,7 @@ class PhysicalDeviceSelector {
|
||||
|
||||
PhysicalDevice::Suitable is_device_suitable(PhysicalDevice const& phys_device) const;
|
||||
|
||||
detail::Result<std::vector<PhysicalDevice>> select_impl(DeviceSelectionMode selection) const;
|
||||
Result<std::vector<PhysicalDevice>> select_impl(DeviceSelectionMode selection) const;
|
||||
};
|
||||
|
||||
// ---- Queue ---- //
|
||||
@ -682,13 +687,13 @@ struct Device {
|
||||
VkAllocationCallbacks* allocation_callbacks = VK_NULL_HANDLE;
|
||||
PFN_vkGetDeviceProcAddr fp_vkGetDeviceProcAddr = nullptr;
|
||||
|
||||
detail::Result<uint32_t> get_queue_index(QueueType type) const;
|
||||
Result<uint32_t> get_queue_index(QueueType type) const;
|
||||
// Only a compute or transfer queue type is valid. All other queue types do not support a 'dedicated' queue index
|
||||
detail::Result<uint32_t> get_dedicated_queue_index(QueueType type) const;
|
||||
Result<uint32_t> get_dedicated_queue_index(QueueType type) const;
|
||||
|
||||
detail::Result<VkQueue> get_queue(QueueType type) const;
|
||||
Result<VkQueue> get_queue(QueueType type) const;
|
||||
// Only a compute or transfer queue type is valid. All other queue types do not support a 'dedicated' queue
|
||||
detail::Result<VkQueue> get_dedicated_queue(QueueType type) const;
|
||||
Result<VkQueue> get_dedicated_queue(QueueType type) const;
|
||||
|
||||
// Return a loaded dispatch table
|
||||
DispatchTable make_table() const;
|
||||
@ -721,7 +726,7 @@ class DeviceBuilder {
|
||||
// Any features and extensions that are requested/required in PhysicalDeviceSelector are automatically enabled.
|
||||
explicit DeviceBuilder(PhysicalDevice physical_device);
|
||||
|
||||
detail::Result<Device> build() const;
|
||||
Result<Device> build() const;
|
||||
|
||||
// For Advanced Users: specify the exact list of VkDeviceQueueCreateInfo's needed for the application.
|
||||
// If a custom queue setup is provided, getting the queues and queue indexes is up to the application.
|
||||
@ -760,13 +765,13 @@ struct Swapchain {
|
||||
VkAllocationCallbacks* allocation_callbacks = VK_NULL_HANDLE;
|
||||
|
||||
// Returns a vector of VkImage handles to the swapchain.
|
||||
detail::Result<std::vector<VkImage>> get_images();
|
||||
Result<std::vector<VkImage>> get_images();
|
||||
|
||||
// Returns a vector of VkImageView's to the VkImage's of the swapchain.
|
||||
// VkImageViews must be destroyed. The pNext chain must be a nullptr or a valid
|
||||
// structure.
|
||||
detail::Result<std::vector<VkImageView>> get_image_views();
|
||||
detail::Result<std::vector<VkImageView>> get_image_views(const void* pNext);
|
||||
Result<std::vector<VkImageView>> get_image_views();
|
||||
Result<std::vector<VkImageView>> get_image_views(const void* pNext);
|
||||
void destroy_image_views(std::vector<VkImageView> const& image_views);
|
||||
|
||||
// A conversion function which allows this Swapchain to be used
|
||||
@ -801,7 +806,7 @@ class SwapchainBuilder {
|
||||
uint32_t graphics_queue_index = detail::QUEUE_INDEX_MAX_VALUE,
|
||||
uint32_t present_queue_index = detail::QUEUE_INDEX_MAX_VALUE);
|
||||
|
||||
detail::Result<Swapchain> build() const;
|
||||
Result<Swapchain> build() const;
|
||||
|
||||
// Set the oldSwapchain member of VkSwapchainCreateInfoKHR.
|
||||
// For use in rebuilding a swapchain.
|
||||
|
Loading…
Reference in New Issue
Block a user