Execute rustfmt.

This commit is contained in:
sebcrozet 2018-10-21 22:11:27 +02:00 committed by Sébastien Crozet
parent a3d363f397
commit b9ca074740
41 changed files with 798 additions and 465 deletions

View File

@ -1,9 +1,7 @@
use na::{MatrixMN, VectorN,
Matrix2, Matrix3, Matrix4,
Matrix2x3, Matrix3x2, Matrix4x2,
Matrix2x4, Matrix3x4, Matrix4x3,
Quaternion,
U1, U2, U3, U4};
use na::{
Matrix2, Matrix2x3, Matrix2x4, Matrix3, Matrix3x2, Matrix3x4, Matrix4, Matrix4x2, Matrix4x3,
MatrixMN, Quaternion, VectorN, U1, U2, U3, U4,
};
/// A matrix with components of type `N`. It has `R` rows, and `C` columns.
///
@ -194,13 +192,13 @@ pub type UVec3 = TVec3<u32>;
/// A 4D vector with `u32` components.
pub type UVec4 = TVec4<u32>;
/// A 1D vector with `f32` components.
pub type Vec1 = TVec1<f32>;
pub type Vec1 = TVec1<f32>;
/// A 2D vector with `f32` components.
pub type Vec2 = TVec2<f32>;
pub type Vec2 = TVec2<f32>;
/// A 3D vector with `f32` components.
pub type Vec3 = TVec3<f32>;
pub type Vec3 = TVec3<f32>;
/// A 4D vector with `f32` components.
pub type Vec4 = TVec4<f32>;
pub type Vec4 = TVec4<f32>;
/// A 1D vector with `u64` components.
pub type U64Vec1 = TVec1<u64>;
@ -270,7 +268,6 @@ pub type I8Vec3 = TVec3<i8>;
/// A 4D vector with `i8` components.
pub type I8Vec4 = TVec4<i8>;
/// A 2x2 matrix with components of type `N`.
pub type TMat2<N> = Matrix2<N>;
/// A 2x2 matrix with components of type `N`.

View File

@ -1,5 +1,5 @@
use na::{Real, DefaultAllocator};
use aliases::TVec;
use na::{DefaultAllocator, Real};
use traits::{Alloc, Dimension};
/// Component-wise exponential.
@ -8,7 +8,9 @@ use traits::{Alloc, Dimension};
///
/// * [`exp2`](fn.exp2.html)
pub fn exp<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| x.exp())
}
@ -18,7 +20,9 @@ pub fn exp<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
///
/// * [`exp`](fn.exp.html)
pub fn exp2<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| x.exp2())
}
@ -28,9 +32,10 @@ pub fn exp2<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
///
/// * [`sqrt`](fn.sqrt.html)
pub fn inversesqrt<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| N::one() / x.sqrt())
}
/// Component-wise logarithm.
@ -39,7 +44,9 @@ pub fn inversesqrt<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
///
/// * [`log2`](fn.log2.html)
pub fn log<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| x.ln())
}
@ -49,13 +56,17 @@ pub fn log<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
///
/// * [`log`](fn.log.html)
pub fn log2<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| x.log2())
}
/// Component-wise power.
pub fn pow<N: Real, D: Dimension>(base: &TVec<N, D>, exponent: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
base.zip_map(exponent, |b, e| b.powf(e))
}
@ -68,6 +79,8 @@ pub fn pow<N: Real, D: Dimension>(base: &TVec<N, D>, exponent: &TVec<N, D>) -> T
/// * [`inversesqrt`](fn.inversesqrt.html)
/// * [`pow`](fn.pow.html)
pub fn sqrt<N: Real, D: Dimension>(v: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| x.sqrt())
}

View File

@ -1,5 +1,5 @@
use na::{Real, Orthographic3, Perspective3};
use aliases::TMat4;
use na::{Orthographic3, Perspective3, Real};
//pub fn frustum<N: Real>(left: N, right: N, bottom: N, top: N, near: N, far: N) -> TMat4<N> {
// unimplemented!()
@ -90,7 +90,6 @@ pub fn ortho<N: Real>(left: N, right: N, bottom: N, top: N, znear: N, zfar: N) -
// unimplemented!()
//}
/// Creates a matrix for a perspective-view frustum based on the right handedness and OpenGL near and far clip planes definition.
///
/// # Important note

View File

