#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub enum MathClass {
Ord, Op, Bin, Rel, Open, Close, Punct, Inner, }
#[rustfmt::skip]
const SPACING_TABLE: [[i8; 8]; 8] = [
[ 0, 3, 4, 5, 0, 0, 0, 3],
[ 3, 4, 0, 5, 0, 0, 0, 3],
[ 4, 4, 0, 0, 4, 0, 0, 4],
[ 5, 5, 0, 0, 5, 0, 0, 5],
[ 0, 0, 0, 0, 0, 0, 0, 0],
[ 0, 3, 4, 5, 0, 0, 0, 3],
[ 3, 3, 0, 5, 3, 3, 3, 3],
[ 3, 3, 4, 5, 3, 0, 3, 3],
];
#[rustfmt::skip]
const TIGHT_SPACING_TABLE: [[i8; 8]; 8] = [
[ 0, 3, 0, 0, 0, 0, 0, 0],
[ 3, 3, 0, 0, 0, 0, 0, 0],
[ 0, 0, 0, 0, 0, 0, 0, 0],
[ 0, 0, 0, 0, 0, 0, 0, 0],
[ 0, 0, 0, 0, 0, 0, 0, 0],
[ 0, 3, 0, 0, 0, 0, 0, 0],
[ 0, 0, 0, 0, 0, 0, 0, 0],
[ 0, 3, 0, 0, 0, 0, 0, 0],
];
impl MathClass {
fn index(self) -> usize {
match self {
Self::Ord => 0,
Self::Op => 1,
Self::Bin => 2,
Self::Rel => 3,
Self::Open => 4,
Self::Close => 5,
Self::Punct => 6,
Self::Inner => 7,
}
}
}
pub fn atom_spacing(left: MathClass, right: MathClass, tight: bool) -> f64 {
let table = if tight { &TIGHT_SPACING_TABLE } else { &SPACING_TABLE };
table[left.index()][right.index()] as f64
}
pub fn mu_to_em(mu: f64, quad: f64) -> f64 {
mu * quad / 18.0
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_ord_bin_spacing() {
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Bin, false), 4.0);
}
#[test]
fn test_ord_rel_spacing() {
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Rel, false), 5.0);
}
#[test]
fn test_ord_ord_no_spacing() {
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Ord, false), 0.0);
}
#[test]
fn test_tight_eliminates_most_spacing() {
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Bin, true), 0.0);
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Rel, true), 0.0);
}
#[test]
fn test_tight_keeps_op_spacing() {
assert_eq!(atom_spacing(MathClass::Ord, MathClass::Op, true), 3.0);
assert_eq!(atom_spacing(MathClass::Op, MathClass::Ord, true), 3.0);
}
#[test]
fn test_mu_to_em() {
let quad = 1.0;
assert!((mu_to_em(3.0, quad) - 3.0 / 18.0).abs() < 1e-10);
assert!((mu_to_em(4.0, quad) - 4.0 / 18.0).abs() < 1e-10);
assert!((mu_to_em(5.0, quad) - 5.0 / 18.0).abs() < 1e-10);
}
}