Merge pull request #174 from Schmarni-Dev/proper_wgpu_init
More correct wgpu init
This commit is contained in:
1
Cargo.lock
generated
1
Cargo.lock
generated
@@ -878,6 +878,7 @@ dependencies = [
|
|||||||
name = "bevy_mod_openxr"
|
name = "bevy_mod_openxr"
|
||||||
version = "0.1.1"
|
version = "0.1.1"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
|
"android_system_properties",
|
||||||
"ash",
|
"ash",
|
||||||
"bevy",
|
"bevy",
|
||||||
"bevy_mod_xr",
|
"bevy_mod_xr",
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ keywords = ["gamedev", "bevy", "Xr", "Vr", "OpenXR"]
|
|||||||
|
|
||||||
[features]
|
[features]
|
||||||
default = ["vulkan", "d3d12", "passthrough"]
|
default = ["vulkan", "d3d12", "passthrough"]
|
||||||
vulkan = ["dep:ash"]
|
vulkan = ["dep:ash", "dep:android_system_properties"]
|
||||||
d3d12 = ["wgpu/dx12", "wgpu-hal/dx12", "dep:winapi"]
|
d3d12 = ["wgpu/dx12", "wgpu-hal/dx12", "dep:winapi"]
|
||||||
passthrough = []
|
passthrough = []
|
||||||
|
|
||||||
@@ -20,6 +20,7 @@ bevy = { workspace = true, default-features = true }
|
|||||||
[target.'cfg(target_os = "android")'.dependencies]
|
[target.'cfg(target_os = "android")'.dependencies]
|
||||||
ndk-context = "0.1"
|
ndk-context = "0.1"
|
||||||
jni = "0.20"
|
jni = "0.20"
|
||||||
|
android_system_properties = { version = "0.1.5", optional = true }
|
||||||
|
|
||||||
# bevy can't be placed behind target or proc macros won't work properly
|
# bevy can't be placed behind target or proc macros won't work properly
|
||||||
[dependencies]
|
[dependencies]
|
||||||
@@ -39,7 +40,7 @@ openxr = { workspace = true, features = ["mint"] }
|
|||||||
wgpu = { workspace = true, features = ["vulkan-portability"] }
|
wgpu = { workspace = true, features = ["vulkan-portability"] }
|
||||||
|
|
||||||
[target.'cfg(target_family = "windows")'.dependencies]
|
[target.'cfg(target_family = "windows")'.dependencies]
|
||||||
openxr = { workspace=true, features = ["mint", "static"] }
|
openxr = { workspace = true, features = ["mint", "static"] }
|
||||||
winapi = { version = "0.3.9", optional = true }
|
winapi = { version = "0.3.9", optional = true }
|
||||||
|
|
||||||
[lints.clippy]
|
[lints.clippy]
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
use std::ffi::{c_void, CString};
|
use std::ffi::{c_void, CString};
|
||||||
|
|
||||||
use ash::vk::Handle;
|
use ash::vk::Handle;
|
||||||
use bevy::log::error;
|
use bevy::log::{debug, error};
|
||||||
use bevy::math::UVec2;
|
use bevy::math::UVec2;
|
||||||
use openxr::{sys, Version};
|
use openxr::{sys, Version};
|
||||||
use wgpu_hal::api::Vulkan;
|
use wgpu_hal::api::Vulkan;
|
||||||
@@ -154,6 +154,13 @@ unsafe impl GraphicsExt for openxr::Vulkan {
|
|||||||
ash::vk::Instance::from_raw(vk_instance as _),
|
ash::vk::Instance::from_raw(vk_instance as _),
|
||||||
)
|
)
|
||||||
};
|
};
|
||||||
|
let api_layers = unsafe { vk_entry.enumerate_instance_layer_properties()? };
|
||||||
|
let has_nv_optimus = api_layers.iter().any(|v| {
|
||||||
|
v.layer_name_as_c_str()
|
||||||
|
.is_ok_and(|v| v == c"VK_LAYER_NV_optimus")
|
||||||
|
});
|
||||||
|
|
||||||
|
drop(api_layers);
|
||||||
|
|
||||||
let vk_instance_ptr = vk_instance.handle().as_raw() as *const c_void;
|
let vk_instance_ptr = vk_instance.handle().as_raw() as *const c_void;
|
||||||
|
|
||||||
@@ -176,31 +183,54 @@ unsafe impl GraphicsExt for openxr::Vulkan {
|
|||||||
return Err(OxrError::FailedGraphicsRequirements);
|
return Err(OxrError::FailedGraphicsRequirements);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// the android_sdk_version stuff is copied from wgpu
|
||||||
|
#[cfg(target_os = "android")]
|
||||||
|
let android_sdk_version = {
|
||||||
|
let properties = android_system_properties::AndroidSystemProperties::new();
|
||||||
|
// See: https://developer.android.com/reference/android/os/Build.VERSION_CODES
|
||||||
|
if let Some(val) = properties.get("ro.build.version.sdk") {
|
||||||
|
match val.parse::<u32>() {
|
||||||
|
Ok(sdk_ver) => sdk_ver,
|
||||||
|
Err(err) => {
|
||||||
|
error!(
|
||||||
|
concat!(
|
||||||
|
"Couldn't parse Android's ",
|
||||||
|
"ro.build.version.sdk system property ({}): {}",
|
||||||
|
),
|
||||||
|
val,
|
||||||
|
err,
|
||||||
|
);
|
||||||
|
0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
error!("Couldn't read Android's ro.build.version.sdk system property");
|
||||||
|
0
|
||||||
|
}
|
||||||
|
};
|
||||||
|
#[cfg(not(target_os = "android"))]
|
||||||
|
let android_sdk_version = 0;
|
||||||
|
|
||||||
let wgpu_vk_instance = unsafe {
|
let wgpu_vk_instance = unsafe {
|
||||||
<Vulkan as Api>::Instance::from_raw(
|
<Vulkan as Api>::Instance::from_raw(
|
||||||
vk_entry.clone(),
|
vk_entry.clone(),
|
||||||
vk_instance.clone(),
|
vk_instance.clone(),
|
||||||
VK_TARGET_VERSION_ASH,
|
vk_device_properties.api_version,
|
||||||
0,
|
android_sdk_version,
|
||||||
None,
|
None,
|
||||||
extensions,
|
extensions,
|
||||||
flags,
|
flags,
|
||||||
false,
|
has_nv_optimus,
|
||||||
None,
|
None,
|
||||||
)?
|
)?
|
||||||
};
|
};
|
||||||
|
|
||||||
let wgpu_features = wgpu::Features::TEXTURE_ADAPTER_SPECIFIC_FORMAT_FEATURES
|
|
||||||
| wgpu::Features::MULTIVIEW
|
|
||||||
| wgpu::Features::MULTI_DRAW_INDIRECT_COUNT
|
|
||||||
| wgpu::Features::MULTI_DRAW_INDIRECT
|
|
||||||
| wgpu::Features::TEXTURE_FORMAT_16BIT_NORM
|
|
||||||
| wgpu::Features::CLEAR_TEXTURE;
|
|
||||||
|
|
||||||
let Some(wgpu_exposed_adapter) = wgpu_vk_instance.expose_adapter(vk_physical_device) else {
|
let Some(wgpu_exposed_adapter) = wgpu_vk_instance.expose_adapter(vk_physical_device) else {
|
||||||
error!("WGPU failed to provide an adapter");
|
error!("WGPU failed to provide an adapter");
|
||||||
return Err(OxrError::FailedGraphicsRequirements);
|
return Err(OxrError::FailedGraphicsRequirements);
|
||||||
};
|
};
|
||||||
|
let wgpu_features = wgpu_exposed_adapter.features;
|
||||||
|
debug!("wgpu features: {wgpu_features:#?}");
|
||||||
|
|
||||||
let enabled_extensions = wgpu_exposed_adapter
|
let enabled_extensions = wgpu_exposed_adapter
|
||||||
.adapter
|
.adapter
|
||||||
@@ -267,20 +297,15 @@ unsafe impl GraphicsExt for openxr::Vulkan {
|
|||||||
let wgpu_instance =
|
let wgpu_instance =
|
||||||
unsafe { wgpu::Instance::from_hal::<wgpu_hal::api::Vulkan>(wgpu_vk_instance) };
|
unsafe { wgpu::Instance::from_hal::<wgpu_hal::api::Vulkan>(wgpu_vk_instance) };
|
||||||
let wgpu_adapter = unsafe { wgpu_instance.create_adapter_from_hal(wgpu_exposed_adapter) };
|
let wgpu_adapter = unsafe { wgpu_instance.create_adapter_from_hal(wgpu_exposed_adapter) };
|
||||||
|
let limits = wgpu_adapter.limits();
|
||||||
|
debug!("wgpu_limits: {limits:#?}");
|
||||||
let (wgpu_device, wgpu_queue) = unsafe {
|
let (wgpu_device, wgpu_queue) = unsafe {
|
||||||
wgpu_adapter.create_device_from_hal(
|
wgpu_adapter.create_device_from_hal(
|
||||||
wgpu_open_device,
|
wgpu_open_device,
|
||||||
&wgpu::DeviceDescriptor {
|
&wgpu::DeviceDescriptor {
|
||||||
label: None,
|
label: None,
|
||||||
required_features: wgpu_features,
|
required_features: wgpu_features,
|
||||||
required_limits: wgpu::Limits {
|
required_limits: limits,
|
||||||
max_bind_groups: 8,
|
|
||||||
max_storage_buffer_binding_size: wgpu_adapter
|
|
||||||
.limits()
|
|
||||||
.max_storage_buffer_binding_size,
|
|
||||||
max_push_constant_size: 4,
|
|
||||||
..Default::default()
|
|
||||||
},
|
|
||||||
memory_hints: wgpu::MemoryHints::Performance,
|
memory_hints: wgpu::MemoryHints::Performance,
|
||||||
},
|
},
|
||||||
None,
|
None,
|
||||||
|
|||||||
Reference in New Issue
Block a user