Los RecyclerView al igual que los GridView y ListView, permite crear listados de ítems ya sea a través de listas o celdas; los RecyclerView pueden verse como una versión más flexible, potente y actualizada que estos y seguramente en algún momento serán el reemplazo definitivo de los mismos; la forma de funcionamiento es la misma empleada que sus predecesores como puedes ver en esta imagen:
Adapter que actúa como puente entre los datos y la vista.
Agregando la librería de soporte para trabajar con los RecyclerViews y CardView
De la misma forma que agregamos las dependencias necesarias para agregar múltiples elementos de la Librería de Soporte (en específico el FloatActionButton), es necesario agregar las dependencias para poder emplear el RecyclerView y CardView en nuestro proyecto; agrega las siguientes dependencias en el archivo build.gradle
:
compile 'com.android.support:cardview-v7:23.0.1'
compile 'com.android.support:recyclerview-v7:23.0.1'
app/build.gradle
Los CardView
El RecyclerView y los CardView forman parte de la librería de soporte; los CardView heredan de los ViewGroups más directamente de los FrameLayout y por ende es un elemento que nos permite definir muchas otros elementos dentro del mismo como por ejemplo los siguientes:
<android.support.v7.widget.CardView xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:id="@+id/card_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_margin="2dp"
card_view:cardCornerRadius="1dp">
<RelativeLayout
android:id="@+id/parent_body_rl"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#FF5722"
android:orientation="vertical"
android:padding="2dp">
<LinearLayout
android:id="@+id/parent_body_ll"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="2dp">
<LinearLayout
android:id="@+id/color_ll"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_gravity="center"
android:layout_margin="10dp"
android:background="#FF0000"
android:orientation="vertical" />
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical"
android:padding="2dp">
<TextView
android:id="@+id/name_tv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="texto 1"
android:textColor="#FFFFFF"
android:textSize="25sp" />
<TextView
android:id="@+id/description_tv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/info_text"
android:padding="10dp"
android:text="texto 2"
android:textColor="#FFFFFF"
android:textSize="15sp" />
</LinearLayout>
</LinearLayout>
</RelativeLayout>
</android.support.v7.widget.CardView>
Obteniendo el siguiente resultado:
En otras palabras, podemos emplear los CardView en conjunto con los RecyclerView; en donde el CardView define los ítems del listado.
Creando un RecyclerView
Antes que nada, necesitas agregar un elemento RecyclerView en el layout de nuestra Activity o Fragment:
<android.support.v7.widget.RecyclerView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/recycler_view"
/>
Al igual que cualquier otro elemento, para referenciar el RecyclerView anterior desde nuestra Activity empleamos el siguiente código Java:
RecyclerView recyclerView = (RecyclerView)findViewById(R.id.recycler_view);
Especificando el posicionamiento del RecyclerView con Layout Manager
A partir de aquí podemos apreciar algunos cambios con respecto al momento de crear los ListView y GridView; para definir el posicionamiento en que deseamos que renderice nuestra lista de ítems (en forma de listas o celdas):
Empleamos el siguiente código Java para que los elementos se posicionan en la lista a través de listados:
LinearLayoutManager linearLayoutManager = new LinearLayoutManager(context); recyclerView.setLayoutManager(LinearLayoutManager);
O el GridLayoutManager
para que los elementos se posicionan en la lista a través de de celdas:
GridLayoutManager gridLayoutManager = new GridLayoutManager(context); recyclerView.setLayoutManager(gridLayoutManager);
Especificando los datos y el modelo
Para mayor facilidad al momento de manipular los datos crearemos un modelo Person
para especificar una lista con nuestros datos que pasaremos posteriormente al Adapter.
public class Person {
String name;
String description;
String color;
Person(String name, String description,String color){
this.name = name;
this.description = description;
this.color = color;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
}
Nada fuera de lo común, la persona costa de un nombre, una descripción (edad, etc) y el color favorito.
Definiendo el Adapter
El Adapter que utiliza los RecyclerView son muy parecidos a los empleados por los ListView y los GridView en lo que a su estructura y comportamiento se refiere; además de esto, vamos a emplear los ViewHolder para referencias más fácilmente los elementos que nos interese de nuestro listado; la definición del Adapter a continuación:
public class ListAdapter extends RecyclerView.Adapter<ListAdapter.ViewHolder>{
private ArrayList<Person> persons;
// Provee una referencia a cada item dentro de una vista y acceder a ellos facilmente
public static class ViewHolder extends RecyclerView.ViewHolder {
// Cada uno de los elementos de mi vista
public TextView nameTextView,descriptionTextView;
public CardView cardView;
public LinearLayout colorLl;
public RelativeLayout parentBodyRl;
public ViewHolder(View v) {
super(v);
parentBodyRl = (RelativeLayout) v.findViewById(R.id.parent_body_rl);
cardView = (CardView) v.findViewById(R.id.card_view);
nameTextView = (TextView) v.findViewById(R.id.name_tv);
descriptionTextView = (TextView) v.findViewById(R.id.description_tv);
colorLl = (LinearLayout) v.findViewById(R.id.color_ll);
}
}
// Constructor
public ListAdapter(ArrayList<Person> persons) {
this.persons = persons;
}
// Create new views (invoked by the layout manager)
@Override
public ListAdapter.ViewHolder onCreateViewHolder(ViewGroup parent,
int viewType) {
// inflo la vista (vista padre)
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_adapter, parent, false);
// creo el grupo de vistas
ViewHolder vh = new ViewHolder(v);
return vh;
}
// Reemplaza en contenido de la vista
@Override
public void onBindViewHolder(ViewHolder viewHolder, final int position) {
viewHolder.nameTextView.setText(persons.get(position).getName());
viewHolder.descriptionTextView.setText(persons.get(position).getDescription());
}
// Retorna el tamano de nuestra data
@Override
public int getItemCount() {
return persons.size();
}
}
Como vemos en el código anterior, hay tres métodos que debemos sobreescribir:
El método getItemCount()
que debe retornar el tamaño de la lista, o lo que es lo mismo, el tamaño de nuestra lista de elementos que se mostrarán en el listado.
El método onCreateViewHolder()
permite inicializar todos los elementos que componen nuestra clase ViewHolder definida anteriormente; además definimos el layout (que puede variar para cada elemento) que utiliza cada elemento. También es posible definir los eventos en esta función.
En el método onBindViewHolder()
se debe definir o enlazar los valores de los distintos campos.
Invocando el Adapter anterior
Desde nuestra Activity o Fragment, creamos un objeto del Adapter definido anteriormente:
ListAdapter listAdapter = new ListAdapter(persons); audioRv.setAdapter(listAdapter);
Y al correr nuestra aplicación en el emulador o dispositivo físico:
Conclusiones
En esta entrada dimos los primeros pasos con los RecyclerView y CardView disponibles en las últimas versiones de Android y en posteriores mediante la Librería de Soporte; pudimos notar que el funcionamiento y la implementación son muy parecidas a lo que estamos acostumbrados con los GridView y ListView; en siguientes entradas veremos lo sencillo que resulta de implementar otras funcionalidades a las RecyclerView y CardView como son el swipe y algunas sencillas animaciones para ocultar secciones de los CardView.
Desarrollo con Laravel, Django, Flask, CodeIgniter, HTML5, CSS3, MySQL, JavaScript, Vue, Android, iOS, Flutter