关于Retrofit+RxJava+MVP的终章
转载请注意:http://blog.youkuaiyun.com/wjzj000/article/details/54898175
本菜开源的一个自己写的Demo,希望能给Androider们有所帮助,水平有限,见谅见谅..
https://github.com/zhiaixinyang/MyFirstApp
https://github.com/zhiaixinyang/PersonalCollect
写在前面:
时隔很久才想起来写博客,因此这个系列的收尾迟迟没有进行。这也不怪我:
过年,总要有个过年的样子。写代码肯定写不出来红包,也整不明白三六九万吃碰胡。
尤其是最近特朗普上台,美国宣布退出tpp。人民币汇率摇摆不定,中日韩关系出现了微妙的变换。
每一个热点都让我寝室难安。说白了就是咸吃萝卜淡操心,我就是不想写学习!
饭还是要一口口吃,坑还是要一个个踩一个个填。今天就把这个坑给填上…
MVP存在的意义
关于MVP是什么,应该无需多讲…为什么?因为能看到这篇博客的。我估计对MVP肯定有了解,不然肯定不会在搜索引擎中,点开了我这么一篇排名如此靠后的文章。
但是为什么要使用MVP,我们必须要说道说道。首先,MVP不是某项特定的技术,更不是某个API,因此它就是看不见摸不着的东西。它的存在是为了指导并规范的解决我们日常开发中遇到的特定问题:
打个最简单的比方,当我们自己写的某个项目的结构比较复杂时,尤其是Activity中的业务非常复杂的时候。因为我们知道,在传统的MVC模式下,随着开发的进行Activity似乎即承担了C的工作,也承包V。因此Activity会随着我们代码的深入越来越复杂。其带来的结构就是Activity越来越长,越来越难以维护。说白点,如果长的一个类谁愿意从头到尾给你看一遍,看都不愿意看何谈维护?
我想这个种情况大家肯定遇到过:在出现问题时,有时我们宁愿重新写一个项目也不愿在之前的项目上去改动。而MVP的出现就是改变这种情况!
MVP的使用
关于MVP我感觉最多的是意为,因为我们不感觉到Activity冗长时,的确没有什么压力。但是,当我们感受到Activity肥胖臃肿的身段之时,便是我们迎接MVP纤细婀娜之日。
不扯淡,直接上用法,看代码:
这是一种设计模式,因此势必会有规范。不过这里不讨论什么才是规范…因为自己用着爽的才叫王道!
Activity的改造
public abstract class BaseActivity<T extends BasePresenter> extends AppCompatActivity implements BaseView{
protected T presenter;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//省略部分代码...
if (presenter!=null) {
presenter.attachView(this);
}
//省略...
}
//省略...
}
BasePresenter以及BaseView
public interface BasePresenter<T extends BaseView>{
void attachView(T view);
void detachView();
}
public interface BaseView {
void showError(String msg);
}
这里可以看到,这是俩个普普通通的接口。这里的BaseView最为普通,只不过是根据自己的需求写了一个抽象方法。但是通过Presenter的泛型让它方便的参与到了MVP中。(这里必须要提一点。我自己的学习过程中,遇到了俩种写法,一种是View接口和Presenter严格分离,另一种就是上述的表示方式。个人认为第一种比较好理解,因为彼此都是独立的。但是接口写起来太多了….至于用什么样的方式仁者见仁智者见智吧。看到这一步我相信各位看官也有自己的理解。)
RxPresenter
这又是个啥呢?看开头,我们也能猜出一二:Rx-RxJava。没有和RxJava有着千丝万缕的关系。
它也不是必要的…就是简单抽象出来一个方法,用于管理每个观察者。
public class RxPresenter<T extends BaseView> implements BasePresenter<T> {
protected T mView;
protected CompositeSubscription mCompositeSubscription;
protected void unSubscribe() {
if (mCompositeSubscription != null) {
mCompositeSubscription.unsubscribe();
}
}
protected void addSubscrebe(Subscription subscription) {
if (mCompositeSubscription == null) {
mCompositeSubscription = new CompositeSubscription();
}
mCompositeSubscription.add(subscription);
}
@Override
public void attachView(T view) {
this.mView = view;
}
@Override
public void detachView() {
this.mView = null;
unSubscribe();
}
}
具体的使用:
首先先根据,我们的正常需要抽象出我们的View接口和Presenter接口,为了方便我们写到同一个接口中:
public interface JokContract {
interface View extends BaseView {
//根据自己的需求进行抽象,在特定的类中进行重写
void initJokData(MainJokBean data);
void showLoading();
void showLoaded();
}
interface Presenter extends BasePresenter<View> {
//根据自己的需求进行抽象,在特定的类中进行重写
void getJokData();
}
}
Presenter接口的具体实现:!!!
这里是核心,用于分离我们的Activity中冗长的逻辑。并且与View层进行沟通的桥梁。
public class JokPresenter extends RxPresenter<JokContract.View> implements JokContract.Presenter{
private JokContract.View view;
private RetrofitHelper retrofitHelper;
public JokPresenter(JokContract.View view) {
//这里我们会拿到View接口的引用。而View的实现就是在我们的Activity之上。
//为什么可以起到分离的作用:其实很简单,通过回调。我们在Presenter中做了原本Activity中做的事情,
//这样我们就可以在Presenter中完成业务,通过View接口引用回调结果到Activity上。
this.view = view;
//对Retrofit的简单封装
retrofitHelper=new RetrofitHelper();
}
@Override
public void getJokData() {
view.showLoading();
Subscription subscription=retrofitHelper.getMainJokData()
.compose(RxUtil.<MainJokBean>rxSchedulerHelper())
.subscribe(new Action1<MainJokBean>() {
@Override
public void call(MainJokBean mainJokBean) {
view.showLoaded();
view.initJokData(mainJokBean);
}
}, new Action1<Throwable>() {
@Override
public void call(Throwable throwable) {
view.showLoaded();
view.showError(throwable.getMessage());
}
});
addSubscrebe(subscription);
}
}
关于Retrofit的应用:可以参照本菜的另一边博客:
http://blog.youkuaiyun.com/wjzj000/article/details/54287823
Activity的实现:
public class JokActivityextends BaseActivity<JokPresenter> implements JokContract.View{
//省略和中心无关的代码
@Override
public void showError(String msg) {
//如果网络加载错误,这里打印这里的msg,我们不需要管内容是什么,因为Presenter处理了。
}
@Override
public void showLoading() {
srfBookKindList.setRefreshing(true);
}
@Override
public void showLoaded() {
srfBookKindList.setRefreshing(false);
}
//这里拿到我们需要的Data,自行处理即可
@Override
public void initJokData(MainJokBean data) {
jokData=data.getResult().getData();
jokAdapter.addData(jokData);
}
}
梳理
MVP中的M其实没什么变化,可以简单理解还是我们的Bean…
这里的P,Presenter是核心,这里我们进行正常的业务逻辑。简单点说就是封装了我们原本Activity中的业务。但是犹豫View层的存在,让这个流程高大威猛了起来。
View层在这里就是被Activity重写,然后被Presenter持有,再特定的时机下进行回调。
简单的比方:Activity中有个RecyclerView,我们需要一个数据的List。这时我们通过Presenter完成耗时的数据请求(Retrofit+RxJava),请求到了List之后,通过持有的View引用,回调特定的方法把List传个Activity。
这样我们的Activity就变得异常的清爽。
我个人感觉比较好理解,真心好用。使用之后代码逻辑异常的清晰。
写在最后
关于MVP,我个人见解真心没有什么好说的。当我们当了特定的场合下,我们真的会发现它真的是太好用了。
最后希望各位看官可以star我的GitHub,三叩九拜,满地打滚求star:
https://github.com/zhiaixinyang/PersonalCollect
https://github.com/zhiaixinyang/MyFirstApp