MVP模式

一.使用背景


 

1.逻辑业务被塞到View中(Activity),使得View变的混乱

2.MVP可以分离显示层和逻辑层,他们之间通过接口进行通信,降低耦合

3.数据层(可能是本地数据库检索数据,远程服务器,或者被替换)

4.UI层(随着产品迭代,肯定会重新设计),如果View中混合着逻辑,那么UI变化导致我们修改新的View控件,就要到原来的View中抽离具体的业务逻辑


理想状态:同一份逻辑代码搭配不同的显示界面,因为他们之间并不依赖于具体,而是依赖抽象

 

对于一个可扩展,稳定的应用来说,我们需要定义分离各个层,主要UI业务逻辑层(mvp中放到P)数据层(M)


 

二.MVP模式的三个角色

1.Presenter---交互中间人

Presenter主要作为沟通ViewModel的桥梁,他从Model层获取数据后(4返回给View层(1

使得ViewModel之间没有耦合,也将业务逻辑从View角色上抽离出来

 

2.View----用户界面

View通常指的是Activity,Fragment或者某个View控件,它含有一个一个Presenter成员变量。通常View需要实现一个逻辑接口,将View上的操作转给Presenter进行实现(2,最后Presenter调用View逻辑接口将结果返回给View元素

 

3.Model----数据存储

对于一个结构化的App来说,Model角色主要是提供数据的存取功能,Presenter需要通过Model层存储,获取数据(3,4,简单的说,Model就是封装了数据库DAO或者网络获取数据的角色,或者两者方式都有的集合



三.MVP简单实现

//接口M

public interface ArticleModel {
    public void saveArticles(List<Article> articles);
    public void loadArticlesFromCache(DataListener<List<Article>> listener);

}
//具体的M

public class ArticleModeImple implements ArticleModel {
    List<Article> mCacheArticles = new LinkedList<>();

    @Override
    public void saveArticles(List<Article> articles) {
        mCacheArticles.addAll(articles);
    }

    @Override
    public void loadArticlesFromCache(DataListener<List<Article>> listener) {
        listener.onComplete(mCacheArticles);
    }
}

//链接V跟P的接口

public interface  ArticleViewInterface {
    public void  showArticles(List<Article> articles);//展示数据
    public void showLoading();
    public void hideLoading();
}

//具体的V

public class MainActivity extends Activity implements ArticleViewInterface {
    RecyclerView mRecycleView;
    ProgressBar progressBar;
    List<Article> mArticles = new LinkedList<Article>();
    ArticleAdapter mAdapter;
    ArticlePresenter mPresenter;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        //初始化控件
        initViews();
        //初始化请求队列
        //....
        //构建ArticlePresenter,与ArticleActity建立关联
        mPresenter = new ArticlePresenter(this);
        //请求文章数据
        mPresenter.fetchArticles();
    }

    private void initViews() {
        //省略代码
        //....
    }

    @Override
    public void showArticles(List<Article> result) {
        mArticles.addAll(result);//更新数据源
        mAdapter.notifyDataSetChanged();//更新UI
    }

    @Override
    public void showLoading() {

    }

    @Override
    public void hideLoading() {

    }
}




//具体的P(一般会有一个接口P)

/**
 *Presenter作为View和Model的中间人
 * */
public class ArticlePresenter {
    //ArticleView接口,代表了View接口角色
    ArticleViewInterface mArticleView;
    //文章数据的Model,也就是Model角色
    ArticleModel mArticleModel = new ArticleModeImple();
    //从网络上获取文章的API
    ArticleAPI mAriticleApi = new ArticleAPIImpl();

    public ArticlePresenter(ArticleViewInterface mArticleView) {
        this.mArticleView = mArticleView;
    }

    //获取文章,也就是我们的业务逻辑
    public void fetchArticles(){
        mArticleView.showLoading();
        mAriticleApi.fetchArticles(new DataListener<List<Article>>(){
            @Override
            public void onComplete(List<Article> result) {
                //数据加载完,调用View的showArticles函数将数据传递给View显示
                mArticleView.showArticles(result);
                mArticleView.hideLoading();
                //存储到数据库
                mArticleModel.saveArticles(result);
            }
        });
    }

    public void loadArticlesFromDB(){
        mArticleModel.loadArticlesFromCache(new DataListener<List<Article>>() {
            @Override
            public void onComplete(List<Article> result) {
                //从数据库加载
                mArticleView.showArticles(result);
            }
        });
    }

}


通过这个用例可以看到,Presenter对于View是完全解耦的,

1.Presenter依赖的是ArticleViewInterface抽象,而不是具体的MainActivity这个类,因此当UI界面变化,只要新UI实现AriticleViewInterface以及相关的逻辑就可以跟Presenter用起来

2.Presenter将业务逻辑从MainActivity抽离出来,让MainActivity变得非常轻量级,MainActivity只要做一些View的初始化

3.MVP中的ViewModel不能直接通信,他们交互通过PresenterArticlePresenter中持有

ArticleViewInterface(抽象),还持有ArticleModel(抽象),这两个的具体实现可以轻易被替换

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值