import 'package:flutter/material.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:go_router/go_router.dart'; import 'package:worldhopper/config/router.dart'; import 'package:worldhopper/l10n/app_localizations.dart'; import 'package:worldhopper/helpers/responsive_helper.dart'; import 'package:worldhopper/providers/navigation_provider.dart'; /// Shell widget that provides the bottom navigation bar /// and handles tab switching for the main app sections class MainShellScreen extends ConsumerStatefulWidget { final StatefulNavigationShell navigationShell; const MainShellScreen({ super.key, required this.navigationShell, }); @override ConsumerState createState() => _MainShellScreenState(); } class _MainShellScreenState extends ConsumerState { bool _initialized = false; @override void didChangeDependencies() { super.didChangeDependencies(); if (!_initialized) { _initialized = true; // Load saved tab index and navigate to it final savedIndex = ref.read(navigationStateProvider); if (savedIndex != widget.navigationShell.currentIndex) { // Delay navigation to allow widget tree to build WidgetsBinding.instance.addPostFrameCallback((_) { widget.navigationShell.goBranch(savedIndex, initialLocation: true); }); } } } void _onDestinationSelected(int index) { // Persist the tab change ref.read(navigationStateProvider.notifier).setTabIndex(index); // If re-tapping the same tab, pop any Navigator-pushed routes // (e.g. sub-settings screens) back to the branch root if (index == widget.navigationShell.currentIndex) { final navigatorKey = AppRouter.branchNavigatorKeys[index]; navigatorKey.currentState?.popUntil((route) => route.isFirst); } // Navigate to the selected tab widget.navigationShell.goBranch( index, initialLocation: index == widget.navigationShell.currentIndex, ); } @override Widget build(BuildContext context) { final l10n = AppLocalizations.of(context); final wide = isWideScreen(MediaQuery.of(context).size.width); if (wide) { return Scaffold( body: Row( children: [ NavigationRail( labelType: NavigationRailLabelType.all, selectedIndex: widget.navigationShell.currentIndex, onDestinationSelected: _onDestinationSelected, destinations: [ NavigationRailDestination( icon: const Icon(Icons.auto_stories_outlined), selectedIcon: const Icon(Icons.auto_stories), label: Text(l10n.navLibrary), ), NavigationRailDestination( icon: const Icon(Icons.dns_outlined), selectedIcon: const Icon(Icons.dns), label: Text(l10n.navServers), ), NavigationRailDestination( icon: const Icon(Icons.settings_outlined), selectedIcon: const Icon(Icons.settings), label: Text(l10n.navSettings), ), ], ), const VerticalDivider(thickness: 1, width: 1), Expanded(child: widget.navigationShell), ], ), ); } return Scaffold( body: widget.navigationShell, bottomNavigationBar: NavigationBar( selectedIndex: widget.navigationShell.currentIndex, onDestinationSelected: _onDestinationSelected, destinations: [ NavigationDestination( icon: const Icon(Icons.auto_stories_outlined), selectedIcon: const Icon(Icons.auto_stories), label: l10n.navLibrary, ), NavigationDestination( icon: const Icon(Icons.dns_outlined), selectedIcon: const Icon(Icons.dns), label: l10n.navServers, ), NavigationDestination( icon: const Icon(Icons.settings_outlined), selectedIcon: const Icon(Icons.settings), label: l10n.navSettings, ), ], ), ); } }