@ -1,6 +1,6 @@
use na::{self, Real, U3};
use aliases::{TVec2, TVec3, TVec4, TMat4};
use aliases::{TMat4, TVec2, TVec3, TVec4};
/// Define a picking region.
///
@ -13,11 +13,15 @@ pub fn pick_matrix<N: Real>(center: &TVec2<N>, delta: &TVec2<N>, viewport: &TVec
let shift = TVec3::new(
(viewport.z - (center.x - viewport.x) * na::convert(2.0)) / delta.x,
(viewport.w - (center.y - viewport.y) * na::convert(2.0)) / delta.y,
N::zero()
N::zero(),
);
let result = TMat4::new_translation(&shift);
result.prepend_nonuniform_scaling(&TVec3::new(viewport.z / delta.x, viewport.w / delta.y, N::one()))
result.prepend_nonuniform_scaling(&TVec3::new(
viewport.z / delta.x,
viewport.w / delta.y,
N::one(),
))
}
/// Map the specified object coordinates `(obj.x, obj.y, obj.z)` into window coordinates using OpenGL near and far clip planes definition.
@ -36,7 +40,12 @@ pub fn pick_matrix<N: Real>(center: &TVec2<N>, delta: &TVec2<N>, viewport: &TVec
/// * [`unproject`](fn.unproject.html)
/// * [`unproject_no`](fn.unproject_no.html)
/// * [`unproject_zo`](fn.unproject_zo.html)
pub fn project<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn project<N: Real>(
obj: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
project_no(obj, model, proj, viewport)
}
@ -58,7 +67,12 @@ pub fn project<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewp
/// * [`unproject`](fn.unproject.html)
/// * [`unproject_no`](fn.unproject_no.html)
/// * [`unproject_zo`](fn.unproject_zo.html)
pub fn project_no<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn project_no<N: Real>(
obj: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
let proj = project_zo(obj, model, proj, viewport);
TVec3::new(proj.x, proj.y, proj.z * na::convert(0.5) + na::convert(0.5))
}
@ -81,7 +95,12 @@ pub fn project_no<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, vi
/// * [`unproject`](fn.unproject.html)
/// * [`unproject_no`](fn.unproject_no.html)
/// * [`unproject_zo`](fn.unproject_zo.html)
pub fn project_zo<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn project_zo<N: Real>(
obj: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
let normalized = proj * model * TVec4::new(obj.x, obj.y, obj.z, N::one());
let scale = N::one() / normalized.w;
@ -108,7 +127,12 @@ pub fn project_zo<N: Real>(obj: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, vi
/// * [`project_zo`](fn.project_zo.html)
/// * [`unproject_no`](fn.unproject_no.html)
/// * [`unproject_zo`](fn.unproject_zo.html)
pub fn unproject<N: Real>(win: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn unproject<N: Real>(
win: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
unproject_no(win, model, proj, viewport)
}
@ -130,7 +154,12 @@ pub fn unproject<N: Real>(win: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, vie
/// * [`project_zo`](fn.project_zo.html)
/// * [`unproject`](fn.unproject.html)
/// * [`unproject_zo`](fn.unproject_zo.html)
pub fn unproject_no<N: Real>(win: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn unproject_no<N: Real>(
win: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
let _2: N = na::convert(2.0);
let transform = (proj * model).try_inverse().unwrap_or_else(TMat4::zeros);
let pt = TVec4::new(
@ -162,7 +191,12 @@ pub fn unproject_no<N: Real>(win: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>,
/// * [`project_zo`](fn.project_zo.html)
/// * [`unproject`](fn.unproject.html)
/// * [`unproject_no`](fn.unproject_no.html)
pub fn unproject_zo<N: Real>(win: &TVec3<N>, model: &TMat4<N>, proj: &TMat4<N>, viewport: TVec4<N>) -> TVec3<N> {
pub fn unproject_zo<N: Real>(
win: &TVec3<N>,
model: &TMat4<N>,
proj: &TMat4<N>,
viewport: TVec4<N>,
) -> TVec3<N> {
let _2: N = na::convert(2.0);
let transform = (proj * model).try_inverse().unwrap_or_else(TMat4::zeros);
let pt = TVec4::new(

View File

@ -1,13 +1,18 @@
use na::DefaultAllocator;
use aliases::{TVec, TMat};
use traits::{Alloc, Number, Dimension};
use aliases::{TMat, TVec};
use traits::{Alloc, Dimension, Number};
/// Perform a component-wise equal-to comparison of two matrices.
///
/// Return a boolean vector which components value is True if this expression is satisfied per column of the matrices.
pub fn equal_columns<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn equal_columns<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = TVec::<_, C>::repeat(false);
for i in 0..C::dim() {
@ -20,16 +25,28 @@ pub fn equal_columns<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y
/// Returns the component-wise comparison of `|x - y| < epsilon`.
///
/// True if this expression is satisfied.
pub fn equal_columns_eps<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>, epsilon: N) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn equal_columns_eps<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
epsilon: N,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
equal_columns_eps_vec(x, y, &TVec::<_, C>::repeat(epsilon))
}
/// Returns the component-wise comparison on each matrix column `|x - y| < epsilon`.
///
/// True if this expression is satisfied.
pub fn equal_columns_eps_vec<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>, epsilon: &TVec<N, C>) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn equal_columns_eps_vec<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
epsilon: &TVec<N, C>,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = TVec::<_, C>::repeat(false);
for i in 0..C::dim() {
@ -42,8 +59,13 @@ pub fn equal_columns_eps_vec<N: Number, R: Dimension, C: Dimension>(x: &TMat<N,
/// Perform a component-wise not-equal-to comparison of two matrices.
///
/// Return a boolean vector which components value is True if this expression is satisfied per column of the matrices.
pub fn not_equal_columns<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn not_equal_columns<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = TVec::<_, C>::repeat(false);
for i in 0..C::dim() {
@ -56,16 +78,28 @@ pub fn not_equal_columns<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C
/// Returns the component-wise comparison of `|x - y| < epsilon`.
///
/// True if this expression is not satisfied.
pub fn not_equal_columns_eps<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>, epsilon: N) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn not_equal_columns_eps<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
epsilon: N,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
not_equal_columns_eps_vec(x, y, &TVec::<_, C>::repeat(epsilon))
}
/// Returns the component-wise comparison of `|x - y| >= epsilon`.
///
/// True if this expression is not satisfied.
pub fn not_equal_columns_eps_vec<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>, epsilon: &TVec<N, C>) -> TVec<bool, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn not_equal_columns_eps_vec<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
epsilon: &TVec<N, C>,
) -> TVec<bool, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = TVec::<_, C>::repeat(false);
for i in 0..C::dim() {

View File

@ -1,11 +1,13 @@
use na::{DefaultAllocator, Real, Unit, Rotation3, Point3};
use na::{DefaultAllocator, Point3, Real, Rotation3, Unit};
use traits::{Dimension, Number, Alloc};
use aliases::{TMat, TVec, TVec3, TMat4};
use aliases::{TMat, TMat4, TVec, TVec3};
use traits::{Alloc, Dimension, Number};
/// The identity matrix.
pub fn identity<N: Number, D: Dimension>() -> TMat<N, D, D>
where DefaultAllocator: Alloc<N, D, D> {
where
DefaultAllocator: Alloc<N, D, D>,
{
TMat::<N, D, D>::identity()
}
@ -38,7 +40,11 @@ pub fn look_at<N: Real>(eye: &TVec3<N>, center: &TVec3<N>, up: &TVec3<N>) -> TMa
/// * [`look_at`](fn.look_at.html)
/// * [`look_at_rh`](fn.look_at_rh.html)
pub fn look_at_lh<N: Real>(eye: &TVec3<N>, center: &TVec3<N>, up: &TVec3<N>) -> TMat4<N> {
TMat::look_at_lh(&Point3::from_coordinates(*eye), &Point3::from_coordinates(*center), up)
TMat::look_at_lh(
&Point3::from_coordinates(*eye),
&Point3::from_coordinates(*center),
up,
)
}
/// Build a right handed look at view matrix.
@ -54,7 +60,11 @@ pub fn look_at_lh<N: Real>(eye: &TVec3<N>, center: &TVec3<N>, up: &TVec3<N>) ->
/// * [`look_at`](fn.look_at.html)
/// * [`look_at_lh`](fn.look_at_lh.html)
pub fn look_at_rh<N: Real>(eye: &TVec3<N>, center: &TVec3<N>, up: &TVec3<N>) -> TMat4<N> {
TMat::look_at_rh(&Point3::from_coordinates(*eye), &Point3::from_coordinates(*center), up)
TMat::look_at_rh(
&Point3::from_coordinates(*eye),
&Point3::from_coordinates(*center),
up,
)
}
/// Builds a rotation 4 * 4 matrix created from an axis vector and an angle and right-multiply it to `m`.

View File

@ -1,30 +1,41 @@
//! (Reexported) Additional features not specified by GLSL specification
pub use self::matrix_clip_space::{ortho, perspective};
pub use self::matrix_projection::{pick_matrix, project, project_no, project_zo, unproject, unproject_no, unproject_zo};
pub use self::matrix_relationnal::{equal_columns, equal_columns_eps, equal_columns_eps_vec, not_equal_columns, not_equal_columns_eps, not_equal_columns_eps_vec};
pub use self::matrix_transform::{identity, look_at, look_at_lh, rotate, scale, look_at_rh, translate, rotate_x, rotate_y, rotate_z};
pub use self::matrix_projection::{
pick_matrix, project, project_no, project_zo, unproject, unproject_no, unproject_zo,
};
pub use self::matrix_relationnal::{
equal_columns, equal_columns_eps, equal_columns_eps_vec, not_equal_columns,
not_equal_columns_eps, not_equal_columns_eps_vec,
};
pub use self::matrix_transform::{
identity, look_at, look_at_lh, look_at_rh, rotate, rotate_x, rotate_y, rotate_z, scale,
translate,
};
pub use self::quaternion_common::{quat_conjugate, quat_inverse, quat_lerp, quat_slerp};
pub use self::quaternion_geometric::{
quat_cross, quat_dot, quat_length, quat_magnitude, quat_normalize,
};
pub use self::quaternion_relational::{
quat_equal, quat_equal_eps, quat_not_equal, quat_not_equal_eps,
};
pub use self::quaternion_transform::{quat_exp, quat_log, quat_pow, quat_rotate};
pub use self::quaternion_trigonometric::{quat_angle, quat_angle_axis, quat_axis};
pub use self::scalar_common::{max3_scalar, max4_scalar, min3_scalar, min4_scalar};
pub use self::scalar_constants::{epsilon, pi};
pub use self::vector_common::{max, max2, max3, max4, min, min2, min3, min4};
pub use self::vector_relational::{equal_eps, equal_eps_vec, not_equal_eps, not_equal_eps_vec};
pub use self::quaternion_common::{quat_conjugate, quat_inverse, quat_lerp, quat_slerp};
pub use self::quaternion_geometric::{quat_cross, quat_dot, quat_length, quat_magnitude, quat_normalize};
pub use self::quaternion_relational::{quat_equal, quat_equal_eps, quat_not_equal, quat_not_equal_eps};
pub use self::quaternion_transform::{quat_exp, quat_log, quat_pow, quat_rotate};
pub use self::quaternion_trigonometric::{quat_angle, quat_angle_axis, quat_axis};
mod matrix_clip_space;
mod matrix_projection;
mod matrix_relationnal;
mod matrix_transform;
mod scalar_common;
mod scalar_constants;
mod vector_common;
mod vector_relational;
mod quaternion_common;
mod quaternion_geometric;
mod quaternion_relational;
mod quaternion_transform;
mod quaternion_trigonometric;
mod quaternion_trigonometric;
mod scalar_common;
mod scalar_constants;
mod vector_common;
mod vector_relational;

View File

@ -31,5 +31,7 @@ pub fn quat_lerp<N: Real>(x: &Qua<N>, y: &Qua<N>, a: N) -> Qua<N> {
/// Interpolate spherically between `x` and `y`.
pub fn quat_slerp<N: Real>(x: &Qua<N>, y: &Qua<N>, a: N) -> Qua<N> {
Unit::new_normalize(*x).slerp(&Unit::new_normalize(*y), a).unwrap()
Unit::new_normalize(*x)
.slerp(&Unit::new_normalize(*y), a)
.unwrap()
}

View File

@ -25,4 +25,4 @@ pub fn quat_magnitude<N: Real>(q: &Qua<N>) -> N {
/// Normalizes the quaternion `q`.
pub fn quat_normalize<N: Real>(q: &Qua<N>) -> Qua<N> {
q.normalize()
}
}

View File

@ -1,6 +1,5 @@
use na::{Real, U4};
use aliases::{Qua, TVec};
/// Component-wise equality comparison between two quaternions.

View File

@ -1,4 +1,4 @@
use na::{Real, UnitQuaternion, Unit};
use na::{Real, Unit, UnitQuaternion};
use aliases::{Qua, TVec3};
@ -24,4 +24,4 @@ pub fn quat_rotate<N: Real>(q: &Qua<N>, angle: N, axis: &TVec3<N>) -> Qua<N> {
//pub fn quat_sqrt<N: Real>(q: &Qua<N>) -> Qua<N> {
// unimplemented!()
//}
//}

View File

@ -19,4 +19,4 @@ pub fn quat_axis<N: Real>(x: &Qua<N>) -> TVec3<N> {
} else {
TVec3::zeros()
}
}
}

View File

@ -1,7 +1,7 @@
use na::{self, DefaultAllocator};
use traits::{Alloc, Number, Dimension};
use aliases::TVec;
use traits::{Alloc, Dimension, Number};
/// Component-wise maximum between a vector and a scalar.
///
@ -17,7 +17,9 @@ use aliases::TVec;
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn max<N: Number, D: Dimension>(a: &TVec<N, D>, b: N) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
a.map(|a| na::sup(&a, &b))
}
@ -35,7 +37,9 @@ pub fn max<N: Number, D: Dimension>(a: &TVec<N, D>, b: N) -> TVec<N, D>
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn max2<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
na::sup(a, b)
}
@ -53,7 +57,9 @@ pub fn max2<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>) -> TVec<N,
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn max3<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
max2(&max2(a, b), c)
}
@ -70,8 +76,15 @@ pub fn max3<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N,
/// * [`min2`](fn.min2.html)
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn max4<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N, D>, d: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
pub fn max4<N: Number, D: Dimension>(
a: &TVec<N, D>,
b: &TVec<N, D>,
c: &TVec<N, D>,
d: &TVec<N, D>,
) -> TVec<N, D>
where
DefaultAllocator: Alloc<N, D>,
{
max2(&max2(a, b), &max2(c, d))
}
@ -89,7 +102,9 @@ pub fn max4<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N,
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn min<N: Number, D: Dimension>(x: &TVec<N, D>, y: N) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|x| na::inf(&x, &y))
}
@ -107,7 +122,9 @@ pub fn min<N: Number, D: Dimension>(x: &TVec<N, D>, y: N) -> TVec<N, D>
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn min2<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
na::inf(x, y)
}
@ -125,7 +142,9 @@ pub fn min2<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<N,
/// * [`min2`](fn.min2.html)
/// * [`min4`](fn.min4.html)
pub fn min3<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
min2(&min2(a, b), c)
}
@ -142,7 +161,14 @@ pub fn min3<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N,
/// * [`min`](fn.min.html)
/// * [`min2`](fn.min2.html)
/// * [`min3`](fn.min3.html)
pub fn min4<N: Number, D: Dimension>(a: &TVec<N, D>, b: &TVec<N, D>, c: &TVec<N, D>, d: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
pub fn min4<N: Number, D: Dimension>(
a: &TVec<N, D>,
b: &TVec<N, D>,
c: &TVec<N, D>,
d: &TVec<N, D>,
) -> TVec<N, D>
where
DefaultAllocator: Alloc<N, D>,
{
min2(&min2(a, b), &min2(c, d))
}

View File

@ -1,7 +1,7 @@
use na::{DefaultAllocator};
use na::DefaultAllocator;
use traits::{Alloc, Number, Dimension};
use aliases::TVec;
use traits::{Alloc, Dimension, Number};
/// Component-wise approximate equality of two vectors, using a scalar epsilon.
///
@ -10,8 +10,14 @@ use aliases::TVec;
/// * [`equal_eps_vec`](fn.equal_eps_vec.html)
/// * [`not_equal_eps`](fn.not_equal_eps.html)
/// * [`not_equal_eps_vec`](fn.not_equal_eps_vec.html)
pub fn equal_eps<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, epsilon: N) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
pub fn equal_eps<N: Number, D: Dimension>(
x: &TVec<N, D>,
y: &TVec<N, D>,
epsilon: N,
) -> TVec<bool, D>
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| abs_diff_eq!(x, y, epsilon = epsilon))
}
@ -22,8 +28,14 @@ pub fn equal_eps<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, epsilo
/// * [`equal_eps`](fn.equal_eps.html)
/// * [`not_equal_eps`](fn.not_equal_eps.html)
/// * [`not_equal_eps_vec`](fn.not_equal_eps_vec.html)
pub fn equal_eps_vec<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, epsilon: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
pub fn equal_eps_vec<N: Number, D: Dimension>(
x: &TVec<N, D>,
y: &TVec<N, D>,
epsilon: &TVec<N, D>,
) -> TVec<bool, D>
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_zip_map(y, epsilon, |x, y, eps| abs_diff_eq!(x, y, epsilon = eps))
}
@ -34,8 +46,14 @@ pub fn equal_eps_vec<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, ep
/// * [`equal_eps`](fn.equal_eps.html)
/// * [`equal_eps_vec`](fn.equal_eps_vec.html)
/// * [`not_equal_eps_vec`](fn.not_equal_eps_vec.html)
pub fn not_equal_eps<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, epsilon: N) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
pub fn not_equal_eps<N: Number, D: Dimension>(
x: &TVec<N, D>,
y: &TVec<N, D>,
epsilon: N,
) -> TVec<bool, D>
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| abs_diff_ne!(x, y, epsilon = epsilon))
}
@ -46,7 +64,13 @@ pub fn not_equal_eps<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, ep
/// * [`equal_eps`](fn.equal_eps.html)
/// * [`equal_eps_vec`](fn.equal_eps_vec.html)
/// * [`not_equal_eps`](fn.not_equal_eps.html)
pub fn not_equal_eps_vec<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>, epsilon: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
pub fn not_equal_eps_vec<N: Number, D: Dimension>(
x: &TVec<N, D>,
y: &TVec<N, D>,
epsilon: &TVec<N, D>,
) -> TVec<bool, D>
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_zip_map(y, epsilon, |x, y, eps| abs_diff_ne!(x, y, epsilon = eps))
}

View File

