Codificación en Android Studio

En este blog veremos como codificar diferentes aspectos de la interfaz de Android Studio, como lo son los Botones, RadioGroup, Spinner,etc.

Primero empezaremos por la clase "Button" o Botones de Android Studio.

1.Codificación de Botones

Crear proyecto en Android Studio

Antes que nada ve a Android Studio, ve al menú de herramientas y selecciona File > New > New Project…  para crear un nuevo proyecto


En la configuración del proyecto ten en cuenta los siguientes aspectos:

  • Application Name: usa el nombre «Botones». 

  • Company Domain Name: Para el dominio elige la entidad que represente tu creación, puede ser tu_nombre.com, el nombre_de_tu_empresa.com o simplemente test.com. 

  • Projection Location: En la ubicación selecciona la carpeta que tengas destinada para guardar tus proyectos. Recuerda no usar espacios en ni caracteres especiales con acentos. 

Ahora en los factores de forma deja por defecto el SDK mínimo de ejecución en la versión 11 de Android Studio.


En la siguiente ventana elige una actividad vacía(Empity Activity) como contenedor principal para los ejemplos que veremos.


Finalmente cambia el titulo del archivo java para la actividad, al igual que su layout y pulsa Finish.

Ya que creamos el proyecto. Para agregar un botón a la actividad principal de tu app dirígete a actividad_botones.xml y agrega la siguiente definición.

<?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.herprogramacion.botones.ActividadBotones">

    <Button
        android:id="@+id/button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:text="AGREGAR" />
</RelativeLayout>

Con ello centramos el botón en el relative layout.

El texto que especifica su acción especifícalo en el atributo android:text. En el ejemplo anterior se usó la palabra "AGREGAR".

Este código debería mostrar en la ventana Preview la siguiente imagen:


"Cambiar texto de un 
botón"

Asigna una cadena directamente al atributo android:text para indicar la acción del botón.

<Button
    android:id="@+id/button"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_centerHorizontal="true"
    android:layout_centerVertical="true"
    android:text="Agregar" />

Por defecto el texto del botón estará en mayúsculas, pero si quieres deshabilitar esta característica usa el valor false en el atributo android:textAllCaps.

<Button
    ...
    android:textAllCaps="false"/>

Ahora, si deseas cambiar el texto programáticamente usa el métodosetText().

Para ello abre ActividadBotones.java. Obtén la instancia del botón con findViewById() y luego invoca setText() con una secuencia de caracteres como parámetro.

public class ActividadBotones extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_botones);

        Button boton = (Button) findViewById(R.id.button);
        boton.setText("Ordenar");
    }
}

Esto produce el siguiente resultado:


Ahora también es posible asignar un recurso string al texto del botón desde XML y Java.

En caso de XML usa la notación de recurso @string o @android:string (strings del sistema) de la siguiente forma:

<Button
    ...
    android:text="@string/texto_agregar"/>

En Java solo usa el operador punto para llegar al identificador perteneciente a la clase R:

Button boton = (Button) findViewById(R.id.button);
boton.setText(R.string.texto_agregar);

Crear botón desde Android Studio

Usa la pestaña Design que se ve en la vista de un layout para arrastrar y soltar un botón desde la paleta o cambiar sus atributos.

Pestaña Design en Android Studio

1. Sitúate en la ventana Palette. Luego busca el elemento Button de la sección Widgets

Android Studio: Button en la sección Widgets de la Paleta

2. Lleva el puntero del mouse hacia el layout y ubícalo según tu objetivo. En mi caso tengo un RelativeLayout, el cual permite orientar mi botón en lugares asociados al contenido del padre y al de otros views.

Por el momento lo ubicaré en el centro absoluto del layout, donde el editor mostrará líneas de guía para saber que valores estoy otorgando:

Ubicación de botón en el centro de un RelativeLayout

3. Una vez elegido el lugar donde se ubicará el botón, confirma con un click su inserción. Esto mostrará en la ventana Properties todos los atributos del botón que puedes editar.

Ubicación de botón en layout

4. Si deseas, da doble click sobre el botón en el layout para desplegar una caja de edición rápida para el id y el texto.

Edición rápida en pestaña Design de un botón

2.Codificacion de un RadiGroup

Los botones de selección permiten al usuario seleccionar una opción de un conjunto. Debes usar botones de selección para conjuntos opcionales que son mutuamente excluyentes si crees que el usuario necesita ver todas las opciones disponibles una al lado de la otra. Si no es necesario mostrar todas las opciones juntas, usa un ícono giratorio en su lugar.

Para crear cada opción del botón de selección, crea un RadioButton en tu diseño. Sin embargo, debido a que los botones de selección son mutuamente excluyentes, debes agruparlos dentro de un RadioGroup. Cuando los agrupas, el sistema garantiza que solo se pueda seleccionar un botón a la vez.

Cuando el usuario selecciona uno de los botones de selección, el objeto RadioButton correspondiente recibe un evento de clic.

Para definir el controlador de eventos de clic correspondiente a un botón, agrega el atributo android:onClick al elemento <RadioButton> en tu diseño XML. El valor de este atributo debe ser el nombre del método al que deseas llamar en respuesta a un evento de clic. La Activity que aloja el diseño debe implementar el método correspondiente.

Por ejemplo, estos son un par de objetos RadioButton:

<?xml version="1.0" encoding="utf-8"?>
<RadioGroup xmlns:android="http://schemas.android.com/apk/res/android"
   
android:layout_width="match_parent"
   
android:layout_height="wrap_content"
   
android:orientation="vertical">
   
<RadioButton android:id="@+id/radio_pirates"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:text="@string/pirates"
       
android:onClick="onRadioButtonClicked"/>
   
<RadioButton android:id="@+id/radio_ninjas"
       
android:layout_width="wrap_content"
       
android:layout_height="wrap_content"
       
android:text="@string/ninjas"
       
android:onClick="onRadioButtonClicked"/>
</RadioGroup>

