Home > Software engineering >  pass data of type int from one child Widget to Parent. dynamic Function(int) can't be assigned
pass data of type int from one child Widget to Parent. dynamic Function(int) can't be assigned

Time:10-31

Im trying to make an Star Pattern Generator in Flutter. I pass Data from type int in a callback function from the child widget: Textfield Widget to the parent Widget CustomBarWidget and after to the Toplevel parent Widget RootPage.

At the Textfield I got an Error at the Line:

onChanged: widget.onChange,

The Error says: The argument type 'dynamic Function(int)' can't be assigned to the parameter type void Function(String)?

Here is the Full Code:

RootPage:

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

  @override
  State<RootPage> createState() => _RootPageState();
}

class _RootPageState extends State<RootPage> {
  int data = 5;

  void getData(int newNumb) {
    setState(() {
      data = newNumb;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: CustomBarWidget(sendData: getData),
      body: StarTriangleWidget(data: data),
    );
  }
}

CustomBarWidget:

class CustomBarWidget extends StatefulWidget implements PreferredSizeWidget {
  const CustomBarWidget({super.key, this.sendData});
  final sendData;

  @override
  Size get preferredSize => const Size.fromHeight(70.0);

  @override
  State<CustomBarWidget> createState() => _CustomBarWidgetState();
}

class _CustomBarWidgetState extends State<CustomBarWidget> {
  int data = 0;

  @override
  Widget build(BuildContext context) {
    return AppBar(
      backgroundColor: Colors.transparent,
      elevation: 0,
      title: Row(
        children: <Widget>[
          TextfielWidget(onChange: (val) {
            widget.sendData(val);
          }),
          ElevatedButton(
            onPressed: () {
              debugPrint("click");
            },
            style: ElevatedButton.styleFrom(
              padding:
                  const EdgeInsets.symmetric(horizontal: 40.0, vertical: 15.0),
              shape: const StadiumBorder(),
            ),
            child: const Text(
              "Enter",
              style: TextStyle(color: Colors.white, fontSize: 18),
            ),
          ),
        ],
      ),
    );
  }
}

textfieldWidget:

class TextfielWidget extends StatefulWidget {
  final Function(int) onChange;

  const TextfielWidget({super.key, required this.onChange});

  @override
  State<TextfielWidget> createState() => _TextfielWidgetState();
}

class _TextfielWidgetState extends State<TextfielWidget> {
  @override
  Widget build(BuildContext context) {
    return Flexible(
        child: TextField(
            onChanged: widget.onChange,
            keyboardType: TextInputType.number,
            decoration: const InputDecoration(
              border: OutlineInputBorder(),
              labelText: 'Enter Number',
            )
          )
        );
  }
}

Where can I change the type of "void Function(String)?"? I can't find the Problem, is the Problem the Textfield itself?

Thank you for help

CodePudding user response:

the onChanged property of TextField accepts a void Function(String)?, but the widget.onChange that you assigned to it returns a Function(int) and it's not void so dart expects something to be returned and handles it like dynamic Function(int), so the solution is to :

change this:

  final Function(int) onChange;

with this:

  final void Function(String)? onChange;

now you say that the value got from the TextField is String, and I understand that you need to get a number from the task you are doing in your app, so whenever you have a String containing a number such as "120" you can convert it to int such as 120 with :

int parsedNumber = int.parse("120"); // 120

your implementation in the onChanged property seems like this :

TextfielWidget(onChange: (val) {
        widget.sendData(val);
      }),

here the val should be String, but you can parse it so it can be int inside the sendData method like this :

 TextfielWidget(onChange: (val) {
            widget.sendData(int.parse(val));
          }),

it will work fine now.

Note: the int.parse(val) will work fine if the val contains only numbers, otherwise, it will throw an Exception if you want that it will return null if there is a problem use instead int.tryParse(val);

Hope this helps.

CodePudding user response:

TextField's onChanged property is type void Function(String) not void Function(int). change all your function type and convert the string to int:

 int data = 5;

  void getData(String newNumb) {
    setState(() {
      data = int.tryParse(newNumb);
    });
  }

  • Related