1 /*
2 * Copyright (c) 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 #include "core/components/stepper/stepper_component.h"
17
18 #include "core/components/ifelse/if_else_component.h"
19 #include "core/components/stepper/render_stepper.h"
20 #include "core/components/stepper/stepper_element.h"
21
22 namespace OHOS::Ace {
23 namespace {
24
25 constexpr int32_t DEFAULT_NODE_INDEX = -1;
26
27 } // namespace
28
StepperComponent(const std::list<RefPtr<Component>> & children)29 StepperComponent::StepperComponent(const std::list<RefPtr<Component>>& children) : ComponentGroup(children)
30 {
31 stepperController_ = AceType::MakeRefPtr<StepperController>();
32 }
33
CreateElement()34 RefPtr<Element> StepperComponent::CreateElement()
35 {
36 return AceType::MakeRefPtr<StepperElement>();
37 }
38
CreateRenderNode()39 RefPtr<RenderNode> StepperComponent::CreateRenderNode()
40 {
41 return RenderStepper::Create();
42 }
43
SetStepperLabels(const std::vector<StepperLabels> & stepperLabels)44 void StepperComponent::SetStepperLabels(const std::vector<StepperLabels>& stepperLabels)
45 {
46 if (stepperLabels.empty()) {
47 LOGW("StepperLabels are empty.");
48 return;
49 }
50 stepperLabels_ = stepperLabels;
51 }
52
GetStepperLabels() const53 const std::vector<StepperLabels>& StepperComponent::GetStepperLabels() const
54 {
55 return stepperLabels_;
56 }
57
InsertChild(int32_t position,const RefPtr<Component> & child)58 void StepperComponent::InsertChild(int32_t position, const RefPtr<Component>& child)
59 {
60 if (position < 0) {
61 LOGE("InsertChild: the position is negative");
62 return;
63 }
64 auto item = StepperItemComponent::GetStepperItem(child);
65 if (!item) {
66 LOGE("InsertChild: no stepper item in child");
67 return;
68 }
69 auto pos = static_cast<uint32_t>(position);
70 const auto& children = GetChildren();
71 if (!child || pos > children.size()) {
72 return;
73 }
74 if (pos == children.size()) {
75 AppendChild(child);
76 return;
77 }
78 item->SetIndex(pos);
79 ComponentGroup::InsertChild(position, child);
80 auto labelIter = stepperLabels_.begin();
81 std::advance(labelIter, position);
82 stepperLabels_.insert(labelIter, item->GetLabel());
83 auto textIter = labelsTextStyles_.begin();
84 std::advance(textIter, position);
85 labelsTextStyles_.insert(textIter, item->GetTextStyle());
86 }
87
AppendChild(const RefPtr<Component> & child)88 void StepperComponent::AppendChild(const RefPtr<Component>& child)
89 {
90 auto stepperItemList = CollectItems(child);
91 if (!stepperItemList.empty()) {
92 for (const auto& item : stepperItemList) {
93 item->SetIndex(GetChildren().size());
94 ComponentGroup::AppendChild(item);
95 AppendLabel(item->GetLabel());
96 AppendTextStyle(item->GetTextStyle());
97 }
98 SetUpdateType(UpdateType::REBUILD);
99 return;
100 }
101
102 auto item = StepperItemComponent::GetStepperItem(child);
103 if (!item) {
104 LOGE("AppendChild: no stepper item in child");
105 return;
106 }
107 item->SetIndex(GetChildren().size());
108 ComponentGroup::AppendChild(child);
109 AppendLabel(item->GetLabel());
110 AppendTextStyle(item->GetTextStyle());
111 }
112
RemoveChild(const RefPtr<Component> & child)113 void StepperComponent::RemoveChild(const RefPtr<Component>& child)
114 {
115 auto item = StepperItemComponent::GetStepperItem(child);
116 if (!item) {
117 LOGE("RemoveChild: no stepper item in child");
118 return;
119 }
120 // removing children will reset label and styles
121 stepperLabels_.clear();
122 labelsTextStyles_.clear();
123 item->SetIndex(DEFAULT_NODE_INDEX);
124 ComponentGroup::RemoveChild(child);
125 }
126
CollectItems(const RefPtr<Component> & child)127 std::list<RefPtr<StepperItemComponent>> StepperComponent::CollectItems(const RefPtr<Component>& child)
128 {
129 std::list<RefPtr<StepperItemComponent>> stepperItemList;
130 auto ifElseComponent = AceType::DynamicCast<IfElseComponent>(child);
131 if (!ifElseComponent) {
132 return stepperItemList;
133 }
134
135 auto children = ifElseComponent->GetChildren();
136 for (auto& childComponent : children) {
137 auto itemComponent = StepperItemComponent::GetStepperItem(childComponent);
138 if (itemComponent) {
139 stepperItemList.emplace_back(itemComponent);
140 }
141 }
142 return stepperItemList;
143 }
144
145 } // namespace OHOS::Ace
146