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 #ifndef FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_PATTERN_SWIPER_SWIPER_LAYOUT_ALGORITHM_H 17 #define FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_PATTERN_SWIPER_SWIPER_LAYOUT_ALGORITHM_H 18 19 #include <cstdint> 20 #include <optional> 21 22 #include "base/geometry/axis.h" 23 #include "base/geometry/ng/offset_t.h" 24 #include "base/memory/referenced.h" 25 #include "core/components_ng/layout/layout_algorithm.h" 26 #include "core/components_ng/layout/layout_wrapper.h" 27 28 namespace OHOS::Ace::NG { 29 30 struct SwiperItemInfo { 31 float startPos = 0.0f; 32 float endPos = 0.0f; 33 RefPtr<FrameNode> node; 34 OffsetF finialOffset; 35 }; 36 37 class ACE_EXPORT SwiperLayoutAlgorithm : public LayoutAlgorithm { 38 DECLARE_ACE_TYPE(SwiperLayoutAlgorithm, LayoutAlgorithm); 39 40 public: 41 using PositionMap = std::map<int32_t, SwiperItemInfo>; 42 43 SwiperLayoutAlgorithm() = default; 44 ~SwiperLayoutAlgorithm() override = default; 45 OnReset()46 void OnReset() override {} 47 void Measure(LayoutWrapper* layoutWrapper) override; 48 void Layout(LayoutWrapper* layoutWrapper) override; 49 50 void LayoutForward(LayoutWrapper* layoutWrapper, const LayoutConstraintF& layoutConstraint, Axis axis, 51 int32_t startIndex, float startPos); 52 void LayoutBackward(LayoutWrapper* layoutWrapper, const LayoutConstraintF& layoutConstraint, Axis axis, 53 int32_t endIndex, float endPos); 54 bool LayoutForwardItem(LayoutWrapper* layoutWrapper, const LayoutConstraintF& layoutConstraint, Axis axis, 55 int32_t& currentIndex, float startPos, float& endPos); 56 bool LayoutBackwardItem(LayoutWrapper* layoutWrapper, const LayoutConstraintF& layoutConstraint, Axis axis, 57 int32_t& currentIndex, float endPos, float& startPos); 58 float GetChildMaxSize(LayoutWrapper* layoutWrapper, Axis axis, bool isMainAxis) const; 59 int32_t GetLoopIndex(int32_t originalIndex) const; 60 SetItemsPosition(const PositionMap & itemPosition)61 void SetItemsPosition(const PositionMap& itemPosition) 62 { 63 itemPosition_ = itemPosition; 64 } 65 GetItemPosition()66 PositionMap&& GetItemPosition() 67 { 68 return std::move(itemPosition_); 69 } 70 SetJumpIndex(int32_t index)71 void SetJumpIndex(int32_t index) 72 { 73 jumpIndex_ = index; 74 } 75 SetCurrentDelta(float offset)76 void SetCurrentDelta(float offset) 77 { 78 currentDelta_ = offset; 79 currentOffset_ = offset; 80 } 81 SetOverScrollFeature()82 void SetOverScrollFeature() 83 { 84 overScrollFeature_ = true; 85 } 86 SetCanOverScroll(bool canOverScroll)87 void SetCanOverScroll(bool canOverScroll) 88 { 89 canOverScroll_ = canOverScroll; 90 } 91 SetTotalItemCount(int32_t totalItemCount)92 void SetTotalItemCount(int32_t totalItemCount) 93 { 94 totalItemCount_ = totalItemCount; 95 } 96 GetContentMainSize()97 float GetContentMainSize() const 98 { 99 return contentMainSize_; 100 } 101 SetContentMainSize(float contentMainSize)102 void SetContentMainSize(float contentMainSize) 103 { 104 contentMainSize_ = contentMainSize; 105 } 106 GetContentCrossSize()107 float GetContentCrossSize() const 108 { 109 return contentCrossSize_; 110 } 111 SetContentCrossSize(float contentCrossSize)112 void SetContentCrossSize(float contentCrossSize) 113 { 114 contentCrossSize_ = contentCrossSize; 115 } 116 SetCurrentOffset(float offset)117 void SetCurrentOffset(float offset) 118 { 119 currentOffset_ = offset; 120 } 121 GetCurrentOffset()122 float GetCurrentOffset() const 123 { 124 return currentOffset_; 125 } 126 SetTargetIndex(std::optional<int32_t> targetIndex)127 void SetTargetIndex(std::optional<int32_t> targetIndex) 128 { 129 targetIndex_ = targetIndex; 130 } 131 SetIsLoop(bool isLoop)132 void SetIsLoop(bool isLoop) 133 { 134 isLoop_ = isLoop; 135 } 136 GetStartIndex()137 int32_t GetStartIndex() const 138 { 139 return itemPosition_.empty() ? 0 : itemPosition_.begin()->first; 140 } 141 GetEndIndex()142 int32_t GetEndIndex() const 143 { 144 return itemPosition_.empty() ? 0 : itemPosition_.rbegin()->first; 145 } 146 GetStartPosition()147 float GetStartPosition() const 148 { 149 if (itemPosition_.empty()) { 150 return 0.0f; 151 } 152 if (GetStartIndex() == 0) { 153 return itemPosition_.begin()->second.startPos; 154 } 155 return itemPosition_.begin()->second.startPos - spaceWidth_; 156 } 157 GetEndPosition()158 float GetEndPosition() const 159 { 160 if (itemPosition_.empty()) { 161 return 0.0f; 162 } 163 if (GetEndIndex() == totalItemCount_ - 1) { 164 return itemPosition_.rbegin()->second.endPos; 165 } 166 return itemPosition_.rbegin()->second.endPos + spaceWidth_; 167 } 168 SetMainSizeIsMeasured(bool mainSizeIsMeasured)169 void SetMainSizeIsMeasured(bool mainSizeIsMeasured) 170 { 171 mainSizeIsMeasured_ = mainSizeIsMeasured; 172 } 173 GetMainSizeIsMeasured()174 bool GetMainSizeIsMeasured() const 175 { 176 return mainSizeIsMeasured_; 177 } 178 GetCurrentIndex()179 int32_t GetCurrentIndex() const 180 { 181 return currentIndex_; 182 } 183 SetIsNeedResetPrevMarginAndNextMargin()184 void SetIsNeedResetPrevMarginAndNextMargin() 185 { 186 isNeedResetPrevMarginAndNextMargin_ = false; 187 } 188 GetIsNeedResetPrevMarginAndNextMargin()189 bool GetIsNeedResetPrevMarginAndNextMargin() const 190 { 191 return isNeedResetPrevMarginAndNextMargin_; 192 } 193 194 private: 195 void MeasureSwiper(LayoutWrapper* layoutWrapper, const LayoutConstraintF& layoutConstraint, Axis axis); 196 void SetInactive( 197 LayoutWrapper* layoutWrapper, float startMainPos, float endMainPos, std::optional<int32_t> targetIndex); 198 199 void PlaceDigitChild(const RefPtr<LayoutWrapper>& indicatorWrapper, const RefPtr<LayoutProperty>& layoutProperty); 200 RefPtr<LayoutWrapper> GetNodeLayoutWrapperByTag(LayoutWrapper* layoutWrapper, const std::string& tagName) const; 201 void MeasureArrow(const RefPtr<LayoutWrapper>& arrowWrapper, const RefPtr<LayoutProperty>& layoutProperty) const; 202 void ArrowLayout( 203 LayoutWrapper* layoutWrapper, const RefPtr<LayoutWrapper>& arrowWrapper, const PaddingPropertyF padding) const; 204 void ResetOffscreenItemPosition(LayoutWrapper* layoutWrapper, int32_t index, bool isForward, Axis axis) const; 205 bool isLoop_ = true; 206 float prevMargin_ = 0.0f; 207 float nextMargin_ = 0.0f; 208 209 PositionMap itemPosition_; 210 float currentOffset_ = 0.0f; 211 float currentDelta_ = 0.0f; 212 float startMainPos_ = 0.0f; 213 float endMainPos_ = 0.0f; 214 215 float paddingBeforeContent_ = 0.0f; 216 float paddingAfterContent_ = 0.0f; 217 float contentMainSize_ = 0.0f; 218 float contentCrossSize_ = 0.0f; 219 int32_t totalItemCount_ = 0; 220 bool mainSizeIsDefined_ = false; 221 222 float spaceWidth_ = 0.0f; 223 bool overScrollFeature_ = false; 224 bool canOverScroll_ = false; 225 226 bool mainSizeIsMeasured_ = false; 227 228 std::optional<int32_t> jumpIndex_; 229 std::optional<int32_t> targetIndex_; 230 std::optional<int32_t> currentTargetIndex_; 231 int32_t currentIndex_ = 0; 232 bool targetIsSameWithStartFlag_ = false; 233 bool isNeedResetPrevMarginAndNextMargin_ = false; 234 }; 235 236 } // namespace OHOS::Ace::NG 237 #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_PATTERN_SWIPER_SWIPER_LAYOUT_ALGORITHM_H 238