Picasso: Already downloaded images disappear while scrolling upwards in listview, loads slowly

Created on 13 Jan 2015  ·  6Comments  ·  Source: square/picasso

Hi everyone,

My listview loads Picasso images slowly. I often have wait on it to download one image, scroll a bit, and wait on it to download the next image in the listview, it doesn't work in advance.

Downloaded images also disappear when I scroll back up. It feels as if Picasso is only loading 4-5 images at a time and replacing the ones already loaded to make room. Here's (http://i.imgur.com/SvzGWLI.png) what my memory looks like right now as I scroll up and down and wait for images to load.

public class MainActivity extends Activity {
    private List<Post> myPosts = new ArrayList<Post>();
    protected String[] mBlogPostTitles;
    public static final String TAG = MainActivity.class.getSimpleName();

    ...

    private void populateListView() {
        Activity activity = MainActivity.this;

        ArrayAdapter<Post> adapter = new MyListAdapter();
        ListView list = (ListView) findViewById(R.id.postsListView);
        list.setAdapter(adapter);
        list.setOnScrollListener(new SampleScrollListener(activity));
    }

    private class MyListAdapter extends ArrayAdapter<Post>{
        public MyListAdapter() {
            super(MainActivity.this, R.layout.item_view, myPosts);
        }

        @Override
        public int getViewTypeCount() {
            return 2;
        }

        @Override
        public int getItemViewType(int position) {
            String imageURL = myPosts.get(position).getImage();
            if(imageURL == null || imageURL.isEmpty()){
                return 1; // text based
            }else{
                return 0; // image based
            }
        }

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {

            PostViewHolder holder;

            int type = getItemViewType(position);

            View itemView = convertView;

            // make sure we have a view to work with
            if (itemView == null) {
                holder = new PostViewHolder();
                if(type == 1) {
                    itemView = getLayoutInflater().inflate(R.layout.item_view, parent, false);
                }else {
                    itemView = getLayoutInflater().inflate(R.layout.image_post_view, parent, false);
                    holder.image = (ImageView) itemView.findViewById(R.id.item_image);
                }
                holder.user = (TextView) itemView.findViewById(R.id.item_txtUser);
                holder.time = (TextView) itemView.findViewById(R.id.item_txtTime);
                holder.post = (TextView) itemView.findViewById(R.id.item_txtPost);
                holder.likes = (TextView) itemView.findViewById(R.id.item_txtLikes);

                itemView.setTag(holder);
            } else {
                holder = (PostViewHolder) itemView.getTag();
            }

            //find the post to work with
            Post currentPost = myPosts.get(position);

            if(type != 1) {
                Context context = itemView.getContext();
                String imageURL = currentPost.getImage();

                Picasso.with(context).setIndicatorsEnabled(true);
                //Picasso.with(context).setLoggingEnabled(true);
                Picasso.with(context)
                        .load(imageURL)
                        .tag(context)
                        .placeholder(R.drawable.kanye8080s)
                        //.skipMemoryCache()
                        .error(R.drawable.stadiumarcadium)
                        .fit()
                        .into(holder.image);
            }
            //Username
            holder.user.setText(currentPost.getUser());

            //Time of post
            holder.time.setText("" + currentPost.getTime());

            //The actual post
            holder.post.setText(currentPost.getPost());

            //Likes for the post
            holder.likes.setText("" + currentPost.getLikes());

            return itemView;
        }
    }
    public class SampleScrollListener implements AbsListView.OnScrollListener {
        private final Context context;

        public SampleScrollListener(Context context) {
            this.context = context;
        }

        @Override
        public void onScrollStateChanged(AbsListView view, int scrollState) {
            final Picasso picasso = Picasso.with(context);
            if (scrollState == SCROLL_STATE_IDLE || scrollState == SCROLL_STATE_TOUCH_SCROLL) {
                picasso.resumeTag(context);
            } else {
                picasso.pauseTag(context);
            }
        }

        @Override
        public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount,
                             int totalItemCount) {
            // Do nothing.
        }
    }


    ...
} 

I have already posted this concern on SO (http://stackoverflow.com/questions/27771646/picasso-keeps-reloading-images-while-scrolling-upwards-in-listview-loads-slowly) but was unable to find a solution. I was wondering if you guys, as a last resort, could help me figure it out? I am already using the fit() call, so I don't think it's a resizing issue. Any help would be greatly appreciated, thanks!

Most helpful comment

rv.getRecycledViewPool().setMaxRecycledViews(0, 0);

By using this my issue resolved

All 6 comments

Are the source bitmaps too big to download? Slow network connection?

Did you try another image loading library? If you do and it works great, please let me know and I can take a look. I have a feeling this is not picassos fault.

Paste a URL that you use or a bunch of them and I will put them in the sample app.

I have the same problem on less powerful smartphones. I am using the recyclerview pattern for the list and definitely had a better cache performance with the volley library: https://github.com/mcxiaoke/android-volley

rv.getRecycledViewPool().setMaxRecycledViews(0, 0);

By using this my issue resolved

Images are reloading in the recyclerview even volley using LruCache class ?

@raj9686 will you plz tell me, where to use this line??

Just Use Glide, it solved my problem and it's easy to change.

https://guides.codepath.com/android/Displaying-Images-with-the-Glide-v3-Library

Was this page helpful?
0 / 5 - 0 ratings