use super::point::Point;
use num_traits::{Num, Zero};
#[derive(Copy, Clone, Debug, Eq, PartialEq, Hash)]
pub struct Rect<T> {
lower_left: Point<T>,
upper_right: Point<T>,
}
impl<T> Rect<T>
where T: Copy + Num + Ord + Zero {
pub fn new(lower_left: Point<T>, upper_right: Point<T>) -> Self {
let r = Self { lower_left, upper_right };
assert!(r.width() >= T::zero());
assert!(r.height() >= T::zero());
r
}
pub fn width(&self) -> T {
self.upper_right.x - self.lower_left.x
}
pub fn height(&self) -> T {
self.upper_right.y - self.lower_left.y
}
pub fn is_on_boundary(&self, p: Point<T>) -> bool {
p.x == self.lower_left.x || p.y == self.lower_left.y || p.x == self.upper_right.x || p.y == self.upper_right.y
}
pub fn contains_point(&self, p: Point<T>) -> bool {
#![allow(unused_comparisons)]
p.x >= self.lower_left.x && p.y >= self.lower_left.y && p.x <= self.upper_right.x && p.y <= self.upper_right.y
}
pub fn lower_left(&self) -> Point<T> {
self.lower_left
}
pub fn lower_right(&self) -> Point<T> {
Point::new(self.upper_right.x, self.lower_left.y)
}
pub fn upper_right(&self) -> Point<T> {
self.upper_right
}
pub fn upper_left(&self) -> Point<T> {
Point::new(self.lower_left.x, self.upper_right.y)
}
}