use std::fmt::Debug;

#[derive(
    bytemuck::Pod,
    bytemuck::Zeroable,
    Copy,
    Clone,
    serde::Serialize,
    serde::Deserialize,
    derive_more::Display,
    derive_more::FromStr,
    PartialEq,
    Eq,
    PartialOrd,
    Ord,
    Default,
    derive_more::Add,
    derive_more::Sub,
    derive_more::Mul,
    derive_more::From,
)]
#[mul(forward)]
#[repr(C)]
#[serde(transparent)]
pub struct BlockNumber(pub u32);

impl num_traits::Bounded for BlockNumber {
    fn min_value() -> Self {
        Self(0)
    }

    fn max_value() -> Self {
        Self(u32::MAX)
    }
}

impl num_traits::Zero for BlockNumber {
    fn zero() -> Self {
        Self(0)
    }

    fn is_zero(&self) -> bool {
        self.0 == 0
    }
}

impl num_traits::One for BlockNumber {
    fn one() -> Self {
        Self(1)
    }
}

impl Debug for BlockNumber {
    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
        self.0.fmt(f)
    }
}

impl num_traits::SaturatingAdd for BlockNumber {
    fn saturating_add(&self, v: &Self) -> Self {
        Self(self.0.saturating_add(v.0))
    }
}