Dentro de la Activity que aloja este diseño, el siguiente método procesa el evento de clic para ambos botones de selección:

fun onRadioButtonClicked(view: View) {
   
if (view is RadioButton) {
       
// Is the button now checked?
       
val checked = view.isChecked

       
// Check which radio button was clicked
       
when (view.getId()) {
            R
.id.radio_pirates ->
               
if (checked) {
                   
// Pirates are the best
               
}
            R
.id.radio_ninjas ->
               
if (checked) {
                   
// Ninjas rule
               
}
       
}
   
}
}

El método que declares en el atributo android:onClick debe tener una firma que refleje el ejemplo de arriba de forma exacta. Específicamente, el método debe cumplir con lo siguiente:

  • Ser público
  • Mostrarse nulo
  • Definir una View como su único parámetro (que será la View en la que se hizo clic)

3.Codificacion de un Spinner

Android Studio tiene este componente, solo es cuestión de arrastrarlo al diseño si se trabaja visualmente. O bien escribir el código:

<Spinner
    android:id="@+id/id_spinner"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    />

Y como cualquier otro elemento de la UI, se puede acomodar como se desee.

Para hacer funcionar un spinner en Android Studio seguimos los pasos:

  1. Primero vamos a configurar el spinner en XML dándole una ID.
  2. Luego enlazamos XML y JAVA, mediante la ID.
  3. A la clase le agregamos implements onItemClickListener, para poder dar clic a cada ítem del spinner.
  4. Después agregamos la lista que contendrá el spinner, con un adaptador.
  5. Y por último agregaremos acciones cuando el usuario haga clic en un elemento del spinner.

Primero buscamos spinner en la sección de arriba a la izquierda. Una vez que aparezca lo arrastramos al diseño de la app.

Luego vamos a darle una ID, como se ve a continuación. Como se ve en la imagen de abajo, estamos trabajando en Constraint layout y el spinner está centrado en toda la pantalla.

Código en Java

Una vez listo el XML, lo siguiente es pasar a JAVA. Lo primero que se tiene que hacer es declarar una variable tipo spinner:

private Spinner spTest;

Luego se relaciona el código XML con la variable en JAVA, con el comando findViewById(. . . ). Como se ve a continuación:

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    inicioXML();
}
private void inicioXML()
{
    spTest = findViewById(R.id.id_spinner);
}

El código está dentro de un método llamado inicioXML. Ese método se llama desde el método onCreate. Esto lo hacemos para dar más orden al código, pero se puede usar findViewById(. . . ) en el método onCreate.

Con esto ya se tiene la variable en java relacionada con el spinner en XML.

Agregando contenido al spinner.

Agregando la lista de componentes al spinner en Android Studio.

  1. Primero se crea un ArrayList, el cual contiene la lista que mostrará el spinner.
  2. Luego se crea un adaptador, el cual se encarga de pasar el ArrayList al spinner.
  3. Por último se agrega el adaptador al spinner. Como se muestra a continuación.

La lista a agregar en este ejemplo es:

“Perro, gato, ratón, ardilla”.

Esta lista la vamos a agregar al spinner con el siguiente código:

private ArrayList<String> lista = new ArrayList<String>();
private void agregandoValores()
{
    lista.add("Perro");
    lista.add("Gato");
    lista.add("Ratón");
    lista.add("Ardilla");
}

Puedes crear el Array ya sea desde tu base de datos o desde los recursos, lo importante es tener un ArrayList con los elementos que va a tener el spinner.

Click al Spinner.

Para que el spinner reaccione a los clic en cada ítem, es necesario implementar en la clase de la Activity OnItemSelectedListener. Como se ve a continuación:

Spinner Android Studio onClic

Aquí nos va a marcar un error y nos sugiere implementar los métodos por default, le damos en aceptar o bien los implementamos manualmente, viendo de manera general nuestro código quedaría así:

Spinner Android Studio implementar

Spinner Android Studio

Pasar lista al spinner

A este punto ya tenemos la lista, y ya tenemos lo necesario para que se haga clic al spinner.

Lo siguiente es pasar la lista al spinner, para esto vamos a crear otro método que llamaremos darClic, aquí agregamos todo el código que se refiera a dar clic por parte del usuario. Usando el siguiente código:

private void darClic()
{
    spTest.setOnItemSelectedListener(this);
    ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, lista);
    adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
    spTest.setAdapter(adapter);
}

Lo que hicimos fue decirle al spinner que este alerta cuando el usuario le de clic. Le agregamos la lista a un adaptador y con ese adaptador pasamos la lista al spinner.

Agregar acción al hacer clic.

Por último se agrega una acción a cada ítem seleccionado. Eso se hace en el método llamado onItemSelected().

Se usa un Switch, para elegir que spinner se seleccionó (en caso de ser más de un spinner), y la acción dependiendo del ítem seleccionado se configura en base al contenido del ítem seleccionado.

Para ver cómo funciona un Switch te sugerimos ver el tutorial de este link.

El código quedaría de la siguiente manera:

@Override
public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
    switch (adapterView.getId())
    {
        case R.id.id_spinner:
            Toast.makeText(cont,adapterView.getSelectedItem().toString(),Toast.LENGTH_SHORT).show();
            break;

        default:
            break;
    }
}

La ID en el switch es la id del spinner, en caso de tener más de un spinner, solo se abrirían más case en el switch y listo. Puedes ver el tutorial de múltiples spinners en la misma activity.
Cuando se selecciona Perro aparecerá un Toast que dice Perro, y lo mismo para los demás componentes de la lista.

Para obtener el nombre del ítem seleccionado se usa:

adapterView.getSelectedItem()

Para obtener la posición del ítem seleccionado se usa:

adapterView.getSelectedItemPosition()
Código final.

El código en JAVA queda así:

public class MainActivity extends AppCompatActivity implements AdapterView.OnItemSelectedListener {

