![Hello HarmonyOS!:鸿蒙应用开发从入门到精通](https://wfqqreader-1252317822.image.myqcloud.com/cover/437/43738437/b_43738437.jpg)
2.3.4 RadioButton和RadioContainer
RadioButton是HarmonyOS中的单选按钮,继承自AbsButton类,AbsButton继承自Button类。AbsButton是一个抽象类,以它作为父类的组件通常用来做选择按钮,比如单选按钮、多选按钮、开关按钮等。RadioButton 组件的属性从 AbsButton类中继承,RadioButton组件区别于一般 Button组件的属性见表2-8。
表2-8 RadioButton组件区别于一般Button组件的属性
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_132_2.jpg?sign=1739278410-lPyfs4me2P3nPC7NIcMJGhSRvmftlXDU-0-36904270a34c78af7269161d8fdb5916)
单选按钮通常是需要用户在几个选项中做选择时应用的。下面来实现一个最简单的RadioButton组件。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_133_1.jpg?sign=1739278410-zrFs4Sq5eK7VJ3ySmoHc74koeaBDQMQ2-0-5ea8606efe1e5d0a8891b150e9959138)
在上述代码中,实现了一个 RadioButton 组件,ohos:text 属性的属性值为“男”,并且在它的前面有一个底色默认为白色的圆圈。当用户点击RadioButton组件时,代表这个单选按钮已经被选中,它的ohos:marked属性值会变为true,并且前面圆圈的颜色会发生变化,页面的预览效果如图2-40所示。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_133_2.jpg?sign=1739278410-M8ze95j20xkWNxqOVzHv9eSox7gCtiAA-0-9a7c740cda21e1f8dac054c84c01baf3)
图2-40 单个单选按钮
下面增加两个RadioButton组件,分别为“男”和“女”,用来做性别选择。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_134_1.jpg?sign=1739278410-ZE0FG8zLfjZSPRyJlT9TmCp4gpsczhmR-0-d3c9e04fcf3766c668a4a92b20266171)
页面的预览效果如图2-41所示。
我们有惯性思维,既然是单选按钮,那么只能从男和女之间选择一个,并且在选择了一个按钮后,另一个按钮就会变成未被选中状态。但是由于每个单选按钮都有被选中状态和未被选中状态,并不能影响其他按钮的状态,所以在上面的代码作用下,我们可以同时选中“男”和“女”,页面的预览效果如图2-42所示。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_135_1.jpg?sign=1739278410-ILEef3x4TfTSAcWFnqmHxh5qyAYCyg0R-0-82ff8fa22bb6dd7499427de0561375a2)
图2-41 多个单选按钮
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_135_2.jpg?sign=1739278410-yQArs0wYVuXSnmmS0UE9BcZttj21qYTU-0-d1ef8f714ed934d5362b745066c97844)
图2-42 多个单选按钮的被选中状态
要解决这个问题,需要对按钮进行分组,保证只有同一个组内的单选按钮才是互斥的,这就需要用到RadioContainer组件。
RadioContainer组件继承自DirectionalLayout,其属性来自DirectionalLayout。从名字上来看,它是单选按钮的容器。我们可以使用这个组件对单选按钮进行分组,代码如下。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_135_3.jpg?sign=1739278410-A8NWVolPgQ6vpYFgKDphJCqoIF7fd1gm-0-eac9fe2d42679d1cd644724e4943f0aa)
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_136_1.jpg?sign=1739278410-3paZNNvXjpHyJJtfPugxSm6o5W4RgYPa-0-50a76803ee4dbcf76ebaf1e71d14a784)
在 RadioButton 组件外层包裹了一层 RadioContainer 组件来标识此RadioContainer组件内的RadioButton组件是同一组的,内部的RadioButton组件具有互斥性,当选中其中某一个RadioButton组件后,其他RadioButton组件的状态都会变为未被选中,页面的预览效果如图2-43所示。
还可以通过 ohos:text_color_on、ohos:text_color_off、ohos:check_element属性对 RadioButton 组件进行样式上的修改。其他代码不变,对 RadioButton组件增加上面三个属性。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_136_2.jpg?sign=1739278410-O0wWQs56wiPUiNsJL1OuRHCkBVRXizOj-0-e104a775a723f02b20ef98ae3ff15948)
图2-43 带组别控制的多个单选按钮
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_136_3.jpg?sign=1739278410-iT77BYA3S5YVPGNxXNkCdyAuxqYNxVIN-0-9c47d3ec90737508536d3005b3d870f9)
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_137_1.jpg?sign=1739278410-GMcxw6PAwHty3xwUWOWcHu0DOS2CbffS-0-44b8ecfdee0b1e44dfc0ebde3d6c21e2)
这里的 ohos:check_element 属性引用了一个自定义样式文件 checkbox_check_element.xml,该文件保存在graphic目录下,内容如下。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_137_2.jpg?sign=1739278410-6XanhbXQiShvL3eBIZmMJkqSYC4U9Ira-0-9281dc942942cc4cf1e8129ec0ab2a22)
该文件是样式选择文件,根节点为<state-container>,子标签包含两个item,代表两种组件状态。每个item都通过ohos:state属性进行按钮状态的选择,通过 ohos:element 属性指定该状态下的组件的样式文件。两个 item 分别针对RadioButton组件前面的圆形标识符被选中和未被选中进行了不同的样式选择,每种状态的样式文件都通过“$graphic”来引用。单选按钮被选中时的样式文件checkbox_element_checked.xml的代码如下。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_137_3.jpg?sign=1739278410-NILa2plJvZaghw2eOe9BDxNshws3Is8j-0-0f9f8bff2d613697c981009a98c75aa2)
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_138_1.jpg?sign=1739278410-yEI8GvFI4Kx8qLgbBdUInE1XwCHLdv2p-0-0f174f009047eea32c64d1bc40961162)
这个资源文件指定了单选按钮被选中时,前面标识符的样式为带背景颜色的圆角矩形。当按钮未被选中时,仅把背景颜色改成灰色,样式文件checkbox_element_unchecked.xml的代码如下。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_138_2.jpg?sign=1739278410-fWtlc3e4FDq0IxSRGRGkmiz0r7kygpR8-0-31426ef5ccde3626cde52655d74eaf5c)
页面的预览效果如图2-44所示。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_138_3.jpg?sign=1739278410-HKSvlzPCpOa4duSKp2IrN1yjbGEKgeqB-0-b68504992e3fb7b9eadf7d4ba0c1d12c)
图2-44 带样式的单选按钮
下面用 Java 代码对单选按钮进行操作,首先为 RadioContainer 组件添加ohos:id属性。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_138_4.jpg?sign=1739278410-F8CACmUmMZfIwhxtusZVwjzm5Xzqiw1Q-0-e8528f88fdb861969434701b4f714f32)
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_139_1.jpg?sign=1739278410-RfAhqBPfrfEgnILigGLp1srAr72tUibE-0-64472b9eb99ed7063d44d2b8c74a4b1e)
在MainAbilitySlice中编写以下代码。
![](https://epubservercos.yuewen.com/0FFABF/23020655009774306/epubprivate/OEBPS/Images/42868_139_2.jpg?sign=1739278410-2F3jAYNKtRanM9vLa1A7nxQVbirC6f9b-0-fffe8c1ed628b88c13b9c44655710fb0)
在上述代码中,添加了RadioContainer.CheckedStateChangedListener()事件监听方法,当 RadioContainer 组件内的 RadioButton 组件状态发生变化时会回调这个方法。在onCheckedChanged(RadioContainer radioContainer,int i)方法中,可以通过入参i的值来对单选按钮进行索引,按照单选按钮的摆放顺序,索引值从0开始递增。在这个案例中,值为“男”的单选按钮的索引值为0,值为“女”的单选按钮的索引值为 1。在对应的 switch-case 语句分支中,可以对不同的按钮进行区分来完成不同的操作。