最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

firebase - Flutter BottomNavigation not visible - Stack Overflow

programmeradmin3浏览0评论

I am building an app with Flutter and I am currently trying to implement a bottomNavigationBar but currently it is not visible when I run the app. My first guess was it could be something to do with the Streambuilder that I have put in the home property of the build method in MyApp class

Here's my code:

import 'package:firebase_app_check/firebase_app_check.dart';
import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:iinhouse/core/screens/create_account.dart';
import 'package:iinhouse/core/screens/home.dart';
import 'package:iinhouse/core/screens/loader.dart';
import 'package:iinhouse/core/screens/login.dart';
import 'package:iinhouse/core/screens/verify_email.dart';

// Create new screens for the bottom navigation.
class Screen1 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 1'));
  }
}

class Screen2 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 2'));
  }
}

class Screen3 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 3'));
  }
}

void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await Firebase.initializeApp();
  await FirebaseAppCheck.instance.activate();
  runApp(const ProviderScope(child: MyApp()));
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'iinhouse',
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
        useMaterial3: true,
      ),
      routes: {
        '/login': (context) => const Login(),
        '/create_account': (context) => const CreateAccountPage(),
        '/verify_email': (context) => const VerifyEmailScreen(),
        '/home': (context) => HomeScreen()
      },
      initialRoute: '/login',
      home: StreamBuilder(
        stream: FirebaseAuth.instance.authStateChanges(),
        builder: (context, snapshot) {
          if (snapshot.connectionState == ConnectionState.waiting) {
            return Loader();
          }

          if (snapshot.hasData) {
            final user = snapshot.data;
            if (user!.emailVerified) {
              return MyHomePage(); // Use the new wrapper widget
            } else {
              return const VerifyEmailScreen();
            }
          }

          return const Login();
        },
      ),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  int _selectedIndex = 0;

  final List<Widget> _screens = <Widget>[
    HomeScreen(), // Ensure HomeScreen is const if possible
    Screen2(),
    Screen3(),
  ];

  void _onItemTapped(int index) {
    setState(() {
      _selectedIndex = index;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: _screens[_selectedIndex],
      bottomNavigationBar: BottomNavigationBar(
        type: BottomNavigationBarType.fixed,
        items: const <BottomNavigationBarItem>[
          BottomNavigationBarItem(
            backgroundColor: Colors.white,
            icon: Icon(
              Icons.home,
              color: Colors.black,
            ),
            label: 'Home',
          ),
          BottomNavigationBarItem(
            icon: Icon(Icons.business),
            label: 'Business',
          ),
          BottomNavigationBarItem(
            icon: Icon(Icons.school),
            label: 'School',
          ),
        ],
        currentIndex: _selectedIndex,
        selectedItemColor: Colors.deepPurple,
        onTap: _onItemTapped,
      ),
    );
  }
}

class HomeScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Text('Home Screen'),
      ),
    );
  }
}

I am building an app with Flutter and I am currently trying to implement a bottomNavigationBar but currently it is not visible when I run the app. My first guess was it could be something to do with the Streambuilder that I have put in the home property of the build method in MyApp class

Here's my code:

import 'package:firebase_app_check/firebase_app_check.dart';
import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:iinhouse/core/screens/create_account.dart';
import 'package:iinhouse/core/screens/home.dart';
import 'package:iinhouse/core/screens/loader.dart';
import 'package:iinhouse/core/screens/login.dart';
import 'package:iinhouse/core/screens/verify_email.dart';

// Create new screens for the bottom navigation.
class Screen1 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 1'));
  }
}

class Screen2 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 2'));
  }
}

class Screen3 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(child: Text('Screen 3'));
  }
}

void main() async {
  WidgetsFlutterBinding.ensureInitialized();
  await Firebase.initializeApp();
  await FirebaseAppCheck.instance.activate();
  runApp(const ProviderScope(child: MyApp()));
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'iinhouse',
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
        useMaterial3: true,
      ),
      routes: {
        '/login': (context) => const Login(),
        '/create_account': (context) => const CreateAccountPage(),
        '/verify_email': (context) => const VerifyEmailScreen(),
        '/home': (context) => HomeScreen()
      },
      initialRoute: '/login',
      home: StreamBuilder(
        stream: FirebaseAuth.instance.authStateChanges(),
        builder: (context, snapshot) {
          if (snapshot.connectionState == ConnectionState.waiting) {
            return Loader();
          }

          if (snapshot.hasData) {
            final user = snapshot.data;
            if (user!.emailVerified) {
              return MyHomePage(); // Use the new wrapper widget
            } else {
              return const VerifyEmailScreen();
            }
          }

          return const Login();
        },
      ),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  int _selectedIndex = 0;

  final List<Widget> _screens = <Widget>[
    HomeScreen(), // Ensure HomeScreen is const if possible
    Screen2(),
    Screen3(),
  ];

  void _onItemTapped(int index) {
    setState(() {
      _selectedIndex = index;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: _screens[_selectedIndex],
      bottomNavigationBar: BottomNavigationBar(
        type: BottomNavigationBarType.fixed,
        items: const <BottomNavigationBarItem>[
          BottomNavigationBarItem(
            backgroundColor: Colors.white,
            icon: Icon(
              Icons.home,
              color: Colors.black,
            ),
            label: 'Home',
          ),
          BottomNavigationBarItem(
            icon: Icon(Icons.business),
            label: 'Business',
          ),
          BottomNavigationBarItem(
            icon: Icon(Icons.school),
            label: 'School',
          ),
        ],
        currentIndex: _selectedIndex,
        selectedItemColor: Colors.deepPurple,
        onTap: _onItemTapped,
      ),
    );
  }
}

class HomeScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: Center(
        child: Text('Home Screen'),
      ),
    );
  }
}
Share Improve this question asked Mar 20 at 10:00 Anesu MazvimaviAnesu Mazvimavi 1671 silver badge11 bronze badges 5
  • You should see the bottom navigation bar after the Firebase loads and if the user has emailVerified. Do you see it then? If so, what else do you expect? – Albert221 Commented Mar 20 at 10:07
  • @Albert221 I was thinking when the Firebase Loads and the user has had their email verified, shouldn't it go to the Homescreen where it has the bottom navigation bar present at the bottom? – Anesu Mazvimavi Commented Mar 20 at 10:13
  • I think so, what behavior do you see instead? – Albert221 Commented Mar 20 at 10:37
  • The initialRoute will be considered when it is defined, and home will not take effect. Just remove initialRoute from MaterialApp – Slashbin Commented Mar 20 at 10:53
  • So I removed intitalRoute and the bottom navigation bar still wasn't showing. However if I removed the Streambuilder the bottom navigation bar is now reflecting – Anesu Mazvimavi Commented Apr 4 at 9:04
Add a comment  | 

1 Answer 1

Reset to default 0

With the StreamBuilder you have setup, Authentication changes will automatically handle the shown page. All you need to do is remove:

  1. initialRoute
  2. Remove other navigations you might be doing, like navigating to the HomeScreen after login. Only CreateAccountPage needs to be navigated to manually.
  3. You might want to listen to userChanges() instead, authStateChanges() will not be triggered when user email gets verified.
发布评论

评论列表(0)

  1. 暂无评论