How do you get proper Material 3 behavior out of NavigationBar?

84 Views Asked by At

I am instantiating a NavigationBar but navigating from a tab's base page to a detail page within (drilling down from a summary to detail) makes the detail go full screen instead of remain within the tab's restricted space (the 90% of the screen above the tab bar). Material has dictated this behavior for years. I have seen many work-arounds out there but I can't believe that Google is so sloppy as to leave this unaddressed.

I would assume there is a flag akin to useMaterial3 that could be provided to NavigationBar to make it behavior properly, but I've not been able to find anything of the sort. Does someone know how to make this widget behave in the updated Material fashion?

class _MyWidgetState extends State<MyWidget> {
  int currentIndex = 0;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      bottomNavigationBar: NavigationBar(
        onDestinationSelected: (int index) {
          setState(() {
            currentIndex = index;
          });
        },
        selectedIndex: currentIndex,
        destinations: const <Widget>[
          NavigationDestination(icon: Icon(Icons.home), label: "Page 1"),
          NavigationDestination(icon: Icon(Icons.person), label: "Page 2"),
        ],
      ),
      body: <Widget>[
        const Page1(),
        const Page2(),
      ][currentIndex],
    );
  }
}

I implemented a work-around to simulate the correct behavior, but it clashes with trying to implement CupertinoPageTransitions in order to get swipe-back functionality (which requires use of Navigator when drilling into that detail page). So I'd really love to know how to make the actual Google-created widget behave as Google claims it should.

class _TabState extends State<Tab> {
  int _index = 0;
  final List<Map> _detail = [];

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: IndexedStack(
        index: _index,
        children: [
          SummaryWidget(onTap: showDetail),
          for (final data in _detail) DetailWidget(id: id, onClose: removeDetail);
        ],
      ),
    );
  }
  
  showDetail() {
    setState(() {
      _detail.add(data);
      _index = 1;
    });
  }

  removeDetail() {
    setState(() {
      _index = 0;
      _detail.removeLast();
    });
  }
}
0

There are 0 best solutions below