Android图片海报制作-MVP的使用

项目地址:https://github.com/coolstar1204/MakePoster

MVP的学习使用

  • 什么是MVP
  • 我的项目哪里是MVP
  • MVP的优点
  • MVP的不足

什么是MVP

MVP 是从经典的模式MVC演变而来,它们的基本思想有相通的地方:Controller/Presenter负责逻辑的处理,Model提供数据,View负责显示。作为一种新的模式,MVP与MVC有着一个重大的区别:在MVP中View并不直接使用Model,它们之间的通信是通过Presenter (MVC中的Controller)来进行的,所有的交互都发生在Presenter内部,而在MVC中View会直接从Model中读取数据而不是通过 Controller。

上面这段是从百科引用而来的,我的个人理解最深的就是,Model不与View交互是其与MVC的最大区别和特点。具体到我的开发中,我为了学习这个模式,在第一个选择图片界面中,我让请求相册数据库时,使用Model层对象进行异步的数据库访问及图片对象列表的创建,然后通过EventBus通知时,只通知到Presenter对象上,而不是直接通知到Activity或Fragment上,这样方便界面调整。

public interface IMain {
    void asyncLoadPictureList(Context context);
}
public void asyncLoadPictureList(final Context context) {
        ThreadBuilder.getInstance().runThread(new Runnable() {
            @Override
            public void run() {
                String[] projection = new String[] { MediaStore.Images.Media._ID,
                        MediaStore.Images.Media.BUCKET_ID, 
                        MediaStore.Images.Media.BUCKET_DISPLAY_NAME, 
                        MediaStore.Images.Media.DISPLAY_NAME, // 图片文件名
                        MediaStore.Images.Media.DATA // 图片绝对路径
                };
                Uri uri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
                try {

                    Cursor cursor = context.getContentResolver().query(uri,projection,null,null,null);
                    if(cursor!=null){
                        List<PictureInfo> list = new ArrayList<PictureInfo>();
                        while (cursor.moveToNext()){
                            PictureInfo item = new PictureInfo();
                            item.fileName = cursor.getString(4);
                            item.picName = cursor.getString(3);
                            item.dirName = cursor.getString(2);
                            if(BitmapUtils.isBigBitmap(item.fileName)){
                                list.add(item);
                            }
                        }
                        EventBus.getDefault().post(list);//使用EventBus进行回调通知
                    }else{
                        EventBus.getDefault().post(new AsyncErrorInfo(2,"parse error"));//使用EventBus进行回调通知
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                    EventBus.getDefault().post(new AsyncErrorInfo(1,"db query error"));//使用EventBus进行回调通知
                }
            }
        });
    }

这里直接使用EventBus进行异步回调更新,只不过在MVP的模式下,更新的地方不在Activity上,而是在
Presenter上。代码如下:

 public MainPresenter(IMainView mainView) {
        this.mainView = mainView;
        this.mainMod = new MainMod();
        EventBus.getDefault().register(this);
    }

    public void releasePresenter(){
        EventBus.getDefault().unregister(this);
    }
    @Subscribe(threadMode = ThreadMode.MainThread)
    public void onEventReceiveList(List<PictureInfo> list){
        mainView.setPictureList(list);
        mainView.stopLoading();
        mainView.showPictureList();
    }

在上面的代码中,mainView是一个接口变量,其保存的就是MVP中的View实现类,在本程序中,我是使用MainActivity实现了这个接口,来完成最后数据的加载显示的。这可以很方便以后界面从Activity转为Fragment等变更。

public interface IMainView {
    public void startLoading();
    public void stopLoading();
    public void setPictureList(List<PictureInfo> list);
    public void showPictureList();
    public void showErrorInfo();
}

最后总结一下本例中主界面的MVP就是:
Activity或Fragment中创建一个Presenter的对象,同时把自己以接口实现类的方式,传入Presenter中成为其成员变量,方便Activity与Presenter的交互调用,在Presenter中,创建出对应的Model对象进行模型数据的管理,同时Presenter实现Model要求的回调,方便Model把更新返回给Presenter,Presenter在接到Model的更新数据回调后,就可以加上自己的业务规则或界面切换逻辑后,调用IMainView中的接口把内容显示到Activity或Fragment中,如此一来,Model就可以不用知道View长什么样了。View也不需要知道数据是怎么来的。

Activity/Fragment —->Presenter———>Model——–>Presenter——->Activity/Fragment

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值