公司项目最近有个这样的需求,要求实现【多个文本,多行显示,且同时只能选中一个】。设计图效果如下:
看上去很简单,使用 RadioGroup + LinearLayout + RadioButton 快速实现:
<RadioGroupandroid:id="@+id/rg"android:layout_width="match_parent"android:layout_height="match_parent"android:layout_marginLeft="@dimen/SIZE_18"android:layout_marginTop="@dimen/SIZE_9"android:layout_marginRight="@dimen/SIZE_18"android:layout_marginBottom="@dimen/SIZE_20"><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="horizontal"><RadioButtonandroid:id="@+id/RadioButton1"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_abnormal_function"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12"></RadioButton><RadioButtonandroid:id="@+id/RadioButton2"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginLeft="@dimen/SIZE_10"android:autoSizeMaxTextSize="18sp"android:autoSizeMinTextSize="6sp"android:autoSizeStepGranularity="1sp"android:autoSizeTextType="uniform"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_experience_problem"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12"></RadioButton><RadioButtonandroid:id="@+id/RadioButton3"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginLeft="@dimen/SIZE_10"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_new_feature_suggestion"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12"></RadioButton></LinearLayout><RadioButtonandroid:id="@+id/RadioButton4"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginTop="@dimen/SIZE_9"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_type_other"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12"></RadioButton>
</RadioGroup>
跑起来后,发现并没有实现单选的效果,究其根本,观其RadioGroup源码:
@Override
public void addView(View child, int index, ViewGroup.LayoutParams params) {if (child instanceof RadioButton) {final RadioButton button = (RadioButton) child;if (button.isChecked()) {mProtectFromCheckedChange = true;if (mCheckedId != -1) {setCheckedStateForView(mCheckedId, false);}mProtectFromCheckedChange = false;setCheckedId(button.getId());}}super.addView(child, index, params);
}
RadioGroup在添加子view时,仅判断了其是否是RadioButton,故LinearLayout并不符合这一条件,要想实现内嵌LinearLayout+RadioButton,只能自定义RadioGroup,并重写addView方法。本文使用了另一方式解决这个问题:
使用多个RadioGroup内嵌RadioButton,当其中1个RadioGroup中的RadioButton被选中时,清除其他RadioGroup的选中效果,代码如下:
<RadioGroupandroid:id="@+id/rg"android:layout_width="match_parent"android:layout_height="match_parent"android:layout_marginLeft="@dimen/SIZE_18"android:layout_marginTop="@dimen/SIZE_9"android:layout_marginRight="@dimen/SIZE_18"android:orientation="horizontal"><RadioButtonandroid:id="@+id/RadioButton1"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_abnormal_function"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12" /><RadioButtonandroid:id="@+id/RadioButton2"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginLeft="@dimen/SIZE_10"android:autoSizeMaxTextSize="18sp"android:autoSizeMinTextSize="6sp"android:autoSizeStepGranularity="1sp"android:autoSizeTextType="uniform"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_experience_problem"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12" /><RadioButtonandroid:id="@+id/RadioButton3"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginLeft="@dimen/SIZE_10"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_new_feature_suggestion"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12" /></RadioGroup><RadioGroupandroid:id="@+id/rgTow"android:layout_width="match_parent"android:layout_height="match_parent"android:layout_marginLeft="@dimen/SIZE_18"android:layout_marginRight="@dimen/SIZE_18"android:layout_marginBottom="@dimen/SIZE_20"><RadioButtonandroid:id="@+id/RadioButton4"style="@style/fontStyle"android:layout_width="wrap_content"android:layout_height="28dp"android:layout_marginTop="@dimen/SIZE_9"android:background="@drawable/bg_button_bg"android:button="@null"android:paddingLeft="@dimen/SIZE_10"android:paddingRight="@dimen/SIZE_10"android:text="@string/str_type_other"android:textColor="@drawable/text_color_select"android:textSize="@dimen/SP_SIZE_12" />
</RadioGroup>
实现逻辑:
private fun init(){mViewBind.rg.setOnCheckedChangeListener(OneCheckedChange())mViewBind.rgTow.setOnCheckedChangeListener(TowCheckedChange())
}inner class OneCheckedChange : OnCheckedChangeListener {override fun onCheckedChanged(group: RadioGroup?, checkedId: Int) {// 清除另一RadioGroup选中状态mViewBind.rgTow.setOnCheckedChangeListener(null)mViewBind.rgTow.clearCheck()mViewBind.rgTow.setOnCheckedChangeListener(TowCheckedChange())// 根据 ID 判断选择的按钮mtype = when (checkedId) {R.id.RadioButton1 -> 1R.id.RadioButton2 -> 2R.id.RadioButton3 -> 3else -> 0}}}inner class TowCheckedChange : OnCheckedChangeListener{override fun onCheckedChanged(group: RadioGroup?, checkedId: Int) {mViewBind.rg.setOnCheckedChangeListener(null)mViewBind.rg.clearCheck()mViewBind.rg.setOnCheckedChangeListener(OneCheckedChange())// 根据 ID 判断选择的按钮if(checkedId == R.id.RadioButton4){mtype =4}}}
至此实现【多个文本,多行显示,且同时只能选中一个】效果。