Skip to content

Commit

Permalink
Added Angle as a different Kind of dimensionless quantity. Resolves #89.
Browse files Browse the repository at this point in the history
  • Loading branch information
M@ Dunlap committed Apr 26, 2019
1 parent 8655f54 commit 4c090b6
Show file tree
Hide file tree
Showing 2 changed files with 98 additions and 0 deletions.
97 changes: 97 additions & 0 deletions src/si/angle.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
//! Angle (dimensionless).
/// AngleKind is a `Kind` for separating angular quantities from their indentically dimensioned
/// non-angular quantity counterparts.
pub trait AngleKind: ::Kind {}

quantity! {
/// Angle (dimensionless).
quantity: Angle; "angle";
/// Angle dimension (dimensionless).
dimension: ISQ<
Z0, // length
Z0, // mass
Z0, // time
Z0, // electric current
Z0, // thermodynamic temperature
Z0, // amount of substance
Z0>; // luminous intensity
kind: AngleKind;
units {
/// SI derived unit of angle. It is the angle subtended at the center of a circle by an
/// arc that is equal in length to the radius of the circle.
@radian: 1.0; "rad", "radian", "radians";
@revolution: 6.283_185_307_179_586_E0; "r", "revolution", "revolutions";
@degree: 1.745_329_251_994_329_5_E-2; "°", "degree", "degrees";
@gon: 1.570_796_326_794_896_7_E-2; "gon", "gon", "gons";
@mil: 9.817_477_E-4; "mil", "mil", "mils";
@minute: 2.908_882_086_657_216_E-4; "′", "minute", "minutes";
@second: 4.848_136_811_095_36_E-6; "″", "second", "seconds";
}
}

mod convert {
use super::*;

impl<U, V> ::lib::convert::From<V> for Angle<U, V>
where
U: ::si::Units<V> + ?Sized,
V: ::num::Num + ::Conversion<V>,
{
fn from(t: V) -> Self {
Angle {
dimension: ::lib::marker::PhantomData,
units: ::lib::marker::PhantomData,
value: t,
}
}
}

storage_types! {
use super::*;

impl<U> ::lib::convert::From<Angle<U, V>> for V
where
U: ::si::Units<V> + ?Sized,
V: ::num::Num + ::Conversion<V>,
{
fn from(t: Angle<U, V>) -> Self {
t.value
}
}
}
}

#[cfg(test)]
mod tests {
storage_types! {
use ::lib::f64::consts::PI;
use num::One;
use num_traits::FromPrimitive;
use si::angle as a;
use si::quantities::*;
use tests::Test;

#[test]
fn from() {
let r1: Angle<V> = Angle::<V>::from(V::one());
let r2: Angle<V> = V::one().into();
let _: V = V::from(r1);
let _: V = r2.into();
}

#[test]
fn check_units() {
Test::assert_eq(&Angle::new::<a::radian>(V::from_f64(2.0 * PI).unwrap()),
&Angle::new::<a::revolution>(V::one()));
Test::assert_eq(&Angle::new::<a::degree>(V::from_f64(360.0).unwrap()),
&Angle::new::<a::revolution>(V::one()));
Test::assert_approx_eq(&Angle::new::<a::gon>(V::from_f64(400.0).unwrap()),
&Angle::new::<a::revolution>(V::one()));
Test::assert_eq(&Angle::new::<a::minute>(V::from_f64(60.0).unwrap()),
&Angle::new::<a::degree>(V::one()));
Test::assert_eq(&Angle::new::<a::second>(V::from_f64(60.0 * 60.0).unwrap()),
&Angle::new::<a::degree>(V::one()));
}
}
}
1 change: 1 addition & 0 deletions src/si/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ system! {
units: SI {
acceleration::Acceleration,
amount_of_substance::AmountOfSubstance,
angle::Angle,
area::Area,
available_energy::AvailableEnergy,
capacitance::Capacitance,
Expand Down

0 comments on commit 4c090b6

Please sign in to comment.