No Android 12 e versões mais recentes, a API
SplashScreen
permite que os apps sejam iniciados
com animação, incluindo um movimento no app durante a inicialização, uma tela de apresentação mostrando
o ícone e uma transição para o próprio app. Um SplashScreen
é um
Window
e,
portanto, abrange um
Activity
.
A experiência da tela de apresentação traz elementos de design padrão para cada inicialização de app, mas também é personalizável para que o app mantenha o branding exclusivo.
Além de usar a API da plataforma SplashScreen
, você também pode usar a biblioteca de compatibilidade
SplashScreen
, que une a API SplashScreen
.
Como a tela de apresentação funciona
Quando um usuário inicia um app enquanto o processo dele não está em execução (uma inicialização
a frio) ou o Activity
não é
criado (uma inicialização com estado salvo), os
seguintes eventos ocorrem:
O sistema vai mostrar a tela de apresentação usando os temas e as animações que você definir.
Quando o app estiver pronto, a tela de apresentação será dispensada e o app será exibido.
A tela de apresentação nunca é exibida durante uma inicialização a quente.
Elementos e mecânicas da tela de apresentação
Os elementos da tela de apresentação são definidos por arquivos de recursos XML no arquivo de manifesto do Android. Há versões dos modos claro e escuro para cada elemento.
Os elementos personalizáveis de uma tela de apresentação são o ícone do app, o plano de fundo do ícone e o plano de fundo da janela:
Considere os seguintes elementos, mostrados na Figura 2:
1 O ícone do app precisa ser um drawable vetorial. Ele pode ser estático ou animado. Embora as animações possam ter uma duração ilimitada, recomendamos não exceder 1.000 milissegundos. O ícone na tela de início é o padrão.
2 O plano de fundo do ícone é opcional e útil se você precisar de mais contraste entre o ícone e o segundo plano da janela. Se você usar um ícone adaptativo, o segundo plano dele será exibido se houver contraste suficiente com o segundo plano da janela.
3 Assim como nos ícones adaptativos, um terço do primeiro plano é mascarado.
4 O plano de fundo da janela consiste em uma única cor opaca. Se o plano de fundo da janela estiver definido e tiver uma cor simples, ele vai ser usado por padrão se o atributo não estiver definido.
Dimensões da tela de apresentação
O ícone da tela de apresentação usa as mesmas especificações dos ícones adaptativos, da seguinte maneira:
- Imagem da marca: precisa ter 200×80 dp.
- Ícone do app com segundo plano: precisa ter 240×240 dp e caber em um círculo de 160 dp de diâmetro.
- Ícone do app sem plano de fundo: precisa ter 288×288 dp e caber em um círculo com 192 dp de diâmetro.
Por exemplo, se o tamanho original de uma imagem for 300×300 dp, o ícone precisa caber em um círculo com um diâmetro de 200 dp. Tudo fora do círculo fica invisível (mascarado).
Animações da tela de apresentação e sequência de inicialização
A latência extra geralmente está associada à inicialização a frio de um aplicativo. Adicionar um ícone animado à tela de apresentação tem um apelo estético óbvio e proporciona uma experiência mais premium. A pesquisa com usuários mostra que o tempo de inicialização percebido é menor ao visualizar uma animação.
Uma animação de tela de apresentação é incorporada aos componentes da sequência de inicialização, conforme mostrado na Figura 4.
Animação de entrada: consiste na visualização do sistema para a tela de apresentação. Ele é controlado pelo sistema e não pode ser personalizado.
Tela de apresentação (mostrada durante a parte de "espera" da sequência): a tela de apresentação pode ser personalizada, permitindo que você forneça sua própria animação e marca do logotipo. Ele precisa atender aos requisitos descritos nesta página para funcionar corretamente.
Animação de saída: consiste na animação que oculta a tela de apresentação. Se você quiser personalizar a tela, use o
SplashScreenView
e o ícone dele. Você pode executar qualquer animação neles, com configurações de transformação, opacidade e cor. Nesse caso, remova manualmente a tela de apresentação quando a animação for concluída.
Ao executar a animação de ícones, a inicialização do app oferece a opção de pular a
sequência nos casos em que o app carregar antes. O app vai acionar onResume()
ou a tela de apresentação expira automaticamente. Portanto, confira se o movimento pode ser
pulado confortavelmente. A tela de apresentação só pode ser dispensada com onResume()
quando o app estiver estável do ponto de vista visual. Portanto, nenhum ícone de carregamento
extra é necessário. Apresentar uma interface incompleta pode ser desagradável para os usuários e
passar a impressão de imprevisibilidade ou falta de cuidado.
Requisitos para animações da tela de apresentação
A tela de apresentação precisa atender às seguintes especificações:
Defina apenas uma cor para o plano de fundo da janela, sem transparência. Os modos diurno e noturno têm suporte à biblioteca de compatibilidade
SplashScreen
.Confira se o ícone animado atende às especificações abaixo:
- Formato:o ícone precisa ser um XML de AnimatedVectorDrawable (AVD).
- Dimensões:um ícone AVD precisa ter quatro vezes o tamanho de um ícone
adaptável, da seguinte maneira:
- A área do ícone precisa ter 432 dp, ou seja, quatro vezes a área de 108 dp de um ícone adaptativo não mascarado.
- Os dois terços internos da imagem ficam visíveis no ícone na tela de início e precisam ter 288 dp. Ou seja, quatro vezes os 72 dp que compõe a área interna mascarada de um ícone adaptativo.
- Duração:recomendamos não exceder 1.000 ms em smartphones. Você pode usar um início atrasado, mas não pode ser maior que 166 ms. Se o tempo de inicialização do app for maior que 1.000 ms, considere uma animação em loop.
Estabeleça um momento adequado para dispensar a tela de apresentação, o que acontece quando o app mostra o primeiro frame. Você pode personalizar ainda mais esse recurso, conforme descrito na seção sobre como manter a tela de apresentação por períodos mais longos.
Recursos da tela de apresentação
Faça o download do exemplo de kit básico, que demonstra como criar, formatar e exportar uma animação para um AVD. Inclui o seguinte:
- Arquivo de projeto da animação do Adobe After Effects.
- Arquivo XML do AVD exportado final.
- Exemplo de GIF da animação.
Ao fazer o download desses arquivos, você aceita os Termos de Serviço do Google.
A maneira como lidamos com os dados nesse serviço está descrita na Política de Privacidade do Google.
Personalizar a tela de apresentação no app
Por padrão, SplashScreen
usará o windowBackground
do tema se
windowBackground
for de uma única cor. Para personalizar a tela de apresentação, adicione
atributos ao tema do app.
É possível personalizar a tela de apresentação do app seguindo um destes procedimentos:
Define os atributos do tema para mudar a aparência dele.
Deixe-o na tela por mais tempo.
Personalize a animação para dispensar a tela de apresentação.
Primeiros passos
A biblioteca SplashScreen
principal leva a tela de apresentação do Android 12 para todos
os dispositivos da API de nível 23 em diante. Para adicioná-lo ao projeto, adicione o seguinte snippet ao
arquivo build.gradle
:
Groovy
dependencies { implementation "androidx.core:core-splashscreen:1.0.0" }
Kotlin
dependencies { implementation("androidx.core:core-splashscreen:1.0.0") }
Definir um tema para a tela de apresentação para mudar a aparência dela
Você pode especificar os atributos abaixo no tema Activity
para personalizar
a tela de apresentação do app. Se você já tiver uma implementação de tela de apresentação
legada que use atributos como android:windowBackground
, considere
fornecer um arquivo de recurso alternativo para o Android 12 e versões mais recentes.
Use
windowSplashScreenBackground
para preencher o plano de fundo com uma única cor específica:<item name="android:windowSplashScreenBackground">@color/...</item>
Use
windowSplashScreenAnimatedIcon
para substituir o ícone no centro da janela inicial.Para apps destinados apenas ao Android 12 (nível 32 da API), faça o seguinte:
Se o objeto for animado e drawable com
AnimationDrawable
eAnimatedVectorDrawable
, definawindowSplashScreenAnimationDuration
para reproduzir a animação enquanto mostra a janela inicial. Isso não é necessário para o Android 13, porque a duração é inferida diretamente doAnimatedVectorDrawable
.<item name="android:windowSplashScreenAnimatedIcon">@drawable/...</item>
Use
windowSplashScreenAnimationDuration
para indicar a duração da animação do ícone da tela de apresentação. Definir essa opção não tem efeito no tempo real em que a tela de apresentação é mostrada, mas é possível recuperá-la ao personalizar a animação de saída da tela de apresentação usandoSplashScreenView.getIconAnimationDuration
. Consulte a seção a seguir sobre como manter a tela de apresentação na tela por períodos mais longos para saber mais.<item name="android:windowSplashScreenAnimationDuration">1000</item>
Use
windowSplashScreenIconBackgroundColor
para definir um plano de fundo por trás do ícone da tela de apresentação. Isso é útil se não houver contraste suficiente entre o plano de fundo da janela e o ícone.<item name="android:windowSplashScreenIconBackgroundColor">@color/...</item>
Você pode usar
windowSplashScreenBrandingImage
para definir a imagem que será exibida na parte de baixo da tela de apresentação. No entanto, as diretrizes de design recomendam não usar uma imagem de marca.<item name="android:windowSplashScreenBrandingImage">@drawable/...</item>
Você pode usar
windowSplashScreenBehavior
para especificar se o app sempre mostra o ícone na tela de apresentação no Android 13 e versões mais recentes. O valor padrão é 0, que mostra o ícone na tela de apresentação se a atividade de inicialização definirsplashScreenStyle
comoSPLASH_SCREEN_STYLE_ICON
ou segue o comportamento do sistema se a atividade não especificar um estilo. Se você preferir nunca mostrar uma tela de apresentação vazia e sempre quiser que o ícone animado apareça, defina esse valor comoicon_preferred
.<item name="android:windowSplashScreenBehavior">icon_preferred</item>
Manter a apresentação na tela por mais tempo
A tela de apresentação é dispensada assim que o app exibe o primeiro frame. Se você
precisar carregar uma pequena quantidade de dados, como carregar as configurações no app de um
disco local de forma assíncrona, use
ViewTreeObserver.OnPreDrawListener
para suspender o app e renderizar o primeiro frame.
Se a atividade inicial terminar antes do desenho, por exemplo, não
definir a visualização do conteúdo e terminar antes de onResume
, o listener
de pré-desenho não será necessário.
Kotlin
// Create a new event for the activity. override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) // Set the layout for the content view. setContentView(R.layout.main_activity) // Set up an OnPreDrawListener to the root view. val content: View = findViewById(android.R.id.content) content.viewTreeObserver.addOnPreDrawListener( object : ViewTreeObserver.OnPreDrawListener { override fun onPreDraw(): Boolean { // Check whether the initial data is ready. return if (viewModel.isReady) { // The content is ready. Start drawing. content.viewTreeObserver.removeOnPreDrawListener(this) true } else { // The content isn't ready. Suspend. false } } } ) }
Java
// Create a new event for the activity. @Override protected void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Set the layout for the content view. setContentView(R.layout.main_activity); // Set up an OnPreDrawListener to the root view. final View content = findViewById(android.R.id.content); content.getViewTreeObserver().addOnPreDrawListener( new ViewTreeObserver.OnPreDrawListener() { @Override public boolean onPreDraw() { // Check whether the initial data is ready. if (mViewModel.isReady()) { // The content is ready. Start drawing. content.getViewTreeObserver().removeOnPreDrawListener(this); return true; } else { // The content isn't ready. Suspend. return false; } } }); }
Personalizar a animação para dispensar a tela de apresentação
Você pode personalizar ainda mais a animação da tela de apresentação usando
Activity.getSplashScreen()
.
Kotlin
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) // ... // Add a callback that's called when the splash screen is animating to the // app content. splashScreen.setOnExitAnimationListener { splashScreenView -> // Create your custom animation. val slideUp = ObjectAnimator.ofFloat( splashScreenView, View.TRANSLATION_Y, 0f, -splashScreenView.height.toFloat() ) slideUp.interpolator = AnticipateInterpolator() slideUp.duration = 200L // Call SplashScreenView.remove at the end of your custom animation. slideUp.doOnEnd { splashScreenView.remove() } // Run your animation. slideUp.start() } }
Java
@Override protected void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); // ... // Add a callback that's called when the splash screen is animating to the // app content. getSplashScreen().setOnExitAnimationListener(splashScreenView -> { final ObjectAnimator slideUp = ObjectAnimator.ofFloat( splashScreenView, View.TRANSLATION_Y, 0f, -splashScreenView.getHeight() ); slideUp.setInterpolator(new AnticipateInterpolator()); slideUp.setDuration(200L); // Call SplashScreenView.remove at the end of your custom animation. slideUp.addListener(new AnimatorListenerAdapter() { @Override public void onAnimationEnd(Animator animation) { splashScreenView.remove(); } }); // Run your animation. slideUp.start(); }); }
No início desse callback, o
drawable vetorial animado
na tela de apresentação é iniciado. Dependendo da duração da inicialização do app, o
drawable poderá estar no meio da animação. Use
SplashScreenView.getIconAnimationStart
para saber quando a animação começou. Você pode calcular a duração restante da animação do
ícone desta maneira:
Kotlin
// Get the duration of the animated vector drawable. val animationDuration = splashScreenView.iconAnimationDuration // Get the start time of the animation. val animationStart = splashScreenView.iconAnimationStart // Calculate the remaining duration of the animation. val remainingDuration = if (animationDuration != null && animationStart != null) { (animationDuration - Duration.between(animationStart, Instant.now())) .toMillis() .coerceAtLeast(0L) } else { 0L }
Java
// Get the duration of the animated vector drawable. Duration animationDuration = splashScreenView.getIconAnimationDuration(); // Get the start time of the animation. Instant animationStart = splashScreenView.getIconAnimationStart(); // Calculate the remaining duration of the animation. long remainingDuration; if (animationDuration != null && animationStart != null) { remainingDuration = animationDuration.minus( Duration.between(animationStart, Instant.now()) ).toMillis(); remainingDuration = Math.max(remainingDuration, 0L); } else { remainingDuration = 0L; }
Outros recursos
- Migrar a implementação da tela de apresentação existente para o Android 12 e versões mais recentes
- App Now in Android (link em inglês), que mostra a implementação de uma tela de apresentação no mundo real.