Prism 源码解读6-事件聚合
0 介绍
事件提供的是1对多的绑定,通过委托链实现对订阅者的调用,事件必须要通过发布者调用。同时事件订阅是强引用,事件订阅者的生命周期总是大于等于事件发布者。如果代码中事件很多就会充斥着各种事件的订阅,不利于维护。
Prism提供了EventAggregator器,可以在任何地方进行订阅,任何地方进行调用/发布,实例只对EventAggregator和事件类型有依赖,使用了弱引用,可以过滤消息,并可以控制回调函数线程。感觉很强大,实现应该挺复杂,但看到实现时有一种恍然大悟的感觉,喜欢这种简单而强大的实现。开始一探究竟吧!
1 整体框架
先从整体框架解析一下吧。EventAggregator

发现这只是一个集合类,保存着事件类型和事件实例,还有一个线程上下文保证线程同步。

看一下EventBase,看来所有的订阅委托都是在着保存着,因为有一个IEventSubscription列表。EventSubscription因该是订阅委托的包装器。

看到有SubscriptionToken和DelegateReference,

这边终于看到Delegate的真正存放地点了。这边存放了弱引用,委托类型和MethodInfo。
看到这边理解了,通过一个集合保存事件,这个事件内部存储着所有订阅委托。
当我们向订阅发布的时候,只要从这个集合中获取对应的事件进行订阅发布。相通了是不是觉得自己也能写一个简单的事件聚合器呢?
2 具体代码
来具体看看代码吧。

看到EventAggregator通过依赖注入,获取MessageSentEvent进行订阅。

保存了UI线程上下文和将事件类型和事件类型实例放到集合中,加锁,线程安全。

事件可以啥都没有但必须继承PubSubEvent,功能都在这里实现了。

threadOption默认是PublisherTHread,这里是说回调函数在什么线程执行,BackgroundThread就是Task创建的线程池线程,Dispatcher就是UI线程



内部订阅进行了校验(主要是委托不为空)和Token

看完订阅再来看看调用

在任何地方调用,还是去EventAggregator获取事件实例,然后调用其Publish


从这边可以看出就是依次调用列表中的委托,DispatcherEventSubscription 调用

BackgroundEventSubscription 调用

到现在还没有讲到Filter,来看看怎么实现过滤消息

在订阅的时候值接受含有Brian的消息
使用了泛型的订阅


使用了prcidate<>保存了filter委托,
在Publish主要就是在GetExecutionStrategy方法中

