2

I have a function that navigates to a new page with route settings

void pushWithSettings(
    {@required BuildContext context, @required Widget newPage}) {
  Navigator.push(
      context,
      MaterialPageRoute(
          settings: RouteSettings(
            name: newPage.toString(),
          ),
          builder: (_) => newPage));
}

and I pop till a particular page using

Navigator.popUntil(context, ModalRoute.withName(Page().toString));

This works well in debug mode but in profile and release mode it pops only once

An Example for context

import 'package:flutter/material.dart';
import 'package:flutter_app/main.dart';

class FirstPage extends StatelessWidget {
  
  @override
  Widget build(BuildContext context) {
    return Column(
      children: <Widget>[
        Center(child: Text("First Page"),),
        RaisedButton(
          onPressed: (){
            pushWithSettings(context: context, newPage: SecondPage());
          },
          child: Text("Navigate to second", style: TextStyle(inherit: false)),
        )
      ],
    );
  }
}

class SecondPage extends StatelessWidget {
  
@override
Widget build(BuildContext context) {
  return Column(
    children: <Widget>[
      Center(child: Text("Second Page"),),
      RaisedButton(
        onPressed: (){
          pushWithSettings(context: context, newPage: ThirdPage());
        },
        child: Text("Navigate to third", style: TextStyle(inherit: false)),
      )
    ],
  );
}
}

class ThirdPage extends StatelessWidget {
  
  @override
  Widget build(BuildContext context) {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Center(child: Text("Third Page"),),
        RaisedButton(
          onPressed: (){
            Navigator.popUntil(context, ModalRoute.withName(FirstPage().toString()));
          },
          child: Text("Navigate to first", style: TextStyle(inherit: false),),
        )
      ],
    );
  }
}

In debug mode tapping the button in the third page navigates to the first page but in profile and release mode tapping the button does nothing. I'm currently running flutter 1.17.4 on the stable channel

faithomotoso
  • 385
  • 2
  • 10
  • Maybe Page().toString() is not returning the same in debug and release. Could you try to add another String as the routeName? Try with a simple string to see if that works. – jamesblasco Jul 13 '20 at 12:25

2 Answers2

2

The first answer works but to avoid adding mixins to all pages I have available I used runtimeType instead so

settings: RouteSettings(
            name: newPage.toString(),
          ),

became

settings: RouteSettings(
            name: newPage.runtimeType.toString(),
          ),
faithomotoso
  • 385
  • 2
  • 10
1

I have tried your code an FirstPage().toString() in Profile mode returns 'Widget' while it returns 'FirstPage' in debug.

I would add a mixin that contains a routeName string you can use.

Also remember, that at least for web is recommended that your initial route is with '/'.


void pushWithSettings(
    {@required BuildContext context, @required NamedRoute newPage}) {
  Navigator.push(
      context,
      MaterialPageRoute(
          settings: RouteSettings(
            name: newPage.routeName,
          ),
          builder: (_) => newPage));
}

mixin NamedRoute implements Widget {
  String get routeName;
}


class ThirdPage extends StatelessWidget with NamedRoute {
  @override
  String get routeName => '/third_page';

  @override
  Widget build(BuildContext context) {
    return Column(
      mainAxisAlignment: MainAxisAlignment.center,
      children: <Widget>[
        Center(
          child: Text("Third Page"),
        ),
        RaisedButton(
          onPressed: () {
            Navigator.popUntil(context, ModalRoute.withName(FirstPage().routeName));
          },
          child: Text(
            "Navigate to first",
            style: TextStyle(inherit: false),
          ),
        )
      ],
    );
  }
}

Check the codepen https://codepen.io/jamesblasco/pen/QWyBQOm

jamesblasco
  • 1,744
  • 1
  • 9
  • 25
  • I tried the mixin. Still didn't work. You're right about the name changing to Widget. I can't run dev tools with profile mode for some reason. – faithomotoso Jul 13 '20 at 19:43
  • The mixin worked. I made a mistake while implementing. Thank you. I tried using runtimeType and it worked also so name: newPage.routeName became name: newPage.runtimeType – faithomotoso Jul 14 '20 at 19:30
  • Glad you make it work. Just notice that flutter recommends to use a path-like naming for your routes – jamesblasco Jul 16 '20 at 11:00
  • "Mobile apps often manage a large number of routes and it's often easiest to refer to them by name. Route names, by convention, use a path-like structure (for example, '/a/b/c'). The app's home page route is named '/' by default. "https://api.flutter.dev/flutter/widgets/Navigator-class.html – jamesblasco Jul 16 '20 at 11:01