安卓:SimpleCursorAdapter使用 [英] Android: SimpleCursorAdapter usage

查看:219
本文介绍了安卓:SimpleCursorAdapter使用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个恼人的问题与SimpleCursorAdapter。我PROGRAMM拥有列表视图和ListActivity。每一行都有自己的布局:

I have ONE annoying problem with SimpleCursorAdapter. My programm has list view and ListActivity. Each row has it's own layout:

<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content" android:layout_width="fill_parent"
android:orientation="horizontal" android:weightSum="1.0">
<TableRow>
    <TextView android:id="@+id/task_time"
        android:layout_width="wrap_content" android:layout_height="wrap_content"
        android:textSize="24sp" android:text="Time">
    </TextView>
    <LinearLayout android:orientation="vertical"
        android:layout_width="wrap_content"
        android:layout_height="fill_parent">
        <TextView android:id="@+id/task_name"
            android:layout_width="wrap_content" android:layout_height="wrap_content"
            android:textSize="20sp" android:text="Name">
        </TextView>
        <TextView android:id="@+id/task_categoty"
            android:layout_width="wrap_content" android:layout_height="wrap_content"
            android:text="Category" android:textSize="12sp">
        </TextView>
    </LinearLayout>
    <TextView android:id="@+id/task_state"
        android:layout_width="wrap_content" android:layout_height="wrap_content"
        android:text="State" android:textSize="12sp">
    </TextView>
    <CheckBox android:id="@+id/task_enabled"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" android:focusable="false">
    </CheckBox>

</TableRow>

任务都存储在SQLite数据库。我有DAO对象(单身)来访问数据库。 TaskDao:

Tasks are stored in SQLite database. I have DAO object (singleton) to access the database. TaskDao:

    public void updateEnabled(int id, boolean enabled){
    SQLiteDatabase db = dbHelper.getWritableDatabase();
    ContentValues cv = new ContentValues();
    cv.put(ENABLED_COLUMN, enabled==true?1:0);
    Log.i(TAG, "update to " + cv.get(ENABLED_COLUMN) );
    try{
        db.beginTransaction();
        db.update(TASK_TABLE, cv, ID_COLUMN+"=?", new String[]{id+""});
        db.setTransactionSuccessful();
    } catch (SQLException e) {
        Log.i(TAG, "edit task failed!");
    } finally {
        db.endTransaction();
        if (db != null)
            db.close();
    }
}

和光标的方法L​​istActivity:

and the Cursor method for ListActivity:

    public Cursor getTasks(){
    SQLiteDatabase db = dbHelper.getReadableDatabase();
    return db.query(TASK_TABLE, COLUMNS, null, null, null, null, NAME_COLUMN);
}

我伸出SimpleCursorAdapter(TaskDbAdapter)是这样的:

I extended SimpleCursorAdapter (TaskDbAdapter) like this:

    @Override
public View getView(int position, View convertView, ViewGroup parent) {
    if(convertView==null){
        convertView = inflater.inflate(R.layout.task_list_row, null);
    }
    Cursor c = getCursor();
    c.moveToPosition(position);
    Log.i(TAG, "getView " + position + " = " + c.getInt(enabledIdx));
    enabled.setTag(c.getInt(c.getColumnIndex(BaseColumns._ID)));
    enabled.setChecked(c.getInt(enabledIdx)>0?true:false);
    enabled.setOnClickListener(this);
    return convertView;
}
@Override
public void onClick(View v) {
    CheckBox box = (CheckBox) v;
    Integer id = (Integer)box.getTag();
    TaskDao.getInstance(context).updateEnabled(id.intValue(), box.isChecked());
}

,最后我用上述所有的东西在我的主ListActivity

And at last I use all the above stuff in my main ListActivity

    private void refreshList(){
    c = TaskDao.getInstance(this).getTasks();
    startManagingCursor(c);
    adapter = new TaskDbAdapter(this, R.layout.task_list_row, c, new String[]{TaskDao.ENABLED_COLUMN}, new int[]{R.id.task_enabled});
    setListAdapter(adapter);
}
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.task);
    getListView().setItemsCanFocus(false);
    getListView().setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
    getListView().setVerticalScrollBarEnabled(true);
    registerForContextMenu(getListView());
    getListView().setOnCreateContextMenuListener(this);
    refreshList();
}


@Override
protected void onResume() {
    super.onResume();
    refreshList();
}
@Override
protected void onPause() {
    super.onPause();

}

一切工作正常。但复选框失去它们的状态。比如我检查我的第一列滚动列表了。在我之前,preSS跟踪我有:

Everything works fine. But CheckBoxes loose their states. For instance I check my first column and scroll the list down. In my trace before press I have:

getView 0 = 0
getView 2 = 0
getView 3 = 0

然后

uptate to 1

,然后(当我向上滚动到第一个元素)

and then (when I scroll up to the first element)

getView 0 = 0
getView 2 = 0
getView 3 = 0

我试图让 getCursor()重新查询(); 在我TaskDbAdapter的onClick方法。但后来我看到在列表中没有的项目!例外,因为游标的管理和(连接被关闭机器人)。当我写的 startManagingCursor(C); 在refreshList()方法,然后检查并取消方法不起作用。 请帮助!

I tried to make getCursor().requery(); in my TaskDbAdapter onClick method. But then I saw no items in the list! And exception because of cursor management(connection was closed by android). When I write startManagingCursor(c); in refreshList() method then check and uncheck methods don't work. Please, Help!

