ChipGroup single selection ChipGroup single selection android android

ChipGroup single selection


To prevent all chips from being deselected you can use the method setSelectionRequired:

chipGroup.setSelectionRequired(true)

You can also define it in the layout using the app:selectionRequired attribute:

<com.google.android.material.chip.ChipGroup    app:singleSelection="true"    app:selectionRequired="true"    app:checkedChip="@id/..."    ..>

Note: This requires a minimum of version 1.2.0


EDIT

With version 1.2.0-alpha02 the old hacky solution is no longer required!

Either use the attribute app:selectionRequired="true"

<com.google.android.material.chip.ChipGroup            android:id="@+id/group"            android:layout_width="match_parent"            android:layout_height="wrap_content"            app:selectionRequired="true"            app:singleSelection="true">  (...)</com.google.android.material.chip.ChipGroup>

Or in code

// Kotlingroup.isSelectionRequired = true// Javagroup.setSelectionRequired(true);

For older versions 👇

There are two steps to achieve this

Step 1

We have this support built-in, just make sure to add app:singleSelection="true" to your ChipGroup, for example:

XML

<com.google.android.material.chip.ChipGroup            android:id="@+id/group"            android:layout_width="match_parent"            android:layout_height="wrap_content"            app:singleSelection="true">        <com.google.android.material.chip.Chip                android:id="@+id/option_1"                style="@style/Widget.MaterialComponents.Chip.Choice"                android:layout_width="wrap_content"                android:layout_height="wrap_content"                android:text="Option 1" />        <com.google.android.material.chip.Chip                android:id="@+id/option_2"                style="@style/Widget.MaterialComponents.Chip.Choice"                android:layout_width="wrap_content"                android:layout_height="wrap_content"                android:text="Option 2" /></com.google.android.material.chip.ChipGroup>

Code

// Kotlingroup.isSingleSelection = true// Javagroup.setSingleSelection(true);

Step 2

Now to support a radio group like functionality:

var lastCheckedId = View.NO_IDchipGroup.setOnCheckedChangeListener { group, checkedId ->    if(checkedId == View.NO_ID) {        // User tried to uncheck, make sure to keep the chip checked                  group.check(lastCheckedId)        return@setOnCheckedChangeListener    }    lastCheckedId = checkedId    // New selection happened, do your logic here.    (...)}

From the docs:

ChipGroup also supports a multiple-exclusion scope for a set of chips. When you set the app:singleSelection attribute, checking one chip that belongs to a chip group unchecks any previously checked chip within the same group. The behavior mirrors that of RadioGroup.


A solution would be to preset a clicked chip and then toggling the clickable property of the chips:

chipGroup.setOnCheckedChangeListener((chipGroup, id) -> {    Chip chip = ((Chip) chipGroup.getChildAt(chipGroup.getCheckedChipId()));    if (chip != null) {        for (int i = 0; i < chipGroup.getChildCount(); ++i) {            chipGroup.getChildAt(i).setClickable(true);        }        chip.setClickable(false);    }});