Execute navigation programmatically

255 Views Asked by At

I try to implement a deep linking logic in my Flutter app. For navigation to my destination and to be sure to have the correct stack I need sometimes to choose the right tab on my BottomNavigationBar, then animate to the correct tab of my TabBar with TabController, scroll to the correct position in my ListView and push then to a for example DetailsScreen of an item in the ListView. But in case of the current state of my current Tab on BottomNavigationBar already opened a DetailsScreen I first need to pop the current Stack and then pushing to for example the details of another item in the list. Using a simple:

Navigator.of(context).pop();
Navigator.of(context).pushNamed(TabNavigatorRoutes.details, arguments: item);

has the result the pushNamed never executed or simply poped immediately after been pushed because, I assume, the pop() still running in the same time so they kill each other.

I fixed this with:

await Navigator.maybePop(context);
Navigator.of(context).pushNamed(TabNavigatorRoutes.details, arguments: item); 

which pops if possible and waits with executing the pushNamed, so fine that works.

Problem, I also have deeper screens and need to execute for example Navigator.of(context).popUntil((route) => route.isFirst); to be sure I popped an existing stack before execute another deep link. Same problem here, a following pushNamed will not execute. Differenz Navigator.of(context).popUntil((route) => route.isFirst); is a void function so I cannot use await here.

I asked ChatGPT about the problem and got the following solution, I should use:

Navigator.of(context).popUntil((route) => route.isFirst);
await Future.delayed(Duration.zero); // Wait for microtask queue to clear
Navigator.of(context).pushNamed(TabNavigatorRoutes.details, arguments: item);

which works yes, but It feels like a really dirty solution. Anyone else had this problem and founds a better solution?

1

There are 1 best solutions below

0
On

I finally solved my problem by calling by using some basics:

while (Navigator.canPop(context)) {
   await Navigator.maybePop(context);
}
Navigator.pushNamed(context, TabNavigatorRoutes.details, arguments: item);

Maybe someone could tell if this could have side effects or could cause other problems? I think the solution is not ideal but better than await Future.delayed(Duration.zero); I'm open for proposals!