OpenTTD Source 20260531-master-g0e951f3528
geometry_type.hpp
Go to the documentation of this file.
1/*
2 * This file is part of OpenTTD.
3 * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
4 * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
5 * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <https://www.gnu.org/licenses/old-licenses/gpl-2.0>.
6 */
7
9
10#ifndef GEOMETRY_TYPE_HPP
11#define GEOMETRY_TYPE_HPP
12
13#if defined(__APPLE__)
14 /* Mac OS X already has both Rect and Point declared */
15# define Rect OTTD_Rect
16# define Point OTTD_Point
17#endif /* __APPLE__ */
18
26inline int CentreBounds(int min, int max, int size)
27{
28 return (min + max - size + 1) / 2;
29}
30
32template <typename T>
33struct Coord2D {
34 T x = 0;
35 T y = 0;
36
37 constexpr Coord2D() = default;
38 constexpr Coord2D(T x, T y) : x(x), y(y) {}
39
44 constexpr auto operator<=>(const Coord2D<T> &) const = default;
45};
46
48template <typename T>
49struct Coord3D {
50 T x = 0;
51 T y = 0;
52 T z = 0;
53
54 constexpr Coord3D() = default;
55 constexpr Coord3D(T x, T y, T z) : x(x), y(y), z(z) {}
56
61 constexpr auto operator<=>(const Coord3D<T> &) const = default;
62};
63
66
68struct Dimension {
69 uint width;
70 uint height;
71
72 constexpr Dimension() : width(0), height(0) {}
73 constexpr Dimension(uint w, uint h) : width(w), height(h) {}
74
75 bool operator< (const Dimension &other) const
76 {
77 int x = this->width - other.width;
78 if (x != 0) return x < 0;
79 return this->height < other.height;
80 }
81
82 bool operator== (const Dimension &other) const
83 {
84 return this->width == other.width && this->height == other.height;
85 }
86};
87
90 uint8_t left = 0;
91 uint8_t top = 0;
92 uint8_t right = 0;
93 uint8_t bottom = 0;
94
95 static const RectPadding zero;
96
101 constexpr uint Horizontal() const { return this->left + this->right; }
102
107 constexpr uint Vertical() const { return this->top + this->bottom; }
108};
109
110inline const RectPadding RectPadding::zero{};
111
113struct Rect {
114 int left = 0;
115 int top = 0;
116 int right = 0;
117 int bottom = 0;
118
123 inline int Width() const { return this->right - this->left + 1; }
124
129 inline int Height() const { return this->bottom - this->top + 1; }
130
136 [[nodiscard]] inline Rect Shrink(int s) const
137 {
138 return {this->left + s, this->top + s, this->right - s, this->bottom - s};
139 }
140
147 [[nodiscard]] inline Rect Shrink(int h, int v) const
148 {
149 return {this->left + h, this->top + v, this->right - h, this->bottom - v};
150 }
151
160 [[nodiscard]] inline Rect Shrink(int left, int top, int right, int bottom) const
161 {
162 return {this->left + left, this->top + top, this->right - right, this->bottom - bottom};
163 }
164
170 [[nodiscard]] inline Rect Shrink(const RectPadding &other) const
171 {
172 return {this->left + other.left, this->top + other.top, this->right - other.right, this->bottom - other.bottom};
173 }
174
181 [[nodiscard]] inline Rect Shrink(const RectPadding &horz, const RectPadding &vert) const
182 {
183 return {this->left + horz.left, this->top + vert.top, this->right - horz.right, this->bottom - vert.bottom};
184 }
185
191 [[nodiscard]] inline Rect Expand(int s) const
192 {
193 return this->Shrink(-s);
194 }
195
201 [[nodiscard]] inline Rect Expand(const RectPadding &other) const
202 {
203 return {this->left - other.left, this->top - other.top, this->right + other.right, this->bottom + other.bottom};
204 }
205
212 [[nodiscard]] inline Rect Translate(int x, int y) const
213 {
214 return {this->left + x, this->top + y, this->right + x, this->bottom + y};
215 }
216
223 [[nodiscard]] inline Rect WithWidth(int width, bool end) const
224 {
225 return end
226 ? this->WithX(this->right - width + 1, this->right)
227 : this->WithX(this->left, this->left + width - 1);
228 }
229
236 [[nodiscard]] inline Rect Indent(int indent, bool end) const
237 {
238 return end
239 ? this->WithX(this->left, this->right - indent)
240 : this->WithX(this->left + indent, this->right);
241 }
242
249 [[nodiscard]] inline Rect WithHeight(int height, bool end = false) const
250 {
251 return end
252 ? this->WithY(this->bottom - height + 1, this->bottom)
253 : this->WithY(this->top, this->top + height - 1);
254 }
255
261 inline bool Contains(const Point &pt) const
262 {
263 /* This is a local version of IsInsideMM, to avoid including math_func everywhere. */
264 return (uint)(pt.x - this->left) <= (uint)(this->right - this->left) && (uint)(pt.y - this->top) <= (uint)(this->bottom - this->top);
265 }
266
272 [[nodiscard]] inline Rect CentreToHeight(int height) const
273 {
274 int new_top = CentreBounds(this->top, this->bottom, height);
275 return {this->left, new_top, this->right, new_top + height - 1};
276 }
277
284 [[nodiscard]] inline Rect WithX(int new_left, int new_right) const { return {new_left, this->top, new_right, this->bottom}; }
285
292 [[nodiscard]] inline Rect WithY(int new_top, int new_bottom) const { return {this->left, new_top, this->right, new_bottom}; }
293
299 [[nodiscard]] inline Rect WithX(const Rect &other) const { return this->WithX(other.left, other.right); }
300
306 [[nodiscard]] inline Rect WithY(const Rect &other) const { return this->WithY(other.top, other.bottom); }
307};
308
314 int x = 0;
315 int y = 0;
316 int width = 0;
317 int height = 0;
318};
319
320#endif /* GEOMETRY_TYPE_HPP */
#define T
Climate temperate.
Definition engines.h:91
Coord2D< int > Point
Coordinates of a point in 2D.
int CentreBounds(int min, int max, int size)
Determine where to position a centred object.
#define Point
Macro that prevents name conflicts between included headers.
A coordinate with two dimensions.
constexpr auto operator<=>(const Coord2D< T > &) const =default
Compare with another instance of this class.
T x
X coordinate.
T y
Y coordinate.
constexpr auto operator<=>(const Coord3D< T > &) const =default
Compare with another instance of this class.
T z
Z coordinate.
Specification of a rectangle with an absolute top-left coordinate and a (relative) width/height.
Padding dimensions to apply to each side of a Rect.
constexpr uint Horizontal() const
Get total horizontal padding of RectPadding.
constexpr uint Vertical() const
Get total vertical padding of RectPadding.
Specification of a rectangle with absolute coordinates of all edges.
Rect WithWidth(int width, bool end) const
Copy Rect and set its width.
int Width() const
Get width of Rect.
Rect Expand(const RectPadding &other) const
Copy and expand Rect by a RectPadding.
Rect Shrink(int s) const
Copy and shrink Rect by s pixels.
Rect Shrink(const RectPadding &other) const
Copy and shrink Rect by a RectPadding.
Rect WithHeight(int height, bool end=false) const
Copy Rect and set its height.
Rect Indent(int indent, bool end) const
Copy Rect and indent it from its position.
Rect CentreToHeight(int height) const
Centre a vertical dimension within this Rect.
int Height() const
Get height of Rect.
Rect WithY(int new_top, int new_bottom) const
Create a new Rect, replacing the top and bottom coordinates.
Rect WithX(int new_left, int new_right) const
Create a new Rect, replacing the left and right coordinates.
Rect WithX(const Rect &other) const
Create a new Rect, replacing the left and right coordinates.
Rect Shrink(int h, int v) const
Copy and shrink Rect by h horizontal and v vertical pixels.
Rect Translate(int x, int y) const
Copy and translate Rect by x,y pixels.
Rect Shrink(int left, int top, int right, int bottom) const
Copy and shrink Rect by pixels.
Rect WithY(const Rect &other) const
Create a new Rect, replacing the top and bottom coordinates.
Rect Shrink(const RectPadding &horz, const RectPadding &vert) const
Copy and shrink Rect by a different horizontal and vertical RectPadding.
bool Contains(const Point &pt) const
Test if a point falls inside this Rect.
Rect Expand(int s) const
Copy and expand Rect by s pixels.