一次只选择一个复选框的自定义列表视图

时间:2014-11-24 12:46:25

标签: android listview checkbox

我有一个自定义列表视图,每行包含一个复选框和文本。现在我想要的是如果任何一个listview行的复选框被选中,那么其他行中的其他复选框如果被选中.it将被自动选择。(即一次只能选择一个复选框)。我应该怎么做。< / p>

到目前为止,我所做的工作如下:

public class CustomAdapter extends BaseAdapter{

    Context context;
    List<String> items;

     boolean array[];


    public CustomAdapter(Context context, List<String> items) {
    super();
    this.context = context;
    this.items = items;
    array =new boolean[items.size()];
}


    @Override
    public int getCount() {
        // TODO Auto-generated method stub
        return items.size();
    }

    @Override
    public Object getItem(int position) {
        // TODO Auto-generated method stub
        return items.get(position);
    }

    @Override
    public long getItemId(int position) {
        // TODO Auto-generated method stub
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        // TODO Auto-generated method stub
        View v=convertView;
        final int pos=position;
        if(v==null)
        {
            v=LayoutInflater.from(context).inflate(R.layout.list,null);
        }

        TextView txt1=(TextView) v.findViewById(R.id.textView1);
        final CheckBox chkbox=(CheckBox) v.findViewById(R.id.checkBox1);

        txt1.setText(items.get(position));
        int selectedindexitem=0;
        chkbox.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                if(chkbox.isChecked())
                {
                    array[pos]=true;


                }else{
                    array[pos]=false;
                }
            }
        }); 
        chkbox.setChecked(array[pos]);





        return v; 
    }




}

In this code i can select multiple checkbox at a time but i need only one checkbox should be checked one at a time.

7 个答案:

答案 0 :(得分:10)

您需要相应地跟踪所选项目和代码。

public class CustomAdapter extends BaseAdapter{
    Integer selected_position = -1;

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
            // Your Code

            chkbox.setChecked(position==selected_position);

            chkbox.setOnCheckedChangeListener(new OnCheckedChangeListener() {

                @Override
                public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                    if(isChecked)
                    {
                        selected_position =  position;
                    }
                    else{
                         selected_position = -1;
                    }
                    notifyDataSetChanged();
                }
            });
            return convertView;


        }
}

答案 1 :(得分:5)

尝试更改所有项目布尔值false在通知适配器后排除选定项目,并为ListView性能实现ViewHolder设计模式:

    @Override
    public View getView(final int position, View convertView, ViewGroup parent) {
        ViewHolder holder;
        if(convertView==null){
            holder = new ViewHolder();
            convertView = LayoutInflater.from(context).inflate(R.layout.list,null);
            holder.txt1 = (TextView) convertView.findViewById(R.id.textView1);
            holder.chkbox = (CheckBox) convertView.findViewById(R.id.checkBox1);
            convertView.setTag(holder);
        }else{
            holder = (ViewHolder) convertView.getTag();
        }

        holder.txt1.setText(items.get(position));
        holder.chkbox.setChecked(array[position]);
        holder.chkbox.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                for (int i=0;i<array.length;i++){
                    if(i==position){
                        array[i]=true;
                    }else{
                        array[i]=false;
                    }
                }
                notifyDataSetChanged();
            }
        });

        return convertView;
    }

    class ViewHolder{
        TextView txt1;
        CheckBox chkbox;
    }

答案 2 :(得分:1)

维护变量:

int checked = -1;  //say

每当你尝试检查一个复选框时,你检查这个变量,如果它是-1然后检查复选框并保存列表项的位置在已检查变量中,当你试图再次检查其他复选框时,如果变量ain&# 39; t等于-1,首先取消选中已检查变量中存储的位置的复选框,然后选中当前位置的复选框并将当前位置保存在已检查变量中

答案 3 :(得分:1)

@Override
    public View getView(int position, View convertView, ViewGroup parent) {
        // TODO Auto-generated method stub
        View v=convertView;
        final int pos=position;
        if(v==null)
        {
            v=LayoutInflater.from(context).inflate(R.layout.list,null);
        }

        TextView txt1=(TextView) v.findViewById(R.id.textView1);
        final CheckBox chkbox=(CheckBox) v.findViewById(R.id.checkBox1);

        txt1.setText(items.get(position));
        int selectedindexitem=0;

        if(position==selected_position)
        {
            chkbox.setChecked(true);
        }
        else
        {
            chkbox.setChecked(false);
        }
        chkbox.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                if(chkbox.isChecked())
                {
                    array[pos]=true;
                    selected_position =  pos;
                }else{
                    array[pos]=false;
                }
            }
        }); 
        chkbox.setChecked(array[pos]);
         MainActivity.lv.setAdapter(new CustomAdapter(context,MainActivity.listitems));




        return v; 
    }

答案 4 :(得分:1)

