鸿蒙开发之UI框架

news/2024/7/21 10:11:20 标签: harmonyos, ui, 华为

鸿蒙开发之UI框架

  • 一、Java UI框架
    • 概述
    • 组件和布局
    • Component和ComponentContainer
    • 布局配置LayoutConfig
    • 组件树
  • 二、常用布局
    • DirectionalLayout
      • 1.垂直方向排列
      • 2.水平方向排列
      • 3.不会自动换行
      • 4.对齐方式
      • 5.权重
    • DependentLayout
      • 相对于同级组件
      • 相对于父组件
      • 示例
    • TableLayout
    • StackLayout
  • 三、常用组件
    • 组件分类
    • Text
    • Button
    • TextField
    • Image
    • TabList和Tab
    • Picker
    • DatePicker
    • TimePicker
    • Switch
    • RadioButton
    • RadioContainer
    • Checkbox
    • ProgressBar
    • RoundProgressBar
    • ToastDialog
    • ScrollView
    • ListContainer
    • PageSlider
  • 四、布局与组件的使用
    • 1.XML创建布局
      • 方式一
      • 修改ability_main.xml
      • 创建按钮的背景
      • 启动测试
      • 方式二
      • 创建XML布局文件
      • 加载XML布局
      • 设置界面入口
      • 启动测试
    • 2.代码创建布局
      • 创建Ability
      • 设置界面入口
      • 编写界面
      • 启动测试
  • 五、页面跳转
    • ability_main.xml
    • MyAbilitySlice
    • MainAbilitySlice
    • 启动测试

一、Java UI框架

概述

Java UI框架提供了一部分Component和ComponentContainer的具体子类,即创建用户界面(UI)的各类组件(如:文本、按钮等)和常用的布局(如:DirectionalLayout和DependentLayout)。用户可通过组件进行交互操作,并获得响应。所有的UI操作都应该在主线程进行设置。

组件和布局

用户界面元素统称为组件,组件根据一定的层级结构进行组合形成布局。组件在未被添加到布局中时,既无法显示也无法交互,因此一个用户界面至少包含一个布局。

在UI框架中,具体的布局类通常以XXLayout命名,完整的用户界面是一个布局,用户界面中的一部分也可以是一个布局。布局中容纳Component与ComponentContainer对象。

Component和ComponentContainer

Component:提供内容显示,是界面中所有组件的基类,可以给Component设置事件处理回调来创建一个可交互的组件。JavaUI框架提供了一些常用的界面元素,也可称之为组件,组件一般直接继承Component或它的子类,如Text、Image等。

ComponentContainer:作为容器容纳Component或ComponentContainer对象,并对它们进行布局。Java UI框架提供了一些标准布局功能的容器,它们继承自ComponentContainer,一般以“Layout”结尾,如DirectionalLayout、DependentLayout等。
在这里插入图片描述

布局配置LayoutConfig

每种布局都根据自身特点提供LayoutConfig供子Component设定布局属性和参数,通过指定布局属性可以对子Component在布局中的显示效果进行约束。如:“width”、“height”是最基本的布局属性,指定了组件的大小。
在这里插入图片描述

组件树

布局把Component和ComponentContainer以树状的层级结构进行组织,这样的一个布局就称为组件树。组件树的特点是仅有一个根组件,其他组件有且仅有一个父节点,组件之间的关系受到父节点的规则约束。

二、常用布局

DirectionalLayout

DirectionalLayout是Java UI中的一种重要组件布局,用于将一组组件(Component)按照水平或者垂直方向排布,能够方便地对齐布局内的组件。

排列方向(orientation)分为水平(horizontal)或者垂直(vertical)方向。使用orientation设置布局内组件的排列方式,默认为垂直排列。
在这里插入图片描述

1.垂直方向排列

垂直方向排列三个按钮

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_content"
    ohos:orientation="vertical">
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:bottom_margin="3vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 1"/>
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:bottom_margin="3vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 2"/>
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:bottom_margin="3vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 3"/>
</DirectionalLayout>

color_cyan_element.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <solid
        ohos:color="#00FFFD"/>
</shape>

在这里插入图片描述

2.水平方向排列

水平方向排列三个按钮

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_content"
    ohos:orientation="horizontal">
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 1"/>
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 2"/>
    <Button
        ohos:width="33vp"
        ohos:height="20vp"
        ohos:left_margin="13vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 3"/>
</DirectionalLayout>

在这里插入图片描述

3.不会自动换行

DirectionalLayout不会自动换行,其子组件会按照设定的方向依次排列,若超过布局本身的大小,超出布局大小的部分将不会被显示

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="20vp"
    ohos:orientation="horizontal">
    <Button
        ohos:width="166vp"
        .....
        ohos:text="Button 1"/>
    <Button
        ohos:width="166vp"
		.....
        ohos:text="Button 2"/>
    <Button
        ohos:width="166vp"
        .....
        ohos:text="Button 3"/>
</DirectionalLayout>

此布局包含了三个按钮,但由于DirectionalLayout不会自动换行,超出布局大小的组件部分无法显示。界面显示如下:
在这里插入图片描述

4.对齐方式

DirectionalLayout中的组件使用layout_alignment控制自身在布局中的对齐方式,当对齐方式与排列方式方向一致时,对齐方式不会生效,如设置了水平方向的排列方式,则左对齐、右对齐将不会生效。

参数作用可搭配排列方式
left左对齐垂直排列
top顶部对齐水平排列
right右对齐垂直排列
bottom底部对齐水平排列
horizontal_center水平方向居中垂直排列
vertical_center垂直方向居中水平排列
center垂直与水平方向都居中水平/垂直排列

三种对齐方式

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="60vp">
    <Button
        ohos:width="50vp"
        ohos:height="20vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:layout_alignment="left"
        ohos:text="Button 1"/>
    <Button
        ohos:width="50vp"
        ohos:height="20vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:layout_alignment="horizontal_center"
        ohos:text="Button 2"/>
    <Button
        ohos:width="50vp"
        ohos:height="20vp"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:layout_alignment="right"
        ohos:text="Button 3"/>
</DirectionalLayout>

在这里插入图片描述

5.权重

权重(weight)就是按比例来分配组件占用父组件的大小,在水平布局下计算公式为:

父布局可分配宽度=父布局宽度-所有子组件width之和;

组件宽度=组件weight/所有组件weight之和*父布局可分配宽度;

实际使用过程中,建议使用width=0来按比例分配父布局的宽度,1:1:1效果如下:

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_content"
    ohos:orientation="horizontal">
    <Button
        ohos:width="0vp"
        ohos:height="20vp"
        ohos:weight="1"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 1"/>
    <Button
        ohos:width="0vp"
        ohos:height="20vp"
        ohos:weight="1"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Button 2"/>
    <Button
        ohos:width="0vp"
        ohos:height="20vp"
        ohos:weight="1"
        ohos:background_element="$graphic:color_cyan_element"
        ohos:text="Button 3"/>
</DirectionalLayout>

在这里插入图片描述

DependentLayout

DependentLayout与DirectionalLayout相比,拥有更多的排布方式,每个组件可以指定相对于其他同级元素的位置,或者指定相对于父组件的位置。

排列方式相对于其他同级组件或者父组件的位置进行布局。
在这里插入图片描述

相对于同级组件

相对于同级组件的位置布局

位置布局|描述|
–|–|-|
above|处于同级组件的上侧。
below|处于同级组件的下侧。
start_of|处于同级组件的起始侧。
end_of|处于同级组件的结束侧。
left_of|处于同级组件的左侧。
right_of|处于同级组件的右侧。

