How to remove an item from recyclerView after removing it from database - android

I am using a recyclerView to display a list of items that can be deleted when user clicks on delete button of each item. In order to do that, i've used a recyclerview adapter.
What i want: From that recycleView adapter, when user clicks on delete button for an item, a dialog fragment is shown and user has to enter a code when that code is valid then the item is removed from both the database and the recyclerView
What i've tried: After calling the show() method on the dialogFragment in the adapter, i'm calling removeItem(getPostion()).
What i get: When the dialog shows up, the item is removed from the recyclerView before the user enters the code but is still in the database
I 've tried other things but none of them worked.
Please help!!!
RecyclerView Adapter (EBAdapter)
public EBViewHolder(View itemView) {
super(itemView);
contact_row = (LinearLayout) itemView.findViewById(R.id.contact_row);
contact_row.setOnClickListener(this);
contact_photo = (ImageView) itemView.findViewById(R.id.contact_photo);
contact_photo.setOnClickListener(this);
contact_fullname = (TextView) itemView.findViewById(R.id.contact_fullname);
contact_relationship = (TextView) itemView.findViewById(R.id.contact_relationship);
contact_action = (ImageView) itemView.findViewById(R.id.contact_action);
contact_action.setOnClickListener(this);
contact_discard = (ImageView) itemView.findViewById(R.id.discard_action);
contact_discard.setOnClickListener(this);
}
#Override
public void onClick(View view){
//Handling recyclerView action clicked
String status;
if(view instanceof ImageView) {
if (view == contact_photo) {
Log.d("Contact", contact_photo.getId() + "photo " + getPosition() + "clicked");
ShowContactPhoto dialog = new ShowContactPhoto();
dialog.setStyle(DialogFragment.STYLE_NO_TITLE,0);
dialog.show(manager, "ScP_dialog");
}
if (view == contact_action) {
Log.d("Contact", contact_fullname.getText() + "action " + getPosition() + "clicked");
status = "active";
Date created_at = new Date();
Date updated_at = new Date();
AddInEmergencyBase dialog = new AddInEmergencyBase(((BitmapDrawable)contact_photo.getDrawable()).getBitmap(), contact_fullname.getText().toString(),contact_relationship.getText().toString(),status,created_at.toString(),updated_at.toString());
dialog.show(manager, "AiB_dialog");
Log.d("Contact", "Dialog Dismissed now");
}
//REGION OF INTEREST:
if (view == contact_discard) {
Log.d("Contact", contact_discard.getId() + "photo " + getPosition() + "clicked");
status = "inactive";
dialog = new DiscardEmergencyPers(contact_fullname.getText().toString(),status,mModels,getPosition(),rc);
position = getPosition();
dialog.show(manager, "DeP_dialog");
//dialog.getDialog().setOnDismissListener(this);
//onDismiss(dialog);
removeItem(getPosition());
Log.d("Contact", dialog.getDialog()+"item removed from data actually updated so hihihi....");
/*ShowContactPhoto dialog = new ShowContactPhoto();
dialog.setStyle(DialogFragment.STYLE_NO_TITLE, 0);
dialog.show(manager, "ScP_dialog");*/
}
}
else{
Log.d("Contact", contact_row.getId() + "row " + getPosition() + "clicked");
}
DialogFragment (DiscardEmergencyPers)
public class DiscardEmergencyPers extends DialogFragment implements View.OnClickListener, AdapterView.OnItemSelectedListener,DialogInterface.OnDismissListener, DialogInterface {
private final String fullname;
private final List<EmBaseInfo> mModels;
private final String status;
private final int position;
private final RecyclerView rc;
//private final String updated_at;
EditText pin_code;
Button cancel, done;
Communicator com;
private EmergenciaDBAdapter emergencia_helper;
private Context context;
private RecyclerView recycler_view;
public DiscardEmergencyPers(String fullname, String status,List<EmBaseInfo> mModels, int position, RecyclerView rc){
this.fullname=fullname;
this.status = status;
this.mModels = mModels;
this.position = position;
this.rc =rc;
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
com = (Communicator) activity;
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.dialog_discardemperson, null);
context = getActivity().getApplicationContext();
getDialog().setTitle("Remove emergency contact");
//Spinner that contains relationships with the current contact
pin_code = (EditText) view.findViewById(R.id.pin);
/*ArrayAdapter adapter = ArrayAdapter.createFromResource(context, R.array.relationship, android.R.layout.simple_spinner_dropdown_item);
relationship_spinner.setAdapter(adapter);
relationship_spinner.setOnItemSelectedListener(this);*/
//End of Spinner
//
emergencia_helper = new EmergenciaDBAdapter(context);
//spinner = (Spinner)view.findViewById(R.id.spinner);
cancel = (Button) view.findViewById(R.id.cancel);
done = (Button) view.findViewById(R.id.done);
cancel.setOnClickListener(this);
done.setOnClickListener(this);
setCancelable(false);
return view;
}
#Override
public void onClick(View view) {
if(view.getId()==R.id.cancel){
dismiss();
com.onDialogMessage("Cancel clicked");
}
else{
com.onDialogMessage("Done clicked");
if(pin_code.getEditableText().toString().equals("12345")){
dismiss();
emergencia_helper.update(status, fullname/*,updated_at*/);
//EBAdapter n_adapter = new EBAdapter(getActivity(),removeItem(this.position),getFragmentManager(),rc);
//rc.setAdapter(n_adapter);
//rc.getAdapter().(this.position);
rc.getAdapter().notifyDataSetChanged();
rc.getAdapter().notifyItemRemoved(0);
//Bundle savedInstanceState=null;
//getActivity().onCreate(savedInstanceState);
CharSequence text = "Good Pin "+rc.getAdapter();
Log.d("Contacts", rc.getClass()+"");
Log.d("Contacts", rc.getAdapter()+" "+getActivity());
int duration = Toast.LENGTH_SHORT;
Toast.makeText(context, text, duration).show();
}
else{
CharSequence text = "Wrong Pin";
//Log.d("Contacts", mModels.toString());
int duration = Toast.LENGTH_SHORT;
Toast.makeText(context, text, duration).show();
}
//long id=emergencia_helper.insert(photo,fullname,phone,relationship, status,created_at,updated_at);
/*if(id<0){
CharSequence text = "Row insertion unsuccessful ";
//Log.d("Contacts", mModels.toString());
int duration = Toast.LENGTH_SHORT;
Toast.makeText(context, text, duration).show();
}
else{
CharSequence text = "Row insertion successful ";
//Log.d("Contacts", mModels.toString());
int duration = Toast.LENGTH_SHORT;
Toast.makeText(context, text, duration).show();
}*/
}
}

Your code is quite complex!
But from what you want: delete item from db and recyclerview after user input right code. So, basically you can reach it by some steps:
Create listener for each recyclerview item (or button on item), when user click that -> open a dialog.
After user input the right code (you have to check if it right) then do two things:
-> Remove view from recyclerview via adapter:
dataSource.remove(index); // remember to remove it from your adapter data source
notifyItemRemoved(index);
-> Remove data from database (how to remove depend on your)
If the data was not removed from your db, please debug your delete function if was called, if it work, or any mistake!
Hope it help!

Related

How to delete item from ListView while using Custom ArrayAdapter w/ Dialog

Some Context: I have a Custom ArrayAdapter for a ListView that has 3 parameters Name, Edit Button, Delete Button. I have setup onClicks in the ArrayAdapter to be able to detect which profile is being clicked with the specific edit/delete button press. When the user deletes a profile I remove the profile from SQLite DB however now I've ran into the problem of trying to update the ArrayList with the removed item and notifyDataSetChanged for my ListView.
Question 1: I can't figure out if I should be doing this in the Class that is containing the ListView and ArrayList or if I should be trying to update this from the ArrayAdapter in the onClicks.
Question 2: Whatever method might be right how can I correctly update the deleted item from the ListView when the user confirms the delete in the Dialog.
Current ArrayAdapter Class
public class ListViewItemAdapter extends ArrayAdapter<ListViewItem>
{
private Context mContext;
private List<ListViewItem> list = new ArrayList<>();
private DatabaseHelper databaseHelper;
private String profileName;
public ListViewItemAdapter(#NonNull Context context, ArrayList<ListViewItem> listItem) {
super(context, 0 , listItem);
mContext = context;
list = listItem;
}
#NonNull
#Override
public View getView(int position, #Nullable View convertView, #NonNull ViewGroup parent) {
View listItem = convertView;
if(listItem == null)
listItem = LayoutInflater.from(mContext).inflate(R.layout.custom_listview,parent,false);
final ListViewItem listViewItem = list.get(position);
//Text View Profile
final TextView name = (TextView) listItem.findViewById(R.id.textView_name);
name.setText(listViewItem.getmName());
profileName = listViewItem.getmName();
//Edit Button Profile
ImageButton image = listItem.findViewById(R.id.imageView_poster);
image.setImageResource(listViewItem.getmImageDrawable());
image.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick(View v)
{
Toast.makeText(mContext,
"Edit Profile:" + listViewItem.getmProfile() + " Name:" + listViewItem.getmName(),
Toast.LENGTH_SHORT).show();
}
});
//Delete Button Profile **Currently Testing**
ImageButton image2 = listItem.findViewById(R.id.imageView_poster2);
image2.setImageResource(listViewItem.getmImageDrawable2());
image2.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick(View v)
{
databaseHelper = new DatabaseHelper(getContext());
Toast.makeText(mContext,
"Delete Profile:" + listViewItem.getmProfile() + " Name:" + listViewItem.getmName(),
Toast.LENGTH_SHORT).show();
AlertDialog.Builder builder = new AlertDialog.Builder(getContext(),R.style.AlertDialogTheme);
builder.setTitle("Delete Profile?")
.setMessage("Are you sure you want to delete\n" + listViewItem.getmName())
.setPositiveButton("yes", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
databaseHelper.deleteRowProfile(listViewItem.getmName());
//
//This is where I'm try to update the ListView
//
}
})
.setNegativeButton(android.R.string.no, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
}
})
.show();
}
});
return listItem;
}
}
Function in Fragment Class that Populates the ListView onViewCreated
public void getProfileList()
{
arrayList = new ArrayList<ListViewItemAdapter>();
listViewItemAdapter = new ListViewItemAdapter(getContext(),arrayList);
Cursor result = databaseHelper.getAllDataCarProfile();
if(listViewItemAdapter != null){
listViewItemAdapter.clear();
listViewItemAdapter.notifyDataSetChanged();
}
if (result.getCount() != 0)
{
while (result.moveToNext())
{
arrayList.add(new ListViewItem("CarProfile",
result.getString(0),
R.drawable.ic_edit_gray_24dp,
R.drawable.ic_delete_grey_24dp));
}
listViewItemAdapter.notifyDataSetChanged();
}
listViewCarProfile.setAdapter(listViewItemAdapter);
}
You can do this in either way . You can create a function in your adapter class and perform the clickListener on it .
deleteItem.setOnClickListener(v -> {
potsList.remove(getAdapterPosition());
notifyDataSetChanged();
}
Or in your class , when remove the item from list , don't forget to notify the adapter . One the adapter get notified , it will reflect the change on screen.

BaseAdapter On Scroll Refresh Data in ListView

I'm Very new to Java and android... I'm Try to create an ListView using BaseAdapter List being created successfully i have a EditText along with button for each list item but the real problem is when i put some data into editText Field and scroll down to change value of last list item then i go back to the top it refreshes the data to default value it doesn't contain the value which was entered by user before scrolling down
My BaseAdaper Code
class CoustomAdptr extends BaseAdapter{
String[] dates;
Integer[] inventory;
Integer totalrooms;
public CoustomAdptr(RoomFragment roomFragment, String[] dates, Integer[] inventory, Integer totalrooms) {
this.dates = dates;
this.inventory = inventory;
this.totalrooms = totalrooms;
}
#Override
public int getCount() {
return dates.length;
}
#Override
public Object getItem(int i) {
return null;
}
#Override
public long getItemId(int i) {
return 0;
}
#Override
public View getView(final int i, View view, ViewGroup viewGroup) {
view = getLayoutInflater().inflate(R.layout.inventory_listview,null);
TextView textView = (TextView) view.findViewById(R.id.roomListViewText);
final EditText editText = (EditText) view.findViewById(R.id.roomListInventory);
final Button updateButton = (Button) view.findViewById(R.id.roomListViewInventoryUpdateButton);
if(inventory[i] == 0){
editText.setBackgroundColor(getResources().getColor(R.color.SoldOut));
editText.setTextColor(getResources().getColor(R.color.SoldOutTextColor));
} else if(inventory[i] < totalrooms){
editText.setBackgroundColor(getResources().getColor(R.color.invetory));
editText.setTextColor(getResources().getColor(R.color.invetoryTextColor));
} else if(inventory[i] == totalrooms){
editText.setBackgroundColor(getResources().getColor(R.color.fullInventory));
editText.setTextColor(getResources().getColor(R.color.fullInventoryTextColor));
}
editText.setText(String.valueOf(inventory[i]));
textView.setText(dates[i]);
updateButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
//String name = editText.getText().toString();
//String name1 = dates[i];
//String name2 = getArguments().getString("room_id");
updateButton.setCompoundDrawablesWithIntrinsicBounds(R.drawable.ic_done_black_24dp,0,0,0);
//updateButton.setBackgroundColor(getResources().getColor(R.color.SoldOut));
updateButton.setText("Updated");
updateButton.setEnabled(false);
Toast.makeText(getContext(), "Update Inventory Button Clicked", Toast.LENGTH_LONG).show();
}
});
return view;
}
}
This is How Im Passing Data to My Adapter
JSONObject jObj = parentObject.getJSONObject("success");
JSONObject jObj2 = jObj.getJSONObject("data");
JSONArray arrajson = jObj2.getJSONArray("inventories");
String arrayCount = Integer.toString(arrajson.length());
String[] dates = new String[arrajson.length()];
Integer[] inventory = new Integer[arrajson.length()];
Integer totalrooms = new Integer(jObj2.getInt("total_room"));
for (int i=0; i<arrajson.length();i++){
JSONObject jsonObject = arrajson.getJSONObject(i);
dates[i] = jsonObject.getString("date");
inventory[i] = jsonObject.getInt("inventory");
}
CoustomAdptr coustomAdptr = new CoustomAdptr(RoomFragment.this,dates,inventory,totalrooms);
listView.setAdapter(coustomAdptr);
Help Needed :- I Want to retain same visible and Value of edittext as users enters on scroll up or down... i hope i was able to explain my problem clearly
After clicking a button, save it's state in a boolean array or somewhere else. And inside getView method, check if this button was previously clicked or not then setup your view accordingly.
It would be better if you create a model class for rows.

