* Copyright (c) 2021-2022 Huawei Device Co., Ltd.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_FLEX_RENDER_FLEX_H
#define FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_FLEX_RENDER_FLEX_H
#include "core/components/common/layout/constants.h"
#include "core/components/common/properties/text_enums.h"
#include "core/components/flex/render_flex_item.h"
#include "core/pipeline/base/render_node.h"
namespace OHOS::Ace {
class FlexComponent;
struct FlexItemProperties {
double totalShrink = 0.0;
double totalGrow = 0.0;
RefPtr<RenderFlexItem> lastShrinkChild;
RefPtr<RenderFlexItem> lastGrowChild;
};
struct BaselineProperties {
double maxBaselineDistance = 0.0;
double maxDistanceAboveBaseline = 0.0;
double maxDistanceBelowBaseline = 0.0;
};
struct MagicLayoutNode {
LayoutParam innerLayout = LayoutParam(Size(), Size());
RefPtr<RenderNode> node;
};
class ACE_FORCE_EXPORT RenderFlex : public RenderNode {
DECLARE_ACE_TYPE(RenderFlex, RenderNode);
public:
ACE_FORCE_EXPORT static RefPtr<RenderNode> Create();
void Update(const RefPtr<Component>& component) override;
void PerformLayout() override;
FlexDirection GetDirection() const
{
return direction_;
}
FlexAlign GetJustifyContent() const
{
return mainAxisAlign_;
}
FlexAlign GetAlignItems() const
{
return crossAxisAlign_;
}
double GetSpace() const
{
return space_;
}
Dimension GetInspectorSpace() const
{
return inspectorSpace_;
}
TextBaseline GetBaseline() const
{
return textBaseline_;
}
bool IsStretchToParent() const
{
return stretchToParent_;
}
FlexAlign GetAlignItem() const
{
return crossAxisAlign_;
}
AlignDeclarationPtr GetAlignPtr() const
{
return alignPtr_;
}
double GetBaselineDistance(TextBaseline baseline) override;
Size GetChildViewPort() override;
void OnChildRemoved(const RefPtr<RenderNode>& child) override;
void Dump() override;
bool IsChildOverflow() const
{
return isChildOverflow_;
}
bool GetAlignDeclarationOffset(AlignDeclarationPtr alignDeclarationPtr, Offset& offset) const override;
bool CheckIfNeedLayoutAgain() override;
void OnVisibleChanged() override;
std::string ProvideRestoreInfo() override;
protected:
void ClearRenderObject() override;
bool MaybeRelease() override;
Overflow overflow_ = Overflow::CLIP;
bool isChildOverflow_ = false;
bool isTabs_ = false;
bool isTabContent_ = false;
private:
void PerformLayoutInWeightMode();
void PerformLayoutInIndexMode();
void PerformLayoutInItemMode();
void LayoutMagicNodes(BaselineProperties& baselineProperties);
void RelayoutForStretchMagicNode();
void RelayoutForStretchFlexNode(const FlexItemProperties& flexItemProperties);
void LayoutHiddenNodes();
* This function is used to travel a single flex item in the first time layout to determine the flexItemProperties.
*
* @param flexItem The item under operation.
* @param flexItemProperties Store all the flex item properties.
*/
void LayoutFlexItem(RefPtr<RenderFlexItem>& flexItem, FlexItemProperties& flexItemProperties);
void RedoLayoutFlexItem(const RefPtr<RenderFlexItem>& flexItem, double flexSize, BaselineProperties& baselineProps,
double& allocatedFlexSpace);
void LayoutInfinityChild(const RefPtr<RenderNode>& item, double mainSize, BaselineProperties& baselineProperties);
* This function is used to determine all the items' sizes in the second time layout according to the
* flexItemProperties. The size of Flex(Row/Column) will be resized by the flex item.
*
* @param flexItemProps FlexItemProperties.
* @param baselineProps The distance properties of baseline.
*/
void ResizeItems(const FlexItemProperties& flexItemProps, BaselineProperties& baselineProps);
void DetermineSelfSize(MainAxisSize mainAxisSize, bool useViewPort);
void DetermineItemsPosition(const BaselineProperties& baselineProperties);
* This function is used to calculate the frontSpace and the betweenSpace according to mainAxisAlign and
* remainSpace. Only when the allocated size is smaller than the maxMainSize, it can be effective. In other word, it
* requires all the items are not flex items.
*
* @param remainSpace Remain space.
* @param frontSpace The space before the first item.
* @param betweenSpace The space between two items.
*/
void CalculateSpace(double remainSpace, double& frontSpace, double& betweenSpace) const;
* This function is used to place all the items according to the size and the space.
*
* @param frontSpace The space before the first item.
* @param betweenSpace The space between two items.
* @param baselineProperties The distance properties of baseline.
*/
void PlaceChildren(double frontSpace, double betweenSpace, const BaselineProperties& baselineProperties);
void LayoutAbsoluteChildren();
void CheckBaselineProperties(const RefPtr<RenderNode>& item, BaselineProperties& baselineProperties);
LayoutParam MakeStretchInnerLayoutParam(const RefPtr<RenderNode>& item) const;
LayoutParam MakeLayoutParamWithLimit(double minMainLimit, double maxMainLimit, bool isStretch) const;
LayoutParam MakeConstrainedLayoutParam(
double mainFlexExtent, const LayoutParam& constraint, bool isStretch, bool supportZerolayout = false) const;
void ResizeByItem(const RefPtr<RenderNode>& item, double& allocatedSize);
void CheckSizeValidity(const RefPtr<RenderNode>& item);
Size GetConstrainedSize(double mainSize);
double GetAvailableMainSize();
double GetMainSize(const RefPtr<RenderNode>& item) const;
double GetCrossSize(const RefPtr<RenderNode>& item) const;
double GetStretchCrossLimit() const;
void InitFlexProperties();
void TravelChildrenFlexProps();
void ClearChildrenLists();
FlexAlign GetSelfAlign(const RefPtr<RenderNode>& item) const;
TextDirection AdjustTextDirectionByDir();
void UpdateAccessibilityAttr();
void OnPaintFinish() override;
bool IsStartTopLeft(FlexDirection direction, TextDirection textDir) const;
void PerformItemAlign(std::list<RefPtr<RenderNode>>& nodelist);
FlexDirection direction_ = FlexDirection::ROW;
FlexAlign mainAxisAlign_ = FlexAlign::FLEX_START;
FlexAlign crossAxisAlign_ = FlexAlign::FLEX_START;
MainAxisSize mainAxisSize_ = MainAxisSize::MAX;
CrossAxisSize crossAxisSize_ = CrossAxisSize::MIN;
TextBaseline textBaseline_ = TextBaseline::ALPHABETIC;
FlexLayoutMode layoutMode_ = FlexLayoutMode::FLEX_ITEM_MODE;
bool stretchToParent_ = false;
double mainSize_ = 0.0;
double crossSize_ = 0.0;
double allocatedSize_ = 0.0;
double space_ = 0.0;
Dimension inspectorSpace_;
std::set<RefPtr<RenderNode>> infinityLayoutNodes_;
std::set<RefPtr<RenderNode>> absoluteNodes_;
std::list<RefPtr<RenderNode>> relativeNodes_;
std::list<RefPtr<RenderFlexItem>> stretchNodes_;
std::map<int32_t, std::list<MagicLayoutNode>> magicNodes_;
std::map<int32_t, double> magicWeightMaps_;
std::set<RefPtr<RenderNode>> displayNodes_;
RefPtr<RenderNode> scrollNode;
bool isMainInfinite_ = false;
bool isCrossInfinite_ = false;
bool useViewPort_ = false;
bool containsNavigation_ = false;
double navigationMainSize_ = 0.0;
int32_t validSizeCount_ = 0;
double totalFlexWeight_ = 0.0;
int32_t maxDisplayIndex_ = 0;
bool useOldLayoutVersion_ = false;
bool isDeclarative_ = false;
bool needRelayoutCross_ = false;
AlignDeclarationPtr alignPtr_ = nullptr;
};
}
#endif