projective_grid/square/
alignment.rs1use crate::square::index::GridCoords;
2use serde::{Deserialize, Serialize};
3
4#[derive(Clone, Copy, Debug, PartialEq, Eq, Serialize, Deserialize)]
12pub struct GridTransform {
13 pub a: i32,
14 pub b: i32,
15 pub c: i32,
16 pub d: i32,
17}
18
19impl GridTransform {
20 pub const IDENTITY: GridTransform = GridTransform {
21 a: 1,
22 b: 0,
23 c: 0,
24 d: 1,
25 };
26
27 #[inline]
29 pub fn apply(&self, i: i32, j: i32) -> GridCoords {
30 GridCoords {
31 i: self.a * i + self.b * j,
32 j: self.c * i + self.d * j,
33 }
34 }
35
36 pub fn inverse(&self) -> Option<GridTransform> {
38 let det = self.a * self.d - self.b * self.c;
39 if det != 1 && det != -1 {
40 return None;
41 }
42 Some(GridTransform {
43 a: self.d / det,
44 b: -self.b / det,
45 c: -self.c / det,
46 d: self.a / det,
47 })
48 }
49}
50
51#[derive(Clone, Copy, Debug, PartialEq, Eq, Serialize, Deserialize)]
53pub struct GridAlignment {
54 pub transform: GridTransform,
55 pub translation: [i32; 2],
56}
57
58impl GridAlignment {
59 pub const IDENTITY: GridAlignment = GridAlignment {
60 transform: GridTransform::IDENTITY,
61 translation: [0, 0],
62 };
63
64 #[inline]
66 pub fn map(&self, i: i32, j: i32) -> GridCoords {
67 let g = self.transform.apply(i, j);
68 GridCoords {
69 i: g.i + self.translation[0],
70 j: g.j + self.translation[1],
71 }
72 }
73
74 pub fn inverse(&self) -> Option<GridAlignment> {
75 let inv = self.transform.inverse()?;
76 let [tx, ty] = self.translation;
77 let g = inv.apply(-tx, -ty);
78 Some(GridAlignment {
79 transform: inv,
80 translation: [g.i, g.j],
81 })
82 }
83}
84
85pub const GRID_TRANSFORMS_D4: [GridTransform; 8] = [
87 GridTransform {
89 a: 1,
90 b: 0,
91 c: 0,
92 d: 1,
93 },
94 GridTransform {
95 a: 0,
96 b: 1,
97 c: -1,
98 d: 0,
99 },
100 GridTransform {
101 a: -1,
102 b: 0,
103 c: 0,
104 d: -1,
105 },
106 GridTransform {
107 a: 0,
108 b: -1,
109 c: 1,
110 d: 0,
111 },
112 GridTransform {
114 a: -1,
115 b: 0,
116 c: 0,
117 d: 1,
118 },
119 GridTransform {
120 a: 1,
121 b: 0,
122 c: 0,
123 d: -1,
124 },
125 GridTransform {
126 a: 0,
127 b: 1,
128 c: 1,
129 d: 0,
130 },
131 GridTransform {
132 a: 0,
133 b: -1,
134 c: -1,
135 d: 0,
136 },
137];