A modern Android application is hard to imagine without image loaders. They take over the rough work of loading asynchronously, processing errors, displaying placeholders, caching, and transforming pictures. Process automatization exempts the developer from the need to “reinvent the wheel”, giving an opportunity to focus on writing business logic instead of boilerplate code. As of 2021, Picasso, Glide, and Fresco libraries are the most commonly used in Android projects.

Every Android developer usually has one go-to choice. This is our take on helping to identify the best option for you.

from Square is built with the idea of bringing maximum simplicity and clarity to work. These goals are reflected in the ability to keep the apk file small – Picasso adds only 121 Kb and 849 of its methods to the project. There are two sides to every coin, and this limited space adversely affects functionality, which only covers basic operations with images. All library documentation fits easily on one web page.

from Bump Tech is built on different principles: powerful functionality and a rich arsenal for managing images. Therefore, Glide increases application sizes by at least 440 Kb and 2678 methods. Yet, in return, the developer gets a flexible and user-friendly library for asynchronously loading pictures.

from Facebook puts emphasis on productivity and careful use of operating system resources. For instance, offering a rather unusual opportunity for developers to use a special SimpleDraweeView to display images.

Now is time to demarcate different ways of adding interactivity to image display with Picasso, Glide, and Fresco. This article will cover three areas: the fade effect, progress bar display during loading, and image rotation after loading is finished.

Fade Effect

In Picasso, animation support is not its most robust feature, and in most cases, users need to add the animation effect code themselves. However, the native fade is already implemented. All images that are not loaded from RAM appear with this animation. It is impossible to influence its duration or other characteristics. The only option is to enable/disable the effect.

Glide 4 makes it possible to define fade using the transition() function. It can take as an argument an instance of the DrawableTransitionOptions class, which defines the parameters for switching to a new image. In particular, Glide allows you to set the transition time. In the example below, we set the fade effect time to 5 seconds.

It should also be taken into account that fade in Glide has 2 modifications: cross fades disabled or enabled. In the first mode, a new image gradually appears on top of the old one. This greatly saves resources, but it will be a problem if the new image has transparent pixels or less size than the old one. In the latter case, 2 animations are processed coherently: first, the old image gradually disappears, followed by the gradual display of a new one. This gives a beautiful effect but requires a lot of resources of the OS. On large lists, cross fade can be a real problem. You can enable/disable it using the transition settings.

If desired, Glide can define other animations when switching to a new image. Alternatively, a new picture can go left or enlarge from small to original size. To implement this approach, you need to describe the animation in an xml file, create an instance of the GenericTransitionOptions class with it as an argument to the constructor function, and add it to the transition() function.

This animation describes the transition to the left.

Managing the fade with Fresco is rather effortless compared to other libraries. This can be done as in the xml layout …

… as well as in the Activity / Fragment code.

At the same time, Fresco only supports an “always-on” cross fade option, which can cause more resource consumption by the application.

Loading Progress Bars

When downloading large images or in cases of an unstable internet connection, a progress bar may come in handy: either infinite or displaying the download status.
When using Picasso, you can only implement the first – a less demanding option. It can be created by either using the placeholder() function or by overriding the Target class.
In the first case, we create an animation in xml.

Then just add it as a placeholder.

In the second method, we add a progress bar to the layout on top of the ImageView, and then create our own class that will control the loading of the image.

Its use is extremely simple: create an instance of ProgressTarget with the necessary links to ImageView and ProgressBar, use it as an argument into() function. The final step is to add the ProgressTarget instance as a tag to the ImageView to protect it from the garbage collector.

Glide offers a more comprehensive approach to creating progress bars. The approach is the same as in Picasso:

  1. add animation to the placeholder function (as an option – use a gif image instead of an xml animation);
  2. extend the RequestListener class.

Also, the flexibility of the settings of this library allows you to get the loading status of the image and display not just an animated plug but more informative content. To do this, you need to override the basic settings in GlideModule. The most high-quality version of such a solution was proposed by Róbert Papp in his OkHttpProgressGlideModule.

Without a doubt, Fresco provides the easiest way to solve the progress bar problem. To create an endless progress bar, it is required to add a line to the xml layout…

…or do it from Activity / Fragment code

Adding a download indicator also does not require much effort. Simply create and customize ProgressDrawable if necessary.

Image Rotation

Adding animation after loading the image is a rare but quite possible option. Without further ado, let’s dive into the implementation specifics for each of the 3 libraries.

Picasso has a Callback class that allows you to execute the necessary logic after loading the image. To apply animation, we need to:

  1. determine the animation we need in xml-format,
  2. load it into Activity / Fragment,
  3. create a Callback object,
  4. put the animation reproduction code in it,
  5. add this object as an argument to the function into().
Step 1.

Step 2.

Steps 3 and 4.

Step 5.

In Glide, you can use the listener() function to reproduce a similar scenario, which takes an object of the RequestListener class as an argument.

In Fresco, the construction of the final animation looks a little different. In addition to creating and loading animation code, you must also create 2 objects: BaseControllerListener (responds to the loading state of the image) and DraweeController (controls requests and returns). The overall result will be identical to the previous examples with Picasso and Glide.

Wrapping up

To wrap up the abovesaid here is a comparative table of the three libraries:

Criterion
Fade effect support Out of the box Out of the box Out of the box
Fade effect control Enable/disable option Adjust the duration, cross fade approach, define different animations for the transition between pictures Enable/disable, adjust the duration
Progress bars support None. A separate progress view required None. A separate progress view required/redefine GlideModule Available. Possible to create different types of progress bars both in the xml-layout and in the Activity / Fragment.
Creation of a progress bar with percents Impossible Supported when using the OkHttp library. A need to override GlideModule Supported by the library
The mechanism for displaying the final animation Callback RequestListener BaseControllerListener
Fade effect support From the box
Fade effect control enable/disable option
Progress bars support None. A separate progress view required
Creation of a progress bar with percents Impossible
The mechanism for displaying the final animation Callback
Fade effect support From the box
Fade effect control Adjust the duration, cross fade approach, define different animations for the transition between pictures
Progress bars support None. A separate progress view required/redefine GlideModule
Creation of a progress bar with percents Supported when using the OkHttp library. A need to override GlideModule
The mechanism for displaying the final animation RequestListener
Fade effect support From the box
Fade effect control Enable/disable, adjust the duration
Progress bars support Available. Possible to create different types of progress bars both in the xml-layout and in the Activity / Fragment.
Creation of a progress bar with percents Supported by the library
The mechanism for displaying the final animation BaseControllerListener

Thus, you can add the option to display animations in all popular image downloaders for Android apps. The image manipulation libraries we’ve discussed above may be succinctly described by the following benefits:

  • Glide provides the best functionality for managing transition effects
  • Fresco has a good API for creating and customizing progress bars
  • Picasso is easy to use even for entry-level specialists

The mechanisms for displaying the final animation in all three libraries are similar and give the same result.