Search code examples
androidlistview

Android Listview repeat the items starting a specific item


At beginning, the list shows three items and when I scroll down, it creates the fourth and fifth item, but the sixth and next ones are not being created. These views mix the information with the first five items and they are repeated until the application crash with a ClassCastException.

The reason is simple, each item has a different layout and type, and I have a different ViewHolder for each one. So as the views are not being created, the ViewHolders are the same as the first five items, and when the list reach one that has a different ViewHolder it crash (it's luck that it happens at the twelfth item). I need to discover why the items are being mixing with the first ones.

This is the code of the adapter, I think it's enough:

public class PostsListAdapter extends BaseAdapter {
    private FacebookPost[] posts;
    private LayoutInflater mInflater;
    
    public PostsListAdapter (Context ctx, FacebookPost[] user_posts) {
        mInflater = (LayoutInflater)ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        posts = user_posts;
    }

    @Override
    public int getCount() {
        return posts.length;
    }

    @Override
    public Object getItem(int position) {
        return posts[position];
    }

    @Override
    public long getItemId(int position) {
        return position;
    }
    
    private abstract static class ViewHolder {
        TextView fromName;
        TextView arrow;
        TextView toName;
        TextView message;
        TextView attribution;
        
    }
    private static class VideoViewHolder extends ViewHolder {
        TextView name;
        TextView caption;
        TextView description;
        ImageView icon;
    }
    private static class PhotoViewHolder extends ViewHolder {
    }
    private static class LinkViewHolder extends ViewHolder {
    }
    private static class StatusViewHolder extends ViewHolder {
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder;
        Log.d("POSITION",""+position);
        if(convertView == null) {
            switch(posts[position].getType()) {
                case FacebookPost.VIDEO:
                    Log.d(""+position,"VIDEO");
                    convertView = mInflater.inflate(R.layout.post_list_item_video, parent, false);
                    holder = new VideoViewHolder();
                    holder.fromName = (TextView)convertView.findViewById(R.id.post_list_item_video_from_name);
                    holder.arrow = (TextView)convertView.findViewById(R.id.post_list_item_video_arrow);
                    holder.toName = (TextView)convertView.findViewById(R.id.post_list_item_video_to_name);
                    holder.message = (TextView)convertView.findViewById(R.id.post_list_item_video_message);
                    ((VideoViewHolder)holder).name = (TextView)convertView.findViewById(R.id.post_list_item_video_name);
                    ((VideoViewHolder)holder).caption = (TextView)convertView.findViewById(R.id.post_list_item_video_caption);
                    ((VideoViewHolder)holder).description = (TextView)convertView.findViewById(R.id.post_list_item_video_description);
                    break;
                case FacebookPost.LINK:
                    Log.d(""+position,"LINK");
                    convertView = mInflater.inflate(R.layout.post_list_item_link, parent, false);
                    holder = new LinkViewHolder();
                    holder.fromName = (TextView)convertView.findViewById(R.id.post_list_item_link_from_name);
                    holder.arrow = (TextView)convertView.findViewById(R.id.post_list_item_link_arrow);
                    holder.toName = (TextView)convertView.findViewById(R.id.post_list_item_link_to_name);
                    holder.message = (TextView)convertView.findViewById(R.id.post_list_item_link_message);
                    break;
                case FacebookPost.STATUS:
                    Log.d(""+position,"STATUS");
                    convertView = mInflater.inflate(R.layout.post_list_item_status, parent, false);
                    holder = new StatusViewHolder();
                    holder.fromName = (TextView)convertView.findViewById(R.id.post_list_item_status_from_name);
                    holder.arrow = (TextView)convertView.findViewById(R.id.post_list_item_status_arrow);
                    holder.toName = (TextView)convertView.findViewById(R.id.post_list_item_status_to_name);
                    holder.message = (TextView)convertView.findViewById(R.id.post_list_item_status_message);
                    break;
                case FacebookPost.PHOTO:
                    Log.d(""+position,"PHOTO");
                    convertView = mInflater.inflate(R.layout.post_list_item_photo, parent, false);
                    holder = new PhotoViewHolder();
                    holder.fromName = (TextView)convertView.findViewById(R.id.post_list_item_photo_from_name);
                    holder.arrow = (TextView)convertView.findViewById(R.id.post_list_item_photo_arrow);
                    holder.toName = (TextView)convertView.findViewById(R.id.post_list_item_photo_to_name);
                    holder.message = (TextView)convertView.findViewById(R.id.post_list_item_photo_message);
                    break;
                default:
                    holder=null;
                    break;
            }
            convertView.setTag(holder);
        }
        else {
            holder = (ViewHolder)convertView.getTag();
        }

        Spanned text = Html.fromHtml(posts[position].getFrom().getName());
        holder.fromName.setText(text);

        if(posts[position].getTo() != null)
            text = Html.fromHtml(posts[position].getTo()[0].getName());
        else
            text=null;
        if(text==null) {
            holder.arrow.setVisibility(View.GONE);
            holder.toName.setVisibility(View.GONE);
        } else
            holder.toName.setText(text);

        text = Html.fromHtml(posts[position].getMessage());
        holder.message.setText(text);
        
        switch(posts[position].getType()) {
            case FacebookPost.VIDEO:
                text = Html.fromHtml(((FacebookVideoPost)posts[position]).getCaption());
                Log.d("CAST: "+position,holder.getClass().getName());
                ((VideoViewHolder)holder).caption.setText(text);
                text = Html.fromHtml(((FacebookVideoPost)posts[position]).getName());
                ((VideoViewHolder)holder).name.setText(text);
                text = Html.fromHtml(((FacebookVideoPost)posts[position]).getDescription());
                ((VideoViewHolder)holder).description.setText(text);
                break;
            case FacebookPost.LINK:
                break;
            case FacebookPost.STATUS:
                Log.d("CAST: "+position,holder.getClass().getName());
                break;
            case FacebookPost.PHOTO:
                break;
        }

        return convertView;
    }
}

Solution

  • I guess you are missing getViewTypeCount