1 /*
2 * Copyright (c) 2022 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/stepper/stepper_pattern.h"
17
18 #include <algorithm>
19
20 #include "base/i18n/localization.h"
21 #include "base/utils/utils.h"
22 #include "core/components/stepper/stepper_theme.h"
23 #include "core/components_ng/pattern/button/button_event_hub.h"
24 #include "core/components_ng/pattern/button/button_pattern.h"
25 #include "core/components_ng/pattern/image/image_pattern.h"
26 #include "core/components_ng/pattern/linear_layout/linear_layout_pattern.h"
27 #include "core/components_ng/pattern/loading_progress/loading_progress_pattern.h"
28 #include "core/components_ng/pattern/stepper/stepper_item_layout_property.h"
29 #include "core/components_ng/pattern/stepper/stepper_node.h"
30 #include "core/components_ng/pattern/swiper/swiper_pattern.h"
31 #include "core/components_ng/pattern/text/text_layout_property.h"
32 #include "core/components_ng/pattern/text/text_pattern.h"
33 #include "core/components_v2/inspector/inspector_constants.h"
34 #include "core/pipeline/pipeline_base.h"
35
36 namespace OHOS::Ace::NG {
37 namespace {
38 constexpr int32_t PRESS_ANIMATION_DURATION = 100;
39 constexpr int32_t HOVER_ANIMATION_DURATION = 250;
40
41 constexpr float BUTTON_ON_HOVER_BEZIER_CURVE_X0 = 0.2f;
42 constexpr float BUTTON_ON_HOVER_BEZIER_CURVE_Y0 = 0.0f;
43 constexpr float BUTTON_ON_HOVER_BEZIER_CURVE_X1 = 0.2f;
44 constexpr float BUTTON_ON_HOVER_BEZIER_CURVE_Y1 = 1.0f;
45
46 constexpr float BUTTON_ON_PRESS_BEZIER_CURVE_X0 = 0.33f;
47 constexpr float BUTTON_ON_PRESS_BEZIER_CURVE_Y0 = 0.0f;
48 constexpr float BUTTON_ON_PRESS_BEZIER_CURVE_X1 = 0.67f;
49 constexpr float BUTTON_ON_PRESS_BEZIER_CURVE_Y1 = 1.0f;
50 } // namespace
51
OnModifyDone()52 void StepperPattern::OnModifyDone()
53 {
54 Pattern::OnModifyDone();
55 auto hostNode = DynamicCast<StepperNode>(GetHost());
56 CHECK_NULL_VOID(hostNode);
57 auto swiperNode =
58 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId())));
59 CHECK_NULL_VOID(swiperNode);
60 index_ = swiperNode->GetLayoutProperty<SwiperLayoutProperty>()->GetIndex().value_or(0);
61
62 auto swiperEventHub = swiperNode->GetEventHub<SwiperEventHub>();
63 CHECK_NULL_VOID(swiperEventHub);
64 maxIndex_ = TotalCount();
65 if (index_ > maxIndex_) {
66 index_ = 0;
67 hostNode->GetLayoutProperty<StepperLayoutProperty>()->UpdateIndex(index_);
68 swiperNode->GetLayoutProperty<SwiperLayoutProperty>()->UpdateIndex(index_);
69 swiperNode->MarkModifyDone();
70 swiperNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
71 }
72 InitSwiperChangeEvent(swiperEventHub);
73 UpdateOrCreateLeftButtonNode(index_);
74 UpdateOrCreateRightButtonNode(index_);
75 InitButtonClickEvent();
76 SetAccessibilityAction();
77 }
78
OnAttachToFrameNode()79 void StepperPattern::OnAttachToFrameNode()
80 {
81 auto host = GetHost();
82 CHECK_NULL_VOID(host);
83 host->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_PARENT);
84 host->GetRenderContext()->UpdateClipEdge(true);
85 }
86
InitSwiperChangeEvent(const RefPtr<SwiperEventHub> & swiperEventHub)87 void StepperPattern::InitSwiperChangeEvent(const RefPtr<SwiperEventHub>& swiperEventHub)
88 {
89 ChangeEvent changeEvent = [weak = WeakClaim(this)](int32_t index) {
90 auto stepperPattern = weak.Upgrade();
91 CHECK_NULL_VOID_NOLOG(stepperPattern->TotalCount() > -1);
92 stepperPattern->UpdateIndexWithoutMeasure(index);
93 stepperPattern->UpdateOrCreateLeftButtonNode(index);
94 stepperPattern->UpdateOrCreateRightButtonNode(index);
95 stepperPattern->InitButtonClickEvent();
96 };
97 if (swiperChangeEvent_) {
98 (*swiperChangeEvent_).swap(changeEvent);
99 } else {
100 swiperChangeEvent_ = std::make_shared<ChangeEvent>(std::move(changeEvent));
101 swiperEventHub->AddOnChangeEvent(swiperChangeEvent_);
102 }
103 }
104
UpdateIndexWithoutMeasure(int32_t index)105 void StepperPattern::UpdateIndexWithoutMeasure(int32_t index)
106 {
107 auto hostNode = DynamicCast<StepperNode>(GetHost());
108 CHECK_NULL_VOID(hostNode);
109 auto stepperLayoutProperty = hostNode->GetLayoutProperty<StepperLayoutProperty>();
110 CHECK_NULL_VOID(stepperLayoutProperty);
111 stepperLayoutProperty->UpdateIndexWithoutMeasure(index);
112
113 auto swiperNode =
114 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId())));
115 CHECK_NULL_VOID(swiperNode);
116 auto swiperLayoutProperty = swiperNode->GetLayoutProperty<SwiperLayoutProperty>();
117 CHECK_NULL_VOID(swiperLayoutProperty);
118 swiperLayoutProperty->UpdateIndexWithoutMeasure(index);
119 }
120
UpdateOrCreateLeftButtonNode(int32_t index)121 void StepperPattern::UpdateOrCreateLeftButtonNode(int32_t index)
122 {
123 auto hostNode = DynamicCast<StepperNode>(GetHost());
124 CHECK_NULL_VOID(hostNode);
125 if (index <= 0) {
126 hostNode->RemoveLeftButtonNode();
127 } else if (!hostNode->HasLeftButtonNode()) {
128 CreateLeftButtonNode();
129 UpdateLeftButtonNode(index);
130 } else {
131 UpdateLeftButtonNode(index);
132 }
133 index_ = index;
134 hostNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
135 }
136
CreateLeftButtonNode()137 void StepperPattern::CreateLeftButtonNode()
138 {
139 auto stepperTheme = GetTheme();
140 CHECK_NULL_VOID(stepperTheme);
141 auto hostNode = DynamicCast<StepperNode>(GetHost());
142 CHECK_NULL_VOID(hostNode);
143 // Create buttonNode
144 auto buttonId = hostNode->GetLeftButtonId();
145 auto buttonPattern = AceType::MakeRefPtr<NG::ButtonPattern>();
146 CHECK_NULL_VOID(buttonPattern);
147 buttonPattern->setComponentButtonType(ComponentButtonType::STEPPER);
148 buttonPattern->SetFocusBorderColor(stepperTheme->GetFocusColor());
149 auto buttonNode = FrameNode::CreateFrameNode(V2::BUTTON_ETS_TAG, buttonId, buttonPattern);
150 CHECK_NULL_VOID(buttonNode);
151 buttonNode->GetEventHub<ButtonEventHub>()->SetStateEffect(true);
152 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateType(ButtonType::NORMAL);
153 buttonNode->GetRenderContext()->UpdateBackgroundColor(stepperTheme->GetMouseHoverColor().ChangeOpacity(0));
154 buttonNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
155 auto buttonRadius = stepperTheme->GetRadius();
156 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateBorderRadius(BorderRadiusProperty(buttonRadius));
157 buttonNode->MountToParent(hostNode);
158 buttonNode->MarkModifyDone();
159 InitButtonOnHoverEvent(buttonNode, true);
160 InitButtonTouchEvent(buttonNode);
161 // Create rowNode
162 auto rowNode = FrameNode::GetOrCreateFrameNode(V2::ROW_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
163 []() { return AceType::MakeRefPtr<LinearLayoutPattern>(false); });
164 rowNode->GetLayoutProperty<LinearLayoutProperty>()->UpdateSpace(stepperTheme->GetControlPadding());
165 rowNode->GetLayoutProperty()->UpdateMargin(
166 { CalcLength(stepperTheme->GetControlPadding()), CalcLength(stepperTheme->GetControlPadding()) });
167 rowNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
168 rowNode->MountToParent(buttonNode);
169 rowNode->MarkModifyDone();
170 // Create imageNode
171 auto imageNode = FrameNode::GetOrCreateFrameNode(V2::IMAGE_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
172 []() { return AceType::MakeRefPtr<ImagePattern>(); });
173 imageNode->GetLayoutProperty()->UpdateUserDefinedIdealSize(
174 CalcSize(CalcLength(stepperTheme->GetArrowWidth()), CalcLength(stepperTheme->GetArrowHeight())));
175 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateImageFit(ImageFit::FILL);
176 ImageSourceInfo imageSourceInfo;
177 imageSourceInfo.SetResourceId(InternalResource::ResourceId::STEPPER_BACK_ARROW);
178 imageSourceInfo.SetFillColor(stepperTheme->GetArrowColor());
179 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateImageSourceInfo(imageSourceInfo);
180 SizeF sourceSize(static_cast<float>(stepperTheme->GetArrowWidth().ConvertToPx()),
181 static_cast<float>(stepperTheme->GetArrowHeight().ConvertToPx()));
182 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateSourceSize(sourceSize);
183 imageNode->MountToParent(rowNode);
184 imageNode->MarkModifyDone();
185 // Create textNode
186 auto textNode = FrameNode::GetOrCreateFrameNode(V2::TEXT_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
187 []() { return AceType::MakeRefPtr<TextPattern>(); });
188 textNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
189 textNode->GetRenderContext()->UpdateBackgroundColor(Color::TRANSPARENT);
190 auto textColor = stepperTheme->GetTextStyle().GetTextColor();
191 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextColor(textColor);
192 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextOverflow(TextOverflow::ELLIPSIS);
193 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontSize(stepperTheme->GetTextStyle().GetFontSize());
194 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateAdaptMinFontSize(stepperTheme->GetMinFontSize());
195 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateAdaptMaxFontSize(
196 stepperTheme->GetTextStyle().GetFontSize());
197 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontWeight(stepperTheme->GetTextStyle().GetFontWeight());
198 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateMaxLines(stepperTheme->GetTextMaxLines());
199 textNode->GetLayoutProperty()->UpdateAlignment(Alignment::CENTER);
200 textNode->GetFocusHub()->SetFocusable(true);
201 textNode->MountToParent(rowNode);
202 textNode->MarkModifyDone();
203 }
204
UpdateLeftButtonNode(int32_t index)205 void StepperPattern::UpdateLeftButtonNode(int32_t index)
206 {
207 auto hostNode = DynamicCast<StepperNode>(GetHost());
208 CHECK_NULL_VOID(hostNode);
209 auto buttonNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetLeftButtonId()));
210 auto rowNode = buttonNode->GetChildAtIndex(0);
211 auto textNode = DynamicCast<FrameNode>(rowNode->GetChildAtIndex(1));
212
213 auto swiperNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId()));
214 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index)));
215 CHECK_NULL_VOID(stepperItemNode);
216 auto stepperItemLayoutProperty = stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>();
217 auto buttonBackText = Localization::GetInstance()->GetEntryLetters("stepper.back");
218 auto leftLabel = stepperItemLayoutProperty->GetLeftLabel().value_or(buttonBackText);
219 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateContent(leftLabel);
220
221 textNode->MarkModifyDone();
222 textNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
223 }
224
UpdateOrCreateRightButtonNode(int32_t index)225 void StepperPattern::UpdateOrCreateRightButtonNode(int32_t index)
226 {
227 auto hostNode = DynamicCast<StepperNode>(GetHost());
228 CHECK_NULL_VOID(hostNode);
229 if (!hostNode->HasRightButtonNode()) {
230 CreateRightButtonNode(index);
231 } else {
232 UpdateRightButtonNode(index);
233 }
234 index_ = index;
235 hostNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
236 }
CreateRightButtonNode(int32_t index)237 void StepperPattern::CreateRightButtonNode(int32_t index)
238 {
239 auto hostNode = DynamicCast<StepperNode>(GetHost());
240 CHECK_NULL_VOID(hostNode);
241 auto swiperNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId()));
242 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index)));
243 CHECK_NULL_VOID(stepperItemNode);
244 auto labelStatus =
245 stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>()->GetLabelStatus().value_or("normal");
246 if (labelStatus == "normal") {
247 isRightLabelDisable_ = false;
248 if (index == maxIndex_) {
249 CreateArrowlessRightButtonNode(index, Localization::GetInstance()->GetEntryLetters("stepper.start"));
250 } else {
251 CreateArrowRightButtonNode(index, false);
252 }
253 } else if (labelStatus == "disabled") {
254 isRightLabelDisable_ = true;
255 CreateArrowRightButtonNode(index, true);
256 } else if (labelStatus == "waiting") {
257 isRightLabelDisable_ = false;
258 CreateWaitingRightButtonNode();
259 } else if (labelStatus == "skip") {
260 isRightLabelDisable_ = false;
261 CreateArrowlessRightButtonNode(index, Localization::GetInstance()->GetEntryLetters("stepper.skip"));
262 }
263 }
264
CreateArrowRightButtonNode(int32_t index,bool isDisabled)265 void StepperPattern::CreateArrowRightButtonNode(int32_t index, bool isDisabled)
266 {
267 auto stepperTheme = GetTheme();
268 CHECK_NULL_VOID(stepperTheme);
269 auto hostNode = DynamicCast<StepperNode>(GetHost());
270 CHECK_NULL_VOID(hostNode);
271 // get rightLabel
272 auto swiperNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId()));
273 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index)));
274 CHECK_NULL_VOID(stepperItemNode);
275 auto buttonNextText = Localization::GetInstance()->GetEntryLetters("stepper.next");
276 auto rightLabel =
277 stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>()->GetRightLabel().value_or(buttonNextText);
278 // Create buttonNode
279 auto buttonId = hostNode->GetRightButtonId();
280 auto buttonPattern = AceType::MakeRefPtr<NG::ButtonPattern>();
281 CHECK_NULL_VOID(buttonPattern);
282 buttonPattern->setComponentButtonType(ComponentButtonType::STEPPER);
283 buttonPattern->SetFocusBorderColor(stepperTheme->GetFocusColor());
284 auto buttonNode = FrameNode::CreateFrameNode(V2::BUTTON_ETS_TAG, buttonId, buttonPattern);
285 CHECK_NULL_VOID(buttonNode);
286 buttonNode->GetEventHub<ButtonEventHub>()->SetStateEffect(true);
287 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateType(ButtonType::NORMAL);
288 Color buttonBackgroundColor =
289 rightIsHover_ ? stepperTheme->GetMouseHoverColor() : stepperTheme->GetMouseHoverColor().ChangeOpacity(0);
290 buttonNode->GetRenderContext()->UpdateBackgroundColor(buttonBackgroundColor);
291 buttonNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
292 auto buttonRadius = stepperTheme->GetRadius();
293 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateBorderRadius(BorderRadiusProperty(buttonRadius));
294 isRightLabelDisable_ ? buttonNode->GetEventHub<ButtonEventHub>()->SetEnabled(false)
295 : buttonNode->GetEventHub<ButtonEventHub>()->SetEnabled(true);
296 buttonNode->MountToParent(hostNode);
297 buttonNode->MarkModifyDone();
298 InitButtonOnHoverEvent(buttonNode, false);
299 InitButtonTouchEvent(buttonNode);
300 // Create rowNode
301 auto rowNode = FrameNode::GetOrCreateFrameNode(V2::ROW_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
302 []() { return AceType::MakeRefPtr<LinearLayoutPattern>(false); });
303 rowNode->GetLayoutProperty<LinearLayoutProperty>()->UpdateSpace(stepperTheme->GetControlPadding());
304 rowNode->GetLayoutProperty()->UpdateMargin(
305 { CalcLength(stepperTheme->GetControlPadding()), CalcLength(stepperTheme->GetControlPadding()) });
306 rowNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
307 rowNode->MountToParent(buttonNode);
308 rowNode->MarkModifyDone();
309 // Create textNode
310 auto textNode = FrameNode::GetOrCreateFrameNode(V2::TEXT_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
311 []() { return AceType::MakeRefPtr<TextPattern>(); });
312 textNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
313 textNode->GetRenderContext()->UpdateBackgroundColor(Color::TRANSPARENT);
314 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateContent(rightLabel);
315 auto textColor = stepperTheme->GetTextStyle().GetTextColor();
316 if (isDisabled) {
317 textColor = textColor.BlendOpacity(stepperTheme->GetDisabledAlpha());
318 }
319 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextColor(textColor);
320 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextOverflow(TextOverflow::ELLIPSIS);
321 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontSize(stepperTheme->GetTextStyle().GetFontSize());
322 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateAdaptMinFontSize(stepperTheme->GetMinFontSize());
323 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateAdaptMaxFontSize(
324 stepperTheme->GetTextStyle().GetFontSize());
325 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontWeight(stepperTheme->GetTextStyle().GetFontWeight());
326 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateMaxLines(stepperTheme->GetTextMaxLines());
327 textNode->GetLayoutProperty()->UpdateAlignment(Alignment::CENTER);
328 textNode->GetFocusHub()->SetFocusable(true);
329 textNode->MountToParent(rowNode);
330 textNode->MarkModifyDone();
331 // Create imageNode
332 auto imageNode = FrameNode::GetOrCreateFrameNode(V2::IMAGE_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
333 []() { return AceType::MakeRefPtr<ImagePattern>(); });
334 imageNode->GetLayoutProperty()->UpdateUserDefinedIdealSize(
335 CalcSize(CalcLength(stepperTheme->GetArrowWidth()), CalcLength(stepperTheme->GetArrowHeight())));
336 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateImageFit(ImageFit::FILL);
337 ImageSourceInfo imageSourceInfo;
338 imageSourceInfo.SetResourceId(InternalResource::ResourceId::STEPPER_NEXT_ARROW);
339 auto imageColor = stepperTheme->GetArrowColor();
340 if (isDisabled) {
341 imageColor = imageColor.BlendOpacity(stepperTheme->GetDisabledAlpha());
342 }
343 imageSourceInfo.SetFillColor(imageColor);
344 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateImageSourceInfo(imageSourceInfo);
345 SizeF sourceSize(static_cast<float>(stepperTheme->GetArrowWidth().ConvertToPx()),
346 static_cast<float>(stepperTheme->GetArrowHeight().ConvertToPx()));
347 imageNode->GetLayoutProperty<ImageLayoutProperty>()->UpdateSourceSize(sourceSize);
348 imageNode->MountToParent(rowNode);
349 imageNode->MarkModifyDone();
350 }
351
CreateArrowlessRightButtonNode(int32_t index,const std::string & defaultContent)352 void StepperPattern::CreateArrowlessRightButtonNode(int32_t index, const std::string& defaultContent)
353 {
354 auto stepperTheme = GetTheme();
355 CHECK_NULL_VOID(stepperTheme);
356 auto hostNode = DynamicCast<StepperNode>(GetHost());
357 CHECK_NULL_VOID(hostNode);
358 // get rightLabel
359 auto swiperNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId()));
360 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index)));
361 auto rightLabel =
362 stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>()->GetRightLabel().value_or(defaultContent);
363 // Create buttonNode
364 auto buttonId = hostNode->GetRightButtonId();
365 auto buttonPattern = AceType::MakeRefPtr<NG::ButtonPattern>();
366 CHECK_NULL_VOID(buttonPattern);
367 buttonPattern->setComponentButtonType(ComponentButtonType::STEPPER);
368 buttonPattern->SetFocusBorderColor(stepperTheme->GetFocusColor());
369 auto buttonNode = FrameNode::CreateFrameNode(V2::BUTTON_ETS_TAG, buttonId, buttonPattern);
370 CHECK_NULL_VOID(buttonNode);
371 buttonNode->GetEventHub<ButtonEventHub>()->SetStateEffect(true);
372 Color buttonBackgroundColor =
373 rightIsHover_ ? stepperTheme->GetMouseHoverColor() : stepperTheme->GetMouseHoverColor().ChangeOpacity(0);
374 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateType(ButtonType::NORMAL);
375 buttonNode->GetRenderContext()->UpdateBackgroundColor(buttonBackgroundColor);
376 buttonNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_CONTENT);
377 auto buttonRadius = stepperTheme->GetRadius();
378 buttonNode->GetLayoutProperty<ButtonLayoutProperty>()->UpdateBorderRadius(BorderRadiusProperty(buttonRadius));
379 buttonNode->MountToParent(hostNode);
380 buttonNode->MarkModifyDone();
381 InitButtonOnHoverEvent(buttonNode, false);
382 InitButtonTouchEvent(buttonNode);
383 // Create textNode
384 auto textNode = FrameNode::GetOrCreateFrameNode(V2::TEXT_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
385 []() { return AceType::MakeRefPtr<TextPattern>(); });
386 textNode->GetRenderContext()->UpdateBackgroundColor(Color::TRANSPARENT);
387 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateContent(rightLabel);
388 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontSize(stepperTheme->GetTextStyle().GetFontSize());
389 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateFontWeight(stepperTheme->GetTextStyle().GetFontWeight());
390 auto textColor = stepperTheme->GetTextStyle().GetTextColor();
391 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextColor(textColor);
392 textNode->GetLayoutProperty<TextLayoutProperty>()->UpdateTextOverflow(TextOverflow::ELLIPSIS);
393 textNode->GetLayoutProperty()->UpdateAlignment(Alignment::CENTER);
394 textNode->GetLayoutProperty()->UpdateMargin(
395 { CalcLength(stepperTheme->GetControlPadding()), CalcLength(stepperTheme->GetControlPadding()) });
396 textNode->GetFocusHub()->SetFocusable(true);
397 textNode->MountToParent(buttonNode);
398 textNode->MarkModifyDone();
399 }
400
CreateWaitingRightButtonNode()401 void StepperPattern::CreateWaitingRightButtonNode()
402 {
403 auto stepperTheme = GetTheme();
404 CHECK_NULL_VOID(stepperTheme);
405 auto hostNode = DynamicCast<StepperNode>(GetHost());
406 CHECK_NULL_VOID(hostNode);
407 // Create loadingProgressNode
408 auto buttonId = hostNode->GetRightButtonId();
409 auto loadingProgressNode = FrameNode::GetOrCreateFrameNode(
410 V2::LOADING_PROGRESS_ETS_TAG, buttonId, []() { return AceType::MakeRefPtr<LoadingProgressPattern>(); });
411 loadingProgressNode->GetLayoutProperty()->UpdateUserDefinedIdealSize(
412 CalcSize(CalcLength(stepperTheme->GetProgressDiameter()), CalcLength(stepperTheme->GetProgressDiameter())));
413 loadingProgressNode->GetPaintProperty<LoadingProgressPaintProperty>()->UpdateColor(
414 stepperTheme->GetProgressColor());
415 loadingProgressNode->GetRenderContext()->UpdateForegroundColor(stepperTheme->GetProgressColor());
416 loadingProgressNode->MountToParent(hostNode);
417 loadingProgressNode->MarkModifyDone();
418 }
419
UpdateRightButtonNode(int32_t index)420 void StepperPattern::UpdateRightButtonNode(int32_t index)
421 {
422 auto hostNode = DynamicCast<StepperNode>(GetHost());
423 CHECK_NULL_VOID(hostNode);
424 hostNode->RemoveRightButtonNode();
425 CreateRightButtonNode(index);
426 }
427
InitButtonOnHoverEvent(RefPtr<FrameNode> buttonNode,bool isLeft)428 void StepperPattern::InitButtonOnHoverEvent(RefPtr<FrameNode> buttonNode, bool isLeft)
429 {
430 CHECK_NULL_VOID(buttonNode);
431 auto buttonInputHub = buttonNode->GetOrCreateInputEventHub();
432 CHECK_NULL_VOID(buttonInputHub);
433 auto hoverCallback = [weak = WeakClaim(this), buttonNodeWeak = WeakPtr<FrameNode>(buttonNode), isLeft](
434 bool isHovered) {
435 auto pattern = weak.Upgrade();
436 CHECK_NULL_VOID(pattern);
437 auto buttonNode = buttonNodeWeak.Upgrade();
438 CHECK_NULL_VOID(buttonNode);
439 pattern->ButtonOnHover(buttonNode, isHovered, isLeft);
440 };
441 buttonOnHoverListenr_ = MakeRefPtr<InputEvent>(std::move(hoverCallback));
442 buttonInputHub->AddOnHoverEvent(buttonOnHoverListenr_);
443 }
444
ButtonOnHover(RefPtr<FrameNode> buttonNode,bool isHover,bool isLeft)445 void StepperPattern::ButtonOnHover(RefPtr<FrameNode> buttonNode, bool isHover, bool isLeft)
446 {
447 if (isLeft) {
448 if (leftIsHover_ == isHover) {
449 return;
450 }
451 leftIsHover_ = isHover;
452 } else {
453 if (rightIsHover_ == isHover) {
454 return;
455 }
456 rightIsHover_ = isHover;
457 }
458 if (isHover) {
459 ButtonHoverInAnimation(buttonNode);
460 } else {
461 ButtonHoverOutAnimation(buttonNode);
462 }
463 }
464
ButtonHoverInAnimation(RefPtr<FrameNode> buttonNode)465 void StepperPattern::ButtonHoverInAnimation(RefPtr<FrameNode> buttonNode)
466 {
467 auto renderContext = buttonNode->GetRenderContext();
468 CHECK_NULL_VOID(renderContext);
469 AnimationOption option;
470 option.SetDuration(HOVER_ANIMATION_DURATION);
471 option.SetCurve(AceType::MakeRefPtr<CubicCurve>(BUTTON_ON_HOVER_BEZIER_CURVE_X0, BUTTON_ON_HOVER_BEZIER_CURVE_Y0,
472 BUTTON_ON_HOVER_BEZIER_CURVE_X1, BUTTON_ON_HOVER_BEZIER_CURVE_Y1));
473 auto stepperTheme = GetTheme();
474 CHECK_NULL_VOID(stepperTheme);
475 Color buttonBackgroundColor = stepperTheme->GetMouseHoverColor();
476 AnimationUtils::Animate(option,
477 [renderContext, buttonBackgroundColor]() { renderContext->UpdateBackgroundColor(buttonBackgroundColor); });
478 }
ButtonHoverOutAnimation(RefPtr<FrameNode> buttonNode)479 void StepperPattern::ButtonHoverOutAnimation(RefPtr<FrameNode> buttonNode)
480 {
481 auto renderContext = buttonNode->GetRenderContext();
482 CHECK_NULL_VOID(renderContext);
483 AnimationOption option;
484 option.SetDuration(HOVER_ANIMATION_DURATION);
485 option.SetCurve(AceType::MakeRefPtr<CubicCurve>(BUTTON_ON_HOVER_BEZIER_CURVE_X0, BUTTON_ON_HOVER_BEZIER_CURVE_Y0,
486 BUTTON_ON_HOVER_BEZIER_CURVE_X1, BUTTON_ON_HOVER_BEZIER_CURVE_Y1));
487 auto stepperTheme = GetTheme();
488 CHECK_NULL_VOID(stepperTheme);
489 Color buttonBackgroundColor = stepperTheme->GetMouseHoverColor().ChangeOpacity(0);
490 AnimationUtils::Animate(option,
491 [renderContext, buttonBackgroundColor]() { renderContext->UpdateBackgroundColor(buttonBackgroundColor); });
492 }
493
InitButtonTouchEvent(RefPtr<FrameNode> buttonNode)494 void StepperPattern::InitButtonTouchEvent(RefPtr<FrameNode> buttonNode)
495 {
496 CHECK_NULL_VOID(buttonNode);
497 auto buttonEventHub = buttonNode->GetEventHub<ButtonEventHub>();
498 CHECK_NULL_VOID(buttonEventHub);
499 buttonEventHub->SetStateEffect(false);
500 auto buttonGestureHub = buttonNode->GetOrCreateGestureEventHub();
501 CHECK_NULL_VOID(buttonGestureHub);
502 auto touchCallback = [weak = WeakClaim(this), buttonNodeWeak = WeakPtr<FrameNode>(buttonNode)](
503 const TouchEventInfo& info) {
504 auto pattern = weak.Upgrade();
505 CHECK_NULL_VOID(pattern);
506 auto buttonNode = buttonNodeWeak.Upgrade();
507 CHECK_NULL_VOID(buttonNode);
508 pattern->ButtonOnTouch(buttonNode, info.GetTouches().front().GetTouchType());
509 };
510 buttonTouchListenr_ = MakeRefPtr<TouchEventImpl>(std::move(touchCallback));
511 buttonGestureHub->AddTouchEvent(buttonTouchListenr_);
512 }
513
ButtonOnTouch(RefPtr<FrameNode> buttonNode,TouchType touchType)514 void StepperPattern::ButtonOnTouch(RefPtr<FrameNode> buttonNode, TouchType touchType)
515 {
516 if (touchType == TouchType::DOWN) {
517 ButtonTouchDownAnimation(buttonNode);
518 }
519 if (touchType == TouchType::UP || touchType == TouchType::CANCEL) {
520 ButtonTouchUpAnimation(buttonNode);
521 }
522 }
523
ButtonTouchDownAnimation(RefPtr<FrameNode> buttonNode)524 void StepperPattern::ButtonTouchDownAnimation(RefPtr<FrameNode> buttonNode)
525 {
526 auto renderContext = buttonNode->GetRenderContext();
527 CHECK_NULL_VOID(renderContext);
528 AnimationOption option;
529 option.SetDuration(PRESS_ANIMATION_DURATION);
530 option.SetCurve(AceType::MakeRefPtr<CubicCurve>(BUTTON_ON_PRESS_BEZIER_CURVE_X0, BUTTON_ON_PRESS_BEZIER_CURVE_Y0,
531 BUTTON_ON_PRESS_BEZIER_CURVE_X1, BUTTON_ON_PRESS_BEZIER_CURVE_Y1));
532 auto stepperTheme = GetTheme();
533 CHECK_NULL_VOID(stepperTheme);
534 Color buttonBackgroundColor = stepperTheme->GetButtonPressedColor();
535 AnimationUtils::Animate(option,
536 [renderContext, buttonBackgroundColor]() { renderContext->UpdateBackgroundColor(buttonBackgroundColor); });
537 }
538
ButtonTouchUpAnimation(RefPtr<FrameNode> buttonNode)539 void StepperPattern::ButtonTouchUpAnimation(RefPtr<FrameNode> buttonNode)
540 {
541 auto renderContext = buttonNode->GetRenderContext();
542 CHECK_NULL_VOID(renderContext);
543 AnimationOption option;
544 option.SetDuration(PRESS_ANIMATION_DURATION);
545 option.SetCurve(AceType::MakeRefPtr<CubicCurve>(BUTTON_ON_PRESS_BEZIER_CURVE_X0, BUTTON_ON_PRESS_BEZIER_CURVE_Y0,
546 BUTTON_ON_PRESS_BEZIER_CURVE_X1, BUTTON_ON_PRESS_BEZIER_CURVE_Y1));
547 auto stepperTheme = GetTheme();
548 CHECK_NULL_VOID(stepperTheme);
549 Color buttonBackgroundColor =
550 rightIsHover_ ? stepperTheme->GetMouseHoverColor() : stepperTheme->GetMouseHoverColor().ChangeOpacity(0);
551 AnimationUtils::Animate(option,
552 [renderContext, buttonBackgroundColor]() { renderContext->UpdateBackgroundColor(buttonBackgroundColor); });
553 }
554
InitButtonClickEvent()555 void StepperPattern::InitButtonClickEvent()
556 {
557 auto hostNode = DynamicCast<StepperNode>(GetHost());
558 CHECK_NULL_VOID(hostNode);
559
560 if (hostNode->HasLeftButtonNode()) {
561 auto leftButtonNode =
562 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetLeftButtonId())));
563 CHECK_NULL_VOID(leftButtonNode);
564 auto leftGestureHub = leftButtonNode->GetOrCreateGestureEventHub();
565 CHECK_NULL_VOID(leftGestureHub);
566 if (leftGestureHub->IsClickEventsEmpty()) {
567 auto leftClickEvent = [weak = WeakClaim(this)](const GestureEvent& info) {
568 auto stepperPattern = weak.Upgrade();
569 CHECK_NULL_VOID_NOLOG(stepperPattern);
570 stepperPattern->HandlingLeftButtonClickEvent();
571 };
572 leftGestureHub->AddClickEvent(MakeRefPtr<ClickEvent>(std::move(leftClickEvent)));
573 }
574 }
575
576 auto rightButtonNode =
577 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetRightButtonId())));
578 CHECK_NULL_VOID(rightButtonNode);
579 auto rightGestureHub = rightButtonNode->GetOrCreateGestureEventHub();
580 CHECK_NULL_VOID(rightGestureHub);
581 if (rightGestureHub->IsClickEventsEmpty()) {
582 auto rightClickEvent = [weak = WeakClaim(this)](const GestureEvent& info) {
583 auto stepperPattern = weak.Upgrade();
584 CHECK_NULL_VOID_NOLOG(stepperPattern);
585 stepperPattern->HandlingRightButtonClickEvent();
586 };
587 rightGestureHub->AddClickEvent(MakeRefPtr<ClickEvent>(std::move(rightClickEvent)));
588 }
589 }
590
HandlingLeftButtonClickEvent()591 void StepperPattern::HandlingLeftButtonClickEvent()
592 {
593 auto hostNode = DynamicCast<StepperNode>(GetHost());
594 CHECK_NULL_VOID(hostNode);
595 auto stepperHub = hostNode->GetEventHub<StepperEventHub>();
596 CHECK_NULL_VOID(stepperHub);
597 auto swiperNode =
598 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId())));
599 auto swiperAnimationController = swiperNode->GetPattern<SwiperPattern>()->GetController();
600 if (swiperAnimationController && !swiperAnimationController->IsStopped()) {
601 return;
602 }
603 auto swiperController = swiperNode->GetPattern<SwiperPattern>()->GetSwiperController();
604 stepperHub->FireChangeEvent(index_, std::clamp<int32_t>(index_ - 1, 0, maxIndex_));
605 stepperHub->FirePreviousEvent(index_, std::clamp<int32_t>(index_ - 1, 0, maxIndex_));
606 swiperController->SwipeTo(std::clamp<int32_t>(index_ - 1, 0, maxIndex_));
607 }
608
HandlingRightButtonClickEvent()609 void StepperPattern::HandlingRightButtonClickEvent()
610 {
611 auto hostNode = DynamicCast<StepperNode>(GetHost());
612 CHECK_NULL_VOID(hostNode);
613 auto stepperHub = hostNode->GetEventHub<StepperEventHub>();
614 CHECK_NULL_VOID(stepperHub);
615 auto swiperNode =
616 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId())));
617 auto swiperAnimationController = swiperNode->GetPattern<SwiperPattern>()->GetController();
618 if (swiperAnimationController && !swiperAnimationController->IsStopped()) {
619 return;
620 }
621 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index_)));
622 CHECK_NULL_VOID(stepperItemNode);
623 auto labelStatus =
624 stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>()->GetLabelStatus().value_or("normal");
625 if (labelStatus == "skip") {
626 stepperHub->FireSkipEvent();
627 } else if (labelStatus == "normal") {
628 if (index_ == maxIndex_) {
629 stepperHub->FireFinishEvent();
630 } else {
631 stepperHub->FireChangeEvent(index_, std::clamp<int32_t>(index_ + 1, 0, maxIndex_));
632 stepperHub->FireNextEvent(index_, std::clamp<int32_t>(index_ + 1, 0, maxIndex_));
633 auto swiperController = swiperNode->GetPattern<SwiperPattern>()->GetSwiperController();
634 swiperController->SwipeTo(std::clamp<int32_t>(index_ + 1, 0, maxIndex_));
635 }
636 }
637 }
638
TotalCount() const639 int32_t StepperPattern::TotalCount() const
640 {
641 auto hostNode = DynamicCast<StepperNode>(GetHost());
642 CHECK_NULL_RETURN(hostNode, 0);
643 auto swiperNode =
644 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId())));
645 CHECK_NULL_RETURN(swiperNode, 0);
646 return swiperNode->TotalChildCount() - 1;
647 }
648
SetAccessibilityAction()649 void StepperPattern::SetAccessibilityAction()
650 {
651 auto host = GetHost();
652 CHECK_NULL_VOID(host);
653 auto accessibilityProperty = host->GetAccessibilityProperty<AccessibilityProperty>();
654 CHECK_NULL_VOID(accessibilityProperty);
655 accessibilityProperty->SetActionScrollForward([weakPtr = WeakClaim(this)]() {
656 const auto& pattern = weakPtr.Upgrade();
657 CHECK_NULL_VOID(pattern);
658 pattern->HandlingRightButtonClickEvent();
659 });
660
661 accessibilityProperty->SetActionScrollBackward([weakPtr = WeakClaim(this)]() {
662 const auto& pattern = weakPtr.Upgrade();
663 CHECK_NULL_VOID(pattern);
664 pattern->HandlingLeftButtonClickEvent();
665 });
666 }
667
GetFocusNode(FocusStep step,const WeakPtr<FocusHub> & currentFocusNode)668 WeakPtr<FocusHub> StepperPattern::GetFocusNode(FocusStep step, const WeakPtr<FocusHub>& currentFocusNode)
669 {
670 auto curFocusNode = currentFocusNode.Upgrade();
671 CHECK_NULL_RETURN(curFocusNode, nullptr);
672 auto hostNode = DynamicCast<StepperNode>(GetHost());
673 CHECK_NULL_RETURN(hostNode, nullptr);
674
675 auto swiperNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetSwiperId()));
676 CHECK_NULL_RETURN(swiperNode, nullptr);
677 auto stepperItemNode = DynamicCast<FrameNode>(swiperNode->GetChildAtIndex(static_cast<int32_t>(index_)));
678 CHECK_NULL_RETURN(stepperItemNode, nullptr);
679 auto buttonFocusHub = stepperItemNode->GetOrCreateFocusHub();
680 CHECK_NULL_RETURN(buttonFocusHub, nullptr);
681
682 auto stepperItemLayoutProperty = stepperItemNode->GetLayoutProperty<StepperItemLayoutProperty>();
683 CHECK_NULL_RETURN(stepperItemLayoutProperty, nullptr);
684 auto labelStatus = stepperItemLayoutProperty->GetLabelStatus().value_or("normal");
685
686 if (hostNode->HasLeftButtonNode()) {
687 auto leftButtonNode =
688 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetLeftButtonId())));
689 CHECK_NULL_RETURN(leftButtonNode, nullptr);
690 leftFocusHub_ = leftButtonNode->GetOrCreateFocusHub();
691 }
692
693 auto rightButtonNode =
694 DynamicCast<FrameNode>(hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetRightButtonId())));
695 CHECK_NULL_RETURN(rightButtonNode, nullptr);
696 auto rightFocusHub = rightButtonNode->GetOrCreateFocusHub();
697 CHECK_NULL_RETURN(rightFocusHub, nullptr);
698
699 if (labelStatus == "normal" || labelStatus == "skip") {
700 if (step == FocusStep::UP || step == FocusStep::LEFT || step == FocusStep::SHIFT_TAB) {
701 return curFocusNode == leftFocusHub_ ? buttonFocusHub : leftFocusHub_;
702 }
703
704 if (curFocusNode != leftFocusHub_ && curFocusNode != rightFocusHub) {
705 return hostNode->HasLeftButtonNode() ? leftFocusHub_ : rightFocusHub;
706 }
707
708 if (curFocusNode == rightFocusHub && !hostNode->HasLeftButtonNode()) {
709 return buttonFocusHub;
710 }
711
712 if (step == FocusStep::DOWN || step == FocusStep::RIGHT || step == FocusStep::TAB) {
713 return curFocusNode == buttonFocusHub ? leftFocusHub_ : rightFocusHub;
714 }
715 } else if (labelStatus == "disabled" || labelStatus == "waiting") {
716 return curFocusNode == leftFocusHub_ ? buttonFocusHub : leftFocusHub_;
717 }
718 return nullptr;
719 }
720
OnColorConfigurationUpdate()721 void StepperPattern::OnColorConfigurationUpdate()
722 {
723 auto host = GetHost();
724 CHECK_NULL_VOID(host);
725 auto hostNode = DynamicCast<StepperNode>(GetHost());
726 CHECK_NULL_VOID(hostNode);
727 auto stepperTheme = GetTheme();
728 CHECK_NULL_VOID(stepperTheme);
729 auto textColor = stepperTheme->GetTextStyle().GetTextColor();
730 auto leftButtonNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetLeftButtonId()));
731 if (leftButtonNode) {
732 auto leftButtonFrameNode = DynamicCast<FrameNode>(leftButtonNode);
733 CHECK_NULL_VOID(leftButtonFrameNode);
734 ButtonSkipColorConfigurationUpdate(leftButtonFrameNode);
735 auto renderContext = leftButtonFrameNode->GetRenderContext();
736 CHECK_NULL_VOID(renderContext);
737 renderContext->UpdateBackgroundColor(stepperTheme->GetMouseHoverColor().ChangeOpacity(0));
738 auto rowNode = leftButtonFrameNode->GetChildAtIndex(0);
739 CHECK_NULL_VOID(rowNode);
740 auto textFrameNode = DynamicCast<FrameNode>(rowNode->GetChildAtIndex(1));
741 CHECK_NULL_VOID(textFrameNode);
742 auto layoutProperty = textFrameNode->GetLayoutProperty<TextLayoutProperty>();
743 CHECK_NULL_VOID(layoutProperty);
744 layoutProperty->UpdateTextColor(textColor);
745 }
746 auto rightButtonNode = hostNode->GetChildAtIndex(hostNode->GetChildIndexById(hostNode->GetRightButtonId()));
747 if (rightButtonNode) {
748 auto rightButtonFrameNode = DynamicCast<FrameNode>(rightButtonNode);
749 CHECK_NULL_VOID(rightButtonFrameNode);
750 ButtonSkipColorConfigurationUpdate(rightButtonFrameNode);
751 auto renderContext = rightButtonFrameNode->GetRenderContext();
752 CHECK_NULL_VOID(renderContext);
753 renderContext->UpdateBackgroundColor(stepperTheme->GetMouseHoverColor().ChangeOpacity(0));
754 auto firstChild = rightButtonFrameNode->GetFirstChild();
755 CHECK_NULL_VOID(firstChild);
756 if (firstChild->GetTag() == V2::ROW_ETS_TAG) {
757 auto textFrameNode = DynamicCast<FrameNode>(firstChild->GetChildAtIndex(0));
758 CHECK_NULL_VOID(textFrameNode);
759 auto layoutProperty = textFrameNode->GetLayoutProperty<TextLayoutProperty>();
760 CHECK_NULL_VOID(layoutProperty);
761 layoutProperty->UpdateTextColor(textColor);
762 }
763 if (firstChild->GetTag() == V2::TEXT_ETS_TAG) {
764 auto textFrameNode = DynamicCast<FrameNode>(firstChild);
765 CHECK_NULL_VOID(textFrameNode);
766 auto layoutProperty = textFrameNode->GetLayoutProperty<TextLayoutProperty>();
767 CHECK_NULL_VOID(layoutProperty);
768 layoutProperty->UpdateTextColor(textColor);
769 }
770 }
771 }
772
ButtonSkipColorConfigurationUpdate(RefPtr<FrameNode> buttonNode)773 void StepperPattern::ButtonSkipColorConfigurationUpdate(RefPtr<FrameNode> buttonNode)
774 {
775 auto pattern = buttonNode->GetPattern<ButtonPattern>();
776 CHECK_NULL_VOID(pattern);
777 pattern->SetSkipColorConfigurationUpdate();
778 }
779 } // namespace OHOS::Ace::NG
780