1.场景(数据更新,状态改变,消息通知等)
我们经常会需要一个广播机制,用以跨页面事件通知这时候,一个事件总线便会非常有用,事件总线通常实现了订阅者模式,订阅者模式包含发布者和订阅者两种角色,可以通过事件总线来触发事件和监听事件
2.全局事件总线,单例模式
//订阅者回调签名
typedef void EventCallback(arg);
class EventBus{
///私有构造函数
EventBus._internal();
///静态对象
static EventBus _singleton = EventBus._internal();
///工厂构造方法
factory EventBus() => _singleton;
///事件订阅队列
var _eMap = Map<Object , List<EventCallback>>();
///订阅
void on(String eventName , EventCallback f){
if(eventName == null || f == null)
return;
_eMap[eventName] ??= List<EventCallback>();
_eMap[eventName].add(f);
}
///取消订阅
void off(String eventName , [EventCallback f]){
var list = _eMap[eventName];
if(eventName == null || list == null)
return;
if(f == null ){
_eMap[eventName] = null;
}else{
list.remove(f);
}
}
///发送事件
void send(String eventName , [args]){
var list = _eMap[eventName];
if(list == null)
return;
int length = list.length - 1;
for(int i = length ; i >= 0 ; i--){
list[i](args);
}
}
}
3.使用案例
- 在需要的地方evnet.send发送事件
- 在监听页面的initstatus方法中event.on获取监听和返回的数据
- 在dispose中event.off取消事件
import 'package:flutter/material.dart';
import 'package:flutter_widget_project/dio_util/constant.dart';
import 'package:flutter_widget_project/event_bus/event_bus.dart';
class EventBusPage extends StatefulWidget {
@override
_EventBusPageState createState() => _EventBusPageState();
}
class _EventBusPageState extends State<EventBusPage> {
EventBus _eventBus = EventBus();
@override
void initState() {
// TODO: implement initState
super.initState();
///一定要写在init方法里
_eventBus.on("login", (arg) {
print("$arg");
});
}
@override
void dispose() {
// TODO: implement dispose
super.dispose();
///一定要关闭,防止泄露
_eventBus.off("login");
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("EventBus"),
),
body: Column(
children: [
MaterialButton(
child: Text("nextpage"),
color: Colors.blue,
onPressed: () => push(EventBusPage2()),
),
],
),
);
}
}
class EventBusPage2 extends StatefulWidget {
@override
_EventBusPage2State createState() => _EventBusPage2State();
}
class _EventBusPage2State extends State<EventBusPage2> {
EventBus _eventBus = EventBus();
@override
void dispose() {
// TODO: implement dispose
super.dispose();
_eventBus.off("login");
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("EventBus"),
),
body: Column(
children: [
MaterialButton(
child: Text("eventsend"),
color: Colors.blue,
onPressed: (){
_eventBus.send("login", ["zws", "123"]);
Navigator.pop(context);
},
),
],
),
);
}
}