Flutter中 WidgetsFlutterBinding.ensureInitialized(); 有什么作用,在什么时候执行呢?

873 阅读2分钟

在 Flutter 应用程序中,WidgetsFlutterBinding.ensureInitialized() 方法的作用是确保框架的初始化。这个调用是必要的,因为它关联了 Flutter 的 engine 和 widget library,使得你可以在运行任何其他操作之前进行安全地使用 Flutter 各种功能。

具体来说,调用 WidgetsFlutterBinding.ensureInitialized() 可以保证:

  • 初始化了消息循环和其他基础设施,这样你就可以创建和交互 Future 和 Stream 等。
  • 对于使用了插件的应用程序,确保插件的初始化工作已经完成,确保可以在插件和平台代码之间正确地交互数据。

通常,如果你是在应用的 main() 函数中,直接调用 runApp() 方法,并开始构建 widgets 之前不需要显式调用这个方法;但在如下情况中,你需要显式地调用它:

  • 在启动函数 main() 里的 runApp() 调用之前进行异步操作:  如果你需要在调用 runApp() 之前执行异步代码,如获取偏好设置、初始化数据库等,那么你需要先确保框架初始化。
  • 在插件初始化之前使用插件:  某些插件在使用前要求先进行初始化。如果你需要在你的 main() 函数中做这些事情,并在 runApp() 之前进行异步操作(如初始化 Firebase),你需要先调用 WidgetsFlutterBinding.ensureInitialized()

下面是一个示例,展示了在 main() 函数中调用 WidgetsFlutterBinding.ensureInitialized() 的情景:

import 'package:flutter/material.dart';

void main() async {
  // 确保Flutter widget绑定初始化
  WidgetsFlutterBinding.ensureInitialized();

  // 可能的异步操作,比如获取本地存储数据等
  final prefs = await SharedPreferences.getInstance();
  final bool isDarkMode = prefs.getBool('isDarkMode') ?? false;

  // 运行整个 Flutter 应用
  runApp(MyApp(isDarkMode: isDarkMode));
}

class MyApp extends StatelessWidget {
  final bool isDarkMode;

  MyApp({required this.isDarkMode});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: isDarkMode ? ThemeData.dark() : ThemeData.light(),
      home: MyHomePage(),
    );
  }
}

class MyHomePage extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Flutter Demo Home Page'),
      ),
      body: Center(
        child: Text(
          'Welcome to Flutter!',
        ),
      ),
    );
  }
}

在上面的代码中,我展示了如何在启动应用之前使用 WidgetsFlutterBinding.ensureInitialized() 来进行异步操作。这是必要的,因为 SharedPreferences.getInstance() 是一个异步操作,如果不先初始化 Flutter 的绑定,那么在 main() 函数中进行异步操作可能会导致错误。通过确保初始化,我们可以安全地在 main() 函数中调用 SharedPreferences.getInstance(),输出结果后再运行 runApp(),以确保我们加载了正确的主题数据。