Skip to content
Tom Gilder edited this page Jul 10, 2021 · 14 revisions

Why isn't my page content changing?

You might need to add a key to a page for Flutter to detect a page has changed:

MaterialPage(key: ValueKey('id1'), child: MyPage())
MaterialPage(key: ValueKey('id2'), child: MyPage())

Also, all pages must be specifically rebuilt if some state changes. Don't rely on a parent page rebuilding, make sure every page that gets state properly depends on it.

How do I pop multiple pages?

It's a bit counterintuitive, but you push! If you're on route /one/two/three and want to pop back to /one, you can just call either Routemaster.of(context).push('/one') or Routemaster.of(context).replace('/one'), depending if you want the user to be able to go back on the web. There's no popUntil method.

How do I remove the '#' from the URL?

Call Routemaster.setPathUrlStrategy() on startup, before you call runApp():

void main() {
  Routemaster.setPathUrlStrategy();
  runApp(MyApp());
}

How do I make hero animations work?

Hero animations will work automatically on the top-level navigator (assuming you're using MaterialApp or CupertinoApp).

For any child navigators, you'll need to wrap PageStackNavigator in a HeroControllerScope, like this:

HeroControllerScope(
  controller: MaterialApp.createMaterialHeroController(),
  child: PageStackNavigator(
    stack: pageStack,
  )
)

How do I disable all page animations?

Use a custom Page object:

class NoAnimationPage<T> extends MaterialPage<T> {
  NoAnimationPage({required Widget child}) : super(child: child);

  @override
  Route<T> createRoute(BuildContext context) {
    return NoAnimationPageRoute<T>(page: this);
  }
}

class NoAnimationPageRoute<T> extends PageRoute<T>
    with MaterialRouteTransitionMixin<T> {
  NoAnimationPageRoute({
    required MaterialPage<T> page,
  }) : super(settings: page) {
    assert(opaque);
  }

  MaterialPage<T> get _page => settings as MaterialPage<T>;

  @override
  Duration get transitionDuration => const Duration(milliseconds: 0);

  @override
  Widget buildTransitions(BuildContext context, Animation<double> animation,
      Animation<double> secondaryAnimation, Widget child) {
    return child;
  }

  @override
  Widget buildContent(BuildContext context) {
    return _page.child;
  }

  @override
  bool get maintainState => _page.maintainState;

  @override
  bool get fullscreenDialog => _page.fullscreenDialog;
}

Then use NoAnimationPage in your route map:

'/home': (routeData) => NoAnimationPage(child: HomePage()),

See the book store example for an example of this.

Clone this wiki locally