AvatarWorkerTask.java

  1package eu.siacs.conversations.ui.util;
  2
  3import android.content.res.Resources;
  4import android.graphics.Bitmap;
  5import android.graphics.drawable.BitmapDrawable;
  6import android.graphics.drawable.Drawable;
  7import android.os.AsyncTask;
  8import android.support.annotation.DimenRes;
  9import android.widget.ImageView;
 10
 11import java.lang.ref.WeakReference;
 12import java.util.concurrent.RejectedExecutionException;
 13
 14import eu.siacs.conversations.entities.Account;
 15import eu.siacs.conversations.services.AvatarService;
 16import eu.siacs.conversations.ui.XmppActivity;
 17import eu.siacs.conversations.ui.adapter.AccountAdapter;
 18import eu.siacs.conversations.utils.UIHelper;
 19
 20public class AvatarWorkerTask extends AsyncTask<AvatarService.Avatarable, Void, Bitmap> {
 21    private final WeakReference<ImageView> imageViewReference;
 22    private AvatarService.Avatarable avatarable = null;
 23    private @DimenRes int size;
 24
 25    public AvatarWorkerTask(ImageView imageView, @DimenRes int size) {
 26        imageViewReference = new WeakReference<>(imageView);
 27        this.size = size;
 28    }
 29
 30    @Override
 31    protected Bitmap doInBackground(AvatarService.Avatarable... params) {
 32        this.avatarable = params[0];
 33        final XmppActivity activity = XmppActivity.find(imageViewReference);
 34        if (activity == null) {
 35            return null;
 36        }
 37        return activity.avatarService().get(avatarable, (int) activity.getResources().getDimension(size), isCancelled());
 38    }
 39
 40    @Override
 41    protected void onPostExecute(Bitmap bitmap) {
 42        if (bitmap != null && !isCancelled()) {
 43            final ImageView imageView = imageViewReference.get();
 44            if (imageView != null) {
 45                imageView.setImageBitmap(bitmap);
 46                imageView.setBackgroundColor(0x00000000);
 47            }
 48        }
 49    }
 50
 51    public static boolean cancelPotentialWork(AvatarService.Avatarable avatarable, ImageView imageView) {
 52        final AvatarWorkerTask workerTask = getBitmapWorkerTask(imageView);
 53
 54        if (workerTask != null) {
 55            final AvatarService.Avatarable old= workerTask.avatarable;
 56            if (old == null || avatarable != old) {
 57                workerTask.cancel(true);
 58            } else {
 59                return false;
 60            }
 61        }
 62        return true;
 63    }
 64
 65    public static AvatarWorkerTask getBitmapWorkerTask(ImageView imageView) {
 66        if (imageView != null) {
 67            final Drawable drawable = imageView.getDrawable();
 68            if (drawable instanceof AsyncDrawable) {
 69                final AsyncDrawable asyncDrawable = (AsyncDrawable) drawable;
 70                return asyncDrawable.getAvatarWorkerTask();
 71            }
 72        }
 73        return null;
 74    }
 75
 76    public static void loadAvatar(final AvatarService.Avatarable avatarable, final ImageView imageView, final @DimenRes int size) {
 77        if (cancelPotentialWork(avatarable, imageView)) {
 78            final XmppActivity activity = XmppActivity.find(imageView);
 79            if (activity == null) {
 80                return;
 81            }
 82            final Bitmap bm = activity.avatarService().get(avatarable, (int) activity.getResources().getDimension(size), true);
 83            if (bm != null) {
 84                cancelPotentialWork(avatarable, imageView);
 85                imageView.setImageBitmap(bm);
 86                imageView.setBackgroundColor(0x00000000);
 87            } else {
 88                imageView.setBackgroundColor(avatarable.getAvatarBackgroundColor());
 89                imageView.setImageDrawable(null);
 90                final AvatarWorkerTask task = new AvatarWorkerTask(imageView, size);
 91                final AsyncDrawable asyncDrawable = new AsyncDrawable(activity.getResources(), null, task);
 92                imageView.setImageDrawable(asyncDrawable);
 93                try {
 94                    task.execute(avatarable);
 95                } catch (final RejectedExecutionException ignored) {
 96                }
 97            }
 98        }
 99    }
100
101    static class AsyncDrawable extends BitmapDrawable {
102        private final WeakReference<AvatarWorkerTask> avatarWorkerTaskReference;
103
104        AsyncDrawable(Resources res, Bitmap bitmap, AvatarWorkerTask workerTask) {
105            super(res, bitmap);
106            avatarWorkerTaskReference = new WeakReference<>(workerTask);
107        }
108
109        AvatarWorkerTask getAvatarWorkerTask() {
110            return avatarWorkerTaskReference.get();
111        }
112    }
113}