博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Unity应用架构设计(5)——ViewModel之间如何共享数据
阅读量:6485 次
发布时间:2019-06-23

本文共 1692 字,大约阅读时间需要 5 分钟。

对于客户端应用程序而言,单页应用程序(Single Page Application)是最常见的表现形式。有经验的开发人员往往会把一个View分解多个SubView。那么,如何在多个SubView之间 『共享数据』 是一个很棘手的事情。又因为ViewModel才是真正为View提供数据来源,所以本质上『共享数据』指的是多个ViewModel之间共享同一块数据控件。

JavaScript中的原型链

谈到『共享』两字,脑海里跳出第一个印象就是『继承』。对吧,因为你是父母的孩子,所以理所当然你可以和父母共享家中的一切。所以『共享』的前提,就是构建一个『继承链』,也就是JavaScript中的『原型链』。

那么JavaScript是怎样实现原型链呢?有经验的JavaScript程序员想必早就记的滚瓜烂熟了——通过内置属性 __proto__ 来实现。

所以ViewModel之间『共享数据』的核心就是如何去实现一个继承链,如下所示:

为ViewModel构建继承关系

有了上述的分析之后,只要仿照JavaScript的 __proto__ 的实现,我们对所有ViewModel的基类ViewModelBase添加一个ParentViewModel 属性,它代表当前ViewModel的父亲对象。

public class ViewModelBase{    public ViewModelBase ParentViewModel { get; set; }    //...}复制代码

接着我参考了WPF中是怎样获取父ViewModel当中的数据:

Binding="{Binding RelativeSource={RelativeSource FindAncestor,  AncestorType={x:Type Window}}, Path=DataContext.ParentViewModelProperty}复制代码

可以看到通过 FindAncestor 方法,去指定 AncestorType 类型的上层对象中获取数据。

所以,我为ViewModelBase 增加一个扩展方法,可以通过继承链实现从指定的祖先对象获取数据。

public static IEnumerable
Ancestors
(this ViewModelBase origin) where T : ViewModelBase{ if (origin==null) { yield break; } var parentViewModel = origin.ParentViewModel; while (parentViewModel!=null) { var castedViewModel = parentViewModel as T; if (castedViewModel != null) { yield return castedViewModel; } parentViewModel = parentViewModel.ParentViewModel; }}复制代码

对应在ViewModel中,可以通过 Ancestors扩展方法获取上层对象的数据

var ancestors = this.Ancestors
();复制代码

最后,以图示的形式会更加直观,下图所示,SubViewModel依靠继承链可以轻松访问到ParentViewModel的共享数据:

小结

本篇文章介绍了怎样在ViewModel之间共享数据,实际上解决方案是非常简单的,人为的构造了一个继承链并随着继承链往上找,总是能找到希望获取到的数据。类似与JavaScript中的原型链,维护了一种至上而下的父子关系。

源代码托管在Github上,

欢迎关注我的公众号:

转载地址:http://ggiuo.baihongyu.com/

你可能感兴趣的文章
删除恢复Hadoop集群中的DataNode
查看>>
Silverlight 2动态创建矩形对象(附完整源代码)
查看>>
从京东技术演进看互联网企业的成长历程
查看>>
MFC ado+mysql+odbc技术分享
查看>>
js中让字符串中特定字符红色显示
查看>>
HttpClient4.5教程-第二章-连接管理
查看>>
redhat Nginx 安装
查看>>
oracle 配置监听
查看>>
moosefs即将发布新版
查看>>
SmartGit 试用过期
查看>>
python 测试驱动开发的简单例子
查看>>
Aes 加密简单例子
查看>>
AE 线编辑
查看>>
软件设计之UML—UML的构成[上]
查看>>
如何使用AdMob中介界面?
查看>>
分享一个shell脚本:通过Jumper机器来创建Jumper和target机器账号
查看>>
UITableViewCell分割线不是左对齐的问题
查看>>
CentOS7 编译安装PHP7
查看>>
MySQL常见错误代码及代码说明
查看>>
Cglib动态代理基础使用
查看>>