filter返回true触发订阅委托。
总结
事件聚合提供了一个很好的思路,我们甚至可以利用事件聚合的思想实现事件聚合微服务组件。
Prism 源码解读6-事件聚合的更多相关文章
- Prism 源码解读1-Bootstrapper和Region的创建
介绍 之前也研究过Prism框架但是一直没有深入理解,现在项目上想把一个Winform的桌面应用程序改造成WPF程序,同时我希望程序是可测试可维护架构良好的,Prism的这些设计理念正好符合我的需求, ...
- Prism 源码解读5-数据绑定和命令
介绍 WPF本身就支持通知.绑定和命令,实现ViewModel和VIew之间的通讯,但相对来说功能比较少,Prism扩充了这些功能并提供更加强有力,简洁的数据绑定和命令. 0 绑定通知 WPF的绑定通 ...
- Prism 源码解读2-View的加载和控制
介绍 上一篇介绍了Region,这一篇跟Region息息相关,讲一下Region中View的加载方式及控制. 4.ViewDiscovery 在创建好Region后需要将View添加到Region中. ...
- Prism 源码解读3-Modules加载
介绍 在软件开发过程中,总想组件式的开发方式,各个组件之间最好互不影响,独立测试.Prism的Modules很好的满足了这一点. 这个架构图很好了讲解了Prism的Modules的概念 Prism支持 ...
- Prism 源码解读7-导航
介绍 Prism提供了一个非常强大的功能导航,导航的意思就是指定对应的View显示.这个导航的强大之处有: 可以设置导航前后的动作 可以指定View实例的生命周期,可以是否导航到新的View实例 提供 ...
- Prism 源码解读4-ViewModel注入
介绍 介绍一个Prism的MVVM实现,主要介绍Prism如何在WPF上进行的一些封装,以实现MVVM.MVVM到底是什么呢?看一下这一幅经典的图 以前没有ViewModel这个概念,就是将Model ...
- AFNetworking 3.0 源码解读 总结(干货)(下)
承接上一篇AFNetworking 3.0 源码解读 总结(干货)(上) 21.网络服务类型NSURLRequestNetworkServiceType 示例代码: typedef NS_ENUM(N ...
- AFNetworking 3.0 源码解读 总结(干货)(上)
养成记笔记的习惯,对于一个软件工程师来说,我觉得很重要.记得在知乎上看到过一个问题,说是人类最大的缺点是什么?我个人觉得记忆算是一个缺点.它就像时间一样,会自己消散. 前言 终于写完了 AFNetwo ...
- AFNetworking 3.0 源码解读(十)之 UIActivityIndicatorView/UIRefreshControl/UIImageView + AFNetworking
我们应该看到过很多类似这样的例子:某个控件拥有加载网络图片的能力.但这究竟是怎么做到的呢?看完这篇文章就明白了. 前言 这篇我们会介绍 AFNetworking 中的3个UIKit中的分类.UIAct ...
随机推荐
- 算法入门——二分查找,旅行商问题,大O表示法
一. 算法入门 博主在市面上发现了很多,很多有关书算法的书籍,但是真正能够让初学者易懂的算法书籍,只是一点点,以下我讲以 Aditya Bhargava写的一本关于算法的入门书籍,为参考,这本书非常的 ...
- MVC01
1.Controller 1) 添加: 在Controller目录右键进行添加,出现很多模式供选择,选择空的Controller,命名后新建.新建后Views 目录将同步生成相应名称的视图文件目录 均 ...
- 【Amaple教程】6. 路由配置
在 第1节<启动路由> 章节中为了能让单页应用顺利跑起来,我们提前介绍了简单的路由配置方法.我们已了解路由配置的目的是指定不同的url下对应的 模块节点(也叫做模块容器)内应该显示哪个模块 ...
- HTML5 Canvas(基础知识)
最近笔者在学习HTML5的新元素<canvas>,会分享一些基础知识以及小例子,最终使用<canvas>实现一个绘制简单图表(条形图.线图或者饼图)的js库,会更新一到两篇文章 ...
- TARS基金会:构建微服务开源生态
导语 在20世纪60至70年代,软件开发人员通常在大型机和小型机上使用单体架构进行软件开发,没有一个应用程序能够满足大多数最终用户的需求.垂直行业使用的软件代码量更小,与其他应用程序的接口更简单,而可 ...
- Elasticsearch数据建模笔记
数据建模 数据建模是创建数据模型的过程 数据模型是对真实世界进行抽象描述的一种工具和方法,实现对现实世界的映射 三个过程:概念模型=>逻辑模型=>数据模型 数据模型:结合具体的数据库,在满 ...
- python sqlite3操作类扩展,包含数据库分页
一.原因 最近在使用python3和sqlite3编辑一些小程序,由于要使用数据库,就离不开增.删.改.查,sqlite3的操作同java里的jdbc很像,于是就想找现成的操作类,找来找去,发现一个 ...
- 序列化器:ModelSerializer
ModelSerializer 类提供了一个快捷方式,可让你基于 Models 自动创建一个 Serializer 类,其中的字段与模型类字段对应. ModelSerializer 类与常规 Seri ...
- 移动端Rem适配(基于vue-cli3 ,ui框架用的是vant-ui)
介绍postcss-pxtorem 是一款 postcss 插件,用于将单位转化为 remlib-flexible 用于设置 rem 基准值 1.安装lib-flexible(用于设置 rem 基准值 ...
- 【JAVA进阶架构师指南】之二:JVM篇
前言 谈到JAVA,就不得不提JVM---JAVA程序员绕不开的话题.也许有童鞋会说,我不懂JVM,但是我一样可以写出JAVA代码,我相信说这种话的童鞋,往往是只有1-3年的初级开发人员,对JAV ...