1 /*
2  * Copyright (c) 2020-2021 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 /**
17  * @addtogroup UI_Utils
18  * @{
19  *
20  * @brief Defines basic UI utils.
21  *
22  * @since 1.0
23  * @version 1.0
24  */
25 
26 /**
27  * @file geometry2d.h
28  *
29  * @brief Defines attributes of 2D geometries (including points, lines, rectangles, and polygons) of the lightweight
30  *        graphics system and provides functions for performing operations on the geometries.
31  *
32  * @since 1.0
33  * @version 1.0
34  */
35 
36 #ifndef GRAPHIC_LITE_GEOMETRY2D_H
37 #define GRAPHIC_LITE_GEOMETRY2D_H
38 
39 #include "gfx_utils/graphic_assert.h"
40 #include "gfx_utils/graphic_math.h"
41 #include "gfx_utils/graphic_types.h"
42 #include "gfx_utils/heap_base.h"
43 #include "gfx_utils/rect.h"
44 #include <string.h>
45 
46 namespace OHOS {
47 /**
48  * @brief Defines a line, which consists of the start and end points.
49  * @since 1.0
50  * @version 1.0
51  */
52 class Line : public HeapBase {
53 public:
54     /**
55      * @brief The default constructor used to create a <b>Line</b> instance.
56      * @since 1.0
57      * @version 1.0
58      */
Line()59     Line() {}
60 
61     /**
62      * @brief A constructor used to create a <b>Line</b> instance.
63      * @param a Indicates the start point of the line.
64      * @param b Indicates the end point of the line.
65      * @since 1.0
66      * @version 1.0
67      */
Line(const Vector2<int16_t> & a,const Vector2<int16_t> & b)68     Line(const Vector2<int16_t>& a, const Vector2<int16_t>& b)
69     {
70         vertex_[0] = a;
71         vertex_[1] = b;
72     }
73 
74     /**
75      * @brief A constructor used to create a <b>Line</b> instance.
76      * @param x1 Indicates the X coordinate of the line's start point.
77      * @param y1 Indicates the Y coordinate of the line's start point.
78      * @param x2 Indicates the X coordinate of the line's end point.
79      * @param y2 Indicates the Y coordinate of the line's end point.
80      * @since 1.0
81      * @version 1.0
82      */
Line(int16_t x1,int16_t y1,int16_t x2,int16_t y2)83     Line(int16_t x1, int16_t y1, int16_t x2, int16_t y2)
84     {
85         vertex_[0].x_ = x1;
86         vertex_[0].y_ = y1;
87         vertex_[1].x_ = x2;
88         vertex_[1].y_ = y2;
89     }
90 
91     /**
92      * @brief A destructor used to delete the <b>Line</b> instance.
93      * @since 1.0
94      * @version 1.0
95      */
~Line()96     ~Line() {}
97 
98     /**
99      * @brief Obtains the start or end point of the line based on the value of <b>index</b>.
100      * @param index Indicates the start or end point to obtain. The value <b>0</b> indicates that the start point is to
101      *              be obtained, and <b>1</b> indicates that the end point is to be obtained.
102      * @return Returns the start or end point of the line.
103      * @since 1.0
104      * @version 1.0
105      */
106     Vector2<int16_t>& operator[](uint8_t index)
107     {
108         return vertex_[index];
109     }
110 
111     /**
112      * @brief Obtains the start or end point of the line based on the value of <b>index</b>.
113      * @param index Indicates the start or end point to obtain. The value <b>0</b> indicates that the start point is to
114      *              be obtained, and <b>1</b> indicates that the end point is to be obtained.
115      * @return Returns the start or end point of the line.
116      * @since 1.0
117      * @version 1.0
118      */
119     const Vector2<int16_t> operator[](uint8_t index) const
120     {
121         return vertex_[index];
122     }
123 
124 protected:
125     Vector2<int16_t> vertex_[2]; /* 2: two vertexes of the line */
126 };
127 
128 /**
129  * @brief Defines a polygon, including vertex coordinates and the maximum number of vertices
130  *        (defined by {@link MAX_VERTEX_NUM}).
131  *
132  * @since 1.0
133  * @version 1.0
134  */
135 class Polygon : public HeapBase {
136 public:
137     /**
138      * @brief The default constructor used to create a <b>Polygon</b> instance.
139      * @since 1.0
140      * @version 1.0
141      */
Polygon()142     Polygon() : vertexNum_(0) {}
143 
144     /**
145      * @brief A constructor used to construct a <b>Polygon</b> instance based on a rectangle.
146      *
147      * @param rect Indicates the rectangle used to construct the polygon.
148      * @since 1.0
149      * @version 1.0
150      */
Polygon(const Rect & rect)151     explicit Polygon(const Rect& rect)
152     {
153         vertexNum_ = 4; // 4: number of vertex
154         vertexes_[0].x_ = rect.GetLeft();
155         vertexes_[0].y_ = rect.GetTop();
156 
157         vertexes_[1].x_ = rect.GetRight();
158         vertexes_[1].y_ = rect.GetTop();
159 
160         vertexes_[2].x_ = rect.GetRight();
161         vertexes_[2].y_ = rect.GetBottom();
162 
163         vertexes_[3].x_ = rect.GetLeft();
164         vertexes_[3].y_ = rect.GetBottom();
165     }
166 
167     /**
168      * @brief A constructor used to create a <b>Polygon</b> instance based on the vertex coordinates and the number of
169      *        coordinates.
170      *
171      * The number of vertex coordinates cannot exceed the value of {@link MAX_VERTEX_NUM}.
172      *
173      * @param vertexes Indicates the pointer to the vertex coordinates.
174      * @param vertexNum Indicates the number of vertices.
175      * @since 1.0
176      * @version 1.0
177      */
178     Polygon(const Vector2<int16_t>* vertexes, const uint8_t vertexNum);
179 
180     /**
181      * @brief A destructor used to delete the <b>Polygon</b> instance.
182      * @since 1.0
183      * @version 1.0
184      */
~Polygon()185     ~Polygon() {}
186 
187     /**
188      * @brief Obtains the minimum rectangle that can contain the polygon. All vertices of the polygon are inside this
189      *        rectangle.
190      *
191      * @return Returns the minimum rectangle that contains the polygon.
192      * @since 1.0
193      * @version 1.0
194      */
195     Rect MakeAABB() const;
196 
197     /**
198      * @brief Obtains the number of vertices of the polygon.
199      *
200      * @return Returns the number of vertices.
201      * @since 1.0
202      * @version 1.0
203      */
GetVertexNum()204     uint8_t GetVertexNum() const
205     {
206         return vertexNum_;
207     }
208 
209     /**
210      * @brief Sets the number of vertices of a polygon.
211      * @param vertexNum Indicates the number of vertices.
212      * @since 1.0
213      * @version 1.0
214      */
SetVertexNum(uint8_t vertexNum)215     void SetVertexNum(uint8_t vertexNum)
216     {
217         vertexNum_ = vertexNum;
218     }
219 
220     const Vector2<int16_t> operator[](uint8_t index) const
221     {
222         return vertexes_[index];
223     }
224 
225     Vector2<int16_t>& operator[](uint8_t index)
226     {
227         ASSERT(index < MAX_VERTEX_NUM);
228         return vertexes_[index];
229     }
230 
231     Polygon& operator=(const Rect& rect)
232     {
233         /* clockwise */
234         vertexNum_ = 4; // 4: number of vertex
235         vertexes_[0].x_ = rect.GetLeft();
236         vertexes_[0].y_ = rect.GetTop();
237 
238         vertexes_[1].x_ = rect.GetRight();
239         vertexes_[1].y_ = rect.GetTop();
240 
241         vertexes_[2].x_ = rect.GetRight();
242         vertexes_[2].y_ = rect.GetBottom();
243 
244         vertexes_[3].x_ = rect.GetLeft();
245         vertexes_[3].y_ = rect.GetBottom();
246 
247         return *this;
248     }
249 
250     /** Maximum number of vertices in a polygon */
251     static const uint8_t MAX_VERTEX_NUM = 8;
252 
253 protected:
254     Vector2<int16_t> vertexes_[MAX_VERTEX_NUM]; /* the vertexes of polygon */
255     uint8_t vertexNum_;                         /* the vertex num of polygon */
256 };
257 
258 /**
259  * @brief Checks whether line segment a and line segment b intersect, and returns the intersection point (if available).
260  * @param a Indicates line segment a.
261  * @param b Indicates line segment b.
262  * @param out Indicates the intersection point.
263  * @return Returns <b>true</b> if the two line segments intersect; returns <b>false</b> otherwise.
264  * @since 1.0
265  * @version 1.0
266  */
267 bool Intersect(const Line& a, const Line& b, Vector2<int16_t>& out);
268 
269 /**
270  * @brief Chekcs whether line segment a and line segment b intersect.
271  * @param a Indicates line segment a.
272  * @param b Indicates line segment b.
273  * @return Returns <b>true</b> if the two line segments intersect; returns <b>false</b> otherwise.
274  * @since 1.0
275  * @version 1.0
276  */
277 bool IsIntersect(const Line& a, const Line& b);
278 
279 /**
280  * @brief Clips a polygon by using a line segment.
281  * @param poly Indicates the polygon to clip.
282  * @param line Indicates the line segment used for clipping.
283  * @since 1.0
284  * @version 1.0
285  */
286 void Clip(Polygon& poly, const Line& line);
287 
288 /**
289  * @brief Implements Sutherland-Hodgman, an algorithm used for clipping polygons.
290  * @param clipRect Indicates the rectangle used for clipping the polygon.
291  * @param polygon Indicates the polygon to clip.
292  * @return Returns the polygon after clipping.
293  * @since 1.0
294  * @version 1.0
295  */
296 Polygon SuthHodgClip(const Rect& clipRect, const Polygon& polygon);
297 
298 /**
299  * @brief Clips a polygon by using a line segment and obtains the intersections.
300  * @param line Indicates the line segment used for clipping.
301  * @param poly Indicates the polygon to clip.
302  * @param pOut Indicates the pointer to the intersections.
303  * @param pNum Indicates the pointer to the number of the intersections.
304  * @since 1.0
305  * @version 1.0
306  */
307 void Clip(const Line& line, const Polygon& poly, Vector2<int16_t>* pOut, uint8_t* pNum);
308 } // namespace OHOS
309 #endif // GRAPHIC_LITE_GEOMETRY2D_H
310