I have 2 problems with my current recycler view with cardview. The first is with the checkbox. The checkboxs seem to check/uncheck themselves all the time. I know I need to set onCheckedChangeListener, just not sure what to put in it. My second issue is each item in the recycler view/cardview has 4 Strings and 1 checkbox, but sometimes one of the strings is too large, which screws up the whole thing.. Is there any way if a string is too long I can make it make the cardview larger so one of the words will go underneath the first word?
Here is the custom object class:
public class Workout{
private String exercise;
private String percent;
private String reps;
private String weight;
private boolean check1;
public Workout(String exercise, String percent, String reps, String weight, boolean check1) {
this.exercise = exercise;
this.percent = percent;
this.reps = reps;
this.weight = weight;
this.check1 = check1;
}
/* accessors omitted for readability */
}
Here is the adapter:
public class MyRecyclerAdapter extends RecyclerView.Adapter<MyViewHolder> {
Context mContext;
ArrayList<Workout> workout;
public MyRecyclerAdapter(Context context, ArrayList<Workout> workout) {
mContext = context;
this.workout = workout;
}
// INITIALIZE HOLDER
#Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.workout_item, null);
MyViewHolder holder = new MyViewHolder(view);
return holder;
}
//BIND DATA TO VIEWS
#Override
public void onBindViewHolder(MyViewHolder holder, int position) {
final Workout objWorkout = workout.get(position);
holder.exercise.setText(workout.get(position).getExercise());
holder.percent.setText(workout.get(position).getPercent());
holder.reps.setText(workout.get(position).getReps());
holder.weight.setText(workout.get(position).getWeight());
holder.check1.setOnCheckedChangeListener();
//LISTENER
holder.setItemClickListener(new ItemClickListener() {
#Override
public void onItemClick(View view, int pos) {
Toast.makeText(mContext, workout.get(pos).getExercise(),Toast.LENGTH_LONG).show();
}
});
}
#Override
public int getItemCount() {
return workout.size();
}
}
Here is the xml for custom item:
<android.support.v7.widget.CardView
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:layout_width="wrap_content"
xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:layout_margin="10dp"
card_view:cardCornerRadius="10dp"
card_view:cardElevation="10dp" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingTop="15dp"
android:paddingLeft="15dp"
android:paddingRight="15dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceSmall"
android:text="Squat"
android:textSize="20sp"
android:id="#+id/txtExercise"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceSmall"
android:text="%"
android:textSize="20sp"
android:id="#+id/txtPercentage"
android:paddingLeft="30dp"
android:layout_alignParentTop="true"
android:layout_toRightOf="#+id/txtExercise"
/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceSmall"
android:text="Reps"
android:textSize="20sp"
android:id="#+id/txtReps"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Weight"
android:textSize="20sp"
android:id="#+id/txtWeight"
android:layout_alignParentTop="true"
android:layout_toLeftOf="#+id/check1"
android:layout_toStartOf="#+id/check1"/>
<CheckBox
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/check1"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:layout_alignParentEnd="true"
android:layout_marginRight="31dp"
android:layout_marginEnd="31dp"
android:checked="false"/>
</RelativeLayout>
Thanks for the help!
For your check box issue:
You need to call holder.check1.setChecked(boolean) in the onBind. Keep in mind that onBind is called several times for each view. So when you scroll, and the recycler view is recycling, it is reusing a checkbox that you aren't specifying if they are checked or not.
Also, because onBind is call so frequently it is best to not set the listener there. Set the listener in the constructor of the view holder.
EDIT
In your listener store the value if it is checked or not. This is usually stored in the object that you are displaying, in your case workout. If you don't have a value there for that, you can use SparseBooleanArray. It is really good for keeping track of what is checked and not.
For your text issue:
sometimes one of the strings is too large, which screws up the whole thing
I am not too sure what you mean. But looking at your xml you do a lot things as far as layout_alignParentTop or layout_toLeftOf. I bet it is something wrong with those once one text is too large. Try changing your root layout to a LinearLayout or try to remove as many of those rules as you can. I bet you will discover your bug when doing that.
Related
Im trying to add rows to a custom list view with user input, but I dont understand how to in the customadapter class..
The custom list view layout:
<TextView
android:id="#+id/activityName"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentStart="true"
android:layout_alignParentTop="true"
android:layout_marginStart="28dp"
android:layout_marginTop="22dp"
android:textSize="35sp"
android:text="Activity Name" />
<TextView
android:id="#+id/xText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="19dp"
android:text="x:"
android:textSize="20sp"
android:layout_below="#+id/activityName"
android:layout_alignStart="#+id/activityName" />
<TextView
android:id="#+id/yText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="y:"
android:textSize="20sp"
android:layout_alignBaseline="#+id/xText"
android:layout_alignBottom="#+id/xText"
android:layout_toEndOf="#+id/xText"
android:layout_marginStart="32dp" />
<TextView
android:id="#+id/zText"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="z:"
android:textSize="20sp"
android:layout_marginEnd="119dp"
android:layout_alignBaseline="#+id/yText"
android:layout_alignBottom="#+id/yText"
android:layout_alignParentEnd="true" />
I've managed to find some guides that show how to enter to a custom list view from arrays, but here I want it to be added from users input..
class CustomAdapter extends BaseAdapter{
#Override
public int getCount(){
return 0;
}
#Override
public Object getItem(int i)
{
return null;
}
#Override
public long getItemId(int i)
{
return 0;
}
#Override
public View getView(int i, View view, ViewGroup viewGroup)
{
view = getLayoutInflater().inflate(R.layout.customlistview, null);
TextView activity_name = (TextView) view.findViewById(R.id.activityName);
TextView x_text = (TextView) view.findViewById(R.id.xText);
TextView y_text = (TextView) view.findViewById(R.id.yText);
TextView z_text = (TextView) view.findViewById(R.id.zText);
return view;
}
}
Could someone help please?
To dynamically change a list or add or delete any list item, you should use an ArrayList.
Where is your ArrayList or Array where the listItems are stored? Please add every details.
You should use RecyclerView instead of ListView. It is more configurable and dynamic.
I'm working on a chatting application. All I did is i can get api response successfully and can show them serially like this
This is id of sender and reciver
This is the messages
For doing this I created an adapter which code is something like this.
public class Single_chat_adapter extends RecyclerView.Adapter<Single_chat_adapter.Single_chat_adapterViewHolder>{
private List<Datum2> data;
private int rowLayout;
private Context context;
public Single_chat_adapter(List<Datum2> data, int rowLayout, Context context) {
this.data = data;
this.rowLayout = rowLayout;
this.context = context;
}
#Override
public Single_chat_adapterViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.card2, parent, false);
return new Single_chat_adapterViewHolder(view); }
#Override
public void onBindViewHolder(Single_chat_adapterViewHolder holder, int position) {
holder.single_msg.setText(data.get(position).getMsg());
}
#Override
public int getItemCount() {
return data.size();
}
public class Single_chat_adapterViewHolder extends RecyclerView.ViewHolder {
TextView single_msg;
public Single_chat_adapterViewHolder(View itemView) {
super(itemView);
single_msg =itemView.findViewById(R.id.userNameTV);
}
}
}
Here I use a single view which is card2.xml. But all I need to do is set senders message in the left side and receiver message in other side.
What To do?
To achieve what you have explained, Create two views in card2.xml(one at the left and the other in the right). I have created one for you.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:paddingStart="5dp"
android:paddingEnd="5dp"
android:layout_marginBottom="6dp"
android:layout_marginTop="4dp"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<ImageView
android:layout_width="40dp"
android:id="#+id/avatar"
android:background="#drawable/circle_stroke"
android:layout_marginStart="5dp"
android:layout_marginEnd="5dp"
android:src="#drawable/useric"
android:layout_height="40dp" />
<RelativeLayout
android:layout_toEndOf="#+id/avatar"
android:id="#+id/msg_back"
android:layout_marginBottom="5dp"
android:layout_gravity="center_vertical"
android:background="#drawable/message_bubble_accent"
android:layout_width="match_parent"
android:padding="10dp"
android:orientation="vertical"
android:layout_height="wrap_content">
<TextView
android:textSize="17sp"
android:id="#+id/user_text"
android:layout_width="wrap_content"
android:textColor="#color/white"
android:text="Hello world how are you?"
android:layout_height="wrap_content" />
<TextView
android:textSize="12sp"
android:layout_below="#+id/user_text"
android:id="#+id/chat_time"
android:textColor="#color/dark"
android:text="3:33pm"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</RelativeLayout>
<ImageView
android:layout_width="40dp"
android:id="#+id/avatar2"
android:layout_alignParentEnd="true"
android:layout_below="#+id/msg_back"
android:background="#drawable/circle_stroke"
android:layout_marginStart="5dp"
android:layout_marginEnd="5dp"
android:src="#drawable/useric"
android:layout_height="40dp" />
<RelativeLayout
android:layout_toStartOf="#+id/avatar2"
android:layout_below="#+id/msg_back"
android:id="#+id/msg_back2"
android:layout_gravity="center_vertical"
android:background="#drawable/message_bubble_white"
android:layout_width="match_parent"
android:padding="10dp"
android:orientation="vertical"
android:layout_height="wrap_content">
<TextView
android:textSize="17sp"
android:id="#+id/user_text2"
android:layout_width="wrap_content"
android:textColor="#color/white"
android:text="Hello world how are you?"
android:layout_height="wrap_content" />
<TextView
android:layout_below="#+id/user_text2"
android:id="#+id/chat_time2"
android:textColor="#color/dark"
android:text="3:33pm"
android:textSize="12sp"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:layout_alignParentEnd="true"
android:layout_below="#+id/user_text2"
android:text="#string/sent"
android:width="20dp"
android:textAppearance="?android:textAppearanceSmall"
android:layout_width="20dp"
android:layout_height="20dp"
android:textColor="#android:color/holo_green_light"/>
</RelativeLayout>
</RelativeLayout>
</LinearLayout>
Modify your onBindViewHolder and add the condition that will check if the message is coming from another user or not. Like this...
#Override
public void onBindViewHolder(Single_chat_adapterViewHolder holder, int position) {
Datum2 datum = data.get(position);
holder.single_msg.setText(datum.getMsg());
int msgId = datum.getMsgId();
if (msgId == datum.getUserMsgId) {
//Do everything pertaining to this user here
holder.rightBubble.setText(single_msg);
//holder.rightAvatar.setText(single_msg) //For setting image
} else {
holder.leftBubble.setText(single_msg);
}
}
Make sure you reference leftBubble and rightBubble from you ViewHolder, and set the current userMsgid from the activity that is using this adapter.
You have to create 2 viewtype and two xml for them additionally and load them in a single adapter. Follow the link may help you.
Android Chat Tutorial: Building a Messaging UI
1) Create 2 views in card2.xml
2) One for left and another for right
3) Put condition in your onBindViewHolder, if message is from senders make left view visible and hide right view and same thing for right view also.
You can put condition inside onCreateViewHolder, this will let you to swap the layout (xml file)
#Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
int layout = -1;
switch (viewType) {
case Message.TYPE_MESSAGE:
layout = R.layout.item_message;
break;
case Message.TYPE_LOG:
layout = R.layout.item_log;
break;
case Message.TYPE_ACTION:
layout = R.layout.item_action;
break;
}
View v = LayoutInflater
.from(parent.getContext())
.inflate(layout, parent, false);
return new ViewHolder(v);
}
You can change viewtype from this method
#Override
public int getItemViewType(int position) {
// Just as an example, return 0 or 2 depending on position
// Note that unlike in ListView adapters, types don't have to be contiguous
return position % 2 * 2;
}
I have a RecyclerView list populated by CardViews. I tried to add a Checkbox to the left side of the CardView and nothing happens. Only the two TextViews appear. What am I missing here?
card_layout.xml:
...
<android.support.v7.widget.CardView
xmlns:card_view="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/singlecard_view1"
android:layout_width="match_parent"
android:layout_height="match_parent"
card_view:cardBackgroundColor="#android:color/white"
card_view:cardCornerRadius="6dp"
android:orientation="horizontal"
android:layout_margin="4dp">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="?android:selectableItemBackground" >
<CheckBox
android:id="#+id/chkSelected"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_centerVertical="true" />
<TextView
android:id="#+id/cardBlankText2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:layout_toRightOf="#+id/chkSelected"
android:layout_toEndOf="#+id/chkSelected"
android:textStyle="bold"
android:textColor="#android:color/black"
android:textAppearance="?android:attr/textAppearanceLarge"
android:clickable="true"
android:gravity="center_vertical"
android:textAlignment="center" />
<TextView
android:id="#+id/cardBlankText3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:layout_toRightOf="#+id/cardBlankText2"
android:layout_toEndOf="#+id/cardBlankText2"
android:textStyle="bold"
android:textColor="#android:color/black"
android:textAppearance="?android:attr/textAppearanceLarge"
android:clickable="true"
android:gravity="center_vertical"
android:textAlignment="center" />
</RelativeLayout>
</android.support.v7.widget.CardView>
...
DataModel.java:
public class DataModel {
private String todo;
private String note1;
private boolean isSelected;
public String getTodo() {
return todo;
}
public void setTodo(String todo) {
this.todo = todo;
}
public String getNote1() {
return note1;
}
public void setNote1(String note1) {
this.note1 = note1;
}
public boolean isSelected() {
return isSelected;
}
public void setSelected(boolean isSelected) {
this.isSelected = isSelected;
}
}
Adapter.java:
...
public class ListViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
CheckBox chkSelected;
TextView cardBlankText2;
TextView cardBlankText3;
public ListViewHolder(View itemView) {
super(itemView);
chkSelected = (CheckBox) itemView.findViewById(R.id.chkSelected);
cardBlankText2 = (TextView)itemView.findViewById(R.id.cardBlankText2);
cardBlankText3 = (TextView)itemView.findViewById(R.id.cardBlankText3);
#Override
public void onBindViewHolder(ListViewHolder holder, int position) {
holder.chkSelected.setChecked(dbList.get(position).isSelected());
holder.chkSelected.setTag(dbList.get(position));
holder.cardBlankText2.setText(dbList.get(position).getTodo());
holder.cardBlankText3.setText(dbList.get(position).getNote1());
}
...
}
Probably the problem of third textview's match parent width
<TextView
android:id="#+id/cardBlankText3"
android:layout_width="match_parent"
It's a common bug that "match_parent" couldn't just fill up the rest of the space but occupied the whole view. (And, yes, in preview, it's totally no problem)
If you want to have the third textview fill up just the rest space after the checkbox and 2nd textview. You could try
<TextView
android:id="#+id/cardBlankText3"
android:layout_width="0dp"
android:layout_alignParentEnd="true"
android:layout_alignParentRight="true"
To avoid textview 2 is too long and leave no space for textview 3, you should also set a max width too. Something like this.
<TextView
android:id="#+id/cardBlankText2"
android:maxWidth="160dp"
Just take a magic number you like.
If you want to have textview 2 and textview 3 divide the space evenly. You can make use of LinearLayout, weight_sum and weight.
I have a list that when you click on the row on the right side the layout with the icon is changed by other. This makes it well but when I scrolling in the list, I notice there are rows with the same icon without do click. Also, if I scroll quickly these same icons are lost and are built differently. I think it's on the reuse of cells but I can not find the solution. What I want is that the image stays active only in the row where clicka.
Thanks!!
Adapter class:
public class ListadoVotantesArrayAdapter extends ArrayAdapter<Votante> {
private Context context;
private LayoutInflater inflater;
private ArrayList<Votante> listaVotantes;
private int rowLayout;
private View mConverView;
public ListadoVotantesArrayAdapter(Context context, int resource, ArrayList<Votante> objects) {
super(context, resource,objects);
this.context = context;
this.inflater = LayoutInflater.from(context);
this.listaVotantes = objects;
this.rowLayout = resource;
}
public int getCount(){
return this.listaVotantes.size();
}
public Votante getVotante(int position){
return this.listaVotantes.get(position);
}
private static class ViewHolder {
public TextView lblName;
public TextView lblLastName;
public TextView lblDni;
public TextView lblVoterNumber;
public RelativeLayout lytVoted;
public RelativeLayout lytCanVote;
public RelativeLayout lytUndo;
}
public View getView(int position, View converView, ViewGroup parent) {
final ViewHolder viewHolder;
mConverView = converView;
if (mConverView == null){
viewHolder = new ViewHolder();
this.mConverView = inflater.inflate(this.rowLayout, parent, false);
if (mConverView != null){
viewHolder.lblName = (TextView) mConverView.findViewById(R.id.lblVoterName);
viewHolder.lblLastName = (TextView) mConverView.findViewById(R.id.lblVoterLastName);
viewHolder.lblDni = (TextView) mConverView.findViewById(R.id.lblDni);
viewHolder.lblVoterNumber = (TextView) mConverView.findViewById(R.id.lblNumber);
viewHolder.lytVoted = (RelativeLayout) mConverView.findViewById(R.id.lytVoted);
viewHolder.lytCanVote = (RelativeLayout) mConverView.findViewById(R.id.lytCanVote);
viewHolder.lytUndo = (RelativeLayout) mConverView.findViewById(R.id.lytUndo);
mConverView.setTag(viewHolder);
}
}else{
viewHolder = (ViewHolder) mConverView.getTag();
}
Votante votante = getVotante(position);
viewHolder.lblName.setText(votante.getNombre());
viewHolder.lblLastName.setText(votante.getApellidos());
viewHolder.lblDni.setText(votante.getDni());
viewHolder.lblVoterNumber.setText(""+votante.getNumVotante());
if (votante.getVotado()){
viewHolder.lytVoted.setVisibility(View.VISIBLE);
viewHolder.lytCanVote.setVisibility(View.GONE);
}else{
viewHolder.lytVoted.setVisibility(View.GONE);
viewHolder.lytCanVote.setVisibility(View.VISIBLE);
}
mConverView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
viewHolder.lytUndo.setVisibility(View.VISIBLE);
notifyDataSetChanged();
}
});
return mConverView;
}
}
Layout Row:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/lyt_voter"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="1dp">
<RelativeLayout
android:id="#+id/lytVoterNumber"
android:layout_width="70dp"
android:layout_height="70dp"
android:layout_alignParentLeft="true"
android:background="#color/lightBlueItemList">
<TextView
android:id="#+id/lblNumber"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:text="1999"
android:textAppearance="?android:attr/textAppearanceMedium" />
</RelativeLayout>
<LinearLayout
android:id="#+id/lytVoterData"
android:layout_width="wrap_content"
android:layout_height="70dp"
android:layout_alignParentTop="true"
android:layout_toLeftOf="#+id/lytCanVote"
android:layout_toRightOf="#+id/lytVoterNumber"
android:layout_toStartOf="#+id/lytCanVote"
android:background="#color/whiteItemList"
android:orientation="vertical"
android:padding="5dp">
<TextView
android:id="#+id/lblVoterLastName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Suarez Garcia de la Serna"
android:textAppearance="?android:attr/textAppearanceMedium" />
<TextView
android:id="#+id/lblVoterName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="José Carlos"
android:textAppearance="?android:attr/textAppearanceMedium" />
<TextView
android:id="#+id/lblDni"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="44950962S"
android:textAppearance="?android:attr/textAppearanceMedium" />
</LinearLayout>
<RelativeLayout
android:id="#+id/lytCanVote"
android:layout_width="70dp"
android:layout_height="70dp"
android:layout_alignParentRight="true"
android:background="#color/yellowItemList"
android:minHeight="30dp"
android:minWidth="30dp">
<ImageView
android:id="#+id/imgVote"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:src="#drawable/flecha" />
</RelativeLayout>
<RelativeLayout
android:id="#+id/lytVoted"
android:layout_width="70dp"
android:layout_height="70dp"
android:layout_alignParentRight="true"
android:background="#color/grrenAcceptList"
android:minHeight="30dp"
android:minWidth="30dp"
android:visibility="gone">
<ImageView
android:id="#+id/imgAccept"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:src="#drawable/aceptar"
/>
</RelativeLayout>
<RelativeLayout
android:layout_width="70dp"
android:layout_height="70dp"
android:minHeight="30dp"
android:minWidth="30dp"
android:background="#color/redD3"
android:id="#+id/lytUndo"
android:layout_alignParentRight="true"
android:visibility="gone">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/imgUndo"
android:layout_centerVertical="true"
android:layout_centerHorizontal="true"
android:src="#drawable/undo"/>
</RelativeLayout>
</RelativeLayout>
You need to follow below Idea
1) this line of code mConverView = converView; doesn't makes sense. directly use converView(View from getView param). Remove mConvertView from the adapter.
2) Add some mechanism which can tell you which row is clicked and save that variable.
Example:- Have an boolean Array of size Rows.size . and set them in onClick.
Boolean[] array = new Boolean[getSize()];
in onClick that you already have in your getview set this.
public void onClick(View v) {
array[position] = !array[position];
viewHolder.lytUndo.setVisibility(View.VISIBLE);
//You do not need to call notifyDatasetChange.
3) in getView(), when you are setting data in to row items/or just before onClick. have a check like below.
if(array[position])// this will tell you if you need to show or hid lytUndo thing
viewHolder.lytUndo.setVisibility(View.VISIBLE); // Show it
else
viewHolder.lytUndo.setVisibility(View.GONE); // hide it or do whatever you want
You might need to set some params as final
I have written this as simple as possible, comment back with your result.
I have a listview and custom adapter extending SingleTypeAdapter for it. The listview contains textview(s). Whenever the number value in the textviews are changed the text color should also change. Eg. if textview change to unsigned number the color should be red otherwise yellow. How can I do that if I want best performance ?
I'm only interested in changing the color between red and white for aplied only to 3 viewtexts fields (change, percentChange, price). How do I do that ?
My adapter:
/**
* Adapter to display a list of stock quotes
*/
public class StockListAdapter extends SingleTypeAdapter<CurrentStock> {
private static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("MMMM dd");
/**
* #param inflater
* #param items
*/
public StockListAdapter(LayoutInflater inflater, List<CurrentStock> items) {
super(inflater, R.layout.stock_quote_list_item);
setItems(items);
}
/**
* #param inflater
*/
public StockListAdapter(LayoutInflater inflater) {
this(inflater, null);
}
/*#Override
public long getItemId(final int position) {
final String id = getItem(position).getObjectId();
return !TextUtils.isEmpty(id) ? id.hashCode() : super
.getItemId(position);
}*/
#Override
protected int[] getChildViewIds() {
return new int[] { R.id.symbol, R.id.exchange, R.id.price, R.id.companyName, R.id.change, R.id.percentChange };
}
#Override
protected void update(int position, CurrentStock currentStock) {
setText(0, currentStock.getSymbol());
setText(1, currentStock.getExchange());
setText(2, currentStock.getPrice().toString());
setText(3, currentStock.getCompanyName());
setText(4, currentStock.getChange().toString());
setText(5, currentStock.getPercentChange());
}
}
And the xml file for the list:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="5dp"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:paddingTop="5dp">
<TextView
android:id="#+id/companyName"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:singleLine="true"
android:textAppearance="?android:attr/textAppearanceMedium"
android:textColor="#color/table_text_selector"/>
<TextView
android:id="#+id/exchange"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:textAppearance="?android:attr/textAppearanceSmall"
android:textColor="#color/table_text_light_selector"
android:layout_below="#id/companyName"/>
<TextView
android:id="#+id/symbol"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:textAppearance="?android:attr/textAppearanceSmall"
android:textColor="#color/table_text_light_selector"
android:layout_below="#id/companyName"
android:layout_toLeftOf="#id/exchange"/>
<TextView
android:id="#+id/price"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:singleLine="true"
android:ellipsize="end"
android:textAppearance="?android:attr/textAppearanceMedium"
android:textColor="#color/table_text_selector"
android:layout_alignParentRight="true"/>
<TextView
android:id="#+id/change"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:textAppearance="?android:attr/textAppearanceSmall"
android:textColor="#color/table_stock_change_text"
android:layout_alignParentRight="true"
android:layout_below="#id/price"/>
<TextView
android:id="#+id/percentChange"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:textAppearance="?android:attr/textAppearanceSmall"
android:textColor="#color/table_stock_change_text"
android:layout_alignBaseline="#id/change"
android:layout_alignBottom="#id/change"
android:layout_toLeftOf="#id/change"
android:layout_marginRight="5dp"/>
</RelativeLayout>
EDIT: The code in getView will be even easier and will not get into trouble with parsing text to numbers. See the new code snippet.
In your StockListAdapter add the getView() method to override the behaviour, when a new stock item is shown.
#Override
public View getView(int position, View convertView, ViewGroup parent) {
View line = super.getView(position, convertView, parent);
// Set price, change and %change to red/white
((TextView) line.findViewById(R.id.price)).setTextColor((currentStock.getPrice() < 0d)? 0xFFFF0000:0xFFFFFFFF);
((TextView) line.findViewById(R.id.change)).setTextColor((currentStock.getChange() < 0d)? 0xFFFF0000:0xFFFFFFFF);
((TextView) line.findViewById(R.id.percentChange)).setTextColor((currentStock.getPercentChange() < 0d)? 0xFFFF0000:0xFFFFFFFF);
}
Some remarks:
Best performance is relative. With this solution the checks and settings are only done as often as necessary. From this point of view it is the most efficient solution.