相对于父组件

相对于父组件的位置布局

位置布局描述
align_parent_left处于父组件的左侧。
align_parent_right处于父组件的右侧。
align_parent_start处于父组件的起始侧。
align_parent_end处于父组件的结束侧。
align_parent_top处于父组件的上侧。
align_parent_bottom处于父组件的下侧。
center_in_parent处于父组件的中间。

示例

<?xml version="1.0" encoding="utf-8"?>
<DependentLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_content"
    ohos:background_element="$graphic:color_background_gray_element">
    <Text
        ohos:id="$+id:text1"
        ohos:width="match_parent"
        ohos:height="match_content"
        ohos:text_size="25fp"
        ohos:top_margin="15vp"
        ohos:left_margin="15vp"
        ohos:right_margin="15vp"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Title"
        ohos:text_weight="1000"
        ohos:text_alignment="horizontal_center"
    />
    <Text
        ohos:id="$+id:text2"
        ohos:width="match_content"
        ohos:height="120vp"
        ohos:text_size="10vp"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Catalog"
        ohos:top_margin="15vp"
        ohos:left_margin="15vp"
        ohos:right_margin="15vp"
        ohos:bottom_margin="15vp"
        ohos:align_parent_left="true"
        ohos:text_alignment="center"
        ohos:multiple_lines="true"
        ohos:below="$id:text1"
        ohos:text_font="serif"/>
    <Text
        ohos:id="$+id:text3"
        ohos:width="match_parent"
        ohos:height="120vp"
        ohos:text_size="25fp"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Content"
        ohos:top_margin="15vp"
        ohos:right_margin="15vp"
        ohos:bottom_margin="15vp"
        ohos:text_alignment="center"
        ohos:below="$id:text1"
        ohos:end_of="$id:text2"
        ohos:text_font="serif"/>
    <Button
        ohos:id="$+id:button1"
        ohos:width="70vp"
        ohos:height="match_content"
        ohos:text_size="15fp"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Previous"
        ohos:right_margin="15vp"
        ohos:bottom_margin="15vp"
        ohos:below="$id:text3"
        ohos:left_of="$id:button2"
        ohos:italic="false"
        ohos:text_weight="5"
        ohos:text_font="serif"/>
    <Button
        ohos:id="$+id:button2"
        ohos:width="70vp"
        ohos:height="match_content"
        ohos:text_size="15fp"
        ohos:background_element="$graphic:color_gray_element"
        ohos:text="Next"
        ohos:right_margin="15vp"
        ohos:bottom_margin="15vp"
        ohos:align_parent_end="true"
        ohos:below="$id:text3"
        ohos:italic="false"
        ohos:text_weight="5"
        ohos:text_font="serif"/>
</DependentLayout>

color_background_gray_element.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <solid
        ohos:color="#ffbbbbbb"/>
</shape>

color_gray_element.xml:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <solid
        ohos:color="#ffbbbbbb"/>
</shape>

在这里插入图片描述

TableLayout

TableLayout使用表格的方式划分子组件, 也就是行和列的方式。

TableLayout可配置表格的排列方式,行数和列数,以及组件的位置。
在这里插入图片描述
在XML文件中创建TableLayout

<?xml version="1.0" encoding="utf-8"?>
<TableLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:height="match_parent"
    ohos:width="match_parent"
    ohos:background_element="#87CEEB"
    ohos:layout_alignment="horizontal_center"
    ohos:padding="8vp">
</TableLayout>

在xml创建Text的背景table_text_bg_element.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
       ohos:shape="rectangle">
    <corners
        ohos:radius="5vp"/>
    <stroke
        ohos:width="1vp"
        ohos:color="gray"/>
    <solid
        ohos:color="#00BFFF"/>
</shape>

在TableLayout布局中添加组件

<?xml version="1.0" encoding="utf-8"?>
<TableLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:height="match_parent"
    ohos:width="match_parent"
    ohos:background_element="#87CEEB"
    ohos:layout_alignment="horizontal_center"
    ohos:padding="8vp">
    <Text
        ohos:height="60vp"
        ohos:width="60vp"
        ohos:background_element="$graphic:table_text_bg_element.xml"
        ohos:margin="8vp"
        ohos:text="1"
        ohos:text_alignment="center"
        ohos:text_size="20fp"/>
 
    <Text
        ohos:height="60vp"
        ohos:width="60vp"
        ohos:background_element="$graphic:table_text_bg_element.xml"
        ohos:margin="8vp"
        ohos:text="2"
        ohos:text_alignment="center"
        ohos:text_size="20fp"/>
 
    <Text
        ohos:height="60vp"
        ohos:width="60vp"
        ohos:background_element="$graphic:table_text_bg_element.xml"
        ohos:margin="8vp"
        ohos:text="3"
        ohos:text_alignment="center"
        ohos:text_size="20fp"/>
 
    <Text
        ohos:height="60vp"
        ohos:width="60vp"
        ohos:background_element="$graphic:table_text_bg_element.xml"
        ohos:margin="8vp"
        ohos:text="4"
        ohos:text_alignment="center"
        ohos:text_size="20fp"/>
</TableLayout>

默认一列多行
在这里插入图片描述
设置行数和列数

ohos:row_count表示设置网格布局中行数,ohos:column_count表示设置网格布局中的列数。如果没有为子布局设置行列数,则自动继承父布局的行数和列数。在网格布局中若子组件的数量超出列数设置,则会自动添加行数。比如下列代码,我们设置一行,两列,但是是三个子组件,行数设置失效,会自动增加一行。

<TableLayout
    ...
    ohos:row_count="2"
    ohos:column_count="2">

设置对齐方式

属性值效果
align_edges表示子组件边界对齐,默认对齐方式。
align_contents表示子组件边距对齐。
<TableLayout
    ...
    ohos:alignment_type="align_contents">
    ...
</TableLayout>

StackLayout

StackLayout直接在屏幕上开辟出一块空白的区域,添加到这个布局中的视图都是以层叠的方式显示,而它会把这些视图默认放到这块区域的左上角,第一个添加到布局中视图显示在最底层,最后一个被放在最顶层。上一层的视图会覆盖下一层的视图。
在这里插入图片描述

StackLayout中组件的布局默认在区域的左上角,并且以后创建的组件会在上层

<?xml version="1.0" encoding="utf-8"?>
<StackLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:id="$+id:stack_layout"
    ohos:height="match_parent"
    ohos:width="match_parent">
 
    <Text
        ohos:id="$+id:text_blue"
        ohos:text_alignment="bottom|horizontal_center"
        ohos:text_size="24fp"
        ohos:text="第一层"
        ohos:height="400vp"
        ohos:width="400vp"
        ohos:background_element="#3F56EA" />
 
    <Text
        ohos:id="$+id:text_light_purple"
        ohos:text_alignment="bottom|horizontal_center"
        ohos:text_size="24fp"
        ohos:text="第二层"
        ohos:height="300vp"
        ohos:width="300vp"
        ohos:background_element="#00AAEE" />
 
    <Text
        ohos:id="$+id:text_orange"
        ohos:text_alignment="center"
        ohos:text_size="24fp"
        ohos:text="第三层"
        ohos:height="80vp"
        ohos:width="80vp"
        ohos:background_element="#00BFC9" />
        
</StackLayout>

三、常用组件

组件分类

