Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

nested routers #4

Closed
slovnicki opened this issue Jan 8, 2021 · 15 comments
Closed

nested routers #4

slovnicki opened this issue Jan 8, 2021 · 15 comments
Assignees
Labels
documentation Improvements or additions to documentation enhancement New feature or request help wanted Could use a couple of fresh hands

Comments

@slovnicki
Copy link
Owner

slovnicki commented Jan 8, 2021

https://gist.github.com/johnpryan/bbca91e23bbb4d39247fa922533be7c9

@slovnicki slovnicki added the enhancement New feature or request label Jan 8, 2021
@slovnicki slovnicki self-assigned this Jan 8, 2021
@slovnicki slovnicki added the documentation Improvements or additions to documentation label Jan 21, 2021
@slovnicki slovnicki modified the milestones: v0.3.0, v0.4.0, v0.5.0, v0.6.0 Jan 23, 2021
@slovnicki slovnicki added enhancement New feature or request and removed enhancement New feature or request labels Feb 3, 2021
@slovnicki slovnicki modified the milestones: v0.6.0, v0.7.0 Feb 6, 2021
@slovnicki
Copy link
Owner Author

#56

@slovnicki slovnicki added the help wanted Could use a couple of fresh hands label Feb 12, 2021
@slovnicki
Copy link
Owner Author

We would really like to do this:

class MyApp extends StatelessWidget {
  final _beamerKey = GlobalKey<BeamerState>();

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        body: Beamer(
          key: _beamerKey,
          routerDelegate:
              BeamerRouterDelegate(initialLocation: _beamLocations[0]),
          routeInformationParser: BeamerRouteInformationParser(
            beamLocations: _beamLocations,
          ),
        ),
        bottomNavigationBar: BottomNavigationBarWidget(
          beamerKey: _beamerKey,
        ),
      ),
    );
  }
}

but then this inner router cannot parse incoming url. We need a "dummy" router just to parse url and pass it down to "main" router that's somewhere inside app. Like this.

I will wait for a possible workaround for this and will not implement the outer router yet, because this snippet works fine for every situation (including updating the url correctly) except parsing incoming url.

@slovnicki slovnicki removed this from the v0.7.0 milestone Feb 22, 2021
@slovnicki slovnicki added this to the v0.9.0 milestone Mar 3, 2021
@slovnicki
Copy link
Owner Author

it definitely goes in v0.9.0.
The main (almost only) focus will be on this

@slovnicki
Copy link
Owner Author

Thank you all for great support in the above comment, but it will not land in v0.9.0 due to some recently developed major cool features that I would like to publish today.

BUT worry not... the date still stands; by the end of this week. And. maybe even cooler, it will land in v0.10.0 🙂

@slovnicki slovnicki modified the milestones: v0.9.0, v0.10.0 Mar 9, 2021
@slovnicki
Copy link
Owner Author

slovnicki commented Mar 14, 2021

ok, so ab9e53d was done for now. It would go something like this, specifically for bottom navigation bar:

class MyApp extends StatelessWidget {
  final _beamerKey = GlobalKey<BeamerState>();

  @override
  Widget build(BuildContext context) {
    return MaterialApp.router(
      routeInformationParser: BeamerRouteInformationParser(),
      routerDelegate: RootRouterDelegate(
        homeBuilder: (context, uri) => Scaffold(
          body: Beamer(
            key: _beamerKey,
            beamLocations: _beamLocations,
          ),
          bottomNavigationBar: BottomNavigationBarWidget(
            beamerKey: _beamerKey,
          ),
        ),
      ),
    );
  }
}

I need to test it some more before releasing. Probably tomorrow night will be ready enough. (edit: it will take some more time)
Currently this is on nested-router branch.

@talski
Copy link

talski commented Mar 15, 2021

how can I do something like this?

