This code demonstrates how to create a multiple-choice alert dialog in an Android application using Kotlin. The dialog allows users to select their favorite colors from a predefined list, with a minimum selection requirement of two. The code provides a detailed explanation of the functionalities and utilizes Material Design components for a modern look.
Breakdown of the Code:
MainActivity.kt:
- This file contains the main logic for the application.
- It defines an
onCreatefunction responsible for setting up the UI and the button click listener. - Clicking the button triggers the creation of the alert dialog.
- The code builds the dialog using
MaterialAlertDialogBuilderand defines functionalities for the positive ("Submit"), neutral ("Cancel") buttons, and the list item clicks. - It keeps track of selected colors and updates the TextView accordingly.
activity_main.xml:
- This file defines the layout of the activity.
- It contains a Button to trigger the dialog and a TextView to display the selected colors.
build.gradle:
- This file specifies the dependencies required for the project.
- In this case, it includes the Material Design library (
com.google.android.material:material:1.6.1) for UI components.
Summary
This code snippet provides a comprehensive example of creating a multiple-choice alert dialog in Kotlin. It demonstrates key functionalities like handling user selections, updating UI elements based on selections, and enforcing minimum selection requirements. By utilizing Material Design components, the code ensures a consistent and modern look for the dialog.
MainActivity.kt
package com.cfsuman.kotlintutorials
import android.os.Bundle
import android.widget.*
import androidx.appcompat.app.AlertDialog
import androidx.appcompat.app.AppCompatActivity
import com.google.android.material.dialog.MaterialAlertDialogBuilder
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val context:MainActivity = this
// get the widgets reference from XML layout
val button = findViewById<Button>(R.id.button)
val textView = findViewById<TextView>(R.id.textView)
// initial checked items
val initialCheckedItems = mutableListOf<Boolean>()
button.setOnClickListener {
val builder = MaterialAlertDialogBuilder(context)
// dialog title
builder.setTitle("Select favorite colors (min 2)")
val colors = arrayOf(
"African violet",
"Alice blue",
"Alloy orange",
"Android green",
"Amaranth pink",
"Antique bronze"
)
if (initialCheckedItems.isEmpty()){
repeat(colors.count()) {initialCheckedItems.add(false)}
}
builder.setMultiChoiceItems(
colors,
initialCheckedItems.toBooleanArray()
) { dialog, which, isChecked ->}
// alert dialog positive button
builder.setPositiveButton("Submit"){dialog,which->
val alertDialog = dialog as AlertDialog
val sparseBooleanArray = alertDialog
.listView.checkedItemPositions
var counter = 0
textView.text = ""
colors.forEachIndexed { index, s ->
if (sparseBooleanArray.get(index, false)) {
textView.append("\n$s")
counter += 1
}
}
if (counter > 0) {
textView.text = "Selected colors: " + textView.text
}
}
// alert dialog neutral button
builder.setNeutralButton("Cancel"){dialog,which->
textView.text = ""
}
// set dialog non cancelable
builder.setCancelable(false)
// finally, create the alert dialog and show it
val dialog = builder.create()
dialog.show()
// initially enable disable the positive button
if((initialCheckedItems.filter { it }).size < 2){
dialog.getButton(
AlertDialog.BUTTON_POSITIVE).isEnabled = false
}
// dialog list item click listener
dialog.listView.onItemClickListener =
AdapterView.OnItemClickListener {
parent, view, position, id ->
val sparseBooleanArray = dialog.listView
.checkedItemPositions
var checkedItems = 0
colors.forEachIndexed { index, s ->
if (sparseBooleanArray.get(index,false)){
checkedItems +=1
initialCheckedItems[index] = true
}else{
initialCheckedItems[index] = false
}
}
dialog.getButton(AlertDialog.BUTTON_POSITIVE)
.isEnabled = checkedItems >=2
}
}
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#DCDCDC"
android:padding="24dp">
<Button
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Show Dialog"
android:textAllCaps="false"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/textView"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginTop="24dp"
android:fontFamily="sans-serif"
android:textSize="24sp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/button" />
</androidx.constraintlayout.widget.ConstraintLayout>
build.gradle dependencies[add]
// Material components
implementation 'com.google.android.material:material:1.6.1'

