浅谈MVP模式(开发Android聊天机器人)

一、首先介绍什么是MVP

    MVP是模型(Model)、视图(View)、主持人(Presenter)的缩写,分别代表三个模块。
    模型(Model):负责处理数据的加载或者存储,例如网络或本地数据库数据的获取等等;
    视图(View):负责界面数据的展示,与用户进行交流;

二、MVP的模块之间交互

    如下图所示:View和Model不会直接去交互,而是通过Presenter作为View和Model的桥梁,其中Presenter中同时持有View层以及Model层的Interface的引用,而View层持有Presenter层的Interface引用。当View层某个界面需要展示某些数据时,首先会调用Presenter层的接口,然后Presenter层会调用Model层进行数据请求操作,当Model层的数据请求完成的时候就会调用Presenter层的回调方法通知Presenter层数据加载完成,最后由Presenter层再调用View层的接口将加载的数据显示在界面上展示给用户。这就是MVP模式的核心过程。

三、MVP的优缺点:

    优点:1、View和Model之间的耦合度降低,使其更关注与自身的业务逻辑,结构清晰维护方便。
        2、便于单元测试。
        3、代码复用度提高。
        4、代码框架更适用于快速的迭代开发
    缺点:主要为每一个View都有Presenter,类比较多书写起来麻烦

四、MVP在Android开发中的使用:

1、我的MVPdemo的源码目录结构如下:

bean包下为:数据类的定义。
Model,Presenter包下各有两个包,其中的Impl为对其相应包的业务逻辑的操作。

运行效果如下:

