初识Android(安卓)MVP模式
接触Android MVP模式在好早之前,一直也没有在项目中真正的实用。刚好有一个机会需要自己去做项目,然后就用上MVP。MVP用起来还是很方便,整个项目结构非常清晰,相比于传统的MVC模式,MVP清晰分工,有太多有点了。这些其实是需要在实用以后才能体会到的,尤其是当项目很复杂的时候。
一、MVP介绍
在MVP模式里通常包含4个要素:
- View:负责绘制UI元素、与用户进行交互(在Android中体现为Activity);
- View interface:需要View实现的接口,View通过View interface与Presenter进行交互,降低耦合,方便进行单元测试;
- Model:负责存储、检索、操纵数据(有时也实现一个Model interface用来降低耦合);
- Presenter:作为View与Model交互的中间纽带,处理与用户交互的负责逻辑。
二、为什么使用MVP模式
在Android开发中,Activity并不是一个标准的MVC模式中的Controller,它 的首要职责是加载应用的布局和初始化用户界面,并接受并处理来自用户的操作请求,进而作出响应。随着界面及其逻辑的复杂度不断提升,Activity类的 职责不断增加,以致变得庞大臃肿。当我们将其中复杂的逻辑处理移至另外的一个类(Presneter)中时,Activity其实就是MVP模式中 View,它负责UI元素的初始化,建立UI元素与Presenter的关联(Listener之类),同时自己也会处理一些简单的逻辑(复杂的逻辑交由 Presenter处理).
另外,回想一下你在开发Android应用时是如何对代码逻辑进行单元测试的?是否每次都要将应用部署到Android模拟器或真机上,然后通过模拟用 户操作进行测试?然而由于Android平台的特性,每次部署都耗费了大量的时间,这直接导致开发效率的降低。而在MVP模式中,处理复杂逻辑的 Presenter是通过interface与View(Activity)进行交互的,这说明了什么?说明我们可以通过自定义类实现这个 interface来模拟Activity的行为对Presenter进行单元测试,省去了大量的部署及测试的时间。
三、MVP与MVC的异同
MVC模式与MVP模式都作为用来分离UI层与业务层的一种开发模式被应用了很多年。在我们选择一种开发模式时,首先需要了解一下这种模式的利弊:
无论MVC或是MVP模式都不可避免地存在一个弊端:
- 额外的代码复杂度及学习成本。(这就导致了这两种开发模式也许并不是很小型应用。)
但比起他们的优点,这点弊端基本可以忽略了:
- 降低耦合度
- 模块职责划分明显
- 利于测试驱动开发
- 代码复用
- 隐藏数据
- 代码灵活性
四、案例
这里用一个案例来详细介绍MVP的实用,当然这里做一个基类封装方便使用。
IPresenterView接口
/** * @author ttarfall * @date 2016-09-06 10:08 */public interface IPresenterView {}
(当然这里用了一个空的接口,其实是可以在里边加一些通用的方法)
BasePresenter基类
/** * 基础basePresenter,用于IView接口的传入,attach,dettach用于绑定与解绑IView,当Activity被销毁的时候,及时解绑IView防止内存溢出 * @author ttarfall * @date 2016-09-06 10:02 */public abstract class BasePresenter<T extends IPresenterView> { protected T paresenterView; public void attach(T mView) { this.paresenterView = mView; } public void dettach() { paresenterView = null; }}
BaseMVPActivity基类
import android.os.Bundle;/** * @author ttarfall * @date 2016-09-06 09:36 */public abstract class BaseMVPActivity<V extends IPresenterView, P extends BasePresenter<V>> extends BaseActivity { protected P presenter; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); presenter = initPresenter(); try { presenter.attach((V) this); } catch (Exception e){ new ClassCastException(this.toString() +"实现IPresenterView或者IPresenterView子类接口"); } } @Override protected void onDestroy() { presenter.dettach(); super.onDestroy(); } //实例化Presenter public abstract P initPresenter();}
BaseMVPFragment基类
import android.os.Bundle;/** * @author ttarfall * @date 2016-09-08 13:45 */public abstract class BaseMVPFragment<V extends IPresenterView, P extends BasePresenter<V>> extends BaseFragment { protected P presenter; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); presenter = initPresenter(); try { presenter.attach((V) this); } catch (Exception e) { new ClassCastException(this.toString() + "实现IPresenterView或者IPresenterView子类接口"); } } @Override public void onDestroy() { presenter.dettach(); super.onDestroy(); } //实例化Presenter public abstract P initPresenter();}
上边是MVP做了一个简单的封装,接下来就是使用了。如图
IMainView源码,当然这里的ILoaddingView 接口也是继承IPresenterView ,只不过增加了一个setLoading方法。
MainPresenter部分源码截图,可以看到我这里其实有3个mode,当然每一个mode都有自己实现的方法。
mode存主要是获取数据的和保存数据使用。这里展示UserInfoMode的使用,IUserInfoMode展示提供的方法。
最后就是IMainView需要在Activity或者Fragment中实现。然后就是Presenter通过IPresenter与Activity或者Fragment互动。
至此一整套MVP的解释到案例就结束了,如果还有不太懂得童鞋可以留言。
更多相关文章
- Android(安卓)MVP模式 初步理解
- Android调用天气接口(和风天气)
- 动手撸一个Android路由框架LuRouter
- Android(安卓)MVC 架构详解
- 简述MVC框架模式以及在你(Android)项目中的应用
- API接口JWT方式的Token认证(下),客户端(Android)的实现
- [程序猿感悟] Android平台开发中的重构三步走
- Android透明状态栏与沉浸模式全解
- 刷中兴N760经历,最靠谱的方式刷Android有感