「这是我参加11月更文挑战的第10天,活动详情检查:2021最后一次更文挑战」。
前面咱们剖析学习了Flutter的项目结构,今天咱们来看看main.dart里边的这样一段代码
void main() {
runApp(const MyApp());
}
Flutter 程序入口
main
办法一般是Flutter App的入口,它内部经过调用runApp办法使用整个Widget增加和运转。而且咱们能够在不同的时机再次调用runApp
,比如在app 启动的时候由于数据加载等问题会有一个空白屏幕的时刻。这个时候咱们就能够经过多次调用runApp
来完成,简略的比如如下:
void main() {
runApp(const SplashScreen()); //
Future.delayed(Duration(seconds: 10), () {
runApp(const MyApp());
});
}
runApp
在外部经过调用runApp办法完成整个Widget作用,那么咱们就去看看runApp办法的完成,如下:
void runApp(Widget app) {
WidgetsFlutterBinding.ensureInitialized()
..scheduleAttachRootWidget(app)
..scheduleWarmUpFrame();
}
这里能够看到上面有三行代码,分别代表了Flutter App启动的三个步骤:
-
WidgetsFlutterBinding
初始化(ensureInitialized()
),与Flutter Engine
进行通讯。 - 绑定根节点创立flutter 闻名的三棵树(
scheduleAttachRootWidget(app)
)进行布局。 - 将布局出来的树进行烘托(
scheduleWarmUpFrame()
)
今天咱们讲WidgetsFlutterBinding,不过也说WidgetsFlutterBinding,由于后边俩个自己学习的仍是半桶水。
什么是WidgetsFlutterBinding?
官方的文档Widgets Binding,以及源代码里边注解有一句话是这样的:
The glue between the widgets layer and the Flutter engine.
你能够看到SystemChannels用于建立通讯(MethodChannel)与引擎(其他语言环境的系统)。
mixin WidgetsBinding on BindingBase, ServicesBinding, SchedulerBinding, GestureBinding, RendererBinding, SemanticsBinding {
@override
void initInstances() {
super.initInstances();
_instance = this;
。。。。。。
SystemChannels.navigation.setMethodCallHandler(_handleNavigationInvocation);
。。。。。。
return true;
}());
}
咱们看头部一行代码能够经过字面意思能够发现WidgetsFlutterBinding 承继自 BindingBase,也带有许多 XXXBinding。WidgetsFlutterBinding 将是 Widget 架构和 Flutter Engine 连接的中心桥梁,也是整个 Flutter 使用层的中心。经过 ensureInitialized()
办法咱们能够得到一个大局单例 WidgetsFlutterBinding。
略微解释一下各种Binding的作用。
- ServicesBinding:Flutter System 渠道音讯监听绑定类。即Platform与Flutter Layer通讯相关服务,一起注册并监听使用生命周期回调。
- SchedulerBinding:Flutter 制作调度器相关绑定类,调试统计制作过程持续时刻等编译形式下的操作。
- GestureBinding:Flutter Gesture事情绑定,处理屏幕事情分发和事情回调,其初始化办法的关键点是回调事情处理
_handlePointerDataPacket
函数被赋值给window的属性,以便window在接收到屏幕事情后调用,window的实例是 Framework Layer 和 Engine 桥接层用来处理屏幕事情。 - RendererBinding:引擎之间的烘托树和Flutter Binding类,内部重点是持有烘托树的根节点。
- SemanticsBinding:引擎之间的语义树和 Flutter Binding 类。
有时候咱们会在发现有的app 在在运转使用程序之前先与 Flutter Engine 进行通讯,所以要先将WidgetsFlutterBinding.ensureInitialized()
提早。
void main() {
WidgetsFlutterBinding.ensureInitialized();
runApp(const MyApp()); //
}
SystemChannels
在binding 初始化里边有这个一句话:
SystemChannels.navigation.setMethodCallHandler(_handleNavigationInvocation);
假如点击进去检查SystemChannels
的源码,能够看到内容使用了MethodChannel
(l办法通道)、EventChanne
(事情通道)、以及生命周期的东西。简略的用表格总结如下(可能不全。):
种类 | 作用 | Flutter Service |
---|---|---|
lifecycle | 生命周期 | widget |
navigation | 导航 | widget |
system | binding中使用 | widget |
accessibility | 辅佐功能(如读取文本信息) | PlatformViews, Semantics |
platform | 系统设置(画面旋转等) | SemanticsService,RouteNotificationMessages etc. |
platform_views | 特定渠道视图操作 | AndroidView, UiKitView |
skia | 图形引擎 | – |
keyEvent | 键输入 | RawKeyEvent |
textInput | 文本输入 | TextInput, AndroidView, UiKitView |
WidgetsBindingObserver
而关于 WidgetsBinding在Widget里边的详细使用,能够检查WidgetsBindingObserver源码,下面举一个简略的使用比如:
class _MyHomePageState extends State<MyHomePage> with WidgetsBindingObserver {
AppLifecycleState _state;
@override void initState() {
super.initState(); WidgetsBinding.instance.addObserver(this);
}
@override void dispose() { WidgetsBinding.instance.removeObserver(this);
super.dispose();
}
@override void didChangeAppLifecycleState(AppLifecycleState state){ print('state = $state');
}
}