【发布时间】:2013-10-29 10:58:51
【问题描述】:
我已经上网 2 天了,尝试了很多东西,但似乎无法弄清楚这有什么问题。
我对 Android 开发还很陌生,所以我可能错过了一些明显的东西。
我有一个应用程序女巫正在使用 sqllite 数据库来存储一些数据,并为此在列表视图中显示该概念证明。我可以将项目添加到列表中,也可以删除它们。
到目前为止一切顺利。我遇到的问题是,当我没有删除更新数据库中名为“已删除”的列并将其设置为 1,然后让适配器更新列表时。好像不行。
如果我使用 delete 语句,它会起作用。它会更新,一切都很好,但我想在数据库中保存已删除的项目但不显示它们(所以基本上“隐藏”项目)
如果我检查数据库,更新本身成功了列更改和所有内容,所以我猜这是一个刷新问题,因为适配器不会重新查询数据库或那个方向的东西
列表视图加载器:
public void fillData() {
if(lw.getAdapter() == null){
// Fields from the database (projection)
// Must include the _id column for the adapter to work
String[] from = new String[] { TodoTable.COLUMN_SUMMARY, TodoTable.COLUMN_ID};
String where = TodoTable.COLUMN_DELETED + " = ?";
Cursor cursor = getContentResolver().query(TodoContentProvider.CONTENT_URI,from,where,new String[] {"0"},null);
// Fields on the UI to which we map
int[] to = new int[] { R.id.label };
adapter = new SimpleCursorAdapter(this, R.layout.todo_row, cursor, from,
to, 0);
Log.v("Count",Integer.toString(cursor.getCount()));
lw.setAdapter(adapter);
}
else
adapter.notifyDataSetChanged();
}
删除函数
@Override
public boolean onContextItemSelected(MenuItem item) {
switch (item.getItemId()) {
case DELETE_ID:
/* Code for actual delete
AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo) item
.getMenuInfo();
Uri uri = Uri.parse(TodoContentProvider.CONTENT_URI + "/"
+ info.id);
getContentResolver().delete(uri, null, null);
fillData();
*/
/* Code for update and hide */
AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo) item
.getMenuInfo();
Uri uri = Uri.parse(TodoContentProvider.CONTENT_URI + "/"
+ info.id);
ContentValues values = new ContentValues();
values.put(TodoTable.COLUMN_DIRTY, 1);
values.put(TodoTable.COLUMN_DELETED, 1);
getContentResolver().update(uri,values,null,null);
fillData();
return true;
}
return super.onContextItemSelected(item);
}
如果我将日志放到 ContentProvider 的查询函数中,它实际上不会触发。
关于如何解决这个问题的任何建议?
如果我使用adapter.swapCursor(cursor);,它可以正常工作,只是不知道这是否是正确的做法。
public void fillData() {
// Fields from the database (projection)
// Must include the _id column for the adapter to work
String[] from = new String[] { TodoTable.COLUMN_SUMMARY, TodoTable.COLUMN_ID};
String where = TodoTable.COLUMN_DELETED + " = ?";
Cursor cursor = getContentResolver().query(TodoContentProvider.CONTENT_URI,from,where,new String[] {"0"},null);
// Fields on the UI to which we map
int[] to = new int[] { R.id.label };
if(lw.getAdapter() == null){
adapter = new SimpleCursorAdapter(this, R.layout.todo_row, cursor, from,
to, 0);
Log.v("Count",Integer.toString(cursor.getCount()));
lw.setAdapter(adapter);
}
else
{
adapter.swapCursor(cursor);
}
}
求帮助
【问题讨论】:
-
如果您使用表现良好的 ContentProvider 和 CursorLoader,则无需调用 notifyDataSetChanged() fillData() 等,请参阅记事本 ContentProvider
-
在这里使用 restartLoader() 并不正确。您需要做的是让您的内容提供者在光标返回之前正确调用 setNotificationUri() 。从那时起,每次更新、删除、插入调用 getContext().getContentResolver().notifyChange() 以获取相同的 uri。即使您在内容提供者之外修改数据,调用 notifyChange() 也应该使用该通知 uri 通知所有游标并触发新的游标加载。
标签: android sqlite listview android-listview adapter