MVP
面向协议编程
presenter 中间调度者(声明协议,来实现接口) view model之间的调度
view: 自定义view代替原有view
model: 交给preset调度,并赋值。
下面可扩展(项目大的时候)
context: 中间者,让VC持有,并且这个是context是view model vc三者间调度
adapter: view的一个适配器可以兼容 各种视图xr x等
自己写个view,并把VC在load里这个view处理适配。
当工程庞大的时候,present 和 view打交道多了就会很错乱。
这时在这之间建立一个中间者context,由他来提供view和present
而且这个context是vc的一个属性,这样随时随地都可以调用
那么这里会出现循环引用问题
self - context -present -self
所以这里把vc弱引用,其它部份弱引用会随时随地没有,是一个风险,那弱引用vc的话就是vc没有了。
self.rootContext = [[Context alloc] init]; //rootContext强引用strong,而这里是vc持有的,会随着vc释放而释放
self.contenxt = self.rootContext;//context弱引用assgin,这里就保持住了rootcontext
self -weak- context -present -self
一个weak指针指向一个长期存在的对象,这个长期存在的对象不释放那么weak指向的对象不会释放,也就是两对象生命 周期绑定了,此时weak打破了闭环。
不想每次写
view = 自己的view
就在基类的viewdidload里写入
self.context.view.frame = self.view.bould
self.context.view = self.view
视图配置好了接下来我们需
加载数据就交给present
view视图构建 -- 就交给delegate
可以定义一个宏
#define GT(instace,protocol,message)[(id<protocol>)(instance)message]
//加载数据
GT(self.context.presenter,KCHomePresenterDelegate,loadData:self.homeAdapter];
示例:
先在VC中buildView
GT(self.context.view,KCHomePresenterDelegate,buildHomeView:self.homeAdapter];
然后在homeView重写buildHomeView中,写入加载数据
GT(self.context.presenter,KCHomePresenterDelegate,loadData:adapter];
然后在homePrsenter重写loadData中,写入加载UI视图
GT(self.context.view,KCHomePresenterDelegate,reloadUIWithData);
问题一:presnt的代码增大了怎么办
当我们这样写下去的最多的代码量会集中在presnt里,所以我们要解决这个问题我们可以按业务的形式去划分变成一个分类(present+A)
问题二:子视图要传值到父视图上面有哪些方法
可以kvo\通知\block都可以,不过这些没有context直接,可以定义协议后直接让context通知某个协议实现某个方法就好了。最简单。但是会有一个问题子视图如何拿得到父视图的context呢。
通过响应裢方式去拿。可以定义一个NSObject+GT写入方法-(Context*)context{};
while{
view.superview
setContext(super.context)
}
问题三:数据格式的规范
比如APP中要传一些结构性的数据,但是每个人的想法不一样,取的结构和名字都不一样。但是做的事情又是一样的。这时候就要考虑写一个工具类或者宏把这些事情统一抽象出来。
比如通知,可以写一个工具类或宏,先把要求的数据传差进来,然后拼接成一个dict
info[@"data"] = data
info[@"table"] = tableName
info[@"event"] = rowEvent
然后发回主线程
dispatch_async(dispatch_get_main_queue(),^{
[NSNotificationCenter defaultCenter] postnotificationName:tablename object:nil userInfo:info];
});