1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62
//! Tolerance value for approximation
//!
//! See [`Tolerance`].
use fj_math::Scalar;
/// A tolerance value
///
/// A tolerance value is used during approximation. It defines the maximum
/// allowed deviation of the approximation from the actual shape.
///
/// The `Tolerance` type enforces that the tolerance value is always larger than
/// zero, which is an attribute that the approximation code relies on.
///
/// # Failing [`From`]/[`Into`] implementation
///
/// The [`From`]/[`Into`] implementations of tolerance are fallible, which goes
/// against the explicit mandate of those traits, as stated in their
/// documentation.
///
/// A fallible [`Into`] provides a lot of convenience in test code. Since said
/// documentation doesn't provide any actual reasoning for this requirement, I'm
/// feeling free to just ignore it.
#[derive(Clone, Copy, Debug, Eq, PartialEq, Hash, Ord, PartialOrd)]
pub struct Tolerance(Scalar);
impl Tolerance {
/// Construct a `Tolerance` from a [`Scalar`]
///
/// Returns an error, if the passed scalar is not larger than zero.
pub fn from_scalar(
scalar: impl Into<Scalar>,
) -> Result<Self, InvalidTolerance> {
let scalar = scalar.into();
if scalar <= Scalar::ZERO {
return Err(InvalidTolerance(scalar));
}
Ok(Self(scalar))
}
/// Return the [`Scalar`] that defines the tolerance
pub fn inner(&self) -> Scalar {
self.0
}
}
impl<S> From<S> for Tolerance
where
S: Into<Scalar>,
{
fn from(scalar: S) -> Self {
Self::from_scalar(scalar)
.expect("Tried to create `Tolerance` from invalid value")
}
}
/// Error converting scalar to tolerance
#[derive(Debug, thiserror::Error)]
#[error("Invalid tolerance ({0}); must be above zero")]
pub struct InvalidTolerance(Scalar);