use std::ops::Add;
use crate::Rollable;
pub struct Die<T: Rollable = u32> {
faces: T,
current_value: T,
}
impl<T: Rollable> Die<T> {
pub fn new(faces: T) -> Self {
let die = Die {
faces,
current_value: T::roll(faces),
};
die
}
pub fn roll(&mut self) -> T {
self.current_value = T::roll(self.faces);
self.current_value
}
pub fn current_face(&self) -> T {
self.current_value
}
}
impl<T: Rollable> Add for Die<T>
where
T: Add,
{
type Output = T::Output;
fn add(self, other: Self) -> Self::Output {
self.current_value + other.current_value
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn current_face() {
let coin: Die<u128> = Die::new(2);
for _ in 0..100 {
assert!(coin.current_face() >= 1);
assert!(coin.current_face() <= 2);
}
}
#[test]
fn roll() {
let mut d12: Die<u64> = Die::new(12);
for _ in 0..100 {
d12.roll();
assert!(d12.current_face() >= 1);
assert!(d12.current_face() <= 12);
}
}
#[test]
fn add_die() {
for _ in 0..100 {
let penny: Die<u8> = Die::new(2);
let quarter: Die<u8> = Die::new(2);
let sum = penny + quarter;
assert!(sum >= 2);
assert!(sum <= 4);
}
}
}