How to call an index in Flutter onTap, using ListTile in a for loop

227

The problem is that you're using the index that is being passed from the function instead of the index inside the loop. replace the commented code

   // onTap: () {
      //   Navigator.pushNamed(context, routeList[index].page);
     // },

with

  onTap: () {
      Navigator.pushNamed(context, routeList[i].page);
    },

the i is the index of the for loop.

Share:
227
Tobsig
Author by

Tobsig

Updated on January 02, 2023

Comments

  • Tobsig
    Tobsig over 1 year

    I'm new to programming. I have created a flutter drawer, which works fine. However, I have learned about for loops and now want to shorten my code so that I don't show 10 x ListTiles. I now have a for loop for my ListTile. I managed to get the drawer working fine, with the Text and the Icon, but cannot seem to get the onTap to work with the routes (pages). I can get the Navigator.pushNamed to return a single page in my routes, but then this same page get returned for all my items in all my ListTiles.

    I have created routes in my main.dart. I have created my class and list of pages. I have created my for loop in a function outside of the Builder and parsed Buildcontext (context) into the function, which seems to be ok. My code does not throw errors, but only return one page.

    I have spend four days now reading do many similar kind of solutions, but I simply can't find a workable solution for myself. I don't seem to find a proper answer to my problem as all solutions through out some kind of error, or at best, no errors, but it does not work. Here is my code.

    // MAIN.DART FILE TO ILLUSTRATE PAGE ROUTES
    
    class MyAppState extends State<MyApp> {
     @override
     Widget build(BuildContext context) {
       return MaterialApp(
         debugShowCheckedModeBanner: false,
         routes: {
           
           '/page2': (context) => const InvoiceApp(),
           '/page3': (context) => const Currency(),
           '/page4': (context) => const Expenses(),
           '/page5': (context) => const Reports(0),
           '/page6': (context) => const Graphs(0),
           '/page7': (context) => const Download(0),
           '/page8': (context) => const Customer(),
           '/page9': (context) => const People(0),
           '/page10': (context) => const Resources(0),
           '/page11': (context) => const Profile(),
         },
         home: Scaffold(
    
    //CLASS ROUTES
    
    class Routes {
     String page;
    
     Routes({required this.page});
    }
    //LIST
    
    list<Routes> routeList = [
     Routes(page: '/page2'),
     Routes(page: '/page3'),
     Routes(page: '/page4'),
     Routes(page: '/page5'),
     Routes(page: '/page6'),
     Routes(page: '/page7'),
     Routes(page: '/page8'),
     Routes(page: '/page9'),
     Routes(page: '/page10'),
     Routes(page: '/page11'),
    ];
    
    //MAIN CODE
    
    class MenuBar extends StatelessWidget {
     const MenuBar({Key? key}) : super(key: key);
    
     List<ListTile> getMenuItems(BuildContext context, var index) {
       List<ListTile> menuList = [];
    
       for (var i = 0; i < menuItemList.length; i++) {
         var item = menuItemList[i];
    
         var loopCode = ListTile(
           title: Text(item),
           leading: Icon(
             icons[i],
             color: Colors.teal,
           ),
    
           // onTap: () {
           //   Navigator.pushNamed(context, routeList[index].page);
           // },
    
           onTap: () {
             Navigator.pushNamed(context, '/page3');
           },
           
         );
         menuList.add(loopCode);
       }
    
       return menuList;
     }
    
     @override
     Widget build(
       BuildContext context,
     ) {
       //  getMenuItems(context);
       return Drawer(
         child: ListView(
           padding: EdgeInsets.zero,
           children: [
             const AccountHeader(),
             Column(
               children: getMenuItems(context, routeList),
             ),
           ],
         ),
       );
     }
    
    List<String> menuItemList = [
     
     'Invoices',
     'Currency Converter',
     'Expenses',
     'Reports',
     'Graphs',
     'Downloads',
     'Customers',
     'People Management',
     'Resources',
     'Profile',
    ];
    List<IconData> icons = [
     Icons.receipt,
     Icons.money,
     Icons.money,
     Icons.report,
     Icons.bar_chart,
     Icons.download,
     Icons.people,
     Icons.people,
     Icons.cake,
     Icons.person,
    ];
    

    PLEASE NOTE:

    1. I have 10 pages in my routes, yet my routes starts at page 2 and ends at page 11. This is not an issue as my main.dart file is my landing page for my app.

    2. My problem is onTap. You will notice two onTap codes (one is commented out). If I use the current active one (...page3), then it works, but all 10 pages then return to page 3 once any of the ten tiles are tapped. If I use the onTap that is commented out, then the app loads, the drawer opens find, but no tile will navigate to any page. Also no errors in my code is issued.

    Can you please help me. Thank you kindly.

    • Yeasin Sheikh
      Yeasin Sheikh over 2 years
      I think you are missing / on routeList for each item.
    • Tobsig
      Tobsig over 2 years
      Thank you for the quick response Yeasin. It does not seem to work though (thank you for showing this obvious error of mine). The code does not render any errors, but when using the onTap (routeList[index].page) it still does not navigate to each page as and when required.
    • Yeasin Sheikh
      Yeasin Sheikh over 2 years
      There are few things I can't find on question like menuItemList, are you basically trying to create listTile from routeList and navigate with onTap?
    • Tobsig
      Tobsig over 2 years
      I have edited my code and included menuItemList and icons. I'm creating a drawer with 10 items (using listTiles for each item). In order to not hardcode and code 10x ListTiles, I now do 1 x ListTile in a for loop. menuItemList is used for the Text of each tile and is working. icons is used for the leading icon in each item and it works. Now i need to do the onTap so that when I select (press) on any of the 10 items (ListTiles), then it must navigate to the corresponding page. This is what I can't manage to do. Thank for the help Yeasin..
  • Tobsig
    Tobsig over 2 years
    Hi Algidaq. Thank you so much. It works perfectly. Your answer resolved the problem. Also thank you to Yeasin for highlighting my '/'error. There is then a difference between using [i] which is the reference to the index in the for loop and [index] which is the index for the function. Thanks so much!!