根据组件的功能,可以将组件分为布局类、显示类、交互类三类:
组件类别|组件名称|功能描述|
–|–|–|–|
布局类|PositionLayout、DirectionalLayout、StackLayout、DependentLayout、TableLayout、AdaptiveBoxLayout|提供了不同布局规范的组件容器,例如以单一方向排列的DirectionalLayout、以相对位置排列的DependentLayout、以确切位置排列的PositionLayout等。
|显示类|Text、Image、Clock、TickTimer、ProgressBar|提供了单纯的内容显示,例如用于文本显示的Text,用于图像显示的Image等。
|交互类|TextField、Button、Checkbox、RadioButton/RadioContainer、Switch、ToggleButton、Slider、Rating、ScrollView、TabList、ListContainer、PageSlider、PageFlipper、PageSliderIndicator、Picker、TimePicker、DatePicker、SurfaceProvider、ComponentProvider|提供了具体场景下与用户交互响应的功能,例如Button提供了点击响应功能,Slider提供了进度选择功能等。

Text

Text是用来显示字符串的组件,在界面上显示为一块文本区域。Text作为一个基本组件,有很多扩展,常见的有按钮组件Button,文本编辑组件TextField。

创建Text

在layout目录下的xml文件中创建Text。

<Text
    ohos:id="$+id:text"
    ohos:width="match_content"
    ohos:height="match_content"
    ohos:text="Text"/>

创建背景

常用的背景如常见的文本背景、按钮背景,可以采用XML格式放置在graphic目录下。如:创建“background_text.xml”,在background_text.xml中定义文本的背景。

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">  //背景形状,oval椭圆,rectangle方形...
    <corners
        ohos:radius="20"/> //背景圆角程度
    <solid
        ohos:color="#878787"/>//背景颜色
</shape>

设置Text

在xml中设置Text的背景。

<Text
    ...
    ohos:background_element="$graphic:background_text"/>

字体大小,颜色,边距

   ohos:text_size="28fp"
    ohos:text_color="blue"
    ohos:left_margin="15vp"
    ohos:bottom_margin="15vp"
    ohos:right_padding="15vp"
    ohos:left_padding="15vp"

设置字体风格和字重

	ohos:italic="true"
    ohos:text_weight="700"
    ohos:text_font="serif"

设置文本对齐方式

ohos:text_alignment="horizontal_center|bottom"

设置文本换行和最大显示行数

ohos:multiple_lines="true"
ohos:max_text_lines="2"

自动调节字体大小

Text对象支持根据文本长度自动调整文本的字体大小和换行。

1.设置自动换行、最大显示行数和自动调节字体大小。

<Text
    ohos:id="$+id:text"
    ohos:width="90vp"
    ohos:height="match_content"
    ohos:min_height="30vp"
    ohos:text="T"
    ohos:text_color="#0000FF"
    ohos:italic="true"
    ohos:text_weight="700"
    ohos:text_font="serif"
    ohos:multiple_lines="true"
    ohos:max_text_lines="1"
    ohos:auto_font_size="true"
    ohos:right_padding="8vp"
    ohos:left_padding="8vp"
    ohos:background_element="$graphic:background_text"/>

2.通过setAutoFontSizeRule设置自动调整规则,三个入参分别是最小的字体大小、最大的字体大小、每次调整文本字体大小的步长。

Text text = (Text) findComponentById(ResourceTable.Id_text);
// 设置自动调整规则
text.setAutoFontSizeRule(30, 100, 1);
// 设置点击一次增多一个"T"
text.setClickedListener(new Component.ClickedListener() {
    @Override
    public void onClick(Component Component) {
        text.setText(text.getText() + "T");
    }
});

跑马灯效果

当文本过长时,可以设置跑马灯效果,实现文本滚动显示。前提是文本换行关闭且最大显示行数为1,默认情况下即可满足前提要求。

// 跑马灯效果
text.setTruncationMode(Text.TruncationMode.AUTO_SCROLLING);
// 启动跑马灯效果
text.startAutoScrolling();

响应点击事件

为Text对象添加一个点击事件,然后自定义响应点击事件的方法。如:通过创建一个Component.ClickedListener对象,然后通过调用setClickedListener将其分配给Text。

Text text = (Text)findComponentById(ResourceTable.Id_text_helloworld);
	// 为按钮设置点击事件回调
    text.setClickedListener(component->{
        // 此处添加点击按钮后的事件处理逻辑
    });

Button

Button是一种常见的组件,点击可以触发对应的操作,通常由文本或图标组成,也可以由图标和文本共同组成。

创建Button

在layout目录下的xml文件中创建Button,可以设置按钮的形状、颜色等。

<Button
    ohos:id="$+id:button"
    ohos:width="match_content"
    ohos:height="match_content"
    ohos:text_size="27fp"
    ohos:text="button"
    ohos:background_element="$graphic:background_button"
    ohos:left_margin="15vp"
    ohos:bottom_margin="15vp"
    ohos:right_padding="8vp"
    ohos:left_padding="8vp"
    ohos:element_left="$graphic:ic_btn_reload"
/>

graphic目录下xml文件(例:background_button.xml)

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <corners
        ohos:radius="10"/>
    <solid
        ohos:color="#007CFD"/>
</shape>

矢量图的转换

阿里巴巴矢量图标库

ic_btn_reload.xml:是一个矢量图,IED可以自动转换为xml文件,然后使用。

在graphic目录右键New => Svg To Xml => 然后选择Svg图标即可将Svg图标转换成xml文件。
ohos:element_left="$graphic:ic_btn_reload"

不同类型的按钮

按照按钮的形状,按钮可以分为:普通按钮,椭圆按钮,胶囊按钮,圆形按钮等。

1.普通按钮

普通按钮和其他按钮的区别在于不需要设置任何形状,只设置文本和背景颜色

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <solid
        ohos:color="#007CFD"/>
</shape>

2.椭圆按钮

椭圆按钮是通过设置background_element的来实现的,background_element的shape设置为椭圆(oval)

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="oval">
    <solid
        ohos:color="#007CFD"/>
</shape>
ohos:background_element="$graphic:oval_button_element"

3.胶囊按钮

胶囊按钮是一种常见的按钮,设置按钮背景时将背景设置为矩形形状,并且设置ShapeElement的radius的半径

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="rectangle">
    <corners
        ohos:radius="100"/>
    <solid
        ohos:color="#007CFD"/>
</shape>
ohos:background_element="$graphic:capsule_button_element"

4.圆形按钮

圆形按钮和椭圆按钮的区别在于组件本身的宽度和高度需要相同

    ohos:width="50vp"
    ohos:height="50vp"
    ohos:background_element="$graphic:circle_button_element"
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:shape="oval">
    <solid
        ohos:color="#007CFD"/>
</shape>

响应点击事件

用户点击按钮时,Button对象将收到一个点击事件,然后自定义响应点击事件的方法。如:通过创建一个Component.ClickedListener对象,然后通过调用setClickedListener将其分配给按钮。

Button button = (Button) findComponentById(ResourceTable.Id_button);
// 为按钮设置点击事件回调
button.setClickedListener(new Component.ClickedListener() {
    public void onClick(Component v) {
        // 此处添加点击按钮后的事件处理逻辑
    }
}); 

TextField

TextField提供了一种文本输入框。

创建TextField

<TextField
    ...
    ohos:height="40vp"
    ohos:width="200vp"
    ohos:left_padding="20vp"
 />

获取输入框的内容

String getContent = textField.getText();

设置TextField

<TextField
    ...
    ohos:background_element="$graphic:background_text_field"
 />

graphic目录下xml文件(例:background_text_field.xml)

