From 28008f79641357c2fd1be1292de15169fcd80cf7 Mon Sep 17 00:00:00 2001
From: Schmarni <51007916+Schmarni-Dev@users.noreply.github.com>
Date: Sat, 9 Dec 2023 06:09:48 +0100
Subject: [PATCH] Fallback to flat when no oxr runtime is found (#51)
* basics done? now to the fun part: changing the ENTIRE lib to work with xr and non xr
* updated stuff and renamed file
* actually add the renamed file into git lol :3
* made lib fallback to flat when no runtime is found but can't compile with default settings under those circumstances
---
Cargo.toml | 1 +
examples/demo/Cargo.toml | 1 +
examples/demo/Cargo_back.toml | 24 --
examples/demo/src/lib.rs | 31 +-
examples/demo/src/lib_bak.rs | 609 ----------------------------
examples/demo/src/setup.rs | 18 +-
src/graphics/mod.rs | 6 +-
src/graphics/vulkan.rs | 4 +-
src/lib.rs | 196 ++++-----
src/xr_init.rs | 354 ++++++++++++++++
src/xr_input/actions.rs | 5 +-
src/xr_input/debug_gizmos.rs | 47 ++-
src/xr_input/hands/emulated.rs | 10 +-
src/xr_input/hands/hand_tracking.rs | 4 +-
src/xr_input/mod.rs | 20 +-
15 files changed, 547 insertions(+), 783 deletions(-)
delete mode 100644 examples/demo/Cargo_back.toml
delete mode 100644 examples/demo/src/lib_bak.rs
create mode 100644 src/xr_init.rs
diff --git a/Cargo.toml b/Cargo.toml
index 4286be2f..73996b7c 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -18,6 +18,7 @@ members = ["examples/android", "examples/demo"]
anyhow = "1.0.75"
ash = "0.37.3"
bevy = "0.12"
+futures-lite = "2.1.0"
mint = "0.5.9"
wgpu = "0.17.1"
wgpu-core = { version = "0.17.1", features = ["vulkan"] }
diff --git a/examples/demo/Cargo.toml b/examples/demo/Cargo.toml
index d38d7d5b..a6abbf91 100644
--- a/examples/demo/Cargo.toml
+++ b/examples/demo/Cargo.toml
@@ -17,4 +17,5 @@ color-eyre = "0.6.2"
[target.'cfg(not(target_os="android"))'.dependencies.bevy_oxr]
path = "../../"
+# May need to be more specific. needs to be false at least on linux without an active runtime to run in flat
default-features = true
diff --git a/examples/demo/Cargo_back.toml b/examples/demo/Cargo_back.toml
deleted file mode 100644
index 0423b999..00000000
--- a/examples/demo/Cargo_back.toml
+++ /dev/null
@@ -1,24 +0,0 @@
-[package]
-name = "demo"
-version = "0.1.0"
-edition = "2021"
-
-
-[lib]
-crate-type = ["cdylib", "lib"]
-# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
-
-[dependencies]
-bevy = { git = "https://github.com/bevyengine/bevy.git" }
-# bevy = "0.11.3"
-# default-features is false because it for some reason complains when trying to statically link openxr
-bevy_oxr = { path = "../../" }
-# bevy_openxr = { git = "https://github.com/Schmarni-Dev/bevy_openxr", default-features = false, branch = "demo"}
-bevy_rapier3d = { git = "https://github.com/devil-ira/bevy_rapier", version = "0.22.0", branch = "bevy-0.12" }
-# bevy_rapier3d = { git = "https://github.com/Schmarni-Dev/bevy_rapier" }
-color-eyre = "0.6.2"
-
-[profile.release]
-lto = "fat"
-codegen-units = 1
-panic = "abort"
diff --git a/examples/demo/src/lib.rs b/examples/demo/src/lib.rs
index 8be09a49..9ce50002 100644
--- a/examples/demo/src/lib.rs
+++ b/examples/demo/src/lib.rs
@@ -3,6 +3,7 @@ use std::{f32::consts::PI, ops::Mul, time::Duration};
use bevy::{
diagnostic::{FrameTimeDiagnosticsPlugin, LogDiagnosticsPlugin},
ecs::schedule::ScheduleLabel,
+ input::{keyboard::KeyCode, Input},
log::info,
prelude::{
bevy_main, default, shape, App, Assets, Color, Commands, Component, Entity, Event,
@@ -16,10 +17,12 @@ use bevy::{
};
use bevy_oxr::{
input::XrInput,
+ xr_init::{XrEnableRequest, XrEnableStatus, xr_only},
resources::{XrFrameState, XrInstance, XrSession},
xr_input::{
+ actions::XrActionSets,
debug_gizmos::OpenXrDebugRenderer,
- hands::common::{ HandInputDebugRenderer, HandResource, HandsResource, OpenXrHandInput},
+ hands::common::{HandInputDebugRenderer, HandResource, HandsResource, OpenXrHandInput},
hands::HandBone,
interactions::{
draw_interaction_gizmos, draw_socket_gizmos, interactions, socket_interactions,
@@ -29,11 +32,25 @@ use bevy_oxr::{
oculus_touch::OculusController,
prototype_locomotion::{proto_locomotion, PrototypeLocomotionConfig},
trackers::{OpenXRController, OpenXRLeftController, OpenXRRightController, OpenXRTracker},
- Hand, actions::XrActionSets,
+ Hand,
},
DefaultXrPlugins,
};
+fn input_stuff(
+ keys: Res>,
+ status: Res,
+ mut request: EventWriter,
+) {
+ if keys.just_pressed(KeyCode::Space) {
+ match status.into_inner() {
+ XrEnableStatus::Enabled => request.send(XrEnableRequest::TryDisable),
+ XrEnableStatus::Disabled => request.send(XrEnableRequest::TryEnable),
+ XrEnableStatus::Waiting => (),
+ }
+ }
+}
+
mod setup;
use crate::setup::setup_scene;
use bevy_rapier3d::prelude::*;
@@ -45,7 +62,7 @@ pub fn main() {
info!("Running bevy_openxr demo");
let mut app = App::new();
- app
+ app.add_systems(Update, input_stuff)
//lets get the usual diagnostic stuff added
.add_plugins(LogDiagnosticsPlugin::default())
.add_plugins(FrameTimeDiagnosticsPlugin)
@@ -60,11 +77,11 @@ pub fn main() {
.add_systems(Startup, setup_scene)
.add_systems(Startup, spawn_controllers_example) //you need to spawn controllers or it crashes TODO:: Fix this
//add locomotion
- .add_systems(Update, proto_locomotion)
+ .add_systems(Update, proto_locomotion.run_if(xr_only()))
.insert_resource(PrototypeLocomotionConfig::default())
//lets add the interaction systems
.add_event::()
- .add_systems(Update, prototype_interaction_input)
+ .add_systems(Update, prototype_interaction_input.run_if(xr_only()))
.add_systems(Update, interactions.before(update_interactable_states))
.add_systems(Update, update_interactable_states)
.add_systems(
@@ -76,7 +93,7 @@ pub fn main() {
//draw the interaction gizmos
.add_systems(
Update,
- draw_interaction_gizmos.after(update_interactable_states),
+ draw_interaction_gizmos.run_if(xr_only()).after(update_interactable_states),
)
.add_systems(Update, draw_socket_gizmos.after(update_interactable_states))
//add our cube spawning system
@@ -85,7 +102,7 @@ pub fn main() {
0.25,
bevy::time::TimerMode::Once,
)))
- .add_systems(Update, request_cube_spawn)
+ .add_systems(Update, request_cube_spawn.run_if(xr_only()))
.add_systems(Update, cube_spawner.after(request_cube_spawn))
//test capsule
.add_systems(Startup, spawn_capsule)
diff --git a/examples/demo/src/lib_bak.rs b/examples/demo/src/lib_bak.rs
deleted file mode 100644
index 54d97662..00000000
--- a/examples/demo/src/lib_bak.rs
+++ /dev/null
@@ -1,609 +0,0 @@
-use bevy::{
- diagnostic::{FrameTimeDiagnosticsPlugin, LogDiagnosticsPlugin},
- log::info,
- prelude::{
- *,
- bevy_main, default, shape, App, Assets, Color, Commands, Component, Event, EventReader,
- EventWriter, GlobalTransform, IntoSystemConfigs, IntoSystemSetConfigs, Mesh, PbrBundle,
- PostUpdate, Query, Res, ResMut, Resource, SpatialBundle, StandardMaterial, Startup,
- Transform, Update, With, Without,
- },
- time::{Time, Timer},
- transform::TransformSystem,
-};
-use bevy_openxr::{
- input::XrInput,
- resources::{XrFrameState, XrInstance, XrSession},
- xr_input::{
- debug_gizmos::OpenXrDebugRenderer,
- hand::{HandBone, HandInputDebugRenderer, HandResource, HandsResource, OpenXrHandInput},
- interactions::{
- draw_interaction_gizmos, draw_socket_gizmos, interactions, socket_interactions,
- update_interactable_states, InteractionEvent, Touched, XRDirectInteractor,
- XRInteractable, XRInteractableState, XRInteractorState, XRSelection,
- },
- oculus_touch::OculusController,
- prototype_locomotion::{proto_locomotion, PrototypeLocomotionConfig},
- trackers::{OpenXRController, OpenXRLeftController, OpenXRRightController, OpenXRTracker},
- Hand,
- },
- DefaultXrPlugins,
-};
-
-mod setup;
-use crate::setup::setup_scene;
-use bevy_rapier3d::prelude::*;
-
-#[bevy_main]
-pub fn main() {
- color_eyre::install().unwrap();
-
- info!("Running bevy_openxr demo");
- let mut app = App::new();
-
- app
- //lets get the usual diagnostic stuff added
- .add_plugins(LogDiagnosticsPlugin::default())
- .add_plugins(FrameTimeDiagnosticsPlugin)
- //lets get the xr defaults added
- .add_plugins(DefaultXrPlugins)
- //lets add the debug renderer for the controllers
- .add_plugins(OpenXrDebugRenderer)
- //rapier goes here
- .add_plugins(RapierPhysicsPlugin::::default().with_default_system_setup(false))
- .add_plugins(RapierDebugRenderPlugin::default())
- //lets setup the starting scene
- .add_systems(Startup, setup_scene)
- .add_systems(Startup, spawn_controllers_example) //you need to spawn controllers or it crashes TODO:: Fix this
- //add locomotion
- .add_systems(Update, proto_locomotion)
- .insert_resource(PrototypeLocomotionConfig::default())
- //lets add the interaction systems
- .add_event::()
- .add_systems(Update, prototype_interaction_input)
- .add_systems(Update, interactions.before(update_interactable_states))
- .add_systems(Update, update_interactable_states)
- .add_systems(
- Update,
- socket_interactions.before(update_interactable_states),
- )
- //add the grabbable system
- .add_systems(Update, update_grabbables.after(update_interactable_states))
- //draw the interaction gizmos
- .add_systems(
- Update,
- draw_interaction_gizmos.after(update_interactable_states),
- )
- .add_systems(Update, draw_socket_gizmos.after(update_interactable_states))
- //add our cube spawning system
- .add_event::()
- .insert_resource(SpawnCubeTimer(Timer::from_seconds(
- 0.25,
- bevy::time::TimerMode::Once,
- )))
- .add_systems(Update, request_cube_spawn)
- .add_systems(Update, cube_spawner.after(request_cube_spawn))
- //test capsule
- .add_systems(Startup, spawn_capsule)
- //physics hands
- .add_plugins(OpenXrHandInput)
- .add_plugins(HandInputDebugRenderer)
- .add_systems(Startup, spawn_physics_hands)
- .add_systems(Update, update_physics_hands);
-
- //configure rapier sets
- app.configure_sets(
- PostUpdate,
- (
- PhysicsSet::SyncBackend,
- PhysicsSet::StepSimulation,
- PhysicsSet::Writeback,
- )
- .chain()
- .before(TransformSystem::TransformPropagate),
- );
- //add rapier systems
- app.add_systems(
- PostUpdate,
- (
- RapierPhysicsPlugin::::get_systems(PhysicsSet::SyncBackend)
- .in_set(PhysicsSet::SyncBackend),
- (
- RapierPhysicsPlugin::::get_systems(PhysicsSet::StepSimulation),
- // despawn_one_box,
- )
- .in_set(PhysicsSet::StepSimulation),
- RapierPhysicsPlugin::::get_systems(PhysicsSet::Writeback)
- .in_set(PhysicsSet::Writeback),
- ),
- );
-
- app.run();
-}
-
-fn spawn_controllers_example(mut commands: Commands) {
- //left hand
- commands.spawn((
- OpenXRLeftController,
- OpenXRController,
- OpenXRTracker,
- SpatialBundle::default(),
- XRDirectInteractor,
- XRInteractorState::default(),
- XRSelection::default(),
- ));
- //right hand
- commands.spawn((
- OpenXRRightController,
- OpenXRController,
- OpenXRTracker,
- SpatialBundle::default(),
- XRDirectInteractor,
- XRInteractorState::default(),
- XRSelection::default(),
- ));
-}
-
-fn spawn_capsule(
- mut commands: Commands,
- mut meshes: ResMut>,
- mut materials: ResMut>,
-) {
- commands.spawn((
- PbrBundle {
- mesh: meshes.add(Mesh::from(shape::Capsule {
- radius: 0.033,
- depth: 0.115,
- ..default()
- })),
- material: materials.add(Color::rgb(0.8, 0.7, 0.6).into()),
- transform: Transform::from_xyz(0.0, 2.0, 0.0),
- ..default()
- },
- // Collider::capsule_y(0.0575, 0.034),
- Collider::capsule(
- Vec3 {
- x: 0.0,
- y: -0.0575,
- z: 0.0,
- },
- Vec3 {
- x: 0.0,
- y: 0.0575,
- z: 0.0,
- },
- 0.034,
- ),
- RigidBody::Dynamic,
- ));
-}
-
-#[derive(Component, PartialEq, Debug, Clone, Copy)]
-pub enum PhysicsHandBone {
- Palm,
- Wrist,
- ThumbMetacarpal,
- ThumbProximal,
- ThumbDistal,
- ThumbTip,
- IndexMetacarpal,
- IndexProximal,
- IndexIntermediate,
- IndexDistal,
- IndexTip,
- MiddleMetacarpal,
- MiddleProximal,
- MiddleIntermediate,
- MiddleDistal,
- MiddleTip,
- RingMetacarpal,
- RingProximal,
- RingIntermediate,
- RingDistal,
- RingTip,
- LittleMetacarpal,
- LittleProximal,
- LittleIntermediate,
- LittleDistal,
- LittleTip,
-}
-#[derive(Component, PartialEq)]
-pub enum BoneInitState {
- True,
- False,
-}
-
-fn spawn_physics_hands(mut commands: Commands) {
- //here we go
- let hands = [Hand::Left, Hand::Right];
- let bones = [
- PhysicsHandBone::Palm,
- PhysicsHandBone::Wrist,
- PhysicsHandBone::ThumbMetacarpal,
- PhysicsHandBone::ThumbProximal,
- PhysicsHandBone::ThumbDistal,
- PhysicsHandBone::ThumbTip,
- PhysicsHandBone::IndexMetacarpal,
- PhysicsHandBone::IndexProximal,
- PhysicsHandBone::IndexIntermediate,
- PhysicsHandBone::IndexDistal,
- PhysicsHandBone::IndexTip,
- PhysicsHandBone::MiddleMetacarpal,
- PhysicsHandBone::MiddleProximal,
- PhysicsHandBone::MiddleIntermediate,
- PhysicsHandBone::MiddleDistal,
- PhysicsHandBone::MiddleTip,
- PhysicsHandBone::RingMetacarpal,
- PhysicsHandBone::RingProximal,
- PhysicsHandBone::RingIntermediate,
- PhysicsHandBone::RingDistal,
- PhysicsHandBone::RingTip,
- PhysicsHandBone::LittleMetacarpal,
- PhysicsHandBone::LittleProximal,
- PhysicsHandBone::LittleIntermediate,
- PhysicsHandBone::LittleDistal,
- PhysicsHandBone::LittleTip,
- ];
- //lets just do the Right ThumbMetacarpal for now
- //i dont understand the groups yet
- let self_group = Group::GROUP_1;
- let interaction_group = Group::ALL;
- let radius = 0.010;
-
- for hand in hands.iter() {
- for bone in bones.iter() {
- //spawn the thing
- commands.spawn((
- SpatialBundle::default(),
- Collider::capsule(
- Vec3 {
- x: 0.0,
- y: -0.0575,
- z: 0.0,
- },
- Vec3 {
- x: 0.0,
- y: 0.0575,
- z: 0.0,
- },
- radius,
- ),
- RigidBody::KinematicPositionBased,
- // CollisionGroups::new(self_group, interaction_group),
- // SolverGroups::new(self_group, interaction_group),
- bone.clone(),
- BoneInitState::False,
- hand.clone(),
- ));
- }
- }
-}
-
-fn update_physics_hands(
- hands_res: Option>,
- mut bone_query: Query<(
- &mut Transform,
- &mut Collider,
- &PhysicsHandBone,
- &mut BoneInitState,
- &Hand,
- )>,
- hand_query: Query<(&Transform, &HandBone, &Hand, Without)>,
-) {
- //sanity check do we even have hands?
- match hands_res {
- Some(res) => {
- //config stuff
- let radius = 0.010;
- for mut bone in bone_query.iter_mut() {
- let hand_res = match bone.4 {
- Hand::Left => res.left,
- Hand::Right => res.right,
- };
-
- //lets just do the Right ThumbMetacarpal for now
- let result = get_start_and_end_entities(hand_res, bone.2);
- if let Some((start_entity, end_entity)) = result {
- //now we need their transforms
- let start_components = hand_query.get(start_entity);
- let end_components = hand_query.get(end_entity);
- let direction = end_components.unwrap().0.translation
- - start_components.unwrap().0.translation;
- if direction.length() < 0.001 {
- //i hate this but we need to skip init if the length is zero
- return;
- }
-
- match *bone.3 {
- BoneInitState::True => {
- //if we are init then we just move em?
- *bone.0 = start_components
- .unwrap()
- .0
- .clone()
- .looking_at(end_components.unwrap().0.translation, Vec3::Y);
- }
- BoneInitState::False => {
- //build a new collider?
- *bone.1 = Collider::capsule(
- Vec3::splat(0.0),
- Vec3 {
- x: 0.0,
- y: 0.0,
- z: -direction.length(),
- },
- radius,
- );
- *bone.3 = BoneInitState::True;
- }
- }
- }
- }
- }
- None => info!("hand states resource not initialized yet"),
- }
-}
-
-fn get_start_and_end_entities(
- hand_res: HandResource,
- bone: &PhysicsHandBone,
-) -> Option<(Entity, Entity)> {
- match bone {
- PhysicsHandBone::Palm => return None,
- PhysicsHandBone::Wrist => return None,
- PhysicsHandBone::ThumbMetacarpal => {
- return Some((hand_res.thumb.metacarpal, hand_res.thumb.proximal))
- }
- PhysicsHandBone::ThumbProximal => {
- return Some((hand_res.thumb.proximal, hand_res.thumb.distal))
- }
- PhysicsHandBone::ThumbDistal => return Some((hand_res.thumb.distal, hand_res.thumb.tip)),
- PhysicsHandBone::ThumbTip => return None,
- PhysicsHandBone::IndexMetacarpal => {
- return Some((hand_res.index.metacarpal, hand_res.index.proximal))
- }
- PhysicsHandBone::IndexProximal => {
- return Some((hand_res.index.proximal, hand_res.index.intermediate))
- }
- PhysicsHandBone::IndexIntermediate => {
- return Some((hand_res.index.intermediate, hand_res.index.distal))
- }
- PhysicsHandBone::IndexDistal => return Some((hand_res.index.distal, hand_res.index.tip)),
- PhysicsHandBone::IndexTip => return None,
- PhysicsHandBone::MiddleMetacarpal => {
- return Some((hand_res.middle.metacarpal, hand_res.middle.proximal))
- }
- PhysicsHandBone::MiddleProximal => {
- return Some((hand_res.middle.proximal, hand_res.middle.intermediate))
- }
- PhysicsHandBone::MiddleIntermediate => {
- return Some((hand_res.middle.intermediate, hand_res.middle.distal))
- }
- PhysicsHandBone::MiddleDistal => {
- return Some((hand_res.middle.distal, hand_res.middle.tip))
- }
- PhysicsHandBone::MiddleTip => return None,
- PhysicsHandBone::RingMetacarpal => {
- return Some((hand_res.ring.metacarpal, hand_res.ring.proximal))
- }
- PhysicsHandBone::RingProximal => {
- return Some((hand_res.ring.proximal, hand_res.ring.intermediate))
- }
- PhysicsHandBone::RingIntermediate => {
- return Some((hand_res.ring.intermediate, hand_res.ring.distal))
- }
- PhysicsHandBone::RingDistal => return Some((hand_res.ring.distal, hand_res.ring.tip)),
- PhysicsHandBone::RingTip => return None,
- PhysicsHandBone::LittleMetacarpal => {
- return Some((hand_res.little.metacarpal, hand_res.little.proximal))
- }
- PhysicsHandBone::LittleProximal => {
- return Some((hand_res.little.proximal, hand_res.little.intermediate))
- }
- PhysicsHandBone::LittleIntermediate => {
- return Some((hand_res.little.intermediate, hand_res.little.distal))
- }
- PhysicsHandBone::LittleDistal => {
- return Some((hand_res.little.distal, hand_res.little.tip))
- }
- PhysicsHandBone::LittleTip => return None,
- };
-}
-
-fn get_hand_res(res: &Res<'_, HandsResource>, hand: Hand) -> HandResource {
- match hand {
- Hand::Left => res.left.clone(),
- Hand::Right => res.right.clone(),
- }
-}
-
-#[derive(Event, Default)]
-pub struct SpawnCubeRequest;
-
-#[derive(Resource)]
-pub struct SpawnCubeTimer(Timer);
-
-fn request_cube_spawn(
- oculus_controller: Res,
- frame_state: Res,
- xr_input: Res,
- instance: Res,
- session: Res,
- mut writer: EventWriter,
- time: Res