Flutter - NavigatorObserver类的工作原理是什么?

时间:2017-09-11 23:32:08

标签: dart flutter

我试图检测导航器执行基本操作的时间(推送 pop ),我发现该课程要实现这一点,请使用NavigatorObserver类,但我无法找到有关其工作原理的示例。

我已经尝试过实现接口:

class MyClassState extends State<MyClass> with NavigatorObserver{

    ....

    @override
    void didPop(Route<dynamic> route, Route<dynamic> previousRoute) {
        print('This is never get called');
    }

    @override
    void didPush(Route<dynamic> route, Route<dynamic> previousRoute) {
        print('This is never get called');
    }
}

我当然打电话给Navigator.of(context).push(...); 但覆盖方法永远不会被调用。

我怀疑与导航器的绑定丢失了,但我不确定。

有什么建议吗?

提前致谢!

编辑:

我认为我想做的事情非常简单,但我无法弄清楚如何去做。

我有第A页,推动第B页

第B页我有必须 必须(在第B页上)。

我想要做的就是在页面B 弹出时使用timer.cancel()取消计时器(使用Android上的后退按钮或appbar中的后退按钮),因为当第B页即使页面B 已经消失,也会弹出仍在执行的计时器。

  • 由于我没有处理后退按钮(appbar中的那个按钮和Android后退按钮),我无法通过Navigator.pop()传递计时器作为参数。

编辑2:

- 我找到了解决问题的方法,我所做的是取消

上的计时器
@override
void dispose() {
  timer.cancel();
  super.dispose();
}

方法。但我不确定这是否是实现它的最佳方式。

注意:

使用此解决方法,如果我按下主页按钮或在Android上打开多任务,计时器仍在执行,当返回应用程序时,这会重新启动,但计时器仍会执行其代码。

2 个答案:

答案 0 :(得分:2)

大多数情况下,您不需要实施NavigatorObserver。请参阅this other StackOverflow answer,说明如何使用pushpop在路由之间传递信息。在您已描述的用例中,您应addListener使用AnimationController vsync来获取合适的State对象。这可以确保在暂停应用程序或处置addListener之后,您的回调不会触发。 (而不是AnimatedBuilder,您可以使用AnimatedWidgetNavigatorObserver,回调的主要目的是重建小部件树的一部分。)

如果您正在使用Firebase Analytics等插件,那么您需要NavigatorObserver的主要时间。您可以在TickerProviderStateMixin中查看示例用法。您将navigatorObservers参数中的MaterialApp传递给static FirebaseAnalyticsObserver observer = new FirebaseAnalyticsObserver(analytics: analytics); ... return new MaterialApp( navigatorObservers: <NavigatorObserver>[observer], ... ); 构造函数:

State

由于NavigatorObserver应位于窗口小部件层次结构的顶部,因此MaterialApp实现State是不常见的。在您构建它的时候,大多数navigatorObservers个对象还不存在,因此您很难将它们放入State数组中。您可以改为使用不是GlobalKey<MyClassState>的类。如有必要,您可以使用State查找需要通知的$('#quoteDisplay').fadeIn('slow');(但如果您正在执行此操作,则可能有更简单的方法来完成您想要的操作)。

答案 1 :(得分:2)

// Register the RouteObserver as a navigation observer.
final RouteObserver<PageRoute> routeObserver = RouteObserver<PageRoute>();
void main() {
  runApp(MaterialApp(
    home: Container(),
    navigatorObservers: [routeObserver],
  ));
}

class RouteAwareWidget extends StatefulWidget {
  State<RouteAwareWidget> createState() => RouteAwareWidgetState();
}

// Implement RouteAware in a widget's state and subscribe it to the RouteObserver.
class RouteAwareWidgetState extends State<RouteAwareWidget> with RouteAware {

  @override
  void didChangeDependencies() {
    super.didChangeDependencies();
    routeObserver.subscribe(this, ModalRoute.of(context));
  }

  @override
  void dispose() {
    routeObserver.unsubscribe(this);
    super.dispose();
  }

  @override
  void didPush() {
    // Route was pushed onto navigator and is now topmost route.
  }

  @override
  void didPopNext() {
    // Covering route was popped off the navigator.
  }

  @override
  Widget build(BuildContext context) => Container();

}