From b5d3f7e794ea867771f33a1bb69a2e4a1c7b7468 Mon Sep 17 00:00:00 2001 From: Carter Anderson Date: Mon, 20 Jul 2020 01:33:30 -0700 Subject: [PATCH] use right handed coordinate system in 3d --- crates/bevy_math/src/face_toward.rs | 2 +- crates/bevy_math/src/lib.rs | 2 ++ crates/bevy_math/src/perspective.rs | 21 +++++++++++ crates/bevy_pbr/src/pipelines/forward/mod.rs | 2 +- crates/bevy_render/src/camera/projection.rs | 4 +-- crates/bevy_render/src/mesh/mesh.rs | 36 +++++++++---------- crates/bevy_render/src/pipeline/pipeline.rs | 2 +- .../src/pipeline/state_descriptors.rs | 2 +- crates/bevy_sprite/src/lib.rs | 2 +- crates/bevy_sprite/src/render/mod.rs | 8 ++--- crates/bevy_ui/src/render/mod.rs | 4 +-- examples/3d/texture.rs | 12 +++---- examples/ui/button.rs | 24 ++++++------- 13 files changed, 72 insertions(+), 49 deletions(-) create mode 100644 crates/bevy_math/src/perspective.rs diff --git a/crates/bevy_math/src/face_toward.rs b/crates/bevy_math/src/face_toward.rs index 57cb1deb31..03ba266b04 100644 --- a/crates/bevy_math/src/face_toward.rs +++ b/crates/bevy_math/src/face_toward.rs @@ -6,7 +6,7 @@ pub trait FaceToward { impl FaceToward for Mat4 { fn face_toward(eye: Vec3, center: Vec3, up: Vec3) -> Self { - let forward = (center - eye).normalize(); + let forward = (eye - center).normalize(); let right = up.cross(forward).normalize(); let up = forward.cross(right); Mat4::from_cols( diff --git a/crates/bevy_math/src/lib.rs b/crates/bevy_math/src/lib.rs index 5cb3c87f2e..76539fc460 100644 --- a/crates/bevy_math/src/lib.rs +++ b/crates/bevy_math/src/lib.rs @@ -1,7 +1,9 @@ mod face_toward; +mod perspective; pub use face_toward::*; pub use glam::*; +pub use perspective::*; pub mod prelude { pub use crate::{FaceToward, Mat3, Mat4, Quat, Vec2, Vec3, Vec4}; diff --git a/crates/bevy_math/src/perspective.rs b/crates/bevy_math/src/perspective.rs new file mode 100644 index 0000000000..a5c57ecc85 --- /dev/null +++ b/crates/bevy_math/src/perspective.rs @@ -0,0 +1,21 @@ +use crate::Mat4; +use glam::Vec4; + +pub trait PerspectiveRh { + fn perspective_rh(fov_y_radians: f32, aspect_ratio: f32, z_near: f32, z_far: f32) -> Self; +} + +impl PerspectiveRh for Mat4 { + fn perspective_rh(fov_y_radians: f32, aspect_ratio: f32, z_near: f32, z_far: f32) -> Self { + let (sin_fov, cos_fov) = (0.5 * fov_y_radians).sin_cos(); + let h = cos_fov / sin_fov; + let w = h /aspect_ratio; + let r = z_far / (z_near - z_far); + Mat4::from_cols( + Vec4::new(w, 0.0, 0.0, 0.0), + Vec4::new(0.0, h, 0.0, 0.0), + Vec4::new(0.0, 0.0, r, -1.0), + Vec4::new(0.0, 0.0, r * z_near, 0.0), + ) + } +} diff --git a/crates/bevy_pbr/src/pipelines/forward/mod.rs b/crates/bevy_pbr/src/pipelines/forward/mod.rs index 1614d8875b..ae41d4814e 100644 --- a/crates/bevy_pbr/src/pipelines/forward/mod.rs +++ b/crates/bevy_pbr/src/pipelines/forward/mod.rs @@ -14,7 +14,7 @@ pub const FORWARD_PIPELINE_HANDLE: Handle = pub fn build_forward_pipeline(shaders: &mut Assets) -> PipelineDescriptor { PipelineDescriptor { rasterization_state: Some(RasterizationStateDescriptor { - front_face: FrontFace::Cw, + front_face: FrontFace::Ccw, cull_mode: CullMode::Back, depth_bias: 0, depth_bias_slope_scale: 0.0, diff --git a/crates/bevy_render/src/camera/projection.rs b/crates/bevy_render/src/camera/projection.rs index 51fdf2bb22..e6d886df8c 100644 --- a/crates/bevy_render/src/camera/projection.rs +++ b/crates/bevy_render/src/camera/projection.rs @@ -1,4 +1,4 @@ -use bevy_math::Mat4; +use bevy_math::{PerspectiveRh, Mat4}; use bevy_property::{Properties, Property}; use serde::{Deserialize, Serialize}; @@ -17,7 +17,7 @@ pub struct PerspectiveProjection { impl CameraProjection for PerspectiveProjection { fn get_projection_matrix(&self) -> Mat4 { - Mat4::perspective_lh(self.fov, self.aspect_ratio, self.near, self.far) + Mat4::perspective_rh(self.fov, self.aspect_ratio, self.near, self.far) } fn update(&mut self, width: usize, height: usize) { self.aspect_ratio = width as f32 / height as f32; diff --git a/crates/bevy_render/src/mesh/mesh.rs b/crates/bevy_render/src/mesh/mesh.rs index 29e9459f92..e3bc164afe 100644 --- a/crates/bevy_render/src/mesh/mesh.rs +++ b/crates/bevy_render/src/mesh/mesh.rs @@ -273,14 +273,9 @@ pub mod shape { let vertices = if quad.flip { [ ( - [south_west.x(), south_west.y(), 0.0], + [south_east.x(), south_east.y(), 0.0], [0.0, 0.0, 1.0], - [0.0, 1.0], - ), - ( - [north_west.x(), north_west.y(), 0.0], - [0.0, 0.0, 1.0], - [0.0, 0.0], + [1.0, 1.0], ), ( [north_east.x(), north_east.y(), 0.0], @@ -288,22 +283,22 @@ pub mod shape { [1.0, 0.0], ), ( - [south_east.x(), south_east.y(), 0.0], + [north_west.x(), north_west.y(), 0.0], [0.0, 0.0, 1.0], - [1.0, 1.0], + [0.0, 0.0], + ), + ( + [south_west.x(), south_west.y(), 0.0], + [0.0, 0.0, 1.0], + [0.0, 1.0], ), ] } else { [ ( - [south_east.x(), south_east.y(), 0.0], + [south_west.x(), south_west.y(), 0.0], [0.0, 0.0, 1.0], - [1.0, 1.0], - ), - ( - [north_east.x(), north_east.y(), 0.0], - [0.0, 0.0, 1.0], - [1.0, 0.0], + [0.0, 1.0], ), ( [north_west.x(), north_west.y(), 0.0], @@ -311,9 +306,14 @@ pub mod shape { [0.0, 0.0], ), ( - [south_west.x(), south_west.y(), 0.0], + [north_east.x(), north_east.y(), 0.0], [0.0, 0.0, 1.0], - [0.0, 1.0], + [1.0, 0.0], + ), + ( + [south_east.x(), south_east.y(), 0.0], + [0.0, 0.0, 1.0], + [1.0, 1.0], ), ] }; diff --git a/crates/bevy_render/src/pipeline/pipeline.rs b/crates/bevy_render/src/pipeline/pipeline.rs index a69ef722b2..da7e2b0159 100644 --- a/crates/bevy_render/src/pipeline/pipeline.rs +++ b/crates/bevy_render/src/pipeline/pipeline.rs @@ -72,7 +72,7 @@ impl PipelineDescriptor { sample_mask: !0, alpha_to_coverage_enabled: false, rasterization_state: Some(RasterizationStateDescriptor { - front_face: FrontFace::Cw, + front_face: FrontFace::Ccw, cull_mode: CullMode::Back, depth_bias: 0, depth_bias_slope_scale: 0.0, diff --git a/crates/bevy_render/src/pipeline/state_descriptors.rs b/crates/bevy_render/src/pipeline/state_descriptors.rs index cd81db2902..29568d5fa2 100644 --- a/crates/bevy_render/src/pipeline/state_descriptors.rs +++ b/crates/bevy_render/src/pipeline/state_descriptors.rs @@ -74,7 +74,7 @@ pub enum FrontFace { impl Default for FrontFace { fn default() -> Self { - FrontFace::Cw + FrontFace::Ccw } } diff --git a/crates/bevy_sprite/src/lib.rs b/crates/bevy_sprite/src/lib.rs index ea6e315fc5..69909c6d4a 100644 --- a/crates/bevy_sprite/src/lib.rs +++ b/crates/bevy_sprite/src/lib.rs @@ -58,7 +58,7 @@ impl AppPlugin for SpritePlugin { meshes.set( QUAD_HANDLE, // Use a flipped quad because the camera is facing "forward" but quads should face backward - Mesh::from(shape::Quad::flipped(Vec2::new(1.0, 1.0))), + Mesh::from(shape::Quad::new(Vec2::new(1.0, 1.0))), ); let mut color_materials = resources.get_mut::>().unwrap(); diff --git a/crates/bevy_sprite/src/render/mod.rs b/crates/bevy_sprite/src/render/mod.rs index 31f65390d2..2499b2e94f 100644 --- a/crates/bevy_sprite/src/render/mod.rs +++ b/crates/bevy_sprite/src/render/mod.rs @@ -21,8 +21,8 @@ pub const SPRITE_SHEET_PIPELINE_HANDLE: Handle = pub fn build_sprite_sheet_pipeline(shaders: &mut Assets) -> PipelineDescriptor { PipelineDescriptor { rasterization_state: Some(RasterizationStateDescriptor { - front_face: FrontFace::Cw, - cull_mode: CullMode::None, + front_face: FrontFace::Ccw, + cull_mode: CullMode::Back, depth_bias: 0, depth_bias_slope_scale: 0.0, depth_bias_clamp: 0.0, @@ -66,8 +66,8 @@ pub fn build_sprite_sheet_pipeline(shaders: &mut Assets) -> PipelineDesc pub fn build_sprite_pipeline(shaders: &mut Assets) -> PipelineDescriptor { PipelineDescriptor { rasterization_state: Some(RasterizationStateDescriptor { - front_face: FrontFace::Cw, - cull_mode: CullMode::None, + front_face: FrontFace::Ccw, + cull_mode: CullMode::Back, depth_bias: 0, depth_bias_slope_scale: 0.0, depth_bias_clamp: 0.0, diff --git a/crates/bevy_ui/src/render/mod.rs b/crates/bevy_ui/src/render/mod.rs index c5f4e927e5..ad472221d8 100644 --- a/crates/bevy_ui/src/render/mod.rs +++ b/crates/bevy_ui/src/render/mod.rs @@ -15,8 +15,8 @@ pub const UI_PIPELINE_HANDLE: Handle = pub fn build_ui_pipeline(shaders: &mut Assets) -> PipelineDescriptor { PipelineDescriptor { rasterization_state: Some(RasterizationStateDescriptor { - front_face: FrontFace::Cw, - cull_mode: CullMode::None, + front_face: FrontFace::Ccw, + cull_mode: CullMode::Back, depth_bias: 0, depth_bias_slope_scale: 0.0, depth_bias_clamp: 0.0, diff --git a/examples/3d/texture.rs b/examples/3d/texture.rs index 4305ae0e30..4581d7661e 100644 --- a/examples/3d/texture.rs +++ b/examples/3d/texture.rs @@ -58,8 +58,8 @@ fn setup( .spawn(PbrComponents { mesh: quad_handle, material: material_handle, - translation: Translation::new(0.0, 0.0, -1.5), - rotation: Rotation(Quat::from_rotation_x(std::f32::consts::PI / 5.0)), + translation: Translation::new(0.0, 0.0, 1.5), + rotation: Rotation(Quat::from_rotation_x(-std::f32::consts::PI / 5.0)), draw: Draw { is_transparent: true, ..Default::default() @@ -71,7 +71,7 @@ fn setup( mesh: quad_handle, material: red_material_handle, translation: Translation::new(0.0, 0.0, 0.0), - rotation: Rotation(Quat::from_rotation_x(std::f32::consts::PI / 5.0)), + rotation: Rotation(Quat::from_rotation_x(-std::f32::consts::PI / 5.0)), draw: Draw { is_transparent: true, ..Default::default() @@ -82,8 +82,8 @@ fn setup( .spawn(PbrComponents { mesh: quad_handle, material: blue_material_handle, - translation: Translation::new(0.0, 0.0, 1.5), - rotation: Rotation(Quat::from_rotation_x(std::f32::consts::PI / 5.0)), + translation: Translation::new(0.0, 0.0, -1.5), + rotation: Rotation(Quat::from_rotation_x(-std::f32::consts::PI / 5.0)), draw: Draw { is_transparent: true, ..Default::default() @@ -93,7 +93,7 @@ fn setup( // camera .spawn(Camera3dComponents { transform: Transform::new_sync_disabled(Mat4::face_toward( - Vec3::new(3.0, 5.0, -8.0), + Vec3::new(3.0, 5.0, 8.0), Vec3::new(0.0, 0.0, 0.0), Vec3::new(0.0, 1.0, 0.0), )), diff --git a/examples/ui/button.rs b/examples/ui/button.rs index 96d8027788..3feef9d5e9 100644 --- a/examples/ui/button.rs +++ b/examples/ui/button.rs @@ -42,23 +42,23 @@ fn button_system( &mut Handle, &Children, )>, - label_query: Query<&mut Label>, + text_query: Query<&mut Text>, ) { for (_button, hover, click, mut material, children) in &mut hover_query.iter() { - let mut label = label_query.get_mut::