2012-01-03 4 views
0
import java.lang.ref.SoftReference; 
import java.util.HashMap; 

import android.graphics.drawable.Drawable; 
import android.os.Handler; 
import android.os.Message; 


public class AsyncImageLoader { 
private HashMap<String, SoftReference<Drawable>> imageCache; 
HashMap<String, SoftReference<Drawable>> drawableMap = new HashMap<String, SoftReference<Drawable>>(); 


public AsyncImageLoader() { 
    //HashMap<String, SoftReference<Drawable>> drawableMap = new HashMap<String, SoftReference<Drawable>>(); 
} 

public Drawable loadDrawable(final String imageUrl, final ImageCallback imageCallback) { 

    if (drawableMap.containsKey(imageUrl)) { 
     SoftReference<Drawable> softReference = imageCache.get(imageUrl); 
     Drawable drawable = softReference.get(); 
     if (drawable != null) { 
      return drawable; 
     } 
    } 
    final Handler handler = new Handler() { 
     @Override 
     public void handleMessage(Message message) { 
      imageCallback.imageLoaded((Drawable) message.obj, imageUrl); 
     } 
    }; 

    //this is the new thread that download the image from url 
    new Thread() { 
     @Override 
     public void run() { 
      Drawable drawable = loadImageFromUrl(imageUrl); 
      imageCache.put(imageUrl, new SoftReference<Drawable>(drawable)); 
      Message message = handler.obtainMessage(0, drawable); 
      handler.sendMessage(message); 
     } 
    }.start(); 
    return null; 
} 

public static Drawable loadImageFromUrl(String url) { 
    return null; 
    // ... 
} 

public interface ImageCallback { 
    public void imageLoaded(Drawable imageDrawable, String imageUrl); 
} 

}Пытаясь понять следующее AyncImageLoader

OK, мое понимание таково:
1) Проверьте, чтобы увидеть, если изображение в кэше, если после этого вернуться вытяжке; 2) Если нет, то создайте новый обработчик для отправки сообщения в поток UI с помощью объекта Drawable как объекта, и этот обработчик не будет отправлен до тех пор, пока функция обратного вызова imageloaded не будет вызвана 3) создайте новый поток, чтобы инициировать загрузку изображения с URL-адреса ,

4) конкретно последовательность для обработчика происходит в этом порядке A) Message message = handler.obtainMessage (0, drawable); B) public void handleMessage (Message message) { imageCallback.imageLoaded ((Drawable) message.obj, imageUrl); } C) handler.sendMessage (сообщение);

Проблема у меня есть номер 4, я abit неясно, getmessage (0, drawable)? получить откуда? где источник? Как я узнаю, откуда она взялась, поток пользовательского интерфейса или другие? Таким образом, после получения этого сообщения обработчик сообщения выполнит обратный вызов. public void handleMessage (Message message) { imageCallback.imageLoaded ((Drawable) message.obj, imageUrl); }

, наконец, оно отправляет сообщение с возможностью использования в качестве полезной нагрузки. handler.sendMessage (сообщение); , но откуда я могу узнать, куда его отправить? Всегда ли он имеет конечный пункт назначения?

благодаря

ответ

3

в основном - есть две нити здесь, основной поток пользовательского интерфейса, что большая часть этого кода выполняется в, а загрузка нити определяется в нижней части.

вызов getMessage просто возвращает объект сообщения из пула, что дешевле, чем создание нового. Это аналогично конструктору в этом использовании.

Поскольку обработчик определен в потоке пользовательского интерфейса, метод handleMessage также выполняется в потоке пользовательского интерфейса. Само сообщение - это просто способ получить извлечение из потока загрузки в поток пользовательского интерфейса, а также вызвать обратный вызов, когда загрузка будет завершена.

Таким образом, в основном все, что делает этот код: если выталкиваемый существует в кеше (SoftReference), тогда верните его. В противном случае получите ссылку на обработчик и запустите поток, который загружает извлечение. Когда этот поток выполняется при загрузке, он создает сообщение и отправляет его обработчику, который по очереди вызывает imageCallback.imageLoaded и передает вновь загружаемый файл.