Use the Clone trait instead of Copy and switch from the copy keyword to calling the clone method.

impl_approx! is broken with a borrow issue. The library does not compile yet. Sorry!
This commit is contained in:
Brendan Zabarauskas 2013-06-29 16:38:55 +10:00
parent c36cb6e555
commit 6fb6d57175
11 changed files with 166 additions and 165 deletions

View file

@ -189,11 +189,11 @@ macro_rules! impl_dimensional_fns(
macro_rules! impl_swap(
($Self:ident) => (
impl<T:Copy> $Self<T> {
impl<T:Clone> $Self<T> {
#[inline]
pub fn swap(&mut self, a: uint, b: uint) {
let tmp = copy *self.index(a);
*self.index_mut(a) = copy *self.index(b);
let tmp = self.index(a).clone();
*self.index_mut(a) = self.index(b).clone();
*self.index_mut(b) = tmp;
}
}
@ -202,7 +202,7 @@ macro_rules! impl_swap(
macro_rules! impl_approx(
($Self:ident) => (
impl<T:Copy + Eq + ApproxEq<T>> ApproxEq<T> for $Self<T> {
impl<T:Clone + Eq + ApproxEq<T>> ApproxEq<T> for $Self<T> {
#[inline]
pub fn approx_epsilon() -> T {
ApproxEq::approx_epsilon::<T,T>()
@ -215,8 +215,7 @@ macro_rules! impl_approx(
#[inline]
pub fn approx_eq_eps(&self, other: &$Self<T>, epsilon: &T) -> bool {
self.zip(other, |a, b| a.approx_eq_eps(b, epsilon)).all(|&x| x)
self.zip(other, |a, b| a.approx_eq_eps(b, epsilon)).iter().all(|&x| x)
}
}
)

View file

@ -19,7 +19,7 @@ use point::Point3;
mod num_macros;
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Frustum<T> {
left: Plane<T>,
right: Plane<T>,
@ -29,7 +29,7 @@ pub struct Frustum<T> {
far: Plane<T>,
}
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct FrustumPoints<T> {
near_top_left: Point3<T>,
near_top_right: Point3<T>,
@ -41,7 +41,7 @@ pub struct FrustumPoints<T> {
far_bottom_right: Point3<T>,
}
impl<T:Copy + Real> Frustum<T> {
impl<T:Clone + Real> Frustum<T> {
/// Constructs a frustum
pub fn from_planes(left: Plane<T>, right: Plane<T>,
bottom: Plane<T>, top: Plane<T>,
@ -80,7 +80,7 @@ impl<T:Copy + Real> Frustum<T> {
}
}
impl<T:Copy + Real + ApproxEq<T>> Frustum<T> {
impl<T:Clone + Real + ApproxEq<T>> Frustum<T> {
/// Computes where the frustum planes intersect to form corners and returns
/// a struct containing the eight resulting position vectors.
pub fn to_points(&self) -> FrustumPoints<T> {
@ -97,7 +97,7 @@ impl<T:Copy + Real + ApproxEq<T>> Frustum<T> {
}
}
impl<T:Copy + Eq + ApproxEq<T>> ApproxEq<T> for Frustum<T> {
impl<T:Clone + Eq + ApproxEq<T>> ApproxEq<T> for Frustum<T> {
#[inline]
pub fn approx_epsilon() -> T {
ApproxEq::approx_epsilon::<T,T>()

View file

@ -22,7 +22,7 @@ mod num_macros;
mod dim_macros;
mod mat_macros;
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Mat2<T> {
x: Vec2<T>,
y: Vec2<T>,
@ -42,7 +42,7 @@ impl_dimensional_fns!(Mat2, Vec2<T>, 2)
impl_approx!(Mat2)
impl_mat!(Mat2, Vec2)
impl_mat_copyable!(Mat2, Vec2)
impl_mat_clonable!(Mat2, Vec2)
impl_mat_numeric!(Mat2, Vec2)
impl_mat_approx_numeric!(Mat2)
impl_mat_neg!(Mat2)
@ -66,33 +66,33 @@ impl<T> Mat2<T> {
}
}
impl<T:Copy + Num> ToMat3<T> for Mat2<T> {
impl<T:Clone + Num> ToMat3<T> for Mat2<T> {
#[inline]
pub fn to_mat3(&self) -> Mat3<T> {
Mat3::new(copy *self.elem(0, 0), copy *self.elem(0, 1), zero!(T),
copy *self.elem(1, 0), copy *self.elem(1, 1), zero!(T),
Mat3::new(self.elem(0, 0).clone(), self.elem(0, 1).clone(), zero!(T),
self.elem(1, 0).clone(), self.elem(1, 1).clone(), zero!(T),
zero!(T), zero!(T), one!(T))
}
}
impl<T:Copy + Num> ToMat4<T> for Mat2<T> {
impl<T:Clone + Num> ToMat4<T> for Mat2<T> {
#[inline]
pub fn to_mat4(&self) -> Mat4<T> {
Mat4::new(copy *self.elem(0, 0), copy *self.elem(0, 1), zero!(T), zero!(T),
copy *self.elem(1, 0), copy *self.elem(1, 1), zero!(T), zero!(T),
Mat4::new(self.elem(0, 0).clone(), self.elem(0, 1).clone(), zero!(T), zero!(T),
self.elem(1, 0).clone(), self.elem(1, 1).clone(), zero!(T), zero!(T),
zero!(T), zero!(T), one!(T), zero!(T),
zero!(T), zero!(T), zero!(T), one!(T))
}
}
impl<T:Copy + Real> Mat2<T> {
impl<T:Clone + Real> Mat2<T> {
#[inline]
pub fn from_angle(radians: T) -> Mat2<T> {
let cos_theta = radians.cos();
let sin_theta = radians.sin();
Mat2::new(copy cos_theta, copy -sin_theta,
copy sin_theta, copy cos_theta)
Mat2::new(cos_theta.clone(), -sin_theta.clone(),
sin_theta.clone(), cos_theta.clone())
}
}
@ -265,7 +265,7 @@ mod mat2_tests{
}
}
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Mat3<T> {
x: Vec3<T>,
y: Vec3<T>,
@ -286,7 +286,7 @@ impl_dimensional_fns!(Mat3, Vec3<T>, 3)
impl_approx!(Mat3)
impl_mat!(Mat3, Vec3)
impl_mat_copyable!(Mat3, Vec3)
impl_mat_clonable!(Mat3, Vec3)
impl_mat_numeric!(Mat3, Vec3)
impl_mat_approx_numeric!(Mat3)
impl_mat_neg!(Mat3)
@ -313,17 +313,17 @@ impl<T> Mat3<T> {
}
}
impl<T:Copy + Num> ToMat4<T> for Mat3<T> {
impl<T:Clone + Num> ToMat4<T> for Mat3<T> {
#[inline]
pub fn to_mat4(&self) -> Mat4<T> {
Mat4::new(copy *self.elem(0, 0), copy *self.elem(0, 1), copy *self.elem(0, 2), zero!(T),
copy *self.elem(1, 0), copy *self.elem(1, 1), copy *self.elem(1, 2), zero!(T),
copy *self.elem(2, 0), copy *self.elem(2, 1), copy *self.elem(2, 2), zero!(T),
Mat4::new(self.elem(0, 0).clone(), self.elem(0, 1).clone(), self.elem(0, 2).clone(), zero!(T),
self.elem(1, 0).clone(), self.elem(1, 1).clone(), self.elem(1, 2).clone(), zero!(T),
self.elem(2, 0).clone(), self.elem(2, 1).clone(), self.elem(2, 2).clone(), zero!(T),
zero!(T), zero!(T), zero!(T), one!(T))
}
}
impl<T:Copy + Real> Mat3<T> {
impl<T:Clone + Real> Mat3<T> {
/// Construct a matrix from an angular rotation around the `x` axis
pub fn from_angle_x(radians: T) -> Mat3<T> {
// http://en.wikipedia.org/wiki/Rotation_matrix#Basic_rotations
@ -331,8 +331,8 @@ impl<T:Copy + Real> Mat3<T> {
let sin_theta = radians.sin();
Mat3::new(one!(T), zero!(T), zero!(T),
zero!(T), copy cos_theta, copy sin_theta,
zero!(T), copy -sin_theta, copy cos_theta)
zero!(T), cos_theta.clone(), sin_theta.clone(),
zero!(T), -sin_theta.clone(), cos_theta.clone())
}
/// Construct a matrix from an angular rotation around the `y` axis
@ -341,9 +341,9 @@ impl<T:Copy + Real> Mat3<T> {
let cos_theta = radians.cos();
let sin_theta = radians.sin();
Mat3::new(copy cos_theta, zero!(T), copy -sin_theta,
Mat3::new(cos_theta.clone(), zero!(T), -sin_theta.clone(),
zero!(T), one!(T), zero!(T),
copy sin_theta, zero!(T), copy cos_theta)
sin_theta.clone(), zero!(T), cos_theta.clone())
}
/// Construct a matrix from an angular rotation around the `z` axis
@ -352,8 +352,8 @@ impl<T:Copy + Real> Mat3<T> {
let cos_theta = radians.cos();
let sin_theta = radians.sin();
Mat3::new(copy cos_theta, copy sin_theta, zero!(T),
copy -sin_theta, copy cos_theta, zero!(T),
Mat3::new(cos_theta.clone(), sin_theta.clone(), zero!(T),
-sin_theta.clone(), cos_theta.clone(), zero!(T),
zero!(T), zero!(T), one!(T))
}
@ -384,9 +384,9 @@ impl<T:Copy + Real> Mat3<T> {
let s = radians.sin();
let _1_c = one!(T) - c;
let x = copy axis.x;
let y = copy axis.y;
let z = copy axis.z;
let x = axis.x.clone();
let y = axis.y.clone();
let z = axis.z.clone();
Mat3::new(_1_c*x*x + c, _1_c*x*y + s*z, _1_c*x*z - s*y,
_1_c*x*y - s*z, _1_c*y*y + c, _1_c*y*z + s*x,
@ -407,7 +407,7 @@ impl<T:Copy + Real> Mat3<T> {
}
}
impl<T:Copy + Real> ToQuat<T> for Mat3<T> {
impl<T:Clone + Real> ToQuat<T> for Mat3<T> {
/// Convert the matrix to a quaternion
pub fn to_quat(&self) -> Quat<T> {
// Implemented using a mix of ideas from jMonkeyEngine and Ken Shoemake's
@ -663,7 +663,7 @@ mod mat3_tests{
}
}
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Mat4<T> {
x: Vec4<T>,
y: Vec4<T>,
@ -685,7 +685,7 @@ impl_dimensional_fns!(Mat4, Vec4<T>, 4)
impl_approx!(Mat4)
impl_mat!(Mat4, Vec4)
impl_mat_copyable!(Mat4, Vec4)
impl_mat_clonable!(Mat4, Vec4)
impl_mat_numeric!(Mat4, Vec4)
impl_mat_approx_numeric!(Mat4)
impl_mat_neg!(Mat4)

View file

@ -41,18 +41,18 @@ macro_rules! impl_mat(
)
)
macro_rules! impl_mat_copyable(
macro_rules! impl_mat_clonable(
($Mat:ident, $Vec:ident) => (
impl<T:Copy> $Mat<T> {
impl<T:Clone> $Mat<T> {
#[inline]
pub fn row(&self, i: uint) -> $Vec<T> {
$Vec::from_slice(self.map(|c| copy *c.index(i)))
$Vec::from_slice(self.map(|c| c.index(i).clone()))
}
#[inline]
pub fn swap_cols(&mut self, a: uint, b: uint) {
let tmp = copy *self.col(a);
*self.col_mut(a) = copy *self.col(b);
let tmp = self.col(a).clone();
*self.col_mut(a) = self.col(b).clone();
*self.col_mut(b) = tmp;
}
@ -63,8 +63,8 @@ macro_rules! impl_mat_copyable(
#[inline]
pub fn swap_elem(&mut self, (ai, aj): (uint, uint), (bi, bj): (uint, uint)) {
let tmp = copy *self.elem(ai, aj);
*self.elem_mut(ai, aj) = copy *self.elem(bi, bj);
let tmp = self.elem(ai, aj).clone();
*self.elem_mut(ai, aj) = self.elem(bi, bj).clone();
*self.elem_mut(bi, bj) = tmp;
}
@ -77,19 +77,19 @@ macro_rules! impl_mat_copyable(
macro_rules! mat_transpose(
(Mat2) => (
Mat2::new(copy *self.elem(0, 0), copy *self.elem(1, 0),
copy *self.elem(0, 1), copy *self.elem(1, 1))
Mat2::new(self.elem(0, 0).clone(), self.elem(1, 0).clone(),
self.elem(0, 1).clone(), self.elem(1, 1).clone())
);
(Mat3) => (
Mat3::new(copy *self.elem(0, 0), copy *self.elem(1, 0), copy *self.elem(2, 0),
copy *self.elem(0, 1), copy *self.elem(1, 1), copy *self.elem(2, 1),
copy *self.elem(0, 2), copy *self.elem(1, 2), copy *self.elem(2, 2))
Mat3::new(self.elem(0, 0).clone(), self.elem(1, 0).clone(), self.elem(2, 0).clone(),
self.elem(0, 1).clone(), self.elem(1, 1).clone(), self.elem(2, 1).clone(),
self.elem(0, 2).clone(), self.elem(1, 2).clone(), self.elem(2, 2).clone())
);
(Mat4) => (
Mat4::new(copy *self.elem(0, 0), copy *self.elem(1, 0), copy *self.elem(2, 0), copy *self.elem(3, 0),
copy *self.elem(0, 1), copy *self.elem(1, 1), copy *self.elem(2, 1), copy *self.elem(3, 1),
copy *self.elem(0, 2), copy *self.elem(1, 2), copy *self.elem(2, 2), copy *self.elem(3, 2),
copy *self.elem(0, 3), copy *self.elem(1, 3), copy *self.elem(2, 3), copy *self.elem(3, 3))
Mat4::new(self.elem(0, 0).clone(), self.elem(1, 0).clone(), self.elem(2, 0).clone(), self.elem(3, 0).clone(),
self.elem(0, 1).clone(), self.elem(1, 1).clone(), self.elem(2, 1).clone(), self.elem(3, 1).clone(),
self.elem(0, 2).clone(), self.elem(1, 2).clone(), self.elem(2, 2).clone(), self.elem(3, 2).clone(),
self.elem(0, 3).clone(), self.elem(1, 3).clone(), self.elem(2, 3).clone(), self.elem(3, 3).clone())
);
)
@ -129,7 +129,7 @@ macro_rules! mat_transpose_self(
macro_rules! impl_mat_numeric(
($Mat:ident, $Vec:ident) => (
impl<T:Copy + Num> $Mat<T> {
impl<T:Clone + Num> $Mat<T> {
#[inline]
pub fn from_value(value: T) -> $Mat<T> { mat_from_value!($Mat) }
@ -141,7 +141,7 @@ macro_rules! impl_mat_numeric(
#[inline]
pub fn mul_t(&self, value: T) -> $Mat<T> {
$Mat::from_slice(self.map(|&c| c.mul_t(copy value)))
$Mat::from_slice(self.map(|&c| c.mul_t(value.clone())))
}
#[inline]
@ -166,7 +166,7 @@ macro_rules! impl_mat_numeric(
#[inline]
pub fn mul_self_t(&mut self, value: T) {
self.map_mut(|x| x.mul_self_t(copy value))
self.map_mut(|x| x.mul_self_t(value.clone()))
}
#[inline]
@ -206,19 +206,19 @@ macro_rules! impl_mat_numeric(
macro_rules! mat_from_value(
(Mat2) => (
Mat2::new(copy value, zero!(T),
zero!(T), copy value)
Mat2::new(value.clone(), zero!(T),
zero!(T), value.clone())
);
(Mat3) => (
Mat3::new(copy value, zero!(T), zero!(T),
zero!(T), copy value, zero!(T),
zero!(T), zero!(T), copy value)
Mat3::new(value.clone(), zero!(T), zero!(T),
zero!(T), value.clone(), zero!(T),
zero!(T), zero!(T), value.clone())
);
(Mat4) => (
Mat4::new(copy value, zero!(T), zero!(T), zero!(T),
zero!(T), copy value, zero!(T), zero!(T),
zero!(T), zero!(T), copy value, zero!(T),
zero!(T), zero!(T), zero!(T), copy value)
Mat4::new(value.clone(), zero!(T), zero!(T), zero!(T),
zero!(T), value.clone(), zero!(T), zero!(T),
zero!(T), zero!(T), value.clone(), zero!(T),
zero!(T), zero!(T), zero!(T), value.clone())
);
)
@ -292,18 +292,18 @@ macro_rules! mat_determinant(
self.col(0).dot(&self.col(1).cross(self.col(2)))
);
(Mat4) => ({
let m0 = Mat3::new(copy *self.elem(1, 1), copy *self.elem(2, 1), copy *self.elem(3, 1),
copy *self.elem(1, 2), copy *self.elem(2, 2), copy *self.elem(3, 2),
copy *self.elem(1, 3), copy *self.elem(2, 3), copy *self.elem(3, 3));
let m1 = Mat3::new(copy *self.elem(0, 1), copy *self.elem(2, 1), copy *self.elem(3, 1),
copy *self.elem(0, 2), copy *self.elem(2, 2), copy *self.elem(3, 2),
copy *self.elem(0, 3), copy *self.elem(2, 3), copy *self.elem(3, 3));
let m2 = Mat3::new(copy *self.elem(0, 1), copy *self.elem(1, 1), copy *self.elem(3, 1),
copy *self.elem(0, 2), copy *self.elem(1, 2), copy *self.elem(3, 2),
copy *self.elem(0, 3), copy *self.elem(1, 3), copy *self.elem(3, 3));
let m3 = Mat3::new(copy *self.elem(0, 1), copy *self.elem(1, 1), copy *self.elem(2, 1),
copy *self.elem(0, 2), copy *self.elem(1, 2), copy *self.elem(2, 2),
copy *self.elem(0, 3), copy *self.elem(1, 3), copy *self.elem(2, 3));
let m0 = Mat3::new(self.elem(1, 1).clone(), self.elem(2, 1).clone(), self.elem(3, 1).clone(),
self.elem(1, 2).clone(), self.elem(2, 2).clone(), self.elem(3, 2).clone(),
self.elem(1, 3).clone(), self.elem(2, 3).clone(), self.elem(3, 3).clone());
let m1 = Mat3::new(self.elem(0, 1).clone(), self.elem(2, 1).clone(), self.elem(3, 1).clone(),
self.elem(0, 2).clone(), self.elem(2, 2).clone(), self.elem(3, 2).clone(),
self.elem(0, 3).clone(), self.elem(2, 3).clone(), self.elem(3, 3).clone());
let m2 = Mat3::new(self.elem(0, 1).clone(), self.elem(1, 1).clone(), self.elem(3, 1).clone(),
self.elem(0, 2).clone(), self.elem(1, 2).clone(), self.elem(3, 2).clone(),
self.elem(0, 3).clone(), self.elem(1, 3).clone(), self.elem(3, 3).clone());
let m3 = Mat3::new(self.elem(0, 1).clone(), self.elem(1, 1).clone(), self.elem(2, 1).clone(),
self.elem(0, 2).clone(), self.elem(1, 2).clone(), self.elem(2, 2).clone(),
self.elem(0, 3).clone(), self.elem(1, 3).clone(), self.elem(2, 3).clone());
self.elem(0, 0) * m0.determinant() -
self.elem(1, 0) * m1.determinant() +
@ -320,7 +320,7 @@ macro_rules! mat_trace(
macro_rules! impl_mat_approx_numeric(
($Mat:ident) => (
impl<T:Copy + Real + ApproxEq<T>> $Mat<T> {
impl<T:Clone + Real + ApproxEq<T>> $Mat<T> {
#[inline]
pub fn inverse(&self) -> Option<$Mat<T>> {
mat_inverse!($Mat)
@ -374,9 +374,9 @@ macro_rules! mat_inverse(
if d.approx_eq(&zero!(T)) {
None
} else {
Some(Mat3::from_cols(self.col(1).cross(self.col(2)).div_t(copy d),
self.col(2).cross(self.col(0)).div_t(copy d),
self.col(0).cross(self.col(1)).div_t(copy d)).transpose())
Some(Mat3::from_cols(self.col(1).cross(self.col(2)).div_t(d.clone()),
self.col(2).cross(self.col(0)).div_t(d.clone()),
self.col(0).cross(self.col(1)).div_t(d.clone())).transpose())
}
});
(Mat4) => ({
@ -390,7 +390,7 @@ macro_rules! mat_inverse(
// So take this matrix, A, augmented with the identity
// and essentially reduce [A|I]
let mut A = copy *self;
let mut A = self.clone();
let mut I = Mat4::identity::<T>();
for uint::range(0, 4) |j| {
@ -408,16 +408,16 @@ macro_rules! mat_inverse(
I.swap_cols(i1, j);
// Scale col j to have a unit diagonal
let ajj = copy *A.elem(j, j);
I.col_mut(j).div_self_t(copy ajj);
A.col_mut(j).div_self_t(copy ajj);
let ajj = A.elem(j, j).clone();
I.col_mut(j).div_self_t(ajj.clone());
A.col_mut(j).div_self_t(ajj.clone());
// Eliminate off-diagonal elems in col j of A,
// doing identical ops to I
for uint::range(0, 4) |i| {
if i != j {
let ij_mul_aij = I.col(j).mul_t(copy *A.elem(i, j));
let aj_mul_aij = A.col(j).mul_t(copy *A.elem(i, j));
let ij_mul_aij = I.col(j).mul_t(A.elem(i, j).clone());
let aj_mul_aij = A.col(j).mul_t(A.elem(i, j).clone());
I.col_mut(i).sub_self_v(&ij_mul_aij);
A.col_mut(i).sub_self_v(&aj_mul_aij);
}
@ -498,7 +498,7 @@ macro_rules! mat_is_symmetric(
macro_rules! impl_mat_neg(
($Mat:ident) => (
impl<T:Copy + Num> Neg<$Mat<T>> for $Mat<T> {
impl<T:Clone + Num> Neg<$Mat<T>> for $Mat<T> {
#[inline]
pub fn neg(&self) -> $Mat<T> {
$Mat::from_slice(self.map(|&x| -x))

View file

@ -31,7 +31,7 @@ mod dim_macros;
/// - `n.y`: corresponds to `B` in the plane equation
/// - `n.z`: corresponds to `C` in the plane equation
/// - `d`: the distance value, corresponding to `D` in the plane equation
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Plane<T> {
norm: Vec3<T>,
dist: T,
@ -42,7 +42,7 @@ impl_dimensional_fns!(Plane, T, 4)
impl_swap!(Plane)
impl_approx!(Plane)
impl<T:Copy + Real> Plane<T> {
impl<T:Clone + Real> Plane<T> {
/// # Arguments
///
/// - `a`: the `x` component of the normal
@ -63,7 +63,7 @@ impl<T:Copy + Real> Plane<T> {
/// Construct a plane from the components of a four-dimensional vector
pub fn from_vec4(vec: Vec4<T>) -> Plane<T> {
Plane::from_abcd(copy vec.x, copy vec.y, copy vec.z, copy vec.w)
Plane::from_abcd(vec.x.clone(), vec.y.clone(), vec.z.clone(), vec.w.clone())
}
/// Compute the distance from the plane to the point
@ -87,7 +87,7 @@ impl<T:Copy + Real> Plane<T> {
}
}
impl<T:Copy + Real + ApproxEq<T>> Plane<T> {
impl<T:Clone + Real + ApproxEq<T>> Plane<T> {
/// Constructs a plane that passes through the the three points `a`, `b` and `c`
pub fn from_3p(a: Point3<T>,
b: Point3<T>,
@ -123,10 +123,10 @@ impl<T:Copy + Real + ApproxEq<T>> Plane<T> {
} else {
// The end-point of the ray is at the three-plane intersection between
// `self`, `other`, and a tempory plane positioned at the origin
do Plane::from_nd(copy ray_dir, zero!(T)).intersection_3pl(self, other).map |ray_pos| {
do Plane::from_nd(ray_dir.clone(), zero!(T)).intersection_3pl(self, other).map |ray_pos| {
Ray3 {
pos: copy *ray_pos,
dir: copy ray_dir,
pos: ray_pos.clone(),
dir: ray_dir.clone(),
}
}
}
@ -140,11 +140,13 @@ impl<T:Copy + Real + ApproxEq<T>> Plane<T> {
/// - `None`: No valid intersection was found. The normals of the three
/// planes are probably coplanar.
pub fn intersection_3pl(&self, other_a: &Plane<T>, other_b: &Plane<T>) -> Option<Point3<T>> {
let mx = Mat3::new(copy self.norm.x, copy other_a.norm.x, copy other_b.norm.x,
copy self.norm.y, copy other_a.norm.y, copy other_b.norm.y,
copy self.norm.z, copy other_a.norm.z, copy other_b.norm.z);
let mx = Mat3::new(self.norm.x.clone(), other_a.norm.x.clone(), other_b.norm.x.clone(),
self.norm.y.clone(), other_a.norm.y.clone(), other_b.norm.y.clone(),
self.norm.z.clone(), other_a.norm.z.clone(), other_b.norm.z.clone());
do mx.inverse().map |m| {
Point3(m.mul_v(&Vec3::new(copy self.dist, copy other_a.dist, copy other_b.dist)))
Point3(m.mul_v(&Vec3::new(self.dist.clone(),
other_a.dist.clone(),
other_b.dist.clone())))
}
}
}

View file

@ -25,7 +25,7 @@ pub trait Point<T,V>: Eq + ApproxEq<T> + ToStr {
}
/// A two-dimensional point
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Point2<T>(Vec2<T>);
impl_dimensional!(Point2, T, 2)
@ -38,7 +38,7 @@ impl<T> Point2<T> {
}
}
impl<T:Copy + Real> Point<T,Vec2<T>> for Point2<T> {
impl<T:Clone + Real> Point<T,Vec2<T>> for Point2<T> {
pub fn translate(&self, offset: &Vec2<T>) -> Point2<T> {
Point2(self.add_v(offset))
}
@ -55,7 +55,7 @@ impl<T> ToStr for Point2<T> {
}
/// A three-dimensional point
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Point3<T>(Vec3<T>);
impl_dimensional!(Point3, T, 3)
@ -68,7 +68,7 @@ impl<T> Point3<T> {
}
}
impl<T:Copy + Real> Point<T,Vec3<T>> for Point3<T> {
impl<T:Clone + Real> Point<T,Vec3<T>> for Point3<T> {
pub fn translate(&self, offset: &Vec3<T>) -> Point3<T> {
Point3(self.add_v(offset))
}

View file

@ -27,7 +27,7 @@ mod num_macros;
/// This is the equivalent of the gluPerspective function, the algorithm of which
/// can be found [here](http://www.opengl.org/wiki/GluPerspective_code).
///
pub fn perspective<T:Copy + Real>(fovy: T, aspectRatio: T, near: T, far: T) -> Mat4<T> {
pub fn perspective<T:Clone + Real>(fovy: T, aspectRatio: T, near: T, far: T) -> Mat4<T> {
let ymax = near * (fovy / two!(T)).to_radians().tan();
let xmax = ymax * aspectRatio;
@ -40,7 +40,7 @@ pub fn perspective<T:Copy + Real>(fovy: T, aspectRatio: T, near: T, far: T) -> M
/// This is the equivalent of the now deprecated [glFrustrum]
/// (http://www.opengl.org/sdk/docs/man2/xhtml/glFrustum.xml) function.
///
pub fn frustum<T:Copy + Real>(left: T, right: T, bottom: T, top: T, near: T, far: T) -> Mat4<T> {
pub fn frustum<T:Clone + Real>(left: T, right: T, bottom: T, top: T, near: T, far: T) -> Mat4<T> {
let c0r0 = (two!(T) * near) / (right - left);
let c0r1 = zero!(T);
let c0r2 = zero!(T);
@ -73,7 +73,7 @@ pub fn frustum<T:Copy + Real>(left: T, right: T, bottom: T, top: T, near: T, far
/// This is the equivalent of the now deprecated [glOrtho]
/// (http://www.opengl.org/sdk/docs/man2/xhtml/glOrtho.xml) function.
///
pub fn ortho<T:Copy + Real>(left: T, right: T, bottom: T, top: T, near: T, far: T) -> Mat4<T> {
pub fn ortho<T:Clone + Real>(left: T, right: T, bottom: T, top: T, near: T, far: T) -> Mat4<T> {
let c0r0 = two!(T) / (right - left);
let c0r1 = zero!(T);
let c0r2 = zero!(T);
@ -101,13 +101,13 @@ pub fn ortho<T:Copy + Real>(left: T, right: T, bottom: T, top: T, near: T, far:
}
pub trait Projection<T> {
pub fn if_valid<U:Copy>(&self, f: &fn() -> U) -> Result<U, ~str>;
pub fn if_valid<U:Clone>(&self, f: &fn() -> U) -> Result<U, ~str>;
pub fn to_mat4(&self) -> Result<Mat4<T>, ~str>;
pub fn to_frustum(&self) -> Result<Frustum<T>, ~str>;
}
/// A symmetrical perspective projection based on a field-of-view angle
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct PerspectiveFOV<T> {
fovy: T, //radians
aspect: T,
@ -115,7 +115,7 @@ pub struct PerspectiveFOV<T> {
far: T,
}
impl<T:Copy + Real> PerspectiveFOV<T> {
impl<T:Clone + Real> PerspectiveFOV<T> {
pub fn to_perspective(&self) -> Result<Perspective<T>, ~str> {
do self.if_valid {
let angle = self.fovy / two!(T);
@ -127,15 +127,15 @@ impl<T:Copy + Real> PerspectiveFOV<T> {
right: xmax,
bottom: -ymax,
top: ymax,
near: copy self.near,
far: copy self.far,
near: self.near.clone(),
far: self.far.clone(),
}
}
}
}
impl<T:Copy + Real> Projection<T> for PerspectiveFOV<T> {
pub fn if_valid<U:Copy>(&self, f: &fn() -> U) -> Result<U, ~str> {
impl<T:Clone + Real> Projection<T> for PerspectiveFOV<T> {
pub fn if_valid<U:Clone>(&self, f: &fn() -> U) -> Result<U, ~str> {
let frac_pi_2: T = Real::frac_pi_2();
cond! (
(self.fovy < zero!(T)) { Err(fmt!("The vertical field of view cannot be below zero, found: %?", self.fovy)) }
@ -158,7 +158,7 @@ impl<T:Copy + Real> Projection<T> for PerspectiveFOV<T> {
}
/// A perspective projection with arbitrary left/right/bottom/top distances
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Perspective<T> {
left: T,
right: T,
@ -168,8 +168,8 @@ pub struct Perspective<T> {
far: T,
}
impl<T:Copy + Real> Projection<T> for Perspective<T> {
pub fn if_valid<U:Copy>(&self, f: &fn() -> U) -> Result<U, ~str> {
impl<T:Clone + Real> Projection<T> for Perspective<T> {
pub fn if_valid<U:Clone>(&self, f: &fn() -> U) -> Result<U, ~str> {
cond! (
(self.left > self.right) { Err(fmt!("`left` cannot be greater than `right`, found: left: %? right: %?", self.left, self.right)) }
(self.bottom > self.top) { Err(fmt!("`bottom` cannot be greater than `top`, found: bottom: %? top: %?", self.bottom, self.top)) }
@ -256,15 +256,15 @@ impl<T:Copy + Real> Projection<T> for Perspective<T> {
right: Plane::from_abcd(theta_r.cos(), zero!(T), theta_r.sin(), zero!(T)),
bottom: Plane::from_abcd(zero!(T), theta_b.cos(), theta_b.sin(), zero!(T)),
top: Plane::from_abcd(zero!(T), theta_t.cos(), theta_t.sin(), zero!(T)),
near: Plane::from_abcd(zero!(T), zero!(T), -one!(T), copy -self.near),
far: Plane::from_abcd(zero!(T), zero!(T), one!(T), copy self.far),
near: Plane::from_abcd(zero!(T), zero!(T), -one!(T), -self.near.clone()),
far: Plane::from_abcd(zero!(T), zero!(T), one!(T), self.far.clone()),
}
}
}
}
/// An orthographic projection with arbitrary left/right/bottom/top distances
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Ortho<T> {
left: T,
right: T,
@ -274,8 +274,8 @@ pub struct Ortho<T> {
far: T,
}
impl<T:Copy + Real> Projection<T> for Ortho<T> {
pub fn if_valid<U:Copy>(&self, f: &fn() -> U) -> Result<U, ~str> {
impl<T:Clone + Real> Projection<T> for Ortho<T> {
pub fn if_valid<U:Clone>(&self, f: &fn() -> U) -> Result<U, ~str> {
cond! (
(self.left > self.right) { Err(fmt!("`left` cannot be greater than `right`, found: left: %? right: %?", self.left, self.right)) }
(self.bottom > self.top) { Err(fmt!("`bottom` cannot be greater than `top`, found: bottom: %? top: %?", self.bottom, self.top)) }
@ -316,12 +316,12 @@ impl<T:Copy + Real> Projection<T> for Ortho<T> {
pub fn to_frustum(&self) -> Result<Frustum<T>, ~str> {
do self.if_valid {
Frustum {
left: Plane::from_abcd(one!(T), zero!(T), zero!(T), copy self.left),
right: Plane::from_abcd(-one!(T), zero!(T), zero!(T), copy self.right),
bottom: Plane::from_abcd(zero!(T), one!(T), zero!(T), copy self.bottom),
top: Plane::from_abcd(zero!(T), -one!(T), zero!(T), copy self.top),
near: Plane::from_abcd(zero!(T), zero!(T), -one!(T), copy self.near),
far: Plane::from_abcd(zero!(T), zero!(T), one!(T),copy self.far),
left: Plane::from_abcd(one!(T), zero!(T), zero!(T), self.left.clone()),
right: Plane::from_abcd(-one!(T), zero!(T), zero!(T), self.right.clone()),
bottom: Plane::from_abcd(zero!(T), one!(T), zero!(T), self.bottom.clone()),
top: Plane::from_abcd(zero!(T), -one!(T), zero!(T), self.top.clone()),
near: Plane::from_abcd(zero!(T), zero!(T), -one!(T), self.near.clone()),
far: Plane::from_abcd(zero!(T), zero!(T), one!(T),self.far.clone()),
}
}
}

View file

@ -33,7 +33,7 @@ pub type Quatf32 = Quat<f32>;
pub type Quatf64 = Quat<f64>;
/// A quaternion in scalar/vector form
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Quat<T> { s: T, v: Vec3<T> }
impl_dimensional!(Quat, T, 4)
@ -72,7 +72,7 @@ impl<T> Quat<T> {
}
}
impl<T:Copy + Real> Quat<T> {
impl<T:Clone + Real> Quat<T> {
/// The multiplicative identity, ie: `q = 1 + 0i + 0j + 0i`
#[inline]
pub fn identity() -> Quat<T> {
@ -136,7 +136,7 @@ impl<T:Copy + Real> Quat<T> {
/// The result of multiplying the quaternion by a vector
#[inline]
pub fn mul_v(&self, vec: &Vec3<T>) -> Vec3<T> {
let tmp = self.v.cross(vec).add_v(&vec.mul_t(copy self.s));
let tmp = self.v.cross(vec).add_v(&vec.mul_t(self.s.clone()));
self.v.cross(&tmp).mul_t(two!(T)).add_v(vec)
}
@ -175,7 +175,7 @@ impl<T:Copy + Real> Quat<T> {
/// The conjugate of the quaternion
#[inline]
pub fn conjugate(&self) -> Quat<T> {
Quat::from_sv(copy self.s, copy -self.v)
Quat::from_sv(self.s.clone(), -self.v.clone())
}
/// The multiplicative inverse of the quaternion
@ -220,7 +220,7 @@ impl<T:Copy + Real> Quat<T> {
}
}
impl<T:Copy + Num> ToMat3<T> for Quat<T> {
impl<T:Clone + Num> ToMat3<T> for Quat<T> {
/// Convert the quaternion to a 3 x 3 rotation matrix
pub fn to_mat3(&self) -> Mat3<T> {
let x2 = self.v.x + self.v.x;
@ -247,14 +247,14 @@ impl<T:Copy + Num> ToMat3<T> for Quat<T> {
}
}
impl<T:Copy + Float> Neg<Quat<T>> for Quat<T> {
impl<T:Clone + Float> Neg<Quat<T>> for Quat<T> {
#[inline]
pub fn neg(&self) -> Quat<T> {
Quat::from_slice(self.map(|&x| -x))
}
}
impl<T:Copy + Float> Quat<T> {
impl<T:Clone + Float> Quat<T> {
#[inline]
pub fn look_at(dir: &Vec3<T>, up: &Vec3<T>) -> Quat<T> {
Mat3::look_at(dir, up).to_quat()

View file

@ -22,13 +22,13 @@ use point::Point3;
///
/// - `pos`: the endpoint of the ray
/// - `dir`: the direction vector
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Ray3<T> {
pos: Point3<T>,
dir: Vec3<T>,
}
impl<T:Copy + Eq + ApproxEq<T>> ApproxEq<T> for Ray3<T> {
impl<T:Clone + Eq + ApproxEq<T>> ApproxEq<T> for Ray3<T> {
#[inline]
pub fn approx_epsilon() -> T {
ApproxEq::approx_epsilon::<T,T>()

View file

@ -19,7 +19,7 @@ mod num_macros;
mod dim_macros;
mod vec_macros;
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Vec2<T> { x: T, y: T }
// GLSL-style type aliases
@ -51,7 +51,7 @@ impl_swap!(Vec2)
impl_approx!(Vec2)
impl_vec!(Vec2 { x, y })
impl_vec_copyable!(Vec2)
impl_vec_clonable!(Vec2)
impl_vec_numeric!(Vec2)
impl_vec_neg!(Vec2)
impl_vec_euclidean!(Vec2)
@ -60,7 +60,7 @@ impl_vec_eq!(Vec2)
impl_vec_bool!(Vec2)
impl_vec_not!(Vec2)
impl<T:Copy + Num> Vec2<T> {
impl<T:Clone + Num> Vec2<T> {
#[inline] pub fn unit_x() -> Vec2<T> { Vec2::new(one!(T), zero!(T)) }
#[inline] pub fn unit_y() -> Vec2<T> { Vec2::new(zero!(T), one!(T)) }
@ -204,7 +204,7 @@ mod vec2_tests {
}
}
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Vec3<T> { x: T, y: T, z: T }
// GLSL-style type aliases
@ -236,7 +236,7 @@ impl_swap!(Vec3)
impl_approx!(Vec3)
impl_vec!(Vec3 { x, y, z })
impl_vec_copyable!(Vec3)
impl_vec_clonable!(Vec3)
impl_vec_numeric!(Vec3)
impl_vec_neg!(Vec3)
impl_vec_euclidean!(Vec3)
@ -245,7 +245,7 @@ impl_vec_eq!(Vec3)
impl_vec_bool!(Vec3)
impl_vec_not!(Vec3)
impl<T:Copy + Num> Vec3<T> {
impl<T:Clone + Num> Vec3<T> {
#[inline] pub fn unit_x() -> Vec3<T> { Vec3::new(one!(T), zero!(T), zero!(T)) }
#[inline] pub fn unit_y() -> Vec3<T> { Vec3::new(zero!(T), one!(T), zero!(T)) }
#[inline] pub fn unit_z() -> Vec3<T> { Vec3::new(zero!(T), zero!(T), one!(T)) }
@ -411,7 +411,7 @@ mod vec3_tests{
}
}
#[deriving(Eq)]
#[deriving(Clone, Eq)]
pub struct Vec4<T> { x: T, y: T, z: T, w: T }
// GLSL-style type aliases
@ -443,7 +443,7 @@ impl_approx!(Vec4)
impl_swap!(Vec4)
impl_vec!(Vec4 { x, y, z, w })
impl_vec_copyable!(Vec4)
impl_vec_clonable!(Vec4)
impl_vec_numeric!(Vec4)
impl_vec_neg!(Vec4)
impl_vec_euclidean!(Vec4)
@ -452,7 +452,7 @@ impl_vec_eq!(Vec4)
impl_vec_bool!(Vec4)
impl_vec_not!(Vec4)
impl<T:Copy + Num> Vec4<T> {
impl<T:Clone + Num> Vec4<T> {
#[inline] pub fn unit_x() -> Vec4<T> { Vec4::new(one!(T), zero!(T), zero!(T), zero!(T)) }
#[inline] pub fn unit_y() -> Vec4<T> { Vec4::new(zero!(T), one!(T), zero!(T), zero!(T)) }
#[inline] pub fn unit_z() -> Vec4<T> { Vec4::new(zero!(T), zero!(T), one!(T), zero!(T)) }

View file

@ -26,9 +26,9 @@ macro_rules! impl_vec(
)
)
macro_rules! impl_vec_copyable(
macro_rules! impl_vec_clonable(
($Vec:ident) => (
impl<T:Copy> $Vec<T> {
impl<T:Clone> $Vec<T> {
#[inline]
pub fn from_value(value: T) -> $Vec<T> {
vec_from_value!($Vec)
@ -38,14 +38,14 @@ macro_rules! impl_vec_copyable(
)
macro_rules! vec_from_value(
(Vec2) => (Vec2::new(copy value, copy value));
(Vec3) => (Vec3::new(copy value, copy value, copy value));
(Vec4) => (Vec4::new(copy value, copy value, copy value, copy value));
(Vec2) => (Vec2::new(value.clone(), value.clone()));
(Vec3) => (Vec3::new(value.clone(), value.clone(), value.clone()));
(Vec4) => (Vec4::new(value.clone(), value.clone(), value.clone(), value.clone()));
)
macro_rules! impl_vec_numeric(
($Vec:ident) => (
impl<T:Copy + Num> $Vec<T> {
impl<T:Clone + Num> $Vec<T> {
#[inline] pub fn identity() -> $Vec<T> { $Vec::from_value(one!(T)) }
#[inline] pub fn zero() -> $Vec<T> { $Vec::from_value(zero!(T)) }
@ -62,11 +62,11 @@ macro_rules! impl_vec_numeric(
#[inline] pub fn rem_v(&self, other: &$Vec<T>) -> $Vec<T> { $Vec::from_slice(self.zip(other, |&a, &b| a % b)) }
#[inline] pub fn neg_self(&mut self) { self.map_mut(|x| *x = -*x) }
#[inline] pub fn add_self_t(&mut self, value: T) { self.map_mut(|x| *x += copy value) }
#[inline] pub fn sub_self_t(&mut self, value: T) { self.map_mut(|x| *x -= copy value) }
#[inline] pub fn mul_self_t(&mut self, value: T) { self.map_mut(|x| *x *= copy value) }
#[inline] pub fn div_self_t(&mut self, value: T) { self.map_mut(|x| *x /= copy value) }
#[inline] pub fn rem_self_t(&mut self, value: T) { self.map_mut(|x| *x %= copy value) }
#[inline] pub fn add_self_t(&mut self, value: T) { self.map_mut(|x| *x += value.clone()) }
#[inline] pub fn sub_self_t(&mut self, value: T) { self.map_mut(|x| *x -= value.clone()) }
#[inline] pub fn mul_self_t(&mut self, value: T) { self.map_mut(|x| *x *= value.clone()) }
#[inline] pub fn div_self_t(&mut self, value: T) { self.map_mut(|x| *x /= value.clone()) }
#[inline] pub fn rem_self_t(&mut self, value: T) { self.map_mut(|x| *x %= value.clone()) }
#[inline] pub fn add_self_v(&mut self, other: &$Vec<T>) { self.zip_mut(other, |a, &b| *a += b) }
#[inline] pub fn sub_self_v(&mut self, other: &$Vec<T>) { self.zip_mut(other, |a, &b| *a -= b) }
@ -99,7 +99,7 @@ macro_rules! vec_dot(
macro_rules! impl_vec_neg(
($Vec:ident) => (
impl<T:Copy + Num> Neg<$Vec<T>> for $Vec<T> {
impl<T:Clone + Num> Neg<$Vec<T>> for $Vec<T> {
#[inline]
pub fn neg(&self) -> $Vec<T> {
$Vec::from_slice(self.map(|&x| -x))
@ -110,7 +110,7 @@ macro_rules! impl_vec_neg(
macro_rules! impl_vec_euclidean(
($Vec:ident) => (
impl<T:Copy + Real> $Vec<T> {
impl<T:Clone + Real> $Vec<T> {
#[inline]
pub fn length2(&self) -> T {
self.dot(self)
@ -179,7 +179,7 @@ macro_rules! vec_angle(
macro_rules! impl_vec_ord(
($Vec:ident) => (
impl<T:Copy + Ord> $Vec<T> {
impl<T:Clone + Ord> $Vec<T> {
#[inline] pub fn lt_t(&self, value: T) -> $Vec<bool> { $Vec::from_slice(self.map(|&x| x < value)) }
#[inline] pub fn le_t(&self, value: T) -> $Vec<bool> { $Vec::from_slice(self.map(|&x| x <= value)) }
#[inline] pub fn ge_t(&self, value: T) -> $Vec<bool> { $Vec::from_slice(self.map(|&x| x >= value)) }
@ -195,7 +195,7 @@ macro_rules! impl_vec_ord(
macro_rules! impl_vec_eq(
($Vec:ident) => (
impl<T:Copy + Eq> $Vec<T> {
impl<T:Clone + Eq> $Vec<T> {
#[inline] pub fn eq_t(&self, value: T) -> $Vec<bool> { $Vec::from_slice(self.map(|&x| x == value)) }
#[inline] pub fn ne_t(&self, value: T) -> $Vec<bool> { $Vec::from_slice(self.map(|&x| x != value)) }
@ -236,7 +236,7 @@ macro_rules! vec_all(
macro_rules! impl_vec_not(
($Vec:ident) => (
impl<T:Copy + Not<T>> Not<$Vec<T>> for $Vec<T> {
impl<T:Clone + Not<T>> Not<$Vec<T>> for $Vec<T> {
pub fn not(&self) -> $Vec<T> {
$Vec::from_slice(self.map(|&x| !x))
}