@ -1,7 +1,7 @@
use na::{Real, DefaultAllocator};
use na::{DefaultAllocator, Real};
use traits::{Number, Alloc, Dimension};
use aliases::{TVec, TVec3};
use traits::{Alloc, Dimension, Number};
/// The cross product of two vectors.
pub fn cross<N: Number, D: Dimension>(x: &TVec3<N>, y: &TVec3<N>) -> TVec3<N> {
@ -14,19 +14,29 @@ pub fn cross<N: Number, D: Dimension>(x: &TVec3<N>, y: &TVec3<N>) -> TVec3<N> {
///
/// * [`distance2`](fn.distance2.html)
pub fn distance<N: Real, D: Dimension>(p0: &TVec<N, D>, p1: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
(p1 - p0).norm()
where
DefaultAllocator: Alloc<N, D>,
{
(p1 - p0).norm()
}
/// The dot product of two vectors.
pub fn dot<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.dot(y)
}
/// If `dot(nref, i) < 0.0`, return `n`, otherwise, return `-n`.
pub fn faceforward<N: Number, D: Dimension>(n: &TVec<N, D>, i: &TVec<N, D>, nref: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
pub fn faceforward<N: Number, D: Dimension>(
n: &TVec<N, D>,
i: &TVec<N, D>,
nref: &TVec<N, D>,
) -> TVec<N, D>
where
DefaultAllocator: Alloc<N, D>,
{
if nref.dot(i) < N::zero() {
n.clone()
} else {
@ -44,7 +54,9 @@ pub fn faceforward<N: Number, D: Dimension>(n: &TVec<N, D>, i: &TVec<N, D>, nref
/// * [`magnitude`](fn.magnitude.html)
/// * [`magnitude2`](fn.magnitude2.html)
pub fn length<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.norm()
}
@ -58,34 +70,40 @@ pub fn length<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
/// * [`magnitude2`](fn.magnitude2.html)
/// * [`nalgebra::norm`](../nalgebra/fn.norm.html)
pub fn magnitude<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.norm()
}
/// Normalizes a vector.
pub fn normalize<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.normalize()
}
/// For the incident vector `i` and surface orientation `n`, returns the reflection direction : `result = i - 2.0 * dot(n, i) * n`.
pub fn reflect_vec<N: Number, D: Dimension>(i: &TVec<N, D>, n: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
let _2 = N::one() + N::one();
i - n * (n.dot(i) * _2)
}
/// For the incident vector `i` and surface normal `n`, and the ratio of indices of refraction `eta`, return the refraction vector.
pub fn refract_vec<N: Real, D: Dimension>(i: &TVec<N, D>, n: &TVec<N, D>, eta: N) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
let ni = n.dot(i);
let k = N::one() - eta * eta * (N::one() - ni * ni);
if k < N::zero() {
TVec::<_, D>::zeros()
}
else {
} else {
i * eta - n * (eta * dot(n, i) + k.sqrt())
}
}

View File

@ -28,4 +28,4 @@ pub fn epsilon_not_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>
pub fn epsilon_not_equal2<N: AbsDiffEq<Epsilon = N>>(x: N, y: N, epsilon: N) -> bool {
abs_diff_ne!(x, y, epsilon = epsilon)
}
*/
*/

View File

@ -1,7 +1,7 @@
use na::{Scalar, DefaultAllocator};
use na::{DefaultAllocator, Scalar};
use aliases::{TMat, TVec};
use traits::{Alloc, Dimension};
use aliases::{TVec, TMat};
/// The `index`-th column of the matrix `m`.
///
@ -11,7 +11,9 @@ use aliases::{TVec, TMat};
/// * [`set_column`](fn.set_column.html)
/// * [`set_row`](fn.set_row.html)
pub fn column<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: usize) -> TVec<N, R>
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.column(index).into_owned()
}
@ -22,8 +24,14 @@ pub fn column<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: u
/// * [`column`](fn.column.html)
/// * [`row`](fn.row.html)
/// * [`set_row`](fn.set_row.html)
pub fn set_column<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: usize, x: &TVec<N, R>) -> TMat<N, R, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn set_column<N: Scalar, R: Dimension, C: Dimension>(
m: &TMat<N, R, C>,
index: usize,
x: &TVec<N, R>,
) -> TMat<N, R, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = m.clone();
res.set_column(index, x);
res
@ -37,7 +45,9 @@ pub fn set_column<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, inde
/// * [`set_column`](fn.set_column.html)
/// * [`set_row`](fn.set_row.html)
pub fn row<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: usize) -> TVec<N, C>
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.row(index).into_owned().transpose()
}
@ -48,8 +58,14 @@ pub fn row<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: usiz
/// * [`column`](fn.column.html)
/// * [`row`](fn.row.html)
/// * [`set_column`](fn.set_column.html)
pub fn set_row<N: Scalar, R: Dimension, C: Dimension>(m: &TMat<N, R, C>, index: usize, x: &TVec<N, C>) -> TMat<N, R, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn set_row<N: Scalar, R: Dimension, C: Dimension>(
m: &TMat<N, R, C>,
index: usize,
x: &TVec<N, C>,
) -> TMat<N, R, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
let mut res = m.clone();
res.set_row(index, &x.transpose());
res

View File

@ -1,17 +1,23 @@
use na::{Real, DefaultAllocator};
use na::{DefaultAllocator, Real};
use traits::{Alloc, Dimension};
use aliases::TMat;
use traits::{Alloc, Dimension};
/// Fast matrix inverse for affine matrix.
pub fn affine_inverse<N: Real, D: Dimension>(m: TMat<N, D, D>) -> TMat<N, D, D>
where DefaultAllocator: Alloc<N, D, D> {
where
DefaultAllocator: Alloc<N, D, D>,
{
// FIXME: this should be optimized.
m.try_inverse().unwrap_or_else(TMat::<_, D, D>::zeros)
}
/// Compute the transpose of the inverse of a matrix.
pub fn inverse_transpose<N: Real, D: Dimension>(m: TMat<N, D, D>) -> TMat<N, D, D>
where DefaultAllocator: Alloc<N, D, D> {
m.try_inverse().unwrap_or_else(TMat::<_, D, D>::zeros).transpose()
where
DefaultAllocator: Alloc<N, D, D>,
{
m.try_inverse()
.unwrap_or_else(TMat::<_, D, D>::zeros)
.transpose()
}

View File

@ -1,17 +1,32 @@
//! (Reexported) Recommended features not specified by GLSL specification
//pub use self::bitfield::*;
pub use self::constants::{e, two_pi, euler, four_over_pi, golden_ratio, half_pi, ln_ln_two, ln_ten, ln_two, one, one_over_pi, one_over_root_two, one_over_two_pi, quarter_pi, root_five, root_half_pi, root_ln_four, root_pi, root_three, root_two, root_two_pi, third, three_over_two_pi, two_over_pi, two_over_root_pi, two_thirds, zero};
pub use self::constants::{
e, euler, four_over_pi, golden_ratio, half_pi, ln_ln_two, ln_ten, ln_two, one, one_over_pi,
one_over_root_two, one_over_two_pi, quarter_pi, root_five, root_half_pi, root_ln_four, root_pi,
root_three, root_two, root_two_pi, third, three_over_two_pi, two_over_pi, two_over_root_pi,
two_pi, two_thirds, zero,
};
//pub use self::integer::*;
pub use self::matrix_access::{column, row, set_column, set_row};
pub use self::matrix_inverse::{affine_inverse, inverse_transpose};
//pub use self::packing::*;
//pub use self::reciprocal::*;
//pub use self::round::*;
pub use self::type_ptr::{make_mat2, make_mat2x2, make_mat2x3, make_mat2x4, make_mat3, make_mat3x2, make_mat3x3, make_mat3x4, make_mat4, make_mat4x2, make_mat4x3, make_mat4x4, make_quat, make_vec1, make_vec2, make_vec3, make_vec4, value_ptr, value_ptr_mut, vec1_to_vec2, vec1_to_vec3, vec1_to_vec4, vec2_to_vec1, vec2_to_vec2, vec2_to_vec3, vec2_to_vec4, vec3_to_vec1, vec3_to_vec2, vec3_to_vec3, vec3_to_vec4, vec4_to_vec1, vec4_to_vec2, vec4_to_vec3, vec4_to_vec4, mat2_to_mat3, mat2_to_mat4, mat3_to_mat2, mat3_to_mat4, mat4_to_mat2, mat4_to_mat3};
pub use self::type_ptr::{
make_mat2, make_mat2x2, make_mat2x3, make_mat2x4, make_mat3, make_mat3x2, make_mat3x3,
make_mat3x4, make_mat4, make_mat4x2, make_mat4x3, make_mat4x4, make_quat, make_vec1, make_vec2,
make_vec3, make_vec4, mat2_to_mat3, mat2_to_mat4, mat3_to_mat2, mat3_to_mat4, mat4_to_mat2,
mat4_to_mat3, value_ptr, value_ptr_mut, vec1_to_vec2, vec1_to_vec3, vec1_to_vec4, vec2_to_vec1,
vec2_to_vec2, vec2_to_vec3, vec2_to_vec4, vec3_to_vec1, vec3_to_vec2, vec3_to_vec3,
vec3_to_vec4, vec4_to_vec1, vec4_to_vec2, vec4_to_vec3, vec4_to_vec4,
};
//pub use self::ulp::*;
pub use self::quaternion::{quat_cast, quat_euler_angles, quat_greater_than, quat_greater_than_equal, quat_less_than, quat_less_than_equal, quat_look_at, quat_look_at_lh, quat_look_at_rh, quat_pitch, quat_roll, quat_yaw};
pub use self::quaternion::{
quat_cast, quat_euler_angles, quat_greater_than, quat_greater_than_equal, quat_less_than,
quat_less_than_equal, quat_look_at, quat_look_at_lh, quat_look_at_rh, quat_pitch, quat_roll,
quat_yaw,
};
//mod bitfield;
mod constants;
@ -24,4 +39,4 @@ mod matrix_inverse;
//mod round;
mod type_ptr;
//mod ulp;
mod quaternion;
mod quaternion;

View File

@ -1,7 +1,6 @@
use na::{Real, U4, UnitQuaternion};
use aliases::{Qua, TVec, TVec3, TMat4};
use na::{Real, UnitQuaternion, U4};
use aliases::{Qua, TMat4, TVec, TVec3};
/// Euler angles of the quaternion `q` as (pitch, yaw, roll).
pub fn quat_euler_angles<N: Real>(x: &Qua<N>) -> TVec3<N> {

View File

@ -1,8 +1,10 @@
use na::{Scalar, Real, DefaultAllocator, Quaternion};
use na::{DefaultAllocator, Quaternion, Real, Scalar};
use traits::{Number, Alloc, Dimension};
use aliases::{Qua, TMat, TMat2, TMat3, TMat4, TVec1, TVec2, TVec3, TVec4,
TMat2x3, TMat2x4, TMat3x2, TMat3x4, TMat4x2, TMat4x3};
use aliases::{
Qua, TMat, TMat2, TMat2x3, TMat2x4, TMat3, TMat3x2, TMat3x4, TMat4, TMat4x2, TMat4x3, TVec1,
TVec2, TVec3, TVec4,
};
use traits::{Alloc, Dimension, Number};
/// Creates a 2x2 matrix from a slice arranged in column-major order.
pub fn make_mat2<N: Scalar>(ptr: &[N]) -> TMat2<N> {
@ -69,19 +71,12 @@ pub fn mat2_to_mat3<N: Number>(m: &TMat2<N>) -> TMat3<N> {
let _0 = N::zero();
let _1 = N::one();
TMat3::new(
m.m11, m.m12, _0,
m.m21, m.m22, _0,
_0, _0, _1
)
TMat3::new(m.m11, m.m12, _0, m.m21, m.m22, _0, _0, _0, _1)
}
/// Converts a 3x3 matrix to a 2x2 matrix.
pub fn mat3_to_mat2<N: Scalar>(m: &TMat3<N>) -> TMat2<N> {
TMat2::new(
m.m11, m.m12,
m.m21, m.m22
)
TMat2::new(m.m11, m.m12, m.m21, m.m22)
}
/// Converts a 3x3 matrix to a 4x4 matrix.
@ -90,19 +85,14 @@ pub fn mat3_to_mat4<N: Number>(m: &TMat3<N>) -> TMat4<N> {
let _1 = N::one();
TMat4::new(
m.m11, m.m12, m.m13, _0,
m.m21, m.m22, m.m23, _0,
m.m31, m.m32, m.m33, _0,
_0, _0, _0, _1,
m.m11, m.m12, m.m13, _0, m.m21, m.m22, m.m23, _0, m.m31, m.m32, m.m33, _0, _0, _0, _0, _1,
)
}
/// Converts a 4x4 matrix to a 3x3 matrix.
pub fn mat4_to_mat3<N: Scalar>(m: &TMat4<N>) -> TMat3<N> {
TMat3::new(
m.m11, m.m12, m.m13,
m.m21, m.m22, m.m23,
m.m31, m.m32, m.m33,
m.m11, m.m12, m.m13, m.m21, m.m22, m.m23, m.m31, m.m32, m.m33,
)
}
@ -112,19 +102,13 @@ pub fn mat2_to_mat4<N: Number>(m: &TMat2<N>) -> TMat4<N> {
let _1 = N::one();
TMat4::new(
m.m11, m.m12, _0, _0,
m.m21, m.m22, _0, _0,
_0, _0, _1, _0,
_0, _0, _0, _1,
m.m11, m.m12, _0, _0, m.m21, m.m22, _0, _0, _0, _0, _1, _0, _0, _0, _0, _1,
)
}
/// Converts a 4x4 matrix to a 2x2 matrix.
pub fn mat4_to_mat2<N: Scalar>(m: &TMat4<N>) -> TMat2<N> {
TMat2::new(
m.m11, m.m12,
m.m21, m.m22,
)
TMat2::new(m.m11, m.m12, m.m21, m.m22)
}
/// Creates a quaternion from a slice arranged as `[x, y, z, w]`.
@ -400,13 +384,16 @@ pub fn make_vec4<N: Scalar>(ptr: &[N]) -> TVec4<N> {
/// Converts a matrix or vector to a slice arranged in column-major order.
pub fn value_ptr<N: Scalar, R: Dimension, C: Dimension>(x: &TMat<N, R, C>) -> &[N]
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
x.as_slice()
}
/// Converts a matrix or vector to a mutable slice arranged in column-major order.
pub fn value_ptr_mut<N: Scalar, R: Dimension, C: Dimension>(x: &mut TMat<N, R, C>) -> &mut [N]
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
x.as_mut_slice()
}

View File

@ -1,7 +1,7 @@
use na::{self, DefaultAllocator};
use traits::{Number, Alloc, Dimension};
use aliases::TMat;
use traits::{Alloc, Dimension, Number};
/// The sum of every component of the given matrix or vector.
///
@ -22,7 +22,9 @@ use aliases::TMat;
/// * [`comp_min`](fn.comp_min.html)
/// * [`comp_mul`](fn.comp_mul.html)
pub fn comp_add<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.iter().fold(N::zero(), |x, y| x + *y)
}
@ -49,7 +51,9 @@ pub fn comp_add<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
/// * [`max3`](fn.max3.html)
/// * [`max4`](fn.max4.html)
pub fn comp_max<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.iter().fold(N::min_value(), |x, y| na::sup(&x, y))
}
@ -76,7 +80,9 @@ pub fn comp_max<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
/// * [`min3`](fn.min3.html)
/// * [`min4`](fn.min4.html)
pub fn comp_min<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.iter().fold(N::max_value(), |x, y| na::inf(&x, y))
}
@ -99,7 +105,9 @@ pub fn comp_min<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
/// * [`comp_max`](fn.comp_max.html)
/// * [`comp_min`](fn.comp_min.html)
pub fn comp_mul<N: Number, R: Dimension, C: Dimension>(m: &TMat<N, R, C>) -> N
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
m.iter().fold(N::one(), |x, y| x * *y)
}

