Skip to main content

wowlab_parsers/parsers/
formatting.rs

1#[derive(Clone, Copy)]
2pub(crate) enum NearIntegerStrategy {
3    NearestSaturating {
4        epsilon: f64,
5    },
6    #[cfg(any(feature = "dbc", test))]
7    FractionalFixed {
8        epsilon: f64,
9    },
10}
11
12impl NearIntegerStrategy {
13    fn format(self, value: f64) -> Option<String> {
14        match self {
15            Self::NearestSaturating { epsilon } if (value - value.round()).abs() < epsilon => {
16                Some(wowlab_types::numeric::f64_to_i64_saturating_round(value).to_string())
17            }
18            #[cfg(any(feature = "dbc", test))]
19            Self::FractionalFixed { epsilon } if value.fract().abs() < epsilon => {
20                Some(format!("{value:.0}"))
21            }
22            _ => None,
23        }
24    }
25
26    #[cfg(test)]
27    fn is_near_integer(self, value: f64) -> bool {
28        self.format(value).is_some()
29    }
30}
31
32pub(crate) fn format_decimal_trimmed(
33    value: f64,
34    precision: u8,
35    near_integer: NearIntegerStrategy,
36) -> String {
37    if let Some(integer) = near_integer.format(value) {
38        return integer;
39    }
40
41    format!("{value:.precision$}", precision = usize::from(precision))
42        .trim_end_matches('0')
43        .trim_end_matches('.')
44        .to_string()
45}
46
47#[cfg(test)]
48mod tests;