Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Flutter call function for each item in list

I've got a 2x2 grid that I am trying to populate with cards, where each card is of a specific style. Each card has a title and a route which when clicked opens another page (route). I'd like to specify the "name" of the card and the "name of the page" which the the click should lead to for each "name" in an index of "names".

The problem is 1. I'm not sure how to do the for-each loop within the widget. 2. Not sure how to make this work for more than 1 parameter being; name of card and name of new page.

I have already tried a few options, 2 of which are shown below.

class SubjectsPage extends StatefulWidget {

  @override
  _SubjectsPageState createState() => new _SubjectsPageState();
}

class _SubjectsPageState extends State<SubjectsPage> with TickerProviderStateMixin {

  @override
  Widget build(BuildContext context) {
    var names = ["one", "two", "three", "four"];
        return new Material(     
          child: new Container(
            child: new Center(
              child: GridView.count(
                crossAxisCount: 2,
                padding: EdgeInsets.fromLTRB(16.0, 128.0, 16.0, 16.0),
                childAspectRatio: 8.0 / 8.5,
                children: <Widget>[

                  //option 1
                  names.forEach((unit) => Cards(unit: unit,)),

                  //option 2
                  for (var i = 0; i < names.length; i++) {
                    Cards(unit: names[i])
                  }

            ],
          ), 
        ),
      ),
    );
  }
}

The error for option 1 is that "the expression here has a type of 'void', and therefore cannot be used."

The error for option 2 is that "the element type 'Set' can't be assigned to the list type 'Widget'."

like image 885
IAlwaysNeedHelp Avatar asked Sep 17 '25 12:09

IAlwaysNeedHelp


1 Answers

Yes, you cannot use forEach but map. You can map strings to widget using map method.

Example:

class SubjectsPage extends StatefulWidget {
  @override
  _SubjectsPageState createState() => new _SubjectsPageState();
}

class _SubjectsPageState extends State<SubjectsPage>
    with TickerProviderStateMixin {
  @override
  Widget build(BuildContext context) {
    var names = ["one", "two", "three", "four"];
    return Material(
      child: Container(
        child: Center(
          child: GridView.count(
            crossAxisCount: 2,
            padding: EdgeInsets.fromLTRB(16.0, 128.0, 16.0, 16.0),
            childAspectRatio: 8.0 / 8.5,
            children: names.map((String name) {
              return Cards(unit: name);
            }).toList(),
          ),
        ),
      ),
    );
  }
}

Or: Your option two can be done like

class SubjectsPage extends StatefulWidget {
  @override
  _SubjectsPageState createState() => new _SubjectsPageState();
}

class _SubjectsPageState extends State<SubjectsPage>
    with TickerProviderStateMixin {
  @override
  Widget build(BuildContext context) {
    var names = ["one", "two", "three", "four"];
    return Material(
      child: Container(
        child: Center(
          child: GridView.count(
            crossAxisCount: 2,
            padding: EdgeInsets.fromLTRB(16.0, 128.0, 16.0, 16.0),
            childAspectRatio: 8.0 / 8.5,
            children: [
                for(String name in names) Cards(unit:name)
            ],
          ),
        ),
      ),
    );
  }
}

Hope that helps!

like image 160
Hemanth Raj Avatar answered Sep 20 '25 17:09

Hemanth Raj