View File

@ -1,7 +1,7 @@
use traits::Number;
use aliases::TVec2;
use traits::Number;
/// The 2D perpendicular product between two vectors.
pub fn cross2d<N: Number>(v: &TVec2<N>, u: &TVec2<N>) -> N {
v.perp(u)
}
}

View File

@ -1,5 +1,5 @@
use traits::Number;
use aliases::TVec3;
use traits::Number;
/// Returns `true` if `{a, b, c}` forms a left-handed trihedron.
///

View File

@ -1,5 +1,7 @@
use aliases::{
TMat2, TMat2x3, TMat2x4, TMat3, TMat3x2, TMat3x4, TMat4, TMat4x2, TMat4x3, TVec2, TVec3, TVec4,
};
use traits::Number;
use aliases::{TVec2, TVec3, TVec4, TMat2, TMat2x3, TMat2x4, TMat3, TMat3x2, TMat3x4, TMat4, TMat4x2, TMat4x3};
/// Builds a 2x2 diagonal matrix.
///

View File

@ -1,25 +1,37 @@
//! (Reexported) Experimental features not specified by GLSL specification.
pub use self::component_wise::{comp_add, comp_max, comp_min, comp_mul};
//pub use self::euler_angles::*;
pub use self::exterior_product::{cross2d};
pub use self::exterior_product::cross2d;
pub use self::handed_coordinate_space::{left_handed, right_handed};
pub use self::matrix_cross_product::{matrix_cross, matrix_cross3};
pub use self::matrix_operation::{diagonal2x2, diagonal2x3, diagonal2x4, diagonal3x2, diagonal3x3, diagonal3x4, diagonal4x2, diagonal4x3, diagonal4x4};
pub use self::matrix_operation::{
diagonal2x2, diagonal2x3, diagonal2x4, diagonal3x2, diagonal3x3, diagonal3x4, diagonal4x2,
diagonal4x3, diagonal4x4,
};
pub use self::norm::{distance2, l1_distance, l1_norm, l2_distance, l2_norm, length2, magnitude2};
pub use self::normal::{triangle_normal};
pub use self::normal::triangle_normal;
pub use self::normalize_dot::{fast_normalize_dot, normalize_dot};
pub use self::quaternion::{
mat3_to_quat, quat_cross_vec, quat_extract_real_component, quat_fast_mix, quat_identity,
quat_inv_cross_vec, quat_length2, quat_magnitude2, quat_rotate_vec, quat_rotate_vec3,
quat_rotation, quat_short_mix, quat_to_mat3, quat_to_mat4, to_quat,
};
pub use self::rotate_normalized_axis::{quat_rotate_normalized_axis, rotate_normalized_axis};
pub use self::rotate_vector::{orientation, rotate_vec2, rotate_vec3, rotate_vec4, rotate_x_vec4, rotate_x_vec3, rotate_y_vec4, rotate_y_vec3, rotate_z_vec4, rotate_z_vec3, slerp};
pub use self::transform::{rotation, scaling, translation, rotation2d, scaling2d, translation2d};
pub use self::transform2::{proj, proj2d, reflect, reflect2d, scale_bias, scale_bias_matrix, shear2d_x, shear_x, shear_y, shear2d_y, shear_z};
pub use self::rotate_vector::{
orientation, rotate_vec2, rotate_vec3, rotate_vec4, rotate_x_vec3, rotate_x_vec4,
rotate_y_vec3, rotate_y_vec4, rotate_z_vec3, rotate_z_vec4, slerp,
};
pub use self::transform::{rotation, rotation2d, scaling, scaling2d, translation, translation2d};
pub use self::transform2::{
proj, proj2d, reflect, reflect2d, scale_bias, scale_bias_matrix, shear2d_x, shear2d_y, shear_x,
shear_y, shear_z,
};
pub use self::transform2d::{rotate2d, scale2d, translate2d};
pub use self::vector_angle::{angle};
pub use self::vector_query::{are_collinear, are_collinear2d, are_orthogonal, is_comp_null, is_normalized, is_null};
pub use self::quaternion::{quat_to_mat3, quat_rotate_vec, quat_cross_vec, mat3_to_quat, quat_extract_real_component, quat_fast_mix, quat_inv_cross_vec, quat_length2, quat_magnitude2, quat_identity, quat_rotate_vec3, quat_rotation, quat_short_mix, quat_to_mat4, to_quat};
pub use self::vector_angle::angle;
pub use self::vector_query::{
are_collinear, are_collinear2d, are_orthogonal, is_comp_null, is_normalized, is_null,
};
mod component_wise;
//mod euler_angles;
@ -30,6 +42,7 @@ mod matrix_operation;
mod norm;
mod normal;
mod normalize_dot;
mod quaternion;
mod rotate_normalized_axis;
mod rotate_vector;
mod transform;
@ -37,4 +50,3 @@ mod transform2;
mod transform2d;
mod vector_angle;
mod vector_query;
mod quaternion;

View File

@ -1,7 +1,7 @@
use na::{Real, DefaultAllocator};
use na::{DefaultAllocator, Real};
use traits::{Alloc, Dimension};
use aliases::TVec;
use traits::{Alloc, Dimension};
/// The squared distance between two points.
///
@ -9,7 +9,9 @@ use aliases::TVec;
///
/// * [`distance`](fn.distance.html)
pub fn distance2<N: Real, D: Dimension>(p0: &TVec<N, D>, p1: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
(p1 - p0).norm_squared()
}
@ -21,7 +23,9 @@ pub fn distance2<N: Real, D: Dimension>(p0: &TVec<N, D>, p1: &TVec<N, D>) -> N
/// * [`l2_distance`](fn.l2_distance.html)
/// * [`l2_norm`](fn.l2_norm.html)
pub fn l1_distance<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
l1_norm(&(y - x))
}
@ -36,7 +40,9 @@ pub fn l1_distance<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
/// * [`l2_distance`](fn.l2_distance.html)
/// * [`l2_norm`](fn.l2_norm.html)
pub fn l1_norm<N: Real, D: Dimension>(v: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
::comp_add(&v.abs())
}
@ -55,7 +61,9 @@ pub fn l1_norm<N: Real, D: Dimension>(v: &TVec<N, D>) -> N
/// * [`magnitude`](fn.magnitude.html)
/// * [`magnitude2`](fn.magnitude2.html)
pub fn l2_distance<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
l2_norm(&(y - x))
}
@ -76,7 +84,9 @@ pub fn l2_distance<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
/// * [`magnitude`](fn.magnitude.html)
/// * [`magnitude2`](fn.magnitude2.html)
pub fn l2_norm<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.norm()
}
@ -92,7 +102,9 @@ pub fn l2_norm<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
/// * [`magnitude`](fn.magnitude.html)
/// * [`magnitude2`](fn.magnitude2.html)
pub fn length2<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.norm_squared()
}
@ -108,7 +120,9 @@ pub fn length2<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
/// * [`magnitude`](fn.magnitude.html)
/// * [`nalgebra::norm_squared`](../nalgebra/fn.norm_squared.html)
pub fn magnitude2<N: Real, D: Dimension>(x: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.norm_squared()
}

View File

@ -7,4 +7,4 @@ use aliases::TVec3;
/// The normal is computed as the normalized vector `cross(p2 - p1, p3 - p1)`.
pub fn triangle_normal<N: Real>(p1: &TVec3<N>, p2: &TVec3<N>, p3: &TVec3<N>) -> TVec3<N> {
(p2 - p1).cross(&(p3 - p1)).normalize()
}
}

View File

@ -1,7 +1,7 @@
use na::{Real, DefaultAllocator};
use na::{DefaultAllocator, Real};
use traits::{Dimension, Alloc};
use aliases::TVec;
use traits::{Alloc, Dimension};
/// The dot product of the normalized version of `x` and `y`.
///
@ -11,7 +11,9 @@ use aliases::TVec;
///
/// * [`normalize_dot`](fn.normalize_dot.html`)
pub fn fast_normalize_dot<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
// XXX: improve those.
x.normalize().dot(&y.normalize())
}
@ -22,7 +24,9 @@ pub fn fast_normalize_dot<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>)
///
/// * [`fast_normalize_dot`](fn.fast_normalize_dot.html`)
pub fn normalize_dot<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
// XXX: improve those.
x.normalize().dot(&y.normalize())
}

View File