推荐答案

我有这个问题,以及挣扎。我结束了存储在数据库中的所有检查框为0或1。然后我检查自己的状态,从数据库,以确定他们是否被标记与否。

I struggled with this as well. I ended up storing all checked boxes in the db as either 0 or 1. Then I check their state from the database to determine if they are marked or not.

公共类DetailCursorAdapter扩展SimpleCursorAdapter {

public class DetailCursorAdapter extends SimpleCursorAdapter {

private Cursor c;
private Context context;    

public DetailCursorAdapter(Context context, int layout, Cursor c,
        String[] from, int[] to) {
    super(context, layout, c, from, to);
    this.c = c;
        this.context = context;

}

public View getView(int pos, View inView, ViewGroup parent) {
    View v = inView;
    if (v == null) {
        LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        v = inflater.inflate(R.layout.check_list, null);
    }
    Log.i("pos = ..................", "pos = "+pos);
    this.c.moveToPosition(pos); 
    //this.c.moveToPosition(this.c.getInt(this.c.getColumnIndex("_id")));   
    CheckBox cBox = (CheckBox) v.findViewById(R.id.bcheck);
    cBox.setTag(this.c.getInt(this.c.getColumnIndex("_id")));

    /*
     * when reloading the list, check for chkd status, this is broken.  Need to query db directly.
     */
    EventDbAdapter mDbHelper = new EventDbAdapter(context);
    mDbHelper.open(); 

    int idTag = (Integer) cBox.getTag();                
    int checked = mDbHelper.selectChk(idTag);
    mDbHelper.close();
    Log.i("results from selectChk.....................", ""+checked);
    if (checked == 1) {
        cBox.setChecked(true);          
    } else {
        cBox.setChecked(false);
    }

    /*
     * Populate the list
     */     
    TextView txtdateTime = (TextView)v.findViewById(R.id.time);
    txtdateTime.setText(this.c.getString(this.c.getColumnIndex("time")));   
    TextView txtdateEvent = (TextView)v.findViewById(R.id.event);
    txtdateEvent.setText(this.c.getString(this.c.getColumnIndex("event")));
    TextView txtdateLocation = (TextView)v.findViewById(R.id.location);
    txtdateLocation.setText(this.c.getString(this.c.getColumnIndex("location")));
    ImageView arrow = (ImageView) v.findViewById(R.id.arrowId);
    arrow.setImageResource(R.drawable.rightarrow);


    Log.i("if chk in db is = 1 then set checked.........",this.c.getString(this.c.getColumnIndex("checked")) +" " +this.c.getString(this.c.getColumnIndex("time")));        


    /*
     * Controls action based on clicked list item (background)
     */
    View lv = v.getRootView(); 
    lv.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View lv) {
            CheckBox cBox = (CheckBox) lv.findViewById(R.id.bcheck);

            // id holds the rowid of each event.  pass this to a new activity to query for description

            // Call Event Detail
            String id = cBox.getTag().toString();
            Intent i = new Intent(context, EventDetail.class);
            //i.putExtra("description", c.getString(c.getColumnIndex("description")));
            i.putExtra("_id", id);
            context.startActivity(i);

        }

    });

    /*
     * Begin - Controls action based on clicked Text only

    txtdateEvent.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            // TODO Auto-generated method stub
            CharSequence charseq = "Darth Vader is alive";
            Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();
        }

    });

    * End - Controls action based on clicked Text only
    */


    /*
     * Controls action based on clicked checkbox 
     */
    cBox.setOnClickListener(new OnClickListener() {  
        @Override
        public void onClick(View v) {
            EventDbAdapter mDbHelper = new EventDbAdapter(context);
            mDbHelper.open(); 

            CheckBox cBox = (CheckBox) v.findViewById(R.id.bcheck);
            if (cBox.isChecked()) {
                //cBox.setChecked(false);
                CharSequence charseq = "Added to My Schedule";
                Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();

                // Update the database for each checked item
                mDbHelper.updateChecked(cBox.getTag().toString(), "1");     
                c.requery();

                // Verify that the db was updated for debugging purposes
                String event = c.getString(c.getColumnIndex("event"));                  
                int id = (Integer) cBox.getTag();

                Log.i("checked _id...........", "id= " + id + " " +c.getString(c.getColumnIndex("_id"))); 
                Log.i("checked checked...........", ""+c.getString(c.getColumnIndex("checked")));

            } else if (!cBox.isChecked()) {
                //cBox.setChecked(true);
                CharSequence charseq = "Removed from My Schedule";
                Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();
                // checkList.remove(cBox.getTag());
                //checkList.add((Integer) cBox.getTag());
                String event = c.getString(c.getColumnIndex("event"));
                //int id = c.getInt(c.getColumnIndex("_id"));
                int id = (Integer) cBox.getTag();
                mDbHelper.updateChecked(cBox.getTag().toString(), "0"); 
                c.requery();
                //int sqlresult = mDbHelper.selectChk(id, event);                   
                //Log.i("sqlresult checked value after update...........", ""+ sqlresult);                  
                //Log.i("unchecked _id...........", ""+c.getString(c.getColumnIndex("_id"))); 
                //Log.i("unchecked checked...........", ""+c.getString(c.getColumnIndex("checked")));
            }
            //mDbHelper.close();
        }
    });

    return(v);
}

}

这篇关于安卓:SimpleCursorAdapter使用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