[NUI] Fix text padding issue
[platform/core/csapi/tizenfx.git] / src / Tizen.NUI / src / public / BaseComponents / AnimatedVectorImageView.cs
1 /*
2  * Copyright(c) 2021 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 using global::System;
19 using System.ComponentModel;
20
21 namespace Tizen.NUI.BaseComponents
22 {
23     /// <summary>
24     /// AnimatedVectorImageView is a class for displaying a vector resource.
25     /// </summary>
26     [EditorBrowsable(EditorBrowsableState.Never)]
27     public partial class AnimatedVectorImageView : LottieAnimationView
28     {
29         #region Constructor, Destructor, Dispose
30         /// <summary>
31         /// Construct VectorAnimationView.
32         /// </summary>
33         [EditorBrowsable(EditorBrowsableState.Never)]
34         public AnimatedVectorImageView() : base()
35         {
36             NUILog.Debug($"[AnimatedVectorImageView START[ constructor objId={GetId()} ] END]");
37         }
38
39         /// <summary>
40         /// Construct VectorAnimationView.
41         /// </summary>
42         /// <param name="scale">Set scaling factor for Vector Animation, while creating.</param>
43         [EditorBrowsable(EditorBrowsableState.Never)]
44         public AnimatedVectorImageView(float scale) : base(scale)
45         {
46             NUILog.Debug($"[AnimatedVectorImageView START[ constructor scale={scale}) objId={GetId()} ] END]");
47         }
48
49         /// <summary>
50         /// You can override it to clean-up your own resources
51         /// </summary>
52         /// <param name="type">DisposeTypes</param>
53         [EditorBrowsable(EditorBrowsableState.Never)]
54         protected override void Dispose(DisposeTypes type)
55         {
56             if (disposed)
57             {
58                 return;
59             }
60             NUILog.Debug($"AnimatedVectorImageView START");
61
62             //Release your own unmanaged resources here.
63             //You should not access any managed member here except static instance.
64             //because the execution order of Finalizes is non-deterministic.
65
66             base.Dispose(type);
67
68             NUILog.Debug($"AnimatedVectorImageView END");
69         }
70         #endregion Constructor, Destructor, Dispose
71
72
73         #region Property
74         /// <summary>
75         /// Set Resource URL
76         /// </summary>
77         // Suppress warning : This has been being used by users, so that the interface can not be changed.
78         [EditorBrowsable(EditorBrowsableState.Never)]
79         public string ResourceURL
80         {
81             get
82             {
83                 return GetValue(ResourceURLProperty) as string;
84             }
85             set
86             {
87                 SetValue(ResourceURLProperty, value);
88                 NotifyPropertyChanged();
89             }
90         }
91
92         private string InternalResourceURL
93         {
94             set
95             {
96                 NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] ResourceURL SET");
97
98                 if (value == resourceUrl)
99                 {
100                     NUILog.Debug($"set same URL! ");
101                     return;
102                 }
103                 resourceUrl = (value == null) ? "" : value;
104                 URL = resourceUrl;
105                 isMinMaxFrameSet = minMaxSetTypes.NotSetByUser;
106                 NUILog.Debug($" [{GetId()}] resourceUrl={resourceUrl}) ]AnimatedVectorImageView END]");
107             }
108             get => resourceUrl;
109         }
110
111         /// <summary>
112         /// Set Resource URL
113         /// </summary>
114         // Suppress warning : This has been being used by users, so that the interface can not be changed.
115         [EditorBrowsable(EditorBrowsableState.Never)]
116         public new string ResourceUrl
117         {
118             get
119             {
120                 return GetValue(ResourceUrlProperty) as string;
121             }
122             set
123             {
124                 SetValue(ResourceUrlProperty, value);
125                 NotifyPropertyChanged();
126             }
127         }
128
129         private string InternalResourceUrl
130         {
131             set
132             {
133                 NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] ResourceUrl SET");
134                 this.ResourceURL = value;
135                 NUILog.Debug($" [{GetId()}] value={value}) ]AnimatedVectorImageView END]");
136             }
137             get
138             {
139                 NUILog.Debug($"[AnimatedVectorImageView [ [{GetId()}] ResourceUrl GET");
140                 return this.ResourceURL;
141             }
142         }
143
144
145         /// <summary>
146         /// RepeatCount of animation.
147         /// The repeat count is 0 by default.
148         /// If the RepeatCount is 0, the animation is never repeated.
149         /// If the RepeatCount is greater than 0, the repeat mode will be taken into account.
150         /// If RepeatCount is -1, animation is infinite loops.
151         /// </summary>
152         [EditorBrowsable(EditorBrowsableState.Never)]
153         public int RepeatCount
154         {
155             get
156             {
157                 return (int)GetValue(RepeatCountProperty);
158             }
159             set
160             {
161                 SetValue(RepeatCountProperty, value);
162                 NotifyPropertyChanged();
163             }
164         }
165
166         private int InternalRepeatCount
167         {
168             set
169             {
170                 NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] RepeatCount SET");
171
172                 repeatCnt = (value < -1) ? -1 : value;
173                 LoopCount = (repeatCnt < 0) ? repeatCnt : repeatCnt + 1;
174
175                 NUILog.Debug($"[{GetId()}] repeatCnt={repeatCnt} ]AnimatedVectorImageView END]");
176             }
177             get => repeatCnt;
178         }
179
180         /// <summary>
181         /// TotalFrame of animation.
182         /// </summary>
183         [EditorBrowsable(EditorBrowsableState.Never)]
184         public new int TotalFrame
185         {
186             get => totalFrameNum;
187         }
188
189         private int totalFrameNum
190         {
191             get => base.TotalFrame;
192         }
193
194         /// <summary>
195         /// CurrentFrame of animation.
196         /// </summary>
197         /// <returns> Returns user set value for the current frame. Cannot provide actual playing current frame. </returns>
198         [EditorBrowsable(EditorBrowsableState.Never)]
199         public new int CurrentFrame
200         {
201             get
202             {
203                 return (int)GetValue(CurrentFrameProperty);
204             }
205             set
206             {
207                 SetValue(CurrentFrameProperty, value);
208                 NotifyPropertyChanged();
209             }
210         }
211
212         private int InternalCurrentFrame
213         {
214             set
215             {
216                 NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] CurrentFrame SET");
217
218                 if (string.IsNullOrEmpty(resourceUrl))
219                 {
220                     throw new InvalidOperationException("Resource Url not yet Set");
221                 }
222
223                 if (value < 0)
224                 {
225                     value = 0;
226                 }
227
228                 innerCurrentFrame = value;
229                 AnimationState = AnimationStates.Paused;
230
231                 base.SetMinMaxFrame(0, IntegerMaxValue);
232                 base.CurrentFrame = innerCurrentFrame;
233
234                 NUILog.Debug($" [{GetId()}] innerCurrentFrame={innerCurrentFrame}) ]AnimatedVectorImageView END]");
235             }
236             get => innerCurrentFrame;
237         }
238
239         /// <summary>
240         /// RepeatMode of animation.
241         /// </summary>
242         [EditorBrowsable(EditorBrowsableState.Never)]
243         public RepeatModes RepeatMode
244         {
245             get
246             {
247                 return (RepeatModes)GetValue(RepeatModeProperty);
248             }
249             set
250             {
251                 SetValue(RepeatModeProperty, value);
252                 NotifyPropertyChanged();
253             }
254         }
255
256         private RepeatModes InternalRepeatMode
257         {
258             set
259             {
260                 NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] RepeatMode SET");
261                 repeatMode = value;
262
263                 switch (repeatMode)
264                 {
265                     case RepeatModes.Restart:
266                         LoopingMode = LoopingModeType.Restart;
267                         break;
268                     case RepeatModes.Reverse:
269                         LoopingMode = LoopingModeType.AutoReverse;
270                         break;
271                     default:
272                         LoopingMode = LoopingModeType.Restart;
273                         break;
274                 }
275
276                 NUILog.Debug($" [{GetId()}] repeatMode={repeatMode}) ]AnimatedVectorImageView END]");
277             }
278             get => repeatMode;
279         }
280
281         /// <summary>
282         /// Get state of animation.
283         /// </summary>
284         [EditorBrowsable(EditorBrowsableState.Never)]
285         public AnimationStates AnimationState
286         {
287             private set
288             {
289                 CurrentAnimationState = value;
290             }
291             get
292             {
293                 if (CurrentAnimationState == AnimationStates.Playing)
294                 {
295                     if (PlayState == PlayStateType.Stopped)
296                     {
297                         CurrentAnimationState = AnimationStates.Stopped;
298                     }
299                 }
300                 return CurrentAnimationState;
301             }
302         }
303         #endregion Property
304
305
306         #region Method
307         /// <summary>
308         /// Set minimum frame and maximum frame
309         /// </summary>
310         /// <param name="minFrame">minimum frame.</param>
311         /// <param name="maxFrame">maximum frame.</param>
312         [EditorBrowsable(EditorBrowsableState.Never)]
313         public void SetMinAndMaxFrame(int minFrame, int maxFrame)
314         {
315             NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] SetMinAndMaxFrame({minFrame}, {maxFrame})");
316
317             minimumFrame = (minFrame) > 0 ? minFrame : 0;
318             maximumFrame = (maxFrame) > 0 ? maxFrame : 0;
319             isMinMaxFrameSet = minMaxSetTypes.SetByMinAndMaxFrameMethod;
320
321             if (minimumFrame > maximumFrame)
322             {
323                 NUILog.Debug($" [{GetId()}] minimumFrame:{minimumFrame} > maximumFrame:{maximumFrame}) ]AnimatedVectorImageView END]");
324                 return;
325             }
326
327             NUILog.Debug($" [{GetId()}] minimumFrame:{minimumFrame}, maximumFrame:{maximumFrame}) ]AnimatedVectorImageView END]");
328         }
329
330         /// <summary>
331         /// SetMinMaxFrame(int startFrame, int endFrame)
332         /// </summary>
333         /// <param name="minFrame"></param>
334         /// <param name="maxFrame"></param>
335         [EditorBrowsable(EditorBrowsableState.Never)]
336         public new void SetMinMaxFrame(int minFrame, int maxFrame)
337         {
338             NUILog.Debug($"SetMinMaxFrame({minFrame}, {maxFrame})!!!");
339
340             minimumFrame = (minFrame) > 0 ? minFrame : 0;
341             maximumFrame = (maxFrame) > 0 ? maxFrame : 0;
342             isMinMaxFrameSet = minMaxSetTypes.SetByBaseSetMinMaxFrameMethod;
343
344             if (minimumFrame >= totalFrameNum)
345             {
346                 minimumFrame = totalFrameNum - 1;
347             }
348
349             if (maximumFrame >= totalFrameNum)
350             {
351                 maximumFrame = totalFrameNum - 1;
352             }
353
354             base.SetMinMaxFrame(minimumFrame, maximumFrame);
355         }
356
357         /// <summary>
358         /// A marker has its start frame and end frame. 
359         /// Animation will play between the start frame and the end frame of the marker if one marker is specified.
360         /// Or animation will play between the start frame of the first marker and the end frame of the second marker if two markers are specified.   *
361         /// </summary>
362         /// <param name="marker1">First marker</param>
363         /// <param name="marker2">Second marker</param>
364         [EditorBrowsable(EditorBrowsableState.Never)]
365         public new void SetMinMaxFrameByMarker(string marker1, string marker2 = null)
366         {
367             NUILog.Debug($"SetMinMaxFrameByMarker({marker1}, {marker2})");
368             isMinMaxFrameSet = minMaxSetTypes.SetByMarker;
369             base.SetMinMaxFrameByMarker(marker1, marker2);
370         }
371
372         /// <summary>
373         /// Play Animation.
374         /// </summary>
375         [EditorBrowsable(EditorBrowsableState.Never)]
376         public new void Play()
377         {
378             NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] AnimationState={AnimationState}, PlayState={PlayState}");
379
380             if (string.IsNullOrEmpty(resourceUrl))
381             {
382                 throw new InvalidOperationException("Resource Url not yet Set");
383             }
384
385             switch (isMinMaxFrameSet)
386             {
387                 case minMaxSetTypes.NotSetByUser:
388                     base.SetMinMaxFrame(0, totalFrameNum - 1);
389                     base.CurrentFrame = 0;
390                     innerCurrentFrame = 0;
391                     break;
392
393                 case minMaxSetTypes.SetByMinAndMaxFrameMethod:
394                     base.SetMinMaxFrame(minimumFrame, maximumFrame);
395                     base.CurrentFrame = minimumFrame;
396                     innerCurrentFrame = minimumFrame;
397                     break;
398
399                 case minMaxSetTypes.SetByMarker:
400                 case minMaxSetTypes.SetByBaseSetMinMaxFrameMethod:
401                 default:
402                     //do nothing!
403                     break;
404             }
405
406             base.Play();
407             AnimationState = AnimationStates.Playing;
408
409             NUILog.Debug($" [{GetId()}] isMinMaxFrameSet={isMinMaxFrameSet}) ]AnimatedVectorImageView END]");
410         }
411
412         /// <summary>
413         /// Pause Animation.
414         /// </summary>
415         [EditorBrowsable(EditorBrowsableState.Never)]
416         public new void Pause()
417         {
418             NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] AnimationState={AnimationState}, PlayState={PlayState}");
419
420             if (string.IsNullOrEmpty(resourceUrl))
421             {
422                 throw new InvalidOperationException("Resource Url not yet Set");
423             }
424
425             base.Pause();
426             AnimationState = AnimationStates.Paused;
427
428             NUILog.Debug($" [{GetId()}] ]AnimatedVectorImageView END]");
429         }
430
431         /// <summary>
432         /// Stop Animation.
433         /// </summary>
434         /// <param name="endAction">Defines, what should be behaviour after cancel operation
435         /// End action is Cancel, Animation Stops at the Current Frame.
436         /// End action is Discard, Animation Stops at the Min Frame
437         /// End action is StopFinal, Animation Stops at the Max Frame
438         /// </param>
439         [EditorBrowsable(EditorBrowsableState.Never)]
440         public void Stop(EndActions endAction = EndActions.Cancel)
441         {
442             NUILog.Debug($"[AnimatedVectorImageView START[ [{GetId()}] endAction:({endAction}), PlayState={PlayState}");
443
444             if (string.IsNullOrEmpty(resourceUrl))
445             {
446                 throw new InvalidOperationException("Resource Url not yet Set");
447             }
448
449             if (AnimationState == AnimationStates.Stopped)
450             {
451                 return;
452             }
453
454             if (innerEndAction != endAction)
455             {
456                 innerEndAction = endAction;
457                 switch (endAction)
458                 {
459                     case EndActions.Cancel:
460                         StopBehavior = StopBehaviorType.CurrentFrame;
461                         break;
462                     case EndActions.Discard:
463                         StopBehavior = StopBehaviorType.MinimumFrame;
464                         break;
465                     case EndActions.StopFinal:
466                         StopBehavior = StopBehaviorType.MaximumFrame;
467                         break;
468                     default:
469                         NUILog.Debug($" [{GetId()}] no endAction : default set");
470                         break;
471                 }
472             }
473             AnimationState = AnimationStates.Stopped;
474
475             base.Stop();
476
477             NUILog.Debug($"isMinMaxFrameSet:{isMinMaxFrameSet}, base.CurrentFrame:{base.CurrentFrame}, totalFrameNum:{totalFrameNum}, minimumFrame:{minimumFrame}, maximumFrame:{maximumFrame}, StopBehavior:{StopBehavior}, endAction:{endAction}");
478
479             switch (isMinMaxFrameSet)
480             {
481                 case minMaxSetTypes.NotSetByUser:
482                     switch(endAction)
483                     {
484                         case EndActions.Cancel:
485                             innerCurrentFrame = base.CurrentFrame;
486                             break;
487                         case EndActions.Discard:
488                             base.CurrentFrame = innerCurrentFrame = 0;
489                             break;
490                         case EndActions.StopFinal:
491                             base.CurrentFrame = innerCurrentFrame= totalFrameNum - 1;
492                             break;
493                     }
494                     break;
495
496                 case minMaxSetTypes.SetByMinAndMaxFrameMethod:
497                     switch (endAction)
498                     {
499                         case EndActions.Cancel:
500                             innerCurrentFrame = base.CurrentFrame;
501                             break;
502                         case EndActions.Discard:
503                             base.CurrentFrame = innerCurrentFrame = minimumFrame;
504                             break;
505                         case EndActions.StopFinal:
506                             base.CurrentFrame = innerCurrentFrame = maximumFrame;
507                             break;
508                     }
509                     break;
510                 case minMaxSetTypes.SetByMarker:
511                 case minMaxSetTypes.SetByBaseSetMinMaxFrameMethod:
512                 default:
513                     //do nothing!
514                     break;
515             }
516             NUILog.Debug($" [{GetId()}] innerCurrentFrame={innerCurrentFrame}, base.CurrentFrame={base.CurrentFrame}");
517             NUILog.Debug($" [{GetId()}] ]AnimatedVectorImageView END]");
518         }
519         #endregion Method
520
521
522         #region Event, Enum, Struct, ETC
523         /// <summary>
524         /// RepeatMode of animation.
525         /// </summary>
526         // Suppress warning : This has been being used by users, so that the interface can not be changed.
527         [System.Diagnostics.CodeAnalysis.SuppressMessage("Naming", "CA1717:Only FlagsAttribute enums should have plural names", Justification = "<Pending>")]
528         [EditorBrowsable(EditorBrowsableState.Never)]
529         public enum RepeatModes
530         {
531             /// <summary>
532             /// When the animation reaches the end and RepeatCount is nonZero, the animation restarts from the beginning. 
533             /// </summary>
534             [EditorBrowsable(EditorBrowsableState.Never)]
535             Restart = LoopingModeType.Restart,
536             /// <summary>
537             /// When the animation reaches the end and RepeatCount nonZero, the animation reverses direction on every animation cycle. 
538             /// </summary>
539             [EditorBrowsable(EditorBrowsableState.Never)]
540             Reverse = LoopingModeType.AutoReverse
541         }
542
543         /// <summary>
544         /// EndActions of animation.
545         /// </summary>
546         // Suppress warning : This has been being used by users, so that the interface can not be changed.
547         [System.Diagnostics.CodeAnalysis.SuppressMessage("Naming", "CA1717:Only FlagsAttribute enums should have plural names", Justification = "<Pending>")]
548         [EditorBrowsable(EditorBrowsableState.Never)]
549         public enum EndActions
550         {
551             /// <summary> End action is Cancel, Animation Stops at the Current Frame.</summary>
552             [EditorBrowsable(EditorBrowsableState.Never)]
553             Cancel = 0,
554             /// <summary>  End action is Discard, Animation Stops at the Min Frame</summary>
555             [EditorBrowsable(EditorBrowsableState.Never)]
556             Discard = 1,
557             /// <summary> End action is StopFinal, Animation Stops at the Max Frame</summary>
558             [EditorBrowsable(EditorBrowsableState.Never)]
559             StopFinal = 2
560         }
561
562         /// <summary>
563         /// AnimationStates of animation.
564         /// </summary>
565         // Suppress warning : This has been being used by users, so that the interface can not be changed.
566         [System.Diagnostics.CodeAnalysis.SuppressMessage("Naming", "CA1717:Only FlagsAttribute enums should have plural names", Justification = "<Pending>")]
567         [EditorBrowsable(EditorBrowsableState.Never)]
568         public enum AnimationStates
569         {
570             /// <summary> The animation has stopped.</summary>
571             [EditorBrowsable(EditorBrowsableState.Never)]
572             Stopped = PlayStateType.Stopped,
573             /// <summary> The animation is playing.</summary>
574             [EditorBrowsable(EditorBrowsableState.Never)]
575             Playing = PlayStateType.Playing,
576             /// <summary> The animation is paused.</summary>
577             [EditorBrowsable(EditorBrowsableState.Never)]
578             Paused = PlayStateType.Paused
579         }
580         #endregion Event, Enum, Struct, ETC
581
582
583         #region Internal
584         #endregion Internal
585
586
587         #region Private
588         private string resourceUrl = null;
589         private int repeatCnt = 0;
590         private RepeatModes repeatMode = RepeatModes.Restart;
591         private int minimumFrame = -1, maximumFrame = -1;
592         private minMaxSetTypes isMinMaxFrameSet = minMaxSetTypes.NotSetByUser;
593         private int innerCurrentFrame = -1;
594         private EndActions innerEndAction = EndActions.Cancel;
595         private enum minMaxSetTypes
596         {
597             NotSetByUser,
598             SetByMinAndMaxFrameMethod,
599             SetByMarker,
600             SetByBaseSetMinMaxFrameMethod,
601         }
602
603         private AnimationStates CurrentAnimationState = AnimationStates.Stopped;
604         private const int IntegerMaxValue = 0x7FFFFFFF;
605         #endregion Private
606     }
607 }