As the title says, i encounter a problem that using a adapter to setup a listview, so that the bottom items which are outside of the screen are duplicated with top items. For example, at the top of listview, appointment 14 is the first item, but when I scroll down to the bottom, the bottom item is supposed to be other item appointment 20, but it appear as appointment 14.
and here is my code:
public class AppointmentArrayAdapter extends BaseAdapter {
ArrayList<Appointment> appointments;
Context context;
LayoutInflater inflater;
public AppointmentArrayAdapter(ArrayList<Appointment> app, Context c){
appointments=app;
context=c;
inflater = (LayoutInflater) c.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
@Override
public int getCount() {
return appointments.size();
}
@Override
public Object getItem(int position) {
return appointments.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if(convertView==null){
convertView = inflater.inflate(R.layout.appointment_list_item, parent, false);
holder = new ViewHolder();
TableLayout ll = (TableLayout) convertView.findViewById(R.id.tableLayout);
TableRow[] row = new TableRow[6];
TableRow.LayoutParams lp = new TableRow.LayoutParams(TableRow.LayoutParams.MATCH_PARENT,
TableRow.LayoutParams.WRAP_CONTENT);
for(int i=0;i<6;i++){
row[i]=new TableRow(context);
row[i].setLayoutParams(lp);
}
TextView itemId = new TextView(context);
TextView itemType = new TextView(context);
itemId.setText(""+appointments.get(position).getId());
itemType.setText(appointments.get(position).getAppointmentType().toString());
row[0].setBackgroundColor(0xFF00FF00);
row[0].addView(itemId);
row[0].addView(itemType);
TextView lable1 = new TextView(context);
TextView patient = new TextView(context);
lable1.setText("Patient: ");
String patientName = DatabaseHandler.getInstance(null).getUserById(appointments.get(position).getPatient()).getName();
patient.setText(patientName);
row[1].addView(lable1);
row[1].addView(patient);
TextView lable2 = new TextView(context);
lable2.setText("Consultant: ");
TextView consultant = new TextView(context);
String consultantName = DatabaseHandler.getInstance(null).getUserById(appointments.get(position).getConsultant()).getName();
consultant.setText(consultantName);
row[2].addView(lable2);
row[2].addView(consultant);
TextView lable3 = new TextView(context);
lable3.setText("Clinic: ");
TextView clinic = new TextView(context);
String clinicName = DatabaseHandler.getInstance(null).getUserById(appointments.get(position).getClinic()).getName();
clinic.setText(clinicName);
row[3].addView(lable3);
row[3].addView(clinic);
TextView lable4 = new TextView(context);
lable4.setText("Timeslot: ");
TextView timelot = new TextView(context);
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm");
String formattedDate = df.format(appointments.get(position).getTime());
timelot.setText(formattedDate);
row[4].addView(lable4);
row[4].addView(timelot);
for(int i=0;i<6;i++)
ll.addView(row[i]);
holder.tableLayout = ll;
convertView.setTag(holder);
}else{
holder = (ViewHolder)convertView.getTag();
}
return convertView;
}
}
class ViewHolder{
TableLayout tableLayout;
}
Android reuses the views you've created before. That's what you get when convertView is != null. So in those cases, you need to do the setText, setBackground, etc. I think the issue is that the if(convertView == null) { block should only be the first two lines that you have. Something like
if (convertView == null) {
inflate the view, create new ViewHolder
} else {
set the ViewHolder variable to the tag
}
set up the text views, background etc. in either case