How to update a "Widget build(BuildContext context)" in flutter

84 Views Asked by At

I am kind of stuck with flutter code here. I'm using 2 dropdown_button2's for choosing destinations which are going alright, but I added a separated class for a "switch destination button" which store both destination's in a string? variable. That's working well. but I can't seem to get the widgets to update without clicking the dropdown_button (then I see that they are updated behind the list).

    class Dropdwn extends StatefulWidget {
      const Dropdwn({Key? key}) : super(key: key);

      @override
      State<Dropdwn> createState() => DropdwnState();
    }

    class DropdwnState extends State<Dropdwn> {
      static List _stations = [];
      static List<String> stringList = [];
      String? value;
      @override
      void initState() {
        super.initState();
        readJsonData();
   
      }

    //i call this void from another class below, but setState does not trigger Widget build to   update..
      void reinitState() {
        setState(() {
          departvalue = selectedValue;
     selectedValue ="Maarheeze" ;
          value = selectedValue;
          print("Vans: $selectedValue");
        });
      }


  @override
  void dispose() {
    textEditingController.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    // print(stringList);

    return Container(
      child: DropdownButtonHideUnderline(
        child: DropdownButton2<String>(
          isExpanded: true,
          hint: Text(
            'Station',
            style: TextStyle(
              fontSize: 14,
              color: Bcolors.textSecondary,
            ),
          ),
          items: DropdwnState.stringList
              .map((item1) => DropdownMenuItem(
                    value: item1,
                    child: Text(
                      item1,
                      style: const TextStyle(
                        fontSize: 14,
                        color: Bcolors.textSecondary,
                      ),
                    ),
                  ))
              .toList(),

          value: selectedValue,

          onChanged: (value) {
            setState(() {
              selectedValue = value;
            });
          },

          buttonStyleData: const ButtonStyleData(
            padding: EdgeInsets.symmetric(horizontal: 16),
            height: 40,
            width: 200,
          ),
          dropdownStyleData: DropdownStyleData(
            width: 300,
            padding: const EdgeInsets.symmetric(vertical: 6),
            decoration: BoxDecoration(
              borderRadius: BorderRadius.circular(4),
              color: Bcolors.secondaryBackground,
            ),
            offset: const Offset(40, -4),
          ),
          iconStyleData: const IconStyleData(
            icon: Icon(
              Icons.arrow_forward_ios_outlined,
            ),
            iconSize: 14,
            iconEnabledColor: Bcolors.secondaryBackground,
            iconDisabledColor: Bcolors.secondaryBackground,
          ),
          menuItemStyleData: const MenuItemStyleData(
            height: 40,
          ),
          dropdownSearchData: DropdownSearchData(
            searchController: textEditingController,
            searchInnerWidgetHeight: 50,
            searchInnerWidget: Container(
              height: 50,
              padding: const EdgeInsets.only(
                top: 8,
                bottom: 4,
                right: 8,
                left: 8,
              ),
              child: TextFormField(
                expands: true,
                maxLines: null,
                controller: textEditingController,
                decoration: InputDecoration(
                  isDense: true,
                  contentPadding: const EdgeInsets.symmetric(
                    horizontal: 10,
                    vertical: 8,
                  ),
                  hintText: 'Zoeken',
                  hintStyle: const TextStyle(
                    fontSize: 12,
                    color: Bcolors.textSecondary,
                  ),
                  border: OutlineInputBorder(
                    borderRadius: BorderRadius.circular(8),
                    borderSide: BorderSide(color: Colors.pinkAccent),
                  ),
                ),
              ),
            ),
            searchMatchFn: (dropdownKey, searchValue) {
              return dropdownKey.value
                  .toString()
                  .toLowerCase()
                  .contains(searchValue.toLowerCase());
            },
          ),
          //This to clear the search value when you close the menu
          onMenuStateChange: (isOpen) {
            readJsonData();
            if (!isOpen) {
              textEditingController.clear();
            }
          },
        ),
      ),
    );
  }
}

class button extends StatefulWidget {
  const button({Key? key}) : super(key: key);

  @override
  _MyWidgetState createState() => _MyWidgetState();
}

class _MyWidgetState extends State<button> {
  GlobalKey<DropdwnState> _key = GlobalKey();

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        IconButton(
          icon: Icon(
            Icons.swap_calls,
            color: Bcolors.textSecondary,
          ),
          onPressed: () {
            setState(() {
              _key.currentState?.reinitState();
            });
          },
        ),
        Dropdwn(key: _key),
      ],
    );
  }
}

I tried globalkey as you see, class button calls

onPressed: () {
            setState(() {
              _key.currentState?.reinitState();


where in DropdownState:
  void reinitState() {
    setState(() {
      departvalue = selectedValue;
 selectedValue ="Maarheeze" ;
      value = selectedValue;
      print("Vans: $selectedValue");
    });
  }

a setState is triggered changing selectedValue to Maarheeze.

only when I open the dropdownmenu, I can see the selected value update.

1

There are 1 best solutions below

1
FaBotch On

What happened if you declare an other GlobalKey inside DropdwnState?

final GlobalKey<DropdwnState> _dropdwnKey = GlobalKey<DropdwnState>();

and

  void reinitState() {
    _dropdwnKey.currentState?.setState(() {
      departvalue = selectedValue;
      selectedValue = "Maarheeze";
      value = selectedValue;
      print("Vans: $selectedValue");
    });
  }

and

@override
  Widget build(BuildContext context) {

    return Container(
      child: DropdownButtonHideUnderline(
        child: DropdownButton2<String>(
          // ...
          key: _dropdwnKey, // Assign the global key to the DropdownButton
          // ...
        ),
      ),
    );
  }