2014-01-06 91 views
1

我有一個包含在每一行有一個複選框一個TextView列表視圖,所以當複選框被選中,我們通過列表視圖的複選框實例會從一個地方帶到另一個(向下滾動重複使用..)和我有幾個選中的複選框如何解決,我想的複選框列表視圖綁定,但沒有工作,我的代碼是:如何將複選框綁定到ListView

SimpleCursorAdapter adapter =new SimpleCursorAdapter(this,R.layout.rating,cu,new String[]{"Title","Favorites"}, new int[]{R.id.text1,R.id.bt_rating},CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER); 
     listv.setAdapter(adapter); 

     adapter.setViewBinder(new SimpleCursorAdapter.ViewBinder(){ 
       /** Binds the Cursor column defined by the specified index to the specified view */ 
       public boolean setViewValue(View view, Cursor cursor, int columnIndex){ 
        if(view.getId() == R.id.bt_rating){ 

         ((CheckBox)view).setChecked(Boolean.valueOf(cursor.getString(cursor.getColumnIndex("Favorites")))); 
         ((CheckBox)view).setOnCheckedChangeListener(myCheckChangList); 
         return true; //true because the data was bound to the view 
        } 
        return false; 
       } 
      }); 


OnCheckedChangeListener myCheckChangList = new OnCheckedChangeListener() { 
      public void onCheckedChanged(CompoundButton buttonView, 
        boolean isChecked) { 
       buttonView.setChecked(isChecked); 
      } 
     }; 

我的行的內容的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" > 

    <CheckBox 
android:id="@+id/bt_rating" 
android:focusable="false" 
android:layout_width="wrap_content" 
android:layout_height="wrap_content" 
android:layout_gravity="center_vertical" 
android:button="@android:drawable/btn_star"/> 

<TextView 

android:id="@+id/text1" 
android:layout_width="fill_parent" 
android:layout_height="wrap_content" 
android:textSize="@dimen/fsinlistview" 

/> 
</LinearLayout> 
+1

http://www.vogella.com/tutorials/AndroidListView/article.html#listviewselection –

+0

沒有找到我需要在那裏悲傷...將繼續我的搜索..謝謝反正.. –

回答

0

它看起來像你的OnCheckedChangedListener是這裏的問題。如果你看一下你的代碼,看到複選框越來越向相同偵聽器的引用。因此,當您選中一個框時,您也將所有其他框設置爲選中狀態 - 而且您還沒有更新您的備份數據。

OnCheckedChangedListener不應該更新複選框的視圖狀態 - 回調解僱了,因爲國家已經改變了。

所以,你需要做以下步驟當用戶檢查複選框:

  1. 找出哪些項目進行檢查,如何對應於您的數據
  2. 更新您的數據,以適應新的檢查/未選中狀態
  3. 通知您的數據變化的適配器/更新你的光標

你能做到這一點類似於下面的東西,標記的看法與它重新行的ID介紹:

public boolean setViewValue(View view, Cursor cursor, int columnIndex){ 
    if(view.getId() == R.id.bt_rating){ 
     view.setTag(cursor.getInt(cursor.getColumnIndex(SomeDBContract.ID))); 
     ((CheckBox)view).setChecked(Boolean.valueOf(cursor.getString(cursor.getColumnIndex("Favorites")))); 
     ((CheckBox)view).setOnCheckedChangeListener(myCheckChangList); 
     return true; //true because the data was bound to the view 
    } 
    return false; 
} 

然後,在你的聽衆,你可以更新你的數據庫根據該ID:

CheckedChangeListener myCheckChangList = new OnCheckedChangeListener() { 
     public void onCheckedChanged(CompoundButton buttonView, 
       boolean isChecked) { 
      int rowId = (int) buttonView.getTag(); 
      // Handle updating the database as per normal 
      updateSomeDbRowAsChecked(rowId, isChecked); 
     } 
    }; 

最後,你需要有一個新的光標,一旦數據庫行來更新你的光標適配器更新:

myAdapter.swapCursor(newCursor); 

你必須調整這一切,以滿足您的代碼,但它應該給你的,你可以解決這個問題的一種方式的想法。

+0

好的將修復,但也我的視窗沒有被調用,因爲我把它放在一個log.d,它不被調用.. –

+0

也剛剛添加的監聽器的內容直接檢查結果,我需要做的是將更改添加到我的數據庫;但爲什麼沒有被調用? –

+0

我不確定,對不起 - 設置視圖聯編程序的代碼看起來是正確的。 –

0

在任何列表視圖,該視圖被重用。在您滾動瀏覽列表時,上下滾動的屏幕會回收並在下面顯示的新信息中使用。

你需要跟蹤你的複選框用一個稀疏數組。當用戶觸及每個數組時,將數組中的索引標記爲「已/未選中」。然後根據數組中的值設置複選框的狀態。

這是從一箇舊的應用程序的一些示例代碼,但這既是一個「全選」複選框,以及管理這些檢查,未經檢查的完整列表。這是我寫的一個教室出勤應用程序,因此老師選擇課堂上的「全部」,然後取消選擇那些不存在的東西要容易得多。

我在這個列表視圖兩個複選框,和兩個稀疏數組,itemCheckedHere和itemCheckedLate(學生是否上課,還是遲到了)。

public class MyDataAdapter extends SimpleCursorAdapter { 
    private Cursor c; 
    private Context context; 
    private Long classnum; 
    private gradeBookDbAdapter mDbHelper; 

    public static final int LATE=2; 
    public static final int ATTEND=1; 
    int idxCol; 
    int idx; 

    // itemChecked will store the position of the checked items. 

