Entendendo RecyclerView de Uma Vez Por Todas
Ana Laura
Posted on December 4, 2023
E aí, cês tão bem?
Nos últimos dias, tenho me dedicado a estudar Android e me deparei com o seguinte desafio: entender o RecyclerView
.
Então, este artigo é para você que não está entendendo muito bem como isso funciona e eu, como uma boa amante de formas diferentes de explicar coisas complexas, cá estou.
Usando RecyclerView para organizar uma festa 🥳
Para te ajudar a entender, vou precisar que você comece imaginando que vamos dar uma festa de comidas típicas do meu estado, Minas Gerais, e para isso, precisamos definir algumas coisas. Saiba que o local da festa já foi escolhido.
Precisamos decidir como organizar as mesas e servir os pratos típicos. Para isso, pensei em nos organizarmos da seguinte forma:
- Precisamos definir no espaço principal onde iremos organizar as mesas e cadeiras para nossos convidados. Temos que distribuir tudo perfeitamente para que a festa seja agradável e todos possam aproveitar.
- Temos um cardápio com todos os pratos que queremos servir. Vamos precisar de um chef/assistente para nos ajudar a decidir quais pratos do cardápio incluir na festa e também ajudar a organizá-los nos suportes adequados. Se decidirmos adicionar um novo prato ao cardápio, nosso Chef nos ajuda a garantir que tenhamos um suporte certo para esse prato. Ele vai gerenciar essa relação entre o cardápio e os suportes, facilitando a escolha e exibição dos pratos na festa.
- Agora, pense nos pratos típicos que queremos servir. Vamos precisar de um suporte para cada prato. Cada suporte será designado para segurar um prato específico, garantindo que quando decidirmos servir algo, já temos um lugar definido para isso. Sem o suporte, teríamos que procurar constantemente onde colocar ou onde está cada prato na mesa, e isso deixaria o atendimento aos convidados menos fluído.
- Pensar na disposição das mesas. Precisamos contratar um planejador de festas. Ele vai nos ajudar a decidir se queremos organizar as mesas em fileiras, círculos ou qualquer outra forma que torne a festa mais aconchegante. Se decidirmos que queremos mesas em círculo, o planejador organiza automaticamente as mesas dessa forma. Ele ajuda a criar o layout ideal para que todos os convidados possam aproveitar a festa da melhor maneira possível.
Resumindo, temos que:
- Definir o espaço principal da festa;
- Suporte especial para cada prato;
- Assistente que organiza o cardápio nos suportes;
- Planejador que decide como organizar as mesas.
E agora você deve estar pensando, mas o que isso tem a ver com RecyclerView?
Festas e RecyclerView, acredito eu, que não tenham muitas coisas em comum. Ouso dizer que são até opostos demais 😅, mas vamos entender um pouco mais onde quero chegar com essa comparação:
O RecyclerView
será o nosso espaço principal da festa, o ViewHolder
é o suporte especial para cada prato, o Adapter
é o assistente que organiza o cardápio nos suportes, e o LayoutManager
é o planejador que decide como organizar as mesas. Juntos, eles tornam a festa organizada e garantem que todos desfrutem da experiência.
Agora que entendemos um pouco mais sobre o que é o que, vamos para o código!
Código e um pouco de teoria 💻
O RecyclerView é tipo um mestre da reciclagem na tela do seu app. Sabe quando você olha para uma lista enorme no celular e pensa "poxa, será que precisava carregar tudo de uma vez?" - é aí que o RecyclerView entra.
Imagina que você está criando uma lista que não para de crescer, tipo uma lista de mensagens de chat. O RecyclerView é como o chefão dessa operação. Ele garante que só os itens que estão aparecendo na tela sejam criados, economizando bateria e tornando tudo mais rápido.
A equipe do RecyclerView inclui alguns membros importantes como já falamos anteriormente:
- RecyclerView: Funciona como o componente visual responsável por posicionar e exibir a lista na tela.
- ViewHolder: Serve como a referência para cada item presente na lista, desempenhando um papel crucial na reciclagem de componentes.
- Adapter: Responsável por mapear os dados do modelo para cada item exibido na lista, garantindo uma conexão eficiente entre os dados e a interface.
- LayoutManager: É o componente encarregado de gerenciar a disposição dos elementos na RecyclerView, proporcionando controle sobre o layout da lista.
Começamos criando nosso espaço principal, ou seja, o RecyclerView
. Podemos adicioná-lo diretamente no XML ou pelo editor de layout:
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recyclerView"
android:layout_width="match_parent"
android:layout_height="match_parent" />
Agora podemos buscá-lo no nosso código Kotlin:
val recyclerView: RecyclerView = findViewById(R.id.recyclerView)
E já ta pronto? Ainda não!
Primeiro vamos precisar vincular nosso RecyclerView
a um LayoutManager
, e depois:
- Vamos precisar de um conjunto de dados, depois precisamos;
- Vincular o conjunto de dados a uma representação visual com o
ViewHolder
e, por fim;. - Vincular este dados ao
RecyclerView
utilizando umAdapter
;
O LayoutManager é o cara responsável por organizar os itens visuais dentro do nosso RecyclerView
, definindo também o critério de quando os itens devem ser "reciclados".
Para começar vamos usar o LinearLayoutManager
, para listas verticais e simples.
recyclerView.layoutManager = LinearLayoutManager(this)
Agora, vamos focar nos itens da nossa lista!
Vou criar um conjunto de dados de comidas. Então, primeiro, criamos a classe Food
. Lembrando que esta classe será um modelo de dados e para isso precisamos criá-la como uma data class.
data class Food(val name: String, val chef: String)
Depois temos que criar uma lista usando nosso modelo:
val FoodList = listOf(
Food("Feijão tropeiro", "Ana Laura"),
Food("Frango caipira", "Julio"),
Food("Pamonha", "Gabriel"),
)
Agora, vamos para a parte de vincular o conjunto de dados a uma representação visual com o ViewHolder.
Os ViewHolders
atuam como um cache para elementos visuais, armazenando referências às views
no layout para otimizar a atualização da interface gráfica. (Lembre-se que estamos falando de dispositivos móveis, ou seja a capacidade é muito menor que de um computador)
São elementos que serão exibidos, exigindo a criação de uma classe ViewHolder
que estende RecyclerView.ViewHolder
. Esta classe recebe um parâmetro por padrão que é o itemView
e também deve ter um método "bind", responsável por vincular dados, associando elementos visuais aos itens do conjunto de dados.
class FoodViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
fun bind(food: Food) {
itemView.findViewById<TextView>(R.id.foodName).text = food.name
itemView.findViewById<TextView>(R.id.foodChef).text = food.chef
}
}
Ah, perceba que ali a gente já selecionou esses dois ID's foodName
e foodChef
, mas ainda não os criamos no nosso XML. Vamos conversar sobre isso:
Agora, o que precisamos fazer é criar o layout do nosso ViewHolder
, ou seja, qual será o layout de cada item do nosso RecyclerView
.
Este layout é criado da mesma forma que criamos qualquer outra Activity
, criando um xml de layout com o nome de food_item.xml
.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="10dp">
<TextView android:id="@+id/foodName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="20sp"
android:textStyle="bold" />
<TextView android:id="@+id/foodChef"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="15sp" />
</LinearLayout>
Agora que estabelecemos nosso ViewHolder
, avançamos para a construção do Adapter
. Nesse processo, vamos sobrescrever os métodos necessários para associar os dados do tipo Food
ao nosso layout.
Imagine o Adapter
como um intermediário que conecta nossos dados de comida ao layout.
Para começar, criamos a classe FoodAdapter
, que recebe uma lista de objetos Food
e estende a classe RecyclerView.Adapter<FoodViewHolder>
.
Esta classe é como um organizador que recebe uma lista de comidas, que chamamos de "conjunto de dados", e ela é especializada para trabalhar com o nosso ViewHolder
de comidas, o FoodViewHolder
. É basicamente uma maneira de dizer ao sistema como os dados (comidas) devem ser exibidos no layout.
class FoodAdapter(private val foods: List<Food>) : RecyclerView.Adapter<FoodViewHolder>() {
}
Antes da gente continuar, preciso te explicar o que é o onCreateViewHolder()
: Este método é acionado durante a criação do ViewHolder
e é responsável por gerar os elementos visuais para cada item da lista.
O termo utilizado para descrever esse processo é "Inflate".
Em outras palavras, o método realiza a criação visual de cada elemento da lista, preparando-os para serem exibidos no RecyclerView
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): FoodViewHolder {
/*estamos criando um Inflater, e gerando um inflate, que é o método que cria os elementos, tendo como primeiro parâmetro o layout do elemento que deve ser replicado. Em nosso caso, o food_item */*
val view = LayoutInflater.from(parent.context).inflate(R.layout.food_item, parent, false)
return FoodViewHolder(view)
}
👀ps: isso será um método da classe FoodAdapter
Agora, precisamos sobrescrever o método de vínculo onBindViewHolder()
. Ele recebe como parâmetro o nosso ViewHolder
de comidas e chama o nosso método bind()
para cada um de nossos elementos de lista. O método bind
é uma convenção usada para associar os dados de um item específico do conjunto de dados ao ViewHolder
correspondente.
override fun onBindViewHolder(holder: FoodViewHolder, position: Int) {
val food = foods[position]
holder.bind(food)
}
👀ps: Lembra que lá na nossa classe FoodViewHolder
tem um método bind, o que será que ele faz mesmo? xD
A classe FoodAdapter
herda de RecyclerView.Adapter
e implementa alguns métodos abstratos necessários, como getItemCount()
que retorna a quantidade de itens.
override fun getItemCount(): Int {
return foods.size
}
Agora que já fizemos tudo isso, podemos vincular o Adapter
ao RecyclerView
que criamos lá atrás:
// essa variável aqui foi criada lá atrás
val recyclerView: RecyclerView = findViewById(R.id.recyclerView)
//criando o Adapter a partir da nossa lista de comidas
val adapter = FoodAdapter(foodList)
//vinculando o adapter ao RecyclerView
recyclerView.adapter = adapter
E fim, temos uma lista criada 🥰
Eu criei um repositório no github com o código e com um desenho não muito bom que eu fiz pra ajudar entender.
Se você leu até o final reage com um 💟 se não, não precisa reagir :(.
bjs bjs e até a próxima
Posted on December 4, 2023
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.