Information is being consumed more on mobile devices than desktop computers. Most of all people produce and consume a lot of images.

As Android developers, we need to make the process of loading images more efficient and easy to maintain. And this post gives a brief description of the top Android libraries when it comes to loading images from the Internet.



This was the first library that i felt in love with. Before using it, the only way I knew to load images from the Internet was using async tasks. I was really surprised by its power and simplicity.

For example, this is what it took to load an image using an async task,

private class DownloadImageTask extends AsyncTask<String, Void, Bitmap> {
  ImageView myImageView;

  public DownloadImageTask(ImageView bmImage) {
      this.myImageView = myImageView;

  protected Bitmap doInBackground(String... urls) {
      String urldisplay = urls[0];
      Bitmap bitmap = null;
      try {
        InputStream in = new;
        bitmap = BitmapFactory.decodeStream(in);
      } catch (Exception e) {
          Log.e("Error", e.getMessage());
      return bitmap;

  protected void onPostExecute(Bitmap result) {

By comparison, here is the equivalent task with Picasso,

  .resize(50, 50)

In addition Picasso has really cool features. It loads images from URLs or in-app resources, applies transformations, it lets you create custom transformations, it maintains a cache of images. It also handles automatic cancellation, and manages error and placeholder images.

And you do all of this with only one line of code.



This library is recommended by Google. They use it in many of their “official” apps (e.g., Android Camera, and Google I/O 2014).

Glide behaves similarly to Picasso. It loads images from URLs, apply transforms, and you can create custom transforms, and it also maintains a cache.

Like Picasso, you can accomplish most of these feats with one line of code. For example,


Unlike Picasso, Glide does not save the original image. It applies the transforms and then it saves to cache. The advantage is that if you use an image with a single transform, the cache will be a lot smaller this way. Also, since it saves the transformed image, it can serve images a lot faster, directly from cache.

Glide supports animated GIFs. I know they are not the best choice for mobile apps but it helps if you need to use them (e.g., LOLZ cat memes).

Glide can decode local videos to still images. This comes in handy when you need to create thumbnails.

I found that in some cases Glide leaves a phantom blur while running animated GIFs. That’s when I decided to look for an alternative.



This may be the newest competitor to Picasso and Glide. Fresco is a library from Facebook. Among other places, they use it in their mobile apps. I personally really like it. However, I think it will work better for new projects.

Fresco does not use ImageView, it uses Drawees, an MVC-like framework for the display of images.

So, if you are starting a new product or project from scratch Fresco is the way to go. Otherwise, you’ll be facing a lot of refactoring of your layout, plus the changes you’ll have to make to your existing apps.

For example, this is how to load an image with Fresco,

Uri uri = Uri.parse(url);
SimpleDraweeView draweeView = (SimpleDraweeView) findViewById(;

Like the other libraries, Fresco handles static images, GIFs, image transforms, and in-memory cache. It uses the NDK for older versions of Android to ensure that you have plenty memory to handle images.

When to Use Picasso, Glide or Fresco

My suggestion is to Use Picasso or Glide for any advanced project and Fresco for new apps.

  • Picasso for static images that you need to show in different sizes.
  • Glide for single size images, or if you need to handle GIFs or stills from video.

If you decide to move away from ImageView, then Fresco offers an alternative.
If you need to look for yet another library, this is what I recommend you look for,

  • Ease of maintainability.
  • How configurable is it? (e.g., can you control cache size?).
  • How well does it work out of the box?
  • How difficult is it to implement?

If you have any comments or questions please let us know or contact me directly via @Baniares