    private Context cont=this;    
    private Spinner spTest;
    private ArrayList<String> lista = new ArrayList<String>();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);        
       
       inicioXML();
       agregandoValores();
       darClic();
    }

    private void inicioXML()
    {
        spTest = findViewById(R.id.id_spinner);
    }

    private void agregandoValores()
    {
        lista.add("Perro");
        lista.add("Gato");
        lista.add("Ratón");
        lista.add("Ardilla");
    }

    private void darClic()
    {
        spTest.setOnItemSelectedListener(this);
        ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, lista);
        adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
        spTest.setAdapter(adapter);
    }

    @Override
    public void onItemSelected(AdapterView<?> adapterView, View view, int i, long l) {
        adapterView.getSelectedItem()
        switch (adapterView.getId())
        {

            case R.id.id_spinner:
                //Hacer algo aquí
                Toast.makeText(cont,adapterView.getSelectedItem().toString(),Toast.LENGTH_SHORT).show();
                break;

            default:
                break;
        }

    }

    @Override
    public void onNothingSelected(AdapterView<?> adapterView) {

    }
}

4.Codificación de un Listview

Lo primero que debemos hacer es arrastrar el widget del ListView desde la paleta de Android Studio al layout, y colocarlo en la posición que deseemos. Inmediatamente nos saldrán a la derecha las propiedades del widget y podremos modificarlo a nuestro gusto. Podremos ver en la pantalla central el simulador una lista de Items y Subitems que nos darán una idea aproximada de cómo quedará nuestra lista.

Si cambiamos la vista de Design a Text podemos modificar directamente el código XML del ListView. 

ListView XML
Java
1
2
3
4
5
6
<<strong>ListView</strong>
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/listView"
        android:layout_below="@+id/logo"
        android:layout_centerHorizontal="true" />



Este es un ejemplo del código XML de la lista que podéis ver en la figura anterior. La lista se declara con «<ListView» y las propiedades empiezan por «android:».

No definiremos todas las propiedades del ListView, pero sí vamos a comentar las más destacadas o útiles:

Permite establecer un color de fondo para la lista, en este caso el blanco.

Permite o no hacer click sobre la lista. Muy útil.

Nos permite establecer un color para la línea que separa cada item de la lista.

Establece el ancho de la línea anteriormente comentada.

Esta propiedad indica el nombre de la lista, en este caso «listView».

5.Como codificar un CheckBox

Un Checkbox es un botón de dos estados (marcado, no marcado) que actúa como control de selección (los radio buttons y switches también pertenecen a esta categoría) ante los usuarios. Lo que permite elegir una o varias opciones de un conjunto.

Checkbox en Android

Por defecto su color será el mismo de la propiedad android:colorAccent en el tema de la aplicación.

Las especificaciones del Material Design sobres controles de selección nos muestra que este view puede pasar por 5 estados, tanto si está marcado como si no:

  • hover: Estado cuando el Checkbox se encuentra inmóvil
  • focused: Cuando la navegación en la UI apunta al checkbox como control de entrada
  • pressed: El checkbox se encuentra bajo selección prolongada
  • disable: El checkbox pierde su capacidad de cambio entre estados
  • disable-focused: El checkbox está deshabilitado pero el sistema de navegación lo enfoca

Las siguientes ilustraciones muestran los estados descritos anteriormente en el tema Material Light y Dark:




La Clase CheckBox

La representación en Java de este control es con la clase CheckBox.

Esto quiere decir que debes usar la etiqueta <CheckBox> en tus layouts para crearlos en la vista.

Por ejemplo…

Abre el layout actividad_principal.xml y agrega un nuevo checkbox como muestra el siguiente código:

<?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.herprogramacion.checkboxes.ActividadPrincipal">

    <CheckBox
        android:id="@+id/checkBox"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:text="Recordarme" />
</RelativeLayout>

En la preview verás:

CheckBox en la Preview de Android Studio

Obtener Valor Del CheckBox

Si quieres saber en qué estado se encuentra actualmente el CheckBox utiliza el método isChecked().

El retorno es de tipo boolean, donde true significa checked y false unchecked.

Ejemplo

Obtener el estado de un checkbox y mostrarlo en un Toast al pulsarse el botón de guardar.

Solución

1. Ubica en el centro del RelativeLayout un CheckBox. En la parte inferior debes poner un Button que se extienda completamente de forma horizontal. Su atributo text tendrá el valor de «Guardar«.

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <CheckBox
        android:id="@+id/seleccion_direccion_envio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:text="Usar la misma dirección de facturación" />

    <Button
        android:id="@+id/boton_guardar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:onClick="loguearCheckbox"
        android:text="Guardar" />
</RelativeLayout>

2. Abre ActividadPrincipal.java y declara el método loguearCheckbox(). En su interior llama el método estático Toast.makeText() y loguea el estado del check box.

Obviamente lo primero es obtener su instancia y luego llamar a isChecked(). Usa las palabras «Marcado» y «No Marcado» dependiendo del valor retornado.

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.view.View;
import android.widget.CheckBox;
import android.widget.Toast;

public class ActividadPrincipal extends AppCompatActivity {

    private CheckBox seleccionDireccion;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        seleccionDireccion = (CheckBox) findViewById(R.id.seleccion_direccion_envio);
    }

    public void loguearCheckbox(View v) {
        String s = "Estado: " + (seleccionDireccion.isChecked() ? "Marcado" : "No Marcado");
        Toast.makeText(this, s, Toast.LENGTH_LONG).show();
    }
}

3. Al correr la app se verá el mensaje con el estado. Prueba ambos casos.

isChecked() en CheckBox

Marcar CheckBox

Para cambiar el estado de un checkbox usa el atributo booleano android:checked. Donde false (valor por defecto) equivale a no marcado y true hace efectiva la verificación.

Por ejemplo. La siguiente caja de confirmación viene marcado de forma predeterminada para indicar que una pizza tendrá como ingrediente adherido champiñones:

<CheckBox
    android:id="@+id/opcion_champinones"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:checked="true"
    android:text="Champiñones" />