class MyAppState extends State<MyApp> {
  @override
  Widget build(BuildContext context) {
    return MaterialApp.router(
      debugShowCheckedModeBanner: false,
      routeInformationParser: BeamerRouteInformationParser(),
      routerDelegate: RootRouterDelegate(
        homeBuilder: (context, uri) => Scaffold(
          body: Row(
            children: [
              Expanded(
                flex: 1,
                child: ListView(
                  children: [
                    ListTile(
                      title: Text('Home'),
                      onTap: () => context.beamToNamed('/home'),
                    ),
                    ListTile(
                      title: Text('Articles'),
                      onTap: () => context.beamToNamed('/articles'),
                    ),
                    ListTile(
                      title: Text('Books'),
                      onTap: () => context.beamToNamed('/books'),
                    ),
                  ],
                ),
              ),
              Expanded(
                flex: 3,
                child: Container(
                  color: Colors.blueAccent,
                  padding: const EdgeInsets.all(32.0),
                  child: Beamer(
                    key: _beamerKey,
                    beamLocations: [
                      HomeLocation(),
                      ArticlesLocation(),
                      BooksLocation(),
                    ],
                  ),
                ),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

I'm getting some errors,

BeamerProvider.of(context) != null
"There was no Router nor BeamerProvider in current context. If using MaterialApp.builder, wrap the MaterialApp.router in BeamerProvider to which you pass the same routerDelegate as to MaterialApp.router."

tried to wrap but did not work, I'm using the nested-router branch

@slovnicki
Copy link
Owner Author

@talski thanks for trying it out so soon 😃
Yeah, ignore that assert message, I will update it because it's not relevant here.

Beamer and the place where you are using it are currently at the same level in Widget tree so you need to do it via the key. This should work (I changed just your onTaps):

class MyAppState extends State<MyApp> {
  @override
  Widget build(BuildContext context) {
    return MaterialApp.router(
      debugShowCheckedModeBanner: false,
      routeInformationParser: BeamerRouteInformationParser(),
      routerDelegate: RootRouterDelegate(
        homeBuilder: (context, uri) => Scaffold(
          body: Row(
            children: [
              Expanded(
                flex: 1,
                child: ListView(
                  children: [
                    ListTile(
                      title: Text('Home'),
                      onTap: () => _beamerKey.currentState.routerDelegate.beamToNamed('/home'),
                    ),
                    ListTile(
                      title: Text('Articles'),
                      onTap: () => _beamerKey.currentState.routerDelegate.beamToNamed('/articles'),
                    ),
                    ListTile(
                      title: Text('Books'),
                      onTap: () => _beamerKey.currentState.routerDelegate.beamToNamed('/books'),
                    ),
                  ],
                ),
              ),
              Expanded(
                flex: 3,
                child: Container(
                  color: Colors.blueAccent,
                  padding: const EdgeInsets.all(32.0),
                  child: Beamer(
                    key: _beamerKey,
                    beamLocations: [
                      HomeLocation(),
                      ArticlesLocation(),
                      BooksLocation(),
                    ],
                  ),
                ),
              ),
            ],
          ),
        ),
      ),
    );
  }
}

@tomosullivan8
Copy link

I get the same error message, I have pretty much the same implementation as @talski but with an AppBar instead.

The following TypeErrorImpl was thrown during a scheduler callback:
Unexpected null value.
There was no Router nor BeamerProvider in current context. If using MaterialApp.builder, wrap the MaterialApp.router in BeamerProvider to which you pass the same routerDelegate as to MaterialApp.router.');

@slovnicki
Copy link
Owner Author

slovnicki commented Mar 15, 2021

@tomosullivan8 Hi!
I provided the solution in the above comment. You need to navigate via beamer's key.

@slovnicki
Copy link
Owner Author

slovnicki commented Mar 15, 2021

@talski, @tomosullivan8 Let me know if this works for you. You can let us know on beamer's Discord also: https://discord.gg/8hDJ7tP5Mz

@tomosullivan8
Copy link

Just saw, you beat me to the reply! Will try it now, thanks.

Is there a way to push over the top of the RootRouteDelegate? An example would be like the following, the 'Home', 'About' and 'Contact' would be nested under the Website, but you can push the page to 'Login' and 'Store' over the 'Website':

  • Website
    • Home
    • About
    • Contact
  • Login
  • Store

The issue I've been having is getting the url to update with the inner router instead of using the root.

@slovnicki
Copy link
Owner Author

slovnicki commented Mar 15, 2021

@tomosullivan8 yeah, this is definitely an use-case I have in mind to implement soon, but it's impossible currently :(
I'm still working things out regarding nested routers.

On one hand, I wanted this homeBuilder because it's easy and covers most use-cases, but on the other hand it would be more natural for RootRouterDelegate to also accept BeamLocations.

I plan to enable both

@tomosullivan8
Copy link

tomosullivan8 commented Mar 15, 2021

I'll take a look at the RootRouterDelegate and see if I can modify it, I think like you say it would seem ideal for this to have the additional locations accepted, but haven't had much experience with Navigator 2.0.

Just an FYI, there is a typo in the RootRouterDelegate, with _currentUri being _currrentUri with an extra r!

@slovnicki
Copy link
Owner Author

slovnicki commented Mar 15, 2021

Just an FYI, there is a typo in the RootRouterDelegate, with _currentUri being _currrentUri with an extra r!

Oh... well, it really shows that it's a working version 😆 You can make a PR to fix that at least :)
I'm currently very invested in this RootRouterDelegate so it might not be a great time for you to modify it because we'll have lots of conflicts.

@tomosullivan8 If you want to make a contribution to that rrr, let me know. I won't fix it myself 🙂

@slovnicki
Copy link
Owner Author

Well, well, well,...
https://github.com/slovnicki/beamer/tree/master/examples/nested_navigation
example-nested-navigation

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
documentation Improvements or additions to documentation enhancement New feature or request help wanted Could use a couple of fresh hands
Projects
None yet
Development

No branches or pull requests

3 participants