Skip to main content

cad_cs/libs/cs/math/
d2.rs

1// 📃 ./src/libs/cs/math/d2.rs
2
3use crate::libs::cs::{
4	abstracts::{AbstractMathCs2, AbstractSignStrExt},
5	model::Cs,
6};
7
8impl AbstractMathCs2 for Cs<2> {
9	/// 📚 【 POL】: Długość rzutu (promień) na płaszczyznę XY.
10	/// 📚 【 ENG】: Projection length (radius) on the XY plane.
11	#[rustfmt::skip] #[inline]	fn rxy(&self) -> f64 { self.0[0].hypot(self.0[1]) }
12
13	/// 📚 【 POL】: Azymut matematyczny (od osi X w stronę Y, CCW).
14	/// 📚 【 ENG】: Mathematical azimuth (from X-axis towards Y, CCW).
15	#[rustfmt::skip] #[inline]	fn arctan_y_x(&self) -> f64 { self.0[1].atan2(self.0[0]) }
16
17	/// 📚 【 POL】: Azymut kompasowy/geodezyjny (od osi Y w stronę X, CW).
18	/// 📚 【 ENG】: Compass/geodetic azimuth (from Y-axis towards X, CW).
19	#[rustfmt::skip] #[inline]	fn arctan_x_y(&self) -> f64 { self.0[0].atan2(self.0[1]) }
20
21	/// 📚 【 POL】: Konwertuje wektor kartezjański [X, Y] na wektor biegunowy [R, Φ] w obrębie Cs2.
22	/// 📚 【 ENG】: Converts a Cartesian vector [X, Y] to a polar vector [R, Φ] within Cs2.
23	#[rustfmt::skip] #[inline]	fn to_rf_from_xy(&self) -> Cs<2> { Cs([self.rxy(), self.arctan_y_x()]) }
24
25	/// 📚 【 POL】: Przekształca współrzędne geograficzne [Szerokość, Długość] w radianach na wektor 3D ECEF (X, Y, Z).
26	/// 📚 【 ENG】: Transforms geographic coordinates [Latitude, Longitude] in radians to a 3D ECEF vector (X, Y, Z).
27	/// ⚙️ 【 POL】: Wykorzystuje zadany promień 'r' (np. promień Ziemi).
28	/// ⚙️ 【 ENG】: Uses the specified radius 'r' (e.g., Earth's radius).
29	fn to_ecef_from_rad_sn_we(&self, r: f64) -> Cs<3> {
30		let (sin_lat, cos_lat) = self.0[0].sin_cos();
31		let (sin_lon, cos_lon) = self.0[1].sin_cos();
32
33		// Oś X: 0°N, 0°E (Greenwich na równiku)
34		// Oś Y: 0°N, 90°E (Ocean Indyjski na równiku)
35		// Oś Z: 90°N (Biegun Północny)
36		// Oś X: 0°N, 0°E | Oś Y: 0°N, 90°E | Oś Z: 90°N
37		Cs([
38			r * cos_lat * cos_lon, // X
39			r * cos_lat * sin_lon, // Y
40			r * sin_lat,           // Z
41		])
42	}
43
44	/// 📚 【 POL】: Zwraca numer ćwiartki na płaszczyźnie XY (1-4).
45	/// 📚 【 ENG】: Returns the quadrant number on the XY plane (1-4).
46	#[rustfmt::skip] #[inline]
47	fn q(&self) -> u8 {
48		match (self.0[0] >= 0.0, self.0[1] >= 0.0) {
49			(true, true) => 1, (false, true) => 2, (false, false) => 3, (true, false) => 4,
50		}
51	}
52
53	/// 📚 【 POL】: Zwraca znaki kierunkowe osi X i Y w formie tablicy stringów (np. ["+", "-"]).
54	/// 📚 【 ENG】: Returns the directional signs of the X and Y axes as an array of strings (e.g., ["+", "-"]).
55	#[rustfmt::skip] #[inline]
56	fn q_sign(&self) -> [&'static str; 2] { [self.0[0].sign_str(), self.0[1].sign_str()] }
57
58	/// 📚 【 POL】: Kwadrat długości rzutu XY (szybsza alternatywa dla rxy).
59	/// 📚 【 ENG】: Squared projection length XY (faster alternative to rxy).
60	#[rustfmt::skip] #[inline]	fn rxy_sq(&self) -> f64 { self.0[0] * self.0[0] + self.0[1] * self.0[1] }
61
62	/// 📚 【 POL】: Iloczyn wektorowy 2D (wyznacznik). Znak określa orientację (lewo/prawo).
63	/// 📚 【 ENG】: 2D cross product (determinant). The sign determines orientation (left/right).
64	#[rustfmt::skip] #[inline]
65	fn cross(&self, other: &Cs<2>) -> f64 { self.0[0] * other.0[1] - self.0[1] * other.0[0] }
66
67	/// 📚 【 POL】: Zwraca wektor prostopadły obrócony o 90° w lewo (CCW).
68	/// 📚 【 ENG】: Returns a perpendicular vector rotated 90° to the left (CCW).
69	#[rustfmt::skip] #[inline]
70	fn perp(&self) -> Cs<2> { Cs([-self.0[1], self.0[0]]) }
71}