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_Components
18  * @{
19  *
20  * @brief Defines UI components such as buttons, texts, images, lists, and progress bars.
21  *
22  * @since 1.0
23  * @version 1.0
24  */
25 
26 /**
27  * @file ui_arc_label.h
28  *
29  * @brief Defines the attributes of an arc label.
30  *
31  * The attributes include the center and radius of an arc, angle range, and text orientation.
32  *
33  * @since 1.0
34  * @version 1.0
35  */
36 
37 #ifndef GRAPHIC_LITE_UI_ARC_LABEL_H
38 #define GRAPHIC_LITE_UI_ARC_LABEL_H
39 
40 #include "animator/animator.h"
41 #include "common/text.h"
42 #include "components/ui_view.h"
43 
44 namespace OHOS {
45 class ArcLabelScrollListener : public HeapBase {
46 public:
47     virtual void Finish() = 0;
48 };
49 
50 /**
51  * @brief Defines functions related to an arc label.
52  *
53  * @since 1.0
54  * @version 1.0
55  */
56 class UIArcLabel : public UIView {
57 public:
58     /**
59      * @brief A default constructor used to create a <b>UIArcLabel</b> instance.
60      *
61      * @since 1.0
62      * @version 1.0
63      */
64     UIArcLabel();
65 
66     /**
67      * @brief A destructor used to delete the <b>UIArcLabel</b> instance.
68      *
69      * @since 1.0
70      * @version 1.0
71      */
72     virtual ~UIArcLabel();
73 
74     /**
75      * @brief Obtains the view type.
76      *
77      * @return Returns <b>UI_ARC_LABEL</b>, as defined in {link UIViewType}.
78      * @since 1.0
79      * @version 1.0
80      */
GetViewType()81     UIViewType GetViewType() const override
82     {
83         return UI_ARC_LABEL;
84     }
85 
86     /**
87      * @brief Obtains the width of this arc text.
88      *
89      * @return Returns the width of this arc text.
90      * @since 1.0
91      * @version 1.0
92      */
GetWidth()93     int16_t GetWidth() override
94     {
95         ReMeasure();
96         return UIView::GetWidth();
97     }
98 
99     /**
100      * @brief Obtains the height of this arc text.
101      *
102      * @return Returns the height of this arc text.
103      * @since 1.0
104      * @version 1.0
105      */
GetHeight()106     int16_t GetHeight() override
107     {
108         ReMeasure();
109         return UIView::GetHeight();
110     }
111 
112     /**
113      * @brief Sets the view style.
114      * @param style Indicates the view style.
115      * @since 1.0
116      * @version 1.0
117      */
SetStyle(Style & style)118     void SetStyle(Style& style) override
119     {
120         UIView::SetStyle(style);
121     }
122 
123     /**
124      * @brief Sets a style.
125      *
126      * @param key Indicates the key of the style to set.
127      * @param value Indicates the value matching the key.
128      * @since 1.0
129      * @version 1.0
130      */
131     void SetStyle(uint8_t key, int64_t value) override;
132 
133     /**
134      * @brief Sets the text content for this arc label.
135      *
136      * @param text Indicates the pointer to the text content.
137      * @since 1.0
138      * @version 1.0
139      */
140     void SetText(const char* text);
141 
142     /**
143      * @brief Obtains the text of this arc label.
144      *
145      * @return Returns the text.
146      * @since 1.0
147      * @version 1.0
148      */
149     const char* GetText() const;
150 
151     /**
152      * @brief Sets the alignment mode for this text.
153      *
154      * @param horizontalAlign Indicates the horizontal alignment mode to set,
155      *                        which can be {@link TEXT_ALIGNMENT_LEFT},
156      *                        {@link TEXT_ALIGNMENT_CENTER}, or {@link TEXT_ALIGNMENT_RIGHT}.
157      * @since 1.0
158      * @version 1.0
159      */
160     void SetAlign(UITextLanguageAlignment horizontalAlign);
161 
162     /**
163      * @brief Obtains the horizontal alignment mode.
164      *
165      * @return Returns the horizontal alignment mode.
166      * @since 1.0
167      * @version 1.0
168      */
169     UITextLanguageAlignment GetHorAlign();
170 
171     /**
172      * @brief Obtains the direction of this text.
173      *
174      * @return Returns the text direction, as defined in {@link UITextLanguageDirect}.
175      * @since 1.0
176      * @version 1.0
177      */
178     UITextLanguageDirect GetDirect();
179 
180     /**
181      * @brief Sets the font ID for this arc label.
182      *
183      * @param fontId Indicates the font ID composed of font name and size.
184      * @since 1.0
185      * @version 1.0
186      */
187     void SetFontId(uint16_t fontId);
188 
189     /**
190      * @brief Obtains the font ID composed of font name and size.
191      *
192      * @return Returns the front ID of this arc label.
193      * @since 1.0
194      * @version 1.0
195      */
196     uint16_t GetFontId();
197 
198     /**
199      * @brief Sets the font for this arc label.
200      *
201      * @param name Indicates the pointer to the font name.
202      * @param size Indicates the font size to set.
203      * @since 1.0
204      * @version 1.0
205      */
206     void SetFont(const char* name, uint8_t size);
207 
208     /**
209      * @brief Sets the center position for this arc text.
210      *
211      * @param x Indicates the x-coordinate to set.
212      * @param y Indicates the y-coordinate to set.
213      * @since 1.0
214      * @version 1.0
215      */
SetArcTextCenter(int16_t x,int16_t y)216     void SetArcTextCenter(int16_t x, int16_t y)
217     {
218         if ((arcCenter_.x != x) || (arcCenter_.y != y)) {
219             arcCenter_.x = x;
220             arcCenter_.y = y;
221             RefreshArcLabel();
222         }
223     }
224 
225     /**
226      * @brief Obtains the center position of this arc text.
227      *
228      * @return Returns the center position of this arc text.
229      * @since 1.0
230      * @version 1.0
231      */
GetArcTextCenter()232     Point GetArcTextCenter() const
233     {
234         return arcCenter_;
235     }
236 
237     /**
238      * @brief Sets the radius for this arc text.
239      *
240      * @param radius Indicates the radius to set.
241      * @since 1.0
242      * @version 1.0
243      */
SetArcTextRadius(uint16_t radius)244     void SetArcTextRadius(uint16_t radius)
245     {
246         if (radius_ != radius) {
247             radius_ = radius;
248             RefreshArcLabel();
249         }
250     }
251 
252     /**
253      * @brief Obtains the radius of this arc text.
254      *
255      * @return Returns the radius of this arc text.
256      * @since 1.0
257      * @version 1.0
258      */
GetArcTextRadius()259     uint16_t GetArcTextRadius() const
260     {
261         return radius_;
262     }
263 
264     /**
265      * @brief Sets the start angle and end angle for this arc text.
266      *
267      * The angle in 12 o'clock direction is 0 degrees, and the value increases clockwise.
268      * The text direction is clockwise when the end angle is greater than the start angle, and the text direction is
269      * counterclockwise otherwise.
270      *
271      * @param startAngle Indicates the start angle to set.
272      * @param endAngle Indicates the end angle to set.
273      * @since 1.0
274      * @version 1.0
275      */
SetArcTextAngle(int16_t startAngle,int16_t endAngle)276     void SetArcTextAngle(int16_t startAngle, int16_t endAngle)
277     {
278         if ((startAngle_ != startAngle) || (endAngle_ != endAngle)) {
279             startAngle_ = startAngle;
280             endAngle_ = endAngle;
281             RefreshArcLabel();
282         }
283     }
284 
285     /**
286      * @brief Obtains the start angle of this arc text.
287      *
288      * @return Returns the start angle of this arc text.
289      * @since 1.0
290      * @version 1.0
291      */
GetArcTextStartAngle()292     int16_t GetArcTextStartAngle() const
293     {
294         return startAngle_;
295     }
296 
297     /**
298      * @brief Obtains the end angle of this arc text.
299      *
300      * @return Returns the end angle of this arc text.
301      * @since 1.0
302      * @version 1.0
303      */
GetArcTextEndAngle()304     int16_t GetArcTextEndAngle() const
305     {
306         return endAngle_;
307     }
308 
309     /**
310      * @brief Sets the orientation for this arc text.
311      *
312      * @param orientation Indicates the text orientation to set.
313      * @since 1.0
314      * @version 1.0
315      */
SetArcTextOrientation(TextOrientation orientation)316     void SetArcTextOrientation(TextOrientation orientation)
317     {
318         if (orientation_ != orientation) {
319             orientation_ = orientation;
320             RefreshArcLabel();
321         }
322     }
323 
324     /**
325      * @brief Obtains the orientation of this arc text.
326      *
327      * @return Returns the orientation of this arc text.
328      * @since 1.0
329      * @version 1.0
330      */
GetArcTextOrientation()331     TextOrientation GetArcTextOrientation() const
332     {
333         return orientation_;
334     }
335 
336     /**
337      * @brief Is it compatible with older versions.
338      *
339      * @param compatibilityMode Indicates compatible with older versions.
340      */
SetCompatibilityMode(bool compatibilityMode)341     void SetCompatibilityMode(bool compatibilityMode)
342     {
343         if (compatibilityMode_ != compatibilityMode) {
344             compatibilityMode_ = compatibilityMode;
345             RefreshArcLabel();
346         }
347     }
348 
349     /**
350      * @brief Draws an arc text.
351      *
352      * @param invalidatedArea Indicates the area to draw.
353      * @since 1.0
354      * @version 1.0
355      */
356     void OnDraw(BufferInfo& gfxDstBuffer, const Rect& invalidatedArea) override;
357 
358     /**
359      * @brief Start animation.
360      *
361      */
362     void Start();
363 
364     /**
365      * @brief Stop animation.
366      *
367      */
368     void Stop();
369 
370     /**
371      * @brief Sets the number of cycles.
372      *
373      * @param rollCount Indicates number of cycles.
374      */
375     void SetRollCount(const uint16_t rollCount);
376 
377     /**
378      * @brief Register a listener that contains a callback to be invoked scroll state change.
379      *
380      * @param scrollListener Indicates the listener to register.
381      */
382     void RegisterScrollListener(ArcLabelScrollListener* scrollListener);
383 
384     /**
385      * @brief Set animation speed.
386      *
387      * @param speed Indicates the scroll speed to set.
388      */
389     void SetRollSpeed(const uint16_t speed);
390 
391     /**
392      * @brief Obtains the scroll speed for this arclabel.
393      *
394      * @return Returns the scroll speed.
395      */
396     uint16_t GetRollSpeed() const;
397 
398     void ReMeasure() override;
399 protected:
400     Text* arcLabelText_;
401     bool compatibilityMode_;
402     float offsetAngle_;
403     ArcTextInfo arcTextInfo_;
404     bool needRefresh_;
405     bool hasAnimator_;
406 
InitArcLabelText()407     virtual void InitArcLabelText()
408     {
409         if (arcLabelText_ == nullptr) {
410             arcLabelText_ = new Text();
411             if (arcLabelText_ == nullptr) {
412                 GRAPHIC_LOGE("new Text fail");
413                 return;
414             }
415         }
416     }
417     void RefreshArcLabel();
418 
419     virtual void DrawArcText(BufferInfo& gfxDstBuffer,
420                              const Rect& mask,
421                              OpacityType opaScale,
422                              ArcTextInfo arcTextInfo,
423                              TextOrientation orientation);
424 
425     virtual Rect GetArcTextRect(const char* text,
426                                 uint16_t fontId,
427                                 uint8_t fontSize,
428                                 const Point& arcCenter,
429                                 int16_t letterSpace,
430                                 TextOrientation orientation,
431                                 const ArcTextInfo& arcTextInfo);
432 
433     virtual uint32_t GetLineEnd(int16_t maxLength);
434 
435     virtual uint16_t GetArcLength();
436 private:
437     friend class ArcLabelAnimator;
438     void MeasureArcTextInfo();
439     void OnMeasureArcTextInfo(const uint16_t arcAngle, const uint16_t letterHeight);
440 
441     Point textSize_;
442     uint16_t radius_;
443     int16_t startAngle_;
444     int16_t endAngle_;
445     Point arcCenter_;
446     TextOrientation orientation_;
447     struct {
448         Animator* animator;
449         ArcLabelScrollListener* scrollListener;
450         uint16_t speed;
451         uint16_t rollCount;
452         float secondLapOffsetAngle_;
453     } animator_;
454 };
455 } // namespace OHOS
456 #endif // GRAPHIC_LITE_UI_ARC_LABEL_H
457