0

I know this forum is full with "Android doesn't display image" questions, but none of them seems to coincide with what I am experiencing.

When I use the debugger and step through my code, it works fine and the image is shown. But when I don't halt the code, it does not update the image at all, or it updates it much later.

This looks like Android isn't invalidating the view, but adding invalidate() does not help either. Any thoughts?

Here is the code:

    Picasso.with(getContext()).load(url).into(new Target() { // using Picasso to load the image

        @Override public void onPrepareLoad(Drawable placeHolderDrawable) {
        }

        @Override public void onBitmapLoaded(final Bitmap bitmap, Picasso.LoadedFrom from) {

            screenSurface.setImageBitmap(bitmap); // trying to display it, screenSurface is the ImageView
            // I tried adding screenSurface.invalidate() here but it doesn't help

        }

        @Override public void onBitmapFailed(Drawable errorDrawable) {
        }

    });

As it looks to me this is a problem with Android, not Picasso, as Picasso seems to emit the callback on the UI thread. Otherwise the image wouldn't be shown during debug either.

Oliver Hausler
  • 4,900
  • 4
  • 35
  • 70

4 Answers4

1

Your Target is getting garbage collected. See this answer for an explanation (first result from searching): https://stackoverflow.com/a/24602348

Community
  • 1
  • 1
iamstuffed
  • 74
  • 2
0

I'm not familiar with Picasso but this loader looks eerily familiar to Volley's ImageLoader.

Double check, but I imagine the Picasso.LoadedFrom param either means it's loaded from cache or from the server. Take a look here: Picasso.LoadedFrom docs

Perhaps in your code you could have something like this:

switch(Picasso.LoadedFrom.valueOf(from)) {
    case NETWORK:
        screenSurface.setImageBitmap(bitmap);
        break;
    case DISK:
        //Do something
        break;
    case MEMORY:
        //Do something
        break;
}

Or could just have a simple if(from network) {setBitmap} else {show loading image} type thing while it loads.

Hope this helps!

The Hungry Androider
  • 2,274
  • 5
  • 27
  • 52
0

Since your target is just a standard image view, I suggest using the basic into(ImageView) method:

Picasso.with(getContext()).load(url).into(screenSurface);

If you for some reason need to use a custom target, the docs suggest adding that interface to a custom view, not creating a bare Target class.

Reference.

x-code
  • 2,940
  • 1
  • 18
  • 19
0

I had a similar issue a while back , and pointed out somewhere that target was Garbage collected and no callback is triggered without a break point , i had to use a field for the target to prevent that , and everything went fine. So , create a target field

public Target target = new Target(){...}

then

Picasso.with(getContext()).load(url).into(target);
user303730
  • 384
  • 1
  • 5
  • 15