Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android Radio buttons in a custom listview changes its state when we scroll the list

I am a beginner and facing a problem where I am creating a ListView with two RadioButtons and a TextView. Everything goes fine, but when I set RadioButtons and scroll it, the values of previous RadioButtons change their values or lose their state dramatically. I am trying to solve this problem for long time. What changes should I make to overcome this problem?

MainActivity.java

public class MainActivity extends Activity {

     private ListView listView1;
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);

            Option weather_data[] = new Option[]
                    {
                        new Option("Heading1"),
                        new Option("Heading12"),
                        new Option("Heading3"),
                        new Option("Heading4"),
                        new Option("Heading5"),
                        new Option("Heading6"),
                        new Option("Heading7"),
                        new Option("Heading8"),
                        new Option("Heading9"),
                        new Option("Heading10")
                    };
            RadioGroupAdapter adapter = new RadioGroupAdapter(this, 
                            R.layout.listitem, weather_data);
                    listView1 = (ListView)findViewById(R.id.list);
                    listView1.setAdapter(adapter);
        }

        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            getMenuInflater().inflate(R.menu.activity_main, menu);
            return true;
        }
    }

Option.java

public class Option {
     public String title;
        public Option(){
            super();
        }

        public Option( String title) {
            super();
            this.title = title;
        }
    }

RadioGroupAdapter.java

public class RadioGroupAdapter extends ArrayAdapter<Option> {

    Context context;
    int layoutResourceId;
    Option data[] = null;

    public RadioGroupAdapter(Context context, int layoutResourceId,
            Option[] data) {
        super(context, layoutResourceId, data);
        this.layoutResourceId = layoutResourceId;
        this.context = context;
        this.data = data;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View row = convertView;
        MatrixHolder holder = null;

        if (row == null) {
            LayoutInflater inflater = ((Activity) context).getLayoutInflater();
            row = inflater.inflate(layoutResourceId, parent, false);

            holder = new MatrixHolder();
            holder.txtTitle = (TextView) row.findViewById(R.id.heading);
            holder.group = (RadioGroup) row.findViewById(R.id.radio_group1);
            final RadioButton[] rb = new RadioButton[2];
            for(int i=0; i<2; i++){
                rb[i]  = new RadioButton(context);
                //rb[i].setButtonDrawable(R.drawable.single_radio_chice);
                rb[i].setId(i);
                RadioGroup.LayoutParams params = new RadioGroup.LayoutParams(
                        0, LayoutParams.WRAP_CONTENT);
                params.weight=1.0f;
                params.setMargins(5, 0, 5, 10);
                holder.group.addView(rb[i],params); //the RadioButtons are added to the radioGroup instead of the layout
            }
            row.setTag(holder);
        } else {
            holder = (MatrixHolder) row.getTag();
        }

        Option option = data[position];
        holder.txtTitle.setText(option.title);
        return row;
    }

    static class MatrixHolder {
        TextView txtTitle;
        RadioGroup group;
        int position;
    }
}

listitem.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal"
    android:weightSum="100" >

    <TextView
        android:id="@+id/heading"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_gravity="left"
        android:padding="10dp"
        android:textSize="18sp"
        android:textStyle="bold"
        android:layout_weight="50" />

    <RadioGroup
        android:id="@+id/radio_group1"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_gravity="center_vertical|center_horizontal"
        android:orientation="horizontal"
        android:layout_weight="50" >
    </RadioGroup>

</LinearLayout>
like image 743
Ashish Patil Avatar asked Sep 17 '13 06:09

Ashish Patil


2 Answers

You need to save the state of RadioButton for each item, so while scrolling in getView() method first it will check the state of each RadioButton.

Step1:- You need to create a Pojo class(Setter & Getter) for saving the state of RadioButton.

For more details go through the below link

http://amitandroid.blogspot.in/2013/03/android-listview-with-checkbox-and.html

This example is a ListView with CheckBox you need to change it to RadioButton according to your requirement.

like image 51
Amit Gupta Avatar answered Sep 21 '22 20:09

Amit Gupta


You adapter is always recreating the item for the list view. When he does that, he takes a "fresh" view and you have to set the data to this view using your array.

In your case, if you want to "save" the state of the radio button, you have to save this data as part of the adapter data, meaning in the array. I suggest you add a field to your Option object and use it save the last value of the radio button. afterwards, when they line Option option = data[position]; is being called, you can then reclaim the last value and display it on screen.

like image 27
Sean Avatar answered Sep 22 '22 20:09

Sean