BaseAdapter完美實現ListView中checkbox全選,取消,多選功能

  很多時候我們需要在ListView中放置checkbox控件,這時候我們可能會想到用simpleAdapter,但是simpleAdapter的getChildAt()方法有個問題:當listview的數目很多時,listview需要滾動,這時候第一個選中的,最後一個也會一起選中。這是由於getChildAt()只能獲取當前可視的區域的ViewGroup。因此,我們需要使用自定義的BaseAdapter.

  BaseAdapter上一篇博客已經介紹過了,而這篇着重在於如何在BaseAdapter中實現完美的checkbox的單選,多選,取消功能。


  首先有個問題我們需要注意一下:checkbox的點擊事件優先級高於listview,因此我們需要屏蔽掉checkbox的優先級,在XML文件中編寫代碼如下:

  android:focusable="false" //設置不獲取焦點

  android:clickable="false"//設置不可點擊

  其次,我們需要將每個checkbox的點擊狀態保存起來,這裏使用isSelected這個HashMap<Integer,Boolean>對象來存儲相應位置處的checkbox的狀態.

  先來看看實際的運行圖:

以下爲程序Activity的代碼:

public class MainActivity extends Activity {
	private List<Map<String,Object>> listItems;
	private ListView listView;
	private String[] header={"姓名","性別","電話","住址","姓名","性別","電話","住址"};
	private String[] content={"張三","男","18850201111","中南海","張三","男","18850201111","中南海"};
	private MyBaseAdapter adapter;
	private Button allselect_bn;
	private Button allcancel_bn;
	private static HashMap<Integer, Boolean> isSelected=new HashMap<Integer, Boolean>();
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		listItems=new ArrayList<Map<String,Object>>();	
		listItems=getListItems();
		listView=(ListView) findViewById(R.id.listview);
		allselect_bn=(Button)findViewById(R.id.allselect_bn);
		allcancel_bn=(Button)findViewById(R.id.allcancel_bn);
		allselect_bn.setOnClickListener(new AllSelectListener());
		allcancel_bn.setOnClickListener(new AllCancelListener());
		adapter=new MyBaseAdapter(this);
		adapter.setIsSelected(isSelected);//設置isSelected map對象
		//初始化isSelected
		for(int i=0;i<header.length;i++){
			adapter.getIsSelected().put(i, true);
			System.out.println(adapter.getIsSelected().get(i));
			};
		listView.setAdapter(adapter);		
		listView.setOnItemClickListener(new OnItemClickListener() {

			@Override
			public void onItemClick(AdapterView<?> parent, View view,
					int position, long id) {
				
				ViewHolder holder=(ViewHolder)view.getTag();
				holder.checkbox.toggle();
				System.out.println("第幾條item"+position+"狀態"+holder.checkbox.isChecked());
				adapter.getIsSelected().put(position, holder.checkbox.isChecked());
				
			}
			
		});
	}
	
	public class AllSelectListener implements OnClickListener{

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			for(int i=0;i<header.length;i++){
				adapter.getIsSelected().put(i, true);
				
			}
			adapter.notifyDataSetChanged();
			
		}

		
	}
	public class AllCancelListener implements OnClickListener{

		@Override
		public void onClick(View v) {
			// TODO Auto-generated method stub
			for(int i=0;i<header.length;i++){
				adapter.getIsSelected().put(i, false);			
			}
			adapter.notifyDataSetChanged();
			
		}
	}
	 private List<Map<String, Object>> getListItems()
	    {
	        List<Map<String, Object>> list = new ArrayList<Map<String, Object>>();
	        Map<String, Object> map;
	        for(int i=0;i<header.length;i++)
	        {
	            map = new HashMap<String, Object>();	            
	            map.put("header", header[i]);
	            map.put("content", content[i]);
	            list.add(map);
	        }
	        return list;
	    }
	    public static class ViewHolder
	    {
	       
	        public TextView title;
	        public TextView info;
	        public CheckBox checkbox;
	        
	    }
	    
	    
	    
	    public class MyBaseAdapter extends BaseAdapter {
	    	private LayoutInflater inflater;
	    	private HashMap<Integer, Boolean> isSelected;
	    	
	    	
	    	/**************構造方法獲取上下文********************************/
	    	private MyBaseAdapter(Context context){
	    		this.inflater=LayoutInflater.from(context);
	    		
	    	}
	    	
	    	@Override
	    	public int getCount() {
	    		// TODO Auto-generated method stub
	    		return listItems.size();
	    	}

	    	@Override
	    	public Object getItem(int position) {
	    		// TODO Auto-generated method stub
	    		return listItems.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
	    		ViewHolder holder=null;
	    		if(convertView==null){
	    			holder=new ViewHolder();
	    			convertView=inflater.inflate(R.layout.task_item, null);
	    			holder.title=(TextView) convertView.findViewById(R.id.nameheader);
	    			holder.info=(TextView) convertView.findViewById(R.id.content);
	    			holder.checkbox=(CheckBox) convertView.findViewById(R.id.checkbox);
	    			convertView.setTag(holder);
	    		}
	    		else
	    			holder=(ViewHolder) convertView.getTag();
	    		/*********以下設置控件顯示內容***********/
	    			holder.title.setText((String) listItems.get(position).get("header"));
	    			holder.info.setText((String) listItems.get(position).get("content"));
	    			System.out.println("getlistview"+getIsSelected().get(position));
	    			holder.checkbox.setChecked(getIsSelected().get(position));//根據checkbox是否被選擇設置勾選
	    			//get(position)可以獲取當前position的checkbox map裏對應的布爾變量
	    		return convertView;
	    	}
	    	public  HashMap<Integer,Boolean> getIsSelected(){
	  			return isSelected;
	          	
	          }
	    	public  void setIsSelected(HashMap<Integer, Boolean> isSelected){
	    	this.isSelected=isSelected;
	    	
	    	}
	    }

}


以下爲XML佈局文件的代碼:

1.activity_main.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical"
     >

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/hello_world" />
    <ListView        
        android:id="@+id/listview"
        android:layout_width="fill_parent"
        
        android:layout_height="200dp"></ListView>
    <Button 
        android:id="@+id/allselect_bn"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="全選"/>
    <Button 
        android:id="@+id/allcancel_bn"
       	android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="取消" />

</LinearLayout>

2.task_item.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="horizontal" 
    >
<TextView android:id="@+id/nameheader"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:gravity="center_vertical"
    android:layout_marginLeft="10dp"
    android:textSize="15dp"
    android:textColor="#000000"
    android:layout_weight="1"
    />
<TextView android:id="@+id/content"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:gravity="center_vertical"
    android:layout_marginLeft="50dp"
    android:textSize="15dp"
    android:textColor="#000000"
    android:layout_weight="1"
    />
<CheckBox 
    android:id="@+id/checkbox"
	android:layout_width="wrap_content"
	android:layout_height="wrap_content"
	android:focusable="false"
	android:clickable="false"
	
	></CheckBox>



</LinearLayout>




 



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章