概述

AdaptiveBoxLayout是自适应盒子布局,该布局提供了在不同屏幕尺寸设备上的自适应布局能力,主要用于相同级别的多个组件需要在不同屏幕尺寸设备上自动调整列数的场景。

  • 该布局中的每个子组件都用一个单独的“盒子”装起来,子组件设置的布局参数都是以盒子作为父布局生效,不以整个自适应布局为生效范围。
  • 该布局中每个盒子的宽度固定为布局总宽度除以自适应得到的列数,高度为match_content,每一行中的所有盒子按高度最高的进行对齐。
  • 该布局水平方向是自动分块,因此水平方向不支持match_content,布局水平宽度仅支持match_parent或固定宽度。
  • 自适应仅在水平方向进行了自动分块,纵向没有做限制,因此如果某个子组件的高设置为match_parent类型,可能导致后续行无法显示。

image.png

方法功能
addAdaptiveRule(int minWidth, int maxWidth, int columns)添加一个自适应盒子布局规则。
removeAdaptiveRule(int minWidth,方法 int maxWidth, int columns)功能移除一个自适应盒子布局规则。
addAdaptiveRule(int minWidth, int maxWidth, int columns)clearAdaptiveRules()添加一个自适应盒子布局规则。移除所有自适应盒子布局规则。

这里需要注意的是,规则匹配规则是按照盒子的宽度匹配的。也就是说如果盒子宽度在规则范围内则生效,否则不生效

示例代码

布局文件

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:height="match_parent"
    ohos:width="match_parent"
    ohos:alignment="center"
    ohos:orientation="vertical">

    <AdaptiveBoxLayout
        ohos:id="$+id:adaptiveBox"
        ohos:height="match_content"
        ohos:width="match_parent"
        ohos:weight="1">

        <Text
            ohos:height="match_content"
            ohos:width="match_content"
            ohos:background_element="$graphic:background_box"
            ohos:margin="10vp"
            ohos:text="讲个故事吧"
            ohos:text_alignment="center"/>

        <Text
            ohos:height="match_content"
            ohos:width="match_content"
            ohos:background_element="$graphic:background_box"
            ohos:margin="10vp"
            ohos:text="从前有座山,山里有座庙"
            ohos:text_alignment="center"/>

        <Text
            ohos:height="match_content"
            ohos:width="match_content"
            ohos:background_element="$graphic:background_box"
            ohos:margin="10vp"
            ohos:text="庙里有个老和尚,老和尚在给小和尚讲故事"
            ohos:multiple_lines="true"
            ohos:text_alignment="center"/>

        <Text
            ohos:height="match_content"
            ohos:width="match_content"
            ohos:background_element="$graphic:background_box"
            ohos:margin="10vp"
            ohos:text="讲的啥呢"
            ohos:text_alignment="center"/>

        <Text
            ohos:height="match_content"
            ohos:width="match_content"
            ohos:background_element="$graphic:background_box"
            ohos:margin="10vp"
            ohos:text="从前有座山山里有座庙"
            ohos:text_alignment="center"/>
    </AdaptiveBoxLayout>

    <DirectionalLayout
        ohos:height="match_content"
        ohos:width="match_parent"
        ohos:orientation="horizontal"
        ohos:top_margin="30vp">

        <Button
            ohos:id="$+id:addRule"
            ohos:height="match_content"
            ohos:width="100vp"
            ohos:background_element="#FFFF00"
            ohos:margin="20vp"
            ohos:padding="10vp"
            ohos:text="添加规则"/>

        <Button
            ohos:id="$+id:removeRule"
            ohos:height="match_content"
            ohos:width="100vp"
            ohos:background_element="#FFFF00"
            ohos:margin="20vp"
            ohos:padding="10vp"
            ohos:text="移除规则"/>
    </DirectionalLayout>


</DirectionalLayout>

自适应代码

package com.example.adaptiveboxlayoutdemo.slice;

import com.example.adaptiveboxlayoutdemo.ResourceTable;
import ohos.aafwk.ability.AbilitySlice;
import ohos.aafwk.content.Intent;
import ohos.agp.components.AdaptiveBoxLayout;
import ohos.agp.components.Button;
import ohos.agp.components.Component;
import ohos.agp.components.Text;
import ohos.hiviewdfx.HiLog;

import java.util.Optional;

public class AdaptiveBoxLayoutSlice extends AbilitySlice implements Component.ClickedListener {
    private AdaptiveBoxLayout ada;
    private Button addBtn;
    private Button removeBtn;
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ability_adaptive_box_layout);
        ada = findComponentById(ResourceTable.Id_adaptiveBox);
        addBtn = findComponentById(ResourceTable.Id_addRule);
        removeBtn = findComponentById(ResourceTable.Id_removeRule);
        // --- listener ---
        addBtn.setClickedListener(this);
        removeBtn.setClickedListener(this);
    }

    @Override
    public void onActive() {
        super.onActive();
    }

    @Override
    public void onForeground(Intent intent) {
        super.onForeground(intent);
    }

    @Override
    public void onClick(Component component) {
        if (component==addBtn) {
            ada.addAdaptiveRule(100, 1300, 3);
            ada.postLayout();
        }

        if (component==removeBtn){
            ada.clearAdaptiveRules();
            ada.postLayout();
        }
    }
}

效果

自适应前
image.png

自适应后
image.png

简单解释下代码

ada.addAdaptiveRule(100, 1300, 3);

对宽度范围在(100-1300)vp的组件启用此规则。
规则的作用就是将当前容器内盒子分成3列

Q.E.D.


全栈混子的菜鸡日常