From 4e59d730fc8c51c355fae88de110d6a6992042d7 Mon Sep 17 00:00:00 2001 From: Hartmut Seichter Date: Fri, 9 Dec 2022 18:35:37 +0100 Subject: [PATCH] updated code with reversed projection matrix code --- src/main.rs | 2 +- src/offaxis.rs | 106 ++++++++++++++++++++++++++++++++++--------------- 2 files changed, 75 insertions(+), 33 deletions(-) diff --git a/src/main.rs b/src/main.rs index 0b907b5..1232584 100644 --- a/src/main.rs +++ b/src/main.rs @@ -20,7 +20,7 @@ mod viewer; fn main() { App::new() - .insert_resource(ClearColor(Color::rgb(0.9, 0.9, 0.9))) + .insert_resource(ClearColor(Color::rgb(0.5, 0.5, 0.5))) .add_plugins(DefaultPlugins.set(WindowPlugin { window: WindowDescriptor { title: "PixSpace".to_string(), diff --git a/src/offaxis.rs b/src/offaxis.rs index 22b67e1..bc37354 100644 --- a/src/offaxis.rs +++ b/src/offaxis.rs @@ -16,38 +16,6 @@ pub struct OffAxisProjection { aspect: f32, } -impl CameraProjection for OffAxisProjection { - fn get_projection_matrix(&self) -> Mat4 { - - println!("Here we go! {:?}",self); - - Mat4::perspective_rh(45.0_f32.to_radians(), - self.aspect, - self.near, - self.far) - - //Mat4::orthographic_rh(-self.aspect, self.aspect, -1.0, 1.0, self.near, self.far) - } - - // what to do on window resize - fn update(&mut self, width: f32, height: f32) { - self.aspect = width / height; - } - - fn far(&self) -> f32 { - self.far - } -} - -impl Default for OffAxisProjection { - fn default() -> Self { - Self { - near: 0.0, - far: 1000.0, - aspect: 1.0, - } - } -} pub fn make_projection_rh_from_frustum(left: f32, right: f32, bottom: f32, top: f32, near:f32, far:f32) -> Mat4 { @@ -65,6 +33,80 @@ pub fn make_projection_rh_from_frustum(left: f32, right: f32, bottom: f32, top: } +pub fn make_projection_rh_from_frustum_reversed(left: f32, right: f32, bottom: f32, top: f32, near:f32, far:f32) -> Mat4 +{ + + assert!(near > 0.0); + + // + // reversed z 0..1 projection based on https://thxforthefish.com/posts/reverse_z/ + // + let a = (right + left) / (right - left); + let b: f32 = (top + bottom) / (top - bottom); + // let c= if far.abs() > f32::MAX { -1.0 } else { -(far + near) / (far - near)}; + // let d = if far.abs() > f32::MAX { -2.0 * near } else { -2.0 * far * near / (far - near) }; + + let c = near / (far - near); + let d = far * near / (far - near); + + + Mat4::from_cols( + Vec4::new(2.0 * near/(right-left),0.0,0.0,0.0), + Vec4::new(0.0,2.0*near/(top-bottom), 0.0,0.0), + Vec4::new(a, b, c, -1.0), + Vec4::new(0.0, 0.0, d, 0.0)) +} + + +pub fn make_projection_rh_custom(fov_y: f32, aspect_ratio: f32, z_near: f32, z_far: f32) -> Mat4 +{ + let tan_fovy = (fov_y * 0.5).tan(); // use half angle beta + let right = tan_fovy * aspect_ratio * z_near; + let left = -right; + let top = tan_fovy * z_near; + let bottom = -top; + + //make_projection_rh_from_frustum(left, right, bottom, top, z_near, z_far) + + make_projection_rh_from_frustum_reversed(left, right, bottom, top, z_near, z_far) +} + + + +impl CameraProjection for OffAxisProjection { + fn get_projection_matrix(&self) -> Mat4 { + + make_projection_rh_custom(45.0_f32.to_radians(), self.aspect, self.near, self.far) + + // Mat4::perspective_rh(45.0_f32.to_radians(), + // self.aspect, + // self.near, + // self.far) + + } + + // what to do on window resize + fn update(&mut self, width: f32, height: f32) { + self.aspect = width / height; + } + + fn far(&self) -> f32 { + println!("Z-Value"); + self.far + } +} + +impl Default for OffAxisProjection { + fn default() -> Self { + Self { + near: 0.1, + far: 1000.0, + aspect: 1.0, + } + } +} + + pub fn offaxis_camera_setup(mut commands: Commands) { let projection = OffAxisProjection::default();