Android 单选按钮的自定义布局

Android 单选按钮的自定义布局,android,radio-button,radio-group,Android,Radio Button,Radio Group,是否有任何方法可以更改单选按钮的布局,并且仍然让放射组识别它 我需要的是,布局将包括两个EditText字段,以便当用户选择该按钮时,这些字段变为活动字段。 我知道我可以基于LinearLayout构建自定义零件,并使用以下工具设置自己的布局: (LinearLayout)LayoutFlater.from(context).充气(R.layout.my_layout,this,true) 但我不知道如何用单选按钮做同样的事情 我尝试过在RadioGroup之外设置额外字段并用按钮将其对齐的选项

是否有任何方法可以更改单选按钮的布局,并且仍然让放射组识别它

我需要的是,布局将包括两个EditText字段,以便当用户选择该按钮时,这些字段变为活动字段。 我知道我可以基于LinearLayout构建自定义零件,并使用以下工具设置自己的布局: (LinearLayout)LayoutFlater.from(context).充气(R.layout.my_layout,this,true) 但我不知道如何用单选按钮做同样的事情

我尝试过在RadioGroup之外设置额外字段并用按钮将其对齐的选项,但根本不起作用。 它似乎过于依赖于设备

这是原始布局的外观:

    <RadioGroup
    android:id="@+id/time_selector_radio_group"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_toLeftOf="@id/time_selector_hours_prompt"
    android:layout_below="@id/time_selector_hours_prompt"
    android:layout_alignParentRight="true"
    android:gravity="right"
    android:orientation="vertical"
    android:checkedButton="@+id/time_selector_first_radio"
    >

    <RadioButton
        android:id="@+id/time_selector_first_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@drawable/radio_button_selector"
        />
    <RadioButton
        android:id="@+id/time_selector_second_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@drawable/radio_button_selector"
        />
    <RadioButton
        android:id="@+id/time_selector_third_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@drawable/radio_button_selector"
        />
    <RadioButton
        android:id="@+id/time_selector_hours_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@drawable/radio_button_selector"
        />

</RadioGroup>
<TextView
    android:id="@+id/time_selector_all_day_prompt"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_toLeftOf="@id/time_selector_radio_group"
    android:layout_below="@id/time_selector_hours_prompt"
    android:layout_marginTop="11dip"
    android:text="@string/time_all_day"
    />
<TextView
    android:id="@+id/time_selector_before_noon_prompt"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_toLeftOf="@id/time_selector_radio_group"
    android:layout_below="@id/time_selector_all_day_prompt"
    android:layout_marginTop="19dip"
    android:text="@string/time_before_noon"
    />
<TextView
    android:id="@+id/time_selector_after_noon_prompt"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_toLeftOf="@id/time_selector_radio_group"
    android:layout_below="@id/time_selector_before_noon_prompt"
    android:layout_marginTop="19dip"
    android:text="@string/time_after_noon"
    />
<TextView
    android:id="@+id/time_selector_starting_time_prompt"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignRight="@id/time_selector_starting_date_prompt"
    android:layout_below="@id/time_selector_after_noon_prompt"
    android:layout_marginTop="20dip"
    android:layout_marginLeft="2dip"
    android:text="@string/advanced_time_selector_dialog_starting_time_prompt"
    />
<EditText
    android:id="@+id/time_selector_starting_time"
    android:layout_width="@dimen/advanced_time_selector_edit_texts_width"
    android:layout_height="wrap_content"
    android:layout_alignRight="@id/time_selector_starting_date"
    android:layout_alignBaseline="@id/time_selector_starting_time_prompt"
    android:textSize="14sp"
    android:paddingRight="10dip"
    android:paddingLeft="10dip"
    android:gravity="center"
    android:singleLine="true"
    android:maxWidth="@dimen/advanced_time_selector_edit_texts_width"
    android:background="@drawable/text_field_bg"
    android:inputType="datetime"
    />
<TextView
    android:id="@+id/time_selector_ending_time_prompt"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignRight="@id/time_selector_ending_date_prompt"
    android:layout_alignBottom="@id/time_selector_starting_time_prompt"
    android:layout_alignBaseline="@id/time_selector_starting_time_prompt"
    android:layout_marginRight="2dip"
    android:layout_marginLeft="2dip"
    android:text="@string/ending_date_prompt"
    />
<EditText
    android:id="@+id/time_selector_ending_time"
    android:layout_width="@dimen/advanced_time_selector_edit_texts_width"
    android:layout_height="wrap_content"
    android:layout_alignRight="@id/time_selector_ending_date"
    android:layout_alignBaseline="@id/time_selector_ending_time_prompt"
    android:textSize="14sp"
    android:paddingRight="10dip"
    android:paddingLeft="10dip"
    android:gravity="center"
    android:singleLine="true"
    android:maxWidth="@dimen/advanced_time_selector_edit_texts_width"
    android:background="@drawable/text_field_bg"
    android:inputType="datetime"
    />