<?xml version="1.0" encoding="UTF-8" ?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
       ohos:shape="rectangle">
    <corners
        ohos:radius="40"/>
    <solid
        ohos:color="#FFFFFF"/>
</shape>

设置提示文字

    ohos:hint="Enter phone number or email"/>

设置内边距

<TextField
    ...
    ohos:left_padding="24vp"
    ohos:right_padding="24vp"
    ohos:top_padding="8vp"
    ohos:bottom_padding="8vp"/>

设置多行显示

    ohos:multiple_lines="true"/>

设置不可用状态

通过TextField的Enable属性来控制文本框是否可用,当设置成false后,文本框不再能被输入。

TextField textField = (TextField) findComponentById(ResourceTable.Id_text_field);
textField.setEnabled(false);

响应焦点变化

textField.setFocusChangedListener(((component, isFocused) -> {
    
    if (isFocused) { 
        // 获取到焦点
        ...
    }else { 
        // 失去焦点
        ...
    }
}));

设置基线

 ohos:basement="#000099"

Image

Image是用来显示图片的组件。

创建Image

在src > main > resources > base > media”,添加一个图片至media文件夹下,既可以在XML中创建Image,也可以在代码中创建Image

在XML中创建Image

<Image
    ohos:id="$+id:image"
    ohos:width="match_content"
    ohos:height="match_content"
    ohos:layout_alignment="center"
    ohos:image_src="$media:plant"/>

在代码中创建Image

Image image = new Image(getContext());
image.setPixelMap(ResourceTable.Media_plant);

在这里插入图片描述

使用Image

设置透明度

ohos:image_src="$media:plant"
    ohos:alpha="0.5"

在这里插入图片描述

设置缩放系数

ohos:image_src="$media:plant"
    ohos:scale_x="0.5"
    ohos:scale_y="0.5"

在这里插入图片描述

设置缩放方式

当图片尺寸与Image尺寸不同时,可以根据不同的缩放方式来对图片进行缩放,如设置Image的宽高为200vp。以按比例缩小居中显示为例,设置ohos:scale_mode=“zoom_center”

缩放方式
按比例将原图扩大(缩小)到Image的宽度,居中显示。zoom_center
按比例将原图扩大(缩小)到Image的宽度,显示在Image的上部分位置。zoom_start
按比例将原图扩大(缩小)到Image的宽度,显示在Image的下部分位置。zoom_end
不按比例将图片扩大/缩小到Image的大小显示。stretch
保持原图的大小,显示在Image的中心。当原图的尺寸大于Image的尺寸时,超过部分裁剪处理。center
按比例将原图缩小到Image的宽度,将图片的内容完整居中显示。inside
按比例将原图扩大(缩小)到Image的宽度和高度中较大的值。如设置的高度值较大时,在垂直方向上完整显示,水平方向上超出Image宽度的部分裁剪处理。clip_center
ohos:image_src="$media:plant"
    ohos:scale_mode="zoom_center"

在这里插入图片描述

设置裁剪对齐模式

当Image尺寸小于图片尺寸时,可以对图片进行裁剪,仍以Image的宽高为200vp为例,小于图片尺寸。以左对齐裁剪为例,设置clip_alignment=“256”

裁剪方式
左对齐裁剪。left
右对齐裁剪。right
顶部对齐裁剪。top
底部对齐裁剪。bottom
居中裁剪。center
ohos:image_src="$media:plant"
    ohos:clip_alignment="256"

在这里插入图片描述

TabList和Tab

Tablist可以实现多个页签栏的切换,Tab为某个页签。子页签通常放在内容区上方,展示不同的分类。页签名称应该简洁明了,清晰描述分类的内容。

Picker

Picker提供了滑动选择器,允许用户从预定义范围中进行选择。

DatePicker

DatePicker主要供用户选择日期。

TimePicker

TimePicker主要供用户选择时间。

Switch

Switch是切换单个设置开/关两种状态的组件。

RadioButton

RadioButton用于多选一的操作,需要搭配RadioContainer使用,实现单选效果。

创建RadioButton

<RadioButton
    ohos:id="$+id:rb_1"
    ohos:height="40vp"
    ohos:width="match_content"
    ohos:text="A.Learning"
    ohos:text_size="20fp"/>

设置RadioButton

设置单选按钮的字体颜色

在xml中设置:text_color_on为选中状态的字体颜色,text_color_off为未选中状态的字体颜色

<RadioButton
    ...
    ohos:text_color_on="#00BFFF"
    ohos:text_color_off="#808080"/>

在Java代码中设置

rBtn.setTextColorOn(new Color(Color.getIntColor("#0066FF")));
rBtn.setTextColorOff(new Color(Color.getIntColor("#505050")));

监听事件

//监听方在RadioContainer身上
RadioContainer rc = (RadioContainer) findComponentById(ResourceTable.Id_rc_sex);
rc.setMarkChangedListener(new RadioContainer.CheckedStateChangedListener() {
    @Override
    public void onCheckedChanged(RadioContainer radioContainer, int i) {
        //i是radioButton的索引,从0开始
        RadioButton rb = (RadioButton) radioContainer.getComponentAt(i);
        String s = rb.getText().toString();
        new ToastDialog(MainAbilitySlice.this).setText(s).show();
    }
});

RadioContainer

RadioContainer是RadioButton的容器,在其包裹下的RadioButton保证只有一个被选项。

Checkbox

Checkbox可以实现选中和取消选中的功能。

创建Checkbox

<Checkbox
    ohos:id="$+id:check_box"
    ohos:height="match_content"
    ohos:width="match_content"
    ohos:text="This is a checkbox"
    ohos:text_size="20fp" />

设置Checkbox

ohos:check_element="$graphic:background_checkbox_check"

<?xml version="1.0" encoding="UTF-8" ?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
       ohos:shape="oval">
    <solid
        ohos:color="#00FFCC"/>
</shape>

Java代码设置Checkbox在选中与取消选中时的背景

ShapeElement elementButtonOn = new ShapeElement();
elementButtonOn.setRgbColor(RgbPalette.RED);
elementButtonOn.setShape(ShapeElement.RECTANGLE);
elementButtonOn.setCornerRadius(0.0f);
 
ShapeElement elementButtonOff = new ShapeElement();
elementButtonOff.setRgbColor(RgbPalette.BLACK);
elementButtonOff.setShape(ShapeElement.RECTANGLE);
elementButtonOff.setCornerRadius(0.0f);
 
StateElement checkElement = new StateElement();
checkElement.addState(new int[]{ComponentState.COMPONENT_STATE_CHECKED}, elementButtonOn);
checkElement.addState(new int[]{ComponentState.COMPONENT_STATE_EMPTY}, elementButtonOff);
 
Checkbox checkbox = (Checkbox) findComponentById(ResourceTable.Id_check_box);
checkbox.setButtonElement(checkElement);

设置Checkbox的文字在选中和取消选中时的颜色

ohos:text_color_on="#00AAEE"
    ohos:text_color_off="#000000"

设置选中状态

checkbox.setChecked(true);

设置不同状态之间的切换

如果当前为选中状态,那么将变为未选中;如果当前是未选中状态,将变为选中状态。

checkbox.toggle();

设置响应Checkbox状态变更的事件

// state表示是否被选中
checkbox.setCheckedStateChangedListener((view, state) -> {
    // 状态改变的逻辑
    ...
});

ProgressBar

ProgressBar用于显示内容或操作的进度。

创建ProgressBar

<ProgressBar
    ohos:progress_width="10vp"
    ohos:height="60vp"
    ohos:width="600vp"
    ohos:max="100"
    ohos:min="0"
    ohos:progress="60"/>

