DSF view Model
View Model是指理想的用户可呈现的数据结构,这与data Model形成了对比,data Model指的是自然的数据结构,尽管两者最终往往是相同的,用户表示的需求经常会发生变化,因此view model的中心特性能够对其进行自定义
1.Flexible Hierarchy(灵活的层次结构)
ViewModel基于调试平台团队在3.2中引入了Flexible Hierarchy API。Flexible Hierarchy API有几个显著的特性:
- viewer中数据表示的各个方面(content,label,column)都有提供程序接口
- viewer为viewer中每个元素检索提供程序接口,这允许从多个源填充视图内容。
- 提供程序接口是异步的。
注意:Flexible Hierarchy在Eclipse平台3.4中仍然是一个临时API。这实际上保证了DSF将在将来的版本中打破向后API兼容性。然而,这些API现在已经被DD和CDT等开源项目以及许多商业Eclipse集成广泛使用,因此API的变化可能很小,而且主要与打包有关。
2.The Adapter Problem
Flexible Hierarchy API的第二个特性是使用适配器模式实现的。适配器模式的一个向下侧是,只能有一个为给定元素注册的特定类型的适配器实例。对于灵活的层次结构提供程序,这意味着每个提供者必须为元素出现在的每个视图实现元素表示逻辑,因此添加新视图可能会强制更改大量模块。
注意:适配器问题带来的限制可以通过Flexible Hierarchy API的标准调试模型实现得到最好的观察。如果开发人员希望扩展Java调试器,为Java堆栈框架提供自定义标签提供程序,那么该开发人员就必须扩展Java堆栈框架对象,以便为其注册新的标签提供程序。
3.Model Proxy Problem
实现Flexible Hierarchy API还有第二个主要挑战,它源于Content Provider和Model Proxy对象的不同生命周期。
Content Provider的生命周期由模型管理。viewer分别为每个element请求对Content Provider程序的引用,而Content Provider的实例可以是静态对象,也可以是每个请求的新创建对象,也可以是元素本身。
Model Proxy是通过IModelProxyFactory适配器创建的,它由viewer根据需要实例化和释放。
一般来说,这种安排意味着Content Provider和Model Proxy是使用单独的对象实现的。但是,这两个对象都需要了解视图中元素的布局,才能正常工作。
4.View Model Design
DSF View Model是一个对象集合,它从Data Model中检索信息,并使用该信息填充一个或多个Flexible Hierarchy viewers的内容。
注:DSF View Model可用于表示任何数据模型。DSF数据模型中有一些特性使得使用视图模型更容易表示它,但是这些特性并不是严格必要的。
当处理来自Flexible Hierarchy Viewers的适配器请求时,view model使用四种类型的元素:
VM Adapter:adapter是view model hierarchy的顶级对象,来自viewer的所有内容更新都由vm adapter的单个实例处理。VM adapter根据update对象中包含的表示上下文将这些更新的处理委托给相应的VM提供程序。
VM Provider :提供程序管理单个视图的内容。它根据update对象中元素的树路径,将内容请求委托给相应的VM节点
VM Node:VM节点允许对视图中类似的元素进行分组。此类节点的示例有:threads节点、stack frames节点、variables节点等。VM节点创建VM上下文对象来表示数据模型中的数据元素。
VM Context:VM Context对象用于填充查看器的内容。给定的VM上下文可能包含对数据模型中某个元素的引用(例如,堆栈帧或变量),也可能仅用于表示目的(例如,Expressions视图中的“addnewexpression”条目)。
注意:DSF view model设计最重要的特性是它如何克服适配器问题。VM context用于将getAdapter()请求从查看器重定向到相应的对象。通过这种方式,一个特定的视图可以有许多不同的视图模型表示,而不是只有一个。
5.Layout Customization(布局再定义)
视图模型的主要设计目标是使在查看器中自定义给定数据模型的布局和其他表示方面变得更容易。解释这种定制的最简单方法是使用一个示例。
Timer Data Model
在前面描述的计时器示例中,其数据模型中有三种类型的元素:Timers-计时器的值每秒递增。这些元素独立于任何其他元素。
Triggers-触发器具有由用户指定的常量值。
Alarms-报警表示一个定时器和一个触发器的组合,每个定时器和触发器的组合都有一个单独的报警对象。警报有一个状态,即已触发或未触发。
Timers View Model
在tree hierarchy的视图中显示时,timers或triggers都可以显示为顶级元素。在视图模型中,布局配置由给定VM提供程序中VM节点的配置控制。这个配置可以很容易地更改,就像在定时器示例中所做的那样(参见下图)。
- Event Handling(事件处理)
view model的另一项重要工作是将源于Data model的事件转换为通用事件(模型增量),查看器可以使用这些事件来更新自身。这些模型增量是对查看器中哪些元素发生了变化以及这些元素发生了什么变化的低级描述。对查看器的某些更新甚至需要更改的元素的完整路径,包括路径中每个元素的索引和子元素数。
Event handling in VM Provider
VM Provider是一个在viewmodel中监听data model事件的对象,事件按下面的步骤处理
- VM Provider从Data Model接收vent(出口)
- VM Provider为每个node调用IVMNode.getDeltaFlags() ,来确定是否需要为给定事件生成模型增量
- 如果需要一个delta(增量),VM Provider为每个node调用IVMNode.buildDelta() ,在节点层次结构中构建增量
- 调用所有节点后,将完成的增量发送给查看器,以便查看器可以自我刷新。
Processing events in TimersVMNode
org.eclipse.cdt.examples.dsf.timers.TimersVMNode141: public int getDeltaFlags(Object e) {142: // This node generates delta if the timers have changed, or if the
143: // label has changed.
144: if (e instanceof TimerService.TimerTickDMEvent) {145: return IModelDelta.STATE;
146: } else if (e instanceof TimerService.TimersChangedEvent) {147: return IModelDelta.CONTENT;
148: }
149: return IModelDelta.NO_CHANGE;
150: }152: public void buildDelta(Object e, VMDelta parentDelta, int nodeOffset, RequestMonitor requestMonitor) {153: if (e instanceof TimerService.TimerTickDMEvent) {154: // Add delta indicating that the given timer has changed.
155: parentDelta.addNode( createVMContext(((TimerService.TimerTickDMEvent)e).getDMContext()), IModelDelta.STATE );
156: } else if (e instanceof TimerService.TimersChangedEvent) {157: // The list of timers has changed, which means that the parent
158: // node needs to refresh its contents, which in turn will re-fetch the
159: // elements from this node.
160: parentDelta.setFlags(parentDelta.getFlags() | IModelDelta.CONTENT);
161: }
162: requestMonitor.done();
163: }
Event Coalescing(事件合并)
Data Model生成事件的速度可能快于view model和viewer处理事件的速度,在这种情况下,view model最好跳过处理某些事件来跟上DataModel。但是仍然需要保持viewer的更新,VM Provider有一个api(IVMProvider.canSkipHandlingEvent()),可用于特定用例的事件合并
Property Provider / Label Provider
IElementPropertyProvider接口实际上不是Flexible Hierarchy API的一部分,而是DSF添加的扩展接口。view model实现者可以使用属性提供程序来配置IElementLabelProvider对象, Flexible Hierarchy viewers调用该对象以获取元素表示的详细信息。
org.eclipse.cdt.examples.dsf.timers.TimersVMNode53: private static final PropertyBasedLabelProvider fgLabelProvider;54: static {55: fgLabelProvider = new PropertyBasedLabelProvider();57: LabelColumnInfo idCol = new LabelColumnInfo(58: new LabelAttribute[] { 59: new LabelText(new MessageFormat("Timer #{0}"), 60: new String[] { PROP_TIMER_NUMBER }), 61: new LabelImage(DsfExamplesPlugin.getDefault().getImageRegistry().62: getDescriptor(DsfExamplesPlugin.IMG_TIMER))63: });64: fgLabelProvider.setColumnInfo(TimersViewColumnPresentation.COL_ID, idCol);65: 66: LabelColumnInfo valueCol = ......74: }
org.eclipse.cdt.examples.dsf.timers.TimersVMNode114: @ConfinedToDsfExecutor("getSession#getExecutor")
115: private void updatePropertiesInSessionThread(final IPropertiesUpdate update) {116: // Find the timer context in the element being updated
117: final TimerDMContext dmc = findDmcInPath(
118: update.getViewerInput(), update.getElementPath(), TimerDMContext.class);
119:
120: // If either update or service are not valid, fail the update and exit.
121: if (!checkDmc(dmc, update) ||
122: !checkService(TimerService.class, null, update))
123: {124: return;
125: }
126:
127: TimerService timerService =
128: getServicesTracker().getService(TimerService.class, null);
129: int value = timerService.getTimerValue(dmc);
130:
131: if (value == -1) {132: handleFailedUpdate(update);
133: return;
134: }136: update.setProperty(PROP_TIMER_NUMBER, dmc.getTimerNumber());
137: update.setProperty(PROP_TIMER_VALUE, value);
138: update.done();
139: }
8.Update Policies
在某些用例中,希望冻结给定视图以防止更新,并保留其内容,即使基础数据已更改。这对于灵活的层次结构视图来说是一个特别的挑战,因为它们是延迟加载的,不能依赖它们来保存检索到的数据。
Cache
为了支持缓存特性,view model 提供了一个带有内部缓存的vm provider的实现,缓存按以下步骤:
1.viewer或者其他客户端请求更新(当前缓存支持元素元素内容和属性数据)
2.缓存检查更新中是否有元素的缓存数据
3.如果更新数据在缓存中,跳到第8步
4.如果数据没有在缓存中,缓存创建一个新的更新对象,他是原始viewer 更新的代理
5.VM Proivder将代理更新转发到VM节点来完成
6.VM节点完成更新,从Data Model中抓取数据
7.缓存接收到代理更新完成,从代理中保存数据
8.缓存使用缓存中的数据完成viewer的更新
Last Value
debugger view的一个常见用例是向用户指示自上次viewer更新以来,viewer中的特定值是否已更改。为了支持此功能,缓存可以在缓存重置时保存元素的最后一个已知值,label provider可以检索最后一个已知值和当前值比较,来确定是否应该在试图中高亮该元素
Update Policy
在view中的更新行为被更新策略对象(IVMUpdatePolic)控制,更新策略检查从Data Model中接收的所有事件,并确定应该如何更新缓存来响应事件,下面是更新策略的示例:
Automatic 从数据模型中清除所有事件的缓存。
Manual(手动)-仅在用户请求refesh时清除缓存。
Breakpoint Hit-在断点命中事件和用户请求刷新时清除缓存。
9.Synchronized Event Handling
在某些情况下,调试器中存在需要多个视图以协调方式处理的事件。例如,用户可以请求调试器减慢步进速度,以允许所有可见视图刷新其内容。此功能按以下方式实现:
1.VM适配器侦听数据模型中的事件(通常VM提供程序是事件侦听器)。
2.当VM适配器接收到一个事件时,它会将该事件转发给所有已知的VM提供程序。
3.VM提供程序处理事件,当事件完全处理完毕时,VM提供程序通知VM适配器事件处理完成。
4.当所有VM提供程序完成处理事件时,VM适配器将通知事件观察者。
DSF view Model相关推荐
- MVC3 在提交表单以后 return View(model) 页面不会根据model的内容更新表单
因为这个问题折腾了一下午,最后Google到: 后返回View(model)前 调用一下ModelState.Clear()即可 因为ModelState只有在接收Post的时候被更新 渲染View的 ...
- (四) View/Model 全解(mvc)
转自:http://www.cnblogs.com/zhangziqiu/archive/2009/03/18/Aspnet-MVC-4.html 一.摘要 本文讲解在Action中向View传递Mo ...
- The 4+1 view model
The 4+1 view model 要开发出用户满意的软件并不是件容易的事,软件架构师必须全面把握各种各样的需求.权衡需求之间有可能的矛盾之处,分门别类地将不同需求一一满足.本文从理解需求种类的复杂 ...
- 谈谈对MVC的理解(View+Model+Controller)
1) 什么是MVC? MVC是一种设计思想,根据职责不同将程序中的组件分成以下3个部分. V(View视图):负责与用户交互.将数据展现,或者是接收数据 M(Model模型):负责业务处理.业务模型, ...
- DSF data model
Data Model指的是由DSF服务检索的数据的自然结构,创建一个debugger的用户接口的一个巨大挑战是:目标上可用的数据量远远大于实际提供给用户的数量.因此,调试服务需要将数据分解为具有适当粒 ...
- C# WPF MVVM开发框架Caliburn.Micro View / View Model 命名⑨
01 - 约定 在收到Caliburn Micro中有关视图和ViewModel解析的反馈后,我们添加了新功能,以简化类型解析,同时保持驱动它的健壮的基于正则表达式的名称转换机制.为了更好地了解这些新 ...
- 【django轻量级框架】View与Model交互(模块的交互关系)
文章目录 1 总体结构 2 各个模块的交互关系 3 Model 4 View 5 ORM语句 1 总体结构 Django是MTV结构,即:Model, Template, View Model:定义数 ...
- Model/View模型视图
catalog version model 函数 遍历 视图 当前项.选中项 Select SelectionMode SelectionBahavior QItemSelectionModel QT ...
- [转] asp.net core Introducing View Components
本文转自:http://www.c-sharpcorner.com/uploadfile/8c19e8/asp-net-5-getting-started-with-asp-net-mvc-6/ In ...
最新文章
- 系统科学丨钱学森:我对系统学认识的历程
- pyqt5 QtDesigner文件打开位置
- mysql中date转sqlserver_MySQL和SQLServer互转
- 商汤招股书详解:40名教授250+博士3593位工程师,AI收入亚洲第一,一年15亿研发工资支出...
- Spring源码解析-applicationContext.xml加载和bean的注册
- String字符串相等判断
- 关于VS2010帮助文档的使用和VC6.0在Win7 64位下的使用
- 全国计算机等级考试题库二级C操作题100套(第85套)
- EOJ Monthly 2020.9 Sponsored by TuSimple E. 加密的情书
- Hibernate @OneToMany等注解设置查询过滤条件等
- android 源码中的单例,Android源码中的一种单例实现
- redis指定配置文件启动_redis基础知识整理-安装
- MySql的用户管理权限
- 【bzoj2219-数论之神】求解x^a==b(%n)-crt推论-原根-指标-BSGS
- Java 实现中文汉字转拼音
- 游戏的本质【转自网易】
- 精美中文简历LaTex模板集锦
- PHP png合并到jpg,合并jpg的png并保持与php的透明度
- Zabbix 5.0.12 异常:Zabbix unreachable poller processes more than 75% busy:
- java mp3 信息_android,java获取MP3文件信息(作者,专辑等)