In order to make an app feel fast, it's important that the user sees something immediately when the app launches. I still see many apps that take several seconds to show anything, and it makes me wonder if the developer simply don't know how to achieve this instant gratification. Therefore I've decided to write a small post explaining how to get this done. If your app needs a lighting fast splash screen then this is for you.
The git repo is available here.
You can install the example here.
Do we need a splash screen?
Some of you might be thinking: If you're so slow that you need a splash screen you're doing it wrong! I would normally agree, but there are two reasons why I think it's better to have a splash screen nonetheless. Firstly, inflating a layout on Android is slow, so no matter what you do there will be a delay before the user sees it. Secondly, the main activity often does a lot of stuff, so it is hard to keep it lean.
It's all in the theme
The splash activity is the first activity to be launched. It shows the splash screen and then, after a short delay, it starts the main activity and finishes. The splash activity has no actual content view, and the reason for this is that it takes too long to inflate even the simplest layout. Instead the splash activity uses a custom theme which defines a default windows background drawable. We set the custom theme in the manifest.
A responsive splash Drawable
A splash screen typically consists of a background and some logos. To make a single drawable that works well across different resolutions and PPIs you need to use the LayerDrawable. The LayerDrawable is a stack of several drawables on top of each other. The stacked drawables can be of different types and can be positioned individually, and you can choose if they are scaled or not.
In my example drawable I use three bitmaps. The first one is a tiled background, the second is the product logo which is positioned a little bit above the middle, and the third one is the company logo positioned in the bottom.
Transitions and progress bar
To make the transition from the splash activity to the main activity smooth I suggest that you override the animation between them. I also suggest that you re-use elements in the splash drawable in the main activity. For example, you can re-use a header or footer. This ties the two activities more together.
If you want to display a progressbar inside the splash activity, then you can add it to the (currently) empty splash layout. It won't inflate and be shown immediately like the background, but it will still be fairly snappy.
The good and the bad
If you want a slightly worse example of splash screen usage, then try out LinkedIn. It has a very nice splash screen, but it is not shown immediately and it shows a solid white color before the splash screen appears. This happens because they have a white background in their theme, and another in their splash layout. Another example is Kindle. They have correctly set the windowBackground, but they have the Kindle logo as part of a layout - so the logo appears slightly after the background of the splash because it needs to be inflated.
If you want to see a "good" example of what happens when you don't use a splash screen at all, then try out YouTube. If you do a cold start of YouTube it takes several seconds before anything is displayed. On my S3 it takes around 3 seconds. It makes you wonder if the phone registered the tap at all.
Can we do even better?
It seems to be possible to change the window background drawable at runtime. So one idea I've been considering is merging the splash activity into the main activity. The main activity could start out with a custom window background that shows the splash on startup, and have the main layout invisible. It could show a spinning progressbar until it's all done and inflated, and then change the window background and set the main layout to visible. Leave any comments or ideas here or on Twitter / @snowpong.