Skip to content

Conversation

@alex-medinsh
Copy link
Contributor

@alex-medinsh alex-medinsh commented Jun 5, 2025

This PR adds a check to didUpdateWidget to make sure that the latest value is rendered if it was updated during the onChanged callback.

Fixes #169983

Pre-launch Checklist

  • I read the [Contributor Guide] and followed the process outlined there for submitting PRs.
  • I read the [Tree Hygiene] wiki page, which explains my responsibilities.
  • I read and followed the [Flutter Style Guide], including [Features we expect every widget to implement].
  • I signed the [CLA].
  • I listed at least one issue that this PR fixes in the description above.
  • I updated/added relevant documentation (doc comments with ///).
  • I added new tests to check the change I am making, or this PR is [test-exempt].
  • I followed the [breaking change policy] and added [Data Driven Fixes] where supported.
  • All existing and new tests are passing.

@github-actions github-actions bot added framework flutter/packages/flutter repository. See also f: labels. f: material design flutter/packages/flutter/material repository. labels Jun 5, 2025
@alex-medinsh alex-medinsh marked this pull request as ready for review June 5, 2025 08:29
@dkwingsmt
Copy link
Contributor

dkwingsmt commented Jun 11, 2025

@bleroux Would you like to review this PR? Seems like you recently edited this widget.

@bleroux bleroux changed the title Fix DropdownMenuFormField not updating when value updated in onChanged Fix DropdownButtonFormField not updating when value updated in onChanged Jun 12, 2025
@bleroux
Copy link
Contributor

bleroux commented Jun 12, 2025

Thanks for working on this. 🙏

Unfortunately, this change is problematic. The new logic will reset the DropdownMenuFormField selected value to initialValue when not expected. For instance, with the following code sample it will be impossible to change the selected value:

Sample code
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(
      home: Scaffold(body: Padding(padding: EdgeInsets.all(8.0), child: HomePage())),
    );
  }
}

class HomePage extends StatefulWidget {
  const HomePage({super.key});

  @override
  State<HomePage> createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  int count = 0;

  static final List<DropdownMenuItem<String>> menuItems =
      ['A', 'B', 'C', 'D'].map((String item) {
        return DropdownMenuItem<String>(value: item, child: Text(item));
      }).toList();

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        const SizedBox(height: 20),
        DropdownButtonFormField<String>(
          value: 'A',
          items: menuItems,
          onChanged: (String? value) {
            setState(() {
              count++;
            });
          },
          decoration: InputDecoration(
            labelText: 'Edition n°$count',
            border: const OutlineInputBorder(),
          ),
        ),
      ],
    );
  }
}

(Just run the code sample and try to select an item in the menu, without this PR it works, with it the selection can’t be changed).

The root of this problem and of #169983, is that DropdownMenuFormField.value is confusing because it does not mean the same thing as DropdownMenu.value:

  • DropdownMenu.value is the value of the selected item.
  • DropdownMenuFormField.value is the initialValue of the form field, it is meant to be apply when the field is first built and when it is reset.

Deprecating DropdownMenuFormField.value and renaming it DropdownMenuFormField.initialValue was considered, see #144135 (comment) which explains why this was not done and why the documentation was updated instead.

@justinmc @QuncCccccc Do you think we should revisit this decision and rename this field?

@alex-medinsh
Copy link
Contributor Author

Thanks for your clarification! My understanding about the value parameter was incorrect. So, if the value parameter is actually the initial value and works as expected, does that mean that doing something like #169983 is not actually supported?

@bleroux
Copy link
Contributor

bleroux commented Jun 12, 2025

Does that mean that doing something like #169983 is not actually supported?

I commented on #169983 (comment) to explain how it can be done with the current API.
I agree this is not very intuitive 😅

@alex-medinsh
Copy link
Contributor Author

I guess we can close this then? Maybe there should be a test similar to your example code, so that changes like mine don't get past 😄

@bleroux
Copy link
Contributor

bleroux commented Jun 12, 2025

I guess we can close this then?

Yes, sorry for the inconvenience.

