Cuando estamos desarrollando en Android a menudo necesitamos enviar datos a otra Activity y esto lo podemos realizar mediante un Intent pero qué sucede si deseamos enviar un objeto para economizar una llamada a la API (es decir recibir un id y llamar a la API para que traiga otra vez el objeto con cierto id). Android nos brinda las opciones de Serializable (propia de Java) y Parcelable sin embargo esta última es hasta 10 veces más rápida por lo que vamos a enfocar en ella.
Parcelable es una interfaz y podemos implementarla manual o mediante un plugin, en esta ocasión optaremos por la segunda. Para instalar el plugin debemos ingresar en Android Studio y buscar «Plugins»
Ingresamos en el criterio de búsqueda «Parcelable» y damos click en instalar plugin
Nos solicitará confirmar si deseamos instalar el plugin y daremos click en «Si»
Una vez que se ha instalado debemos reiniciar Android Studio para que los cambios surtan efecto
Ahora vamos a abrir nuestro proyecto en Android Studio y nos vamos a dirigir a una clase, por ejemplo:
Persona.java
public class Persona { public int id; public String nombre; public String apellidos; public int edad; public Persona(int pId,String pNombre,String pApellidos, int pEdad) { id = pId; nombre = pNombre; apellidos = pApellidos; edad = pEdad; } }
Damos click derecho dentro de la clase y seleccionamos la opción «Generar»
Aparece un nuevo menú donde elegiremos «Parcelable»
En la nueva ventana seleccionaremos los atributos a incluir para Parcelable, en nuestro caso deseamos pasar todo el objeto a otra Activity por lo que seleccionamos todos las propiedades
Después de unos segundos aparece en nuestra clase unos métodos que se han generado, la clase debe aparecer similar a la siguiente
Persona.java
public class Persona implements Parcelable { public int id; public String nombre; public String apellidos; public int edad; @Override public int describeContents() { return 0; } @Override public void writeToParcel(Parcel dest, int flags) { dest.writeInt(this.id); dest.writeString(this.nombre); dest.writeString(this.apellidos); dest.writeInt(this.edad); } public Persona() { } public Persona(int pId,String pNombre,String pApellidos, int pEdad) { id = pId; nombre = pNombre; apellidos = pApellidos; edad = pEdad; } protected Persona(Parcel in) { this.id = in.readInt(); this.nombre = in.readString(); this.apellidos = in.readString(); this.edad = in.readInt(); } public static final Parcelable.Creator<Persona> CREATOR = new Parcelable.Creator<Persona>() { @Override public Persona createFromParcel(Parcel source) { return new Persona(source); } @Override public Persona[] newArray(int size) { return new Persona[size]; } }; }
Como se puede observar se implementa la interfaz Parcelable y debemos sobreescribir algunos métodos y funciones sin embargo el plugin que instalamos realiza la tarea por nosotros. Dos de las acciones más importantes son writeToParcel que se encarga de tomar los valores del objeto y salvarlos y createFromParcel que recupera los valores.
Ahora vamos a pasar un objeto entre dos Activity
MainActivity.java
Acá vamos a realizar las siguientes acciones:
- Crear una instancia de la clase Persona y estableceremos los valores pasándolos al constructor.
- En el layout agregaremos un Button, cuando se de click en él se navega a la segunda Activity y se pasa la instancia del objeto.
public class MainActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // creamos la instancia de la clase Persona final Persona persona = new Persona(1,"Carlos","Castro",9); // obtenemos la referencia del objeto Button button = (Button) findViewById(R.id.btn); // establecemos el onClickListener button.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { // Creamos el intent para navegar a la segunda Activity Intent intent = new Intent(MainActivity.this,SecondActivity.class); // se envía el objeto con la llave de "Persona" intent.putExtra("Persona",persona); // iniciamos el intent startActivity(intent); } }); } }
El layout queda de la siguiente manera
activity_main.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:paddingBottom="@dimen/activity_vertical_margin" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin" tools:context="com.example.itadmin.ejemploparcelable.MainActivity"> <Button android:id="@+id/btn" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="Abrir activity"/> </RelativeLayout>
En la segunda Activity vamos a realizar lo siguiente:
- Obtenemos el objeto enviado.
- Obtenemos la referencia al TextView.
- Cambiamos el texto del TextView por el nombre del objeto que nos han enviado.
SecondActivity.java
public class SecondActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_second); /* obtenemos el objeto que se ha enviado nótese que obtenemos el Intent que se ha ejecutado para iniciar la Activity en la que estamos luego obtenemos un objeto Parcelable con la llave que enviamos por parámetro */ Persona persona = (Persona) getIntent().getParcelableExtra("Persona"); // obtenemos la referencia al TextView TextView textView = (TextView) findViewById(R.id.txtvSecondActivity); // establecemos como texto del TextView el nombre que viene en el objeto enviado textView.setText(persona.nombre); } }
activity_second.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:paddingBottom="@dimen/activity_vertical_margin" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin" tools:context="com.example.itadmin.ejemploparcelable.SecondActivity"> <TextView android:id="@+id/txtvSecondActivity" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Second Activity" /> </RelativeLayout>
La aplicación corriendo despliega el siguiente resultado
Main Activity
Second Activity
Bueno hemos aprendido a utilizar la interfaz Parcelable de manera que podemos economizarnos tiempo de carga y su implementación es sencilla.
El código está disponible en GitHub, espero que les sea de ayuda 🙂