Android: How to refresh CursorAdapter with support for older APIs?

I read some posts and found that reQuery() is deprecated and some suggested using SwapCursor() or ChangeCursor().
I have a Favorite button on whose click I update DB and change color of the Button. When I scroll and come back to particular view(and Button) color is reset.
I know it is because view is recycled. I have a condition based on a DB column value to set the color of the Button.
I want view to get updated values from DB after I press the Button. For which I have to refresh/requery Cursor/DB.
How do I do that with CursorAdapter keeping in mind that my min. API is 19?
UPDATE
CursorAdapter code:
public class ToDoCursorAdapter extends CursorAdapter {
SparseBooleanArray selectionArrayAr = new SparseBooleanArray();
SparseBooleanArray selectionArrayRef = new SparseBooleanArray();
SparseBooleanArray selectionArrayFav = new SparseBooleanArray();
//Boolean isSet = false;
private MainButtons_Interface mAdapterCallback;
public ToDoCursorAdapter(Context context, Cursor cursor) {
super(context, cursor, 0);
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
ViewHolderItem viewHolder = new ViewHolderItem();
View rowView = LayoutInflater.from(context).inflate(R.layout.listview, parent, false);
viewHolder.engTextV = (TextView) rowView.findViewById(R.id.engText);
viewHolder.arTextV = (TextView) rowView.findViewById(R.id.arabText);
viewHolder.buttonIAV = (Button) rowView.findViewById(R.id.buttonIA); //For Arabic Text
viewHolder.refTextV = (TextView) rowView.findViewById(R.id.refText);
viewHolder.buttonIRV = (Button) rowView.findViewById(R.id.buttonIR); //For Ref Text
viewHolder.buttonIFV = (ImageButton) rowView.findViewById(R.id.buttonF);
rowView.setTag(viewHolder);
return rowView;
}
#Override
public void bindView(final View view, final Context context, final Cursor cursor) {
final ViewHolderItem viewHolder = (ViewHolderItem) view.getTag();
String arabic = cursor.getString(cursor.getColumnIndexOrThrow("PlainArab_Text")).trim().replaceAll("[\n]{2,}", "TWOFEEDS").replaceAll("\n", " ").replaceAll(" +", " ").replaceAll("<br/>", "\n").replaceAll("TWOFEEDS", "\n") + "\n";
String english = cursor.getString(cursor.getColumnIndexOrThrow("PlainEng_Text")).trim().replaceAll("[\n]{2,}", "TWOFEEDS").replaceAll("\n", " ").replaceAll(" +", " ").replaceAll("<br/>", "\n").replaceAll("TWOFEEDS", "\n") + "\n";
String ref = cursor.getString(cursor.getColumnIndexOrThrow("REF")).trim().replaceAll("<br/> <br/>", " ").replaceAll("<br/>", "\n");
final Integer HadithID = cursor.getInt(cursor.getColumnIndexOrThrow("ID"));
final Integer IsFav = cursor.getInt(cursor.getColumnIndexOrThrow("IsFavorite"));
viewHolder.arTextV.setText(arabic);
viewHolder.engTextV.setText(english);
viewHolder.refTextV.setText(ref);
final int position = cursor.getPosition();
boolean isSelectedA = selectionArrayAr.get(position);
boolean isSelectedR = selectionArrayRef.get(position);
boolean isSelectedF = selectionArrayFav.get(position);
if (isSelectedA) {
viewHolder.arTextV.setVisibility(view.GONE);
viewHolder.buttonIAV.setText("Show Arabic Version");
} else if (!isSelectedA){
viewHolder.arTextV.setVisibility(view.VISIBLE);
viewHolder.buttonIAV.setText("Hide Arabic Version");
}
if (isSelectedR) {
viewHolder.refTextV.setVisibility(view.GONE);
viewHolder.buttonIRV.setText("Show Refrence");
} else if (!isSelectedR){
viewHolder.refTextV.setVisibility(view.VISIBLE);
viewHolder.buttonIRV.setText("Hide Refrence");
}
//boolean isSelectedF = selectionArrayFav.get(position);
if(isSelectedF) {
viewHolder.buttonIFV.setImageResource(R.drawable.favoritebutton_afterclick);
} else if (!isSelectedF){
viewHolder.buttonIFV.setImageResource(R.drawable.favoritebutton);
}
//Arabic Button
viewHolder.buttonIAV.setOnClickListener(
new View.OnClickListener()
{ #Override
public void onClick(View v) {
boolean isSelectedAc = selectionArrayAr.get(position);
if(!isSelectedAc) {
viewHolder.arTextV.setVisibility(v.GONE);
viewHolder.buttonIAV.setText("Show Arabic Version");
setSelectedAr(position, true);
} else if (isSelectedAc){
viewHolder.arTextV.setVisibility(v.VISIBLE);
setSelectedAr(position, false);
viewHolder.buttonIAV.setText("Hide Arabic version");
}
}
}
);
//Ref Button
viewHolder.buttonIRV.setOnClickListener(
new View.OnClickListener()
{ #Override
public void onClick(View v) {
boolean isSelectedRc = selectionArrayRef.get(position);
if(!isSelectedRc) {
viewHolder.refTextV.setVisibility(v.GONE);
viewHolder.buttonIRV.setText("Show Reference");
setSelectedRef(position, true);
} else if (isSelectedRc){
viewHolder.refTextV.setVisibility(v.VISIBLE);
setSelectedRef(position, false);
viewHolder.buttonIRV.setText("Hide Reference");
}
}
}
);
//Fav Button
viewHolder.buttonIFV.setOnClickListener(
new View.OnClickListener()
{ #Override
public void onClick(View v) {
boolean isSelectedF = selectionArrayFav.get(position);
boolean IsSet = ((ListViewActivity) context).addRemFav(HadithID);
String mess ="";
if(IsSet){
mess = "Hadith add to Favorite list";
} else if(!IsSet){
mess = "Hadith removed from Favorite list";
}
if(!isSelectedF) {
viewHolder.buttonIFV.setImageResource(R.drawable.favoritebutton_afterclick);
setSelectedF(position, true);
} else if (isSelectedF){
viewHolder.buttonIFV.setImageResource(R.drawable.favoritebutton);
setSelectedF(position, false);
}
Toast.makeText(v.getContext(), mess, Toast.LENGTH_SHORT).show();
}
}
);
}
// our ViewHolder.
static class ViewHolderItem {
TextView engTextV;
TextView arTextV;
TextView refTextV;
Button buttonIAV;
Button buttonIRV;
ImageButton buttonIFV;
}
// Method to mark items in selection
public void setSelectedAr(int position, boolean isSelected) {
selectionArrayAr.put(position, isSelected);
}
public void setSelectedRef(int position, boolean isSelected) {
selectionArrayRef.put(position, isSelected);
}
public void setSelectedF(int position, boolean isSelected) {
selectionArrayFav.put(position, isSelected);
}
UPDATE
I added this logic to my function which was called on clicking the Button.
Cursor todoCursor1 = hadDB.rawQuery("SELECT ID as _id, * FROM HAD_TABLE WHERE ID < 7001 ", null);
todoAdapter.changeCursor(todoCursor1);
Basically, you just need to requery DB so that you get updated records/Data and then change your current cursor with new one, todoCursor1 is my case above.
Also, changeCursor() will close your current cursor, in case you would want to go back to old cursor you should use swapCursor() instead as it will return you old cursor.
Now my only thing I want to know is, if this will work for APIs 19 and up.
I added this logic to my function which was called on clicking the Button.
Cursor todoCursor1 = hadDB.rawQuery("SELECT ID as _id, * FROM HAD_TABLE WHERE ID < 7001 ", null);
todoAdapter.changeCursor(todoCursor1);
Basically, you just need to requery DB so that you get updated records/Data and then change your current cursor with new one, todoCursor1 is my case above.
Also, changeCursor() will close your current cursor, in case you would want to go back to old cursor you should use swapCursor() instead as it will return you old cursor.

Android ArrayAdapter gives newly scrolled item

I have an ArrayAdapter which shows some posts using a fragment. In this fragment I have some buttons. So all of the posts shown have these buttons.
The problem is, when I click a button of a post to setText to a field of this post; instead of changing text of post that I clicked, it changes text of newly scrolled item.
For example if I scroll down the ListView a new item comes. Then regardless of which post I clicked it changes text of this new post.
How can I prevent this to happen? I take current post using
getItem(position)
By scroolling I mean new element of the list are loaded and shown.
public View getView(final int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = (LayoutInflater) context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View v = inflater.inflate(R.layout.comment_small,parent,false);
TextView tvOwner = (TextView) v.findViewById(R.id.tvCommentSmallOwner);
TextView tvCreationDate = (TextView) v.findViewById(R.id.tvCommentSmallCreationDate);
TextView tvCreationDateValue = (TextView) v.findViewById(R.id.tvCommentSmallCreationDate);
TextView tvContent = (TextView) v.findViewById(R.id.tvCommentSmallContent);
tvVoteCount = (TextView) v.findViewById(R.id.tvCommentVoteCount);
c = getItem(position);
tvOwner.setText(context.getResources().getString(R.string.generic_by) + " " + c.getOwnerId());
SimpleDateFormat dateFormat = new SimpleDateFormat("dd-MM-yyyy HH:mm:ss");
String s =c.getPostDate();
System.out.println(s);
tvCreationDateValue.setText(s);
tvContent.setText(c.getContent());
btnDownVote = (ImageButton) v.findViewById(R.id.btnCommentDownVote);
btnUpVote = (ImageButton) v.findViewById(R.id.btnCommentUpVote);
tvVoteCount.setText("" + c.getNetCount());
btnUpVote.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
c=getItem(position);
ServerRequests sr = new ServerRequests(getContext());
MemberLocalStore memberLocalStore = new MemberLocalStore(getContext());
Member m = memberLocalStore.getLoggedInMember();
sr.voteComment(c, true, m.getId(), new Consumer<String>() {
#Override
public void accept(String vote) {
tvVoteCount.setText("" + vote);
}
});
}
});
btnDownVote.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
c=getItem(position);
ServerRequests sr = new ServerRequests(getContext());
MemberLocalStore memberLocalStore = new MemberLocalStore(getContext());
Member m = memberLocalStore.getLoggedInMember();
sr.voteComment(c, false, m.getId(), new Consumer<String>() {
#Override
public void accept(String vote) {
tvVoteCount.setText("" + vote);
}
});
}
});
return v;
}
I want to vote (like,dislike) some posts but when I click upvote button that marked as 1, overall vote of the post that marked as 2 changes.

