skip to Main Content

I am implementing a sort by function which displays sort options through a modal bottom sheet, I am able to do it in my "Home Page" widget. Would like to check if I can extract these codes and sub it as a widget for better organization. I am unable to do as I am concerned with the return values from the radio value.

Appreciate any help given, thanks!!

Here is my code:

child: TextButton.icon( // Button to press sort 
    onPressed: (() {
      showModalBottomSheet( // show modal 
          shape: RoundedRectangleBorder(
              borderRadius:
                  BorderRadius.circular(10.0)),
          context: context,
          builder: (BuildContext build) {
            return Column(
              mainAxisSize: MainAxisSize.min,
              children: <Widget>[ // radio values 
                RadioListTile(
                  value: 1,
                  groupValue: selectedRadioTile,
                  title: Text(
                      "Case Earliest to Latest"),
                  onChanged: (val) {
                    print(
                        "Radio Tile pressed $val");
                    setSelectedRadioTile(val!);
                    print(selectedRadioTile);
                    Navigator.pop(context);
                  },
                  activeColor:
                      constants.secondaryBlueColour,
                ),
                RadioListTile(
                  value: 2,
                  groupValue: selectedRadioTile,
                  title: Text(
                      "Case Latest to Earliest "),
                  onChanged: (val) {
                    print(
                        "Radio Tile pressed $val");
                    setSelectedRadioTile(val!);
                    print(selectedRadioTile);
                    Navigator.pop(context);
                  },
                  activeColor:
                      constants.secondaryBlueColour,
                )
              ],
            );
          });
    }),
    icon: Icon(
      Icons.sort,
      size: 28,
      color: constants.textGrayColour,
    ),
    label: Text("Sort",
        style: TextStyle(
            color: constants.textGrayColour,
            fontWeight: FontWeight.bold)))),***
    Container(
      margin: const EdgeInsets.only(top: 5),
      width: MediaQuery.of(context).size.width * 0.5,
      decoration: BoxDecoration(
          border: Border(
        left: BorderSide(
            width: 2.0,
            color:
                constants.categoryButtonBackgroundColour),
        bottom: BorderSide(
            width: 2.0,
            color:
                constants.categoryButtonBackgroundColour),
      )),
      child: TextButton.icon(
          onPressed: () {},
          icon: Icon(Icons.filter_alt,
              size: 28, color: constants.textGrayColour),
          label: Text("Filter",
              style: TextStyle(
                  color: constants.textGrayColour,
                  fontWeight: FontWeight.bold))),
    ),
  ],
),

I implemented a SortWidget() but am wondering how I can return the current radio value to my homepage and set the state in the homepage based on the radio value

2

Answers


  1. showModalBottomSheet is a future method, you can use async method for this. and Navigator.pop(context, value); will give you the result. you can also used callback method, seems not needed for your case.

    onPressed:()async {
      final value = await showModalBottomSheet(
        shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(10.0)),
        context: context,
        builder: (BuildContext build) {
          return MyBottomSheetWidget(selectedRadioTile: selectedRadioTile);
        },
      );
       print("$value");
    }
    
    class MyBottomSheetWidget extends StatelessWidget {
      // make it statefulWidget if you want to update dialog ui
      const MyBottomSheetWidget({
        Key? key,
        required this.selectedRadioTile,
      }) : super(key: key);
    
      final selectedRadioTile;
    
      @override
      Widget build(BuildContext context) {
        return Column(
          mainAxisSize: MainAxisSize.min,
          children: <Widget>[
            // radio values
            RadioListTile(
              value: 1,
              groupValue: selectedRadioTile,
              title: Text("Case Earliest to Latest"),
              onChanged: (val) {
                print("Radio Tile pressed $val");
    
                Navigator.pop(context, val);
              },
            ),
            RadioListTile(
              value: 2,
              groupValue: selectedRadioTile,
              title: Text("Case Latest to Earliest "),
              onChanged: (val) {
                print("Radio Tile pressed $val");
                // setSelectedRadioTile(val!);
                print(selectedRadioTile);
                Navigator.pop(context, val);
              },
            )
          ],
        );
      }
    }
    
    Login or Signup to reply.
  2. showModalBottomSheet is actually a function which can’t converted to widget without having some other widget in place. What you can do is, create a function which hold code of this showModalBottomSheet and call that function on button click.

    But if you want to create a separate widget then you can create the widget from the internal code of the showModalBottomSheet which starts with return Column.

    You need to create a widget which can take two properties which are int variable named selected and a Function named setSelected. Then you can call that widget from inside the showModalBottomSheet and pass two props from your page. This selected will be set as selectedRadioTile & setSelected will be set as setSelectedRadioTile.

    Example Code

    class BottomFilter extends StatelessWidget {
      const BottomFilter(
          {Key? key,
          required this.selected,
          required this.setSelected})
          : super(key: key);
    
      final int selected;
      final Function setSelected;
      @override
      Widget build(BuildContext context) {
        return Column(
          mainAxisSize: MainAxisSize.min,
          children: <Widget>[
            // radio values
            RadioListTile(
              value: 1,
              groupValue: selected,
              title: Text("Case Earliest to Latest"),
              onChanged: (val) {
                print("Radio Tile pressed $val");
                setSelected(val!);
                print(selected);
                Navigator.pop(context);
              },
              activeColor: Colors.amber,
            ),
            RadioListTile(
              value: 2,
              groupValue: selected,
              title: Text("Case Latest to Earliest "),
              onChanged: (val) {
                print("Radio Tile pressed $val");
                setSelected(val!);
                print(selected);
                Navigator.pop(context);
              },
              activeColor: Colors.amber,
            )
          ],
        );
      }
    }
    

    Call it like this

    builder: (BuildContext build) {
              return BottomFilter(selected: selectedRadioTile, setSelected:  setSelectedRadioTile);
            })
    

    Dartpad link to test this code https://dartpad.dev/?id=9359bc416ae48b996085d6f98a977e27

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search