设置ProgressBar方向为垂直

ohos:orientation="vertical"

设置当前进度

ohos:progress="60"

progressBar.setProgressValue(60);

设置最大和最小值

ohos:max="400"
ohos:min="0"

progressBar.setMaxValue(400);
progressBar.setMinValue(0);

设置进度颜色

ohos:progress_element="#FF9900"

设置底色颜色

ohos:background_instruct_element="#FFFFFF"

设置分割线

ohos:divider_lines_enabled="true"
ohos:divider_lines_number="5"

progressBar.enableDividerLines(true);
progressBar.setDividerLinesNumber(5);

设置分割线颜色

progressBar.setDividerLineColor(Color.MAGENTA);

设置提示文字

ohos:progress_hint_text="20%"
    ohos:progress_hint_text_color="#FFCC99"

事件改变进度值

ProgressBar progressBar = (ProgressBar) findComponentById(ResourceTable.Id_my_pgb);
progressBar.setClickedListener(new Component.ClickedListener() {
    @Override
    public void onClick(Component component) {
        ProgressBar pgb = (ProgressBar) component;
        pgb.setProgressValue(pgb.getProgress()+5);
    }
});

RoundProgressBar

RoundProgressBar继承自ProgressBar,拥有ProgressBar的属性,在设置同样的属性时用法和ProgressBar一致,用于显示环形进度。

ToastDialog

ToastDialog是在窗口上方弹出的对话框,是通知操作的简单反馈。ToastDialog会在一段时间后消失,在此期间,用户还可以操作当前窗口的其他组件。

创建ToastDialog

new ToastDialog(getContext())
        .setText("This is a ToastDialog")
        .show();

设置其他属性

ToastDialog toastDialog = new ToastDialog(this);
//设置位置
toastDialog.setAlignment(LayoutAlignment.CENTER);
//大小
toastDialog.setSize(MATCH_CONTENT, MATCH_CONTENT);
//显示事件
toastDialog.setDuration(durationTime);
//自动关闭
toastDialog.setAutoClosable(true);

自定义ToastDialog的Component

DirectionalLayout toastLayout = (DirectionalLayout) LayoutScatter.getInstance(this)
                    .parse(ResourceTable.Layout_layout_toast, null, false);
new ToastDialog(getContext())
    .setComponent(toastLayout)
    .setSize(DirectionalLayout.LayoutConfig.MATCH_CONTENT, DirectionalLayout.LayoutConfig.MATCH_CONTENT)
    .setAlignment(LayoutAlignment.CENTER)
    .show();

layout_toast.xml布局

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:height="match_content"
    ohos:width="match_content"
    ohos:orientation="vertical">
    <Text
        ohos:id="$+id:msg_toast"
        ohos:height="match_content"
        ohos:width="match_content"
        ohos:left_padding="16vp"
        ohos:right_padding="16vp"
        ohos:top_padding="4vp"
        ohos:bottom_padding="4vp"
        ohos:layout_alignment="center"
        ohos:text_size="16fp"
        ohos:text="This is a ToastDialog for the customized component"
        ohos:background_element="$graphic:background_toast_element"/>
</DirectionalLayout>    

background_toast_element.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
       ohos:shape="rectangle">
    <corners
        ohos:radius="30vp"/>
    <solid
        ohos:color="#66808080"/>
</shape>

ScrollView

ScrollView是一种带滚动功能的组件,它采用滑动的方式在有限的区域内显示更多的内容。

创建ScrollView

<ScrollView
    ohos:id="$+id:scrollview"
    ohos:height="300vp"
    ohos:width="300vp"
    ohos:background_element="#FFDEAD"
    ohos:top_margin="32vp"
    ohos:bottom_padding="16vp"
    ohos:layout_alignment="horizontal_center">
    <DirectionalLayout
        ohos:height="match_content"
        ohos:width="match_content">
        <Image
            ohos:id="$+id:img_1"
            ohos:width="300vp"
            ohos:height="match_content"
            ohos:top_margin="16vp"
            ohos:image_src="$media:dog.png"/>
        <!--    放置任意需要展示的组件-->
        ...
    </DirectionalLayout>
</ScrollView>

ListContainer

ListContainer是用来呈现连续、多行数据的组件,包含一系列相同类型的列表项。

在layout目录下的xml文件中创建ListContainer

<?xml version="1.0" encoding="utf-8"?>
    <ListContainer
        xmlns:ohos="http://schemas.huawei.com/res/ohos"
        ohos:id="$+id:list_container"
        ohos:height="200vp"
        ohos:width="300vp"
        ohos:layout_alignment="horizontal_center"/>

在layout目录下新建xml文件(例:item_sample.xml),作为ListContainer的子布局。

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:height="match_content"
    ohos:width="match_parent"
    ohos:left_margin="16vp"
    ohos:right_margin="16vp"
    ohos:orientation="vertical">
    <Text
        ohos:id="$+id:item_index"
        ohos:height="match_content"
        ohos:width="match_content"
        ohos:padding="4vp"
        ohos:text="Item0"
        ohos:text_size="20fp"
        ohos:layout_alignment="center"/>
</DirectionalLayout>

创建SampleItem.java,作为ListContainer的数据包装类。

public class SampleItem {
    private String name;
    public SampleItem(String name) {
        this.name = name;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}

ListContainer每一行可以为不同的数据,因此需要适配不同的数据结构,使其都能添加到ListContainer上。创建SampleItemProvider.java,继承自RecycleItemProvider。

方法作用
int getCount()返回填充的表项个数。
Object getItem(int position)根据position返回对应的数据。
long getItemId(int position)返回某一项的id。
Component getComponent(int position, Component covertComponent,ComponentContainer componentContainer)根据position返回对应的界面组件。
public class SampleItemProvider extends RecycleItemProvider {
    //把数据封装在SampleItem对象的list里
    private List<SampleItem> list;
    //传入一个AbilitySlice
    private AbilitySlice slice;

    //构造器初始化属性
    public SampleItemProvider(List<SampleItem> list, AbilitySlice slice) {
        this.list = list;
        this.slice = slice;
    }

    @Override
    public int getCount() {
        return list.size();
    }

    @Override
    public Object getItem(int position) {
        return list.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    /**
     * @param position           组件在数据集里的位置
     * @param convertComponent   要重用的前一个组件
     * @param componentContainer 获取的组件的父组件
     * @return 实现getComponent需要item的布局,自己创建item_sample
     */
    @Override
    public Component getComponent(int position, Component convertComponent, ComponentContainer componentContainer) {
        Component component = convertComponent;
        if (component == null) {
            component = LayoutScatter.getInstance(slice).parse(ResourceTable.Layout_item_sample, null, false);
        }

        SampleItem sampleItem = list.get(position);
        Text text = (Text) component.findComponentById(ResourceTable.Id_item_index);
        text.setText(sampleItem.getName());
        return component;
    }
}

添加ListContainer的数据,并适配其数据结构。

public class MainAbilitySlice extends AbilitySlice{
    static final HiLogLabel LOG_LABEL = new HiLogLabel(HiLog.LOG_APP, 0x00002, "MainAbilitySlice");

    @Override
    public void onStart(Intent intent) {
        HiLog.info(LOG_LABEL, "--------onStart2");
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ListContainer);

        //初始化
        initListContainer();
        };