Maybe there should be a test similar to your example code, so that changes like mine don't get past 😄

That's very true, if you want to file a PR to add such a test, it will be welcomed. If not I will try to file one next week.

@alex-medinsh
Copy link
Contributor Author

Do you prefer if I open a new PR or repurpose this one?

@bleroux
Copy link
Contributor

bleroux commented Jun 12, 2025

Do you prefer if I open a new PR or repurpose this one?

If possible open a new one as it will make things easier to track for people who will read this in some years 😄

@alex-medinsh
Copy link
Contributor Author

Opened a new PR

@justinmc
Copy link
Contributor

@justinmc @QuncCccccc Do you think we should revisit this decision and rename this field?

I say it should be renamed! Assuming any effort to migrate is not too crazy.

github-merge-queue bot pushed a commit that referenced this pull request Jun 16, 2025
This PR adds a new test that verifies that the value param is only used
on initial build and when resetting the field.

Test for
#170050 (comment)

## Pre-launch Checklist

- [x] I read the [Contributor Guide] and followed the process outlined
there for submitting PRs.
- [x] I read the [Tree Hygiene] wiki page, which explains my
responsibilities.
- [x] I read and followed the [Flutter Style Guide], including [Features
we expect every widget to implement].
- [x] I signed the [CLA].
- [x] I listed at least one issue that this PR fixes in the description
above.
- [x] I updated/added relevant documentation (doc comments with `///`).
- [x] I added new tests to check the change I am making, or this PR is
[test-exempt].
- [x] I followed the [breaking change policy] and added [Data Driven
Fixes] where supported.
- [x] All existing and new tests are passing.

---------

Co-authored-by: Bruno Leroux <[email protected]>
github-merge-queue bot pushed a commit that referenced this pull request Jun 24, 2025
…ialValue" (#170805)

## Description

This PR renames the DropdownButtonFormField constuctor parameter 'value'
to 'initialValue'.
See
#170050 (comment)
and
#170050 (comment)
for some context.

## Related Issue

Fixes [DropdownButtonFormField retains selected value even after setting
value to null](#169983 (comment))

## Tests

Adds 2 tests (one to validate the deprecated parameter can still be
used, one for the dart fix).
Updates many (renaming the confusing parameter).
@alex-medinsh alex-medinsh deleted the dropdownbutton-formfield-null branch July 2, 2025 08:01
mboetger pushed a commit to mboetger/flutter that referenced this pull request Jul 21, 2025
This PR adds a new test that verifies that the value param is only used
on initial build and when resetting the field.

Test for
flutter#170050 (comment)

## Pre-launch Checklist

- [x] I read the [Contributor Guide] and followed the process outlined
there for submitting PRs.
- [x] I read the [Tree Hygiene] wiki page, which explains my
responsibilities.
- [x] I read and followed the [Flutter Style Guide], including [Features
we expect every widget to implement].
- [x] I signed the [CLA].
- [x] I listed at least one issue that this PR fixes in the description
above.
- [x] I updated/added relevant documentation (doc comments with `///`).
- [x] I added new tests to check the change I am making, or this PR is
[test-exempt].
- [x] I followed the [breaking change policy] and added [Data Driven
Fixes] where supported.
- [x] All existing and new tests are passing.

---------

Co-authored-by: Bruno Leroux <[email protected]>
mboetger pushed a commit to mboetger/flutter that referenced this pull request Jul 21, 2025
…ialValue" (flutter#170805)

## Description

This PR renames the DropdownButtonFormField constuctor parameter 'value'
to 'initialValue'.
See
flutter#170050 (comment)
and
flutter#170050 (comment)
for some context.

## Related Issue

Fixes [DropdownButtonFormField retains selected value even after setting
value to null](flutter#169983 (comment))

## Tests

Adds 2 tests (one to validate the deprecated parameter can still be
used, one for the dart fix).
Updates many (renaming the confusing parameter).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

f: material design flutter/packages/flutter/material repository. framework flutter/packages/flutter repository. See also f: labels.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

DropdownButtonFormField retains selected value even after setting value to null

4 participants