navigation_history_observer 1.0.3+1

  • Readme
  • Changelog
  • Example
  • Installing
  • new61

Flutter Navigation History Observer #

A flutter navigation observer that adds access to lists that track the navigation stack both forwards and backwards.

Usage #

This is a singleton, meaning you can access its single instance from anywhere by calling the default constructor.

To initialize the first instance you must add it to your app's navigator observers list like so:

void main() {
  runApp(MaterialApp(
    home: Container(),
    navigatorObservers: [NavigationHistoryObserver()],
  ));
}

History:

To access the history, use NavigationHistoryObserver().history from anywhere in your code.

Use NavigationHistoryObserver().top to peek on the navigation stack's top element - which would be the current route.

Popped routes (forwards history):

To access the popped routes, use NavigationHistoryObserver().poppedRoutes from anywhere in your code.

UseNavigationHistoryObserver().next to get the most recent popped route.

This feature is intended to track the pages visited by the user, rather than navigating forwards. Please keep in mind that popped routes have already been disposed, meaning that you can't simply navigate to them as is via Navigator.push(context, route).

If you'd still like to navigate forwards, you may try Navigator.pushNamed(context, name), whereas the name should be extracted from route.settings.name provided that you're using named routes in your app.
However, there's no guarantee that it'll work.

Nevertheless, I discourage having forwards-navigation in your app.

History Change Stream:

The NavigationHistoryObserver class holds a StreamController that broadcasts each time the navigation stack changes.

Use NavigationHistoryObserver().historyChangeStream.listen((change) => action) to listen for changes.

The change object is of type HistoryChange. It holds the following properties:

  1. action - a NavigationStackAction enum reporting the action that caused this change. Values: push, pop, remove, replace.
  2. newRoute - the new route that was added/removed from the stack.
  3. oldRoute - the old route that was in place before this action happened.

This provides you with an easy-to-use interface that allows updating states across your app whenever the navigation stack changes. See the example for basic usage.

Developer's Note: #

The history and poppedRoutes getters return clones of the actual private collections as BuiltLists, meaning they're immutable. To change these collections, use the default Navigator as you normally would, and they'll update as you navigate throughout your app.

Special Thanks #

  • Shoutout to the Flutter Israel Developers community for being supportive and encouraging me to create this package.
  • Special thanks to Sahar Vanunu for giving me the original idea for this package.

[1.0.3+1] - Jun. 20, 2020 #

  • Example updated - The example page is now in main.dart to show the full code on pub.dev

[1.0.3] - Jun. 20, 2020 #

  • Changed library name from navigation_history_observer to navigationhistoryobserver.
  • Removed route from HistoryChange, added newRoute and oldRoute instead.
  • Added next getter to get most resent popped route.
  • No longer supporting forwards navigation as it causes severe issues.
  • Added more usage details and special thanks to the readme.

[1.0.2] - Jun. 19, 2020 #

  • Added example project, updated historyChanged to historyChangeStream for better semantics.

[1.0.1] - Jun. 19, 2020 #

  • Added stream to broadcast changes in history.

[1.0.0] - Jun. 17, 2020 #

  • First stable release.

example/lib/main.dart

import 'package:flutter/material.dart';
import 'package:navigation_history_observer/navigation_history_observer.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
        visualDensity: VisualDensity.adaptivePlatformDensity,
      ),
      home: ExamplePage(pageNum: 1,),
      navigatorObservers: [NavigationHistoryObserver()],
    );
  }
}

class ExamplePage extends StatefulWidget {

  ExamplePage({Key key, this.pageNum}) : super(key: key);

  final int pageNum;

  @override
  _ExamplePageState createState() => _ExamplePageState();

}

class _ExamplePageState extends State<ExamplePage> {

  final NavigationHistoryObserver historyObserver = NavigationHistoryObserver();

  int historyCount = 0;
  int poppedCount = 0;

  @override
  void initState() {
    super.initState();

    historyCount = historyObserver.history.length;
    poppedCount = historyObserver.poppedRoutes.length;

    historyObserver.historyChangeStream.listen(
      (change) => setState(() {
          historyCount = historyObserver.history.length;
          poppedCount = historyObserver.poppedRoutes.length;
        }
      )
    );
  }

  @override
  Widget build(BuildContext context) =>
      Scaffold(
        appBar: AppBar(
          title: Row(
            children: <Widget>[
              Text("Navigation example ${widget.pageNum}"),
            ],
          ),
        ),
        body: Center(
          child: Column(
            children: <Widget>[
              Text("Welcome to the navigation page!"),
              Text("History has $historyCount routes"),
              Text("There are $poppedCount popped routes"),
              RaisedButton(
                child: Text("Navigate to a new page"),
                onPressed: () => Navigator.push(
                    context,
                    MaterialPageRoute(
                        builder: (context) => ExamplePage(pageNum: widget.pageNum + 1)
                    )
                ),
              )
            ],
          ),
        ),
      );
}

Use this package as a library

1. Depend on it

Add this to your package's pubspec.yaml file:


dependencies:
  navigation_history_observer: ^1.0.3+1

2. Install it

You can install packages from the command line:

with Flutter:


$ flutter pub get

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

3. Import it

Now in your Dart code, you can use:


import 'package:navigation_history_observer/navigation_history_observer.dart';
  
Popularity:
Describes how popular the package is relative to other packages. [more]
22
Health:
Code health derived from static analysis. [more]
100
Maintenance:
Reflects how tidy and up-to-date the package is. [more]
100
Overall:
Weighted score of the above. [more]
61
Learn more about scoring.

We analyzed this package on Jul 10, 2020, and provided a score, details, and suggestions below. Analysis was completed with status completed using:

  • Dart: 2.8.4
  • pana: 0.13.14
  • Flutter: 1.17.5

Analysis suggestions

Package not compatible with SDK dart

Because:

  • navigation_history_observer that is a package requiring null.

Health suggestions

Format lib/navigation_history_observer.dart.

Run flutter format to format lib/navigation_history_observer.dart.

Dependencies

Package Constraint Resolved Available
Direct dependencies
Dart SDK >=2.7.0 <3.0.0
built_collection ^4.3.2 4.3.2
flutter 0.0.0
Transitive dependencies
collection 1.14.12 1.14.13
matcher 0.12.8
meta 1.1.8 1.2.2
path 1.7.0
quiver 2.1.3
sky_engine 0.0.99
stack_trace 1.9.5
typed_data 1.1.6 1.2.0
vector_math 2.0.8 2.1.0-nullsafety