    /**
     * 初始化布局以及加载数据
     */
    private void initListContainer() {
        ListContainer listContainer = (ListContainer) findComponentById(ResourceTable.Id_list_container);
        List<SampleItem> list = getData();
        SampleItemProvider sampleItemProvider = new SampleItemProvider(list,this,this);
        listContainer.setItemProvider(sampleItemProvider);
    }

    /**
     * 构造数据
     * @return
     */
    private ArrayList<SampleItem> getData() {
        ArrayList<SampleItem> list = new ArrayList<>();
        for (int i = 0; i <= 18; i++) {
            list.add(new SampleItem("Item"+i));
        }
        return list;
    }
}

在这里插入图片描述
设置响应点击事件。

SampleItemProvider添加接口并设置初始化

    //list中的每个SampleItem被点击的时候触发,需要自己新建接口
    private ItemClickedListener linstener;

    //构造器初始化属性
    public SampleItemProvider(List<SampleItem> list, AbilitySlice slice, ItemClickedListener linstener) {
        this.list = list;
        this.slice = slice;
        this.linstener = linstener;
    }

 /**
     * 设置响应点击事件接口
     */
    public interface ItemClickedListener {
        void itemClick(SampleItem sampleItem);
    }

修改getComponent()方法

    /**
     * @param position           组件在数据集里的位置
     * @param convertComponent   要重用的前一个组件
     * @param componentContainer 获取的组件的父组件
     * @return 实现getComponent需要item的布局,自己创建item_sample
     */
    @Override
    public Component getComponent(int position, Component convertComponent, ComponentContainer componentContainer) {
        Component component = convertComponent;
        if (component == null) {
            component = LayoutScatter.getInstance(slice).parse(ResourceTable.Layout_item_sample, null, false);
        }

        SampleItem sampleItem = list.get(position);
        Text text = (Text) component.findComponentById(ResourceTable.Id_item_index);
        text.setText(sampleItem.getName());
        text.setClickedListener(new Component.ClickedListener() {
            @Override
            public void onClick(Component component) {
                linstener.itemClick(sampleItem);
            }
        });

        return component;
    }

继承SampleItemProvider.ItemClickedListener接口并重新其方法

public class MainAbilitySlice extends AbilitySlice  implements SampleItemProvider.ItemClickedListener{

	 @Override
	    public void itemClick(SampleItem sampleItem) {
	        new ToastDialog(getContext())
	                .setText("clicked:"+sampleItem.getName())
	                // Toast显示在界面中间
	                .setAlignment(LayoutAlignment.CENTER)
	                .show();
	    }
	}

在这里插入图片描述
设置点击事件(二)
该方式不需要自定义接口,目前使用时发现有问题

  text.setClickedListener(new Component.ClickedListener() {
            @Override
            public void onClick(Component component) {
                ListContainer listContainer = (ListContainer) componentContainer.findComponentById(ResourceTable.Id_list_container);
                listContainer.setItemClickedListener(new ListContainer.ItemClickedListener() {
                    @Override
                    public void onItemClicked(ListContainer listContainer, Component component, int i, long l) {
                        SampleItem item = (SampleItem) listContainer.getItemProvider().getItem(position);
                        new ToastDialog(slice.getContext())
                                .setText("clicked:"+item.getName())
                                // Toast显示在界面中间
                                .setAlignment(LayoutAlignment.CENTER)
                                .show();
                    }
                });
            }
        });

ListContainer的样式设置

属性Java方法作用
orientationsetOrientation(int orientation)设置布局方向
-setContentStartOffSet(int startOffset) setContentEndOffSet(int endOffset) setContentOffSet(int startOffset, int endOffset)设置列表容器的开始和结束偏移量
rebound_effectsetReboundEffect(boolean enabled)设置是否启用回弹效果
-setReboundEffectParams(int overscrollPercent, float overscrollRate, int remainVisiblePercent)setReboundEffectParams(ListContainer.ReboundEffectParams reboundEffectParams)设置回弹效果参数
shader_colorsetShaderColor(Color color)设置着色器颜色

设置布局方向

orientation设置为“horizontal”,表示横向布局;orientation设置为“vertical”,表示纵向布局。默认为纵向布局。

ohos:orientation="horizontal"

listContainer.setOrientation(Component.HORIZONTAL);

设置开始和结束偏移量

listContainer.setContentOffSet(32,16);

设置回弹效果

ohos:rebound_effect="true"

PageSlider

PageSlider是一个交互类组件.

main_pageSlider.xml

<?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:background_element="blue"
    ohos:orientation="vertical">

    <PageSlider
        ohos:id="$+id:pager_slider"
        ohos:height="0vp"
        ohos:width="match_parent"
        ohos:background_element="#ffffff"
        ohos:weight="1"/>

    <RadioContainer
        ohos:id="$+id:radio_container"
        ohos:height="60vp"
        ohos:width="match_parent"
        ohos:alignment="horizontal_center"
        ohos:orientation="horizontal">

        <RadioButton
            ohos:height="match_parent"
            ohos:width="match_content"
            ohos:text_size="20fp"
            />

        <RadioButton
            ohos:height="match_parent"
            ohos:width="match_content"
            ohos:text_size="20fp"
            />

    </RadioContainer>
</DirectionalLayout>

pageSlider1.xml

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

    <Text
        ohos:height="match_content"
        ohos:width="match_content"
        ohos:center_in_parent="true"
        ohos:text="PageSlider1"
        ohos:text_size="25fp"/>
</DependentLayout>

在AbiltiySlice里使用

public class MainAbilitySlice extends AbilitySlice {
    static final HiLogLabel LOG_LABEL = new HiLogLabel(HiLog.LOG_APP, 0x00002, "MainAbilitySlice");

    private RadioContainer radioContainer;
    private PageSlider pageSlider;
    private List<Component> pageviews;

    @Override
    public void onStart(Intent intent) {
        HiLog.info(LOG_LABEL, "--------onStart2");
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_main_pageSlider);

        radioContainer = (RadioContainer) findComponentById(ResourceTable.Id_radio_container);
        ((RadioButton) radioContainer.getComponentAt(0)).setChecked(true);

        pageSlider = (PageSlider) findComponentById(ResourceTable.Id_pager_slider);
        LayoutScatter layoutScatter = LayoutScatter.getInstance(getContext());
        DependentLayout dependentLayout1 = (DependentLayout) layoutScatter.parse(ResourceTable.Layout_pageSlider1, null, false);
        DependentLayout dependentLayout2 = (DependentLayout) layoutScatter.parse(ResourceTable.Layout_pageSlider2, null, false);

        //将view装入数组
        pageviews = new ArrayList<Component>();
        pageviews.add(dependentLayout1);
        pageviews.add(dependentLayout2);

        //绑定适配器
        pageSlider.setProvider(new PageSliderProvider() {
            @Override
            //获取当前窗体界面数
            public int getCount() {
                HiLog.info(LOG_LABEL, "--------getCount");
                return pageviews.size();
            }

            //返回一个对象,这个对象表明了PagerAdapter适配器选择哪个对象放在当前的pageviews中
            @Override
            public Object createPageInContainer(ComponentContainer componentContainer, int i) {
                componentContainer.addComponent(pageviews.get(i));
                HiLog.info(LOG_LABEL, "--------createPageInContainer");
                return pageviews.get(i);
            }

            //是从ViewGroup中移出当前View
            @Override
            public void destroyPageFromContainer(ComponentContainer componentContainer, int i, Object o) {
                ((PageSlider) componentContainer).removeComponent(pageviews.get(i));
                HiLog.info(LOG_LABEL, "--------destroyPageFromContainer");
            }

            //断是否由对象生成界面
            @Override
            public boolean isPageMatchToObject(Component component, Object o) {
                HiLog.info(LOG_LABEL, "--------isPageMatchToObject");
                return component == o;
            }
        });

