我使用AbsListView.MultiChoiceModeListener
选择一个或任何一个
并从ListView
(列表)和SQLite数据库中删除。 ListView
是
通常由其他活动的数据填充。通过如下代码
方法onActionItemClicked(ActionMode mode, MenuItem item)
仅删除
列表中的最后一项。如何从列表中选择和删除项目以及
此活动中的SQLite数据库和更新列表?
DatabaseHelper.class
public class DatabaseHelper extends SQLiteOpenHelper {
private static final String TABLE_NAME = "value_table";
private static final String COL1 = "ID";
private static final String COL2 = "name";
public DatabaseHelper(Context context/*, String name, SQLiteDatabase.CursorFactory factory, int version*/) {
super(context, TABLE_NAME, null, 1);
}
@Override
public void onCreate(SQLiteDatabase db) {
String createTable = "CREATE TABLE " + TABLE_NAME + " (ID INTEGER PRIMARY KEY AUTOINCREMENT, " +
COL2 +" TEXT)";
db.execSQL(createTable);
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP IF TABLE EXISTS " + TABLE_NAME);
onCreate(db);
}
public boolean addData(String item) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues contentValues = new ContentValues();
contentValues.put(COL2, item);
long result = db.insert(TABLE_NAME, null, contentValues);
//if date as inserted incorrectly it will return -1
if (result == -1) {
return false;
} else {
return true;
}
}
public Cursor getData(){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT * FROM " + TABLE_NAME;
Cursor data = db.rawQuery(query, null);
return data;
}
public Cursor getItemID(String name){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT " + COL1 + " FROM " + TABLE_NAME +
" WHERE " + COL2 + " = '" + name + "'";
Cursor data = db.rawQuery(query, null);
return data;
}
/**
* Updates the name field
* @param newName
* @param id
* @param oldName
*/
public void updateName(String newName, int id, String oldName){
SQLiteDatabase db = this.getWritableDatabase();
String query = "UPDATE " + TABLE_NAME + " SET " + COL2 +
" = '" + newName + "' WHERE " + COL1 + " = '" + id + "'" +
" AND " + COL2 + " = '" + oldName + "'";
db.execSQL(query);
}
/**
* Delete from database
* @param id
* @param name
*/
public void deleteName(int id, String name){
SQLiteDatabase db = this.getWritableDatabase();
String query = "DELETE FROM " + TABLE_NAME + " WHERE "
+ COL1 + " = '" + id + "'" +
" AND " + COL2 + " = '" + name + "'";
db.execSQL(query);
}
public void remove(int id){
SQLiteDatabase db = this.getWritableDatabase();
String query = "DELETE FROM " + TABLE_NAME + " WHERE "
+ COL1 + " = '" + id + "'";
db.execSQL( query);
}
}
ListDataActivity.class
public class ListDataActivity extends AppCompatActivity{
DatabaseHelper mDatabaseHelper;
private ListView mListView;
ArrayList<String> listData;
ArrayList<String> UserSelection = new ArrayList<>();
ArrayList<Integer> listDataSelect;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.list_layout);
mListView = (ListView) findViewById(R.id.listView);
mListView.setChoiceMode(AbsListView.CHOICE_MODE_MULTIPLE_MODAL);
mListView.setMultiChoiceModeListener(modeListener);
mDatabaseHelper = new DatabaseHelper(this);
populateListView();
}
private void populateListView() {
//get the data and append to a list
Cursor data = mDatabaseHelper.getData();
listData = new ArrayList<>();
while (data.moveToNext()) {
//get the value from the database in column 1
//then add it to the ArrayList
listData.add(data.getString(1));
}
//create the list adapter and set the adapter
ListAdapter adapter = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1, listData);
mListView.setAdapter(adapter);
}
private void toastMessage(String message){
Toast.makeText(this,message, Toast.LENGTH_SHORT).show();
}
AbsListView.MultiChoiceModeListener modeListener=new AbsListView.MultiChoiceModeListener() {
@Override
public void onItemCheckedStateChanged(ActionMode mode, int position, long id, boolean checked) {
if (UserSelection.contains(listData.get(position))) {
UserSelection.remove(listData.get(position));
} else {
UserSelection.add(listData.get(position));
}
mode.setTitle(UserSelection.size() + " items selected....");
String name=listData.get(position);
Cursor data = mDatabaseHelper.getItemID(name);
int itemID = -1;
while(data.moveToNext()){
itemID = data.getInt(0);
listDataSelect.add(itemID);
}
}
@Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
MenuInflater menuInflater=mode.getMenuInflater();
menuInflater.inflate(R.menu.menu_context,menu);
return true;
}
@Override
public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
return true;
}
@Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
switch (item.getItemId()){
case R.id.menu_delete:
for(int i=0; i<listDataSelect.size();i++){
mDatabaseHelper.remove(listDataSelect.get(i));
}
break;
}
return true;
}
@Override
public void onDestroyActionMode(ActionMode mode) {
}
};
}
答案 0 :(得分:0)
在onActionItemClicked(..)
中通过调用此行来查找:
mDatabaseHelper.remove(pos);
您只删除值为pos
的项目。您的代码中存在几个问题,尤其是分配项目ID(从listView填充的ID,而不是ID数据库)以及作为参数传递给remove()
全局变量。
让我澄清一下我的意思。从您的remove()
类的dbHelper
开始,它删除表id
等于传递的id
的行。问题是您传递了ListView item id
,以便如果用户有更多项目或已经进行了大量操作,则它将抛出异常或不会删除,因为您的数据库中没有这样的id
。 br />
综上所述,将参数传递给此方法所需要做的就是传递databaseId作为参数(您可以通过创建其他方法来获取此ID)。
第二,在您的onItemCheckedChanged()
中,您不能为全局变量分配新值。每次检查新项目时,变量都会更改。这就是为什么删除最后一项或随机删除一项(尽管不是随机)的原因。
好的,它看起来像是一长篇文章,包含很多理解,但是解决方案比您想象的要容易得多。
每次在onItemCheckedStateChanged()
中获取数据库行id
并将其传递到全局列表。当前,您传递了项目id
。然后在onActionItemClicked()
中运行remove()
类的循环调用方法Helper
,并将List中的项目作为参数传递。
就这样!
顺便说一句,BTW考虑使用RecyclerView而不是ListView-更好,更新。