@ -1,4 +1,4 @@
use na::{Real, Unit, Rotation3, UnitQuaternion, U3};
use na::{Real, Rotation3, Unit, UnitQuaternion, U3};
use aliases::{Qua, TMat3, TMat4, TVec3, TVec4};
@ -19,7 +19,9 @@ pub fn quat_extract_real_component<N: Real>(q: &Qua<N>) -> N {
/// Normalized linear interpolation between two quaternions.
pub fn quat_fast_mix<N: Real>(x: &Qua<N>, y: &Qua<N>, a: N) -> Qua<N> {
Unit::new_unchecked(*x).nlerp(&Unit::new_unchecked(*y), a).unwrap()
Unit::new_unchecked(*x)
.nlerp(&Unit::new_unchecked(*y), a)
.unwrap()
}
//pub fn quat_intermediate<N: Real>(prev: &Qua<N>, curr: &Qua<N>, next: &Qua<N>) -> Qua<N> {
@ -54,12 +56,16 @@ pub fn quat_rotate_vec<N: Real>(q: &Qua<N>, v: &TVec4<N>) -> TVec4<N> {
/// The rotation required to align `orig` to `dest`.
pub fn quat_rotation<N: Real>(orig: &TVec3<N>, dest: &TVec3<N>) -> Qua<N> {
UnitQuaternion::rotation_between(orig, dest).unwrap_or_else(UnitQuaternion::identity).unwrap()
UnitQuaternion::rotation_between(orig, dest)
.unwrap_or_else(UnitQuaternion::identity)
.unwrap()
}
/// The spherical linear interpolation between two quaternions.
pub fn quat_short_mix<N: Real>(x: &Qua<N>, y: &Qua<N>, a: N) -> Qua<N> {
Unit::new_normalize(*x).slerp(&Unit::new_normalize(*y), a).unwrap()
Unit::new_normalize(*x)
.slerp(&Unit::new_normalize(*y), a)
.unwrap()
}
//pub fn quat_squad<N: Real>(q1: &Qua<N>, q2: &Qua<N>, s1: &Qua<N>, s2: &Qua<N>, h: N) -> Qua<N> {
@ -68,7 +74,9 @@ pub fn quat_short_mix<N: Real>(x: &Qua<N>, y: &Qua<N>, a: N) -> Qua<N> {
/// Converts a quaternion to a rotation matrix.
pub fn quat_to_mat3<N: Real>(x: &Qua<N>) -> TMat3<N> {
UnitQuaternion::new_unchecked(*x).to_rotation_matrix().unwrap()
UnitQuaternion::new_unchecked(*x)
.to_rotation_matrix()
.unwrap()
}
/// Converts a quaternion to a rotation matrix in homogenous coordinates.
@ -87,4 +95,3 @@ pub fn to_quat<N: Real>(x: &TMat4<N>) -> Qua<N> {
let rot = x.fixed_slice::<U3, U3>(0, 0).into_owned();
mat3_to_quat(&rot)
}

View File

@ -1,6 +1,6 @@
use na::{Real, Rotation3, Unit, UnitComplex};
use aliases::{TVec2, TVec3, TVec4, TMat4};
use aliases::{TMat4, TVec2, TVec3, TVec4};
/// Build the rotation matrix needed to align `normal` and `up`.
pub fn orientation<N: Real>(normal: &TVec3<N>, up: &TVec3<N>) -> TMat4<N> {
@ -58,5 +58,7 @@ pub fn rotate_z_vec4<N: Real>(v: &TVec4<N>, angle: N) -> TVec4<N> {
/// Computes a spherical linear interpolation between the vectors `x` and `y` assumed to be normalized.
pub fn slerp<N: Real>(x: &TVec3<N>, y: &TVec3<N>, a: N) -> TVec3<N> {
Unit::new_unchecked(*x).slerp(&Unit::new_unchecked(*y), a).unwrap()
Unit::new_unchecked(*x)
.slerp(&Unit::new_unchecked(*y), a)
.unwrap()
}

View File

@ -1,7 +1,7 @@
use na::{Real, Unit, Rotation2, Rotation3};
use na::{Real, Rotation2, Rotation3, Unit};
use aliases::{TMat3, TMat4, TVec2, TVec3};
use traits::Number;
use aliases::{TVec3, TVec2, TMat3, TMat4};
/// A rotation 4 * 4 matrix created from an axis of 3 scalars and an angle expressed in radians.
///
@ -42,7 +42,6 @@ pub fn translation<N: Number>(v: &TVec3<N>) -> TMat4<N> {
TMat4::new_translation(v)
}
/// A rotation 3 * 3 matrix created from an angle expressed in radians.
///
/// # See also:

View File

@ -1,7 +1,7 @@
use na::{U2, U3};
use aliases::{TMat3, TMat4, TVec2, TVec3};
use traits::Number;
use aliases::{TVec2, TVec3, TMat3, TMat4};
/// Build planar projection matrix along normal axis and right-multiply it to `m`.
pub fn proj2d<N: Number>(m: &TMat3<N>, normal: &TVec2<N>) -> TMat3<N> {
@ -57,10 +57,7 @@ pub fn scale_bias_matrix<N: Number>(scale: N, bias: N) -> TMat4<N> {
let _1 = N::one();
TMat4::new(
scale, _0, _0, bias,
_0, scale, _0, bias,
_0, _0, scale, bias,
_0, _0, _0, _1,
scale, _0, _0, bias, _0, scale, _0, bias, _0, _0, scale, bias, _0, _0, _0, _1,
)
}
@ -74,11 +71,7 @@ pub fn shear2d_x<N: Number>(m: &TMat3<N>, y: N) -> TMat3<N> {
let _0 = N::zero();
let _1 = N::one();
let shear = TMat3::new(
_1, y, _0,
_0, _1, _0,
_0, _0, _1
);
let shear = TMat3::new(_1, y, _0, _0, _1, _0, _0, _0, _1);
m * shear
}
@ -86,12 +79,7 @@ pub fn shear2d_x<N: Number>(m: &TMat3<N>, y: N) -> TMat3<N> {
pub fn shear_x<N: Number>(m: &TMat4<N>, y: N, z: N) -> TMat4<N> {
let _0 = N::zero();
let _1 = N::one();
let shear = TMat4::new(
_1, _0, _0, _0,
y, _1, _0, _0,
z, _0, _1, _0,
_0, _0, _0, _1,
);
let shear = TMat4::new(_1, _0, _0, _0, y, _1, _0, _0, z, _0, _1, _0, _0, _0, _0, _1);
m * shear
}
@ -101,11 +89,7 @@ pub fn shear2d_y<N: Number>(m: &TMat3<N>, x: N) -> TMat3<N> {
let _0 = N::zero();
let _1 = N::one();
let shear = TMat3::new(
_1, _0, _0,
x, _1, _0,
_0, _0, _1
);
let shear = TMat3::new(_1, _0, _0, x, _1, _0, _0, _0, _1);
m * shear
}
@ -113,12 +97,7 @@ pub fn shear2d_y<N: Number>(m: &TMat3<N>, x: N) -> TMat3<N> {
pub fn shear_y<N: Number>(m: &TMat4<N>, x: N, z: N) -> TMat4<N> {
let _0 = N::zero();
let _1 = N::one();
let shear = TMat4::new(
_1, x, _0, _0,
_0, _1, _0, _0,
_0, z, _1, _0,
_0, _0, _0, _1,
);
let shear = TMat4::new(_1, x, _0, _0, _0, _1, _0, _0, _0, z, _1, _0, _0, _0, _0, _1);
m * shear
}
@ -127,12 +106,7 @@ pub fn shear_y<N: Number>(m: &TMat4<N>, x: N, z: N) -> TMat4<N> {
pub fn shear_z<N: Number>(m: &TMat4<N>, x: N, y: N) -> TMat4<N> {
let _0 = N::zero();
let _1 = N::one();
let shear = TMat4::new(
_1, _0, x, _0,
_0, _1, y, _0,
_0, _0, _1, _0,
_0, _0, _0, _1,
);
let shear = TMat4::new(_1, _0, x, _0, _0, _1, y, _0, _0, _0, _1, _0, _0, _0, _0, _1);
m * shear
}

View File

@ -1,7 +1,7 @@
use na::{Real, UnitComplex};
use traits::Number;
use aliases::{TMat3, TVec2};
use traits::Number;
/// Builds a 2D rotation matrix from an angle and right-multiply it to `m`.
///

View File

@ -1,12 +1,13 @@
use na::{DefaultAllocator, Real};
use traits::{Dimension, Alloc};
use aliases::TVec;
use traits::{Alloc, Dimension};
/// The angle between two vectors.
pub fn angle<N: Real, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> N
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.angle(y)
}

View File

@ -1,7 +1,7 @@
use na::{Real, DefaultAllocator};
use na::{DefaultAllocator, Real};
use traits::{Number, Dimension, Alloc};
use aliases::{TVec, TVec2, TVec3};
use traits::{Alloc, Dimension, Number};
/// Returns `true` if two vectors are collinear (up to an epsilon).
///
@ -23,7 +23,9 @@ pub fn are_collinear2d<N: Number>(v0: &TVec2<N>, v1: &TVec2<N>, epsilon: N) -> b
/// Returns `true` if two vectors are orthogonal (up to an epsilon).
pub fn are_orthogonal<N: Number, D: Dimension>(v0: &TVec<N, D>, v1: &TVec<N, D>, epsilon: N) -> bool
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
abs_diff_eq!(v0.dot(v1), N::zero(), epsilon = epsilon)
}
@ -34,18 +36,24 @@ pub fn are_orthogonal<N: Number, D: Dimension>(v0: &TVec<N, D>, v1: &TVec<N, D>,
/// Returns `true` if all the components of `v` are zero (up to an epsilon).
pub fn is_comp_null<N: Number, D: Dimension>(v: &TVec<N, D>, epsilon: N) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
v.map(|x| abs_diff_eq!(x, N::zero(), epsilon = epsilon))
}
/// Returns `true` if `v` has a magnitude of 1 (up to an epsilon).
pub fn is_normalized<N: Real, D: Dimension>(v: &TVec<N, D>, epsilon: N) -> bool
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
abs_diff_eq!(v.norm_squared(), N::one(), epsilon = epsilon * epsilon)
}
/// Returns `true` if `v` is zero (up to an epsilon).
pub fn is_null<N: Number, D: Dimension>(v: &TVec<N, D>, epsilon: N) -> bool
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
abs_diff_eq!(*v, TVec::<N, D>::zeros(), epsilon = epsilon)
}

View File

@ -1,114 +1,114 @@
/*! # nalgebra-glm nalgebra in _easy mode_
**nalgebra-glm** is a GLM-like interface for the **nalgebra** general-purpose linear algebra library.
[GLM](https://glm.g-truc.net) itself is a popular C++ linear algebra library essentially targeting computer graphics. Therefore
**nalgebra-glm** draws inspiration from GLM to define a nice and easy-to-use API for simple graphics application.
**nalgebra-glm** is a GLM-like interface for the **nalgebra** general-purpose linear algebra library.
[GLM](https://glm.g-truc.net) itself is a popular C++ linear algebra library essentially targeting computer graphics. Therefore
**nalgebra-glm** draws inspiration from GLM to define a nice and easy-to-use API for simple graphics application.
All the types of **nalgebra-glm** are aliases of types from **nalgebra**. Therefore there is a complete and
seamless inter-operability between both.
All the types of **nalgebra-glm** are aliases of types from **nalgebra**. Therefore there is a complete and
seamless inter-operability between both.
## Getting started
First of all, you should start by taking a look at the official [GLM API documentation](http://glm.g-truc.net/0.9.9/api/index.html)
since **nalgebra-glm** implements a large subset of it. To use **nalgebra-glm** to your project, you
should add it as a dependency to your `Crates.toml`:
## Getting started
First of all, you should start by taking a look at the official [GLM API documentation](http://glm.g-truc.net/0.9.9/api/index.html)
since **nalgebra-glm** implements a large subset of it. To use **nalgebra-glm** to your project, you
should add it as a dependency to your `Crates.toml`:
```toml
[dependencies]
nalgebra-glm = "0.1"
```
```toml
[dependencies]
nalgebra-glm = "0.1"
```
Then, you should add an `extern crate` statement to your `lib.rs` or `main.rs` file. It is **strongly
recommended** to add a crate alias to `glm` as well so that you will be able to call functions of
**nalgebra-glm** using the module prefix `glm::`. For example you will write `glm::rotate(...)` instead
of the more verbose `nalgebra_glm::rotate(...)`:
Then, you should add an `extern crate` statement to your `lib.rs` or `main.rs` file. It is **strongly
recommended** to add a crate alias to `glm` as well so that you will be able to call functions of
**nalgebra-glm** using the module prefix `glm::`. For example you will write `glm::rotate(...)` instead
of the more verbose `nalgebra_glm::rotate(...)`:
```rust
extern crate nalgebra_glm as glm;
```
```rust
extern crate nalgebra_glm as glm;
```
## Features overview
**nalgebra-glm** supports most linear-algebra related features of the C++ GLM library. Mathematically
speaking, it supports all the common transformations like rotations, translations, scaling, shearing,
and projections but operating in homogeneous coordinates. This means all the 2D transformations are
expressed as 3x3 matrices, and all the 3D transformations as 4x4 matrices. This is less computationally-efficient
and memory-efficient than nalgebra's [transformation types](https://www.nalgebra.org/points_and_transformations/#transformations),
but this has the benefit of being simpler to use.
### Main differences compared to GLM
While **nalgebra-glm** follows the feature line of the C++ GLM library, quite a few differences
remain and they are mostly syntactic. The main ones are:
* All function names use `snake_case`, which is the Rust convention.
* All type names use `CamelCase`, which is the Rust convention.
* All function arguments, except for scalars, are all passed by-reference.
* The most generic vector and matrix types are [`TMat`](type.TMat.html) and [`TVec`](type.TVec.html) instead of `mat` and `vec`.
* Some feature are not yet implemented and should be added in the future. In particular, no packing
functions are available.
* A few features are not implemented and will never be. This includes functions related to color
spaces, and closest points computations. Other crates should be used for those. For example, closest
points computation can be handled by the [ncollide](https://ncollide.org) project.
## Features overview
**nalgebra-glm** supports most linear-algebra related features of the C++ GLM library. Mathematically
speaking, it supports all the common transformations like rotations, translations, scaling, shearing,
and projections but operating in homogeneous coordinates. This means all the 2D transformations are
expressed as 3x3 matrices, and all the 3D transformations as 4x4 matrices. This is less computationally-efficient
and memory-efficient than nalgebra's [transformation types](https://www.nalgebra.org/points_and_transformations/#transformations),
but this has the benefit of being simpler to use.
### Main differences compared to GLM
While **nalgebra-glm** follows the feature line of the C++ GLM library, quite a few differences
remain and they are mostly syntactic. The main ones are:
* All function names use `snake_case`, which is the Rust convention.
* All type names use `CamelCase`, which is the Rust convention.
* All function arguments, except for scalars, are all passed by-reference.
* The most generic vector and matrix types are [`TMat`](type.TMat.html) and [`TVec`](type.TVec.html) instead of `mat` and `vec`.
* Some feature are not yet implemented and should be added in the future. In particular, no packing
functions are available.
* A few features are not implemented and will never be. This includes functions related to color
spaces, and closest points computations. Other crates should be used for those. For example, closest
points computation can be handled by the [ncollide](https://ncollide.org) project.
In addition, because Rust does not allows function overloading, all functions must be given a unique name.
Here are a few rules chosen arbitrarily for **nalgebra-glm**:
* Functions operating in 2d will usually end with the `2d` suffix, e.g., [`glm::rotate2d`](fn.rotate2d.html) is for 2D while [`glm::rotate`](fn.rotate.html) is for 3D.
* Functions operating on vectors will often end with the `_vec` suffix, possibly followed by the dimension of vector, e.g., [`glm::rotate_vec2`](fn.rotate_vec2.html).
* Every function related to quaternions start with the `quat_` prefix, e.g., [`glm::quat_dot(q1, q2)`](fn.quat_dot.html).
* All the conversion functions have unique names as described [below](#conversions).
### Vector and matrix construction
Vectors, matrices, and quaternions can be constructed using several approaches:
* Using functions with the same name as their type in lower-case. For example [`glm::vec3(x, y, z)`](fn.vec3.html) will create a 3D vector.
* Using the `::new` constructor. For example [`Vec3::new(x, y, z)`](../nalgebra/base/type.MatrixMN.html#method.new-27) will create a 3D vector.
* Using the functions prefixed by `make_` to build a vector a matrix from a slice. For example [`glm::make_vec3(&[x, y, z])`](fn.make_vec3.html) will create a 3D vector.
Keep in mind that constructing a matrix using this type of functions require its components to be arranged in column-major order on the slice.
* Using a geometric construction function. For example [`glm::rotation(angle, axis)`](fn.rotation.html) will build a 4x4 homogeneous rotation matrix from an angle (in radians) and an axis.
* Using swizzling and conversions as described in the next sections.
### Swizzling
Vector swizzling is a native feature of **nalgebra** itself. Therefore, you can use it with all
the vectors of **nalgebra-glm** as well. Swizzling is supported as methods and works only up to
dimension 3, i.e., you can only refer to the components `x`, `y` and `z` and can only create a
2D or 3D vector using this technique. Here is some examples, assuming `v` is a vector with float
components here:
* `v.xx()` is equivalent to `glm::vec2(v.x, v.x)` and to `Vec2::new(v.x, v.x)`.
* `v.zx()` is equivalent to `glm::vec2(v.z, v.x)` and to `Vec2::new(v.z, v.x)`.
* `v.yxz()` is equivalent to `glm::vec3(v.y, v.x, v.z)` and to `Vec3::new(v.y, v.x, v.z)`.
* `v.zzy()` is equivalent to `glm::vec3(v.z, v.z, v.y)` and to `Vec3::new(v.z, v.z, v.y)`.
In addition, because Rust does not allows function overloading, all functions must be given a unique name.
Here are a few rules chosen arbitrarily for **nalgebra-glm**:
* Functions operating in 2d will usually end with the `2d` suffix, e.g., [`glm::rotate2d`](fn.rotate2d.html) is for 2D while [`glm::rotate`](fn.rotate.html) is for 3D.
* Functions operating on vectors will often end with the `_vec` suffix, possibly followed by the dimension of vector, e.g., [`glm::rotate_vec2`](fn.rotate_vec2.html).
* Every function related to quaternions start with the `quat_` prefix, e.g., [`glm::quat_dot(q1, q2)`](fn.quat_dot.html).
* All the conversion functions have unique names as described [below](#conversions).
### Vector and matrix construction
Vectors, matrices, and quaternions can be constructed using several approaches:
* Using functions with the same name as their type in lower-case. For example [`glm::vec3(x, y, z)`](fn.vec3.html) will create a 3D vector.
* Using the `::new` constructor. For example [`Vec3::new(x, y, z)`](../nalgebra/base/type.MatrixMN.html#method.new-27) will create a 3D vector.
* Using the functions prefixed by `make_` to build a vector a matrix from a slice. For example [`glm::make_vec3(&[x, y, z])`](fn.make_vec3.html) will create a 3D vector.
Keep in mind that constructing a matrix using this type of functions require its components to be arranged in column-major order on the slice.
* Using a geometric construction function. For example [`glm::rotation(angle, axis)`](fn.rotation.html) will build a 4x4 homogeneous rotation matrix from an angle (in radians) and an axis.
* Using swizzling and conversions as described in the next sections.
### Swizzling
Vector swizzling is a native feature of **nalgebra** itself. Therefore, you can use it with all
the vectors of **nalgebra-glm** as well. Swizzling is supported as methods and works only up to
dimension 3, i.e., you can only refer to the components `x`, `y` and `z` and can only create a
2D or 3D vector using this technique. Here is some examples, assuming `v` is a vector with float
components here:
* `v.xx()` is equivalent to `glm::vec2(v.x, v.x)` and to `Vec2::new(v.x, v.x)`.
* `v.zx()` is equivalent to `glm::vec2(v.z, v.x)` and to `Vec2::new(v.z, v.x)`.
* `v.yxz()` is equivalent to `glm::vec3(v.y, v.x, v.z)` and to `Vec3::new(v.y, v.x, v.z)`.
* `v.zzy()` is equivalent to `glm::vec3(v.z, v.z, v.y)` and to `Vec3::new(v.z, v.z, v.y)`.
Any combination of two or three components picked among `x`, `y`, and `z` will work.
### Conversions
It is often useful to convert one algebraic type to another. There are two main approaches for converting
between types in `nalgebra-glm`:
* Using function with the form `type1_to_type2` in order to convert an instance of `type1` into an instance of `type2`.
For example [`glm::mat3_to_mat4(m)`](fn.mat3_to_mat4.html) will convert the 3x3 matrix `m` to a 4x4 matrix by appending one column on the right
and one row on the left. Those now row and columns are filled with 0 except for the diagonal element which is set to 1.
* Using one of the [`convert`](fn.convert.html), [`try_convert`](fn.try_convert.html), or [`convert_unchecked`](fn.convert_unchecked.html) functions.
These functions are directly re-exported from nalgebra and are extremely versatile:
1. The `convert` function can convert any type (especially geometric types from nalgebra like `Isometry3`) into another algebraic type which is equivalent but more general. For example,
`let sim: Similarity3<_> = na::convert(isometry)` will convert an `Isometry3` into a `Similarity3`.
In addition, `let mat: Mat4 = glm::convert(isometry)` will convert an `Isometry3` to a 4x4 matrix. This will also convert the scalar types,
therefore: `let mat: DMat4 = glm::convert(m)` where `m: Mat4` will work. However, conversion will not work the other way round: you
can't convert a `Matrix4` to an `Isometry3` using `glm::convert` because that could cause unexpected results if the matrix does
not complies to the requirements of the isometry.
2. If you need this kind of conversions anyway, you can use `try_convert` which will test if the object being converted complies with the algebraic requirements of the target type.
This will return `None` if the requirements are not satisfied.
3. The `convert_unchecked` will ignore those tests and always perform the conversion, even if that breaks the invariants of the target type.
This must be used with care! This is actually the recommended method to convert between homogeneous transformations generated by `nalgebra-glm` and
specific transformation types from **nalgebra** like `Isometry3`. Just be careful you know your conversions make sense.
Any combination of two or three components picked among `x`, `y`, and `z` will work.
### Conversions
It is often useful to convert one algebraic type to another. There are two main approaches for converting
between types in `nalgebra-glm`:
* Using function with the form `type1_to_type2` in order to convert an instance of `type1` into an instance of `type2`.
For example [`glm::mat3_to_mat4(m)`](fn.mat3_to_mat4.html) will convert the 3x3 matrix `m` to a 4x4 matrix by appending one column on the right
and one row on the left. Those now row and columns are filled with 0 except for the diagonal element which is set to 1.
* Using one of the [`convert`](fn.convert.html), [`try_convert`](fn.try_convert.html), or [`convert_unchecked`](fn.convert_unchecked.html) functions.
These functions are directly re-exported from nalgebra and are extremely versatile:
1. The `convert` function can convert any type (especially geometric types from nalgebra like `Isometry3`) into another algebraic type which is equivalent but more general. For example,
`let sim: Similarity3<_> = na::convert(isometry)` will convert an `Isometry3` into a `Similarity3`.
In addition, `let mat: Mat4 = glm::convert(isometry)` will convert an `Isometry3` to a 4x4 matrix. This will also convert the scalar types,
therefore: `let mat: DMat4 = glm::convert(m)` where `m: Mat4` will work. However, conversion will not work the other way round: you
can't convert a `Matrix4` to an `Isometry3` using `glm::convert` because that could cause unexpected results if the matrix does
not complies to the requirements of the isometry.
2. If you need this kind of conversions anyway, you can use `try_convert` which will test if the object being converted complies with the algebraic requirements of the target type.
This will return `None` if the requirements are not satisfied.
3. The `convert_unchecked` will ignore those tests and always perform the conversion, even if that breaks the invariants of the target type.
This must be used with care! This is actually the recommended method to convert between homogeneous transformations generated by `nalgebra-glm` and
specific transformation types from **nalgebra** like `Isometry3`. Just be careful you know your conversions make sense.
### Should I use nalgebra or nalgebra-glm?
Well that depends on your tastes and your background. **nalgebra** is more powerful overall since it allows stronger typing,
and goes much further than simple computer graphics math. However, has a bit of a learning curve for
those not used to the abstract mathematical concepts for transformations. **nalgebra-glm** however
have more straightforward functions and benefit from the various tutorials existing on the internet
for the original C++ GLM library.
### Should I use nalgebra or nalgebra-glm?
Well that depends on your tastes and your background. **nalgebra** is more powerful overall since it allows stronger typing,
and goes much further than simple computer graphics math. However, has a bit of a learning curve for
those not used to the abstract mathematical concepts for transformations. **nalgebra-glm** however
have more straightforward functions and benefit from the various tutorials existing on the internet
for the original C++ GLM library.
Overall, if you are already used to the C++ GLM library, or to working with homogeneous coordinates (like 4D
matrices for 3D transformations), then you will have more success with **nalgebra-glm**. If on the other
hand you prefer more rigorous treatments of transformations, with type-level restrictions, then go for **nalgebra**.
If you need dynamically-sized matrices, you should go for **nalgebra** as well.
Overall, if you are already used to the C++ GLM library, or to working with homogeneous coordinates (like 4D
matrices for 3D transformations), then you will have more success with **nalgebra-glm**. If on the other
hand you prefer more rigorous treatments of transformations, with type-level restrictions, then go for **nalgebra**.
If you need dynamically-sized matrices, you should go for **nalgebra** as well.
Keep in mind that **nalgebra-glm** is just a different API for **nalgebra**. So you can very well use both
and benefit from both their advantages: use **nalgebra-glm** when mathematical rigor is not that important,
and **nalgebra** itself when you need more expressive types, and more powerful linear algebra operations like
matrix factorizations and slicing. Just remember that all the **nalgebra-glm** types are just aliases to **nalgebra** types,
and keep in mind it is possible to convert, e.g., an `Isometry3` to a `Mat4` and vice-versa (see the [conversions section](#conversions)).
*/
Keep in mind that **nalgebra-glm** is just a different API for **nalgebra**. So you can very well use both
and benefit from both their advantages: use **nalgebra-glm** when mathematical rigor is not that important,
and **nalgebra** itself when you need more expressive types, and more powerful linear algebra operations like
matrix factorizations and slicing. Just remember that all the **nalgebra-glm** types are just aliases to **nalgebra** types,
and keep in mind it is possible to convert, e.g., an `Isometry3` to a `Mat4` and vice-versa (see the [conversions section](#conversions)).
*/
#![doc(html_favicon_url = "http://nalgebra.org/img/favicon.ico")]
@ -119,68 +119,83 @@ extern crate alga;
extern crate nalgebra as na;
pub use aliases::*;
pub use common::{
abs, ceil, clamp, clamp_scalar, clamp_vec, float_bits_to_int, float_bits_to_int_vec,
float_bits_to_uint, float_bits_to_uint_vec, floor, fract, int_bits_to_float,
int_bits_to_float_vec, lerp, lerp_scalar, lerp_vec, mix, mix_scalar, mix_vec, modf, modf_vec,
round, sign, smoothstep, step, step_scalar, step_vec, trunc, uint_bits_to_float,
uint_bits_to_float_scalar,
};
pub use constructors::*;
pub use common::{abs, ceil, clamp, clamp_scalar, clamp_vec, float_bits_to_int, float_bits_to_int_vec, float_bits_to_uint, float_bits_to_uint_vec, floor, fract, int_bits_to_float, int_bits_to_float_vec, mix, modf, modf_vec, round, sign, smoothstep, step, step_scalar, step_vec, trunc, uint_bits_to_float, uint_bits_to_float_scalar};
pub use geometric::{reflect_vec, cross, distance, dot, faceforward, length, magnitude, normalize, refract_vec};
pub use matrix::{transpose, determinant, inverse, matrix_comp_mult, outer_product};
pub use traits::{Dimension, Number, Alloc};
pub use trigonometric::{acos, acosh, asin, asinh, atan, atan2, atanh, cos, cosh, degrees, radians, sin, sinh, tan, tanh};
pub use vector_relational::{all, any, equal, greater_than, greater_than_equal, less_than, less_than_equal, not, not_equal};
pub use exponential::{exp, exp2, inversesqrt, log, log2, pow, sqrt};
pub use geometric::{
cross, distance, dot, faceforward, length, magnitude, normalize, reflect_vec, refract_vec,
};
pub use matrix::{determinant, inverse, matrix_comp_mult, outer_product, transpose};
pub use traits::{Alloc, Dimension, Number};
pub use trigonometric::{
acos, acosh, asin, asinh, atan, atan2, atanh, cos, cosh, degrees, radians, sin, sinh, tan, tanh,
};
pub use vector_relational::{
all, any, equal, greater_than, greater_than_equal, less_than, less_than_equal, not, not_equal,
};
pub use gtx::{
comp_add, comp_max, comp_min, comp_mul,
cross2d,
left_handed, right_handed,
matrix_cross, matrix_cross3,
diagonal2x2, diagonal2x3, diagonal2x4, diagonal3x2, diagonal3x3, diagonal3x4, diagonal4x2, diagonal4x3, diagonal4x4,
distance2, l1_distance, l1_norm, l2_distance, l2_norm, length2, magnitude2,
triangle_normal,
fast_normalize_dot, normalize_dot,
quat_rotate_normalized_axis, rotate_normalized_axis,
orientation, rotate_vec2, rotate_vec3, rotate_vec4, rotate_x_vec4, rotate_x_vec3, rotate_y_vec4, rotate_y_vec3, rotate_z_vec4, rotate_z_vec3, slerp,
rotation, scaling, translation, rotation2d, scaling2d, translation2d,
proj, proj2d, reflect, reflect2d, scale_bias, scale_bias_matrix, shear2d_x, shear_x, shear_y, shear2d_y, shear_z,
rotate2d, scale2d, translate2d,
angle,
are_collinear, are_collinear2d, are_orthogonal, is_comp_null, is_normalized, is_null,
quat_to_mat3, quat_rotate_vec, quat_cross_vec, mat3_to_quat, quat_extract_real_component, quat_fast_mix, quat_inv_cross_vec, quat_length2, quat_magnitude2, quat_identity, quat_rotate_vec3, quat_rotation, quat_short_mix, quat_to_mat4, to_quat
pub use ext::{
epsilon, equal_columns, equal_columns_eps, equal_columns_eps_vec, equal_eps, equal_eps_vec,
identity, look_at, look_at_lh, look_at_rh, max, max2, max3, max3_scalar, max4, max4_scalar,
min, min2, min3, min3_scalar, min4, min4_scalar, not_equal_columns, not_equal_columns_eps,
not_equal_columns_eps_vec, not_equal_eps, not_equal_eps_vec, ortho, perspective, pi,
pick_matrix, project, project_no, project_zo, quat_angle, quat_angle_axis, quat_axis,
quat_conjugate, quat_cross, quat_dot, quat_equal, quat_equal_eps, quat_exp, quat_inverse,
quat_length, quat_lerp, quat_log, quat_magnitude, quat_normalize, quat_not_equal,
quat_not_equal_eps, quat_pow, quat_rotate, quat_slerp, rotate, rotate_x, rotate_y, rotate_z,
scale, translate, unproject, unproject_no, unproject_zo,
};
pub use gtc::{
e, two_pi, euler, four_over_pi, golden_ratio, half_pi, ln_ln_two, ln_ten, ln_two, one, one_over_pi, one_over_root_two, one_over_two_pi, quarter_pi, root_five, root_half_pi, root_ln_four, root_pi, root_three, root_two, root_two_pi, third, three_over_two_pi, two_over_pi, two_over_root_pi, two_thirds, zero,
column, row, set_column, set_row,
affine_inverse, inverse_transpose,
make_mat2, make_mat2x2, make_mat2x3, make_mat2x4, make_mat3, make_mat3x2, make_mat3x3, make_mat3x4, make_mat4, make_mat4x2, make_mat4x3, make_mat4x4, make_quat, make_vec1, make_vec2, make_vec3, make_vec4, value_ptr, value_ptr_mut, vec1_to_vec2, vec1_to_vec3, vec1_to_vec4, vec2_to_vec1, vec2_to_vec2, vec2_to_vec3, vec2_to_vec4, vec3_to_vec1, vec3_to_vec2, vec3_to_vec3, vec3_to_vec4, vec4_to_vec1, vec4_to_vec2, vec4_to_vec3, vec4_to_vec4, mat2_to_mat3, mat2_to_mat4, mat3_to_mat2, mat3_to_mat4, mat4_to_mat2, mat4_to_mat3,
quat_cast, quat_euler_angles, quat_greater_than, quat_greater_than_equal, quat_less_than, quat_less_than_equal, quat_look_at, quat_look_at_lh, quat_look_at_rh, quat_pitch, quat_roll, quat_yaw
affine_inverse, column, e, euler, four_over_pi, golden_ratio, half_pi, inverse_transpose,
ln_ln_two, ln_ten, ln_two, make_mat2, make_mat2x2, make_mat2x3, make_mat2x4, make_mat3,
make_mat3x2, make_mat3x3, make_mat3x4, make_mat4, make_mat4x2, make_mat4x3, make_mat4x4,
make_quat, make_vec1, make_vec2, make_vec3, make_vec4, mat2_to_mat3, mat2_to_mat4,
mat3_to_mat2, mat3_to_mat4, mat4_to_mat2, mat4_to_mat3, one, one_over_pi, one_over_root_two,
one_over_two_pi, quarter_pi, quat_cast, quat_euler_angles, quat_greater_than,
quat_greater_than_equal, quat_less_than, quat_less_than_equal, quat_look_at, quat_look_at_lh,
quat_look_at_rh, quat_pitch, quat_roll, quat_yaw, root_five, root_half_pi, root_ln_four,
root_pi, root_three, root_two, root_two_pi, row, set_column, set_row, third, three_over_two_pi,
two_over_pi, two_over_root_pi, two_pi, two_thirds, value_ptr, value_ptr_mut, vec1_to_vec2,
vec1_to_vec3, vec1_to_vec4, vec2_to_vec1, vec2_to_vec2, vec2_to_vec3, vec2_to_vec4,
vec3_to_vec1, vec3_to_vec2, vec3_to_vec3, vec3_to_vec4, vec4_to_vec1, vec4_to_vec2,
vec4_to_vec3, vec4_to_vec4, zero,
};
pub use ext::{
ortho, perspective,
pick_matrix, project, project_no, project_zo, unproject, unproject_no, unproject_zo,
equal_columns, equal_columns_eps, equal_columns_eps_vec, not_equal_columns, not_equal_columns_eps, not_equal_columns_eps_vec,
identity, look_at, look_at_lh, rotate, scale, look_at_rh, translate, rotate_x, rotate_y, rotate_z,
max3_scalar, max4_scalar, min3_scalar, min4_scalar,
epsilon, pi,
max, max2, max3, max4, min, min2, min3, min4,
equal_eps, equal_eps_vec, not_equal_eps, not_equal_eps_vec,
quat_conjugate, quat_inverse, quat_lerp, quat_slerp,
quat_cross, quat_dot, quat_length, quat_magnitude, quat_normalize,
quat_equal, quat_equal_eps, quat_not_equal, quat_not_equal_eps,
quat_exp, quat_log, quat_pow, quat_rotate,
quat_angle, quat_angle_axis, quat_axis
pub use gtx::{
angle, are_collinear, are_collinear2d, are_orthogonal, comp_add, comp_max, comp_min, comp_mul,
cross2d, diagonal2x2, diagonal2x3, diagonal2x4, diagonal3x2, diagonal3x3, diagonal3x4,
diagonal4x2, diagonal4x3, diagonal4x4, distance2, fast_normalize_dot, is_comp_null,
is_normalized, is_null, l1_distance, l1_norm, l2_distance, l2_norm, left_handed, length2,
magnitude2, mat3_to_quat, matrix_cross, matrix_cross3, normalize_dot, orientation, proj,
proj2d, quat_cross_vec, quat_extract_real_component, quat_fast_mix, quat_identity,
quat_inv_cross_vec, quat_length2, quat_magnitude2, quat_rotate_normalized_axis,
quat_rotate_vec, quat_rotate_vec3, quat_rotation, quat_short_mix, quat_to_mat3, quat_to_mat4,
reflect, reflect2d, right_handed, rotate2d, rotate_normalized_axis, rotate_vec2, rotate_vec3,
rotate_vec4, rotate_x_vec3, rotate_x_vec4, rotate_y_vec3, rotate_y_vec4, rotate_z_vec3,
rotate_z_vec4, rotation, rotation2d, scale2d, scale_bias, scale_bias_matrix, scaling,
scaling2d, shear2d_x, shear2d_y, shear_x, shear_y, shear_z, slerp, to_quat, translate2d,
translation, translation2d, triangle_normal,
};
pub use na::{convert, convert_ref, convert_unchecked, convert_ref_unchecked, try_convert, try_convert_ref};
pub use na::{Scalar, Real, DefaultAllocator, U1, U2, U3, U4};
pub use na::{
convert, convert_ref, convert_ref_unchecked, convert_unchecked, try_convert, try_convert_ref,
};
pub use na::{DefaultAllocator, Real, Scalar, U1, U2, U3, U4};
mod aliases;
mod constructors;
mod common;
mod matrix;
mod constructors;
mod exponential;
mod geometric;
mod matrix;
mod traits;
mod trigonometric;
mod vector_relational;
mod exponential;
//mod integer;
//mod packing;

View File

@ -1,34 +1,52 @@
use na::{Scalar, Real, DefaultAllocator};
use na::{DefaultAllocator, Real, Scalar};
use traits::{Alloc, Dimension, Number};
use aliases::{TMat, TVec};
use traits::{Alloc, Dimension, Number};
/// The determinant of the matrix `m`.
pub fn determinant<N: Real, D: Dimension>(m: &TMat<N, D, D>) -> N
where DefaultAllocator: Alloc<N, D, D> {
where
DefaultAllocator: Alloc<N, D, D>,
{
m.determinant()
}
/// The inverse of the matrix `m`.
pub fn inverse<N: Real, D: Dimension>(m: &TMat<N, D, D>) -> TMat<N, D, D>
where DefaultAllocator: Alloc<N, D, D> {
m.clone().try_inverse().unwrap_or_else(TMat::<N, D, D>::zeros)
where
DefaultAllocator: Alloc<N, D, D>,
{
m.clone()
.try_inverse()
.unwrap_or_else(TMat::<N, D, D>::zeros)
}
/// Component-wise multiplication of two matrices.
pub fn matrix_comp_mult<N: Number, R: Dimension, C: Dimension>(x: &TMat<N, R, C>, y: &TMat<N, R, C>) -> TMat<N, R, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn matrix_comp_mult<N: Number, R: Dimension, C: Dimension>(
x: &TMat<N, R, C>,
y: &TMat<N, R, C>,
) -> TMat<N, R, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
x.component_mul(y)
}
/// Treats the first parameter `c` as a column vector and the second parameter `r` as a row vector and does a linear algebraic matrix multiply `c * r`.
pub fn outer_product<N: Number, R: Dimension, C: Dimension>(c: &TVec<N, R>, r: &TVec<N, C>) -> TMat<N, R, C>
where DefaultAllocator: Alloc<N, R, C> {
pub fn outer_product<N: Number, R: Dimension, C: Dimension>(
c: &TVec<N, R>,
r: &TVec<N, C>,
) -> TMat<N, R, C>
where
DefaultAllocator: Alloc<N, R, C>,
{
c * r.transpose()
}
/// The transpose of the matrix `m`.
pub fn transpose<N: Scalar, R: Dimension, C: Dimension>(x: &TMat<N, R, C>) -> TMat<N, C, R>
where DefaultAllocator: Alloc<N, R, C> {
where
DefaultAllocator: Alloc<N, R, C>,
{
x.transpose()
}

View File

@ -1,48 +1,80 @@
use num::{Signed, FromPrimitive, Bounded};
use approx::AbsDiffEq;
use num::{Bounded, FromPrimitive, Signed};
use alga::general::{Ring, Lattice};
use na::{Scalar, DimName, DimMin, U1};
use alga::general::{Lattice, Ring};
use na::allocator::Allocator;
use na::{DimMin, DimName, Scalar, U1};
/// A type-level number representing a vector, matrix row, or matrix column, dimension.
pub trait Dimension: DimName + DimMin<Self, Output = Self> {}
impl<D: DimName + DimMin<D, Output = Self>> Dimension for D {}
/// A number that can either be an integer or a float.
pub trait Number: Scalar + Ring + Lattice + AbsDiffEq<Epsilon = Self> + Signed + FromPrimitive + Bounded {
pub trait Number:
Scalar + Ring + Lattice + AbsDiffEq<Epsilon = Self> + Signed + FromPrimitive + Bounded
{
}
impl<T: Scalar + Ring + Lattice + AbsDiffEq<Epsilon = Self> + Signed + FromPrimitive + Bounded> Number for T {
}
impl<T: Scalar + Ring + Lattice + AbsDiffEq<Epsilon = Self> + Signed + FromPrimitive + Bounded>
Number for T
{}
#[doc(hidden)]
pub trait Alloc<N: Scalar, R: Dimension, C: Dimension = U1>:
Allocator<N, R> + Allocator<N, C> + Allocator<N, U1, R> + Allocator<N, U1, C> + Allocator<N, R, C> + Allocator<N, C, R> + Allocator<N, R, R> + Allocator<N, C, C> +
Allocator<bool, R> + Allocator<bool, C> +
Allocator<f32, R> + Allocator<f32, C> +
Allocator<u32, R> + Allocator<u32, C> +
Allocator<i32, R> + Allocator<i32, C> +
Allocator<f64, R> + Allocator<f64, C> +
Allocator<u64, R> + Allocator<u64, C> +
Allocator<i64, R> + Allocator<i64, C> +
Allocator<i16, R> + Allocator<i16, C> +
Allocator<(usize, usize), R> + Allocator<(usize, usize), C>
Allocator<N, R>
+ Allocator<N, C>
+ Allocator<N, U1, R>
+ Allocator<N, U1, C>
+ Allocator<N, R, C>
+ Allocator<N, C, R>
+ Allocator<N, R, R>
+ Allocator<N, C, C>
+ Allocator<bool, R>
+ Allocator<bool, C>
+ Allocator<f32, R>
+ Allocator<f32, C>
+ Allocator<u32, R>
+ Allocator<u32, C>
+ Allocator<i32, R>
+ Allocator<i32, C>
+ Allocator<f64, R>
+ Allocator<f64, C>
+ Allocator<u64, R>
+ Allocator<u64, C>
+ Allocator<i64, R>
+ Allocator<i64, C>
+ Allocator<i16, R>
+ Allocator<i16, C>
+ Allocator<(usize, usize), R>
+ Allocator<(usize, usize), C>
{
}
impl<N: Scalar, R: Dimension, C: Dimension, T>
Alloc<N, R, C> for T
where T: Allocator<N, R> + Allocator<N, C> + Allocator<N, U1, R> + Allocator<N, U1, C> + Allocator<N, R, C> + Allocator<N, C, R> + Allocator<N, R, R> + Allocator<N, C, C> +
Allocator<bool, R> + Allocator<bool, C> +
Allocator<f32, R> + Allocator<f32, C> +
Allocator<u32, R> + Allocator<u32, C> +
Allocator<i32, R> + Allocator<i32, C> +
Allocator<f64, R> + Allocator<f64, C> +
Allocator<u64, R> + Allocator<u64, C> +
Allocator<i64, R> + Allocator<i64, C> +
Allocator<i16, R> + Allocator<i16, C> +
Allocator<(usize, usize), R> + Allocator<(usize, usize), C>
{
}
impl<N: Scalar, R: Dimension, C: Dimension, T> Alloc<N, R, C> for T where
T: Allocator<N, R>
+ Allocator<N, C>
+ Allocator<N, U1, R>
+ Allocator<N, U1, C>
+ Allocator<N, R, C>
+ Allocator<N, C, R>
+ Allocator<N, R, R>
+ Allocator<N, C, C>
+ Allocator<bool, R>
+ Allocator<bool, C>
+ Allocator<f32, R>
+ Allocator<f32, C>
+ Allocator<u32, R>
+ Allocator<u32, C>
+ Allocator<i32, R>
+ Allocator<i32, C>
+ Allocator<f64, R>
+ Allocator<f64, C>
+ Allocator<u64, R>
+ Allocator<u64, C>
+ Allocator<i64, R>
+ Allocator<i64, C>
+ Allocator<i16, R>
+ Allocator<i16, C>
+ Allocator<(usize, usize), R>
+ Allocator<(usize, usize), C>
{}

View File

@ -1,95 +1,124 @@
use na::{self, Real, DefaultAllocator};
use na::{self, DefaultAllocator, Real};
use aliases::TVec;
use traits::{Alloc, Dimension};
/// Component-wise arc-cosinus.
pub fn acos<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|e| e.acos())
}
/// Component-wise hyperbolic arc-cosinus.
pub fn acosh<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|e| e.acosh())
}
/// Component-wise arc-sinus.
pub fn asin<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|e| e.asin())
}
/// Component-wise hyperbolic arc-sinus.
pub fn asinh<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|e| e.asinh())
}
/// Component-wise arc-tangent of `y / x`.
pub fn atan2<N: Real, D: Dimension>(y: &TVec<N, D>, x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
y.zip_map(x, |y, x| y.atan2(x))
}
/// Component-wise arc-tangent.
pub fn atan<N: Real, D: Dimension>(y_over_x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
y_over_x.map(|e| e.atan())
}
/// Component-wise hyperbolic arc-tangent.
pub fn atanh<N: Real, D: Dimension>(x: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.map(|e| e.atanh())
}
/// Component-wise cosinus.
pub fn cos<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.cos())
}
/// Component-wise hyperbolic cosinus.
pub fn cosh<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.cosh())
}
/// Component-wise conversion from radians to degrees.
pub fn degrees<N: Real, D: Dimension>(radians: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
radians.map(|e| e * na::convert(180.0) / N::pi())
}
/// Component-wise conversion fro degrees to radians.
pub fn radians<N: Real, D: Dimension>(degrees: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
degrees.map(|e| e * N::pi() / na::convert(180.0))
}
/// Component-wise sinus.
pub fn sin<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.sin())
}
/// Component-wise hyperbolic sinus.
pub fn sinh<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.sinh())
}
/// Component-wise tangent.
pub fn tan<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.tan())
}
/// Component-wise hyperbolic tangent.
pub fn tanh<N: Real, D: Dimension>(angle: &TVec<N, D>) -> TVec<N, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
angle.map(|e| e.tanh())
}