Por otro lado, la forma programática de modificar el valor se da con el método setChecked(), que recibe el estado como parámetro.

Ejemplo:

Aplicar seguro automáticamente si el giro a reclamar sobrepasa los 2000 USD.

Solución

1. El  layout para dicha situación se basa en un EditText que recibe el monto del giro y un CheckBox en la parte inferior de este, que determina si se aplican costos para asegurar el giro en caso de robo.

Esto en definición XML podría traducirse en un LinearLayout de orientación vertical con ambos views.

actividad_principal.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="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

    <android.support.design.widget.TextInputLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content">

        <EditText
            android:id="@+id/campo_monto"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:ems="10"
            android:hint="Monto del giro"
            android:inputType="numberDecimal"
            android:singleLine="true" />
    </android.support.design.widget.TextInputLayout>

    <CheckBox
        android:id="@+id/opcion_asegurar"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Aplicar seguro" />

</LinearLayout>

Nota: Usé un TextInputLayout para proporcionar etiquetas flotantes. Aprende a usarlo en mi artículo TextInputLayout En Android: Material Design.

2. Usa la interfaz TextWatcher para verificar el cambio del monto en el campo de texto. La idea es comprobar que el valor sea mayor o igual a 2000 para marcar el checkbox automáticamente a través de setChecked().

ActividadPrincipal.java

public class ActividadPrincipal extends AppCompatActivity {

    private CheckBox opcionAsegurar;
    private EditText campoMontoGiro;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        opcionAsegurar = (CheckBox) findViewById(R.id.opcion_asegurar);

        campoMontoGiro = (EditText) findViewById(R.id.campo_monto);
        campoMontoGiro.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {

            }

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {

            }

            @Override
            public void afterTextChanged(Editable s) {
                String str = s.toString();

                // Precondición
                if (TextUtils.isEmpty(str)) {
                    str = "0";
                }

                float monto = Float.parseFloat(str);

                if (monto >= 2000) {
                    opcionAsegurar.setChecked(true);
                }
            }
        });
    }
}

3. Digita un número mayor a 2000 y prueba la marcación automática:

Marcar CheckBox con setChecked() debido a EditText

Deshabilitar CheckBox

Usa el atributo general android:enabled con el valor de false para deshabilitar ante el usuario un CheckBox.

Ejemplo:

Mostrar las características premium de un software deshabilitadas ante un usuario que no tiene licencia válida.

Solución

Modifica el layout para que haya un TextView con un texto informativo sobre la limitación de cuentas premium. Por debajo sitúa dos checkboxes deshabilitados con las opciones nombradas abajo.

actividad_principal.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="match_parent"
    android:orientation="vertical"
    android:padding="16dp">


    <TextView
        android:id="@+id/texto_info"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Solo cuentas premium"
        android:textAppearance="@style/TextAppearance.AppCompat.Body2" />

    <CheckBox
        android:id="@+id/opcion_reporte"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:enabled="false"
        android:focusable="true"
        android:text="Generar reporte mensual" />

    <CheckBox
        android:id="@+id/opcion_ajuste_local"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:enabled="false"
        android:focusable="true"
        android:text="Envío ajustado a zona de tiempo local" />
</LinearLayout>

Deshabilitar CheckBox

Análogamente llama al método setEnabled() con el valor de false en su parámetro para deshabilitar.

Ejemplo:

Simula que el usuario presiona un botón de la parte inferior e inmediatamente obtiene una cuenta premium. En consecuencia, habilita las opciones restringidas.

Solución

1. Añade al layout el botón en la parte inferior:

<Button
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Actualizar Cuenta"
    android:id="@+id/boton_actualizar"
    android:onClick="actualizarCuenta"
    android:layout_gravity="center_horizontal"
    android:layout_marginTop="16dp" />

2. Ahora procesa los clicks sobre el botón con el método actualizarCuenta(). Usa setEnabled() con el valor de true para habilitar las cajas de confirmación.

public class ActividadPrincipal extends AppCompatActivity {

    private View opcionReporte, opcionZona;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        opcionReporte = findViewById(R.id.opcion_reporte);
        opcionZona = findViewById(R.id.opcion_ajuste_local);

    }

    public void actualizarCuenta(View view) {
        opcionReporte.setEnabled(true);
        opcionZona.setEnabled(true);
    }
}

Método setEnabled() en CheckBox

CheckBox En Android Studio

En esta sección crearás un layout para presentar al usuario un conjunto de gustos que puede seleccionar para recomendar información de acuerdo a sus preferencias.

Aunque ubicar un CheckBox en la pestaña Design de Android Studio es intuitivo, este ejemplo te servirá como práctica si aún desconoces este aspecto.

1. Abre actividad_principal.xml y cambia todo el contenido por un nodo principal del tipo GridLayout. Este contenedor permitirá dividir en columnas el conjunto de datos.

<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

</GridLayout>

2. Selecciona la pestaña Design y ubícate en la ventana Palette. Luego selecciona el view Plain Text en el grupo Widgets.

Arrastra el TextView a la celda definida en (0,0):

TextView en GridLayout

El view anterior es el texto de información para guiar al usuario. Usa en su atributo android:text el valor «Elige tus intereses».

3. Ahora pon dos espacios. Uno en la celda (0,1) y otro en (1,0). Este elemento se encuentra en el grupo Expert al final de la paleta como Space.

Añadir Space en GridLayout

4. Ahora busca CheckBox en Widgets y agrega 5 elementos desde (2,0) a (6,0). Luego agrega otros 5 desde (2,2) hasta (6,2).

Cuadrícula de checkboxes en GridLayout

5. Ahora modifica el texto e id de cada checkbox. Puedes hacerlo a través del panel Properties, pero es más fácil dar doble click en cada elemento para hacerlo a través de un diálogo emergente.

Cambiar texto de checkbox

Usa las siguientes categorías en los textos: Belleza, Libros y Literatura, Carreras, Educación, Eventos, Familia, Comidas y Bebidas, Videojuegos, Deportes, Arte.

Para los identificadores solo emplea el formato campo_<interes>.

6. Si todo salió bien, el código resultante es el siguiente:

<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

    <TextView
        android:id="@+id/textView"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="0"
        android:text="Elige tus intereses"
        android:textAppearance="@style/TextAppearance.AppCompat.Body1" />

    <Space
        android:layout_width="20dp"
        android:layout_height="20dp"
        android:layout_column="1"
        android:layout_row="0" />

    <Space
        android:layout_width="20dp"
        android:layout_height="20dp"
        android:layout_column="0"
        android:layout_row="1" />

    <CheckBox
        android:id="@+id/opcion_belleza"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="2"
        android:checked="false"
        android:text="Belleza" />

    <CheckBox
        android:id="@+id/campo_libros_literatura"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="3"
        android:checked="false"
        android:text="Libros y Literatura" />

    <CheckBox
        android:id="@+id/campo_comida_bebidas"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="2"
        android:layout_row="3"
        android:checked="false"
        android:text="Comida y Bebidas" />

    <CheckBox
        android:id="@+id/campo_carreras"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="4"
        android:checked="false"
        android:text="Carreras" />

    <CheckBox
        android:id="@+id/campo_videojuegos"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="2"
        android:layout_row="4"
        android:checked="false"
        android:text="Videojuegos" />

    <CheckBox
        android:id="@+id/campo_educacion"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="5"
        android:checked="false"
        android:text="Educación" />

    <CheckBox
        android:id="@+id/campo_deportes"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="2"
        android:layout_row="5"
        android:checked="false"
        android:text="Deportes" />

    <CheckBox
        android:id="@+id/campo_eventos"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="0"
        android:layout_row="6"
        android:checked="false"
        android:text="Eventos" />

    <CheckBox
        android:id="@+id/campo_familia"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="2"
        android:layout_row="2"
        android:checked="false"
        android:text="Familia" />

    <CheckBox
        android:id="@+id/campo_arte"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_column="2"
        android:layout_row="6"
        android:checked="false"
        android:text="Arte" />

</GridLayout>

Conjunto de checkboxes para intereses

Manejo De Eventos

Procesar Clicks con OnClickListener

Si deseas ejecutar acciones cuando el usuario selecciona un CheckBox usa la escucha View.OnClickListener.

Recuerda que esta posee al controlador onClick() para especificar las acciones a realizar en tiempo de ejecución.

Solo debes asignar una instancia con setOnClickListener() a la instancia de la caja de confirmación.

Por ejemplo:

findViewById(R.id.opcion_tv).setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View v) {
        // Ejecutar acciones
    }
});

Otra forma es asignar un controlador genérico en el atributo android:onClick del checkbox como vimos en la sección de botones.

Ejemplo:

Revelar el password que el usuario escriba en el campo de texto si marca un CheckBox 

Solución

1. Añade un EditText centrado en un RelativeLayout con inputType tipo textPassword. Por debajo añade un CheckBox.

actividad_principal.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <CheckBox
        android:id="@+id/opcion_mostrar"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignLeft="@+id/campo_contrasena"
        android:layout_alignStart="@+id/campo_contrasena"
        android:layout_below="@+id/campo_contrasena"
        android:onClick="mostrarContraseña"
        android:text="¿Mostrar contraseña?" />

    <EditText
        android:id="@+id/campo_contrasena"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:ems="10"
        android:hint="Contraseña"
        android:inputType="textPassword" />
</RelativeLayout>

2. Abre ActividadPrincipa.java y obtén las instancias de los views en onCreate(). Luego definir el controlador mostrarContrasena().

En su interior tendremos que comprobar con isChecked() si el checkbox está marcado. Si es así entonces cambia su tipo de entrada con setInputType() para tener el password visible.

De lo contrario asigna el tipo que tiene por defecto para enmascarar la contraseña.

Adicionalmente es necesario guardar la posición del cursor antes de aplicar el cambio de entrada, ya que setInputType() restaura el cursor a la posición 0.

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.text.InputType;
import android.view.View;
import android.widget.CheckBox;
import android.widget.EditText;

public class ActividadPrincipal extends AppCompatActivity {

    private CheckBox opcionMostrar;
    private EditText campoContrasena;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        opcionMostrar = (CheckBox)findViewById(R.id.opcion_mostrar);
        campoContrasena = (EditText)findViewById(R.id.campo_contrasena);
    }

    public void mostrarContraseña(View v){
        // Salvar cursor
        int cursor = campoContrasena.getSelectionEnd();

        if(opcionMostrar.isChecked()){
            campoContrasena.setInputType(InputType.TYPE_CLASS_TEXT
                    | InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD);
        }else{
            campoContrasena.setInputType(InputType.TYPE_CLASS_TEXT
                    | InputType.TYPE_TEXT_VARIATION_PASSWORD);
        }

        // Restaurar cursor
        campoContrasena.setSelection(cursor);
    }

}

Password visible en EditText con CheckBox

Cambios de Estado con OnCheckedChangeListener

La escucha CompoundButton.OnCheckedChangeListener permite realizar operaciones cuando el estado del botón cambia.

Para asignar una nueva instancia usa el método setOnCheckedChangeListener() en la instancia del CheckBox.

Luego sobrescribe el controlador onCheckedChanged() con las acciones que deseas ejecutar. Este método recibe dos parámetros.

  • buttonView: Hace referencia  al checkbox que cambió su estado.
  • isChecked: El estado al que cambió el checkbox.

Ejemplo:

Crear una pregunta para el usuario que identifique desde que canal supo sobre la compañía.

Las opciones son: Televisión, Radio, Periódico, Email, Amigos y Otros. 

Al seleccionar «Otros» debe mostrarse un campo para que escriba dichas fuentes.

Solución:

1. Modifica actividad_principal.xml donde exista:

  • Un TextView en la parte superior con el texto «¿Dónde oíste de nosotros?»
  • 5 elementos CheckBox en forma vertical con las opciones mencionadas.
  • Un EditText sin presencia (visibility en gone) por debajo de las opciones.

¿El resultado?

<?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="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

    <TextView
        android:id="@+id/texto_info"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginBottom="8dp"
        android:text="¿Dónde oíste de nosotros?"
        android:textAppearance="@style/TextAppearance.AppCompat.Body1" />

    <CheckBox
        android:id="@+id/opcion_tv"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:checked="false"
        android:text="Tv" />

    <CheckBox
        android:id="@+id/opcion_radio"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:checked="false"
        android:text="Radio" />

    <CheckBox
        android:id="@+id/opcion_periodico"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:checked="false"
        android:text="Periódico" />

    <CheckBox
        android:id="@+id/opcion_amigo"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:checked="false"
        android:text="Un amigo" />

    <CheckBox
        android:id="@+id/opcion_otros"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:checked="false"
        android:text="Otros" />

    <EditText
        android:id="@+id/campo_otros"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:visibility="gone"
        android:layout_marginTop="16dp"
        android:hint="¿Cuáles otros?"
        android:inputType="textMultiLine"
        android:lines="3"
        android:maxLines="3"
        android:textAppearance="@style/TextAppearance.AppCompat.Body1" />
</LinearLayout>

2. En el código Java obtén las instancias de la opción y el campo para «Otros». Luego asigna la escucha OnCheckedChangeListener de forma anónima a opcion_campo.

En su controlador onCheckedChanged() cambia la visibilidad del campo de texto dependiendo del segundo parámetro. Para true usará la bandera VISIBLE y para false GONE.

public class ActividadPrincipal extends AppCompatActivity {

    private CheckBox opcionOtros;
    private View campoOtros;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        opcionOtros = (CheckBox) findViewById(R.id.opcion_otros);
        campoOtros = findViewById(R.id.campo_otros);

        opcionOtros.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                campoOtros.setVisibility(isChecked ? View.VISIBLE : View.GONE);
            }
        });
    }

}

Uso de OnCheckedChangeListener en CheckBox con EditText

Personalizar Estilo De CheckBox

Veamos algunos de los casos más frecuentes a la hora de cambiar el aspecto de un checkbox:

Cambiar Color en Estado Activo

Esto se puede hacer de dos formas:

1. Usar el atributo app:buttonTint para cambiar el tinte de la caja. Sin embargo en su estado OFF el borde será de ese mismo color.

<CheckBox
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Personalizar"
    app:buttonTint="@color/colorPrimary"
    android:id="@+id/checkbox" />

2. Usar un tema propio personalizando el atributo colorAccent. Simplemente aplícalo al view con el atributo android:theme.

styles.xml

<style name="CheckBoxIndigo">
    <item name="colorAccent">@color/colorPrimary</item>
</style>

layout

<CheckBox
    android:id="@+id/checkbox"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Personalizar"
    android:theme="@style/CheckBoxIndigo" />

Cambiar color de CheckBox

Background Personalizado del Botón

Si deseas cambiar el background de la caja de confirmación usa el atributo android:button para signar un drawable de tipo lista, donde se especifiquen los estados marcado (state_checked) y no marcado.

Ejemplo:

Crear un background para un checkbox que sea circular y tenga color aguamarina.

Solución:

1. Crea un nuevo Drawable resource file para usar una definición XML con un nodo <selector>. En este deben existir dos ítems. El estado chequeado y el estado normal:

boton_checkbox.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:drawable="@drawable/background_checkbox_on" android:state_checked="true" />
    <item android:drawable="@drawable/background_checkbox_off" />

</selector>

2. Crea dos drawables más para materializar la definición del background en cada estado. En este caso usaremos el nodo <vector> para construir un drawable de vector que simplifique la definición del icono.

background_checkbox_on.xml

<?xml version="1.0" encoding="utf-8"?>
<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="32dp"
    android:height="32dp"
    android:viewportHeight="48"
    android:viewportWidth="48">

    <group
        android:scaleX=".2"
        android:scaleY=".2"
        android:translateX="6"
        android:translateY="6">
        <group
            android:scaleX="7.5"
            android:scaleY="7.5">
            <path
                android:fillColor="#45D0BB"
                android:pathData="M12,2A10,10 0 0,1 22,12A10,10 0 0,1 12,22A10,10 0 0,1 2,12A10,10 0 0,1 12,2M12,4A8,8 0 0,0 4,12A8,8 0 0,0 12,20A8,8 0 0,0 20,12A8,8 0 0,0 12,4M11,16.5L6.5,12L7.91,10.59L11,13.67L16.59,8.09L18,9.5L11,16.5Z" />
        </group>
    </group>

</vector>

Background personalizado para CheckBox

background_checkbox_off.xml

<?xml version="1.0" encoding="utf-8"?>
<vector xmlns:android="http://schemas.android.com/apk/res/android"
    android:width="32dp"
    android:height="32dp"
    android:viewportHeight="48"
    android:viewportWidth="48">

    <group
        android:scaleX=".2"
        android:scaleY=".2"
        android:translateX="6"
        android:translateY="6">
        <group
            android:scaleX="7.5"
            android:scaleY="7.5">
            <path
                android:fillColor="#6E6E6E"
                android:pathData="M12,20A8,8 0 0,1 4,12A8,8 0 0,1 12,4A8,8 0 0,1 20,12A8,8 0 0,1 12,20M12,2A10,10 0 0,0 2,12A10,10 0 0,0 12,22A10,10 0 0,0 22,12A10,10 0 0,0 12,2Z" />
        </group>
    </group>
</vector>

Background personalizado para CheckBox en estado OFF

3. A continuación asigna el drawable de lista en el atributo android:button de un checkbox de ejemplo en actividad_principal.xml.

<CheckBox
    android:id="@+id/checkbox2"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_gravity="center_horizontal"
    android:layout_marginTop="48dp"
    android:button="@drawable/boton_checkbox"
    android:text="Personalizar" />

