记得创建module,首先创建Base层
创建Presenter层
package com.example.Presenter;
import java.lang.ref.WeakReference;
import io.reactivex.disposables.CompositeDisposable;
/**
* 由于使用MVP可能会遇到内存泄漏的问题,所以需要引用的形式来处理,当内存对象被回收时,可以及时回收p层,避免内存泄漏
* 强引用User user=new User()强引用,就是普通的引用形式,如果一个对象拒用强引用,用垃圾回收(GC)
* 软引用softRrferece<String> username 在内存不足的时候会被回收,不会OOM
* 弱引用WeakREference<String> username放发生Gc的时候,会被直接回收掉弱引用对象,不管空间是否足够,都会被回收
* 虚引用PhantomRerence 幽灵引用,尽量不要用,没有办法去实例一个对象,对这个对象发生命周期完全没有影响
*/
public class BasePresenter<V>{
WeakReference<V>weakReference;//使用弱引用声明一个V层,当发生Gc时,可以回收掉
protected CompositeDisposable disposable=new CompositeDisposable();//作为p层的回收条件,避免P层出现内存泄漏
//当声明一个V层的时候,需要把这个V层加入到软引用
public void attachView(V view){
if (weakReference==null){
weakReference=new WeakReference<V>(view);
}
}
//当一个V层需要销毁时,需要置空C层和P层的声明
public void distach(){
if (weakReference!=null){
weakReference.clear();
weakReference=null;
}
if (disposable!=null){
disposable.clear();
disposable=null;
}
}
//此方法用于判断当前的V层是否加入到了软引用,weakReference.get()相当于取出V层
public Boolean isAttach(){
return weakReference!=null&&weakReference.get()!=null;
}
//从软引用取出当前的View
public V getView(){
if (weakReference!=null&&weakReference.get()!=null){
return weakReference.get();
}
return null;
}
}
创建View:BaseActivity
package com.example.view;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import com.example.Presenter.BasePresenter;
public abstract class BaseActivity<V,P extends BasePresenter> extends AppCompatActivity {
protected P presenter;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(bindLayoutld());
initView();
initData();
if (presenter!=null){
presenter.attachView((V)this);
}
}
protected abstract void initData();
protected abstract void initView();
protected abstract int bindLayoutld();
@Override
protected void onDestroy() {
super.onDestroy();
if (presenter!=null){
presenter.distach();
}
}
}
创建View:BaseFagment
创建实现层
创建Api接口
package com.example.rejinster.net;
import com.example.Base.Base1;
import com.example.Base.JavaB;
import io.reactivex.Observable;
import retrofit2.http.POST;
import retrofit2.http.Query;
public interface ApiService {
@POST("/user/register")
Observable<JavaB> register(@Query("username")String username,
@Query("password")String password,
@Query("repassword")String repassword);
}
创建BaseRetrofitManger管理
package com.example.rejinster.net;
import java.io.IOException;
import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import okhttp3.logging.HttpLoggingInterceptor;
import retrofit2.Retrofit;
import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory;
import retrofit2.converter.gson.GsonConverterFactory;
/**
* 请求管理
* 封装Retrofit,使用单例模式对外暴露一个实例
*/
public class RetrofitManger {
private RetrofitManger(){
}
private static RetrofitManger retrofitManger=null;
public static RetrofitManger getInstance(){
if (retrofitManger==null){
retrofitManger=new RetrofitManger();
}
return retrofitManger;
}
//网络请求框架的实例
private Retrofit retrofit;
public Retrofit getRetrofit(){
if (retrofit==null){
OkHttpClient client=
new OkHttpClient.Builder().addInterceptor(new HttpLoggingInterceptor().setLevel(HttpLoggingInterceptor.Level.BODY))
.addInterceptor(new Interceptor() {
@Override
public Response intercept(Chain chain) throws IOException {
Request request = chain.request().newBuilder().addHeader(
"token", "asdasd"
).build();
return chain.proceed(request);
}
})
.build();
retrofit=new Retrofit.Builder()
.baseUrl("http://43.143.146.165:7777/")
.client(client)
.addConverterFactory(GsonConverterFactory.create())//添加类型转换工厂,可以不手动转换,直接返回楚ban类
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())//线程切换的适配器
.build();
}
return retrofit;
}
}
创建BaseMode
package com.example.rejinster.day3mvp;
import com.example.rejinster.net.ApiService;
import com.example.rejinster.net.RetrofitManger;
/**
* 所有数据模型的基准
*/
public class BaseModel {
protected ApiService apiService;
public BaseModel(){
//拿到整个项目的接口实现
apiService= RetrofitManger.getInstance().getRetrofit().create(ApiService.class);
}
}
创建P层RsgisinPresentera接口
package com.example.rejinster.presenter;
import com.example.Base.JavaB;
import io.reactivex.Observable;
public interface RsgisinPresentera {
//M层主要功能负责网络请假返回的bean类
interface Model{
Observable<JavaB> register(String username, String password, String repassword);
}
//P层主要功能负责触发网络连接
interface Presenter{
void register(String username,String password,String repassword);
}
//V层
interface View{
//拿到的数据
void OnRegister(JavaB javaB);
//报错信息
void OnRegisterFalied(String error);
}
}
创建Model层
import com.example.Base.JavaB;
import com.example.rejinster.day3mvp.BaseModel;
import com.example.rejinster.presenter.RsgisinPresentera;
import io.reactivex.Observable;
public class RegistiModel extends BaseModel implements RsgisinPresentera.Model {
@Override
public Observable<JavaB> register(String username, String password, String repassword) {
return apiService.register(username, password, repassword);
}
}
创建P层ResdistPresenter
package com.example.rejinster.presenter;
import com.example.Base.JavaB;
import com.example.Presenter.BasePresenter;
import com.example.rejinster.Model.RegistiModel;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.Disposable;
import io.reactivex.schedulers.Schedulers;
public class ResdistPresenter extends BasePresenter<RsgisinPresentera.View>implements RsgisinPresentera.Presenter {
RegistiModel model=new RegistiModel();
@Override
public void register(String username, String password, String repassword) {
model.register(username, password, repassword)
.subscribeOn(Schedulers.io())//执行耗时操作的时,在io线程中,也就是子线程
.observeOn(AndroidSchedulers.mainThread())//当观测对象发生改变时,运行在ul线程
.subscribe(new Observer<JavaB>() {
@Override
public void onSubscribe(Disposable d) {
//这个会调用填写P层防止内存泄漏
disposable.add(d);
}
@Override
public void onNext(JavaB javaB) {
//请求回调的结果,会回调出bean类
if (isAttach()){
//如果当前View层已经绑定在弱引用中,则咱们可以获取View
getView().OnRegister(javaB);
}
}
@Override
public void onError(Throwable e) {
//请求发生错误时的回调
getView().OnRegisterFalied(e.getMessage());
}
@Override
public void onComplete() {
//请求完成时发生的回调
}
});
}
}
实现V层
package com.example.rejinster.view;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.Toast;
import com.alibaba.android.arouter.launcher.ARouter;
import com.example.Base.JavaB;
import com.example.day3mvp.R;
import com.example.rejinster.presenter.ResdistPresenter;
import com.example.rejinster.presenter.RsgisinPresentera;
import com.example.view.BaseActivity;
public class RegisterActivity extends BaseActivity<RsgisinPresentera.View, ResdistPresenter> implements RsgisinPresentera.View {
private EditText registerUsername;
private EditText registerPassword;
private EditText registerRepassword;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_register);
initView();
}
@Override
protected void initData() {
presenter = new ResdistPresenter();
}
public void initView() {
registerUsername = (EditText) findViewById(R.id.register_username);
registerPassword = (EditText) findViewById(R.id.register_password);
registerRepassword = (EditText) findViewById(R.id.register_repassword);
}
@Override
protected int bindLayoutld() {
return R.layout.activity_register;
}
@Override
public void OnRegister(JavaB javaB) {
if (javaB.getErrorCode()==200){
Toast.makeText(this, "注册成功"+javaB.getData().getNickname(), Toast.LENGTH_SHORT).show();
}
}
@Override
public void OnRegisterFalied(String error) {
Toast.makeText(this, "error"+error, Toast.LENGTH_SHORT).show();
}
public void register(View view) {
String usernameString = registerUsername.getText().toString();
String passwordString = registerPassword.getText().toString();
String rePasswordString = registerRepassword.getText().toString();
presenter.register(usernameString, passwordString, rePasswordString);
//传值
ARouter.getInstance().build("/text/login")
.withString("username",usernameString)
.withString("password",passwordString)
.navigation();
}
}
可以根据上面的展示图看,登录注册解串全可以根据实现层修改