use core::fmt;
macro_rules! zone {
( $($i:ty, $b:expr),+ ) => {
$( zone![single: $i, $b]; )+
};
(single: $i:ty, $b:literal) => { paste::paste! {
use super::{[<Position$b>], [<Size$b>]};
#[doc = "A 2D zone combines a [`" [<Position$b>] "`] with a [`" [<Size$b>] "`]."]
#[derive(Clone, Copy, Default, PartialEq, Eq)]
pub struct [<Zone$b>] {
pub p: [<Position$b>],
pub s: [<Size$b>],
}
impl fmt::Debug for [<Zone$b>] {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "[<Zone$b>] {{ p: {:?}, s: {:?} }}", self.p, self.s,)
}
}
impl fmt::Display for [<Zone$b>] {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{} {}", self.p, self.s)
}
}
impl [<Zone$b>] {
pub const fn new(position: [<Position$b>], size: [<Size$b>]) -> Self {
[<Zone$b>] {
p: position,
s: size,
}
}
pub const fn new_raw(x: $i, y: $i, width: $i, height: $i) -> Self {
Self::new([<Position$b>]::new(x, y), [<Size$b>]::new(width, height))
}
pub const fn position_size(&self) -> ([<Position$b>], [<Size$b>]) {
(self.p, self.s)
}
pub const fn position(&self) -> [<Position$b>] {
self.p
}
pub fn set_position(mut self, position: impl Into<[<Position$b>]>) {
self.p = position.into();
}
pub const fn size(&self) -> [<Size$b>] {
self.s
}
pub fn set_size(mut self, size: impl Into<[<Size$b>]>) {
self.s = size.into();
}
pub const fn x(&self) -> $i {
self.p.x()
}
pub fn set_x(&mut self, x: $i) {
self.p.set_x(x)
}
pub const fn y(&self) -> $i {
self.p.y()
}
pub fn set_y(&mut self, y: $i) {
self.p.set_y(y)
}
pub const fn w(&self) -> $i {
self.s.w()
}
pub fn set_w(&mut self, width: $i) {
self.s.set_w(width)
}
pub const fn h(&self) -> $i {
self.s.h()
}
pub fn set_h(&mut self, height: $i) {
self.s.set_h(height)
}
}
impl [<Zone$b>] {
pub const fn as_tuple(&self) -> ($i, $i, $i, $i) {
(self.p.x(), self.p.y(), self.s.w(), self.s.h())
}
pub const fn from_tuple(tup: ($i, $i, $i, $i)) -> [<Zone$b>] {
Self::new_raw(tup.0, tup.1, tup.2, tup.3)
}
pub const fn as_tuple_i32(&self) -> (i32, i32, i32, i32) {
let p = self.p.as_tuple_i32();
let s = self.s.as_tuple_i32();
(p.0, p.1, s.0, s.1)
}
pub const fn from_tuple_i32(tup: (i32, i32, i32, i32)) -> [<Zone$b>] {
Self::new(
[<Position$b>]::from_tuple_i32((tup.0, tup.1)),
[<Size$b>]::from_tuple_i32((tup.2, tup.3)),
)
}
pub const fn as_tuple_u32(&self) -> (u32, u32, u32, u32) {
let p = self.p.as_tuple_u32();
let s = self.s.as_tuple_u32();
(p.0, p.1, s.0, s.1)
}
pub const fn from_tuple_u32(tup: (u32, u32, u32, u32)) -> [<Zone$b>] {
Self::new(
[<Position$b>]::from_tuple_u32((tup.0, tup.1)),
[<Size$b>]::from_tuple_u32((tup.2, tup.3)),
)
}
pub const fn as_tuple_u16(&self) -> (u16, u16, u16, u16) {
let p = self.p.as_tuple_u16();
let s = self.s.as_tuple_u16();
(p.0, p.1, s.0, s.1)
}
pub const fn from_tuple_u16(tup: (u16, u16, u16, u16)) -> [<Zone$b>] {
Self::new(
[<Position$b>]::from_tuple_u16((tup.0, tup.1)),
[<Size$b>]::from_tuple_u16((tup.2, tup.3)),
)
}
pub const fn as_tuple_i16(&self) -> (i16, i16, i16, i16) {
let p = self.p.as_tuple_i16();
let s = self.s.as_tuple_i16();
(p.0, p.1, s.0, s.1)
}
pub const fn from_tuple_i16(tup: (i16, i16, i16, i16)) -> [<Zone$b>] {
Self::new(
[<Position$b>]::from_tuple_i16((tup.0, tup.1)),
[<Size$b>]::from_tuple_i16((tup.2, tup.3)),
)
}
pub const fn as_tuple_usize(&self) -> (usize, usize, usize, usize) {
let p = self.p.as_tuple_usize();
let s = self.s.as_tuple_usize();
(p.0, p.1, s.0, s.1)
}
pub const fn from_tuple_usize(tup: (usize, usize, usize, usize)) -> [<Zone$b>] {
Self::new(
[<Position$b>]::from_tuple_usize((tup.0, tup.1)),
[<Size$b>]::from_tuple_usize((tup.2, tup.3)),
)
}
}
impl From<(i32, i32, i32, i32)> for [<Zone$b>] {
fn from(tup: (i32, i32, i32, i32)) -> [<Zone$b>] {
Self::from_tuple_i32(tup)
}
}
impl From<[<Zone$b>]> for (i32, i32, i32, i32) {
fn from(z: [<Zone$b>]) -> (i32, i32, i32, i32) {
z.as_tuple_i32()
}
}
impl From<(i16, i16, i16, i16)> for [<Zone$b>] {
fn from(tup: (i16, i16, i16, i16)) -> [<Zone$b>] {
Self::from_tuple_i16(tup)
}
}
impl From<[<Zone$b>]> for (i16, i16, i16, i16) {
fn from(z: [<Zone$b>]) -> (i16, i16, i16, i16) {
z.as_tuple_i16()
}
}
impl From<(u16, u16, u16, u16)> for [<Zone$b>] {
fn from(tup: (u16, u16, u16, u16)) -> [<Zone$b>] {
Self::from_tuple_u16(tup)
}
}
impl From<[<Zone$b>]> for (u16, u16, u16, u16) {
fn from(z: [<Zone$b>]) -> (u16, u16, u16, u16) {
z.as_tuple_u16()
}
}
impl From<(u32, u32, u32, u32)> for [<Zone$b>] {
fn from(tup: (u32, u32, u32, u32)) -> [<Zone$b>] {
Self::from_tuple_u32(tup)
}
}
impl From<[<Zone$b>]> for (u32, u32, u32, u32) {
fn from(z: [<Zone$b>]) -> (u32, u32, u32, u32) {
z.as_tuple_u32()
}
}
impl From<(usize, usize, usize, usize)> for [<Zone$b>] {
fn from(tup: (usize, usize, usize, usize)) -> [<Zone$b>] {
Self::from_tuple_usize(tup)
}
}
impl From<[<Zone$b>]> for (usize, usize, usize, usize) {
fn from(z: [<Zone$b>]) -> (usize, usize, usize, usize) {
z.as_tuple_usize()
}
}
}};
}
zone![i8, 8, i16, 16, i32, 32, i64, 64];