This commit is contained in:
parent
bc94b68c0c
commit
e9ce480f96
10 changed files with 175 additions and 136 deletions
|
@ -21,7 +21,8 @@ impl App {
|
|||
|
||||
impl ApplicationHandler for App {
|
||||
fn resumed(&mut self, event_loop: &ActiveEventLoop) {
|
||||
self.window.create_window(event_loop)
|
||||
self.window
|
||||
.create_window(event_loop)
|
||||
.map_err(|err| format!("Failed to create window: {}", err))
|
||||
.unwrap();
|
||||
|
||||
|
@ -37,22 +38,29 @@ impl ApplicationHandler for App {
|
|||
WindowEvent::Resized(size) => {
|
||||
match self.render_context.as_mut() {
|
||||
Some(render_context) => {
|
||||
if let Err(error) = render_context.update_resolution(size.width, size.height) {
|
||||
log::error!("Failed to update resolution of render context : {}", error);
|
||||
if let Err(error) =
|
||||
render_context.update_resolution(size.width, size.height)
|
||||
{
|
||||
log::error!(
|
||||
"Failed to update resolution of render context : {}",
|
||||
error
|
||||
);
|
||||
}
|
||||
}
|
||||
None => log::warn!("Window resized but no render context found")
|
||||
None => log::warn!("Window resized but no render context found"),
|
||||
};
|
||||
}
|
||||
WindowEvent::RedrawRequested => {
|
||||
match self.render_context.as_mut() {
|
||||
Some(render_context) => {
|
||||
if let Err(error) = render_context.render() {
|
||||
log::error!("Failed to render with render context : {}", error);
|
||||
if !event_loop.exiting() {
|
||||
match self.render_context.as_mut() {
|
||||
Some(render_context) => {
|
||||
if let Err(error) = render_context.render() {
|
||||
log::error!("Failed to render with render context : {}", error);
|
||||
}
|
||||
}
|
||||
}
|
||||
None => log::warn!("Window resized but no render context found")
|
||||
};
|
||||
None => log::warn!("Window resized but no render context found"),
|
||||
};
|
||||
}
|
||||
|
||||
self.window.request_redraw();
|
||||
}
|
||||
|
|
|
@ -2,4 +2,4 @@ mod app;
|
|||
mod window;
|
||||
|
||||
pub use app::App;
|
||||
pub use window::Window;
|
||||
pub use window::Window;
|
||||
|
|
|
@ -24,14 +24,15 @@ impl Window {
|
|||
}
|
||||
|
||||
pub fn required_extensions(&self) -> anyhow::Result<Vec<*const c_char>> {
|
||||
let display_handle = self.handle
|
||||
let display_handle = self
|
||||
.handle
|
||||
.as_ref()
|
||||
.ok_or_else(|| anyhow::anyhow!("Window not found"))?
|
||||
.display_handle()?;
|
||||
|
||||
#[allow(unused_mut)]
|
||||
let mut extension_names = ash_window::enumerate_required_extensions(display_handle.as_raw())?
|
||||
.to_vec();
|
||||
let mut extension_names =
|
||||
ash_window::enumerate_required_extensions(display_handle.as_raw())?.to_vec();
|
||||
|
||||
// TODO: Move this because is not related to Window extensions
|
||||
#[cfg(any(target_os = "macos", target_os = "ios"))]
|
||||
|
@ -55,7 +56,7 @@ impl Window {
|
|||
pub fn request_redraw(&self) {
|
||||
match self.handle.as_ref() {
|
||||
Some(window) => window.request_redraw(),
|
||||
None => log::warn!("Redraw requested but no window found")
|
||||
None => log::warn!("Redraw requested but no window found"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,17 +3,15 @@ use std::ffi::CString;
|
|||
pub enum LayersSelector<'a> {
|
||||
Nothing,
|
||||
SpecificLayers(Vec<&'a str>),
|
||||
All
|
||||
All,
|
||||
}
|
||||
|
||||
pub fn use_layers(
|
||||
entry: &ash::Entry,
|
||||
selector: LayersSelector,
|
||||
) -> Vec<CString> {
|
||||
pub fn use_layers(entry: &ash::Entry, selector: LayersSelector) -> Vec<CString> {
|
||||
let layers_available = get_layers_available(entry)
|
||||
.iter()
|
||||
.filter_map(|layer| {
|
||||
layer.layer_name_as_c_str()
|
||||
layer
|
||||
.layer_name_as_c_str()
|
||||
.and_then(|layer_name| Ok(CString::from(layer_name)))
|
||||
.ok()
|
||||
})
|
||||
|
@ -27,18 +25,20 @@ pub fn use_layers(
|
|||
}
|
||||
|
||||
fn get_layers_available(entry: &ash::Entry) -> Vec<ash::vk::LayerProperties> {
|
||||
unsafe { entry.enumerate_instance_layer_properties().unwrap_or_default() }
|
||||
unsafe {
|
||||
entry
|
||||
.enumerate_instance_layer_properties()
|
||||
.unwrap_or_default()
|
||||
}
|
||||
}
|
||||
|
||||
fn select_layers(
|
||||
layers_available: &Vec<CString>,
|
||||
layers_to_select: &[&str],
|
||||
) -> Vec<CString> {
|
||||
fn select_layers(layers_available: &Vec<CString>, layers_to_select: &[&str]) -> Vec<CString> {
|
||||
layers_to_select
|
||||
.iter()
|
||||
.filter_map(|layer_name| {
|
||||
if layers_available.iter().any(|layer_available| {
|
||||
layer_available.to_str()
|
||||
layer_available
|
||||
.to_str()
|
||||
.and_then(|layer_available| Ok(layer_available.eq(*layer_name)))
|
||||
.unwrap_or(false)
|
||||
}) {
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
use std::sync::Arc;
|
||||
use crate::vulkan::{VkInstance, VkPhysicalDevice, LOG_TARGET};
|
||||
use ash::prelude::VkResult;
|
||||
use ash::vk;
|
||||
use std::sync::Arc;
|
||||
|
||||
pub struct VkDevice {
|
||||
instance: Arc<VkInstance>,
|
||||
|
@ -37,7 +37,9 @@ impl VkDevice {
|
|||
.enabled_features(&features);
|
||||
|
||||
let device = unsafe {
|
||||
instance.handle.create_device(physical_device.handle, &device_create_info, None)?
|
||||
instance
|
||||
.handle
|
||||
.create_device(physical_device.handle, &device_create_info, None)?
|
||||
};
|
||||
log::debug!(target: LOG_TARGET, "Device created ({:?})", device.handle());
|
||||
|
||||
|
@ -53,11 +55,16 @@ impl VkDevice {
|
|||
|
||||
pub(super) fn get_device_queue(&self, queue_index: u32) -> vk::Queue {
|
||||
unsafe {
|
||||
self.handle.get_device_queue(self.queue_family_index, queue_index)
|
||||
self.handle
|
||||
.get_device_queue(self.queue_family_index, queue_index)
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) fn create_image_view(&self, image: vk::Image, surface_format: vk::SurfaceFormatKHR) -> VkResult<vk::ImageView> {
|
||||
pub(super) fn create_image_view(
|
||||
&self,
|
||||
image: vk::Image,
|
||||
surface_format: vk::SurfaceFormatKHR,
|
||||
) -> VkResult<vk::ImageView> {
|
||||
let create_view_info = vk::ImageViewCreateInfo::default()
|
||||
.view_type(vk::ImageViewType::TYPE_2D)
|
||||
.format(surface_format.format)
|
||||
|
@ -79,13 +86,19 @@ impl VkDevice {
|
|||
unsafe { self.handle.create_image_view(&create_view_info, None) }
|
||||
}
|
||||
|
||||
pub(super) fn create_command_pool(&self, info: &vk::CommandPoolCreateInfo) -> VkResult<vk::CommandPool> {
|
||||
pub(super) fn create_command_pool(
|
||||
&self,
|
||||
info: &vk::CommandPoolCreateInfo,
|
||||
) -> VkResult<vk::CommandPool> {
|
||||
let info = info.queue_family_index(self.queue_family_index);
|
||||
|
||||
unsafe { self.handle.create_command_pool(&info, None) }
|
||||
}
|
||||
|
||||
pub(super) fn allocate_command_buffers(&self, info: &vk::CommandBufferAllocateInfo) -> VkResult<Vec<vk::CommandBuffer>> {
|
||||
pub(super) fn allocate_command_buffers(
|
||||
&self,
|
||||
info: &vk::CommandBufferAllocateInfo,
|
||||
) -> VkResult<Vec<vk::CommandBuffer>> {
|
||||
unsafe { self.handle.allocate_command_buffers(&info) }
|
||||
}
|
||||
|
||||
|
@ -93,7 +106,10 @@ impl VkDevice {
|
|||
unsafe { self.handle.create_fence(&info, None) }
|
||||
}
|
||||
|
||||
pub(super) fn create_semaphore(&self, info: &vk::SemaphoreCreateInfo) -> VkResult<vk::Semaphore> {
|
||||
pub(super) fn create_semaphore(
|
||||
&self,
|
||||
info: &vk::SemaphoreCreateInfo,
|
||||
) -> VkResult<vk::Semaphore> {
|
||||
unsafe { self.handle.create_semaphore(&info, None) }
|
||||
}
|
||||
}
|
||||
|
@ -105,4 +121,4 @@ impl Drop for VkDevice {
|
|||
log::debug!(target: LOG_TARGET, "Device destroyed ({:?})", self.handle.handle());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,20 +11,22 @@ pub struct VkInstance {
|
|||
}
|
||||
|
||||
impl VkInstance {
|
||||
pub fn new(
|
||||
required_extensions: &Vec<*const c_char>,
|
||||
) -> Self {
|
||||
pub fn new(required_extensions: &Vec<*const c_char>) -> Self {
|
||||
let entry = Entry::linked();
|
||||
|
||||
log::debug!(target: LOG_TARGET, "Initializing Vulkan instance");
|
||||
|
||||
if log::log_enabled!(target: LOG_TARGET, log::Level::Debug) {
|
||||
let layer_properties = unsafe { entry.enumerate_instance_layer_properties() }
|
||||
.unwrap_or_default();
|
||||
let layer_properties =
|
||||
unsafe { entry.enumerate_instance_layer_properties() }.unwrap_or_default();
|
||||
|
||||
for layer_property in layer_properties {
|
||||
let layer_extensions = unsafe { entry.enumerate_instance_extension_properties(layer_property.layer_name_as_c_str().ok()) }
|
||||
.unwrap_or_default();
|
||||
let layer_extensions = unsafe {
|
||||
entry.enumerate_instance_extension_properties(
|
||||
layer_property.layer_name_as_c_str().ok(),
|
||||
)
|
||||
}
|
||||
.unwrap_or_default();
|
||||
log::debug!(target: LOG_TARGET, "{layer_property:#?} {layer_extensions:#?}");
|
||||
}
|
||||
}
|
||||
|
@ -44,12 +46,13 @@ impl VkInstance {
|
|||
LayersSelector::SpecificLayers(vec![
|
||||
"VK_LAYER_KHRONOS_validation",
|
||||
"VK_LAYER_MANGOHUD_overlay_x86_64",
|
||||
"VK_LAYER_NV_optimus"
|
||||
"VK_LAYER_NV_optimus",
|
||||
]),
|
||||
);
|
||||
|
||||
{
|
||||
let layers = layers.iter()
|
||||
let layers = layers
|
||||
.iter()
|
||||
.map(|layer| layer.to_string_lossy())
|
||||
.collect::<Vec<_>>();
|
||||
log::debug!(target: LOG_TARGET, "Selected debug layers : {}", layers.join(", "))
|
||||
|
@ -92,7 +95,7 @@ impl VkInstance {
|
|||
Self {
|
||||
entry,
|
||||
handle: instance,
|
||||
surface_loader
|
||||
surface_loader,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -100,14 +103,17 @@ impl VkInstance {
|
|||
let physical_devices = unsafe { self.handle.enumerate_physical_devices() };
|
||||
physical_devices
|
||||
.unwrap_or_default()
|
||||
.iter().map(|physical_device| VkPhysicalDevice::new(&self.handle, *physical_device))
|
||||
.iter()
|
||||
.map(|physical_device| VkPhysicalDevice::new(&self.handle, *physical_device))
|
||||
.collect()
|
||||
}
|
||||
}
|
||||
|
||||
impl Drop for VkInstance {
|
||||
fn drop(&mut self) {
|
||||
unsafe { self.handle.destroy_instance(None); }
|
||||
unsafe {
|
||||
self.handle.destroy_instance(None);
|
||||
}
|
||||
log::debug!(target: LOG_TARGET, "Vulkan instance destroyed ({:?})", self.handle.handle());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use crate::vulkan::vk_surface::VkSurface;
|
||||
use ash::vk;
|
||||
use crate::vulkan::LOG_TARGET;
|
||||
use ash::vk;
|
||||
|
||||
pub struct VkPhysicalDevice {
|
||||
// Vulkan properties
|
||||
|
@ -34,24 +34,18 @@ impl VkPhysicalDevice {
|
|||
queue_flags: Option<vk::QueueFlags>,
|
||||
surface: Option<&VkSurface>,
|
||||
) -> Option<(u32, &vk::QueueFamilyProperties)> {
|
||||
self.queue_family_properties
|
||||
.iter()
|
||||
.enumerate()
|
||||
.find_map(|(index, queue_family_property)| {
|
||||
self.queue_family_properties.iter().enumerate().find_map(
|
||||
|(index, queue_family_property)| {
|
||||
let surface_check_passed = match surface {
|
||||
Some(surface) => {
|
||||
surface.physical_device_queue_supported(self, index as u32)
|
||||
.unwrap_or(false)
|
||||
}
|
||||
Some(surface) => surface
|
||||
.physical_device_queue_supported(self, index as u32)
|
||||
.unwrap_or(false),
|
||||
None => true,
|
||||
};
|
||||
|
||||
let queue_flags_check_passed = match queue_flags {
|
||||
Some(queue_flags) => {
|
||||
queue_family_property.queue_flags
|
||||
.contains(queue_flags)
|
||||
}
|
||||
None => true
|
||||
Some(queue_flags) => queue_family_property.queue_flags.contains(queue_flags),
|
||||
None => true,
|
||||
};
|
||||
|
||||
if surface_check_passed && queue_flags_check_passed {
|
||||
|
@ -59,7 +53,8 @@ impl VkPhysicalDevice {
|
|||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
},
|
||||
)
|
||||
}
|
||||
|
||||
pub fn pick_physical_device_and_queue_by<'a>(
|
||||
|
@ -67,12 +62,13 @@ impl VkPhysicalDevice {
|
|||
queue_flags: Option<vk::QueueFlags>,
|
||||
surface: Option<&VkSurface>,
|
||||
) -> Option<(&'a VkPhysicalDevice, u32, &'a vk::QueueFamilyProperties)> {
|
||||
physical_devices
|
||||
.iter()
|
||||
.find_map(|physical_device| {
|
||||
physical_device.find_queue_family_by(queue_flags, surface)
|
||||
.and_then(|(queue_index, queue_family_properties)| Some((physical_device, queue_index, queue_family_properties)))
|
||||
})
|
||||
physical_devices.iter().find_map(|physical_device| {
|
||||
physical_device
|
||||
.find_queue_family_by(queue_flags, surface)
|
||||
.and_then(|(queue_index, queue_family_properties)| {
|
||||
Some((physical_device, queue_index, queue_family_properties))
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
pub fn priority(&self) -> usize {
|
||||
|
@ -81,7 +77,7 @@ impl VkPhysicalDevice {
|
|||
vk::PhysicalDeviceType::VIRTUAL_GPU => 2,
|
||||
vk::PhysicalDeviceType::INTEGRATED_GPU => 3,
|
||||
vk::PhysicalDeviceType::DISCRETE_GPU => 4,
|
||||
_ => 0
|
||||
_ => 0,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use std::sync::Arc;
|
||||
use crate::vulkan::{VkDevice, VkInstance, VkPhysicalDevice, VkSurface, VkSwapchain, LOG_TARGET};
|
||||
use ash::vk;
|
||||
use std::sync::Arc;
|
||||
|
||||
pub struct VkRenderContext {
|
||||
instance: Arc<VkInstance>,
|
||||
|
@ -8,7 +8,6 @@ pub struct VkRenderContext {
|
|||
device: Arc<VkDevice>,
|
||||
|
||||
swapchain: Arc<VkSwapchain>,
|
||||
|
||||
// present_queue: vk::Queue,
|
||||
//
|
||||
// pool: vk::CommandPool,
|
||||
|
@ -25,32 +24,34 @@ pub struct VkRenderContext {
|
|||
|
||||
impl VkRenderContext {
|
||||
pub fn init(window: &crate::display::Window) -> anyhow::Result<Self> {
|
||||
let required_extensions = window
|
||||
.required_extensions()?;
|
||||
let required_extensions = window.required_extensions()?;
|
||||
|
||||
let instance = Arc::new(VkInstance::new(&required_extensions));
|
||||
let surface = Arc::new(VkSurface::new(
|
||||
&window,
|
||||
instance.clone()
|
||||
)?);
|
||||
let surface = Arc::new(VkSurface::new(&window, instance.clone())?);
|
||||
|
||||
let mut physical_devices = instance.get_physical_devices();
|
||||
physical_devices.sort_by(|a, b| b.priority().cmp(&a.priority()));
|
||||
|
||||
let (physical_device, queue_family_index, properties) = VkPhysicalDevice::pick_physical_device_and_queue_by(
|
||||
&physical_devices,
|
||||
Some(vk::QueueFlags::GRAPHICS),
|
||||
Some(&surface),
|
||||
).ok_or_else(|| anyhow::anyhow!("Unable to find physical device"))?;
|
||||
let (physical_device, queue_family_index, properties) =
|
||||
VkPhysicalDevice::pick_physical_device_and_queue_by(
|
||||
&physical_devices,
|
||||
Some(vk::QueueFlags::GRAPHICS),
|
||||
Some(&surface),
|
||||
)
|
||||
.ok_or_else(|| anyhow::anyhow!("Unable to find physical device"))?;
|
||||
log::debug!(target: LOG_TARGET, "Selected queue {properties:#?} for physical device {:?}", physical_device.properties.device_name_as_c_str());
|
||||
|
||||
let device = Arc::new(VkDevice::new_graphics_device(instance.clone(), &physical_device, queue_family_index)?);
|
||||
let device = Arc::new(VkDevice::new_graphics_device(
|
||||
instance.clone(),
|
||||
&physical_device,
|
||||
queue_family_index,
|
||||
)?);
|
||||
|
||||
let swapchain = Arc::new(VkSwapchain::new(
|
||||
&window,
|
||||
surface.clone(),
|
||||
device.clone(),
|
||||
&physical_device
|
||||
&physical_device,
|
||||
)?);
|
||||
|
||||
// let present_queue = device.get_device_queue(0);
|
||||
|
@ -97,7 +98,6 @@ impl VkRenderContext {
|
|||
device,
|
||||
|
||||
swapchain,
|
||||
|
||||
// present_queue,
|
||||
//
|
||||
// pool,
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
use std::sync::Arc;
|
||||
use crate::vulkan::{VkInstance, VkPhysicalDevice, LOG_TARGET};
|
||||
use ash::prelude::VkResult;
|
||||
use ash::vk;
|
||||
use std::sync::Arc;
|
||||
use winit::raw_window_handle::{HasDisplayHandle, HasWindowHandle};
|
||||
|
||||
pub struct VkSurface {
|
||||
|
@ -10,11 +10,9 @@ pub struct VkSurface {
|
|||
}
|
||||
|
||||
impl VkSurface {
|
||||
pub fn new(
|
||||
window: &crate::display::Window,
|
||||
instance: Arc<VkInstance>,
|
||||
) -> anyhow::Result<Self> {
|
||||
let window_handle = window.handle()
|
||||
pub fn new(window: &crate::display::Window, instance: Arc<VkInstance>) -> anyhow::Result<Self> {
|
||||
let window_handle = window
|
||||
.handle()
|
||||
.ok_or_else(|| anyhow::anyhow!("Window handle is not available."))?;
|
||||
|
||||
let surface = unsafe {
|
||||
|
@ -29,42 +27,48 @@ impl VkSurface {
|
|||
|
||||
log::debug!(target: LOG_TARGET, "Surface created ({:?})", surface);
|
||||
|
||||
Ok(Self {
|
||||
instance,
|
||||
surface,
|
||||
})
|
||||
Ok(Self { instance, surface })
|
||||
}
|
||||
|
||||
pub fn physical_device_queue_supported(&self, physical_device: &VkPhysicalDevice, queue_index: u32) -> VkResult<bool> {
|
||||
pub fn physical_device_queue_supported(
|
||||
&self,
|
||||
physical_device: &VkPhysicalDevice,
|
||||
queue_index: u32,
|
||||
) -> VkResult<bool> {
|
||||
unsafe {
|
||||
self.instance.surface_loader.get_physical_device_surface_support(
|
||||
physical_device.handle,
|
||||
queue_index,
|
||||
self.surface,
|
||||
)
|
||||
self.instance
|
||||
.surface_loader
|
||||
.get_physical_device_surface_support(
|
||||
physical_device.handle,
|
||||
queue_index,
|
||||
self.surface,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_physical_device_surface_infos(&self, physical_device: &VkPhysicalDevice) -> VkResult<(
|
||||
pub fn get_physical_device_surface_infos(
|
||||
&self,
|
||||
physical_device: &VkPhysicalDevice,
|
||||
) -> VkResult<(
|
||||
Vec<vk::SurfaceFormatKHR>,
|
||||
vk::SurfaceCapabilitiesKHR,
|
||||
Vec<vk::PresentModeKHR>
|
||||
Vec<vk::PresentModeKHR>,
|
||||
)> {
|
||||
unsafe {
|
||||
let formats = self.instance.surface_loader.get_physical_device_surface_formats(
|
||||
physical_device.handle,
|
||||
self.surface,
|
||||
)?;
|
||||
let formats = self
|
||||
.instance
|
||||
.surface_loader
|
||||
.get_physical_device_surface_formats(physical_device.handle, self.surface)?;
|
||||
|
||||
let capabilities = self.instance.surface_loader.get_physical_device_surface_capabilities(
|
||||
physical_device.handle,
|
||||
self.surface,
|
||||
)?;
|
||||
let capabilities = self
|
||||
.instance
|
||||
.surface_loader
|
||||
.get_physical_device_surface_capabilities(physical_device.handle, self.surface)?;
|
||||
|
||||
let present_modes = self.instance.surface_loader.get_physical_device_surface_present_modes(
|
||||
physical_device.handle,
|
||||
self.surface,
|
||||
)?;
|
||||
let present_modes = self
|
||||
.instance
|
||||
.surface_loader
|
||||
.get_physical_device_surface_present_modes(physical_device.handle, self.surface)?;
|
||||
|
||||
Ok((formats, capabilities, present_modes))
|
||||
}
|
||||
|
@ -74,8 +78,10 @@ impl VkSurface {
|
|||
impl Drop for VkSurface {
|
||||
fn drop(&mut self) {
|
||||
unsafe {
|
||||
self.instance.surface_loader.destroy_surface(self.surface, None);
|
||||
self.instance
|
||||
.surface_loader
|
||||
.destroy_surface(self.surface, None);
|
||||
}
|
||||
log::debug!(target: LOG_TARGET, "Surface destroyed ({:?})", self.surface);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
use std::sync::Arc;
|
||||
use crate::display::Window;
|
||||
use crate::vulkan::{VkDevice, VkPhysicalDevice, VkSurface, LOG_TARGET};
|
||||
use ash::prelude::VkResult;
|
||||
use ash::vk;
|
||||
use crate::display::Window;
|
||||
use std::sync::Arc;
|
||||
|
||||
pub struct VkSwapchain {
|
||||
surface: Arc<VkSurface>,
|
||||
|
@ -28,11 +28,8 @@ impl VkSwapchain {
|
|||
) -> anyhow::Result<Self> {
|
||||
log::debug!(target: LOG_TARGET, "Creating swapchain");
|
||||
|
||||
let (
|
||||
surface_formats,
|
||||
surface_capabilities,
|
||||
present_modes
|
||||
) = surface.get_physical_device_surface_infos(physical_device)?;
|
||||
let (surface_formats, surface_capabilities, present_modes) =
|
||||
surface.get_physical_device_surface_infos(physical_device)?;
|
||||
log::debug!(target: LOG_TARGET, "Supported surface formats by physical device: {surface_formats:#?}");
|
||||
log::debug!(target: LOG_TARGET, "Surface capabilities: {surface_capabilities:#?}");
|
||||
|
||||
|
@ -50,7 +47,8 @@ impl VkSwapchain {
|
|||
}
|
||||
log::debug!(target: LOG_TARGET, "Selected surface image count: {desired_image_count}");
|
||||
|
||||
let window_size = window.size()
|
||||
let window_size = window
|
||||
.size()
|
||||
.ok_or_else(|| anyhow::anyhow!("Window size is not valid"))?
|
||||
.to_physical::<u32>(1.0);
|
||||
log::debug!(target: LOG_TARGET, "Window size: {window_size:?}");
|
||||
|
@ -105,14 +103,21 @@ impl VkSwapchain {
|
|||
}
|
||||
|
||||
let swapchain = unsafe {
|
||||
self.device.swapchain_loader.create_swapchain(&swapchain_create_info, None)?
|
||||
self.device
|
||||
.swapchain_loader
|
||||
.create_swapchain(&swapchain_create_info, None)?
|
||||
};
|
||||
|
||||
let present_images = unsafe { self.device.swapchain_loader.get_swapchain_images(swapchain)? };
|
||||
let present_images = unsafe {
|
||||
self.device
|
||||
.swapchain_loader
|
||||
.get_swapchain_images(swapchain)?
|
||||
};
|
||||
let present_images_view = present_images
|
||||
.iter()
|
||||
.map(|i| {
|
||||
self.device.create_image_view(*i, self.surface_format)
|
||||
self.device
|
||||
.create_image_view(*i, self.surface_format)
|
||||
.expect("Failed to create image view")
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
@ -120,7 +125,7 @@ impl VkSwapchain {
|
|||
if log::log_enabled!(target: LOG_TARGET, log::Level::Debug) {
|
||||
let label = match self.swapchain {
|
||||
None => "Swapchain created",
|
||||
Some(_) => "Swapchain updated"
|
||||
Some(_) => "Swapchain updated",
|
||||
};
|
||||
log::debug!(target: LOG_TARGET, "{label} ({swapchain:?}) : {swapchain_create_info:#?}");
|
||||
}
|
||||
|
@ -134,10 +139,7 @@ impl VkSwapchain {
|
|||
|
||||
pub(super) fn update_resolution(&mut self, width: u32, height: u32) -> VkResult<()> {
|
||||
log::debug!(target: LOG_TARGET, "New resolution requested for swapchain {width}x{height}");
|
||||
self.surface_resolution = vk::Extent2D {
|
||||
width,
|
||||
height,
|
||||
};
|
||||
self.surface_resolution = vk::Extent2D { width, height };
|
||||
|
||||
self.create_swapchain()?;
|
||||
|
||||
|
@ -164,9 +166,13 @@ impl VkSwapchain {
|
|||
impl Drop for VkSwapchain {
|
||||
fn drop(&mut self) {
|
||||
if let Some(swapchain) = self.swapchain {
|
||||
unsafe { self.device.swapchain_loader.destroy_swapchain(swapchain, None); }
|
||||
unsafe {
|
||||
self.device
|
||||
.swapchain_loader
|
||||
.destroy_swapchain(swapchain, None);
|
||||
}
|
||||
self.swapchain = None;
|
||||
log::debug!(target: LOG_TARGET, "Swapchain destroyed ({swapchain:?})");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue