Hola amigos 馃憢 Bienvenidos a un nuevo tutorial de Universo Android. Hoy aprenderemos a usar RadioButton y RadioGroup, los componentes esenciales para crear opciones de selecci贸n 煤nica en formularios, encuestas y configuraciones de tu aplicaci贸n Android.
Al finalizar este tutorial tendr谩s:
- RadioButton b谩sico y avanzado
- RadioGroup con selecci贸n 煤nica
- Validaci贸n de selecciones
- RadioButton personalizado
- Material Design RadioButton
- Eventos y listeners
- Ejemplos pr谩cticos completos
馃煩 1. ¿Qu茅 es RadioButton y RadioGroup?
RadioButton es un bot贸n de selecci贸n 煤nica que permite elegir una opci贸n de un conjunto. RadioGroup es el contenedor que agrupa RadioButtons asegurando que solo uno est茅 seleccionado a la vez.
馃煩 2. Caracter铆sticas Principales
- Selecci贸n 煤nica autom谩tica
- Estado visual claro (seleccionado/no seleccionado)
- Agrupaci贸n l贸gica de opciones
- F谩cil validaci贸n de formularios
- Compatible con Material Design
馃煩 3. Crear el Proyecto
Creamos un nuevo proyecto en Android Studio con Empty Activity.
馃煩 4. Agregar Dependencias
馃搫 build.gradle (Module: app)
dependencies {
implementation 'androidx.appcompat:appcompat:1.6.1'
implementation 'com.google.android.material:material:1.11.0'
implementation 'androidx.constraintlayout:constraintlayout:2.1.4'
}馃煩 5. Dise帽o XML Principal
馃搫 activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="16dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="RadioButton Demo"
android:textSize="24sp"
android:textStyle="bold"
android:textColor="#2196F3"
android:layout_marginBottom="24dp" />
<!-- RadioGroup B谩sico -->
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="G茅nero:"
android:textSize="18sp"
android:textStyle="bold"
android:layout_marginTop="8dp" />
<RadioGroup
android:id="@+id/radioGroupGender"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:layout_marginTop="8dp">
<RadioButton
android:id="@+id/radioMale"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Masculino"
android:textSize="16sp"
android:padding="8dp" />
<RadioButton
android:id="@+id/radioFemale"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Femenino"
android:textSize="16sp"
android:padding="8dp" />
<RadioButton
android:id="@+id/radioOther"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Otro"
android:textSize="16sp"
android:padding="8dp" />
</RadioGroup>
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:background="#CCCCCC"
android:layout_marginTop="24dp"
android:layout_marginBottom="24dp" />
<!-- RadioGroup Horizontal -->
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Tama帽o:"
android:textSize="18sp"
android:textStyle="bold" />
<RadioGroup
android:id="@+id/radioGroupSize"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:layout_marginTop="8dp">
<RadioButton
android:id="@+id/radioSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="S"
android:layout_marginEnd="16dp" />
<RadioButton
android:id="@+id/radioMedium"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="M"
android:checked="true"
android:layout_marginEnd="16dp" />
<RadioButton
android:id="@+id/radioLarge"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="L"
android:layout_marginEnd="16dp" />
<RadioButton
android:id="@+id/radioXLarge"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="XL" />
</RadioGroup>
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:background="#CCCCCC"
android:layout_marginTop="24dp"
android:layout_marginBottom="24dp" />
<!-- RadioGroup con Tarjetas -->
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Plan de Suscripci贸n:"
android:textSize="18sp"
android:textStyle="bold" />
<RadioGroup
android:id="@+id/radioGroupPlan"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:layout_marginTop="8dp">
<!-- Plan B谩sico -->
<androidx.cardview.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
app:cardCornerRadius="8dp"
app:cardElevation="2dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="16dp">
<RadioButton
android:id="@+id/radioBasic"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical" />
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical"
android:layout_marginStart="12dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Plan B谩sico"
android:textSize="16sp"
android:textStyle="bold" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Funciones b谩sicas"
android:textSize="14sp"
android:textColor="#666666" />
</LinearLayout>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="$0/mes"
android:textSize="18sp"
android:textStyle="bold"
android:textColor="#4CAF50"
android:layout_gravity="center_vertical" />
</LinearLayout>
</androidx.cardview.widget.CardView>
<!-- Plan Premium -->
<androidx.cardview.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
app:cardCornerRadius="8dp"
app:cardElevation="2dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="16dp">
<RadioButton
android:id="@+id/radioPremium"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical" />
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical"
android:layout_marginStart="12dp">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Plan Premium"
android:textSize="16sp"
android:textStyle="bold" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Todas las funciones"
android:textSize="14sp"
android:textColor="#666666" />
</LinearLayout>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="$9.99/mes"
android:textSize="18sp"
android:textStyle="bold"
android:textColor="#2196F3"
android:layout_gravity="center_vertical" />
</LinearLayout>
</androidx.cardview.widget.CardView>
</RadioGroup>
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:background="#CCCCCC"
android:layout_marginTop="24dp"
android:layout_marginBottom="24dp" />
<!-- RadioGroup con Im谩genes -->
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="M茅todo de Pago:"
android:textSize="18sp"
android:textStyle="bold" />
<RadioGroup
android:id="@+id/radioGroupPayment"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:layout_marginTop="8dp">
<RadioButton
android:id="@+id/radioCard"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Tarjeta de Cr茅dito/D茅bito"
android:drawableStart="@android:drawable/ic_menu_gallery"
android:drawablePadding="12dp"
android:padding="12dp"
android:background="?android:attr/selectableItemBackground" />
<RadioButton
android:id="@+id/radioPaypal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="PayPal"
android:drawableStart="@android:drawable/ic_menu_send"
android:drawablePadding="12dp"
android:padding="12dp"
android:background="?android:attr/selectableItemBackground" />
<RadioButton
android:id="@+id/radioCash"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Efectivo"
android:drawableStart="@android:drawable/ic_menu_info_details"
android:drawablePadding="12dp"
android:padding="12dp"
android:background="?android:attr/selectableItemBackground" />
</RadioGroup>
<!-- Botones de Acci贸n -->
<Button
android:id="@+id/btnSubmit"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Enviar Formulario"
android:layout_marginTop="24dp" />
<Button
android:id="@+id/btnClear"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Limpiar Selecci贸n"
android:backgroundTint="#FF9800"
android:layout_marginTop="8dp" />
<!-- Resultado -->
<TextView
android:id="@+id/txtResult"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:background="#F5F5F5"
android:layout_marginTop="16dp"
android:visibility="gone" />
</LinearLayout>
</ScrollView>馃煩 6. MainActivity
馃搫 MainActivity.java
import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.RadioButton;
import android.widget.RadioGroup;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity {
RadioGroup radioGroupGender, radioGroupSize, radioGroupPlan, radioGroupPayment;
RadioButton radioMale, radioFemale, radioOther;
RadioButton radioSmall, radioMedium, radioLarge, radioXLarge;
RadioButton radioBasic, radioPremium;
RadioButton radioCard, radioPaypal, radioCash;
Button btnSubmit, btnClear;
TextView txtResult;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initializeViews();
setupListeners();
}
private void initializeViews() {
// RadioGroups
radioGroupGender = findViewById(R.id.radioGroupGender);
radioGroupSize = findViewById(R.id.radioGroupSize);
radioGroupPlan = findViewById(R.id.radioGroupPlan);
radioGroupPayment = findViewById(R.id.radioGroupPayment);
// RadioButtons - G茅nero
radioMale = findViewById(R.id.radioMale);
radioFemale = findViewById(R.id.radioFemale);
radioOther = findViewById(R.id.radioOther);
// RadioButtons - Tama帽o
radioSmall = findViewById(R.id.radioSmall);
radioMedium = findViewById(R.id.radioMedium);
radioLarge = findViewById(R.id.radioLarge);
radioXLarge = findViewById(R.id.radioXLarge);
// RadioButtons - Plan
radioBasic = findViewById(R.id.radioBasic);
radioPremium = findViewById(R.id.radioPremium);
// RadioButtons - Pago
radioCard = findViewById(R.id.radioCard);
radioPaypal = findViewById(R.id.radioPaypal);
radioCash = findViewById(R.id.radioCash);
// Buttons y TextView
btnSubmit = findViewById(R.id.btnSubmit);
btnClear = findViewById(R.id.btnClear);
txtResult = findViewById(R.id.txtResult);
}
private void setupListeners() {
// Listener para RadioGroup G茅nero
radioGroupGender.setOnCheckedChangeListener((group, checkedId) -> {
RadioButton selectedRadio = findViewById(checkedId);
if (selectedRadio != null) {
Toast.makeText(this,
"G茅nero: " + selectedRadio.getText(),
Toast.LENGTH_SHORT).show();
}
});
// Listener para RadioGroup Tama帽o
radioGroupSize.setOnCheckedChangeListener((group, checkedId) -> {
RadioButton selectedRadio = findViewById(checkedId);
if (selectedRadio != null) {
Toast.makeText(this,
"Tama帽o: " + selectedRadio.getText(),
Toast.LENGTH_SHORT).show();
}
});
// Listener para RadioGroup Plan
radioGroupPlan.setOnCheckedChangeListener((group, checkedId) -> {
if (checkedId == R.id.radioBasic) {
Toast.makeText(this, "Plan B谩sico seleccionado", Toast.LENGTH_SHORT).show();
} else if (checkedId == R.id.radioPremium) {
Toast.makeText(this, "Plan Premium seleccionado", Toast.LENGTH_SHORT).show();
}
});
// Listener para RadioGroup Pago
radioGroupPayment.setOnCheckedChangeListener((group, checkedId) -> {
RadioButton selectedRadio = findViewById(checkedId);
if (selectedRadio != null) {
Toast.makeText(this,
"Pago: " + selectedRadio.getText(),
Toast.LENGTH_SHORT).show();
}
});
// Bot贸n Enviar
btnSubmit.setOnClickListener(v -> submitForm());
// Bot贸n Limpiar
btnClear.setOnClickListener(v -> clearSelections());
}
private void submitForm() {
StringBuilder result = new StringBuilder();
boolean isValid = true;
// Validar G茅nero
int genderId = radioGroupGender.getCheckedRadioButtonId();
if (genderId == -1) {
result.append("❌ Selecciona un g茅nero\n");
isValid = false;
} else {
RadioButton selectedGender = findViewById(genderId);
result.append("✓ G茅nero: ").append(selectedGender.getText()).append("\n");
}
// Validar Tama帽o
int sizeId = radioGroupSize.getCheckedRadioButtonId();
if (sizeId == -1) {
result.append("❌ Selecciona un tama帽o\n");
isValid = false;
} else {
RadioButton selectedSize = findViewById(sizeId);
result.append("✓ Tama帽o: ").append(selectedSize.getText()).append("\n");
}
// Validar Plan
int planId = radioGroupPlan.getCheckedRadioButtonId();
if (planId == -1) {
result.append("❌ Selecciona un plan\n");
isValid = false;
} else {
String planName = planId == R.id.radioBasic ? "B谩sico" : "Premium";
result.append("✓ Plan: ").append(planName).append("\n");
}
// Validar M茅todo de Pago
int paymentId = radioGroupPayment.getCheckedRadioButtonId();
if (paymentId == -1) {
result.append("❌ Selecciona m茅todo de pago\n");
isValid = false;
} else {
RadioButton selectedPayment = findViewById(paymentId);
result.append("✓ Pago: ").append(selectedPayment.getText()).append("\n");
}
// Mostrar resultado
txtResult.setVisibility(View.VISIBLE);
if (isValid) {
txtResult.setBackgroundColor(0xFFE8F5E9);
txtResult.setTextColor(0xFF4CAF50);
result.insert(0, "✅ Formulario V谩lido\n\n");
Toast.makeText(this, "Formulario enviado correctamente", Toast.LENGTH_SHORT).show();
} else {
txtResult.setBackgroundColor(0xFFFFEBEE);
txtResult.setTextColor(0xFFF44336);
result.insert(0, "⚠️ Formulario Incompleto\n\n");
}
txtResult.setText(result.toString());
}
private void clearSelections() {
radioGroupGender.clearCheck();
radioGroupSize.clearCheck();
radioGroupPlan.clearCheck();
radioGroupPayment.clearCheck();
txtResult.setVisibility(View.GONE);
Toast.makeText(this, "Selecciones limpiadas", Toast.LENGTH_SHORT).show();
}
}馃煩 7. RadioButton Personalizado
馃搫 res/drawable/radio_selector.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Estado seleccionado -->
<item android:state_checked="true">
<shape android:shape="oval">
<solid android:color="#2196F3" />
<size android:width="24dp" android:height="24dp" />
<stroke android:width="2dp" android:color="#2196F3" />
</shape>
</item>
<!-- Estado no seleccionado -->
<item android:state_checked="false">
<shape android:shape="oval">
<solid android:color="#FFFFFF" />
<size android:width="24dp" android:height="24dp" />
<stroke android:width="2dp" android:color="#CCCCCC" />
</shape>
</item>
</selector>Aplicar:
<RadioButton
android:button="@drawable/radio_selector"
android:text="Opci贸n personalizada" />馃煩 8. M茅todos Principales
| M茅todo | Descripci贸n |
|---|---|
setChecked(boolean) | Seleccionar RadioButton |
isChecked() | Verificar si est谩 seleccionado |
getCheckedRadioButtonId() | Obtener ID del seleccionado |
clearCheck() | Limpiar selecci贸n |
check(int) | Seleccionar por ID |
setOnCheckedChangeListener() | Detectar cambios |
馃煩 9. Validaci贸n de RadioGroup
private boolean isRadioGroupSelected(RadioGroup radioGroup) {
return radioGroup.getCheckedRadioButtonId() != -1;
}
private String getSelectedRadioText(RadioGroup radioGroup) {
int selectedId = radioGroup.getCheckedRadioButtonId();
if (selectedId != -1) {
RadioButton radioButton = findViewById(selectedId);
return radioButton.getText().toString();
}
return null;
}馃煩 10. RadioButton Din谩mico
private void addRadioButtonDynamically(RadioGroup radioGroup, String text) {
RadioButton radioButton = new RadioButton(this);
radioButton.setText(text);
radioButton.setTextSize(16);
radioButton.setPadding(8, 8, 8, 8);
RadioGroup.LayoutParams params = new RadioGroup.LayoutParams(
RadioGroup.LayoutParams.WRAP_CONTENT,
RadioGroup.LayoutParams.WRAP_CONTENT
);
radioButton.setLayoutParams(params);
radioGroup.addView(radioButton);
}馃煩 11. Material RadioButton
<com.google.android.material.radiobutton.MaterialRadioButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Material Radio"
app:buttonTint="#2196F3" />馃煩 12. Comparaci贸n CheckBox vs RadioButton
| Caracter铆stica | RadioButton | CheckBox |
|---|---|---|
| Selecci贸n | 脷nica | M煤ltiple |
| Agrupaci贸n | RadioGroup | Sin grupo |
| Deselecci贸n | Solo seleccionando otro | Click directo |
| Uso | Opciones excluyentes | Opciones independientes |
▶️ C贸mo Ejecutar
- Abre Android Studio
- Crea el proyecto
- Copia el c贸digo
- Presiona Run
- Prueba las diferentes opciones
馃И Resultado Final
Aplicaci贸n con m煤ltiples RadioGroups, validaci贸n completa y diferentes estilos de presentaci贸n.
馃摜 Descargar Proyecto
馃憠
馃檶 Gracias por Visitar mi Blog
✔️ Comp谩rtelo
✔️ D茅jame un comentario
✔️ S铆gueme para m谩s contenido
❓ Preguntas Frecuentes
1. ¿Cu谩l es la diferencia entre RadioButton y CheckBox?
RadioButton permite selecci贸n 煤nica en un grupo. CheckBox permite m煤ltiples selecciones independientes.
2. ¿C贸mo deseleccionar un RadioButton?
Solo seleccionando otro RadioButton del mismo grupo, o usando clearCheck() en el RadioGroup.
3. ¿Puedo tener RadioButtons sin RadioGroup?
S铆, pero perder谩s la funcionalidad de selecci贸n 煤nica autom谩tica.
4. ¿C贸mo valido que se haya seleccionado algo?
Verifica que getCheckedRadioButtonId() no retorne -1.

No hay comentarios:
Publicar un comentario