        pageSlider.addPageChangedListener(new PageSlider.PageChangedListener() {
            @Override
            public void onPageSliding(int i, float v, int i1) {
                //v:指示页面的位置偏移量。值的范围是(0,1]。
                // 0表示正在显示目标页面。
                //i1:指示显示页面的位置偏移像素数。
            }

            @Override
            public void onPageSlideStateChanged(int i) {
                HiLog.info(LOG_LABEL, "--------onPageSlideStateChanged");
            }

            @Override
            public void onPageChosen(int i) {
                ((RadioButton) radioContainer.getComponentAt(i)).setChecked(true);
            }
        });
        radioContainer.setMarkChangedListener((radioContainer, i) -> pageSlider.setCurrentPage(i));
    }

}

在这里插入图片描述

四、布局与组件的使用

HarmonyOS提供了Ability和AbilitySlice两个基础类。有界面的Ability绑定了系统的Window进行UI展示,且具有生命周期。AbilitySlice主要用于承载Ability的具体逻辑实现和界面UI,是应用显示、运行和跳转的最小单元。AbilitySlice通过setUIContent为界面设置布局。

//设置界面入口,root为界面组件树根节点。
setUIContent(ComponentContainer root)

AbilitySlice的UI接口

接口声明接口描述
setUIContent(ComponentContainer root)设置界面入口,root为界面组件树根节点。

在Java UI框架中,提供了两种编写布局的方式,这两种方式创建出的布局没有本质差别。

1.在代码中创建布局:

用代码创建Component和ComponentContainer对象,为这些对象设置合适的布局参数和属性值,并将Component添加到ComponentContainer中,从而创建出完整界面。

2.在XML中声明UI布局:

按层级结构来描述Component和ComponentContainer的关系,给组件节点设定合适的布局参数和属性值,代码中可直接加载生成此布局。

1.XML创建布局

XML声明布局的方式更加简便直观。每一个Component和ComponentContainer对象大部分属性都支持在XML中进行设置,它们都有各自的XML属性列表。某些属性仅适用于特定的组件,例如:只有Text支持“text_color”属性,但不支持该属性的组件如果添加了该属性,该属性则会被忽略。具有继承关系的组件子类将继承父类的属性列表,Component作为组件的基类,拥有各个组件常用的属性,比如:ID、布局参数等。

ID

ohos:id="$+id:text"

在XML中使用此格式声明一个对开发者友好的ID,在编译过程中转换成一个常量。尤其在DependentLayout布局中,组件之间需要描述相对位置关系,描述时要通过ID来指定对应组件。

布局中的组件通常要设置独立的ID,以便在程序中查找该组件。如果布局中有不同组件设置了相同的ID,在通过ID查找组件时会返回查找到的第一个组件,因此尽量保证在所要查找的布局中为组件设置独立的ID值,避免出现与预期不符合的问题。

布局参数

ohos:width="20vp"
ohos:height="10vp"

具体的数值:10(以像素为单位)、10vp(以屏幕相对像素为单位)。
match_parent:表示组件大小将扩展为父组件允许的最大值,它将占据父组件方向上的剩余大小。
match_content:表示组件大小与它的内容占据的大小范围相适应。

方式一

修改ability_main.xml

打开layout下面的“ability_main.xml”文件,创建一个文本和一个按钮

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_parent"
    ohos:orientation="vertical"
    ohos:padding="32">
    <Text
        ohos:id="$+id:text"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:text="My name is Text."
        ohos:text_size="25vp"/>
    <Button
        ohos:id="$+id:button"
        ohos:margin="50"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:background_element="$graphic:background_button"
        ohos:text="My name is Button."
        ohos:text_size="50"/>
</DirectionalLayout>

创建按钮的背景

按钮的背景是通过“background_button”来指定的。右键点击“graphic”文件夹,选择“New > File”,命名为“background_button.xml”。

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:ohos="http://schemas.huawei.com/res/ohos"
       ohos:shape="rectangle">
    <corners
        ohos:radius="10"/>
    <solid
        ohos:color="#007CFD"/>
</shape>

启动测试

在这里插入图片描述

方式二

创建XML布局文件

1.在DevEco Studio的“Project”窗口,打开“entry > src > main > resources > base”,右键点击“layout”文件夹,选择“New > File”,命名为“first_layout.xml”。

2.打开新创建的first_layout.xml布局文件,修改其中的内容,对布局和组件的属性和层级进行描述

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_parent"
    ohos:orientation="vertical"
    ohos:padding="32">
    <Text
        ohos:id="$+id:text"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:text="My name is Text."
        ohos:text_size="25vp"/>
    <Button
        ohos:id="$+id:button"
        ohos:margin="50"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:text="My name is Button."
        ohos:text_size="50"/>
</DirectionalLayout>

加载XML布局

在代码中需要加载XML布局,并添加为根布局或作为其他布局的子Component。

package com.example.myapplication.slice;

import com.example.myapplication.ResourceTable;
import ohos.aafwk.ability.AbilitySlice;
import ohos.aafwk.content.Intent;
import ohos.agp.colors.RgbColor;
import ohos.agp.components.Button;
import ohos.agp.components.Component;
import ohos.agp.components.element.ShapeElement;

public class ExampleAbilitySlice extends AbilitySlice {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        // 加载XML布局作为根布局
        super.setUIContent(ResourceTable.Layout_first_layout);
        Button button = (Button) findComponentById(ResourceTable.Id_button);
        if (button != null) {
            // 设置组件的属性
            ShapeElement background = new ShapeElement();
            background.setRgbColor(new RgbColor(0, 125, 255));
            background.setCornerRadius(25);
            button.setBackground(background);

            button.setClickedListener(new Component.ClickedListener() {
                @Override
                // 在组件中增加对点击事件的检测
                public void onClick(Component Component) {
                    // 此处添加按钮被点击需要执行的操作
                }
            });
        }
    }
}

设置界面入口

public class MainAbility extends Ability {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        super.setMainRoute(ExampleAbilitySlice.class.getName());
    }
}

启动测试

在这里插入图片描述

2.代码创建布局

创建Ability

在这里插入图片描述
在这里插入图片描述
生成如下文件
在这里插入图片描述

设置界面入口

public class MainAbility extends Ability {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
       //super.setMainRoute(MainAbilitySlice.class.getName());
        super.setMainRoute(MyAbilitySlice.class.getName());
    }
}

编写界面

设置组件大小的方法有两种:

通过setWidth/setHeight直接设置宽高。
通过setLayoutConfig方法设置布局属性来设定宽高。

区别:

setLayoutConfig增加更多的布局属性设置
两种方法设置的宽高以最后设置的作为最终结果。

取值:

具体以像素为单位的数值。
MATCH_PARENT:表示组件大小将扩展为父组件允许的最大值,它将占据父组件方向上的剩余大小。
MATCH_CONTENT:表示组件大小与它内容占据的大小范围相适应。
public class MyAbilitySlice extends AbilitySlice {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        //xml布局
        //super.setUIContent(ResourceTable.Layout_ability_my);

        // 1.声明布局
        DependentLayout myLayout = new DependentLayout(this);
        // 2.设置页面布局大小
        myLayout.setWidth(MATCH_PARENT);
        myLayout.setHeight(MATCH_PARENT);
        //3.设置布局背景色
        ShapeElement element = new ShapeElement();
        element.setRgbColor(new RgbColor(255, 255, 255));
        myLayout.setBackground(element);