易于维护您的选择。从模型中选择。

 class PropertyModel{
 String VAL= "SOME VALUE"
 boolean selected = false;

public String getVAL() {return VAL;}
public void setVAL(String VAL) {this.VAL = VAL;}
public boolean isSelected() {return selected;}
public void setSelected(boolean selected) {this.selected = selected;} 
}

准备你的观点:

  public class CheckBoxAdptr extends BaseAdapter{
  /*       
   ..........
  */

  public View getView(int position, View view, ViewGroup parent) {
    PropertyModel items = list.get(position);
    View row;
    if (view == null) {
        LayoutInflater inflater = (LayoutInflater) context
                .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        row = inflater.inflate(R.layout.list_item_checkbox, null);
    }
    else{row = view;}

    TextView T1 = (TextView) row.findViewById(R.id.list_item_1);
    CheckBox checkBox = (CheckBox) row.findViewById(R.id.list_item_check_box);

    T1.setText(""+items.getVAL());
    if(items.isSelected()){
        checkBox.setChecked(true);
    }
    else {checkBox.setChecked(false);}

    return row;
}
}

现在,在您的活动或片段中设置适配器并执行以下操作:

   final ArrayList<PropertyModel> list = getList();
    CheckBoxAdptr adpt = new CheckBoxAdptr(getActivity(), list);
    listview.setAdapter(adpt);

    listview.setOnItemClickListener(new AdapterView.OnItemClickListener() {
        @Override
        public void onItemClick(AdapterView<?> adapterView, View view, int position, long id) {
            for(int i = 0; i<list.size(); i++){
                if(i!=position){
                    list.get(i).setSelected(false);
                }
                else{
                    list.get(i).setSelected(true);
                }
            }
            adpt.notifyDataSetChanged();
        }
    });

请注意,您的所有工作都由adpt.notifyDataSetChanged()完成。希望这会有所帮助。

答案 5 :(得分:1)

使用 getView (与发布的大多数答案一样)对我来说无法正常工作。它没有足够的响应。有时它会取消选中上一个复选框,有时不会。

这对我很有用:

首先,我们需要存储所有先前检查过的复选框的位置:

Set<Integer> selectedPreviousPositions = new HashSet<>();

然后在onItemClick侦听器中,我们取消选中所有复选框,然后再选中我们选中的那个。

    @Override
    public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
        boolean isChecked = ((CheckBox) view.findViewById(R.id.cbSelected)).isChecked();
        if (!isChecked) {
             final ListView listDevices = (ListView) findViewById(R.id.lvDevices);
             for (Integer pos : selectedPreviousPositions ) {
                 View pView = listDevices.getChildAt(pos);
                 if (pView != null) { // unnecessary but we never know !
                     ((CheckBox)pView.findViewById(R.id.checkboxID)).setChecked(false);
                 }
             }
            selectedUniquePositions.add(new Integer(position));
            // Now we can check the selected checkbox
            ((CheckBox) view.findViewById(R.id.cbSelected)).setChecked(true);
        } else {
            ((CheckBox) view.findViewById(R.id.cbSelected)).setChecked(false);
            selectedPreviousPositions.remove(new Integer(position));

        }
    }

答案 6 :(得分:0)

在适配器内部,为复选框设置OnClickListener()。每当单击复选框时,都存储单击的复选框位置并调用notifyDataSetChanged()。对于列表视图中的所有视图,将再次使用getView()方法。每当调用getView()时,都将选中先前存储的位置的复选框,然后取消选中其余复选框。

public class CustomAdapter extends ArrayAdapter<YourModelObject>
{
    private int selectedCheckBoxPosition = -1;

    public int getSelectedCheckBoxPosition() 
    {
        return selectedCheckBoxPosition;
    }

    @Override
    public View getView(final int position, View convertView, final ViewGroup parent) 
    {
        final ViewHolder viewHolder;

        LayoutInflater layoutInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

        if (convertView == null) 
        {
            convertView = layoutInflater.inflate(R.layout.list_item, null);
            viewHolder = new ViewHolder();
            viewHolder.checkBox = (CheckBox) convertView;
            convertView.setTag(viewHolder);
        } 
        else 
        {
            viewHolder = (ViewHolder) convertView.getTag();
        }

        if (position == selectedCheckBoxPosition)
        {
            viewHolder.checkBox.setChecked(true);
            Log.d(TAG, "checkbox CHECKED at pos: " + position);
        }
        else 
        {
            viewHolder.checkBox.setChecked(false);
            Log.d(TAG, "checkbox UNCHECKED at pos: " + position);
        }

        //viewHolder.checkBox.setText("sample text");

        viewHolder.checkBox.setOnClickListener(new View.OnClickListener() 
        {
            @Override
            public void onClick(View view) {
                selectedCheckBoxPosition = position;
                Log.d(TAG, "onClick() - set selectedCheckBoxPosition = " + position);
                notifyDataSetChanged();
            }
        });
        return convertView;
    }

    private class ViewHolder 
    {
        CheckBox checkBox;
    }
}
相关问题