Android開發中的MVP實現

最近想要重構代碼,因為項目需要給幾個學校使用,而每個學校的界面是有差別的,但是功能幾乎一模一樣,雖然用gradle的分支可以做到代碼的差異,但是公共部分的代碼邏輯也越來越多,所以想重構一下,最近比較火的MVP模式看了一下,覺得很合適,不過網上很多資料也是抄來抄去,有的還有錯誤,就想按照自己的理解把MVP模式描述一下,方便他人理解,先說一下大家最熟悉的MVC設計模式吧

深度截圖20161205163205.png

MVC模式解耦合了M層和V層,M層和V層通過C層來交互

然后看一下MVP,我下面的文字以I開頭的是接口的意思(手打的圖好累...)

深度截圖20161205160152.png

MVP和MVC最大的區別是P層代替了以前的C層,控制的不再是具體的實現而是接口,這樣不管是多人開發還是頻繁的UI更改,都不會影響P層,只要C和V層的接口不變,要改動的只是UI而已,這樣代碼就很清晰,而且方便測試,因為邏輯層和視圖層完全分離了,下面用代碼來說話,還是先來MVC模式的,用登錄這個例子吧,android已經很好的把C層和V層分開了,我們寫的xml相當于V層,Activity相當于C層

public interface ICallback{
  void receive(boolean success);
}
public class LoginModel{
  public void login(String name,String password,ICallback callback){
    WebApi.login(name,password,callback);
  }
}
public class LoginActivity extends Activity{
  private LoginModel mLoginModel;
  private EditText mUserNameEt;
  private EditText mPasswordEt;
  private Button mSubmitBtn;
  public void onCreate(......){
    mLoginModel = new LoginModel(...);
    mSubmitBtn.setOnClickListener(new OnClickListener(View view){
        mLoginModel.login(mUserNameEt.get...,mPasswordEt.get...,new Callback(){
          public void receive(boolean success){
            if(success){
              startActivity(new Intent(this,MainActivity.class));
              finish();
            } else {
              Toast.makeText(this,"登錄失敗",Toast.LENGTH_SHORT).show();
            }
          }
        });
    });
  }
}

我們再來看一下用MVP模式怎么寫

public interface ILoginModel{
  public void login(String name,String password,Callback callback);
}
public class LoginModelImpl implements ILoginModel{
  public void login(String name,String password,Callback callback){
    WebApi.login(name,password,callback);
  }
}
public interface ILoginView{
  public void showDialog();
  public void dismissDialog();
  public void showToast(String message);
  public void navigateToMain();
}
public interface IPresenter{
  public void login(String name,String password);
}
public class PresenterImpl implements IPresenter,ICallback{
  private ILoginView mLoginView;
  private ILoginModel mLoginModel;

  public PresenterImpl(ILoginView loginView){
    this.mLoginView = loginView;
    this.mLoginModel = new LoginModelImpl();
  }

  public void login(String name,String password){
    if(isEmpty(name)||isEmpty(password)){
        this.mLoginView.showToast("用戶名或密碼不能為空");
        return;
    }
    this.mLoginModel.login(name,password,this);
  }

  public void receive(boolean success){
    if(success){
      this.mLoginView.navigateToMain();
    }else{
      this.mLoginView.showToast("登錄失敗");
    }
  }

  private boolean isEmpty(String text){
    return text==null||"".equals(text)?true:false;
  }
}
public class LoginActivity extends Activity implements ILoginView{
  private IPresenter mPresenter;
  private EditText mUserNameEt;
  private EditText mPasswordEt;
  private Button mSubmitBtn;
  public void onCreate(......){
    mPresenter = new PresenterImpl(this);
    mSubmitBtn.setOnClickListener(new OnClickListener(View view){
        mLoginModel.login(mUserNameEt.getText().toString(),
                          mPasswordEt.getText().toString());
    });
  }

  public void showDialog(){
    //顯示一個轉圈的dialog;
  }

  public void dismissDialog(){
    //隱藏轉圈的dialog;
  }

  public void showToast(String message){
    Toast.makeText(this,message,Toast.LENGTH_SHORT).show();
  }

  public void navigateToMain(){
    startActivity(new Intent(this,MainActivity.class));
    finish();
  }
}

MVP的類和代碼確實要多一些,但是這些是非常值得的,可以看出現在的代碼邏輯要比MVC模式寫起來更清晰,代碼測試也更簡單,甚至可以在沒有頁面效果圖只有功能的時候完成功能,UI的改變也不會影響任何的業務代碼。

以上MVP設計模式是個人理解,如果有誤請指正,謝謝,共同探討,共同進步

 

來自:http://www.jianshu.com/p/4e2a1dfd4d95

 

 本文由用戶 CarSowerby 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!