View File

@ -1,7 +1,7 @@
use na::{DefaultAllocator};
use na::DefaultAllocator;
use aliases::TVec;
use traits::{Number, Alloc, Dimension};
use traits::{Alloc, Dimension, Number};
/// Checks that all the vector components are `true`.
///
@ -21,7 +21,9 @@ use traits::{Number, Alloc, Dimension};
/// * [`any`](fn.any.html)
/// * [`not`](fn.not.html)
pub fn all<D: Dimension>(v: &TVec<bool, D>) -> bool
where DefaultAllocator: Alloc<bool, D> {
where
DefaultAllocator: Alloc<bool, D>,
{
v.iter().all(|x| *x)
}
@ -46,7 +48,9 @@ pub fn all<D: Dimension>(v: &TVec<bool, D>) -> bool
/// * [`all`](fn.all.html)
/// * [`not`](fn.not.html)
pub fn any<D: Dimension>(v: &TVec<bool, D>) -> bool
where DefaultAllocator: Alloc<bool, D> {
where
DefaultAllocator: Alloc<bool, D>,
{
v.iter().any(|x| *x)
}
@ -70,7 +74,9 @@ pub fn any<D: Dimension>(v: &TVec<bool, D>) -> bool
/// * [`not`](fn.not.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x == y)
}
@ -94,7 +100,9 @@ pub fn equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bo
/// * [`not`](fn.not.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn greater_than<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x > y)
}
@ -118,7 +126,9 @@ pub fn greater_than<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) ->
/// * [`not`](fn.not.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn greater_than_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x >= y)
}
@ -142,7 +152,9 @@ pub fn greater_than_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D
/// * [`not`](fn.not.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn less_than<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x < y)
}
@ -166,7 +178,9 @@ pub fn less_than<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVe
/// * [`not`](fn.not.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn less_than_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x <= y)
}
@ -191,7 +205,9 @@ pub fn less_than_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>)
/// * [`less_than_equal`](fn.less_than_equal.html)
/// * [`not_equal`](fn.not_equal.html)
pub fn not<D: Dimension>(v: &TVec<bool, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<bool, D> {
where
DefaultAllocator: Alloc<bool, D>,
{
v.map(|x| !x)
}
@ -215,6 +231,8 @@ pub fn not<D: Dimension>(v: &TVec<bool, D>) -> TVec<bool, D>
/// * [`less_than_equal`](fn.less_than_equal.html)
/// * [`not`](fn.not.html)
pub fn not_equal<N: Number, D: Dimension>(x: &TVec<N, D>, y: &TVec<N, D>) -> TVec<bool, D>
where DefaultAllocator: Alloc<N, D> {
where
DefaultAllocator: Alloc<N, D>,
{
x.zip_map(y, |x, y| x != y)
}