use crate::ellipsoid::{GRS80, WGS84};
use crate::error::ProjError;
use crate::tm::TmParams;
#[derive(Debug, Clone, Copy)]
pub enum CrsKind {
Geographic4326,
WebMercator,
TransverseMercator(TmParams),
}
pub fn kind_for(epsg: u32) -> Result<CrsKind, ProjError> {
match epsg {
4326 => Ok(CrsKind::Geographic4326),
7844 => Ok(CrsKind::Geographic4326),
3857 => Ok(CrsKind::WebMercator),
32601..=32660 => Ok(CrsKind::TransverseMercator(TmParams::utm_north(
(epsg - 32600) as u8,
WGS84,
))),
32701..=32760 => Ok(CrsKind::TransverseMercator(TmParams::utm_south(
(epsg - 32700) as u8,
WGS84,
))),
7846..=7859 => Ok(CrsKind::TransverseMercator(TmParams::utm_south(
(epsg - 7800) as u8,
GRS80,
))),
other => Err(ProjError::UnsupportedEpsg(other)),
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn known_codes_resolve() {
assert!(matches!(kind_for(4326).unwrap(), CrsKind::Geographic4326));
assert!(matches!(kind_for(7844).unwrap(), CrsKind::Geographic4326));
assert!(matches!(kind_for(3857).unwrap(), CrsKind::WebMercator));
assert!(matches!(kind_for(32754).unwrap(), CrsKind::TransverseMercator(_)));
assert!(matches!(kind_for(7855).unwrap(), CrsKind::TransverseMercator(_)));
}
#[test]
fn mga_zone_55_central_meridian_is_147() {
if let CrsKind::TransverseMercator(p) = kind_for(7855).unwrap() {
assert_eq!(p.lon0_deg, 147.0);
assert_eq!(p.false_northing, 10_000_000.0);
} else {
panic!("expected TM");
}
}
#[test]
fn utm_zone_30_north_central_meridian_is_neg_3() {
if let CrsKind::TransverseMercator(p) = kind_for(32630).unwrap() {
assert_eq!(p.lon0_deg, -3.0);
assert_eq!(p.false_northing, 0.0);
} else {
panic!("expected TM");
}
}
#[test]
fn unsupported_returns_error() {
assert!(matches!(kind_for(99999).unwrap_err(), ProjError::UnsupportedEpsg(99999)));
}
}