skip to Main Content

I have a series of APIs that are called on my home page and a series of widgets are created after receiving data from the server.
I want to shorten the loading time of these widgets, so I want my home page to be fully built while my splash screen is being shown, so that when the navigation operation happens, the audience will be faced with a ready page.

tested the following code, but apparently, until the HomeScreen widget is used in the build method, the build operation and calling the apis will not happen on the home page:

import 'package:flutter/material.dart';
import 'package:imam/config/routes/routes.dart';
import 'package:imam/core/utils/extensions.dart';
import 'package:imam/features/home/screens/home_screen.dart';

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

  @override
  State<SplashScreen> createState() => _SplashScreenState();
}

class _SplashScreenState extends State<SplashScreen> {
  late HomeScreen homeScreen;

  @override
  void initState() {
    homeScreen =  HomeScreen();
    Future.delayed(const Duration(seconds: 3), () {
      context.pushNamed(Routes.homeScreen);
    });
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return const Scaffold(
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            Text(
              'Splash Screen',
              style: TextStyle(
                fontWeight: FontWeight.bold,
                fontSize: 24,
              ),
            ),
            SizedBox(height: 20),
            CircularProgressIndicator(),
          ],
        ),
      ),
    );
  }
}

please pay attention that I don’t want to wait for the load data of the home page, I just want all the components of the home page to be created at the same time in those 3 seconds when the splash page is shown.

And I don’t want to use the Stack widget as a trick to solve this problem because the pages are supposed to be moved with navigation.
Thanks for your kindness.

2

Answers


  1. try using FutureBuilder in your SplashScreen,

    class SplashScreen extends StatefulWidget {
      const SplashScreen({super.key});
    
      @override
      SplashScreenState createState() => SplashScreenState();
    }
    
    class SplashScreenState extends State<SplashScreen> {
      late Future<void> _initializing;
    
      @override
      void initState() {
        super.initState();
        _initializing = _initializingApp();
      }
    
      Future<void> _initializingApp() async {
        // Perform expensive operations, such as data fetching or widget pre-building
        await Future.delayed(const Duration(seconds: 3));
        //Note: you can also fetch all the data, your HomeScreen() needs, in here and pass it to the HomeScreen()
      }
    
      @override
      Widget build(BuildContext context) {
        return FutureBuilder(
          future: _initializing,
          builder: (context, snapshot) {
            if (snapshot.connectionState == ConnectionState.done) {
              return const HomeScreen();
            } else if (snapshot.hasError) {
              //handle errors here
            } else {
              return const Scaffold(
                body: Center(
                  child: Column(
                    mainAxisAlignment: MainAxisAlignment.center,
                    children: [
                      Text(
                        'Splash Screen',
                        style: TextStyle(
                          fontWeight: FontWeight.bold,
                          fontSize: 24,
                        ),
                      ),
                      SizedBox(height: 20),
                      CircularProgressIndicator(),
                    ],
                  ),
                ),
              );
            }
          },
        );
      }
    }
    
    Login or Signup to reply.
  2. please pay attention that I don’t want to wait for the load data of
    the home page

    Then follow the approach that you exactly want! Since you mentioned that you don’t want to wait for the data to load on the home screen, do not load it on the home screen.

    Instead, one of the approaches you could follow is loading data on the splash screen, and then passing it to the home screen. The splash screen loads (asynchronously) the necessary data to be passed to the home screen, therefore navigate to the home screen and pass the loaded data.

    Here is a high-level coding example:

    Splash screen:

    class SplashScreen extends StatefulWidget {
      @override
      _SplashScreenState createState() => _SplashScreenState();
    }
    
    class _SplashScreenState extends State<SplashScreen> {
      @override
      void initState() {
        super.initState();
        _loadData();
      }
    
      Future<void> _loadData() async {
        await Future.delayed(Duration(seconds: 3));
    
        final data = "Loaded Data";
        Navigator.of(context).pushReplacement(
          MaterialPageRoute(
            builder: (context) => HomeScreen(data: data),
          ),
        );
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          body: Center(
            child: CircularProgressIndicator(),
          ),
        );
      }
    }
    

    _loadData() should be the simulation of data loading. Therefore, you pass data to HomeScreen.

    Next, Home Screen:

    class HomeScreen extends StatelessWidget {
      final String data;
    
      HomeScreen({required this.data});
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          appBar: AppBar(
            title: Text('Home Screen'),
          ),
          body: Center(
            child: Text(data),
          ),
        );
      }
    }
    

    Keep in mind that in this case, the data-loading business logic will be a part of the splash screen; The Home screen receives data instead of loading it.


    Additionally, as a quick workaround, you could check this answer:

    https://stackoverflow.com/a/70489180/5501940

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search