4. Ejecuta la app y observa el cambio de estados:

Ejemplo de cambios de estados en CheckBox

Añadir Un CheckBox Dinámicamente

En ocasiones tendrás una fuente de datos de la cual dependen tus Checkboxes.

Puede que la lista de nombres se encuentre en una arreglo de recursos, en una base de datos SQLite, que se provean desde un servicio web, desde un archivo xml, etc.

Así no es posible definir en el layout con anterioridad la cantidad exacta de checkboxes y su contenido explícitamente.

Lo que debes hacer es crearlos en tiempo de ejecución o dinámicamente a través del constructor de la clase CheckBox() y luego añadirlo con addView() en el contenedor padre.

Ejemplo:

Añadir un CheckBox por cada industria disponible para selección del usuario. La lista de datos se encuentra en un array

Solución

1. Primero cambia el contenido de actividad_principal.xml por un nodo LinearLayout que contenga una sección para las opciones. Dicha sección debe llevar un TextView con el mensaje «Selecciona tu industria:».

Debido a que necesitas los checkboxes alineados verticalmente usa el atributo android:orientation con el valor vertical en la sección.

<?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="match_parent"
    android:orientation="vertical"
    android:padding="16dp">

    <LinearLayout
        android:id="@+id/seccion_industria"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical">

        <TextView
            android:id="@+id/texto_info"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Selecciona tu industria:"
            android:textAppearance="?android:attr/textAppearanceMedium" />
    </LinearLayout>
</LinearLayout>

2. Añade en la actividad principal un arreglo estático de strings con las siguientes industrias:

public static String[] INDUSTRIAS ={
        "Arte",
        "Computación",
        "Ingeniería civil",
        "Bioquímica",
        "Música",
        "Astronomía",
        "Zoología"
};

3. Para añadir en tiempo real cada checkbox primero obtén el contenedor seccion_industria con el método findViewById().

Luego emplea una estructura for que recorra todos los elementos de INDUSTRIAS. En cada iteración crea una instancia de CheckBox y añádela al contenedor con addView().

Súper importante que añadas al checkbox el texto con setText() antes de ser añadido. Además añade los parámetros de ancho y alto en formato «wrap content» a través de setLayoutParams().

ActividadPrincipal.java

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.view.ViewGroup.LayoutParams;
import android.widget.CheckBox;
import android.widget.LinearLayout;

public class ActividadPrincipal extends AppCompatActivity {

    public static String[] INDUSTRIAS = {
            "Arte",
            "Computación",
            "Ingeniería civil",
            "Bioquímica",
            "Música",
            "Astronomía",
            "Zoología"
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.actividad_principal);

        LinearLayout seccionIndustria = (LinearLayout) findViewById(R.id.seccion_industria);

        for (String industria : INDUSTRIAS) {
            CheckBox opcion = new CheckBox(this);
            opcion.setText(industria);
            opcion.setLayoutParams(
                    new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
            seccionIndustria.addView(opcion);
        }

    }

}

El constructor de la clase CheckBox() recibe como parámetro el contexto de referencia. Debido a que será la actividad principal es posible usar el operador this.

6.Como iniciar una activity

Sigue estos pasos para agregar un método a la clase MainActivity, a la que se llama cuando presionas el botón Enviar:

  1. En el archivo app > java > com.example.myfirstapp > MainActivity, agrega el stub del siguiente método sendMessage():

  1. class MainActivity : AppCompatActivity() {
       
    override fun onCreate(savedInstanceState: Bundle?) {
           
    super.onCreate(savedInstanceState)
            setContentView
    (R.layout.activity_main)
       
    }

       
    /** Called when the user taps the Send button */
       
    fun sendMessage(view: View) {
           
    // Do something in response to button
       
    }

    }

    Es posible que veas un error porque Android Studio no puede resolver la clase View que se usa como argumento del método. Para borrar el error, haz clic en la declaración View, coloca el cursor sobre ella y presiona Alt + Intro (o, en Mac, Opción + Intro) a fin de realizar una corrección rápida. Si aparece un menú, selecciona Import class.

  2. Regresa al archivo activity_main.xml para llamar al método desde el botón, de la siguiente manera:
    1. Selecciona el botón en el editor de diseño.
    2. En la ventana Attributes, ubica la propiedad onClick y selecciona sendMessage [MainActivity] de la lista desplegable.

    De esta manera, cuando se presione el botón, el sistema llamará al método sendMessage().

    Toma nota de los detalles de este método. Son necesarios para que el sistema reconozca el método como compatible con el atributo android:onClick. Específicamente, el método tiene las siguientes características:

    • Acceso público
    • Un valor que se muestra de unit vacío o, en Kotlin, implícito
    • Un objeto View como único parámetro, que es el objeto View en el que hiciste clic al final del paso 1
  3. A continuación, deberás completar este método para leer el contenido del campo de texto y proporcionar dicho texto a otra actividad

Un Intent es un objeto que proporciona vinculación en tiempo de ejecución entre componentes separados, como dos actividades. El Intent representa la intención que tiene una app de realizar una tarea. Puedes usar intents para varias tareas; pero, en esta lección, tu intent inicia otra actividad.

En MainActivity, agrega la constante EXTRA_MESSAGE y el código sendMessage(), como se muestra a continuación:


const val EXTRA_MESSAGE = "com.example.myfirstapp.MESSAGE"

class MainActivity : AppCompatActivity() {
   
override fun onCreate(savedInstanceState: Bundle?) {
       
super.onCreate(savedInstanceState)
        setContentView
(R.layout.activity_main)
   
}

   
/** Called when the user taps the Send button */
   
fun sendMessage(view: View) {
       
val editText = findViewById<EditText>(R.id.editTextTextPersonName)
       
val message = editText.text.toString()
       
val intent = Intent(this, DisplayMessageActivity::class.java).apply {
            putExtra
(EXTRA_MESSAGE, message)
       
}
        startActivity
(intent)

   
}
}

