so i declared a button for every item in the ListView but it happens that it responds to more Items then just the clicked one. For example if i push the button of the first button the 9th and 18th item are getting changed aswell. It would be awesome if you could help me with this one :) thanks in advance
This is the CusomtListAdapter which fills the ListView
public class CustomListAdapter extends BaseAdapter {
private ArrayList<Task> tasks;
private LayoutInflater inflater = null;
private Application application;
public CustomListAdapter(Activity activity, Application application,
ArrayList<Task> tasks) {
this.application = application;
this.tasks = tasks;
inflater = (LayoutInflater) application.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
public static class ViewHolder {
TextView lv_tv_description;
TextView lv_tv_period;
Button lv_bt_done;
TextView lv_gone_pk;
TextView lv_gone_group_pk;
TextView lv_gone_description;
TextView lv_gone_period;
TextView lv_gone_period_kind;
TextView lv_gone_time;
TextView lv_gone_done;
}
@Override
public int getCount() {
return tasks.size();
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return 0;
}
@Override
public View getView(final int position, View vi, ViewGroup parent) {
final ViewHolder viewHolder;
if (vi == null) {
vi = inflater.inflate(R.layout.listview, parent, false);
viewHolder = new ViewHolder();
viewHolder.lv_tv_description = (TextView) vi.findViewById(R.id.lv_tv_description);
viewHolder.lv_tv_period = (TextView) vi.findViewById(R.id.lv_tv_period);
viewHolder.lv_bt_done = (Button) vi.findViewById(R.id.lv_bt_done);
viewHolder.lv_gone_pk = (TextView) vi.findViewById(R.id.lv_gone_pk);
viewHolder.lv_gone_group_pk = (TextView) vi.findViewById(R.id.lv_gone_group_pk);
viewHolder.lv_gone_description = (TextView) vi.findViewById(R.id.lv_gone_description);
viewHolder.lv_gone_period = (TextView) vi.findViewById(R.id.lv_gone_period);
viewHolder.lv_gone_period_kind = (TextView) vi.findViewById(R.id.lv_gone_period_kind);
viewHolder.lv_gone_time = (TextView) vi.findViewById(R.id.lv_gone_time);
viewHolder.lv_gone_done = (TextView) vi.findViewById(R.id.lv_gone_done);
vi.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) vi.getTag();
}
viewHolder.lv_tv_description.setText(tasks.get(position).getDescription());
viewHolder.lv_tv_period.setText(tasks.get(position).getPeriod_kind());
viewHolder.lv_bt_done.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
DatabaseHandler dbhandler = new DatabaseHandler(application);
View pk_view = (View) v.getParent().getParent().getParent();
TextView textview_pk = ((TextView) pk_view.findViewById(R.id.lv_gone_pk));
View parentView = (View) v.getParent().getParent();
TextView textview1 = ((TextView) parentView.findViewById(R.id.lv_tv_description));
TextView textview2 = ((TextView) parentView.findViewById(R.id.lv_tv_period));
Button button = ((Button) parentView.findViewById(R.id.lv_bt_done));
if (viewHolder.lv_bt_done.getText().toString().equalsIgnoreCase("done")) {
viewHolder.lv_tv_description.setPaintFlags(viewHolder.lv_tv_description.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);
viewHolder.lv_gone_description.setPaintFlags(viewHolder.lv_gone_description.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);
viewHolder.lv_bt_done.setText("UNDO");
viewHolder.lv_bt_done.setBackgroundResource(R.drawable.layout_rounded_background_accent);
notifyDataSetChanged();
dbhandler.updateDone(Integer.valueOf(textview_pk.getText().toString()), "true");
} else if (viewHolder.lv_bt_done.getText().toString().equalsIgnoreCase("undo")) {
viewHolder.lv_tv_description.setPaintFlags(viewHolder.lv_tv_description.getPaintFlags() & (~Paint.STRIKE_THRU_TEXT_FLAG));
viewHolder.lv_gone_description.setPaintFlags(viewHolder.lv_gone_description.getPaintFlags() & (~Paint.STRIKE_THRU_TEXT_FLAG));
viewHolder.lv_bt_done.setText("DONE");
viewHolder.lv_bt_done.setBackgroundResource(R.drawable.layout_rounded_background);
notifyDataSetChanged();
dbhandler.updateDone(Integer.valueOf(textview_pk.getText().toString()), "false");
}
dbhandler.close();
}
});
viewHolder.lv_gone_pk.setText(String.valueOf(tasks.get(position).getPk()));
if (tasks.get(position).getDone().equalsIgnoreCase("true")) {
viewHolder.lv_tv_description.setPaintFlags(viewHolder.lv_tv_description.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);
viewHolder.lv_tv_period.setPaintFlags(viewHolder.lv_tv_description.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG);
viewHolder.lv_bt_done.setText("UNDO");
viewHolder.lv_bt_done.setBackgroundResource(R.drawable.layout_rounded_background_accent);
}
return vi;
}}
and this is the matching layout file for all the items
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minHeight="70dp">
<LinearLayout
android:focusable="false"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout
android:focusable="false"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1">
<RelativeLayout
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="1">
<TextView
android:focusable="false"
android:id="@+id/lv_tv_description"
android:textSize="20dp"
android:textColor="@android:color/black"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_marginTop="7dp"/>
</RelativeLayout>
<RelativeLayout
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="2">
<TextView
android:focusable="false"
android:id="@+id/lv_tv_period"
android:textColor="@android:color/black"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"/>
</RelativeLayout>
</LinearLayout>
<RelativeLayout
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight="4">
<Button
android:id="@+id/lv_bt_done"
android:text="DONE"
android:focusable="false"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignParentTop="true"
android:layout_marginTop="10dp"
android:background="@drawable/layout_rounded_background"/>
</RelativeLayout>
</LinearLayout>
<!-- invisible TextViews -->
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_pk"
android:visibility="visible"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_group_pk"
android:visibility="visible"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_description"
android:visibility="gone"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_period"
android:visibility="gone"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_period_kind"
android:visibility="gone"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_time"
android:visibility="gone"
android:layout_alignParentRight="true"/>
<TextView
android:focusable="false"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/lv_gone_done"
android:visibility="gone"
android:layout_alignParentRight="true"/>
</RelativeLayout>
if you need anything else please let me know in the comments :)
The View
gets reused in the ListView
via the second parameter (convertView
) of the getView()
method.
From the documentation,
convertView - The old view to reuse, if possible. Note: You should check that this view is non-null and of an appropriate type before using. If it is not possible to convert this view to display the correct data, this method can create a new view.
So at any time, only the number of views (plus a couple more) that are visible on your device screen is available in memory. As you scroll the list, the views that go off the screen are reused for the items that are coming into the screen.
In your case, the 1st, 9th item and 18th item are the same View
being reused. That's why you are getting the changed View
for the 9th and 18th item when you press the button only on the 1st item.
Solution:
When the button is pressed, add that state information in some data structure. For example, in an array
of booleans
, save true for the item whose button is in pressed state and false for other buttons.
And in the getView()
method, check the state of the button from that array of booleans and change the view respectively.