源码下载:(http://download.csdn.net/detail/qq_30000411/9687960)
该demo为MVP模式下开发的聊天机器人demo。

2、各个包下的代码如下:

(1)、bean 包下的JiQiRen类为数据类的定义

package com.xyliwp.mvpdemo.bean;

/**
 * Created by lwp940118 on 2016/11/20.
 */
public class JiQiRen {
    private int tag;
    private String message;

    public int getTag() {
        return tag;
    }

    public void setTag(int tag) {
        this.tag = tag;
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }
}

(2)、Model层的两个子包下的文件

JiQiRenModelModel层接口的定义

package com.xyliwp.mvpdemo.Model.Model;

import com.xyliwp.mvpdemo.Model.ModelImpl.JiQiRenModelImpl;

/**
 * model层的接口
 * Created by lwp940118 on 2016/11/20.
 */
public interface JiQiRenModel {
    /**
     * 加载数据并且的接口
     * @param infor
     * @param listener
     */
    void loadMessage(String infor, JiQiRenModelImpl.OnLoadMessageListListener listener);
}

JiQiRenModelImplModel层的业务逻辑

package com.xyliwp.mvpdemo.Model.ModelImpl;

import android.os.Handler;

import com.xyliwp.mvpdemo.Model.Model.JiQiRenModel;
import com.xyliwp.mvpdemo.bean.JiQiRen;

import org.json.JSONException;
import org.json.JSONObject;

import java.io.IOException;

import okhttp3.FormBody;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;

/**
 * Created by lwp940118 on 2016/11/20.
 */
public class JiQiRenModelImpl implements JiQiRenModel{
    public static final String api = "http://www.tuling123.com/openapi/api";
    public static final String key = "959060c92fb845acb8d9073934355364";
    public static final String url = api+"?key="+key+"&info=";

    private Handler handler = null;

    @Override
    public void loadMessage(final String infor, final OnLoadMessageListListener listener) {
        handler = new Handler(){
            @Override
            public void handleMessage(android.os.Message msg) {
                JiQiRen message = (JiQiRen) msg.obj;
                if (message.getTag() == 1){
                    listener.onSuccess(message);
                }else{
                    listener.onFailure(message);
                }
            }
        };
        new Thread(new Runnable() {
            @Override
            public void run() {

                OkHttpClient okHttpClient = new OkHttpClient();
                FormBody.Builder builder = new FormBody.Builder();
                builder.add("json","true");
                RequestBody body = builder.build();
                Request request = new Request.Builder()
                        .url(url+infor)
                        .post(body)
                        .build();
                try {
                    Response response = okHttpClient.newCall(request).execute();
                    if (response.isSuccessful()){
                        JSONObject jsonObject = new JSONObject(response.body().string());
                        JiQiRen message = new JiQiRen();
                        message.setMessage(jsonObject.toString());
                        message.setTag(1);
                        android.os.Message message1 = new android.os.Message();
                        message1.obj = message;
                        handler.sendMessage(message1);
                    }else {
                        JiQiRen message = new JiQiRen();
                        message.setMessage("小凤异常,小凤异常,小凤异常,重要的事情说三边");
                        message.setTag(0);
                        android.os.Message message1 = new android.os.Message();
                        message1.obj = message;
                        handler.sendMessage(message1);
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }catch (JSONException e){
                    e.printStackTrace();
                }
            }
        }).start();
    }

    public interface OnLoadMessageListListener{
        void onSuccess(JiQiRen message);
        void onFailure(JiQiRen message);
    }

}

(3)、Presenter层两个子包下的文件
JiQiRenPresenter为Presenter层的接口

这里写代package com.xyliwp.mvpdemo.Presenter.Presenter;

/**
 * Created by lwp940118 on 2016/11/20.
 */
public interface JiQiRenPresenter {
    /**
     * 添加消息的message
     * @param message
     */
    void loadMessage(String message);
}

JiQiRenPresenterImpl为Presenter层的Model层调用以及View层的数据展示。

package com.xyliwp.mvpdemo.Presenter.PresenterImpl;

import com.xyliwp.mvpdemo.Model.Model.JiQiRenModel;
import com.xyliwp.mvpdemo.Model.ModelImpl.JiQiRenModelImpl;
import com.xyliwp.mvpdemo.Presenter.Presenter.JiQiRenPresenter;
import com.xyliwp.mvpdemo.View.JiQiRenView;
import com.xyliwp.mvpdemo.bean.JiQiRen;

/**
 * Created by lwp940118 on 2016/11/20.
 */
public class JiQiRenPresenterImpl implements JiQiRenPresenter,JiQiRenModelImpl.OnLoadMessageListListener{
    private JiQiRenView jiQiRenView;

    private JiQiRenModel messageModel;

    public JiQiRenPresenterImpl(JiQiRenView jiQiRenView){
        this.jiQiRenView = jiQiRenView;
        this.messageModel = new JiQiRenModelImpl();
    }

    @Override
    public void onSuccess(JiQiRen message) {
        jiQiRenView.addMessage(message);
    }

    @Override
    public void loadMessage(String message) {
        messageModel.loadMessage(message,this);
    }

    @Override
    public void onFailure(JiQiRen message) {
        jiQiRenView.showMessageFailure(message);
    }

}

(4)、View层的接口文件

package com.xyliwp.mvpdemo.View;

import com.xyliwp.mvpdemo.bean.JiQiRen;

/**
 * 机器人的view
 * Created by lwp940118 on 2016/11/20.
 */
public interface JiQiRenView {

    /**
     * 信息添加成功 展示给接界面
     * @param jiQiRen
     */
    void addMessage(JiQiRen jiQiRen);

    /**
     * 添加失败 将失败展示给界面
     * @param jiQiRen
     */
    void showMessageFailure(JiQiRen jiQiRen);

}

(5)、MVP模式在Android中Activity的调用,向Presenter发送数据请求,和Presenter返回数据显示。

package com.xyliwp.mvpdemo;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;

import com.xyliwp.mvpdemo.Presenter.Presenter.JiQiRenPresenter;
import com.xyliwp.mvpdemo.Presenter.PresenterImpl.JiQiRenPresenterImpl;
import com.xyliwp.mvpdemo.View.JiQiRenView;
import com.xyliwp.mvpdemo.bean.JiQiRen;

public class MainActivity extends AppCompatActivity implements JiQiRenView{

    private TextView textView;
    private EditText editText;
    private Button button;
    private JiQiRenPresenter messagePresenter;


    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        messagePresenter = new JiQiRenPresenterImpl(this);
        initView();
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                messagePresenter.loadMessage(editText.getText().toString());
            }
        });
    }

    private void initView(){
        textView = (TextView)findViewById(R.id.textview);
        editText = (EditText)findViewById(R.id.edittext);
        button = (Button)findViewById(R.id.button);
    }

    @Override
    public void addMessage(JiQiRen message) {
        String s = message.getMessage();
        textView.setText(s);
    }

    @Override
    public void showMessageFailure(JiQiRen message) {
        textView.setText(message.getMessage());
    }
}

xml文件

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <EditText
        android:layout_width="match_parent"
        android:layout_height="80dp"
        android:id="@+id/edittext"/>
    <TextView
        android:id="@+id/textview"
        android:layout_width="match_parent"
        android:layout_height="300dp" />
    <Button
        android:id="@+id/button"
        android:layout_width="match_parent"
        android:layout_height="40dp"
        android:text="button"/>

</LinearLayout>

读者可自行结合MVC开发框架来对比理解MVP开发框架

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值