diff --git a/src/graphics/d3d12.rs b/src/graphics/d3d12.rs index b696af4..e162197 100644 --- a/src/graphics/d3d12.rs +++ b/src/graphics/d3d12.rs @@ -33,7 +33,9 @@ use crate::VIEW_TYPE; pub fn initialize_xr_instance( window: Option, + xr_entry: xr::Entry, reqeusted_extensions: XrExtensions, + available_extensions: XrExtensions, prefered_blend_mode: XrPreferdBlendMode, app_info: XrAppInfo, ) -> eyre::Result<( @@ -46,12 +48,9 @@ pub fn initialize_xr_instance( RenderAdapter, Instance, )> { - let xr_entry = super::xr_entry()?; - #[cfg(target_os = "android")] xr_entry.initialize_android_loader()?; - let available_extensions: XrExtensions = xr_entry.enumerate_extensions()?.into(); assert!(available_extensions.raw().khr_d3d12_enable); //info!("available xr exts: {:#?}", available_extensions); diff --git a/src/graphics/mod.rs b/src/graphics/mod.rs index 4256cfb..67bff10 100644 --- a/src/graphics/mod.rs +++ b/src/graphics/mod.rs @@ -21,6 +21,8 @@ use crate::resources::{ }; use crate::OXrSessionSetupInfo; +use crate::Backend; + use openxr as xr; use self::extensions::XrExtensions; @@ -91,6 +93,7 @@ pub fn start_xr_session( } } pub fn initialize_xr_instance( + backend_preference: &[Backend], window: Option, reqeusted_extensions: XrExtensions, prefered_blend_mode: XrPreferdBlendMode, @@ -105,18 +108,57 @@ pub fn initialize_xr_instance( RenderAdapter, Instance, )> { - #[cfg(feature = "vulkan")] - { - vulkan::initialize_xr_instance(window, reqeusted_extensions, prefered_blend_mode, app_info) + if backend_preference.is_empty() { + eyre::bail!("Cannot initialize with no backend selected"); } - #[cfg(feature = "d3d12")] - { - d3d12::initialize_xr_instance(window, reqeusted_extensions, prefered_blend_mode, app_info) + let xr_entry = xr_entry()?; + + #[cfg(target_os = "android")] + xr_entry.initialize_android_loader()?; + + let available_extensions: XrExtensions = xr_entry.enumerate_extensions()?.into(); + + for backend in backend_preference { + match backend { + #[cfg(feature = "vulkan")] + Backend::Vulkan => { + if !available_extensions.raw().khr_vulkan_enable2 { + continue; + } + return vulkan::initialize_xr_instance( + window, + xr_entry, + reqeusted_extensions, + available_extensions, + prefered_blend_mode, + app_info, + ); + } + #[cfg(feature = "d3d12")] + Backend::D3D12 => { + if !available_extensions.raw().khr_d3d12_enable { + continue; + } + return d3d12::initialize_xr_instance( + window, + xr_entry, + reqeusted_extensions, + available_extensions, + prefered_blend_mode, + app_info, + ); + } + } } + eyre::bail!( + "No selected backend was supported by the runtime. Selected: {:?}", + backend_preference + ); } pub fn try_full_init( world: &mut World, + backend_preference: &[Backend], reqeusted_extensions: XrExtensions, prefered_blend_mode: XrPreferdBlendMode, app_info: XrAppInfo, @@ -140,6 +182,7 @@ pub fn try_full_init( render_adapter, wgpu_instance, ) = initialize_xr_instance( + backend_preference, primary_window.clone(), reqeusted_extensions, prefered_blend_mode, diff --git a/src/graphics/vulkan.rs b/src/graphics/vulkan.rs index 6a5379d..72c5d00 100644 --- a/src/graphics/vulkan.rs +++ b/src/graphics/vulkan.rs @@ -28,7 +28,9 @@ use super::{XrAppInfo, XrPreferdBlendMode}; pub fn initialize_xr_instance( window: Option, + xr_entry: xr::Entry, reqeusted_extensions: XrExtensions, + available_extensions: XrExtensions, prefered_blend_mode: XrPreferdBlendMode, app_info: XrAppInfo, ) -> eyre::Result<( @@ -41,12 +43,9 @@ pub fn initialize_xr_instance( RenderAdapter, Instance, )> { - let xr_entry = super::xr_entry()?; - #[cfg(target_os = "android")] xr_entry.initialize_android_loader()?; - let available_extensions: XrExtensions = xr_entry.enumerate_extensions()?.into(); assert!(available_extensions.raw().khr_vulkan_enable2); //info!("available xr exts: {:#?}", available_extensions); diff --git a/src/lib.rs b/src/lib.rs index b1c6122..80e2bff 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -47,6 +47,7 @@ pub const RIGHT_XR_TEXTURE_HANDLE: ManualTextureViewHandle = ManualTextureViewHa /// Adds OpenXR support to an App pub struct OpenXrPlugin { + pub backend_preference: Vec, pub reqeusted_extensions: XrExtensions, pub prefered_blend_mode: XrPreferdBlendMode, pub app_info: XrAppInfo, @@ -59,6 +60,7 @@ impl Plugin for OpenXrPlugin { app.insert_resource(ExitAppOnSessionExit::default()); #[cfg(not(target_arch = "wasm32"))] match graphics::initialize_xr_instance( + &self.backend_preference, SystemState::>>::new(&mut app.world) .get(&app.world) .get_single() @@ -169,6 +171,14 @@ impl Plugin for OpenXrPlugin { } } +#[derive(Debug)] +pub enum Backend { + #[cfg(feature = "vulkan")] + Vulkan, + #[cfg(feature = "d3d12")] + D3D12, +} + #[derive(Resource)] struct DoPipelinedRendering; @@ -230,6 +240,7 @@ fn xr_skip_frame( } pub struct DefaultXrPlugins { + pub backend_preference: Vec, pub reqeusted_extensions: XrExtensions, pub prefered_blend_mode: XrPreferdBlendMode, pub app_info: XrAppInfo, @@ -238,6 +249,12 @@ pub struct DefaultXrPlugins { impl Default for DefaultXrPlugins { fn default() -> Self { Self { + backend_preference: vec![ + #[cfg(feature = "vulkan")] + Backend::Vulkan, + #[cfg(feature = "d3d12")] + Backend::D3D12, + ], reqeusted_extensions: default(), prefered_blend_mode: default(), app_info: default(), @@ -263,6 +280,7 @@ impl PluginGroup for DefaultXrPlugins { }) .disable::() .add_before::(OpenXrPlugin { + backend_preference: self.backend_preference, prefered_blend_mode: self.prefered_blend_mode, reqeusted_extensions: self.reqeusted_extensions, app_info: self.app_info.clone(),