1 /*
2 * Copyright (c) 2022-2023 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 #include "core/components_ng/pattern/loading_progress/loading_progress_modifier.h"
17
18 #include "base/geometry/arc.h"
19 #include "core/common/container.h"
20 #include "core/components_ng/pattern/loading_progress/loading_progress_utill.h"
21 #include "core/components_ng/render/drawing_prop_convertor.h"
22 #include "core/pipeline_ng/pipeline_context.h"
23
24 namespace OHOS::Ace::NG {
25 namespace {
26 constexpr float TOTAL_ANGLE = 360.0f;
27 constexpr float ROTATEX = -116.0f;
28 constexpr float ROTATEY = 30.0f;
29 constexpr float ROTATEZ = 22.0f;
30 constexpr float COUNT = 50.0f;
31 constexpr float HALF = 0.5f;
32 constexpr float DOUBLE = 2.0f;
33 constexpr int32_t SKEWY = 3;
34 constexpr int32_t SCALEY = 4;
35 constexpr float RING_ALPHA = 200 / 255.0f;
36 constexpr int32_t RING_ALPHA_DARK = 255;
37 constexpr int32_t RING_ALPHA_DARK_BACKGROUNG = 150;
38 constexpr Color DEFAULT_COLOR_DARK = Color(0x99FFFFFF);
39 constexpr int32_t TOTAL_POINTS_COUNT = 20;
40 constexpr int32_t TAIL_ANIAMTION_DURATION = 400;
41 constexpr int32_t TRANS_DURATION = 100;
42 constexpr float TOTAL_TAIL_LENGTH = 60.0f;
43 constexpr float TAIL_ALPHA_RATIO = 0.82f;
44 constexpr float INITIAL_SIZE_SCALE = 0.825f;
45 constexpr float INITIAL_OPACITY_SCALE = 0.7f;
46 constexpr float COMET_TAIL_ANGLE = 3.0f;
47 constexpr int32_t LOADING_DURATION = 1200;
48 constexpr float FOLLOW_START = 72.0f;
49 constexpr float FOLLOW_SPAN = 10.0f;
50 constexpr float FULL_COUNT = 100.0f;
51 constexpr float STAGE1 = 0.25f;
52 constexpr float STAGE2 = 0.65f;
53 constexpr float STAGE3 = 0.75f;
54 constexpr float STAGE4 = 0.85f;
55 constexpr float STAGE5 = 1.0f;
56 constexpr float OPACITY1 = 0.2f;
57 constexpr float OPACITY2 = 0.7f;
58 constexpr float OPACITY3 = 1.0f;
59 constexpr float SIZE_SCALE1 = 0.65f;
60 constexpr float SIZE_SCALE2 = 0.825f;
61 constexpr float SIZE_SCALE3 = 0.93f;
62 constexpr float MOVE_STEP = 0.06f;
63 constexpr float TRANS_OPACITY_SPAN = 0.3f;
64 constexpr float FULL_OPACITY = 255.0f;
65 constexpr float FAKE_DELTA = 0.01f;
66 constexpr float BASE_SCALE = 0.707f; // std::sqrt(2)/2
67 constexpr float REFRESH_DARK_MODE_RING_BLUR_RADIUS = 0.4f;
68 constexpr int32_t ANIMATION_MIN_FFR = 15;
69 constexpr int32_t ANIMATION_MAX_FFR = 60;
70 constexpr int32_t ANIMATION_EXPECT_FFR = 30;
71 } // namespace
LoadingProgressModifier(LoadingProgressOwner loadingProgressOwner,const WeakPtr<Pattern> & pattern)72 LoadingProgressModifier::LoadingProgressModifier(
73 LoadingProgressOwner loadingProgressOwner, const WeakPtr<Pattern>& pattern)
74 : enableLoading_(AceType::MakeRefPtr<PropertyBool>(true)),
75 offset_(AceType::MakeRefPtr<PropertyOffsetF>(OffsetF())),
76 contentSize_(AceType::MakeRefPtr<PropertySizeF>(SizeF())),
77 date_(AceType::MakeRefPtr<AnimatablePropertyFloat>(0.0f)),
78 color_(AceType::MakeRefPtr<AnimatablePropertyColor>(LinearColor::TRANSPARENT)),
79 centerDeviation_(AceType::MakeRefPtr<AnimatablePropertyFloat>(0.0f)),
80 cometOpacity_(AceType::MakeRefPtr<AnimatablePropertyFloat>(INITIAL_OPACITY_SCALE)),
81 cometSizeScale_(AceType::MakeRefPtr<AnimatablePropertyFloat>(INITIAL_SIZE_SCALE)),
82 cometTailLen_(AceType::MakeRefPtr<AnimatablePropertyFloat>(TOTAL_TAIL_LENGTH)),
83 sizeScale_(AceType::MakeRefPtr<AnimatablePropertyFloat>(1.0f)),
84 useContentModifier_(AceType::MakeRefPtr<PropertyBool>(false)),
85 pattern_(pattern),
86 loadingProgressOwner_(loadingProgressOwner)
87 {
88 AttachProperty(enableLoading_);
89 AttachProperty(offset_);
90 AttachProperty(contentSize_);
91 AttachProperty(date_);
92 AttachProperty(color_);
93 AttachProperty(centerDeviation_);
94 AttachProperty(cometOpacity_);
95 AttachProperty(cometSizeScale_);
96 AttachProperty(cometTailLen_);
97 };
98
onDraw(DrawingContext & context)99 void LoadingProgressModifier::onDraw(DrawingContext& context)
100 {
101 if (useContentModifier_->Get()) {
102 return;
103 }
104 if (!enableLoading_->Get()) {
105 return;
106 }
107 float date = date_->Get();
108 auto diameter = std::min(contentSize_->Get().Width(), contentSize_->Get().Height());
109 RingParam ringParam;
110 ringParam.strokeWidth = LoadingProgressUtill::GetRingStrokeWidth(diameter) * sizeScale_->Get();
111 ringParam.radius = LoadingProgressUtill::GetRingRadius(diameter) * sizeScale_->Get();
112 ringParam.movement =
113 (ringParam.radius * DOUBLE + ringParam.strokeWidth) * centerDeviation_->Get() * sizeScale_->Get();
114 ringParam.darkRingRadius = LoadingProgressUtill::GetRingDarkRadius(diameter) * sizeScale_->Get();
115 ringParam.darkBackgroundWidth = LoadingProgressUtill::GetRingDarkBackgroundWidth(diameter) * sizeScale_->Get();
116 ringParam.darkBackgroundRadius = LoadingProgressUtill::GetRingDarkBackgroundRadius(diameter) * sizeScale_->Get();
117
118 CometParam cometParam;
119 cometParam.radius = LoadingProgressUtill::GetCometRadius(diameter) * sizeScale_->Get();
120 cometParam.alphaScale = cometOpacity_->Get();
121 cometParam.sizeScale = cometSizeScale_->Get();
122 cometParam.pointCount = GetCometNumber();
123
124 auto orbitRadius = LoadingProgressUtill::GetOrbitRadius(diameter) * sizeScale_->Get();
125 if (date > COUNT) {
126 DrawRing(context, ringParam);
127 DrawOrbit(context, cometParam, orbitRadius, date);
128 } else {
129 DrawOrbit(context, cometParam, orbitRadius, date);
130 DrawRing(context, ringParam);
131 }
132 }
133
DrawRing(DrawingContext & context,const RingParam & ringParam)134 void LoadingProgressModifier::DrawRing(DrawingContext& context, const RingParam& ringParam)
135 {
136 auto& canvas = context.canvas;
137 canvas.Save();
138 RSPen pen;
139 RSFilter filter;
140 auto ringColor = color_->Get();
141 ringColor.BlendOpacity(RING_ALPHA);
142 pen.SetColor(ToRSColor(ringColor));
143 if (Container::CurrentColorMode() == ColorMode::DARK) {
144 if (ringColor.GetValue() == DEFAULT_COLOR_DARK.GetValue()) {
145 ringColor = LinearColor::WHITE;
146 }
147 // draw ring background
148 DrawRingBackground(context, ringParam, ringColor);
149
150 ringColor.BlendOpacity(RING_ALPHA_DARK / FULL_OPACITY);
151 pen.SetColor(ToRSColor(ringColor));
152
153 #ifndef USE_ROSEN_DRAWING
154 filter.SetImageFilter(RSImageFilter::CreateBlurImageFilter(
155 ringParam.darkRingRadius, ringParam.darkRingRadius, RSTileMode::DECAL, nullptr));
156 #else
157 filter.SetImageFilter(RSRecordingImageFilter::CreateBlurImageFilter(
158 ringParam.darkRingRadius, ringParam.darkRingRadius, RSTileMode::DECAL, nullptr));
159 #endif
160 pen.SetFilter(filter);
161 }
162 if (loadingProgressOwner_ == LoadingProgressOwner::REFRESH && Container::CurrentColorMode() == ColorMode::DARK) {
163 filter.SetMaskFilter(RSMaskFilter::CreateBlurMaskFilter(
164 RSBlurType::NORMAL, PipelineBase::GetCurrentDensity() * REFRESH_DARK_MODE_RING_BLUR_RADIUS));
165 pen.SetFilter(filter);
166 }
167 pen.SetWidth(ringParam.strokeWidth);
168 pen.SetAntiAlias(true);
169 canvas.AttachPen(pen);
170 canvas.DrawCircle(
171 { offset_->Get().GetX() + contentSize_->Get().Width() * HALF,
172 offset_->Get().GetY() + contentSize_->Get().Height() * HALF + ringParam.movement },
173 ringParam.radius);
174 canvas.DetachPen();
175 canvas.Restore();
176 }
177
DrawRingBackground(DrawingContext & context,const RingParam & ringParam,LinearColor & ringColor)178 void LoadingProgressModifier::DrawRingBackground(
179 DrawingContext& context, const RingParam& ringParam, LinearColor& ringColor)
180 {
181 auto& canvas = context.canvas;
182 canvas.Save();
183 RSPen pen;
184
185 ringColor.BlendOpacity(RING_ALPHA_DARK_BACKGROUNG / FULL_OPACITY);
186 pen.SetColor(ToRSColor(ringColor));
187
188 RSFilter filter;
189 #ifndef USE_ROSEN_DRAWING
190 filter.SetImageFilter(RSImageFilter::CreateBlurImageFilter(
191 ringParam.darkBackgroundRadius, ringParam.darkBackgroundRadius, RSTileMode::DECAL, nullptr));
192 #else
193 filter.SetImageFilter(RSRecordingImageFilter::CreateBlurImageFilter(
194 ringParam.darkBackgroundRadius, ringParam.darkBackgroundRadius, RSTileMode::DECAL, nullptr));
195 #endif
196 pen.SetFilter(filter);
197 pen.SetWidth(ringParam.darkBackgroundWidth);
198 pen.SetAntiAlias(true);
199 canvas.AttachPen(pen);
200 canvas.DrawCircle({ offset_->Get().GetX() + contentSize_->Get().Width() * HALF,
201 offset_->Get().GetY() + contentSize_->Get().Height() * HALF + ringParam.movement },
202 ringParam.radius);
203 canvas.DetachPen();
204 canvas.Restore();
205 }
206
DrawOrbit(DrawingContext & context,const CometParam & cometParam,float orbitRadius,float date)207 void LoadingProgressModifier::DrawOrbit(
208 DrawingContext& context, const CometParam& cometParam, float orbitRadius, float date)
209 {
210 auto pointCounts = cometParam.pointCount;
211 auto& canvas = context.canvas;
212 float width = contentSize_->Get().Width();
213 float height = contentSize_->Get().Height();
214 double angle = TOTAL_ANGLE * date / FULL_COUNT;
215 RSCamera3D camera;
216 RSMatrix matrix;
217 AdjustMatrix(camera, matrix);
218 auto center = RSPoint(offset_->Get().GetX() + width / 2, offset_->Get().GetY() + height / 2);
219 RSBrush brush;
220 brush.SetAntiAlias(true);
221 canvas.Save();
222 canvas.Translate(center.GetX(), center.GetY());
223 std::vector<RSPoint> points;
224 for (uint32_t i = 0; i < pointCounts; i++) {
225 RSPoint point;
226 float cometAngal = GetCurentCometAngle(angle, pointCounts - i, pointCounts);
227 float rad = cometAngal * PI_NUM / (TOTAL_ANGLE * HALF);
228 point.SetX(std::cos(rad) * orbitRadius);
229 point.SetY(-std::sin(rad) * orbitRadius);
230 points.push_back(point);
231 }
232 std::vector<RSPoint> distPoints(points.size());
233 matrix.MapPoints(distPoints, points, points.size());
234 auto cometColor = color_->Get();
235 float colorAlpha = cometColor.GetAlpha() / FULL_OPACITY;
236 if (Container::CurrentColorMode() == ColorMode::DARK && cometColor.GetValue() == DEFAULT_COLOR_DARK.GetValue()) {
237 colorAlpha = OPACITY3;
238 }
239 auto baseAlpha = colorAlpha * cometParam.alphaScale;
240 for (uint32_t i = 0; i < distPoints.size(); i++) {
241 RSPoint pointCenter = distPoints[i];
242 if (cometColor.GetValue() == Color::FOREGROUND.GetValue()) {
243 brush.SetColor(ToRSColor(cometColor));
244 } else {
245 float setAlpha = GetCurentCometOpacity(baseAlpha, distPoints.size() - i, distPoints.size());
246 if (NearZero(setAlpha)) {
247 continue;
248 }
249 brush.SetColor(
250 ToRSColor(Color::FromRGBO(cometColor.GetRed(), cometColor.GetGreen(), cometColor.GetBlue(), setAlpha)));
251 }
252 canvas.AttachBrush(brush);
253 canvas.DrawCircle(pointCenter, cometParam.radius * cometParam.sizeScale);
254 }
255 canvas.DetachBrush();
256 canvas.Restore();
257 }
258
AdjustMatrix(RSCamera3D & camera,RSMatrix & matrix)259 void LoadingProgressModifier::AdjustMatrix(RSCamera3D& camera, RSMatrix& matrix)
260 {
261 camera.Save();
262 camera.RotateYDegrees(ROTATEY);
263 camera.RotateXDegrees(ROTATEX);
264 camera.RotateZDegrees(ROTATEZ);
265 camera.ApplyToMatrix(matrix);
266 camera.Restore();
267 auto temp = matrix.Get(SKEWY);
268 matrix.Set(RSMatrix::SKEW_Y, matrix.Get(SCALEY));
269 matrix.Set(RSMatrix::SCALE_Y, temp);
270 }
271
StartRecycleRingAnimation()272 void LoadingProgressModifier::StartRecycleRingAnimation()
273 {
274 auto context = PipelineBase::GetCurrentContext();
275 CHECK_NULL_VOID(context);
276 auto previousStageCurve = AceType::MakeRefPtr<CubicCurve>(0.0f, 0.0f, 0.67f, 1.0f);
277 AnimationOption option;
278 RefPtr<FrameRateRange> frameRateRange =
279 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
280 option.SetFrameRateRange(frameRateRange);
281 option.SetDuration(isVisible_ ? LOADING_DURATION : 0);
282 option.SetCurve(previousStageCurve);
283 if (context->IsFormRender() && !IsDynamicComponent()) {
284 option.SetIteration(1);
285 } else {
286 option.SetIteration(-1);
287 }
288 AnimationUtils::OpenImplicitAnimation(option, previousStageCurve, nullptr);
289 auto middleStageCurve = AceType::MakeRefPtr<CubicCurve>(0.33f, 0.0f, 0.67f, 1.0f);
290 AnimationUtils::AddKeyFrame(
291 STAGE1, middleStageCurve, [weakCenterDeviation = AceType::WeakClaim(AceType::RawPtr(centerDeviation_))]() {
292 auto centerDeviation = weakCenterDeviation.Upgrade();
293 CHECK_NULL_VOID(centerDeviation);
294 centerDeviation->Set(-1 * MOVE_STEP);
295 });
296 auto latterStageCurve = AceType::MakeRefPtr<CubicCurve>(0.33f, 0.0f, 1.0f, 1.0f);
297 AnimationUtils::AddKeyFrame(
298 STAGE3, latterStageCurve, [weakCenterDeviation = AceType::WeakClaim(AceType::RawPtr(centerDeviation_))]() {
299 auto centerDeviation = weakCenterDeviation.Upgrade();
300 CHECK_NULL_VOID(centerDeviation);
301 centerDeviation->Set(MOVE_STEP);
302 });
303 AnimationUtils::AddKeyFrame(
304 STAGE5, latterStageCurve, [weakCenterDeviation = AceType::WeakClaim(AceType::RawPtr(centerDeviation_))]() {
305 auto centerDeviation = weakCenterDeviation.Upgrade();
306 CHECK_NULL_VOID(centerDeviation);
307 centerDeviation->Set(0.0f);
308 });
309 AnimationUtils::CloseImplicitAnimation();
310 }
311
StartRecycleCometAnimation()312 void LoadingProgressModifier::StartRecycleCometAnimation()
313 {
314 auto context = PipelineBase::GetCurrentContext();
315 CHECK_NULL_VOID(context);
316 auto curve = AceType::MakeRefPtr<LinearCurve>();
317 AnimationOption option;
318 RefPtr<FrameRateRange> frameRateRange =
319 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
320 option.SetFrameRateRange(frameRateRange);
321 option.SetDuration(isVisible_ ? LOADING_DURATION : 0);
322 option.SetCurve(curve);
323 if (context->IsFormRender() && !IsDynamicComponent()) {
324 option.SetIteration(1);
325 } else {
326 option.SetIteration(-1);
327 }
328
329 cometOpacity_->Set(OPACITY2);
330 cometTailLen_->Set(TOTAL_TAIL_LENGTH);
331 AnimationUtils::OpenImplicitAnimation(option, curve, nullptr);
332 AnimationUtils::AddKeyFrame(STAGE1, curve,
333 [weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
334 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
335 auto cometOpacity = weakCometOpacity.Upgrade();
336 if (cometOpacity) {
337 cometOpacity->Set(OPACITY1);
338 }
339 auto cometSizeScale = weakCometSizeScale.Upgrade();
340 if (cometSizeScale) {
341 cometSizeScale->Set(SIZE_SCALE1);
342 }
343 });
344 AnimationUtils::AddKeyFrame(STAGE2, curve,
345 [weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
346 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
347 auto cometOpacity = weakCometOpacity.Upgrade();
348 if (cometOpacity) {
349 cometOpacity->Set(OPACITY3);
350 }
351 auto cometSizeScale = weakCometSizeScale.Upgrade();
352 if (cometSizeScale) {
353 cometSizeScale->Set(SIZE_SCALE3);
354 }
355 });
356 AnimationUtils::AddKeyFrame(STAGE3, curve,
357 [weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
358 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
359 auto cometOpacity = weakCometOpacity.Upgrade();
360 if (cometOpacity) {
361 cometOpacity->Set(OPACITY3);
362 }
363 auto cometSizeScale = weakCometSizeScale.Upgrade();
364 if (cometSizeScale) {
365 cometSizeScale->Set(1.0f);
366 }
367 });
368 AnimationUtils::AddKeyFrame(STAGE4, curve,
369 [weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
370 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
371 auto cometOpacity = weakCometOpacity.Upgrade();
372 if (cometOpacity) {
373 cometOpacity->Set(OPACITY3);
374 }
375 auto cometSizeScale = weakCometSizeScale.Upgrade();
376 if (cometSizeScale) {
377 cometSizeScale->Set(SIZE_SCALE3);
378 }
379 });
380 AnimationUtils::AddKeyFrame(STAGE5, curve,
381 [weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
382 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
383 auto cometOpacity = weakCometOpacity.Upgrade();
384 if (cometOpacity) {
385 cometOpacity->Set(OPACITY2);
386 }
387 auto cometSizeScale = weakCometSizeScale.Upgrade();
388 if (cometSizeScale) {
389 cometSizeScale->Set(SIZE_SCALE2);
390 }
391 });
392 AnimationUtils::CloseImplicitAnimation();
393 }
394
StartCometTailAnimation()395 void LoadingProgressModifier::StartCometTailAnimation()
396 {
397 auto curve = AceType::MakeRefPtr<LinearCurve>();
398 AnimationOption option;
399 RefPtr<FrameRateRange> frameRateRange =
400 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
401 option.SetFrameRateRange(frameRateRange);
402 option.SetDuration(TAIL_ANIAMTION_DURATION);
403 option.SetIteration(1);
404 option.SetCurve(curve);
405 auto pattern = pattern_.Upgrade();
406 auto host = pattern? pattern->GetHost(): nullptr;
407 auto context = host? host->GetContextRefPtr(): nullptr;
408 AnimationUtils::Animate(option, [weakCometTailLen = AceType::WeakClaim(AceType::RawPtr(cometTailLen_))]() {
409 auto cometTailLen = weakCometTailLen.Upgrade();
410 CHECK_NULL_VOID(cometTailLen);
411 cometTailLen->Set(TOTAL_TAIL_LENGTH);
412 }, nullptr, nullptr, context);
413 }
414
GetCurentCometOpacity(float baseOpacity,uint32_t index,uint32_t totalNumber)415 float LoadingProgressModifier::GetCurentCometOpacity(float baseOpacity, uint32_t index, uint32_t totalNumber)
416 {
417 return baseOpacity * std::pow(TAIL_ALPHA_RATIO, std::clamp(index, 1u, totalNumber) - 1);
418 }
419
GetCurentCometAngle(float baseAngle,uint32_t index,uint32_t totalNumber)420 float LoadingProgressModifier::GetCurentCometAngle(float baseAngle, uint32_t index, uint32_t totalNumber)
421 {
422 return std::fmod((baseAngle - (std::clamp(index, 1u, totalNumber) - 1) * COMET_TAIL_ANGLE), TOTAL_ANGLE);
423 }
424
GetCometNumber()425 uint32_t LoadingProgressModifier::GetCometNumber()
426 {
427 CHECK_NULL_RETURN(cometTailLen_, TOTAL_POINTS_COUNT);
428 return static_cast<uint32_t>(cometTailLen_->Get() / COMET_TAIL_ANGLE);
429 }
430
StartRecycle()431 void LoadingProgressModifier::StartRecycle()
432 {
433 auto context = PipelineBase::GetCurrentContext();
434 CHECK_NULL_VOID(context);
435 if (isLoading_) {
436 return;
437 }
438 sizeScale_->Set(1.0f);
439 if (date_) {
440 isLoading_ = true;
441 date_->Set(0.0f);
442 AnimationOption option = AnimationOption();
443 RefPtr<FrameRateRange> frameRateRange =
444 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
445 option.SetFrameRateRange(frameRateRange);
446 RefPtr<Curve> curve = AceType::MakeRefPtr<CubicCurve>(0.25f, 0.30f, 0.50f, 0.14f);
447 option.SetDuration(isVisible_ ? LOADING_DURATION : 0);
448 option.SetDelay(0);
449 option.SetCurve(curve);
450 if (context->IsFormRender() && !IsDynamicComponent()) {
451 option.SetIteration(1);
452 } else {
453 option.SetIteration(-1);
454 }
455 auto pattern = pattern_.Upgrade();
456 auto host = pattern? pattern->GetHost(): nullptr;
457 auto context = host? host->GetContextRefPtr(): nullptr;
458 AnimationUtils::Animate(option, [weakDate = AceType::WeakClaim(AceType::RawPtr(date_))]() {
459 auto date = weakDate.Upgrade();
460 CHECK_NULL_VOID(date);
461 date->Set(FULL_COUNT);
462 }, nullptr, nullptr, context);
463 }
464 cometOpacity_->Set(INITIAL_OPACITY_SCALE);
465 cometSizeScale_->Set(INITIAL_SIZE_SCALE);
466 // ring up and down shift animation
467 StartRecycleRingAnimation();
468 // comet's circle Color transparency and sizeScale animation
469 StartRecycleCometAnimation();
470 }
471
StartTransToRecycleAnimation()472 void LoadingProgressModifier::StartTransToRecycleAnimation()
473 {
474 sizeScale_->Set(1.0f);
475 auto curve = AceType::MakeRefPtr<CubicCurve>(0.6f, 0.2f, 1.0f, 1.0f);
476 AnimationOption option;
477 RefPtr<FrameRateRange> frameRateRange =
478 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
479 option.SetFrameRateRange(frameRateRange);
480 option.SetDuration(TRANS_DURATION);
481 option.SetIteration(1);
482 option.SetCurve(curve);
483 auto pattern = pattern_.Upgrade();
484 auto host = pattern? pattern->GetHost(): nullptr;
485 auto context = host? host->GetContextRefPtr(): nullptr;
486 AnimationUtils::Animate(
487 option,
488 [weakDate = AceType::WeakClaim(AceType::RawPtr(date_)),
489 weakCometOpacity = AceType::WeakClaim(AceType::RawPtr(cometOpacity_)),
490 weakCometSizeScale = AceType::WeakClaim(AceType::RawPtr(cometSizeScale_))]() {
491 auto date = weakDate.Upgrade();
492 if (date) {
493 date->Set(FULL_COUNT);
494 }
495 auto cometOpacity = weakCometOpacity.Upgrade();
496 if (cometOpacity) {
497 cometOpacity->Set(1.0 - TRANS_OPACITY_SPAN);
498 }
499 auto cometSizeScale = weakCometSizeScale.Upgrade();
500 if (cometSizeScale) {
501 cometSizeScale->Set(INITIAL_SIZE_SCALE);
502 }
503 },
504 [weak = AceType::WeakClaim(this)]() {
505 auto modify = weak.Upgrade();
506 CHECK_NULL_VOID(modify);
507 modify->StartRecycle();
508 }, nullptr, context);
509 StartCometTailAnimation();
510 }
511
ChangeRefreshFollowData(float refreshFollowRatio)512 void LoadingProgressModifier::ChangeRefreshFollowData(float refreshFollowRatio)
513 {
514 auto ratio = CorrectNormalize(refreshFollowRatio);
515 sizeScale_->Set(BASE_SCALE + (1.0 - BASE_SCALE) * ratio);
516 if (isLoading_) {
517 CloseAnimation(FOLLOW_START, COMET_TAIL_ANGLE, 1.0f, 1.0f);
518 }
519 CHECK_NULL_VOID(date_);
520 date_->Set(FOLLOW_START + FOLLOW_SPAN * ratio);
521 cometTailLen_->Set(COMET_TAIL_ANGLE);
522 cometOpacity_->Set(1.0f);
523 cometSizeScale_->Set(1.0f);
524 }
525
ChangeSizeScaleData(float refreshFadeAwayRatio)526 void LoadingProgressModifier::ChangeSizeScaleData(float refreshFadeAwayRatio)
527 {
528 auto ratio = CorrectNormalize(refreshFadeAwayRatio);
529 sizeScale_->Set(BASE_SCALE + (1.0 - BASE_SCALE) * ratio);
530 }
531
CloseAnimation(float date,float cometLen,float cometOpacity,float cometScale)532 void LoadingProgressModifier::CloseAnimation(float date, float cometLen, float cometOpacity, float cometScale)
533 {
534 isLoading_ = false;
535 AnimationOption option = AnimationOption();
536 RefPtr<Curve> curve = AceType::MakeRefPtr<LinearCurve>();
537 option.SetDuration(0);
538 option.SetIteration(1);
539 option.SetCurve(curve);
540 RefPtr<FrameRateRange> frameRateRange =
541 AceType::MakeRefPtr<FrameRateRange>(ANIMATION_MIN_FFR, ANIMATION_MAX_FFR, ANIMATION_EXPECT_FFR);
542 option.SetFrameRateRange(frameRateRange);
543 date_->Set(date + FAKE_DELTA);
544 cometTailLen_->Set(cometLen + FAKE_DELTA);
545 cometOpacity_->Set(cometOpacity + FAKE_DELTA);
546 cometSizeScale_->Set(cometScale + FAKE_DELTA);
547 centerDeviation_->Set(0.0f + FAKE_DELTA);
548 auto pattern = pattern_.Upgrade();
549 auto host = pattern? pattern->GetHost(): nullptr;
550 auto context = host? host->GetContextRefPtr(): nullptr;
551 AnimationUtils::Animate(option, [weak = AceType::WeakClaim(this), date, cometLen, cometOpacity, cometScale]() {
552 auto curObj = weak.Upgrade();
553 CHECK_NULL_VOID(curObj);
554 curObj->date_->Set(date);
555 curObj->cometTailLen_->Set(cometLen);
556 curObj->cometOpacity_->Set(cometOpacity);
557 curObj->cometSizeScale_->Set(cometScale);
558 curObj->centerDeviation_->Set(0.0f);
559 }, nullptr, nullptr, context);
560 }
CorrectNormalize(float originData)561 float LoadingProgressModifier::CorrectNormalize(float originData)
562 {
563 auto ratio = originData;
564 if (ratio < 0.0f) {
565 ratio = 0.0f;
566 }
567 if (ratio > 1.0f) {
568 ratio = 1.0f;
569 };
570 return ratio;
571 }
572 } // namespace OHOS::Ace::NG
573