Moved bound implementations into the corresponding modules
This commit is contained in:
parent
2722815d84
commit
d3d7241c86
5 changed files with 105 additions and 49 deletions
13
src/aabb.rs
13
src/aabb.rs
|
@ -20,11 +20,13 @@
|
|||
//! dimension) where the slope of every line is either 0 or undefined. These
|
||||
//! are useful for very cheap collision detection.
|
||||
|
||||
use bound::*;
|
||||
use point::{Point, Point2, Point3};
|
||||
use vector::{Vector, Vector2, Vector3};
|
||||
use ray::{Ray2};
|
||||
use intersect::Intersect;
|
||||
use num::{zero, one, BaseNum, BaseFloat};
|
||||
use plane::Plane;
|
||||
use std::fmt;
|
||||
use std::num::Float;
|
||||
|
||||
|
@ -217,3 +219,14 @@ impl<S: BaseFloat> Intersect<Option<Point2<S>>> for (Ray2<S>, Aabb2<S>) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Aabb3<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
//TODO: match all 8 corners
|
||||
match (self.min.relate(plane), self.max.relate(plane)) {
|
||||
(Relation::In, Relation::In) => Relation::In,
|
||||
(Relation::Out, Relation::Out) => Relation::Out,
|
||||
(_, _) => Relation::Cross,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
58
src/bound.rs
58
src/bound.rs
|
@ -15,60 +15,22 @@
|
|||
|
||||
//! Generic spatial bounds.
|
||||
|
||||
use aabb::{Aabb, Aabb3};
|
||||
use num::BaseNum;
|
||||
use plane::Plane;
|
||||
use point::{Point, Point3};
|
||||
use sphere::Sphere;
|
||||
|
||||
/// Spatial relation between two objects.
|
||||
#[derive(Copy, Clone, Debug, Eq, Hash, Ord, PartialOrd, PartialEq)]
|
||||
#[repr(u8)]
|
||||
pub enum Relation {
|
||||
/// Completely inside
|
||||
In,
|
||||
/// Crosses the boundary
|
||||
Cross,
|
||||
/// Completely outside
|
||||
Out,
|
||||
/// Completely inside
|
||||
In,
|
||||
/// Crosses the boundary
|
||||
Cross,
|
||||
/// Completely outside
|
||||
Out,
|
||||
}
|
||||
|
||||
/// Generic bound.
|
||||
pub trait Bound<S> {
|
||||
/// Classify the spatial relation with a plane
|
||||
fn relate(&self, &Plane<S>) -> Relation;
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Point3<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
let dist = self.dot(&plane.n);
|
||||
if dist > plane.d {
|
||||
Relation::In
|
||||
}else if dist < plane.d {
|
||||
Relation::Out
|
||||
}else {
|
||||
Relation::Cross
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Aabb3<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
match (self.min.relate(plane), self.max.relate(plane)) {
|
||||
(Relation::In, Relation::In) => Relation::In,
|
||||
(Relation::Out, Relation::Out) => Relation::Out,
|
||||
(_, _) => Relation::Cross,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Sphere<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
let dist = self.center.dot(&plane.n) - plane.d;
|
||||
if dist > self.radius {
|
||||
Relation::In
|
||||
}else if dist < - self.radius {
|
||||
Relation::Out
|
||||
}else {
|
||||
Relation::Cross
|
||||
}
|
||||
}
|
||||
/// Classify the spatial relation with a plane
|
||||
fn relate(&self, &Plane<S>) -> Relation;
|
||||
}
|
||||
|
|
15
src/point.rs
15
src/point.rs
|
@ -23,7 +23,9 @@ use std::ops::*;
|
|||
|
||||
use approx::ApproxEq;
|
||||
use array::{Array1, FixedArray};
|
||||
use bound::*;
|
||||
use num::{BaseNum, BaseFloat, one, zero};
|
||||
use plane::Plane;
|
||||
use vector::*;
|
||||
|
||||
/// A point in 2-dimensional space.
|
||||
|
@ -445,3 +447,16 @@ impl<S: BaseNum> fmt::Debug for Point3<S> {
|
|||
write!(f, "[{:?}, {:?}, {:?}]", self.x, self.y, self.z)
|
||||
}
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Point3<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
let dist = self.dot(&plane.n);
|
||||
if dist > plane.d {
|
||||
Relation::In
|
||||
}else if dist < plane.d {
|
||||
Relation::Out
|
||||
}else {
|
||||
Relation::Cross
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,9 +15,11 @@
|
|||
|
||||
//! Bounding sphere
|
||||
|
||||
use bound::*;
|
||||
use intersect::Intersect;
|
||||
use num::{BaseFloat, zero};
|
||||
use num::{BaseNum, BaseFloat, zero};
|
||||
use point::{Point, Point3};
|
||||
use plane::Plane;
|
||||
use ray::Ray3;
|
||||
use vector::Vector;
|
||||
|
||||
|
@ -42,3 +44,16 @@ impl<S: BaseFloat> Intersect<Option<Point3<S>>> for (Sphere<S>, Ray3<S>) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<S: BaseNum> Bound<S> for Sphere<S> {
|
||||
fn relate(&self, plane: &Plane<S>) -> Relation {
|
||||
let dist = self.center.dot(&plane.n) - plane.d;
|
||||
if dist > self.radius {
|
||||
Relation::In
|
||||
}else if dist < - self.radius {
|
||||
Relation::Out
|
||||
}else {
|
||||
Relation::Cross
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
51
tests/bound.rs
Normal file
51
tests/bound.rs
Normal file
|
@ -0,0 +1,51 @@
|
|||
// Copyright 2013-2015 The CGMath Developers. For a full listing of the authors,
|
||||
// refer to the AUTHORS file at the top-level directory of this distribution.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
extern crate cgmath;
|
||||
|
||||
use cgmath::{Aabb3, Bound, Plane, Point, Point3, Relation, Sphere, Vector, vec3};
|
||||
|
||||
#[test]
|
||||
fn point() {
|
||||
let point = Point3::new(1f32, 2.0, 3.0);
|
||||
let normal = vec3(0f32, -0.8, -0.36);
|
||||
let plane = Plane::from_point_normal(point, normal);
|
||||
|
||||
assert_eq!(point.relate(&plane), Relation::Cross);
|
||||
assert_eq!(point.add_v(&normal).relate(&plane), Relation::In);
|
||||
assert_eq!(point.add_v(&normal.mul_s(-1.0)).relate(&plane), Relation::Out);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sphere() {
|
||||
let point = Point3::new(1f32, 2.0, 3.0);
|
||||
let sphere = Sphere { center: point, radius: 1.0 };
|
||||
let normal = vec3(0f32, 0.0, 1.0);
|
||||
|
||||
assert_eq!(sphere.relate(
|
||||
&Plane::from_point_normal(point, normal)
|
||||
), Relation::Cross);
|
||||
assert_eq!(sphere.relate(
|
||||
&Plane::from_point_normal(point.add_v(&normal.mul_s(-3.0)), normal),
|
||||
), Relation::In);
|
||||
assert_eq!(sphere.relate(
|
||||
&Plane::from_point_normal(point.add_v(&normal.mul_s(3.0)), normal),
|
||||
), Relation::Out);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn aabb() {
|
||||
//TODO
|
||||
}
|
Loading…
Reference in a new issue