请注意,该按钮没有任何文本,它被添加到文本视图中,因此我们可以将其放在左侧。 所发生的事情是,文本正在“悄悄上升”

所以,我把它改成这样:

<RadioGroup
    android:id="@+id/time_selector_radio_group"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_toLeftOf="@id/time_selector_hours_prompt"
    android:layout_below="@id/time_selector_hours_prompt"
    android:layout_alignParentRight="true"
    android:layout_marginRight="30dip"
    android:gravity="right"
    android:orientation="vertical"
    android:checkedButton="@+id/time_selector_first_radio"
    >

    <RadioButton
        android:id="@+id/time_selector_all_day_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@null"
        android:drawableRight="@drawable/radio_button_selector"
        android:text="@string/time_all_day"
        android:textColor="@color/content_text_color"
        />
    <RadioButton
        android:id="@+id/time_selector_before_noon_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@null"
        android:drawableRight="@drawable/radio_button_selector"
        android:text="@string/time_before_noon"
        android:textColor="@color/content_text_color"
        />

    <RadioButton
        android:id="@+id/time_selector_after_noon_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="1dip"
        android:button="@null"
        android:drawableRight="@drawable/radio_button_selector"
        android:text="@string/time_after_noon"
        android:textColor="@color/content_text_color"
        />

    <RelativeLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:orientation="horizontal">   
        <RadioButton
            android:id="@+id/time_selector_hours_radio"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginTop="1dip"
            android:button="@null"
            android:drawableRight="@drawable/radio_button_selector"
            android:layout_alignParentRight="true"
            android:text="@string/advanced_time_selector_dialog_starting_time_prompt"
            android:textColor="@color/content_text_color"
            android:layout_marginLeft="-1dip"
            android:paddingLeft="-1dip"
            />  
        <RelativeLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="horizontal"
            android:layout_toLeftOf="@id/time_selector_hours_radio"
            android:layout_alignParentLeft="true">            
            <EditText
                android:id="@+id/time_selector_starting_time"
                android:layout_width="@dimen/advanced_time_selector_edit_texts_width"
                android:layout_height="wrap_content"
                android:textSize="14sp"
                android:paddingRight="10dip"
                android:paddingLeft="10dip"
                android:gravity="center"
                android:singleLine="true"
                android:maxWidth="@dimen/advanced_time_selector_edit_texts_width"
                android:background="@drawable/text_field_bg"
                android:layout_alignParentRight="true"
                android:layout_alignBaseline="@id/time_selector_hours_radio"
                android:inputType="datetime"
                />
            <TextView
                android:id="@+id/time_selector_ending_time_prompt"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginRight="2dip"
                android:layout_marginLeft="2dip"
                android:text="@string/ending_date_prompt"
                android:layout_alignBaseline="@id/time_selector_hours_radio"
                android:layout_toLeftOf="@id/time_selector_starting_time"
                />
            <EditText
                android:id="@+id/time_selector_ending_time"
                android:layout_width="@dimen/advanced_time_selector_edit_texts_width"
                android:layout_height="wrap_content"
                android:textSize="14sp"
                android:paddingRight="10dip"
                android:paddingLeft="10dip"
                android:gravity="center"
                android:singleLine="true"
                android:maxWidth="@dimen/advanced_time_selector_edit_texts_width"
                android:layout_toLeftOf="@id/time_selector_ending_time_prompt"
                android:layout_alignBaseline="@id/time_selector_hours_radio"
                android:background="@drawable/text_field_bg"
                android:inputType="datetime"
                />
        </RelativeLayout>
    </RelativeLayout>

</RadioGroup>

它仍然不是完美的,当然,它不承认它是一个放射组


我想扩展RadioButton,但不知道如何更改那里的布局。

您必须创建一个扩展RadioGroup的类,并覆盖addViewPassThroughHierarchyChangeListener,才能为单选按钮使用自定义布局。默认情况下,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);
}

private class PassThroughHierarchyChangeListener implements
        ViewGroup.OnHierarchyChangeListener {
    private ViewGroup.OnHierarchyChangeListener mOnHierarchyChangeListener;

    /**
     * {@inheritDoc}
     */
    public void onChildViewAdded(View parent, View child) {
        if (parent == RadioGroup.this && child instanceof RadioButton) {
            int id = child.getId();
            // generates an id if it's missing
            if (id == View.NO_ID) {
                id = View.generateViewId();
                child.setId(id);
            }
            ((RadioButton) child).setOnCheckedChangeWidgetListener(
                    mChildOnCheckedChangeListener);
        }

        if (mOnHierarchyChangeListener != null) {
            mOnHierarchyChangeListener.onChildViewAdded(parent, child);
        }
    }

    /**
     * {@inheritDoc}
     */
    public void onChildViewRemoved(View parent, View child) {
        if (parent == RadioGroup.this && child instanceof RadioButton) {
            ((RadioButton) child).setOnCheckedChangeWidgetListener(null);
        }

        if (mOnHierarchyChangeListener != null) {
            mOnHierarchyChangeListener.onChildViewRemoved(parent, child);
        }
    }
}

