Implement Coordinate for all numerical types (#372)

This allows Size, Point and Rectangle to be made with any numeric type
This commit is contained in:
i509VCB 2021-08-30 15:02:00 -05:00 committed by GitHub
parent cc48759338
commit b07f1af494
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 148 additions and 50 deletions

View File

@ -28,58 +28,156 @@ pub trait Coordinate:
fn abs(self) -> Self; fn abs(self) -> Self;
} }
impl Coordinate for f64 { /// Implements Coordinate for an unsigned numerical type.
#[inline] macro_rules! unsigned_coordinate_impl {
fn downscale(self, scale: f64) -> f64 { ($ty:ty, $ ($tys:ty),* ) => {
self / scale unsigned_coordinate_impl!($ty);
} $(
#[inline] unsigned_coordinate_impl!($tys);
fn upscale(self, scale: f64) -> f64 { )*
self * scale };
}
#[inline]
fn to_f64(self) -> f64 {
self
}
#[inline]
fn from_f64(v: f64) -> f64 {
v
}
#[inline]
fn non_negative(self) -> bool {
self >= 0.0
}
#[inline]
fn abs(self) -> f64 {
self.abs()
}
}
impl Coordinate for i32 { ($ty:ty) => {
impl Coordinate for $ty {
#[inline] #[inline]
fn downscale(self, scale: i32) -> i32 { fn downscale(self, scale: Self) -> Self {
self / scale self / scale
} }
#[inline] #[inline]
fn upscale(self, scale: i32) -> i32 { fn upscale(self, scale: Self) -> Self {
self.saturating_mul(scale) self.saturating_mul(scale)
} }
#[inline] #[inline]
fn to_f64(self) -> f64 { fn to_f64(self) -> f64 {
self as f64 self as f64
} }
#[inline] #[inline]
fn from_f64(v: f64) -> i32 { fn from_f64(v: f64) -> Self {
v as i32 v as Self
} }
#[inline]
fn non_negative(self) -> bool {
true
}
#[inline]
fn abs(self) -> Self {
self
}
}
};
}
unsigned_coordinate_impl! {
u8,
u16,
u32,
u64,
u128
}
/// Implements Coordinate for an signed numerical type.
macro_rules! signed_coordinate_impl {
($ty:ty, $ ($tys:ty),* ) => {
signed_coordinate_impl!($ty);
$(
signed_coordinate_impl!($tys);
)*
};
($ty:ty) => {
impl Coordinate for $ty {
#[inline]
fn downscale(self, scale: Self) -> Self {
self / scale
}
#[inline]
fn upscale(self, scale: Self) -> Self {
self.saturating_mul(scale)
}
#[inline]
fn to_f64(self) -> f64 {
self as f64
}
#[inline]
fn from_f64(v: f64) -> Self {
v as Self
}
#[inline] #[inline]
fn non_negative(self) -> bool { fn non_negative(self) -> bool {
self >= 0 self >= 0
} }
#[inline] #[inline]
fn abs(self) -> i32 { fn abs(self) -> Self {
self.abs() self.abs()
} }
}
};
}
signed_coordinate_impl! {
i8,
i16,
i32,
i64,
i128
}
macro_rules! floating_point_coordinate_impl {
($ty:ty, $ ($tys:ty),* ) => {
floating_point_coordinate_impl!($ty);
$(
floating_point_coordinate_impl!($tys);
)*
};
($ty:ty) => {
impl Coordinate for $ty {
#[inline]
fn downscale(self, scale: Self) -> Self {
self / scale
}
#[inline]
fn upscale(self, scale: Self) -> Self {
self * scale
}
#[inline]
fn to_f64(self) -> f64 {
self as f64
}
#[inline]
fn from_f64(v: f64) -> Self {
v as Self
}
#[inline]
fn non_negative(self) -> bool {
self >= 0.0
}
#[inline]
fn abs(self) -> Self {
self.abs()
}
}
};
}
floating_point_coordinate_impl! {
f32,
f64
} }
/* /*