oxiproj_transformations/
lib.rs1#![forbid(unsafe_code)]
2pub mod batch_helmert;
10pub mod conversions;
11mod internal;
12pub mod transformations;
13
14use oxiproj_core::{Ellipsoid, IoUnits, Operation, ProjError, ProjResult};
15
16pub use oxiproj_core::GridRegistry;
20
21pub use transformations::helmert_batch;
22
23pub mod epoch_transform;
25pub use epoch_transform::{epoch_path, plate_for_frame, propagate_epoch};
26
27pub mod covariance;
29pub use covariance::{
30 propagate_through_affine_2d, propagate_through_helmert_3, propagate_through_helmert_7_xy,
31};
32
33pub mod frame_chain;
34pub use frame_chain::{
35 apply_frame_transform, find_frame_transform, FrameTransform, FRAME_TRANSFORMS,
36};
37
38pub mod epoch_pipeline;
40pub use epoch_pipeline::{transform_epoch_aware, EpochAwareResult};
41
42pub trait TransParamLookup {
45 fn get_dms(&self, key: &str) -> Option<f64>;
47 fn get_f64(&self, key: &str) -> Option<f64>;
49 fn get_int(&self, key: &str) -> Option<i64>;
51 fn get_str(&self, key: &str) -> Option<&str>;
53 fn get_bool(&self, key: &str) -> bool;
55 fn exists(&self, key: &str) -> bool;
57}
58
59pub struct TransParams<'a> {
61 pub ellipsoid: &'a Ellipsoid,
63 pub params: &'a dyn TransParamLookup,
65 pub registry: Option<&'a dyn GridRegistry>,
67}
68
69pub struct TransBuild {
71 pub operation: Box<dyn Operation>,
73 pub left: IoUnits,
75 pub right: IoUnits,
77}
78
79impl TransBuild {
80 pub fn new(operation: Box<dyn Operation>, left: IoUnits, right: IoUnits) -> TransBuild {
82 TransBuild {
83 operation,
84 left,
85 right,
86 }
87 }
88}
89
90pub fn build(name: &str, p: &TransParams) -> ProjResult<TransBuild> {
93 conversions::build(name, p)
94 .or_else(|| transformations::build(name, p))
95 .unwrap_or(Err(ProjError::InvalidOp))
96}
97
98#[cfg(test)]
99mod tests {
100 use super::*;
101 use oxiproj_core::Ellipsoid;
102
103 struct NoParams;
104 impl TransParamLookup for NoParams {
105 fn get_dms(&self, _key: &str) -> Option<f64> {
106 None
107 }
108 fn get_f64(&self, _key: &str) -> Option<f64> {
109 None
110 }
111 fn get_int(&self, _key: &str) -> Option<i64> {
112 None
113 }
114 fn get_str(&self, _key: &str) -> Option<&str> {
115 None
116 }
117 fn get_bool(&self, _key: &str) -> bool {
118 false
119 }
120 fn exists(&self, _key: &str) -> bool {
121 false
122 }
123 }
124
125 fn wgs84() -> Ellipsoid {
126 Ellipsoid::named("WGS84").unwrap()
127 }
128
129 #[test]
130 fn build_noop_succeeds() {
131 let ell = wgs84();
132 let np = NoParams;
133 let pp = TransParams {
134 ellipsoid: &ell,
135 params: &np,
136 registry: None,
137 };
138 assert!(build("noop", &pp).is_ok());
139 }
140
141 #[test]
142 fn build_unknown_is_invalid_op() {
143 let ell = wgs84();
144 let np = NoParams;
145 let pp = TransParams {
146 ellipsoid: &ell,
147 params: &np,
148 registry: None,
149 };
150 assert_eq!(build("nonexistent", &pp).err(), Some(ProjError::InvalidOp));
151 }
152}