我编写了一个名为
RadioGroup plus
的自定义
RadioGroup
,它将遍历它的子对象并找到
RadioButton
,无论
RadioButton
嵌套的深度有多深,它都会将找到的所有
RadioButton
链接在一起

您可以在此处找到回购协议:

回购协议的
自述文件
涵盖了如何使用它,实际上它的工作原理与您想象的一样,例如:

<worker8.com.github.radiogroupplus.RadioGroupPlus
    android:id="@+id/radio_group_plus"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical">
    <LinearLayout...>
       <ImageView...>
       <TextView...>
       <RadioButton...>
    </LinearLayout>
    <LinearLayout...>
       <ImageView...>
       <TextView...>
       <RadioButton...>
    </LinearLayout>
    <LinearLayout...>
       <ImageView...>
       <TextView...>
       <RadioButton...>
    </LinearLayout>
</worker8.com.github.radiogroupplus.RadioGroupPlus>
将此添加到“依赖项”下:

compile 'com.github.worker8:RadioGroupPlus:v1.0.1'
然后在xml中,将
RadioGroup
更改为
worker8.com.github.radiogroupplus.radiogroupplus
。现在,
radiogroup plus
下的所有
单选按钮都应该链接在一起


希望有帮助

这个问题可能已经有十年历史了,但我放弃它是为了帮助其他陷入这种情况的人

我用
TextView
代替了
单选按钮
,并创建了一个类来对它们进行分组,这可能是一种老式的方式,但我发现这是对我来说最优雅、最灵活的方式

用于文本视图布局的XML:

<RelativeLayout...>
    <TextView... android:id="@+id/o1">
    <TextView... android:id="@+id/o2">
    <ImageView...>
    <TextView... android:id="@+id/o3">
    <TextView... android:id="@+id/o4">
</RelativeLayout>

ButtonGroup.java

import java.util.ArrayList;
...

public class ButtonGroup {
    ArrayList<TextView> mOptions;
    int cur=0;
    int colorOn = Color.BLUE;
    int colorOff = Color.GRAY;
    ButtonGroup(ArrayList<TextView> options) {
        mOptions = options;
    }

    public void turnOn(int i){
        if(i!=cur){
            TextView pre = mOptions.get(cur);
            pre.setTextColor(colorOff);
            cur=i;
        }

        TextView next = mOptions.get(i);
        next.setTextColor(colorOn);
    }
}
import java.util.ArrayList;
...
公共类按钮组{
ArrayList mOptions;
int cur=0;
int colorOn=Color.BLUE;
int colorfoff=Color.GRAY;
按钮组(ArrayList选项){
选项=选项;
}
公共真空开关(int i){
如果(i!=cur){
TextView pre=mOptions.get(cur);
预置色(色差);
cur=i;
}
TextView next=mOptions.get(i);
next.setTextColor(colorOn);
}
}
onCreate活动方法:

protected void onCreate(Bundle savedInstanceState) {
    int current = 0;
    ArrayList<TextView> optionList = new ArrayList<>();
    optionList.add((TextView) findViewById(R.id.o1));
    optionList.add((TextView) findViewById(R.id.o2));
    optionList.add((TextView) findViewById(R.id.o3));
    optionList.add((TextView) findViewById(R.id.o4));
    ButtonGroup options = new ButtonGroup(optionList);
    options.turnOn(current);
}
创建时受保护的void(Bundle savedInstanceState){
int电流=0;
ArrayList optionList=新建ArrayList();
添加((TextView)findViewById(R.id.o1));
optionList.add((TextView)findViewById(R.id.o2));
optionList.add((TextView)findViewById(R.id.o3));
optionList.add((TextView)findViewById(R.id.o4));
按钮组选项=新建按钮组(选项列表);
选项。打开(当前);
}
它会给你类似的感觉


有您尝试过的示例代码吗?@donfede请参阅补充内容
protected void onCreate(Bundle savedInstanceState) {
    int current = 0;
    ArrayList<TextView> optionList = new ArrayList<>();
    optionList.add((TextView) findViewById(R.id.o1));
    optionList.add((TextView) findViewById(R.id.o2));
    optionList.add((TextView) findViewById(R.id.o3));
    optionList.add((TextView) findViewById(R.id.o4));
    ButtonGroup options = new ButtonGroup(optionList);
    options.turnOn(current);
}