Reputation: 2150
I'm still not getting exactly how a custom CursorAdapter
should work, so after hard tries, here is the thing :
getView()
.CursorAdapter
, that I re-assign itself to the ListView
.CursorAdapter
class in the ListView
method, and I don't know how to update my adapter from the inside.For people who don't want to read my boring explanations, here is the code of the getView
:
@Override
public View getView(int position, View convertView, ViewGroup parent){
convertViewParam = convertView;
ViewHolder viewHolder = new ViewHolder();
if (convertViewParam == null) {
int type = getItemViewType(position);
switch (type) {
case TYPE_ADD_NOTE_TOP:
convertViewParam = inflater.inflate(R.layout.add_note_top, null);
viewHolder.contentNote = (EditText)convertViewParam.findViewById(R.id.add_note_top_id);
break;
case TYPE_ITEM:
convertViewParam = inflater.inflate(R.layout.row_note, null);
viewHolder.delete = (Button)convertViewParam.findViewById(R.id.delete);
if (deleteMode){
viewHolder.delete.setVisibility(View.VISIBLE);
}else{
viewHolder.delete.setVisibility(View.GONE);
}
viewHolder.contentNote = (TextView)convertViewParam.findViewById(R.id.note);
getCursor().moveToPosition(position - 1);
int currentPosition = getCursor().getPosition();
Cursor c = getCursor();
c.moveToPosition(currentPosition);
((TextView) viewHolder.contentNote).setText(c.getString(c.getColumnIndex("content_note")));
int rowId = c.getInt(c.getColumnIndex("_id"));
viewHolder.delete.setTag(new Integer(rowId));
viewHolder.contentNote.setTag(new Integer(rowId));
OnClickListener listener = new OnClickListener() {
@Override
public void onClick(View v) {
int thePosition = (Integer) v.getTag();
int posCurs = notesCursorAdapter.getCursor().getPosition();
NoteDataSource.getSingletonObject(context).deleteNote(thePosition, context);
notesCursorAdapter.changeCursor(NoteDataSource.getSingletonObject(context).getAllNotes());
notesCursorAdapter.notifyDataSetChanged();
}
};
viewHolder.delete.setOnClickListener(listener);
break;
case TYPE_ADD_NOTE_BOTTOM:
convertViewParam = inflater.inflate(R.layout.add_note_bottom, null);
LinearLayout linearLayout = (LinearLayout)convertViewParam.findViewById(R.id.bottomLayout);
linearLayout.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
}
});
break;
}
convertViewParam.setTag(viewHolder);
} else {
viewHolder = (ViewHolder)convertViewParam.getTag();
if (viewHolder.contentNote!=null){
if (viewHolder.contentNote.getTag() == convertViewParam.findViewById(R.id.note)){
int test = (Integer) viewHolder.delete.getTag();
System.out.println("current tag " + test);
String txt = getCursor().getString(getCursor().getColumnIndex("content_note"));
((TextView) viewHolder.contentNote).setText(txt);
}
}
}
return convertViewParam;
}
I get the following error when I launch the delete event:
03-28 17:51:32.996: E/AndroidRuntime(7115): android.database.CursorIndexOutOfBoundsException: Index 2 requested, with a size of 2
If you want more info ask.
I'm looking for a bug fix or an just explanation, thanks.
Upvotes: 0
Views: 1544
Reputation: 87064
It would help to know on which line you get the exception. First of all one bad thing is that you delete a note from the database based on a position int
and after that you fetch again all the data and move the position on that cursor on the previous deleted position.
If you have 3 notes(and you show them in the list) in the database and you want to delete the last one this will happen:
thePosition
will be 2
thePosition
(value 2)If you want to delete a note then pass as a tag the _id
for that row and use that to delete the note:
Cursor c = getCursor();
c.moveToPosition(position);
long rowId = c.getLong(c.getColumnIndex("_id"));
viewHolder.delete.setTag(new Long(rowId));
Then in the onClick()
method use that to delete the note and stop messing with the moveToPosition()
on the cursor.
Upvotes: 1
Reputation: 13552
Thats a very well written problem statement. I have had this problem and broke my head over it. Try this.
public interface ItemDeletedListener(){ public void itemDeleted(int position); }
create an instance of ItemDeletedListener in your adapter, m_listener.
Write a setter function, setItemDeletedListener( ItemDeletedListener listener){}
In your getView(), onClickListener, call m_listener and pass the position that needs to be deleted.
Now in your Activity, Do the following.
Upvotes: 2