lib_efo/
utils.rs

1//! Utilities asserting that the data being worked on is sound and well formatted.
2//!
3//! This module provides simple helpers that validate file system paths.
4//!
5//!
6
7#![warn(missing_docs, clippy::missing_docs_in_private_items)]
8
9use clap::ValueEnum;
10use rand::distr::Uniform;
11
12use crate::error::EpochError;
13
14/// How to fill in unspecified stat values.
15///
16/// When an entity is created or edited, any stat that is not explicitly
17/// provided will be assigned a value according to the chosen level.
18#[derive(Debug, ValueEnum, Copy, Clone, PartialEq, Eq, PartialOrd, Ord)]
19pub enum RngLevel {
20    /// All non specified values are zero
21    Zero,
22    /// All non specified values are low
23    Low,
24    /// All non specified values are medium
25    Med,
26    /// All non specified values are high
27    High,
28    /// All non specified values are very high
29    Legendary,
30    /// Stats are all over the place
31    Mixed,
32    /// All non specified are either high or low
33    Flawed,
34    /// All non-specified values are apocalyptic
35    Apocaliptic,
36    /// All non-specified values are doomed
37    Doom,
38}
39
40impl RngLevel {
41    /// Turn into a range for rng generation
42    pub fn to_range(&self) -> std::ops::Range<i32> {
43        match self {
44            RngLevel::Zero => 0..1,
45            RngLevel::Low => 0..20,
46            RngLevel::Med => 10..40,
47            RngLevel::High => 20..50,
48            RngLevel::Legendary => 40..70,
49            RngLevel::Mixed => 0..70,
50            RngLevel::Flawed => -20..30,
51            RngLevel::Apocaliptic => -50..30,
52            RngLevel::Doom => -70..40,
53        }
54    }
55
56    /// Turn into a rng generator
57    pub fn to_rng(&self) -> Result<Uniform<i32>, EpochError> {
58        Ok(Uniform::try_from(self.to_range())?)
59    }
60}
61
62/// Build a table with the exact border / separator style you posted
63/// and return the rendered string.
64///
65/// # Parameters
66/// * `$items` - A table builder that implements the `Table` trait
67///   (e.g. `Vec<Vec<...>>.into_table()`, `items.into_table()`, …).
68/// * `$name`  - The name that should be stored in `EpochError::TableStringConversionError`.
69/// * `$id`    - The id that should be stored in `EpochError::TableStringConversionError`.
70#[macro_export]
71macro_rules! items_table {
72    ($items:expr, $name:expr, $id:expr) => {{
73        $items
74            .with_title()
75            .bold(true)
76            .border(
77                cli_table::format::Border::builder()
78                    .top(cli_table::format::HorizontalLine::new('┌', '┐', '┬', '─'))
79                    .bottom(cli_table::format::HorizontalLine::new('└', '┘', '┴', '─'))
80                    .left(cli_table::format::VerticalLine::new('│'))
81                    .right(cli_table::format::VerticalLine::new('│'))
82                    .build(),
83            )
84            .separator(
85                cli_table::format::Separator::builder()
86                    .column(Some(cli_table::format::VerticalLine::new('│')))
87                    .row(Some(cli_table::format::HorizontalLine::new(
88                        '├', '┤', '┼', '─',
89                    )))
90                    .build(),
91            )
92            .display()
93            .map_err(|_e| EpochError::TableStringConversionError {
94                name: $name.clone(),
95                id: $id,
96            })
97    }};
98}