Android ViewHolder in CursorAdapter causing listView to get screwed

I've been struggeling in the past few days trying to figure this out, I hope you can help me...
I have an Activity that shows a list of Players by setting a listadapter like this:
PlayerCursorAdapter playerAdapter = new PlayerCursorAdapter(this,
R.layout.players_row, c, columns, to);
setListAdapter(playerAdapter);
When clicking an item in the list, this code will be executed showing a dialog with an "Edit" and "Delete" option for editing and removing players:
private class OnPlayerItemClickListener implements OnItemClickListener {
public void onItemClick(AdapterView<?> parent, View view, int position,
long rowId) {
Toast.makeText(view.getContext(),
"Clicked Item [" + position + "], rowId [" + rowId + "]",
Toast.LENGTH_SHORT).show();
// Prepare Dialog with "Edit" and "Delete" option
final CharSequence[] choices = {
view.getContext().getString(R.string.buttonEdit),
view.getContext().getString(R.string.buttonDelete) };
AlertDialog.Builder builder = new AlertDialog.Builder(
view.getContext());
builder.setTitle(R.string.title_edit_delete_player);
builder.setItems(choices, new EditOrDeleteDialogOnClickListener(
view, rowId));
AlertDialog alert = builder.create();
// Show Dialog
alert.show();
}
Based on your choice (Edit or delete player), the following listener will be executed:
private class EditOrDeleteDialogOnClickListener implements
DialogInterface.OnClickListener {
private View view;
private long rowId;
public EditOrDeleteDialogOnClickListener(View view, long rowId) {
this.view = view;
this.rowId = rowId;
}
public void onClick(DialogInterface dialog, int item) {
if (item == 0) {
// Edit
showDialog(PlayGameActivity.DIALOG_EDIT_PLAYER_ID);
} else if (item == 1) {
// Delete from database
DatabaseHelper databaseHelper = new DatabaseHelper(
view.getContext());
databaseHelper.deletePlayer(rowId);
// Requery to update view.
((PlayerCursorAdapter) getListAdapter()).getCursor().requery();
Toast.makeText(
view.getContext(),
view.getContext().getString(
R.string.message_player_removed)
+ " " + rowId, Toast.LENGTH_SHORT).show();
}
}
}
The code for the adapter is here:
public class PlayerCursorAdapter extends SimpleCursorAdapter {
private LayoutInflater layoutInflater;
private int layout;
public PlayerCursorAdapter(Context context,
int layout, Cursor c, String[] from, int[] to) {
super(context, layout, c, from, to);
this.layout = layout;
layoutInflater = LayoutInflater.from(context);
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
Cursor c = getCursor();
View view = layoutInflater.inflate(layout, parent, false);
// Get Data
int nameCol = c.getColumnIndex(Player.COLUMN_PLAYER_NAME);
String name = c.getString(nameCol);
int gamesPlayedCol = c.getColumnIndex(Player.COLUMN_GAMES_PLAYED);
String gamesPlayed = c.getString(gamesPlayedCol);
int gamesWonCol = c.getColumnIndex(Player.COLUMN_GAMES_WON);
String gamesWon = c.getString(gamesWonCol);
// Set data on fields
TextView topText = (TextView) view.findViewById(R.id.topText);
if (name != null)
topText.setText(name);
TextView bottomText = (TextView) view.findViewById(R.id.bottomText);
if (gamesPlayed != null && gamesWon != null)
bottomText.setText(view.getContext().getString(
R.string.info_played_won)
+ gamesPlayed + "/" + gamesWon);
CheckBox checkBox = (CheckBox) view.findViewById(R.id.checkBox);
// Set up PlayerViewHolder
PlayerViewHolder playerViewHolder = new PlayerViewHolder();
playerViewHolder.playerName = name;
playerViewHolder.gamesPlayed = gamesPlayed;
playerViewHolder.gamesWon = gamesWon;
playerViewHolder.isChecked = checkBox.isChecked();
view.setTag(playerViewHolder);
return view;
}
private class PlayerViewHolder {
String playerName;
String gamesPlayed;
String gamesWon;
boolean isChecked;
}
#Override
public void bindView(View view, Context context, Cursor c) {
PlayerViewHolder playerViewHolder = (PlayerViewHolder) view.getTag();
TextView topText = (TextView) view.findViewById(R.id.topText);
topText.setText(playerViewHolder.playerName);
TextView bottomText = (TextView) view.findViewById(R.id.bottomText);
bottomText.setText(view.getContext()
.getString(R.string.info_played_won)
+ playerViewHolder.gamesPlayed
+ "/"
+ playerViewHolder.gamesWon);
CheckBox checkBox = (CheckBox) view.findViewById(R.id.checkBox);
checkBox.setChecked(playerViewHolder.isChecked);
}
}
Now, the problem is that after removing a few of the players in the list, the list gets screwed up, eg. it shows something different than what is actually available.
I've experimented a little and if I stop using the PlayerViewHolder in bindView and instead read the text from the cursor and assign it directly to the text fields, then it works.... So question is, why is my ViewHolder screwing up things???
Any help will be greatly appreciated!
Thanks!
Zyb3r
Found a solution...
Basically I reinitialize the Cursor and ListAdapter plus assigns the ListAdapter to the ListView all over again when I change the data in the database.
I'm not entirely sure why this is nessasary, but notifyDataSetChanged(), notifyDataSetInvalidated() and all the other things I tried didn't work, so now I'm using this approach. :o)
Zyb3r

Categories

Resources