用了MVP写过一个项目了,在这个新项目开始之际将MVP的写法做个记录。以下仅是个人对MVP的理解。
附上demo地址点击打开链接
MVP即Model,View,Presnter。
在我的理解下MVP就是将数据和View完全分离,view层只管根据数据修改ui,model只管获取数据,而presenter是两者之间的桥梁,调用model对象方法获取数据并且对数据进行的一定的处理,然后将处理好的数据返给view。以一个登录的过程为例:将activity作为view,在view层new一个presenter对象并通过将view传过去presenter。然后当用户点击登录时,调用presenter中的方法login方法,在login方法中从model中获取登录请求的结果,最后通过刚传过来的view对象回调回ativity并根据结果改变ui。
好像光通过文字讲述有点空洞,那就直接上代码吧。由于免费api难找,就使用的聚合数据的万年历的接口为例。
public interface Presenter
{
void attachView(V mvpView);
void detachView();
}
public interface MvpView {
void showError(int errorCode);
void showEmpty(String msg);
}
public interface MvpModel {
}
public class DayContract {
public interface View extends MvpView {
void setDayInfo(DayResponse.ResultBean.DataBean dayInfo);
}
public interface Model extends MvpModel {
void getDayInfo(String date, RestAPIObserver
restAPIObserver);
}
}
public class BasePresenter
implements Presenter
{
protected T mMvpView;
protected M mMvpModel;
protected Context context;
public BasePresenter(Context context) {
this.context = context;
}
@Override
public void attachView(T mvpView) {
mMvpView = mvpView;
}
@Override
public void detachView() {
mMvpView = null;
}
public boolean isViewAttached() {
return mMvpView != null;
}
public T getMvpView() {
return mMvpView;
}
}
public class DayContract {
public interface View extends MvpView {
void setDayInfo(DayResponse.ResultBean.DataBean dayInfo);
}
public interface Model extends MvpModel {
void getDayInfo(String date, RestAPIObserver
restAPIObserver);
}
}
public class DayModelImpl implements DayContract.Model {
@Override
public void getDayInfo(String date, RestAPIObserver
restAPIObserver) {
//网络请求用的Retrofit+Rxjava这里就不具体展开了
new DayApi().getDayInfo(date,restAPIObserver);
}
}
public class DayPresenter extends BasePresenter
{
public DayPresenter(Context context) {
super(context);
mMvpModel = new DayModelImpl();
}
public void getDayInfo(String date){
mMvpModel.getDayInfo(date, new RestAPIObserver
(context,true) {
@Override
protected void onSuccess(DayResponse dayResponse) {
//将结果传回view层
mMvpView.setDayInfo(dayResponse.getResult().getData());
}
@Override
protected void onApiError(ApiException e) {
mMvpView.showError(e.getResponseError().getError_code());
}
});
}
}
public class MainActivity extends AppCompatActivity implements DayContract.View, View.OnClickListener {
@BindView(R.id.tv_holiday)
TextView tv_holiday;
@BindView(R.id.tv_lunarYear)
TextView tv_lunarYear;
@BindView(R.id.tv_animalsyear)
TextView tv_animalsyear;
@BindView(R.id.tv_suit)
TextView tv_suit;
@BindView(R.id.btn_getDayInfo)
Button btn_getDayInfo;
private DayPresenter presenter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this);
presenter = new DayPresenter(this);
//将view传给presenter,为了回调
presenter.attachView(this);
btn_getDayInfo.setOnClickListener(this);
}
@Override
protected void onDestroy() {
super.onDestroy();
presenter.detachView();
}
@Override
public void showError(int errorCode) {
}
@Override
public void showEmpty(String msg) {
}
@Override
public void setDayInfo(DayResponse.ResultBean.DataBean dayInfo) {
//根据结果修改ui
tv_animalsyear.setText(dayInfo.getAnimalsYear());
tv_holiday.setText(dayInfo.getHoliday());
tv_lunarYear.setText(dayInfo.getLunarYear());
tv_suit.setText(dayInfo.getSuit());
}
@Override
public void onClick(View view) {
presenter.getDayInfo("2017-8-10");
}
}