    public MyDataAdapter(Context context, int layout, Cursor c, String[] from, 
      int[] to, Long mRowId) { 
     super(context, layout, c, from, to); 
     this.c = c; 
     this.context = context; 
     mDbHelper = new gradeBookDbAdapter(context); 
     mDbHelper.open(); 
     classnum = mRowId; 
     c.moveToFirst(); 



    } 
    public class ViewHolder{ 
     public TextView text; 
     public TextView text2; 
     public ImageView image; 
     public CheckBox here; 
     public CheckBox late; 
    } 


    public View getView(final int pos, View inView, ViewGroup parent) { 
     Bitmap bm; 
     ImageView studentPhoto; 
     View vi=inView; 
     final ViewHolder holder; 

     if (inView == null) { 
      LayoutInflater inflater = (LayoutInflater) context 
        .getSystemService(Context.LAYOUT_INFLATER_SERVICE); 
      vi = inflater.inflate(R.layout.show_attendance, null); 

      holder=new ViewHolder(); 
      holder.text=(TextView)vi.findViewById(R.id.stuname); 
      holder.text2=(TextView)vi.findViewById(R.id.stuIndex); 
      holder.image=(ImageView)vi.findViewById(R.id.icon); 
      holder.here=(CheckBox)vi.findViewById(R.id.attend); 
      holder.late=(CheckBox)vi.findViewById(R.id.late); 
      vi.setTag(holder); 

     } 
     else 
      holder=(ViewHolder)vi.getTag(); 


     c.moveToPosition(pos); 
     int index = c.getColumnIndex(gradeBookDbAdapter.KEY_NAME); 
     String name = c.getString(index); 
     holder.text.setText(name); 
     index = c.getColumnIndex(gradeBookDbAdapter.KEY_ROWID); 
     String Index = c.getString(index); 
     holder.text2.setText(Index); 

     bm = gradeBookDbAdapter.getStudentPhoto(name); 
     if (bm != null) { 
      holder.image.setImageBitmap(bm); 
     }   
     else { 
      // use icon image 
      holder.image.setImageResource(R.drawable.person_icon); 
     } 


     // pull out existing attend/late fields and set accordingly 
     int attend = c.getInt(c.getColumnIndex(gradeBookDbAdapter.KEY_ATTEND)); 
     if(attend==1){ 
      holder.here.setChecked(true); 
      itemCheckedHere.set(pos, true); 
     } 
     //else { 
     // holder.here.setChecked(false); 
     // itemCheckedHere.set(pos, false); 
     //} 

     int late = c.getInt(c.getColumnIndex(gradeBookDbAdapter.KEY_LATE)); 
     if (late==1){ 
      holder.late.setChecked(true); 
      itemCheckedLate.set(pos, true); 
     } 
     //else { 
     // holder.late.setChecked(false); 
     // itemCheckedLate.set(pos, false); 
     //} 


     if (selectAllTouched) { 
      if(selectAll){ 
       holder.here.setChecked(true); 
       itemCheckedHere.set(pos, true); 
       int who= new Integer(holder.text2.getText().toString()); 
       mDbHelper.updateAttend(who, classnum, ATTEND, 1, attendDate); 
      } 
      else{ 
       holder.here.setChecked(false); 
       itemCheckedHere.set(pos, false); 
       int who = new Integer(holder.text2.getText().toString()); 
       mDbHelper.updateAttend(who, classnum, ATTEND, 0, attendDate); 
      } 
     } 


     holder.here.setOnClickListener(new OnClickListener() { 

      public void onClick(View v) { 

       CheckBox cb = (CheckBox) v.findViewById(R.id.attend); 

       if (cb.isChecked()) { 
        itemCheckedHere.set(pos, true); 
        int Index = new Integer(holder.text2.getText().toString()); 
        mDbHelper.updateAttend(Index, classnum, ATTEND, 1, attendDate); 
       } else if (!cb.isChecked()) { 
        itemCheckedHere.set(pos, false); 
        int Index = new Integer(holder.text2.getText().toString()); 
        mDbHelper.updateAttend(Index, classnum, ATTEND, 0, attendDate); 
       } 
      } 
     }); 
     holder.late.setOnClickListener(new OnClickListener() { 

      public void onClick(View v) { 
       CheckBox cb = (CheckBox) v.findViewById(R.id.late); 

       if (cb.isChecked()) { 
        itemCheckedLate.set(pos, true); 
        int Index = new Integer(holder.text2.getText().toString()); 
        mDbHelper.updateAttend(Index, classnum, LATE, 1, attendDate); 
       } else if (!cb.isChecked()) { 
        itemCheckedLate.set(pos, false); 
        int Index = new Integer(holder.text2.getText().toString()); 
        mDbHelper.updateAttend(Index, classnum, LATE, 0, attendDate); 
       } 
      } 
     }); 


     holder.here.setChecked(itemCheckedHere.get(pos)); // this will Check or Uncheck the 
     holder.late.setChecked(itemCheckedLate.get(pos)); // this will Check or Uncheck the 
     // CheckBox in ListView 
     // according to their original 
     // position and CheckBox never 
     // loss his State when you 
     // Scroll the List Items. 

     return vi; 
    } 

} 

}

+0

非常感謝你馬丁,但這個代碼是不同的,我會看到它,如果我用完解決方案:) –

+0

是的,它不同於你的。我的目的不是爲你寫代碼,而是提供一個如何在列表視圖中處理複選框的例子。如果您正在尋找即插即用的代碼,那麼您可以簡單地將其放入您的項目中,我需要首先向您提供我的貝寶賬戶,您可以通過這些賬戶向我支付我的費用。 – Martin