        // 4.1创建一个文本组件
        Text text = new Text(this);
        text.setText("My name is Text.");
        text.setTextSize(55);
        text.setTextColor(Color.BLACK);
        // 4.2设置文本的布局
        DependentLayout.LayoutConfig textConfig =
                new DependentLayout.LayoutConfig(MATCH_CONTENT,MATCH_CONTENT);
        textConfig.addRule(DependentLayout.LayoutConfig.CENTER_IN_PARENT);

        text.setLayoutConfig(textConfig);

        //5.将组件添加到布局中
        myLayout.addComponent(text);

        //6.将布局添加到组件树中
        super.setUIContent(myLayout);
    }

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

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

启动测试

在这里插入图片描述

五、页面跳转

ability_main.xml

ability_main.xml是主页面布局xml

<?xml version="1.0" encoding="utf-8"?>
<DirectionalLayout
    xmlns:ohos="http://schemas.huawei.com/res/ohos"
    ohos:width="match_parent"
    ohos:height="match_parent"
    ohos:orientation="vertical"
    ohos:padding="32">
    <Text
        ohos:id="$+id:text"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:text="这是第一张页面"
        ohos:text_size="25vp"/>
    <Button
        ohos:id="$+id:button"
        ohos:margin="50"
        ohos:width="match_content"
        ohos:height="match_content"
        ohos:layout_alignment="horizontal_center"
        ohos:background_element="$graphic:background_button"
        ohos:text="跳转页面"
        ohos:text_size="50"/>
</DirectionalLayout>

MyAbilitySlice

MyAbilitySlice是第二张页面,也是跳转页面.

public class MyAbilitySlice extends AbilitySlice {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        //xml布局
        //super.setUIContent(ResourceTable.Layout_ability_my);

        // 1.声明布局
        DependentLayout myLayout = new DependentLayout(this);
        // 2.设置页面布局大小
        myLayout.setWidth(MATCH_PARENT);
        myLayout.setHeight(MATCH_PARENT);
        //3.设置布局背景色
        ShapeElement element = new ShapeElement();
        element.setRgbColor(new RgbColor(255, 255, 255));
        myLayout.setBackground(element);

        // 4.1创建一个文本组件
        Text text = new Text(this);
        text.setText("这是第二张页面");
        text.setTextSize(55);
        text.setTextColor(Color.BLACK);
        // 4.2设置文本的布局
        DependentLayout.LayoutConfig textConfig =
                new DependentLayout.LayoutConfig(MATCH_CONTENT,MATCH_CONTENT);
        textConfig.addRule(DependentLayout.LayoutConfig.CENTER_IN_PARENT);

        text.setLayoutConfig(textConfig);

        //5.将组件添加到布局中
        myLayout.addComponent(text);

        //6.将布局添加到组件树中
        super.setUIContent(myLayout);
    }

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

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

MainAbilitySlice

MainAbilitySlice是主页面,跳转逻辑实现

public class MainAbilitySlice extends AbilitySlice {
    @Override
    public void onStart(Intent intent) {
        super.onStart(intent);
        super.setUIContent(ResourceTable.Layout_ability_main);

        //获取xml布局里面的button
        Button button = (Button) findComponentById(ResourceTable.Id_button);

        if (button != null) {
            // 为按钮设置监听事件


            //方式一
//            button.setClickedListener(component -> {
//
//            });

            //方式二
            button.setClickedListener(new Component.ClickedListener() {
                @Override
                public void onClick(Component component) {
                    //跳转目的地
                    Intent secondIntent = new Intent();
                    Operation operation = new Intent.OperationBuilder()
                            .withDeviceId("")//方法跳转目的地的设备,"":本机
                            .withBundleName("com.example.myapplication")//跳转目标页面所在的应用
                           // .withAbilityName("com.example.myapplication.MyAbility")//跳转到应用的那个Ability上
                            .withAbilityName(".MyAbility")//跳转到应用的那个Ability上
                            .build();
                    secondIntent.setOperation(operation);
                    startAbility(secondIntent); // 通过AbilitySlice的startAbility接口实现从MainAbility跳转到MyAbility页面
                }
            });
        }
    }

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

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

启动测试

在这里插入图片描述
点击Button
在这里插入图片描述
点击"<"返回按钮
在这里插入图片描述


http://www.niftyadmin.cn/n/876604.html

相关文章

Redis之Linux与Windows环境下的安装、启动与停止

Redis之Linux与Windows环境下的安装、启动与停止Redis概述基于Linux的Redis安装基于Linux的Redis启动与停止1.默认方式2.端口方式3.配置文件方式(一)4.配置文件方式(二)基于Windows的Redis安装Redis远程连接Redis的配置Redis概述 Redis 是一个开源&#xff08;BSD许可&#xff…

鸿蒙开发之Service Ability

鸿蒙开发之Service Ability1.基本概念2.创建Service2.注册Service3.启动Service启动本地设备Service启动远程设备Service4.停止Service停止本地设备Service停止远程设备Service5.连接Service使用代理跨设备调度创建Service Ability创建Page Ability本地设备连接Service远程设备…

Error creating bean with name ‘dataSource‘ 、 Failed to determine a suitable driver class

项目场景&#xff1a; sharding-jdbc和SpringBoot整合&#xff0c;使用druid数据源&#xff0c;使用<artifactId>druid-spring-boot-starter</artifactId>包 问题描述&#xff1a; 启动或测试出现初始化数据源&#xff08; Init DruidDataSource&#xff09;时报错…

在Windows环境与Linux环境下搭建MySQL主从同步

在Windows环境与Linux环境下搭建MySQL主从同步MySQL主从同步之Windows版准备Mysql实例修改主、从库的配置文件重启主库和从库创建授权主从复制的账号设置从库向主库同步/复制数据测试主从是否生效MySQL主从同步之Linux版MySQL安装主MySQL配置从MySQL配置重启创建授权主从复制的…

深入了解ArrayList

深入了解ArrayList1.数据结构2.继承关系3.ArrayList构造方法ArrayList()ArrayList(Collection<? extends E> c)ArrayList(int initialCapacity)4.add()add(E e)add(int index, E element)addAll(Collection<? extends E> c)addAll(int index, Collection<? e…

Sharding-JDBC之分库分表与读写分离

Sharding-JDBC之分库分表与读写分离一、分库分表什么是分库分表分库分表的方式分库分表的技术模式二、初识Sharding-JDBCSharding-JDBC概述Sharding-JDBC基本概念Sharding-JDBC执行过程引入依赖规则配置创建DataSource三、水平分表创建数据库/表配置分片规则1.properties配置2.…

Nginx之Linux环境与Windows环境下的安装与使用

Nginx之Linux环境与Windows环境下的安装与使用Nginx概述Linux环境下的搭建与使用1.下载、安装2.启动3.关闭4.重启与停止5.其他命令Window环境下的搭建与使用1.下载、安装2.解压3.启动4.关闭Nginx概述 Nginx &#xff08;engine x&#xff09; 是一个高性能的Web服务器和反向代理…

微信扫码支付完整实现示例

微信扫码支付完整实现示例阅读文档支付接口调用过程核心参数准备SDK下载SDK安装SDK到本地仓库微信扫码支付快速开始引入SDK创建WxConfig类统一下单生成二维码查询订单关闭订单支付成功回调推送支付通知RabbitMQ Web STOMP插件安装插件消息推送测试阅读文档 在线微信支付开发文…