Skip to content

Unable to change Radio() widget fillColor with ThemeData.radioTheme #159269

@kosiara

Description

@kosiara

Steps to reproduce

One cannot define a Theme for a Radio button widget which changes the fillColor :

                              Theme(
                                data: ThemeData(
                                  radioTheme: RadioThemeData(
                                    fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
                                      if (states.contains(MaterialState.disabled)) {
                                        return Colors.blueAccent.withOpacity(.32);
                                      }
                                      return Colors.blueAccent;
                                    }),
                                  ),
                                ),
                                child: Radio(
                                    value: deliveryOptions[0],
                                    groupValue: currentDeliveryMethod,
                                    onChanged: _radioChanged,
                                  ),
                              )

I believe it's because of the way Radio() widget is defined in
./packages/flutter/lib/src/material/radio.dart

especially:

line: 485

final Color? activeColor = widget.fillColor?.resolve(activeStates)
      ?? _widgetFillColor.resolve(activeStates)
      ?? radioTheme.fillColor?.resolve(activeStates);

where _widgetFillColor is always defined to be:

MaterialStateProperty<Color?> get _widgetFillColor {
    return MaterialStateProperty.resolveWith((Set<MaterialState> states) {
      if (states.contains(MaterialState.disabled)) {
        return null;
      }
      if (states.contains(MaterialState.selected)) {
        return widget.activeColor;
      }
      return null;
    });
  }

a hotfix for that would be to define it directly in the Radio widget:

                                Radio(
                                    fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
                                       if (states.contains(MaterialState.disabled)) {
                                         return Colors.blueAccent.withOpacity(.32);
                                       }
                                       return Colors.blueAccent;
                                     }),
                                    value: deliveryOptions[0],
                                    groupValue: currentDeliveryMethod,
                                    onChanged: _radioChanged,
                                  ),

Expected results

Expected result would be to respect context.theme.themeData.radioTheme.fillColor data in Radio() widget

                              Theme(
                                data: ThemeData(
                                  radioTheme: RadioThemeData(
                                    fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
                                      if (states.contains(MaterialState.disabled)) {
                                        return Colors.blueAccent.withOpacity(.32);
                                      }
                                      return Colors.blueAccent;
                                    }),
                                  ),
                                ),
                                child: Radio(
                                    value: deliveryOptions[0],
                                    groupValue: currentDeliveryMethod,
                                    onChanged: _radioChanged,
                                  ),
                              )

Actual results

Radio() widget ignores context.theme.themeData.radioTheme.fillColor and is always the default color unless one overrides fillColor directly in the Widget

Code sample

Code sample
                              Theme(
                                data: ThemeData(
                                  radioTheme: RadioThemeData(
                                    fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
                                      if (states.contains(MaterialState.disabled)) {
                                        return Colors.blueAccent.withOpacity(.32);
                                      }
                                      return Colors.blueAccent;
                                    }),
                                  ),
                                ),
                                child: Radio(
                                    value: deliveryOptions[0],
                                    groupValue: currentDeliveryMethod,
                                    onChanged: _radioChanged,
                                  ),
                              )

Screenshots or Video

Screenshots / Video demonstration

[Upload media here]

Flutter Doctor output

Doctor output
Doctor summary (to see all details, run flutter doctor -v):
[✓] Flutter (Channel stable, 3.24.0, on macOS 14.5 23F79 darwin-arm64, locale en-US)
[✓] Android toolchain - develop for Android devices (Android SDK version 34.0.0)
[✓] Xcode - develop for iOS and macOS (Xcode 16.0)
[✓] Chrome - develop for the web
[✓] Android Studio (version 2023.3)
[✓] Android Studio (version 2024.2)
[✓] Android Studio (version 2023.1)
[✓] Android Studio (version 2022.3)
[✓] IntelliJ IDEA Community Edition (version 2023.2)
[✓] VS Code (version 1.89.0)
[✓] Connected device (4 available)
[✓] Network resources

Metadata

Metadata

Assignees

Labels

Bot is counting down the days until it unassigns the issueP2Important issues not at the top of the work listf: material designflutter/packages/flutter/material repository.f: themingStyling widgets with a themeframeworkflutter/packages/flutter repository. See also f: labels.good first issueRelatively approachable for first-time contributorsr: solvedIssue is closed as solvedteam-designOwned by Design Languages teamtriaged-designTriaged by Design Languages team

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions