Moved some files + use rustdoc_ng to generate the documenatiton.

Trait failes are merged in three files:
    * operations.rs - for low-level matrix/vector operations
    * geometry.rs   - for operations with a clear, broadly known geometric meaning.
    * structure.rs  - for operations to access/alter the object inner structures.

Specialisations are moved to the `spec` folder.
This commit is contained in:
Sébastien Crozet 2013-09-22 10:58:21 +02:00
parent 9a9de20b8a
commit 7de844b46a
43 changed files with 577 additions and 808 deletions

View File

@ -16,7 +16,7 @@ bench:
doc:
mkdir -p $(nalgebra_doc_path)
rust doc src/lib.rs --output-dir $(nalgebra_doc_path)
rustdoc_ng html src/lib.rs
distcheck:
rm -rf $(tmp)

View File

@ -1,156 +0,0 @@
body {
padding: 1em 6em;
margin: 0;
margin-bottom: 4em;
font-family: "Helvetica Neue", Helvetica, sans-serif;
font-size: 12pt;
background-color: white;
color: black;
line-height: 1.6em;
min-width: 45em;
max-width: 60em;
}
h1 {
font-size: 24pt;
margin-top: 1.6em;
padding-left: 0.4em;
line-height: 1.6em;
background-color:#FFF2CE;
border-radius: 0.2em;
}
h2 {
font-size: 16pt;
margin-top: 1.6em;
padding: 0.2em 0.5em;
background-color:#FFF2CE;
border-radius: 0.4em;
}
h2 code {
color: #097334;
font-size: 16pt;
}
h3 {
font-size: 14pt;
color: black;
background-color:#D9E7FF;
border-radius: 0.4em;
padding: 0.2em 0.5em;
}
h3 code {
color: #541800;
font-size: 14pt;
font-style: italic;
}
h4 {
font-size: 11pt;
margin-top: 0em;
margin-bottom: 0em;
}
code {
font-size: 11pt;
}
pre {
margin-left: 1.1em;
padding: .4em .4em .4em .8em;
font-size: 10pt;
background-color: #F5F5F5;
border-radius: 0.5em;
border: 1px solid rgba(0, 0, 0, 0.15);
}
pre.rust {
background-color: #F3F6FF;
}
a, a:visited, a:link {
text-decoration: none;
color: rgb(0, 105, 214);
}
h1 a:link, h1 a:visited, h2 a:link, h2 a:visited,
h3 a:link, h3 a:visited { color: black; }
/* Code highlighting */
.cm-s-default span.cm-keyword {color: #708;}
.cm-s-default span.cm-atom {color: #219;}
.cm-s-default span.cm-number {color: #164;}
.cm-s-default span.cm-def {color: #00f;}
.cm-s-default span.cm-variable {color: black;}
.cm-s-default span.cm-variable-2 {color: #05a;}
.cm-s-default span.cm-variable-3 {color: #085;}
.cm-s-default span.cm-property {color: black;}
.cm-s-default span.cm-operator {color: black;}
.cm-s-default span.cm-comment {color: #a50;}
.cm-s-default span.cm-string {color: #a11;}
.cm-s-default span.cm-string-2 {color: #f50;}
.cm-s-default span.cm-meta {color: #555;}
.cm-s-default span.cm-error {color: #f00;}
.cm-s-default span.cm-qualifier {color: #555;}
.cm-s-default span.cm-builtin {color: #30a;}
.cm-s-default span.cm-bracket {color: #cc7;}
.cm-s-default span.cm-tag {color: #170;}
.cm-s-default span.cm-attribute {color: #00c;}
#versioninfo {
position: fixed;
bottom: 0px;
right: 0px;
background-color: white;
padding: 0.5em;
}
a.lessimportant {
color: gray;
font-size: 60%;
}
blockquote {
color: black;
border-left: solid 1px silver;
margin: 1em;
padding: 0.5em 1em 0.5em 1em;
}
/* Make the table under the tutorial's 'Types' section look nicer */
table {
border-top: 1px solid silver;
border-bottom: 1px solid silver;
padding: 0.8em;
font-size: smaller;
}
/* Also for the benefit of the type table */
td {
padding-right: 1em;
}
/* Only display one level of hierarchy in the TOC */
#TOC ul ul {
display: none;
}
#TOC ul {
list-style: none;
padding-left: 0px;
}
/* Adjust list alignment so rustdoc indexes don't align with blockquotes */
div.index ul {
padding-left: 1em;
}
ul {
margin-top: 0em
}
div.section.level3 {
margin-left: 1.0em;
}

View File

@ -1,19 +1,10 @@
use std::num::{One, Zero};
use std::rand::{Rand, Rng, RngUtil};
use std::cmp::ApproxEq;
use traits::cross::Cross;
use traits::dim::Dim;
use traits::inv::Inv;
use traits::row::Row;
use traits::col::Col;
use traits::transpose::Transpose;
use traits::absolute::Absolute;
use traits::rotation::{Rotation, Rotate, RotationMatrix};
use traits::transformation::{Transform}; // FIXME: implement Transformation and Transformable
use traits::homogeneous::ToHomogeneous;
use traits::indexable::Indexable;
use traits::norm::Norm;
use traits::comp::absolute_rotate::AbsoluteRotate;
use traits::geometry::{Cross, Rotation, Rotate, RotationMatrix, AbsoluteRotate, Transform,
ToHomogeneous, Norm};
use traits::structure::{Dim, Row, Col, Indexable};
use traits::operations::{Inv, Transpose, Absolute};
use vec::{Vec1, Vec2, Vec3, Vec2MulRhs, Vec3MulRhs};
use mat::{Mat2, Mat3};

View File

@ -1,18 +1,11 @@
use std::num::{One, Zero};
use std::rand::{Rand, Rng, RngUtil};
use std::cmp::ApproxEq;
use traits::dim::Dim;
use traits::absolute::Absolute;
use traits::mat::Mat;
use traits::inv::Inv;
use traits::rotation::{Rotation, Rotate, RotationMatrix};
use traits::translation::{Translation, Translate};
use Ts = traits::transformation::Transform;
use traits::transformation::{Transformation};
use traits::rlmul::RMul;
use traits::homogeneous::{ToHomogeneous, FromHomogeneous};
use traits::col::Col;
use traits::comp::absolute_rotate::AbsoluteRotate;
use traits::structure::{Dim, Mat, Col};
use traits::operations::{Absolute, Inv, RMul};
use traits::geometry::{Rotation, Rotate, RotationMatrix, Translation, Translate, Transformation,
ToHomogeneous, FromHomogeneous, AbsoluteRotate};
use Ts = traits::geometry::Transform;
use adaptors::rotmat::Rotmat;
use vec::{Vec2, Vec3, Vec2MulRhs, Vec3MulRhs};
use mat::Mat3;

View File

@ -1,3 +1,5 @@
//! Matrix with dimensions unknown at compile-time.
use std::rand::Rand;
use std::rand;
use std::num::{One, Zero};
@ -5,8 +7,7 @@ use std::vec;
use std::cmp::ApproxEq;
use std::util;
use dvec::{DVec, DVecMulRhs};
use traits::inv::Inv;
use traits::transpose::Transpose;
use traits::operations::{Inv, Transpose};
/// Matrix with dimensions unknown at compile-time.
#[deriving(Eq, ToStr, Clone)]

View File

@ -1,3 +1,5 @@
//! Vector with dimensions unknown at compile-time.
#[doc(hidden)]; // we hide doc to not have to document the $trhs double dispatch trait.
use std::num::{Zero, One, Algebraic};
@ -7,10 +9,8 @@ use std::vec;
use std::vec::{VecIterator, VecMutIterator};
use std::cmp::ApproxEq;
use std::iter::FromIterator;
use traits::dot::Dot;
use traits::norm::Norm;
use traits::iterable::{Iterable, IterableMut};
use traits::translation::Translation;
use traits::geometry::{Dot, Norm, Translation};
use traits::structure::{Iterable, IterableMut};
mod metal;

View File

@ -6,7 +6,7 @@
#[link(name = "nalgebra"
, vers = "0.1"
, author = "Sébastien Crozet"
, uuid = "1E96070F-4778-4EC1-B080-BF69F7048216")];
, uuid = "1e96070f-4778-4ec1-b080-bf69f7048216")];
#[crate_type = "lib"];
#[deny(non_camel_case_types)];
#[deny(non_uppercase_statics)];
@ -20,14 +20,7 @@ pub mod dmat;
pub mod dvec;
pub mod vec;
pub mod mat;
// specialization for some 1d, 2d and 3d operations
mod mat_spec;
mod vec_spec;
mod vec0_spec;
mod identity_spec;
// mod lower_triangular;
// mod chol;
pub mod types;
/// Wrappers around raw matrices to restrict their behaviour.
pub mod adaptors {
@ -35,51 +28,40 @@ pub mod adaptors {
pub mod transform;
}
pub mod types;
/// Traits implemented by matrices and vectors.
///
/// They should not be imported from here since all of them are re-exported by the `mat` or the
/// `vec` module.
pub mod traits {
pub mod vector;
pub mod sample;
pub mod indexable;
pub mod row;
pub mod iterable;
pub mod outer;
pub mod cross;
pub mod inv;
pub mod transpose;
pub mod dim;
pub mod basis;
pub mod rotation;
pub mod translation;
pub mod transformation;
pub mod rlmul;
pub mod scalar_op;
pub mod homogeneous;
pub mod vec_cast;
pub mod mat_cast;
pub mod norm;
pub mod dot;
pub mod mat;
pub mod absolute;
pub mod col;
/// Traits of operations having a well-known or explicit geometric meaning.
pub mod geometry;
/// Unusual traits which are composition of other primitive traits.
/// Those are mainly shortcuts to make some operation easier to use or faster.
/// Mathematics purists should really not go in there!
pub mod comp {
pub mod rotation_with_translation;
pub mod absolute_rotate;
}
/// Traits giving structural informations on linear algebra objects or the space they live in.
pub mod structure;
/// Low level operations on vectors and matrices.
pub mod operations;
}
// specialization for some 1d, 2d and 3d operations
#[doc(hidden)]
mod spec {
mod identity;
mod mat;
mod vec0;
mod vec;
}
// mod lower_triangular;
// mod chol;
#[cfg(test)]
mod tests {
mod mat;
mod vec;
mod mat;
}
#[cfg(test)]
mod bench {
mod mat;
mod vec;
mod mat;
}

View File

@ -1,3 +1,5 @@
//! Matrices with dimensions known at compile-time.
#[allow(missing_doc)]; // we allow missing to avoid having to document the mij components.
use std::cast;
@ -7,24 +9,11 @@ use std::vec::{VecIterator, VecMutIterator};
use vec::*;
// traits
pub use traits::mat::Mat;
pub use traits::absolute::Absolute;
pub use traits::dim::Dim;
pub use traits::indexable::Indexable;
pub use traits::iterable::{Iterable, IterableMut};
pub use traits::scalar_op::{ScalarSub, ScalarAdd};
pub use traits::mat_cast::MatCast;
pub use traits::inv::Inv;
pub use traits::rlmul::RMul;
pub use traits::rotation::{Rotation, RotationMatrix, Rotate};
pub use traits::transformation::{Transformation, Transform};
pub use traits::translation::{Translation, Translate};
pub use traits::transpose::{Transpose};
pub use traits::homogeneous::{ToHomogeneous, FromHomogeneous};
pub use traits::row::Row;
pub use traits::col::Col;
pub use traits::comp::rotation_with_translation::RotationWithTranslation;
pub use traits::comp::absolute_rotate::AbsoluteRotate;
pub use traits::structure::{Mat, Dim, Indexable, Iterable, IterableMut, MatCast, Row, Col};
pub use traits::operations::{Absolute, ScalarSub, ScalarAdd, Inv, RMul, Transpose};
pub use traits::geometry::{Rotation, RotationMatrix, Rotate, Transformation, Transform,
Translation, Translate, ToHomogeneous, FromHomogeneous,
RotationWithTranslation, AbsoluteRotate};
// structs
pub use dmat::DMat;

View File

@ -1,10 +1,7 @@
use std::num::{One, Zero};
use mat;
use traits::inv::Inv;
use traits::transpose::Transpose;
use traits::translation::{Translation, Translate};
use traits::rotation::{Rotation, Rotate};
use traits::transformation::{Transformation, Transform};
use traits::operations::{Inv, Transpose};
use traits::geometry::{Translation, Translate, Rotation, Rotate, Transformation, Transform};
impl One for mat::Identity {
#[inline]

View File

@ -3,13 +3,8 @@ use std::num::{Zero, One, Algebraic, Bounded};
use std::vec::{VecIterator, VecMutIterator};
use std::iter::{Iterator, FromIterator};
use std::cmp::ApproxEq;
use traits::iterable::{Iterable, IterableMut};
use traits::basis::Basis;
use traits::dim::Dim;
use traits::translation::Translation;
use traits::indexable::Indexable;
use traits::dot::Dot;
use traits::norm::Norm;
use traits::structure::{Iterable, IterableMut, Indexable, Basis, Dim};
use traits::geometry::{Translation, Dot, Norm};
use vec;
impl<N> vec::Vec0<N> {

View File

@ -1,7 +0,0 @@
/// Trait of objects having an absolute value.
/// This is useful of the object and the absolute value do not have the same type.
pub trait Absolute<A> {
/// Compute some absolute representation of this object.
/// Typically, this will make all component of a matrix or vector positive.
fn absolute(&self) -> A;
}

View File

@ -1,35 +0,0 @@
// FIXME: return an iterator instead
/// Traits of objecs which can form a basis.
pub trait Basis {
/// Iterate through the canonical basis of the space in which this object lives.
fn canonical_basis(&fn(Self) -> bool);
/// Iterate through a basis of the subspace orthogonal to `self`.
fn orthonormal_subspace_basis(&self, &fn(Self) -> bool);
/// Creates the canonical basis of the space in which this object lives.
fn canonical_basis_list() -> ~[Self] {
let mut res = ~[];
do Basis::canonical_basis |elem| {
res.push(elem);
true
}
res
}
/// Creates a basis of the subspace orthogonal to `self`.
fn orthonormal_subspace_basis_list(&self) -> ~[Self] {
let mut res = ~[];
do self.orthonormal_subspace_basis |elem| {
res.push(elem);
true
}
res
}
}

View File

@ -1,9 +0,0 @@
/// Traits to access columns of a matrix or vector.
pub trait Col<C> {
/// The number of columun of this matrix or vector.
fn num_cols(&self) -> uint;
/// Reads the `i`-th column of `self`.
fn col(&self, i: uint) -> C;
/// Writes the `i`-th column of `self`.
fn set_col(&mut self, i: uint, C);
}

View File

@ -1,16 +0,0 @@
/// Trait of matrices having the following operation:
///
/// self.absolute_rotate(v) = self.rotation_matrix().absolute().rmul(v)
///
/// The operation is accessible using the `RotationMatrix`, `Absolute`, and `RMul` traits, but
/// doing so is not easy in generic code as it can be a cause of type over-parametrization.
///
/// # Known use case:
/// * to compute efficiently the AABB of a rotated AABB.
pub trait AbsoluteRotate<V> {
/// This is the same as:
///
/// self.absolute_rotate(v) = self.rotation_matrix().absolute().rmul(v)
fn absolute_rotate(&self, &V) -> V;
}

View File

@ -1,70 +0,0 @@
use traits::rotation::Rotation;
use traits::translation::Translation;
// NOTE: we cannot call this an Isometry since an isometry really does not need to have a rotation
// nor a translation (this can be a reflexion).
/// Utilities to make rotations with regard to a point different than the origin.
/// All those operations are the composition of rotations and translations.
/// This could be implemented in term of the `Rotation` and `Translation` traits, but having those
/// here make it easier to use.
///
/// # Known use case:
/// * to change the center of a rotation.
pub trait RotationWithTranslation<LV: Neg<LV>, AV>: Rotation<AV> + Translation<LV> {
/**
* Applies a rotation centered on a specific point.
*
* - `m`: the object to be rotated.
* - `ammount`: the rotation to apply.
* - `point`: the center of rotation.
*/
#[inline]
fn rotated_wrt_point(&self, ammount: &AV, center: &LV) -> Self {
let mut res = self.translated(&-center);
res.rotate_by(ammount);
res.translate_by(center);
res
}
/// Rotates an object using a specific center of rotation.
///
/// # Arguments
/// * `m` - the object to be rotated
/// * `ammount` - the rotation to be applied
/// * `center` - the new center of rotation
#[inline]
fn rotate_wrt_point(&mut self, ammount: &AV, center: &LV) {
self.translate_by(&-center);
self.rotate_by(ammount);
self.translate_by(center);
}
/**
* Applies a rotation centered on the input translation.
*
* # Arguments
* * `m` - the object to be rotated.
* * `ammount` - the rotation to apply.
*/
#[inline]
fn rotated_wrt_center(&self, ammount: &AV) -> Self {
self.rotated_wrt_point(ammount, &self.translation())
}
/**
* Applies a rotation centered on the input translation.
*
* # Arguments
* * `m` - the object to be rotated.
* * `ammount` - the rotation to apply.
*/
#[inline]
fn rotate_wrt_center(&mut self, ammount: &AV) {
let center = self.translation();
self.rotate_wrt_point(ammount, &center)
}
}
impl<LV: Neg<LV>, AV, M: Rotation<AV> + Translation<LV>> RotationWithTranslation<LV, AV> for M;

View File

@ -1,16 +0,0 @@
/**
* Trait of elements having a cross product.
*/
pub trait Cross<V> {
/// Computes the cross product between two elements (usually vectors).
fn cross(&self, other: &Self) -> V;
}
/**
* Trait of elements having a cross product operation which can be expressed as a matrix.
*/
pub trait CrossMatrix<M> {
/// The matrix associated to any cross product with this vector. I.e. `v.cross(anything)` =
/// `v.cross_matrix().rmul(anything)`.
fn cross_matrix(&self) -> M;
}

View File

@ -1,7 +0,0 @@
/**
* Trait of objects having a spacial dimension.
*/
pub trait Dim {
/// The dimension of the object.
fn dim(unused_self: Option<Self>) -> uint;
}

View File

@ -1,17 +0,0 @@
/// Traits of objects having a dot product.
pub trait Dot<N> {
/// Computes the dot (inner) product of two vectors.
#[inline]
fn dot(&self, &Self) -> N;
/**
* Short-cut to compute the projection of a point on a vector, but without
* computing intermediate vectors.
* This must be equivalent to:
*
* (a - b).dot(c)
*
*/
#[inline]
fn sub_dot(&self, b: &Self, c: &Self) -> N;
}

257
src/traits/geometry.rs Normal file
View File

@ -0,0 +1,257 @@
use traits::structure::Mat;
/// Trait of object which represent a translation, and to wich new translation
/// can be appended.
pub trait Translation<V> {
// FIXME: add a "from translation: translantion(V) -> Self ?
/// Gets the translation associated with this object.
fn translation(&self) -> V;
/// Gets the inverse translation associated with this object.
fn inv_translation(&self) -> V;
/// In-place version of `translated`.
fn translate_by(&mut self, &V);
/// Appends a translation.
fn translated(&self, &V) -> Self;
/// Sets the translation.
fn set_translation(&mut self, V);
}
/// Trait of objects able to rotate other objects. This is typically implemented by matrices which
/// rotate vectors.
pub trait Translate<V> {
/// Apply a translation to an object.
fn translate(&self, &V) -> V;
/// Apply an inverse translation to an object.
fn inv_translate(&self, &V) -> V;
}
/// Trait of object which can represent a rotation, and to which new rotations can be appended. A
/// rotation is assumed to be an isometry without translation and without reflexion.
pub trait Rotation<V> {
/// Gets the rotation associated with `self`.
fn rotation(&self) -> V;
/// Gets the inverse rotation associated with `self`.
fn inv_rotation(&self) -> V;
/// In-place version of `rotated`.
fn rotate_by(&mut self, &V);
/// Appends a rotation to `self`.
fn rotated(&self, &V) -> Self;
/// Sets the rotation of `self`.
fn set_rotation(&mut self, V);
}
/// Trait of objects able to rotate other objects.
///
/// This is typically implemented by matrices which rotate vectors.
pub trait Rotate<V> {
/// Applies a rotation to `v`.
fn rotate(&self, v: &V) -> V;
/// Applies an inverse rotation to `v`.
fn inv_rotate(&self, v: &V) -> V;
}
/// Trait of object which represent a transformation, and to which new transformations can
/// be appended.
///
/// A transformation is assumed to be an isometry without reflexion.
pub trait Transformation<M> {
/// Gets the transformation of `self`.
fn transformation(&self) -> M;
/// Gets the inverse transformation of `self`.
fn inv_transformation(&self) -> M;
/// In-place version of `transformed`.
fn transform_by(&mut self, &M);
/// Appends a transformation to `self`.
fn transformed(&self, &M) -> Self;
/// Sets the transformation of `self`.
fn set_transformation(&mut self, M);
}
/// Trait of objects able to transform other objects.
///
/// This is typically implemented by matrices which transform vectors.
pub trait Transform<V> {
/// Applies a transformation to `v`.
fn transform(&self, &V) -> V;
/// Applies an inverse transformation to `v`.
fn inv_transform(&self, &V) -> V;
}
/// Trait of transformation having a rotation extractable as a rotation matrix. This can typically
/// be implemented by quaternions to convert them to a rotation matrix.
pub trait RotationMatrix<LV, AV, R: Mat<LV, LV> + Rotation<AV>> : Rotation<AV> {
/// Gets the rotation matrix represented by `self`.
fn to_rot_mat(&self) -> R;
}
/// Traits of objects having a dot product.
pub trait Dot<N> {
/// Computes the dot (inner) product of two vectors.
#[inline]
fn dot(&self, &Self) -> N;
/**
* Short-cut to compute the projection of a point on a vector, but without
* computing intermediate vectors.
* This must be equivalent to:
*
* (a - b).dot(c)
*
*/
#[inline]
fn sub_dot(&self, b: &Self, c: &Self) -> N;
}
/// Traits of objects having an euclidian norm.
pub trait Norm<N: Algebraic> {
/// Computes the norm of `self`.
#[inline]
fn norm(&self) -> N {
self.sqnorm().sqrt()
}
/// Computes the squared norm of `self`.
///
/// This is usually faster than computing the norm itself.
#[inline]
fn sqnorm(&self) -> N;
/// Gets the normalized version of `self`.
#[inline]
fn normalized(&self) -> Self;
/// In-place version of `normalized`.
#[inline]
fn normalize(&mut self) -> N;
}
/**
* Trait of elements having a cross product.
*/
pub trait Cross<V> {
/// Computes the cross product between two elements (usually vectors).
fn cross(&self, other: &Self) -> V;
}
/// Traits of objects which can be put in homogeneous coordinates form.
pub trait ToHomogeneous<U> {
/// Gets the homogeneous coordinates form of this object.
fn to_homogeneous(&self) -> U;
}
/// Traits of objects which can be build from an homogeneous coordinate form.
pub trait FromHomogeneous<U> {
/// Builds an object from its homogeneous coordinate form.
///
/// Note that this this is not required that `from` is the inverse of `to_homogeneous`.
/// Typically, `from` will remove some informations unrecoverable by `to_homogeneous`.
fn from(&U) -> Self;
}
/**
* Trait of elements having a cross product operation which can be expressed as a matrix.
*/
pub trait CrossMatrix<M> {
/// The matrix associated to any cross product with this vector. I.e. `v.cross(anything)` =
/// `v.cross_matrix().rmul(anything)`.
fn cross_matrix(&self) -> M;
}
/// Composition of a rotation and an absolute value.
///
/// The operation is accessible using the `RotationMatrix`, `Absolute`, and `RMul` traits, but
/// doing so is not easy in generic code as it can be a cause of type over-parametrization.
pub trait AbsoluteRotate<V> {
/// This is the same as:
///
/// ~~~{.rust}
/// self.rotation_matrix().absolute().rmul(v)
/// ~~~
fn absolute_rotate(&self, v: &V) -> V;
}
/// Trait of vectors able to sample a unit sphere.
///
/// The number of sample must be sufficient to approximate a sphere using a support mapping
/// function.
pub trait UniformSphereSample {
/// Iterate through the samples.
fn sample(&fn(Self));
}
/// Various composition of rotation and translation.
///
/// Utilities to make rotations with regard to a point different than the origin. All those
/// operations are the composition of rotations and translations.
///
/// Those operations are automatically implemented in term of the `Rotation` and `Translation`
/// traits.
pub trait RotationWithTranslation<LV: Neg<LV>, AV>: Rotation<AV> + Translation<LV> {
/// Applies a rotation centered on a specific point.
///
/// # Arguments
/// * `m` - the object to be rotated.
/// * `amount` - the rotation to apply.
/// * `point` - the center of rotation.
#[inline]
fn rotated_wrt_point(&self, amount: &AV, center: &LV) -> Self {
let mut res = self.translated(&-center);
res.rotate_by(amount);
res.translate_by(center);
res
}
/// Rotates `self` using a specific center of rotation.
///
/// The rotation is applied in-place.
///
/// # Arguments
/// * `m` - the object to be rotated
/// * `amount` - the rotation to be applied
/// * `center` - the new center of rotation
#[inline]
fn rotate_wrt_point(&mut self, amount: &AV, center: &LV) {
self.translate_by(&-center);
self.rotate_by(amount);
self.translate_by(center);
}
/// Applies a rotation centered on the translation of `m`.
///
/// # Arguments
/// * `m` - the object to be rotated.
/// * `amount` - the rotation to apply.
#[inline]
fn rotated_wrt_center(&self, amount: &AV) -> Self {
self.rotated_wrt_point(amount, &self.translation())
}
/// Applies a rotation centered on the translation of `m`.
///
/// The rotation os applied on-place.
///
/// # Arguments
/// * `m` - the object to be rotated.
/// * `amount` - the rotation to apply.
#[inline]
fn rotate_wrt_center(&mut self, amount: &AV) {
let center = self.translation();
self.rotate_wrt_point(amount, &center)
}
}
impl<LV: Neg<LV>, AV, M: Rotation<AV> + Translation<LV>> RotationWithTranslation<LV, AV> for M;

View File

@ -1,13 +0,0 @@
/// Traits of objects which can be put in homogeneous coordinates.
pub trait ToHomogeneous<U> {
/// Gets the homogeneous coordinates version of this object.
fn to_homogeneous(&self) -> U;
}
/// Traits of objects which can be build from an homogeneous coordinate representation.
pub trait FromHomogeneous<U> {
/// Builds an object with its homogeneous coordinate version. Note this it is not required for
/// `from` to be the iverse of `to_homogeneous`. Typically, `from` will remove some informations
/// unrecoverable by `to_homogeneous`.
fn from(&U) -> Self;
}

View File

@ -1,17 +0,0 @@
// FIXME: this trait should not be on nalgebra.
// however, it is needed because std::ops::Index is (strangely) to poor: it
// does not have a function to set values.
// Also, using Index with tuples crashes.
/// This is a workaround trait.
///
/// It exists because the `Index` trait cannot be used to express write access.
/// Thus, this is the same as the `Index` trait but without the syntactic sugar and with a method
/// to write to a specific index.
pub trait Indexable<Index, Res> {
/// Reads the `i`-th element of `self`.
fn at(&self, i: Index) -> Res;
/// Writes to the `i`-th element of `self`.
fn set(&mut self, i: Index, Res);
/// Swaps the `i`-th element of `self` with its `j`-th element.
fn swap(&mut self, i: Index, j: Index);
}

View File

@ -1,9 +0,0 @@
/**
* Trait of inversible objects. Typically used to implement matrix inverse.
*/
pub trait Inv {
/// Returns the inverse of an element.
fn inverse(&self) -> Option<Self>;
/// Inplace version of `inverse`.
fn inplace_inverse(&mut self) -> bool;
}

View File

@ -1,30 +0,0 @@
use std::vec;
/// Traits of objects which can be iterated through like a vector.
pub trait Iterable<N> {
/// Gets a vector-like read-only iterator.
fn iter<'l>(&'l self) -> vec::VecIterator<'l, N>;
}
/// Traits of mutable objects which can be iterated through like a vector.
pub trait IterableMut<N> {
/// Gets a vector-like read-write iterator.
fn mut_iter<'l>(&'l mut self) -> vec::VecMutIterator<'l, N>;
}
/*
* FIXME: the prevous traits are only workarounds.
* It should be something like:
pub trait Iterable<'self, N, I: Iterator<N>> {
fn iter(&'self self) -> I;
}
pub trait IterableMut<'self, N, I: Iterator<N>> {
fn mut_iter(&'self self) -> I;
}
* but this gives an ICE =(
* For now, we oblige the iterator to be one specific type which works with
* everything on this lib.
*/

View File

@ -1,8 +0,0 @@
use traits::row::Row;
use traits::col::Col;
use traits::rlmul::{RMul, LMul};
/// Trait of matrix. A matrix must have lines and columns.
pub trait Mat<R, C> : Row<R> + Col<C> + RMul<R> + LMul<C> { }
impl<M: Row<R> + Col<C> + RMul<R> + LMul<C>, R, C> Mat<R, C> for M;

View File

@ -1,6 +0,0 @@
/// Trait of matrices which can be converted to another matrix. Used to change the type of a matrix
/// components.
pub trait MatCast<M> {
/// Converts `m` to have the type `M`.
fn from(m: Self) -> M;
}

View File

@ -1,23 +0,0 @@
/// Traits of objects having an euclidian norm.
pub trait Norm<N: Algebraic> {
/// Computes the norm a an object.
#[inline]
fn norm(&self) -> N {
self.sqnorm().sqrt()
}
/**
* Computes the squared norm of an object. Usually faster than computing the
* norm itself.
*/
#[inline]
fn sqnorm(&self) -> N;
/// Gets the normalized version of the argument.
#[inline]
fn normalized(&self) -> Self;
/// In-place version of `normalized`.
#[inline]
fn normalize(&mut self) -> N;
}

98
src/traits/operations.rs Normal file
View File

@ -0,0 +1,98 @@
/// Trait of objects having an absolute value.
/// This is useful if the object does not have the same type as its absolute value.
pub trait Absolute<A> {
/// Computes some absolute value of this object.
/// Typically, this will make all component of a matrix or vector positive.
fn absolute(&self) -> A;
}
/// Trait of objects having an inverse. Typically used to implement matrix inverse.
pub trait Inv {
/// Returns the inverse of `self`.
fn inverse(&self) -> Option<Self>;
/// In-place version of `inverse`.
fn inplace_inverse(&mut self) -> bool;
}
/// Trait of objects which can be transposed. Note that, for the moment, this
/// does not allow the implementation by non-square matrix (or anything which
/// is not stable by transposition).
pub trait Transpose {
/// Computes the transpose of a matrix.
fn transposed(&self) -> Self;
/// In-place version of `transposed`.
fn transpose(&mut self);
}
/// Traits of objects having an outer product.
pub trait Outer<V, M> {
/// Computes the outer product: `self * other`
fn outer(&self, other: &V) -> M;
}
// XXX: those two traits should not exist since there is generalized operator overloading of Add
// and Sub.
// However, using the same trait multiple time as a trait bound (ex: impl<T: Add<N, V> + Add<V, V>)
// does not work properly, mainly because the way we are doing generalized operator overloading is
// verry hacky.
//
// Hopefully, this will be fixed on a future version of the language!
/// Trait of objects having a right multiplication with another element.
pub trait RMul<V> {
/// Computes `self * v`
fn rmul(&self, v: &V) -> V;
}
impl<M: Mul<T, T>, T> RMul<T> for M {
fn rmul(&self, v: &T) -> T {
self * *v
}
}
/// Trait of objects having a left multiplication with another element.
pub trait LMul<V> {
/// Computes `v * self`
fn lmul(&self, &V) -> V;
}
impl<T: Mul<M, T>, M> LMul<T> for M {
fn lmul(&self, v: &T) -> T {
v * *self
}
}
// XXX: those traits should not exist since there is generalized operator overloading of Add and
// Sub.
// However, using the same trait multiple time as a trait bound (ex: impl<T: Add<N, V> + Add<V, V>)
// does not work properly, mainly because the way we are doing generalized operator overloading is
// verry hacky.
//
// Hopefully, this will be fixed on a future version of the language!
/// Trait of objects having an addition with a scalar.
pub trait ScalarAdd<N> {
/// Gets the result of `self + n`.
fn add_s(&self, n: &N) -> Self;
}
impl<N, T: Add<N, T>> ScalarAdd<N> for T {
/// Gets the result of `self + n`.
fn add_s(&self, n: &N) -> T {
*self + *n
}
}
/**
* Trait of objects having a subtraction with a scalar.
*/
pub trait ScalarSub<N> {
/// Gets the result of `self - n`.
fn sub_s(&self, n: &N) -> Self;
}
impl<N, T: Sub<N, T>> ScalarSub<N> for T {
/// Gets the result of `self - n`.
fn sub_s(&self, n: &N) -> T {
*self - *n
}
}

View File

@ -1,5 +0,0 @@
/// Traits of objects having an outer product.
pub trait Outer<V, M> {
/// Computes the outer product `self * other`
fn outer(&self, other: &V) -> M;
}

View File

@ -1,35 +0,0 @@
// XXX: those traits should not exist since there is generalized operator overloading of Add and
// Sub.
// However, using the same trait multiple time as a trait bound (ex: impl<T: Add<N, V> + Add<V, V>)
// does not work properly, mainly because the way we are doing generalized operator overloading is
// verry hacky.
//
// Hopefully, this will be fixed on a future version of the language!
/**
* Trait of objects having a right multiplication with another element.
*/
pub trait RMul<V> {
/// Computes self * v
fn rmul(&self, v: &V) -> V;
}
impl<M: Mul<T, T>, T> RMul<T> for M {
fn rmul(&self, v: &T) -> T {
self * *v
}
}
/**
* Trait of objects having a left multiplication with another element.
*/
pub trait LMul<V> {
/// Computes v * self
fn lmul(&self, &V) -> V;
}
impl<T: Mul<M, T>, M> LMul<T> for M {
fn lmul(&self, v: &T) -> T {
v * *self
}
}

View File

@ -1,37 +0,0 @@
use traits::mat::Mat;
/// Trait of object which represent a rotation, and to wich new rotations can
/// be appended. A rotation is assumed to be an isomitry without translation
/// and without reflexion.
pub trait Rotation<V> {
/// Gets the rotation associated with this object.
fn rotation(&self) -> V;
/// Gets the inverse rotation associated with this object.
fn inv_rotation(&self) -> V;
/// In-place version of `rotated`.
fn rotate_by(&mut self, &V);
/// Appends a rotation.
fn rotated(&self, &V) -> Self;
/// Sets the rotation.
fn set_rotation(&mut self, V);
}
/// Trait of objects able to rotate other objects. This is typically implemented by matrices which
/// rotate vectors.
pub trait Rotate<V> {
/// Apply a rotation to an object.
fn rotate(&self, &V) -> V;
/// Apply an inverse rotation to an object.
fn inv_rotate(&self, &V) -> V;
}
/// Trait of transformation having a rotation extractable as a rotation matrix. This can typically
/// be implemented by quaternions to convert them
pub trait RotationMatrix<LV, AV, R: Mat<LV, LV> + Rotation<AV>> : Rotation<AV> {
/// Gets the rotation matrix from this object.
fn to_rot_mat(&self) -> R;
}

View File

@ -1,9 +0,0 @@
/// Traits to access rows of a matrix or vector.
pub trait Row<R> {
/// The number of columun of this matrix or vector.
fn num_rows(&self) -> uint;
/// Reads the `i`-th row of `self`.
fn row(&self, i: uint) -> R;
/// Writes the `i`-th row of `self`.
fn set_row(&mut self, i: uint, R);
}

View File

@ -1,6 +0,0 @@
/// Traits of vectors able to sample a sphere. The number of sample must be sufficient to
/// approximate a sphere using support mapping functions.
pub trait UniformSphereSample {
/// Iterate throught the samples.
fn sample(&fn(Self));
}

View File

@ -1,37 +0,0 @@
// XXX: those traits should not exist since there is generalized operator overloading of Add and
// Sub.
// However, using the same trait multiple time as a trait bound (ex: impl<T: Add<N, V> + Add<V, V>)
// does not work properly, mainly because the way we are doing generalized operator overloading is
// verry hacky.
//
// Hopefully, this will be fixed on a future version of the language!
/**
* Trait of objects having an addition with a scalar.
*/
pub trait ScalarAdd<N> {
/// Gets the result of an addition by a scalar.
fn add_s(&self, &N) -> Self;
}
impl<N, T: Add<N, T>> ScalarAdd<N> for T {
/// Gets the result of an addition by a scalar.
fn add_s(&self, n: &N) -> T {
*self + *n
}
}
/**
* Trait of objects having a subtraction with a scalar.
*/
pub trait ScalarSub<N> {
/// Gets the result of a subtraction by a scalar.
fn sub_s(&self, &N) -> Self;
}
impl<N, T: Sub<N, T>> ScalarSub<N> for T {
/// Gets the result of an subition by a scalar.
fn sub_s(&self, n: &N) -> T {
*self - *n
}
}

158
src/traits/structure.rs Normal file
View File

@ -0,0 +1,158 @@
use std::num::Zero;
use std::vec::{VecIterator, VecMutIterator};
use traits::operations::{RMul, LMul, ScalarAdd, ScalarSub};
use traits::geometry::{Dot, Norm, UniformSphereSample};
/// Trait of matrices.
///
/// A matrix has rows and columns and are able to multiply them.
pub trait Mat<R, C> : Row<R> + Col<C> + RMul<R> + LMul<C> { }
impl<M: Row<R> + Col<C> + RMul<R> + LMul<C>, R, C> Mat<R, C> for M;
/// Trait of matrices which can be converted to another matrix.
///
/// Use this to change easily the type of a matrix components.
pub trait MatCast<M> {
/// Converts `m` to have the type `M`.
fn from(m: Self) -> M;
}
// XXX: we keep ScalarAdd and ScalarSub here to avoid trait impl conflict (overriding) between the
// different Add/Sub traits. This is _so_ unfortunate…
// NOTE: cant call that `Vector` because it conflicts with std::Vector
/// Trait grouping most common operations on vectors.
pub trait Vec<N>: Dim + Sub<Self, Self> + Add<Self, Self> + Neg<Self> + Zero + Eq + Mul<N, Self>
+ Div<N, Self> + Dot<N> {
}
/// Trait of vector with components implementing the `Algebraic` trait.
pub trait AlgebraicVec<N: Algebraic>: Vec<N> + Norm<N> {
}
/// Trait grouping uncommon, low-level and borderline (from the mathematical point of view)
/// operations on vectors.
pub trait VecExt<N>: Vec<N> + Basis + Indexable<uint, N> + Iterable<N> + Round +
UniformSphereSample + ScalarAdd<N> + ScalarSub<N> + Bounded + Orderable
{ }
/// Trait grouping uncommon, low-level and borderline (from the mathematical point of view)
/// operations on vectors.
pub trait AlgebraicVecExt<N: Algebraic>: AlgebraicVec<N> + VecExt<N>
{ }
impl<N, V: Dim + Sub<V, V> + Add<V, V> + Neg<V> + Zero + Eq + Mul<N, V> + Div<N, V> + Dot<N>>
Vec<N> for V;
impl<N: Algebraic, V: Vec<N> + Norm<N>> AlgebraicVec<N> for V;
impl<N,
V: Vec<N> + Basis + Indexable<uint, N> + Iterable<N> + Round +
UniformSphereSample + ScalarAdd<N> + ScalarSub<N> + Bounded + Orderable>
VecExt<N> for V;
impl<N: Algebraic, V: AlgebraicVec<N> + VecExt<N>> AlgebraicVecExt<N> for V;
/// Trait of vectors which can be converted to another vector. Used to change the type of a vector
/// components.
pub trait VecCast<V> {
/// Converts `v` to have the type `V`.
fn from(v: Self) -> V;
}
// FIXME: return an iterator instead
/// Traits of objects which can form a basis (typically vectors).
pub trait Basis {
/// Iterates through the canonical basis of the space in which this object lives.
fn canonical_basis(&fn(Self) -> bool);
/// Iterates through a basis of the subspace orthogonal to `self`.
fn orthonormal_subspace_basis(&self, &fn(Self) -> bool);
/// Creates the canonical basis of the space in which this object lives.
fn canonical_basis_list() -> ~[Self] {
let mut res = ~[];
do Basis::canonical_basis |elem| {
res.push(elem);
true
}
res
}
/// Creates a basis of the subspace orthogonal to `self`.
fn orthonormal_subspace_basis_list(&self) -> ~[Self] {
let mut res = ~[];
do self.orthonormal_subspace_basis |elem| {
res.push(elem);
true
}
res
}
}
/// Trait to access rows of a matrix or a vector.
pub trait Row<R> {
/// The number of column of `self`.
fn num_rows(&self) -> uint;
/// Reads the `i`-th row of `self`.
fn row(&self, i: uint) -> R;
/// Writes the `i`-th row of `self`.
fn set_row(&mut self, i: uint, R);
}
/// Trait to access columns of a matrix or vector.
pub trait Col<C> {
/// The number of column of this matrix or vector.
fn num_cols(&self) -> uint;
/// Reads the `i`-th column of `self`.
fn col(&self, i: uint) -> C;
/// Writes the `i`-th column of `self`.
fn set_col(&mut self, i: uint, C);
}
/// Trait of objects having a spacial dimension known at compile time.
pub trait Dim {
/// The dimension of the object.
fn dim(unused_self: Option<Self>) -> uint;
}
// FIXME: this trait should not be on nalgebra.
// however, it is needed because std::ops::Index is (strangely) to poor: it
// does not have a function to set values.
// Also, using Index with tuples crashes.
/// This is a workaround of current Rust limitations.
///
/// It exists because the `Index` trait cannot be used to express write access.
/// Thus, this is the same as the `Index` trait but without the syntactic sugar and with a method
/// to write to a specific index.
pub trait Indexable<Index, Res> {
/// Reads the `i`-th element of `self`.
fn at(&self, i: Index) -> Res;
/// Writes to the `i`-th element of `self`.
fn set(&mut self, i: Index, Res);
/// Swaps the `i`-th element of `self` with its `j`-th element.
fn swap(&mut self, i: Index, j: Index);
}
/// This is a workaround of current Rust limitations.
///
/// Traits of objects which can be iterated through like a vector.
pub trait Iterable<N> {
/// Gets a vector-like read-only iterator.
fn iter<'l>(&'l self) -> VecIterator<'l, N>;
}
/// This is a workaround of current Rust limitations.
///
/// Traits of mutable objects which can be iterated through like a vector.
pub trait IterableMut<N> {
/// Gets a vector-like read-write iterator.
fn mut_iter<'l>(&'l mut self) -> VecMutIterator<'l, N>;
}

View File

@ -1,28 +0,0 @@
/// Trait of object which represent a transformation, and to wich new transformations can
/// be appended. A transformation is assumed to be an isomitry without translation
/// and without reflexion.
pub trait Transformation<M> {
/// Gets the transformation associated with this object.
fn transformation(&self) -> M;
/// Gets the inverse transformation associated with this object.
fn inv_transformation(&self) -> M;
/// In-place version of `transformed`.
fn transform_by(&mut self, &M);
/// Appends a transformation.
fn transformed(&self, &M) -> Self;
/// Sets the transformation.
fn set_transformation(&mut self, M);
}
/// Trait of objects able to transform other objects. This is typically implemented by matrices which
/// transform vectors.
pub trait Transform<V> {
/// Apply a transformation to an object.
fn transform(&self, &V) -> V;
/// Apply an inverse transformation to an object.
fn inv_transform(&self, &V) -> V;
}

View File

@ -1,28 +0,0 @@
/// Trait of object which represent a translation, and to wich new translation
/// can be appended.
pub trait Translation<V> {
// FIXME: add a "from translation: translantion(V) -> Self ?
/// Gets the translation associated with this object.
fn translation(&self) -> V;
/// Gets the inverse translation associated with this object.
fn inv_translation(&self) -> V;
/// In-place version of `translated`.
fn translate_by(&mut self, &V);
/// Appends a translation.
fn translated(&self, &V) -> Self;
/// Sets the translation.
fn set_translation(&mut self, V);
}
/// Trait of objects able to rotate other objects. This is typically implemented by matrices which
/// rotate vectors.
pub trait Translate<V> {
/// Apply a translation to an object.
fn translate(&self, &V) -> V;
/// Apply an inverse translation to an object.
fn inv_translate(&self, &V) -> V;
}

View File

@ -1,11 +0,0 @@
// FIXME: valid only for square matrices…
/// Trait of objects which can be transposed. Note that, for the moment, this
/// does not allow the implementation by non-square matrix (or anything which
/// is not stable by transposition).
pub trait Transpose {
/// Computes the transpose of a matrix.
fn transposed(&self) -> Self;
/// In-place version of `transposed`.
fn transpose(&mut self);
}

View File

@ -1,6 +0,0 @@
/// Trait of vectors which can be converted to another vector. Used to change the type of a vector
/// components.
pub trait VecCast<V> {
/// Converts `v` to have the type `V`.
fn from(v: Self) -> V;
}

View File

@ -1,45 +0,0 @@
use std::num::Zero;
use traits::dim::Dim;
use traits::basis::Basis;
use traits::indexable::Indexable;
use traits::iterable::Iterable;
use traits::sample::UniformSphereSample;
use traits::scalar_op::{ScalarAdd, ScalarSub};
use traits::dot::Dot;
use traits::norm::Norm;
// XXX: we keep ScalarAdd and ScalarSub here to avoid trait impl conflict (overriding) between the
// different Add/Sub traits. This is _so_ unfortunate…
// NOTE: cant call that `Vector` because it conflicts with std::Vector
/// Trait grouping most common operations on vectors.
pub trait Vec<N>: Dim + Sub<Self, Self> + Add<Self, Self> + Neg<Self> + Zero + Eq + Mul<N, Self>
+ Div<N, Self> + Dot<N> {
}
/// Trait of vector with components implementing the `Algebraic` trait.
pub trait AlgebraicVec<N: Algebraic>: Vec<N> + Norm<N> {
}
/// Trait grouping uncommon, low-level and borderline (from the mathematical point of view)
/// operations on vectors.
pub trait VecExt<N>: Vec<N> + Basis + Indexable<uint, N> + Iterable<N> + Round +
UniformSphereSample + ScalarAdd<N> + ScalarSub<N> + Bounded + Orderable
{ }
/// Trait grouping uncommon, low-level and borderline (from the mathematical point of view)
/// operations on vectors.
pub trait AlgebraicVecExt<N: Algebraic>: AlgebraicVec<N> + VecExt<N>
{ }
impl<N, V: Dim + Sub<V, V> + Add<V, V> + Neg<V> + Zero + Eq + Mul<N, V> + Div<N, V> + Dot<N>>
Vec<N> for V;
impl<N: Algebraic, V: Vec<N> + Norm<N>> AlgebraicVec<N> for V;
impl<N,
V: Vec<N> + Basis + Indexable<uint, N> + Iterable<N> + Round +
UniformSphereSample + ScalarAdd<N> + ScalarSub<N> + Bounded + Orderable>
VecExt<N> for V;
impl<N: Algebraic, V: AlgebraicVec<N> + VecExt<N>> AlgebraicVecExt<N> for V;

View File

@ -1,3 +1,5 @@
//! Useful type aliases.
use vec::{Vec1, Vec2, Vec3, Vec4, Vec5, Vec6};
use mat::{Mat1, Mat2, Mat3, Mat4, Mat5, Mat6};
use adaptors::rotmat::Rotmat;

View File

@ -1,3 +1,5 @@
//! Vectors with dimensions known at compile-time.
#[doc(hidden)]; // we hide doc to not have to document the $trhs double dispatch trait.
use std::cast;
@ -7,23 +9,13 @@ use std::vec::{VecIterator, VecMutIterator};
use std::iter::{Iterator, FromIterator};
use std::cmp::ApproxEq;
use traits::translation::{Translation, Translate};
use traits::transformation::Transform;
use traits::rotation::Rotate;
use traits::geometry::{Transform, Rotate};
pub use traits::homogeneous::{FromHomogeneous, ToHomogeneous};
pub use traits::vec_cast::VecCast;
pub use traits::vector::{Vec, VecExt, AlgebraicVec, AlgebraicVecExt};
pub use traits::basis::Basis;
pub use traits::dim::Dim;
pub use traits::indexable::Indexable;
pub use traits::iterable::{Iterable, IterableMut};
pub use traits::sample::UniformSphereSample;
pub use traits::scalar_op::{ScalarAdd, ScalarSub};
pub use traits::cross::{Cross, CrossMatrix};
pub use traits::outer::Outer;
pub use traits::dot::Dot;
pub use traits::norm::Norm;
pub use traits::geometry::{FromHomogeneous, ToHomogeneous, Dot, Norm, Cross, CrossMatrix,
Translation, Translate, UniformSphereSample};
pub use traits::structure::{VecCast, Vec, VecExt, AlgebraicVec, AlgebraicVecExt, Basis, Dim,
Indexable, Iterable, IterableMut};
pub use traits::operations::{Outer, ScalarAdd, ScalarSub};
// structs
pub use dvec::DVec;