Skip to content

Commit

Permalink
Merge pull request #205 from hannobraun/aabb
Browse files Browse the repository at this point in the history
Add `math::Aabb`
  • Loading branch information
hannobraun authored Feb 17, 2022
2 parents 2b2262b + 19a98c9 commit e29d024
Show file tree
Hide file tree
Showing 15 changed files with 121 additions and 50 deletions.
24 changes: 12 additions & 12 deletions src/camera.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
use std::f64::consts::FRAC_PI_2;

use nalgebra::{Point, TAffine, Transform, Translation, Vector};
use parry3d_f64::{
bounding_volume::AABB,
query::{Ray, RayCast as _},
};
use parry3d_f64::query::{Ray, RayCast as _};
use winit::dpi::PhysicalPosition;

use crate::{math::Triangle, window::Window};
use crate::{
math::{Aabb, Triangle},
window::Window,
};

/// The camera abstraction
///
Expand Down Expand Up @@ -38,19 +38,19 @@ impl Camera {

const INITIAL_FIELD_OF_VIEW_IN_X: f64 = FRAC_PI_2; // 90 degrees

pub fn new(aabb: &AABB) -> Self {
pub fn new(aabb: &Aabb) -> Self {
let initial_distance = {
// Let's make sure we choose a distance, so that the model fills
// most of the screen.
//
// To do that, first compute the model's highest point, as well as
// the furthest point from the origin, in x and y.
let highest_point = aabb.maxs.z;
let highest_point = aabb.max.z;
let furthest_point = [
aabb.mins.x.abs(),
aabb.maxs.x,
aabb.mins.y.abs(),
aabb.maxs.y,
aabb.min.x.abs(),
aabb.max.x,
aabb.min.y.abs(),
aabb.max.y,
]
.into_iter()
.reduce(|a, b| f64::max(a, b))
Expand Down Expand Up @@ -180,7 +180,7 @@ impl Camera {
transform
}

pub fn update_planes(&mut self, aabb: &AABB) {
pub fn update_planes(&mut self, aabb: &Aabb) {
let view_transform = self.camera_to_model();
let view_direction = Vector::from([0., 0., -1.]);

Expand Down
8 changes: 3 additions & 5 deletions src/kernel/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,7 @@ pub mod shapes;
pub mod topology;
pub mod triangulation;

use parry3d_f64::bounding_volume::AABB;

use crate::debug::DebugInfo;
use crate::{debug::DebugInfo, math::Aabb};

use self::topology::{edges::Edges, faces::Faces, vertices::Vertices};

Expand All @@ -16,7 +14,7 @@ pub trait Shape {
///
/// If a shape is empty, its [`Aabb`]'s `min` and `max` points must be equal
/// (but are otherwise not specified).
fn bounding_volume(&self) -> AABB;
fn bounding_volume(&self) -> Aabb;

/// Compute triangles to approximate the shape's faces
///
Expand Down Expand Up @@ -75,7 +73,7 @@ macro_rules! dispatch {
}

dispatch! {
bounding_volume() -> AABB;
bounding_volume() -> Aabb;
faces(
tolerance: f64,
debug: &mut DebugInfo,
Expand Down
10 changes: 5 additions & 5 deletions src/kernel/shapes/circle.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use nalgebra::point;
use parry3d_f64::bounding_volume::AABB;

use crate::{
debug::DebugInfo,
Expand All @@ -12,13 +11,14 @@ use crate::{
},
Shape,
},
math::Aabb,
};

impl Shape for fj::Circle {
fn bounding_volume(&self) -> AABB {
AABB {
mins: point![-self.radius, -self.radius, 0.0],
maxs: point![self.radius, self.radius, 0.0],
fn bounding_volume(&self) -> Aabb {
Aabb {
min: point![-self.radius, -self.radius, 0.0],
max: point![self.radius, self.radius, 0.0],
}
}

Expand Down
5 changes: 2 additions & 3 deletions src/kernel/shapes/difference_2d.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
use parry3d_f64::bounding_volume::AABB;

use crate::{
debug::DebugInfo,
kernel::{
Expand All @@ -10,10 +8,11 @@ use crate::{
},
Shape,
},
math::Aabb,
};

impl Shape for fj::Difference2d {
fn bounding_volume(&self) -> AABB {
fn bounding_volume(&self) -> Aabb {
// This is a conservative estimate of the bounding box: It's never going
// to be bigger than the bounding box of the original shape that another
// is being subtracted from.
Expand Down
5 changes: 2 additions & 3 deletions src/kernel/shapes/difference_3d.rs
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
use parry3d_f64::bounding_volume::AABB;

use crate::{
debug::DebugInfo,
kernel::{
topology::{edges::Edges, faces::Faces, vertices::Vertices},
Shape,
},
math::Aabb,
};

impl Shape for fj::Difference {
fn bounding_volume(&self) -> AABB {
fn bounding_volume(&self) -> Aabb {
// This is a conservative estimate of the bounding box: It's never going
// to be bigger than the bounding box of the original shape that another
// is being subtracted from.
Expand Down
8 changes: 3 additions & 5 deletions src/kernel/shapes/sketch.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
use parry3d_f64::bounding_volume::AABB;

use crate::{
debug::DebugInfo,
kernel::{
Expand All @@ -11,13 +9,13 @@ use crate::{
},
Shape,
},
math::{Point, Vector},
math::{Aabb, Point, Vector},
};

impl Shape for fj::Sketch {
fn bounding_volume(&self) -> AABB {
fn bounding_volume(&self) -> Aabb {
let vertices = self.vertices();
AABB::from_points(vertices.0.iter().map(|vertex| vertex.location()))
Aabb::from_points(vertices.0.iter().map(|vertex| *vertex.location()))
}

fn faces(&self, _: f64, _: &mut DebugInfo) -> Faces {
Expand Down
7 changes: 4 additions & 3 deletions src/kernel/shapes/sweep.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use std::f64::consts::PI;

use nalgebra::vector;
use parry3d_f64::{bounding_volume::AABB, math::Isometry};
use parry3d_f64::math::Isometry;

use crate::{
debug::DebugInfo,
Expand All @@ -14,12 +14,13 @@ use crate::{
},
Shape,
},
math::Aabb,
};

impl Shape for fj::Sweep {
fn bounding_volume(&self) -> AABB {
fn bounding_volume(&self) -> Aabb {
let mut aabb = self.shape.bounding_volume();
aabb.maxs.z = self.length;
aabb.max.z = self.length;
aabb
}

Expand Down
10 changes: 4 additions & 6 deletions src/kernel/shapes/transform.rs
Original file line number Diff line number Diff line change
@@ -1,19 +1,17 @@
use parry3d_f64::{bounding_volume::AABB, math::Isometry};
use parry3d_f64::math::Isometry;

use crate::{
debug::DebugInfo,
kernel::{
topology::{edges::Edges, faces::Faces, vertices::Vertices},
Shape,
},
math::Transform,
math::{Aabb, Transform},
};

impl Shape for fj::Transform {
fn bounding_volume(&self) -> AABB {
self.shape
.bounding_volume()
.transform_by(&transform(self).into())
fn bounding_volume(&self) -> Aabb {
transform(self).transform_aabb(&self.shape.bounding_volume())
}

fn faces(&self, tolerance: f64, debug_info: &mut DebugInfo) -> Faces {
Expand Down
5 changes: 2 additions & 3 deletions src/kernel/shapes/union.rs
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
use parry3d_f64::bounding_volume::{BoundingVolume as _, AABB};

use crate::{
debug::DebugInfo,
kernel::{
topology::{edges::Edges, faces::Faces, vertices::Vertices},
Shape,
},
math::Aabb,
};

impl Shape for fj::Union {
fn bounding_volume(&self) -> AABB {
fn bounding_volume(&self) -> Aabb {
let a = self.a.bounding_volume();
let b = self.b.bounding_volume();

Expand Down
4 changes: 2 additions & 2 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ fn main() -> anyhow::Result<()> {
// This can't be addressed with the current structure, since the watcher
// closure takes ownership of the model.
//
// This big is tracked in the following issues:
// This is being tracked in the following issue:
// https://github.com/hannobraun/fornjot/issues/32
let shape = model.load(&parameters)?;

Expand All @@ -72,7 +72,7 @@ fn main() -> anyhow::Result<()> {
// by some value.
let tolerance = {
let mut min_extent = f64::MAX;
for &extent in aabb.extents().iter() {
for extent in aabb.size().components() {
if extent > 0. && extent < min_extent {
min_extent = extent;
}
Expand Down
64 changes: 64 additions & 0 deletions src/math/aabb.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
use parry3d_f64::bounding_volume::BoundingVolume as _;

use super::{Point, Vector};

/// An axis-aligned bounding box (AABB)
pub struct Aabb {
/// The minimum coordinates of the AABB
pub min: Point<3>,

/// The maximum coordinates of the AABB
pub max: Point<3>,
}

impl Aabb {
/// Construct an AABB from a list of points
///
/// The resulting AABB will contain all the points.
pub fn from_points(points: impl IntoIterator<Item = Point<3>>) -> Self {
let points: Vec<_> = points.into_iter().collect();
parry3d_f64::bounding_volume::AABB::from_points(&points).into()
}

/// Construct an AABB from a Parry AABB
pub fn from_parry(aabb: parry3d_f64::bounding_volume::AABB) -> Self {
Self {
min: aabb.mins.into(),
max: aabb.maxs.into(),
}
}

/// Convert the AABB to a Parry AABB
pub fn to_parry(&self) -> parry3d_f64::bounding_volume::AABB {
parry3d_f64::bounding_volume::AABB {
mins: self.min,
maxs: self.max,
}
}

/// Access the vertices of the AABB
pub fn vertices(&self) -> [Point<3>; 8] {
self.to_parry().vertices()
}

/// Compute the center point of the AABB
pub fn center(&self) -> Point<3> {
self.to_parry().center()
}

/// Compute the size of the AABB
pub fn size(&self) -> Vector<3> {
self.to_parry().extents().into()
}

/// Merge this AABB with another
pub fn merged(&self, other: &Aabb) -> Aabb {
self.to_parry().merged(&other.to_parry()).into()
}
}

impl From<parry3d_f64::bounding_volume::AABB> for Aabb {
fn from(aabb: parry3d_f64::bounding_volume::AABB) -> Self {
Self::from_parry(aabb)
}
}
5 changes: 3 additions & 2 deletions src/math/mod.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
pub mod aabb;
pub mod point;
pub mod segment;
pub mod transform;
pub mod triangle;
pub mod vector;

pub use self::{
point::Point, segment::Segment, transform::Transform, triangle::Triangle,
vector::Vector,
aabb::Aabb, point::Point, segment::Segment, transform::Transform,
triangle::Triangle, vector::Vector,
};
10 changes: 9 additions & 1 deletion src/math/transform.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use super::{Point, Triangle, Vector};
use super::{Aabb, Point, Triangle, Vector};

/// A transform
pub struct Transform(parry3d_f64::math::Isometry<f64>);
Expand All @@ -22,6 +22,14 @@ impl Transform {
c: self.transform_point(&triangle.c),
}
}

/// Transform the given axis-aligned bounding box
pub fn transform_aabb(&self, aabb: &Aabb) -> Aabb {
Aabb {
min: self.transform_point(&aabb.min),
max: self.transform_point(&aabb.max),
}
}
}

impl From<parry3d_f64::math::Isometry<f64>> for Transform {
Expand Down
1 change: 1 addition & 0 deletions src/math/triangle.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use super::Point;

/// A triangle
#[derive(Clone, Copy)]
pub struct Triangle {
pub a: Point<3>,
Expand Down
5 changes: 5 additions & 0 deletions src/math/vector.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,11 @@ impl<const D: usize> Vector<D> {
pub fn dot(&self, other: &Self) -> f64 {
self.to_na().dot(&other.to_na())
}

/// Access an iterator over the vector's components
pub fn components(&self) -> [f64; D] {
self.0
}
}

impl Vector<1> {
Expand Down

0 comments on commit e29d024

Please sign in to comment.