A dificuldade que temos em encontrar informações atualizadas e mais organizadas sobre animações Android me motivou a escrever este artigo e espero que o conteúdo seja útil também pra você.
A ideia aqui é começarmos pelo básico para a repetição dos assuntos se tornar algo familiar ao final deste assunto.
Bora?
Você pode encontrar o projeto completo no Github por aqui.
Lembrando que sempre que quiser visualizar no código a animação, basta mudar no AndroidManifest a tela de início para aquela que você deseja visualizar melhor. Estarão separadas por part1, part2, part3, etc.
1. Criando uma animação básica Fade, Explose e Slide
Neste primeiro exemplo, veremos como ficam as animações em Android usando uma imagem do projeto. Neste caso, as 3 implementações são sobre:
- Fade
- Explose
- Slide
Basicamente, o código dentro de cada click é onde definimos nosso root que é a principal view e quais ações queremos tomar na imagem (Sumir e aparecer, em geral).
Temos no Android a classe TransitionManager para nos quebrar esse galho.
TransitionManager.beginDelayedTransition(root, Fade())
Visualizando a animação do código acima, podemos ver o comportamento de cada item: Fade, Explose, Slide.
Duas possíveis ações para ir para uma próxima tela.
- Podemos fazer via Scenes (disponibilizado pelo Android). Eu, particularmente, não acho que seja a melhor opção pois temos que colocar o método no xml para 2 arquivos de xml de view enxergarem o estado de cena que ele está, podendo também personalizar.
- Outra maneira é setando de fato uma Transição antes de criar nossa Intent para a próxima tela.
2. Criando uma Scene entre duas view de XML
Criei uma activity chamada AnimationScene1Activity para visualizarmos melhor e dentro criei 2 cenas.
lateinit var scene: Scene
lateinit var nextScene: Scene
E declarei onde estão cada xml que deve ir quando clicado.
scene = Scene.getSceneForLayout(root, R.layout.activity_animation_scene_one, this)
nextScene = Scene.getSceneForLayout(root, R.layout.activity_animation_scene_one_two, this)
Valide em qual estado está para fazer a Cena.
<p> CODE: https://gist.github.com/nicconicco/5ed6a76b3b94029ef35d0ce2e24b72f2.js</p>
No xml. Em cada click eu coloco a chamada do método:
android:onClick="changeScene"
E assim a animação padrão de entrada é a Fade.
Vamos visualizar como ficou.
Beleza, agora vamos personalizar essa animação!
Para isso precisamos criar um transition.xml
Eu nomeei o meu para my_transition.xml e o código é o seguinte:
<p> CODE: https://gist.github.com/nicconicco/e637a81e7293acc2e05866e12d6547b7.js</p>
Ali, eu seto qual imagem vai ter a animação e quais são os botões de ação. Tem o tempo para começar e quanto ela dura.
No meu changeScene adicionei o seguinte código:
<p> CODE: https://gist.github.com/nicconicco/c655e64609538fdea5a34abf0f41f370.js</p>
E passo nos dois métodos de go como segundo parâmetro:
TransitionManager.go(nextScene, transition)
…
TransitionManager.go(scene, transition)
O resultado fica assim:
Semelhante a ZoomIn, ZoomOut:
Ok! Agora vamos ver como funciona indo para outra atividade.
Podemos setar também a animação para Slide adicionando para mudar esse comportamento.
<p> CODE: https://gist.github.com/nicconicco/031ad38943aa9eded8bf13e6012133f6.js</p>
Confira o resultado:
3. Criando animação entre duas Activities.
Bom, aqui seguindo a documentação oficial vamos ter os seguintes passos:
1 — Criar um tema especificando a transição
2— Na tela que voltar, podemos setar via código a animação que desejamos.
Bora?
Criei a activity TransitionBetweenViewsActivity
Criei o tema e o código e ficou o seguinte:
<p> CODE: https://gist.github.com/nicconicco/4622dbf229dbfc35d8b941edcbff47cf.js</p>
Uso ele no meu tema principal do AndroidManifest.
Código na ação do botão:
<p> CODE: https://gist.github.com/nicconicco/6bf70175bfbee221de19acbefa3f14c6.js</p>
No meu código de volta criei 2 arquivos novos de fade_in.xml e fade_out.xml dentro do package anim (crie essa pasta)
<p> CODE: https://gist.github.com/nicconicco/23a5502ef873b17428cb11d5bc77c0b9.js</p>
O código para escrever animações do projeto se chama overridePendingTransition, assim, clicando no botão voltar podemos personalizar.
<p> CODE: https://gist.github.com/nicconicco/6fbcf86c3e182cc23f5ec88b0e1ca51c.js</p>
E o resultado:
O ponto que podemos colocar como destaque é no tema BaseAppTheme
Eu coloquei em negrito para dar destaque que ele começa com a animação android:windowEnterTransition = slide_bottom e termina sua animação windowExitTransition = explode.
Agora vamos avançar para algo mais detalhado.
4. Configurando melhor o comportamento do SLIDE
No meu primeiro exemplo faltou dizer que com a propriedade Slide, podemos definir o comportamento dela. De onde vir, se da direita para esquerda, bottom para top, etc.
Para isso, vamos adicionar mais um botão e setar o comportamento passando no construtor de onde deve vir.
O código ficou:
/**
* TransitionManager.beginDelayedTransition(root, Slide(Gravity.TOP))
* TransitionManager.beginDelayedTransition(root, Slide(Gravity.BOTTOM))
* TransitionManager.beginDelayedTransition(root, Slide(Gravity.START))
*/
TransitionManager.beginDelayedTransition(root, Slide(Gravity.END))
Veja o resultado:
5. Animando mais de uma view por vez
Agora vamos animar, mais de uma view e entender como pegar os filhos de uma view para animar cada um deles.
Criei a classe CoordinatedSlideActivity
Ao clicar no menu no canto direito, você vai fazer todas as animações da view que estiverem dentro. Para isso vamos usar o Slide indo no sentido Top.
Uma vez configurado o menu, vamos pegar nosso Root view e dentro dele, temos o método childCount que vai nos retornar quantos itens tem lá dentro.
Ai iremos pegar cada um desses elementos e fazer animações em android.
O Código ficou assim:
<p> CODE: https://gist.github.com/nicconicco/326bd79aa481894b85e95b3f6c5463f2.js</p>
Resultado disso:
Se você olhar o xml vai ver que lá dentro tem 5 ImageView`s.
6. Esticando a imagem, rotacionando e cortando com animação
Aqui, o título já nos dá uma ideia do que vamos ver.
Criei a classe ChangeAnimationActivity
E dentro do click eu configuro como quero que minha animação se comporte:
<p> CODE: https://gist.github.com/nicconicco/18ba069aa68a75e091bc70c0f5880542.js</p>
O resultado:
Não tem muito o que detalhar. Mudei a largura e altura da imagem no eixo X e Y e rotacionando ela em 30 graus. Deixei comentada a última linha, mas você pode cortar a imagem se preferir.
Pra você dar zoom na imagem, por exemplo, pode setar seu transition:
transitionSet.addTransition(ChangeImageTransform())
E setar em sua imagem:
image.scaleType = ImageView.ScaleType.CENTER
Resultado:
7. Compartilhando animações entre telas com transitionName
Vamos fazer uma animação para compartilhar um tipo de transição com nome. interessante para quando entramos no detalhe do produto. Depois mais a frente vamos fazer com listas.
As classes de referência sao: SharedAnimationActivity e SequenceAnimationActivity
Na classe Shared coloquei no evento do click o seguinte código:
<p> CODE: https://gist.github.com/nicconicco/a6961790f265ae8fb5d07065efcfad09.js</p>
Também comentei lá no BaseAppTheme como vem de padrão as animações de entrada e saída:
<!– specify enter and exit transitions –>
<!–<item name=”android:windowEnterTransition”>@android:transition/slide_top</item>–>
<!–<item name=”android:windowExitTransition”>@android:transition/slide_bottom</item>–>
Tanto na imagem de entrada como de saída do detalhe, coloquei a seguinte tag android:transitionName=”robot_android” assim ele sabe que, vou começar nessa imagem com esses ids e ir para a segunda tela com o id tal. Bastante cuidado: o id deve ser único.
E sem mais delongas, esse é o resultado:
Aqui, não falarei sobre a volta pois já discutimos em tópicos anteriores.
Listas
Colocar animações nos componentes de lista não é algo super prazeroso, concorda? Por isso, peguei alguns exemplos que encontrei na internet adaptando para os meus objetivos sem muitos problemas. Você pode fazer o mesmo em seu projeto.
Animação horizontal dando ênfase ao item central
Bom, agora vamos entrar no mundo de listas. Foquei em pesquisar exemplos reais e aqui está um tutorial que me chamou bastante atenção: Custom Android Views: Carousel RecyclerView
Nenhum segredo de implementação, com resultados bem legais para seções variadas (*coff coff Ifood*) e o código estará em animation_part7
Resultado:
Lista simples: animando em direções vários itens
Um blog que fez uma sequência de animações me chamou bastante atenção também:
Enter animation using recyclerview and layoutanimation
Ele coloca um spinner controlando a lista para mostrar os diferentes tipos de layout. Eu acrescentei uma lista lateral com vários itens para a direita como exemplo apenas.
Achei que isso se encaixa bem em alguns layouts que vemos em apps.
O resultado:
Criando uma lista semelhante ao Netflix
Explicando um pouco sobre esse componente. A ideia que vi em outros lugares é a de criar uma lista com um header por exemplo. E dentro dele outra lista na horizontal.
Existem várias maneiras de fazer isso. Em questão de performace prefiro, particularmente, usar o RecyclerView e o ListAdapterDiffUtil.
Então vamos lá. Seguindo a ideia da lista dentro de lista sabemos que vamos ter um “Pai” que vai ter seus “filhos” internos. Sendo assim, teremos 2 tipos de objetos como dito. Um Pai que tem um header e uma lista de filhos e dentro dele o filho tem as propriedades que serão escritas no detalhe do card do netflix.
Criei a classe NetflixActivity
Teremos que ter 2 adapters. Um para o Pai e outro para o Filho.
Criei com os nomes NetflixHeaderAdapter e NetflixCarouselAdapter.O Código de cada um ficou assim:
NetflixHeaderAdapter
NetflixCarouselAdapter
Adicionei também no xml um AppBarLayout para termos nosso top com uma apresentação e ela ir sumindo conforme o scroll.
O trick agora foi adicionar ao clicar fazer a animação.
<p> CODE: https://gist.github.com/nicconicco/484a2d1a8533968c32d671efd8b52bd2.js</p>
Para isso, no detalhe do produto você precisa também setar o transitionName, conforme vimos acima. Passamos por bundle extras nosso transitionName.
<p> CODE: https://gist.github.com/nicconicco/e3035558ec2629d8d76203df4b350af3.js</p>
Criei um AppBarLayout com CollapsingBar no topo para ficar algo mais real. Ela tem uma toolbar dentro e uma imagem do nosso assunto aqui.
Codando e conectando tudo o resultado ficou assim!
Conclusão
É isso! Chegamos em uma telinha bem animada, com bastante personalizações e animações em mente, agora cabe a você adaptar ao seu projeto.
Lembre-se de usar animações com responsabilidade, sem poluição.
Espero que esse artigo sobre animações em Android seja útil pra você e suas animações. Ficou com alguma dúvida ou quer sugerir algo sobre o tema pra nossa comunidade? É só deixar nos comentários!
Aproveito para compartilhar alguns cursos que considero bem úteis sobre o tema:
– https://www.udemy.com/course/the-complete-android-animations-course/learn/practice/1033362
– https://www.udemy.com/course/curso-android-material-design/learn/lecture/8262654#overview