MVP 特点
MVP 模式将Activity 中的业务逻辑全部分离出来,让Activity 只做 UI 逻辑的处理,所有跟Android API无关的业务逻辑由 Presenter 层来完成。
将业务处理分离出来后最明显的好处就是管理方便,但是缺点就是增加了代码量。
MVP 理论知识
在MVP 架构中跟MVC类似的是同样也分为三层。
Activity 和Fragment 视为View层,负责处理 UI。
Presenter 为业务处理层,既能调用UI逻辑,又能请求数据,该层为纯Java类,不涉及任何Android API。
Model 层中包含着具体的数据请求,数据源。
一张图看关系:
例子:
/**
* 接口封装类
*/
public class LoginContract {
// view层接口
public interface LoginView {
public void onLoadSuccess(LoginResult result);
public void onLoadFailed(String msg);
}
// model层接口
public interface LoginModel {
void getLoginData(LoginRequest loginRequest, LoginOnLoadListener listener);
}
// presenter层接口
public interface LoginPresenter {
void getData(LoginRequest loginRequest);
}
// callback
public interface LoginOnLoadListener {
public void onSuccess(LoginResult result);
public void onFailure(String msg);
}
}
model类:
public class LoginModel implements LoginContract.LoginModle {
@Override
public void getLoginData(LoginRequest loginRequest, final LoginContract.LoginOnLoadListener listener) {
// model用来访问网络
ApiRetrofit.getInstance().login(loginRequest)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Subscriber <LoginResult> () {
@Override
public void onCompleted() {
}
@Override
public void onError(Throwable e) {
listener.onFailure(e.getMessage());
}
@Override
public void onNext(LoginResult loginResult) {
listener.onSuccess(loginResult);
}
});
}
}
presenter类:
public class LoginPresenter implements LoginContract.Presenter {
private LoginModel model;
private LoginView mView;
public LoginPresenter(LoginView view) {
this.mView=view
model=new LoginModel();
}
@Override
public void getDataFromNet(LoginRequest loginRequest) {
//将model层获取的数据传入到view层
model.getLoginData(loginRequest, new LoginContract.LoginOnLoadListener() {
@Override
public void onSuccess(LoginResult result) {
mView.onLoadSuccess(result);
}
@Override
public void onFailure(String e) {
mView.onLoadFail(e);
}
});
}
}
view:
public class LoginActivity extends BaseActivity implements LoginContract.View {
@Bind(R.id.bt_login)
Button btLogin;
private LoginPresenter mPresenter;
...
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// TODO: add setContentView(...) invocation
ButterKnife.bind(this);
mPresenter = new LoginPresenter(this);
btLogin.setOnClickListener(v -> mPresenter.getDataFromNet(new LoginRequest()););
}
...
@Override
public void onLoadFail(String msg) {
LogUtils.i(TAG,msg);
...
}
@Override
public void onLoadSuccess(LoginResult result) {
LogUtils.i(TAG,result.toString());
...
}
}