MVVM 与 ReactiveCocoa 的运用(2)

416 查看

  • 绑定,绑定,绑定(重要的实情说三遍)

RACCommand能实时地更新search按钮的状态,但是时候来处理activity indicator的可见状态了.
RACCommand拥有一个执行的属性,它是用来表示命令开始和结束执行时反应真假事件的信号量.你可以通过这个信号量来反映程序中当前命令执行的状态.
在RWTFlickrSearchViewController.m的bindViewModel的尾部添加:

以上代码用来将UIApplication中的networkActivityIndicatorVisible属性和命令执行信号绑定.用来保证当命令执行时,小的网络激活状态标志在status bar里显示.
下一步,添加:

当指令执行后,加载标志将会被隐藏;这和你刚刚绑定的属性相反.
ReactiveCocoa已经为我们提供了不执行的相反的信号.最后,添加如下代码:

上面的代码用来保证当命令执行时键盘会隐藏.executionSignals属性用来在命令执行时实时地发出信号.
这是个signals中的一个signal属性(前面教程里有介绍).当一个新的命令执行的时候就会被创建和执行,隐藏键盘.
运行程序,来验证以上代码的执行.

  • Model呢?

到现在为止,你已经定义了一个View(RWTFlickrSearchViewController)和ViewModel(RWTFlickrSearchViewModel),但是,怎么木有Model呢?
答案很简单:就是还没有啊!
当前app用户点击搜索按钮后就会执行命令,但却没有实现什么.
我们需要实现的是利用当前输入的搜索文本通过ViewModel在Flickr进行搜索,继而返回相匹配的图片列表.
你可以将此逻辑直接放在ViewModel里,但相信我,你会后悔的!如果是个view controller,我到时强烈你这么做.
View Model拥有UI状态的属性,而且还能够执行命令(经常为UI上的动作方法).通过用户的交互来管理改变UI状态.
然而,并不表示这些交互实际的业务逻辑应该在View Model里面.而这应该是Model的工作.
下一步,将会给应用增加Model层.
在Model group里添加一个名为RWTFlickrSearch的新协议并提供了如下的方法:

这个协议定义了Model层的初始方法,用来将负责搜索Flickr的任务从ViewModel里移出.
接下来,在同一group里创建一个名为RWTFlickrSearchImpl的NSObject的子类.并使其遵从刚才的协议:

在RWTFlickrSearchImpl.m里添加以下代码:

是不是觉得似曾相识?如果是的,那是因为这个同一’虚拟’的实现曾经位于ViewModel里.
下一步是要在ViewModel里使用Model层.在ViewModel group里添加一个名为RWTViewModelServices的新协议:

这个协议定义了ViewModel获得对RWTFlickrSearch协议引用的方法.
在RWTFlickrSearchViewModel.h导入这个新协议: