Skip to content

Commit

Permalink
chore: make color.rs actually presentable
Browse files Browse the repository at this point in the history
  • Loading branch information
raklaptudirm committed Mar 30, 2024
1 parent 22403d6 commit 4d6881d
Showing 1 changed file with 50 additions and 40 deletions.
90 changes: 50 additions & 40 deletions src/ataxx/color.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,10 @@ use crate::util::type_macros;
/// specifically White, Black, and None(no Color/no piece).
#[derive(Copy, Clone, PartialEq, Eq, Default, FromPrimitive)]
pub enum Color {
White,
Black,
#[default] None,
White,
Black,
#[default]
None,
}

// Implement conversions from numerical types.
Expand All @@ -45,57 +46,66 @@ type_macros::impl_from_integer_for_enum! {
}

impl Color {
/// N is the number of possible Colors, excluding None.
pub const N: usize = 2;
/// N is the number of possible Colors, excluding None.
pub const N: usize = 2;
}

// Implement not(!) operation to switch to the other Color.
impl ops::Not for Color {
type Output = Color;
fn not(self) -> Self::Output {
Color::try_from(self as usize ^ 1).unwrap()
}
type Output = Color;

/// not implements the not unary operator (!) which switches the current Color
/// to its opposite, i.e. [`Color::Black`] to [`Color::White`] and vice versa.
fn not(self) -> Self::Output {
Color::try_from(self as usize ^ 1).unwrap()
}
}

#[derive(Debug)]
pub enum ColorParseError {
StringTooLong,
StringFormatInvalid,
StringTooLong,
StringFormatInvalid,
}

impl fmt::Display for Color {
/// Implements displaying the Color in a human-readable form.
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"{}",
match *self {
Self::White => "o",
Self::Black => "x",
Self::None => "-",
}
)
}
/// Implements displaying the Color in a human-readable form. [`Color::Black`]
/// is formatted as `x` and [`Color::White`] is formatted as `o`.
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"{}",
match *self {
Self::Black => "x",
Self::White => "o",
Self::None => "-",
}
)
}
}

impl fmt::Debug for Color {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self)
}
/// Debug implements debug printing of a Color in a human-readable form. It uses
/// [`Color::fmt`] under the hood to format and print the Color.
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self)
}
}

impl FromStr for Color {
type Err = ColorParseError;

fn from_str(s: &str) -> Result<Self, Self::Err> {
if s.len() != 1 {
return Err(ColorParseError::StringTooLong);
}

match s {
"o" | "O" | "w" | "W" => Ok(Color::White),
"x" | "X" | "b" | "B" => Ok(Color::Black),
_ => Err(ColorParseError::StringFormatInvalid),
}
}
type Err = ColorParseError;

/// from_str converts the given human-readable string into its corresponding
/// [`Color`]. `x`, `X`, `b`, `B` are parsed as [`Color::Black`] and `o`, `O`,
/// `w`, `W` are parsed as [`Color::White`]. Best practice is to use `x` and `o`
/// respectively for black and white.
fn from_str(s: &str) -> Result<Self, Self::Err> {
if s.len() != 1 {
return Err(ColorParseError::StringTooLong);
}

match s {
"x" | "X" | "b" | "B" => Ok(Color::Black),
"o" | "O" | "w" | "W" => Ok(Color::White),
_ => Err(ColorParseError::StringFormatInvalid),
}
}
}

0 comments on commit 4d6881d

Please sign in to comment.