Thu, 21 Dec 2017 10:46:41 +0200
Smallest angles
| 7 | 1 | def degree_rep(angle): |
| 2 | from math import degrees | |
| 3 | return '∠ %.2f°' % degrees(angle) | |
| 4 | ||
| 5 | def position_vector(vertex): | |
| 6 | assert isinstance(vertex, Vertex) | |
| 7 | return Vector(*vertex.coordinates) | |
| 8 | ||
| 9 | def angle_magnitude_key(angle): | |
| 10 | ''' | |
| 11 | Returns how great an angle is. | |
| 12 | ''' | |
| 13 | from math import pi as π | |
| 14 | normalized_angle = abs(angle) % (2 * π) | |
| 15 | if normalized_angle > π: | |
| 16 | normalized_angle = (2 * π) - normalized_angle | |
| 17 | return normalized_angle | |
| 18 | ||
| 0 | 19 | class Vertex: |
| 20 | def __init__(self, x, y, z): | |
| 5 | 21 | if not all(is_real(coordinate) for coordinate in (x, y, z)): |
| 22 | raise ValueError(str.format('Bad vertex coordinates: {!r}', | |
| 23 | (x, y, z), | |
| 24 | )) | |
| 0 | 25 | self.x, self.y, self.z = x, y, z |
| 26 | def __repr__(self): | |
| 27 | return str.format('Vertex({!r}, {!r}, {!r})', self.x, self.y, self.z) | |
| 28 | def distance_to(self, other): | |
| 29 | # can't use hypot because of 3 arguments | |
| 30 | from math import sqrt | |
| 31 | return sqrt( | |
| 32 | (self.x - other.x) ** 2 + | |
| 33 | (self.y - other.y) ** 2 + | |
| 34 | (self.z - other.z) ** 2 | |
| 35 | ) | |
|
3
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
36 | @property |
|
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
37 | def coordinates(self): |
|
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
38 | return self.x, self.y, self.z |
| 5 | 39 | def __add__(self, other): |
| 7 | 40 | assert not (type(self) == type(other) == Vertex) |
| 41 | if type(self) == Vector and type(other) == Vector: | |
| 42 | result_type = Vector | |
| 43 | else: | |
| 44 | result_type = Vertex | |
| 45 | return result_type(self.x + other.x, self.y + other.y, self.z + other.z) | |
| 46 | def __radd__(self, other): | |
| 47 | return self + other | |
| 5 | 48 | def __neg__(self): |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
49 | return type(self)(-self.x, -self.y, -self.z) |
| 5 | 50 | def __sub__(self, other): |
| 7 | 51 | result = self + (-position_vector(other)) |
| 52 | if isinstance(other, Vertex): | |
| 53 | return Vector(*result.coordinates) | |
| 54 | else: | |
| 55 | return result | |
| 5 | 56 | def __mul__(self, scalar): |
| 7 | 57 | assert is_real(scalar) |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
58 | return type(self)(self.x * scalar, self.y * scalar, self.z * scalar) |
| 5 | 59 | def __rmul__(self, other): |
| 60 | return self * other | |
| 61 | def __truediv__(self, scalar): | |
| 7 | 62 | assert is_real(scalar) |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
63 | return type(self)(self.x / scalar, self.y / scalar, self.z / scalar) |
| 5 | 64 | def __floordiv__(self, scalar): |
| 7 | 65 | assert is_real(scalar) |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
66 | return type(self)(self.x // scalar, self.y // scalar, self.z // scalar) |
| 5 | 67 | def __matmul__(self, transformation_matrix): |
| 68 | return transform(self, transformation_matrix) | |
| 69 | def __eq__(self, other): | |
| 70 | return self.coordinates == other.coordinates | |
| 71 | def __lt__(self, other): | |
| 72 | return self.coordinates < other.coordinates | |
| 73 | def __hash__(self): | |
| 74 | return hash(self.coordinates) | |
| 75 | ||
| 76 | class VertexOp: | |
| 77 | def __init__(self, callable): | |
| 78 | self.callable = callable | |
| 79 | def __rmul__(self, coordinate): | |
| 80 | return self.callable(coordinate) | |
| 0 | 81 | |
| 82 | class LineSegment: | |
| 83 | def __init__(self, v1, v2): | |
| 84 | self.v1, self.v2 = v1, v2 | |
| 85 | def __repr__(self): | |
| 86 | return str.format('LineSegment({!r}, {!r})', self.v1, self.v2) | |
|
3
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
87 | @property |
| 7 | 88 | def length(self): |
| 89 | return self.v1.distance_to(self.v2) | |
| 90 | @property | |
|
3
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
91 | def vertices(self): |
|
1dc58f44d556
Can now write dat files, added direct color handling
Santeri Piippo
parents:
1
diff
changeset
|
92 | return self.v1, self.v2 |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
93 | def __len__(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
94 | return 2 |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
95 | def __getitem__(self, index): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
96 | return self.vertices[index] |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
97 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
98 | class IndexRing: |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
99 | def __init__(self, container): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
100 | self.container = container |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
101 | def __getitem__(self, index): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
102 | return self.container[index % len(self.container)] |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
103 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
104 | class Vector(Vertex): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
105 | def __init__(self, x, y, z): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
106 | super().__init__(x, y, z) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
107 | def __repr__(self): |
| 7 | 108 | return str.format('Vector({!r}, {!r}, {!r})', self.x, self.y, self.z) |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
109 | def length(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
110 | from math import sqrt |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
111 | return sqrt(self.x ** 2 + self.y ** 2 + self.z ** 2) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
112 | def normalized(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
113 | length = self.length() |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
114 | if length > 0: |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
115 | return Vector(self.x / length, self.y / length, self.z / length) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
116 | else: |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
117 | return Vector(0, 0, 0) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
118 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
119 | def dot_product(v1, v2): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
120 | ''' Returns the dot product v1 · v2. ''' |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
121 | return v1.x * v2.x + v1.y * v2.y + v1.z * v2.z |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
122 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
123 | def cross_product(v1, v2): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
124 | ''' Returns the cross product v1 × v2. ''' |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
125 | return Vector( |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
126 | x = v1.y * v2.z - v1.z * v2.y, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
127 | y = v1.z * v2.x - v1.x * v2.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
128 | z = v1.x * v2.y - v1.y * v2.x, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
129 | ) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
130 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
131 | def unit_normal(a, b, c): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
132 | x = Matrix3x3([ |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
133 | 1, a.y, a.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
134 | 1, b.y, b.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
135 | 1, c.y, c.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
136 | ]).determinant() |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
137 | y = Matrix3x3([ |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
138 | a.x, 1, a.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
139 | b.x, 1, b.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
140 | c.x, 1, c.z, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
141 | ]).determinant() |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
142 | z = Matrix3x3([ |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
143 | a.x, a.y, 1, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
144 | b.x, b.y, 1, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
145 | c.x, c.y, 1, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
146 | ]).determinant() |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
147 | return Vector(x, y, z).normalized() |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
148 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
149 | def pairs(iterable, *, count = 2): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
150 | ''' |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
151 | Iterates the given iterable and returns tuples containing `count` |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
152 | sequential values in the iterable. |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
153 | |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
154 | Formally, for a vector A with indices 0…n and pair count k, this |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
155 | function yields: |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
156 | (A₀, A₁, …, Aₖ), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
157 | (A₁, A₂, …, Aₖ₊₁), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
158 | …, |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
159 | (Aₙ₋₂, Aₙ₋₁, …, Aₖ₋₂), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
160 | (Aₙ₋₁, A₀, …, Aₖ₋₁). |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
161 | ''' |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
162 | iterable_count = len(iterable) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
163 | for index in range(iterable_count): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
164 | yield tuple( |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
165 | iterable[(index + offset) % iterable_count] |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
166 | for offset in range(count) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
167 | ) |
| 0 | 168 | |
| 1 | 169 | class Polygon: |
| 170 | def __init__(self, vertices): | |
| 171 | self.vertices = vertices | |
| 172 | def __repr__(self): | |
| 173 | return str.format('Polygon({!r})', self.vertices) | |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
174 | def area(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
175 | total = Vector(0, 0, 0) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
176 | for v1, v2 in pairs(self.vertices): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
177 | total += cross_product(v1, v2) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
178 | return dot_product(total, unit_normal(self.vertices[0], self.vertices[1], self.vertices[2])) |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
179 | def centroid(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
180 | ... |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
181 | raise NotImplementedError |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
182 | def __getitem__(self, index): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
183 | return self.vertices[index % len(self.vertices)] |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
184 | def __len__(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
185 | return len(self.vertices) |
| 7 | 186 | @property |
| 187 | def perimeter_lines(self): | |
| 188 | for v1, v2 in pairs(self.vertices): | |
| 189 | yield LineSegment(v1, v2) | |
| 190 | @property | |
| 191 | def smallest_angle(self): | |
| 192 | from math import acos, inf | |
| 193 | min_angle = inf | |
| 194 | for v1, v2, v3 in pairs(self.vertices, count = 3): | |
| 195 | vec1 = (position_vector(v3) - position_vector(v2)).normalized() | |
| 196 | vec2 = (position_vector(v1) - position_vector(v2)).normalized() | |
| 197 | cosine = dot_product(vec1, vec2) / vec1.length() / vec2.length() | |
| 198 | min_angle = min(min_angle, angle_magnitude_key(acos(cosine))) | |
| 199 | return min_angle | |
| 200 | @property | |
| 201 | def hairline_ratio(self): | |
| 202 | lengths = [line.length for line in self.perimeter_lines] | |
| 203 | return max(lengths) / min(lengths) | |
| 1 | 204 | |
| 0 | 205 | def is_real(number): |
| 206 | return isinstance(number, int) or isinstance(number, float) | |
| 207 | ||
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
208 | class Matrix3x3: |
| 0 | 209 | ''' |
| 210 | A 3×3 matrix forming the top-left portion of a full 4×4 transformation | |
| 211 | matrix. | |
| 212 | ''' | |
| 213 | def __init__(self, values): | |
| 214 | assert(all(is_real(x) for x in values)) | |
| 215 | assert len(values) == 9 | |
| 216 | self.values = values | |
| 217 | def __repr__(self): | |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
218 | return str.format('Matrix3x3({!r})', self.values) |
| 0 | 219 | def __getitem__(self, index): |
| 220 | return self.values[index] | |
|
6
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
221 | def determinant(self): |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
222 | v = self.values |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
223 | return sum([ |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
224 | +(v[0] * v[4] * v[8]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
225 | +(v[1] * v[5] * v[6]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
226 | +(v[2] * v[3] * v[7]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
227 | -(v[2] * v[4] * v[6]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
228 | -(v[1] * v[3] * v[8]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
229 | -(v[0] * v[5] * v[7]), |
|
6da1e81c5652
Added code to compute areas of triangles and quadrilaterals
Santeri Piippo
parents:
5
diff
changeset
|
230 | ]) |
| 0 | 231 | |
| 232 | def complete_matrix(matrix, anchor): | |
| 233 | ''' | |
| 234 | Combines a 3×3 matrix and an anchor vertex into a full 4×4 | |
| 235 | transformation matrix. | |
| 236 | ''' | |
| 237 | return [ | |
| 238 | matrix[0], matrix[1], matrix[2], anchor.x, | |
| 239 | matrix[3], matrix[4], matrix[5], anchor.y, | |
| 240 | matrix[6], matrix[7], matrix[8], anchor.z, | |
| 241 | 0, 0, 0, 1, | |
| 242 | ] | |
| 243 | ||
| 244 | def transform(vertex, transformation_matrix): | |
| 245 | ''' | |
| 246 | Transforms a vertex by a 4×4 transformation matrix. | |
| 247 | ''' | |
| 248 | u = transformation_matrix[0] * vertex.x \ | |
| 249 | + transformation_matrix[1] * vertex.y \ | |
| 250 | + transformation_matrix[2] * vertex.z \ | |
| 251 | + transformation_matrix[3] | |
| 252 | v = transformation_matrix[4] * vertex.x \ | |
| 253 | + transformation_matrix[5] * vertex.y \ | |
| 254 | + transformation_matrix[6] * vertex.z \ | |
| 255 | + transformation_matrix[7] | |
| 256 | w = transformation_matrix[8] * vertex.x \ | |
| 257 | + transformation_matrix[9] * vertex.y \ | |
| 258 | + transformation_matrix[10] * vertex.z \ | |
| 259 | + transformation_matrix[11] | |
| 260 | return Vertex(u, v, w) |