Puedes esperar que Android Studio vuelva a mostrar errores Cannot resolve symbol. Para borrar los errores, presiona Alt + Intro o, en Mac, Opción + Regresar. Deberías terminar con las siguientes importaciones:


import androidx.appcompat.app.AppCompatActivity
import android.content.Intent
import android.os.Bundle
import android.view.View
import android.widget.EditText

Todavía queda un error para DisplayMessageActivity, pero no te preocupes porque lo solucionarás en el siguiente paso.

Esto es lo que sucede en sendMessage():

  • El constructor Intent toma dos parámetros, un Context y una Class.

    El parámetro Context se usa primero porque la clase Activity es una subclase de Context.

    El parámetro Class del componente de la app, al que el sistema entrega el Intent,, es, en este caso, la actividad que va a comenzar.

  • El método putExtra() agrega el valor de EditText al intent. Un Intent puede transportar tipos de datos como pares clave-valor llamados extras.

    Tu clave es una constante pública EXTRA_MESSAGE porque la actividad siguiente usa la clave para obtener el valor de texto. Te recomendamos definir las claves para extras de intents con el nombre del paquete de la app como prefijo. De esta manera, se garantiza que las claves sean únicas en el caso de que tu app interactúe con otras aplicaciones.

  • El método startActivity() inicia una instancia de DisplayMessageActivity que especifica el Intent. Luego, deberás crear esa clase.

Para crear la segunda actividad, sigue estos pasos:

  1. En la ventana Project, haz clic con el botón derecho en la carpeta de la app y selecciona New > Activity > Empty Activity.
  2. En la ventana Configure Activity, ingresa "DisplayMessageActivity" en Activity Name. Deja todas las demás propiedades con sus valores predeterminados y haz clic en Finish.

Android Studio realiza tres acciones automáticamente:

  • Crea el archivo DisplayMessageActivity.
  • Crea el archivo de diseño activity_display_message.xml, que se corresponde con el archivo DisplayMessageActivity.
  • Agrega el elemento <activity> obligatorio en AndroidManifest.xml.

Si ejecutas la app y presionas el botón en la primera actividad, se iniciará la segunda. Sin embargo, estará vacía porque usa el diseño vacío proporcionado por la plantilla.

Vista de texto centrada en la parte superior del diseño
Figura 1: Vista de texto centrada en la parte superior del diseño

La nueva actividad incluye un archivo de diseño en blanco. Sigue estos pasos para agregar una vista de texto al lugar donde aparece el mensaje:

  1. Abre el archivo app > res > layout > activity_display_message.xml.
  2. Haz clic en Enable Autoconnection to Parent  en la barra de herramientas. De esta manera, se habilita la conexión automática. Consulta la figura 1.
  3. En el panel Palette, haz clic en Text, arrastra un elemento TextView al diseño y suéltalo cerca de la parte central superior del diseño de manera que se ajuste a la línea vertical que aparecerá. La opción de conexión automática agrega restricciones a la derecha y a la izquierda para ubicar la vista en el centro horizontal.
  4. Crea una restricción más desde la parte superior de la vista de texto hasta la parte superior del diseño para que se vea como en la figura 1.

De manera opcional, puedes realizar algunos ajustes en el estilo de texto si expandes textAppearance en el panel Common Attributes de la ventana Attributes y cambias los atributos como textSize y textColor.

En este paso, puedes modificar la segunda actividad para mostrar el mensaje que pasó la primera actividad.

  1. En DisplayMessageActivity, agrega el siguiente código al método onCreate():


  1. import androidx.appcompat.app.AppCompatActivity
    import android.content.Intent
    import android.os.Bundle
    import android.widget.TextView

En cada pantalla de tu app que no sea el punto de entrada principal, es decir, todas las pantallas que no sean la "pantalla principal", se debe proporcionar navegación para que el usuario pueda regresar a la pantalla superior lógica en la jerarquía de la app. Para ello, agrega un botón Arriba en la barra de la app.

Para agregar un botón Arriba, debes declarar qué actividad es la superior lógica en el archivo AndroidManifest.xml. Abre el archivo que se encuentra en app > manifests > AndroidManifest.xml, busca la etiqueta <activity> para DisplayMessageActivity y reemplázala por lo siguiente:

<activity android:name=".DisplayMessageActivity"
         
android:parentActivityName=".MainActivity">
   
<!-- The meta-data tag is required if you support API level 15 and lower -->
   
<meta-data
       
android:name="android.support.PARENT_ACTIVITY"
       
android:value=".MainActivity" />
</activity>

El sistema Android agregará automáticamente el botón Arriba en la barra de la app.

Haz clic en Apply Changes  en la barra de herramientas para ejecutar la app. Cuando se abra, escribe un mensaje en el campo de texto y presiona Send a fin de ver el mensaje en la segunda actividad.

Imagen de la app abierta, con texto que se ingresa a la izquierda de la pantalla y se muestra a la derecha
Figura 2: Imagen de la app abierta, con texto que se ingresa a la izquierda de la pantalla y se muestra a la derecha

Eso es todo. Compilaste tu primera app para Android.

Si quieres continuar aprendiendo los conceptos básicos sobre el desarrollo de apps para Android, regresa a Cómo compilar tu primera app y sigue los demás vínculos que se proporcionan allí.

  • override fun onCreate(savedInstanceState: Bundle?) {
       
    super.onCreate(savedInstanceState)
        setContentView
    (R.layout.activity_display_message)
       

       
    // Get the Intent that started this activity and extract the string
       
    val message = intent.getStringExtra(EXTRA_MESSAGE)

       
    // Capture the layout's TextView and set the string as its text
       
    val textView = findViewById<TextView>(R.id.textView).apply {
            text
    = message
       
    }

    }
  • Presiona Alt + Intro o, en Mac, Opción + Regresar para importar estas otras clases necesarias:


  • Comentarios