فهرست منبع

只使用一次的LiveData

詹子聪 5 سال پیش
والد
کامیت
4dd3b76d4c

+ 7 - 5
app/build.gradle

@@ -1,5 +1,5 @@
 apply plugin: 'com.android.application'
-apply plugin: 'com.hujiang.android-aspectjx'
+//apply plugin: 'com.hujiang.android-aspectjx'
 
 
 android {
@@ -27,14 +27,16 @@ dependencies {
     testImplementation 'junit:junit:4.12'
     androidTestImplementation 'androidx.test.ext:junit:1.1.0'
     androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.1'
+
+    implementation project(path: ':common')
     implementation project(path: ':mvp')
 
     // 查看内存泄露
     debugImplementation 'com.squareup.leakcanary:leakcanary-android:2.1'
 
-    compile 'org.aspectj:aspectjrt:1.8.+'
+//    compile 'org.aspectj:aspectjrt:1.8.+'
 }
 
-aspectjx {
-    exclude  "android.support",'androidx','com.google','com.squareup.leakcanary','com.squareup.leakcanary.core','com.alipay','org.apache','com.tencent'
-}
+//aspectjx {
+//    exclude  "android.support",'androidx','com.google','com.squareup.leakcanary','com.squareup.leakcanary.core','com.alipay','org.apache','com.tencent'
+//}

+ 78 - 77
app/src/main/java/com/miekir/newmvp/LoadingAspect.java

@@ -1,79 +1,80 @@
 package com.miekir.newmvp;
 
-import android.util.Log;
-
-import com.miekir.mvp.base.NeedLoading;
-
-import org.aspectj.lang.JoinPoint;
-import org.aspectj.lang.ProceedingJoinPoint;
-import org.aspectj.lang.annotation.After;
-import org.aspectj.lang.annotation.Around;
-import org.aspectj.lang.annotation.Aspect;
-import org.aspectj.lang.annotation.Before;
-import org.aspectj.lang.annotation.Pointcut;
-import org.aspectj.lang.reflect.MethodSignature;
-
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-
-/**
- * https://blog.csdn.net/zhengchao1991/article/details/53391244
- * 加载框
- */
-@Aspect
-public class LoadingAspect {
-    private static final String TAG = "LoadingAspect";
-    // 要注意加上execution(* *(..)) && 防止被执行两次
-    @Pointcut("execution(* *(..)) && @annotation(com.miekir.mvp.base.NeedLoading)")
-    public void timeTask() {}
-
-    @Around("timeTask()")
-    public void onTimeTaskAround(ProceedingJoinPoint joinPoint) throws Throwable {
-        Object targetObject  = joinPoint.getTarget();
-        Field liveDataField = null;
-        try {
-            liveDataField = targetObject.getClass().getField("dialogLiveData");
-        } catch (Exception e) {
-            e.printStackTrace();
-            joinPoint.proceed();
-            return;
-        }
-
-        if (liveDataField != null) {
-            // 得到此属性的值
-            Object liveData = liveDataField.get(targetObject);
-            if (liveData == null) {
-                Log.e(TAG, "live data value null....");
-                return;
-            }
-            //如果在Around中不调用joinPoint.proceed(),则@Before注解的方法不会调用,但是@After还是会调用。
-            joinPoint.proceed();
-            Log.e(TAG, "proceed....");
-        } else {
-            Log.e(TAG, "live data null....");
-        }
-    }
-
-    @Before("timeTask()")
-    public void beforeMethod(JoinPoint joinPoint){
-        // 注入加载框
-        Object targetObject  = joinPoint.getTarget();
-        try {
-            Method showDialogMethod = targetObject.getClass().getMethod("showLoading");
-            /*Method showDialogMethod = targetObject.getClass().getMethod("showLoading", String.class);
-            String message = "";
-            Method taskMethod = ((MethodSignature)joinPoint.getSignature()).getMethod();
-            if (taskMethod.isAnnotationPresent(NeedLoading.class)) {
-                NeedLoading loading = taskMethod.getAnnotation(NeedLoading.class);
-                if (loading != null) {
-                    message = loading.message();
-                }
-            }
-            showDialogMethod.invoke(targetObject, message);*/
-
-            showDialogMethod.invoke(targetObject);
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-    }
-}
+//import android.util.Log;
+//
+//import com.miekir.mvp.base.NeedLoading;
+//
+//import org.aspectj.lang.JoinPoint;
+//import org.aspectj.lang.ProceedingJoinPoint;
+//import org.aspectj.lang.annotation.After;
+//import org.aspectj.lang.annotation.Around;
+//import org.aspectj.lang.annotation.Aspect;
+//import org.aspectj.lang.annotation.Before;
+//import org.aspectj.lang.annotation.Pointcut;
+//import org.aspectj.lang.reflect.MethodSignature;
+//
+//import java.lang.reflect.Field;
+//import java.lang.reflect.Method;
+//
+///**
+// * https://blog.csdn.net/zhengchao1991/article/details/53391244
+// * 加载框
+// */
+//@Aspect
+//public class LoadingAspect {
+//    private static final String TAG = "LoadingAspect";
+//    // 要注意加上execution(* *(..)) && 防止被执行两次
+//    @Pointcut("execution(* *(..)) && @annotation(com.miekir.mvp.base.NeedLoading)")
+//    public void timeTask() {}
+//
+//    @Around("timeTask()")
+//    public void onTimeTaskAround(ProceedingJoinPoint joinPoint) throws Throwable {
+//        Object targetObject  = joinPoint.getTarget();
+//        Field liveDataField = null;
+//        try {
+// dialogLiveData这个属性必须必须是public的,否则在此时是在子类,非public的话getField会拿不到而报错
+//            liveDataField = targetObject.getClass().getField("dialogLiveData");
+//        } catch (Exception e) {
+//            e.printStackTrace();
+//            joinPoint.proceed();
+//            return;
+//        }
+//
+//        if (liveDataField != null) {
+//            // 得到此属性的值
+//            Object liveData = liveDataField.get(targetObject);
+//            if (liveData == null) {
+//                Log.e(TAG, "live data value null....");
+//                return;
+//            }
+//            //如果在Around中不调用joinPoint.proceed(),则@Before注解的方法不会调用,但是@After还是会调用。
+//            joinPoint.proceed();
+//            Log.e(TAG, "proceed....");
+//        } else {
+//            Log.e(TAG, "live data null....");
+//        }
+//    }
+//
+//    @Before("timeTask()")
+//    public void beforeMethod(JoinPoint joinPoint){
+//        // 注入加载框
+//        Object targetObject  = joinPoint.getTarget();
+//        try {
+//            Method showDialogMethod = targetObject.getClass().getMethod("showLoading");
+//            /*Method showDialogMethod = targetObject.getClass().getMethod("showLoading", String.class);
+//            String message = "";
+//            Method taskMethod = ((MethodSignature)joinPoint.getSignature()).getMethod();
+//            if (taskMethod.isAnnotationPresent(NeedLoading.class)) {
+//                NeedLoading loading = taskMethod.getAnnotation(NeedLoading.class);
+//                if (loading != null) {
+//                    message = loading.message();
+//                }
+//            }
+//            showDialogMethod.invoke(targetObject, message);*/
+//
+//            showDialogMethod.invoke(targetObject);
+//        } catch (Exception e) {
+//            e.printStackTrace();
+//        }
+//    }
+//}

+ 12 - 4
app/src/main/java/com/miekir/newmvp/MainActivity.java

@@ -6,15 +6,18 @@ import android.view.View;
 import android.widget.TextView;
 import android.widget.Toast;
 
+import androidx.lifecycle.Observer;
+
 import com.miekir.mvp.model.DataMethod;
 import com.miekir.mvp.presenter.InjectPresenter;
+import com.miekir.mvp.jetpack.MvpObserver;
 import com.miekir.mvp.view.BaseMvpActivity;
 
 import java.util.List;
 
 public class MainActivity extends BaseMvpActivity {
     @InjectPresenter
-    TestPresenter viewModel1;
+    TestPresenter presenter;
 
     @Override
     public int getLayoutID() {
@@ -30,15 +33,20 @@ public class MainActivity extends BaseMvpActivity {
             @Override
             public void onClick(View view) {
                 // 点击之后,后台执行耗时操作
-                viewModel1.go();
+                presenter.go().observeOnce(new MvpObserver<TestBean1>() {
+                    @Override
+                    public void onDataChanged(TestBean1 testBean1) {
+                        Toast.makeText(getApplicationContext(), "hello", Toast.LENGTH_SHORT).show();
+                    }
+                });
             }
         });
 
         findViewById(R.id.btn_test).setOnClickListener(new View.OnClickListener() {
             @Override
             public void onClick(View view) {
-                // 点击之后,后台执行耗时操作
-                startActivity(new Intent(MainActivity.this, MainActivity.class));
+            // 点击之后,后台执行耗时操作
+            startActivity(new Intent(MainActivity.this, MainActivity.class));
             }
         });
     }

+ 9 - 5
app/src/main/java/com/miekir/newmvp/TestPresenter.java

@@ -1,8 +1,7 @@
 package com.miekir.newmvp;
 
-import com.miekir.mvp.base.NeedLoading;
-import com.miekir.mvp.model.DataSource;
 import com.miekir.mvp.presenter.BasePresenter;
+import com.miekir.mvp.jetpack.MvpLiveData;
 
 import java.util.ArrayList;
 import java.util.List;
@@ -22,8 +21,10 @@ public class TestPresenter extends BasePresenter {
 
     }
 
-    @NeedLoading
-    public void go() {
+    public MvpLiveData<TestBean1> go() {
+        showLoading();
+        final MvpLiveData<TestBean1> specificLiveData = new MvpLiveData<>();
+
         new Thread(new Runnable() {
             @Override
             public void run() {
@@ -32,13 +33,16 @@ public class TestPresenter extends BasePresenter {
                     List<TestBean1> testBean1List = new ArrayList<>();
                     testBean1List.add(new TestBean1(3, "ViewModel Jason"));
                     // 这里还有问题,就是post的错误没法被正确的方法接收
-                    postFail("错误", SOURCE_LOGIN_RESULT);
+                    //postFail("错误", SOURCE_LOGIN_RESULT);
+                    specificLiveData.postValue(null);
                 } catch (Exception e) {
                     e.printStackTrace();
                 }
                 dismissLoading();
             }
         }).start();
+
+        return specificLiveData;
     }
 
     @Override

+ 1 - 4
build.gradle

@@ -8,9 +8,7 @@ buildscript {
     }
     dependencies {
         classpath 'com.android.tools.build:gradle:3.6.1'
-        classpath 'com.hujiang.aspectjx:gradle-android-plugin-aspectjx:2.0.10'
-        // NOTE: Do not place your application dependencies here; they belong
-        // in the individual module build.gradle files
+//        classpath 'com.hujiang.aspectjx:gradle-android-plugin-aspectjx:2.0.10'
     }
 }
 
@@ -18,7 +16,6 @@ allprojects {
     repositories {
         google()
         jcenter()
-        
     }
 }
 

+ 0 - 1
mvp/build.gradle

@@ -36,5 +36,4 @@ dependencies {
     implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycle_version"
     implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version"
     implementation 'androidx.lifecycle:lifecycle-extensions:2.2.0'
-
 }

+ 44 - 0
mvp/src/main/java/com/miekir/mvp/jetpack/MvpLiveData.java

@@ -0,0 +1,44 @@
+package com.miekir.mvp.jetpack;
+
+import androidx.annotation.NonNull;
+import androidx.lifecycle.MutableLiveData;
+import androidx.lifecycle.Observer;
+
+/**
+ * Copyright (C), 2019-2020, Miekir
+ *
+ * @author Miekir
+ * @date 2020/11/14 20:45
+ * Description:
+ */
+public class MvpLiveData<T> extends MutableLiveData<T> {
+    /**
+     * 得到一个LiveData,用于传递Observer参数的形式,这里暂时用不到
+     */
+    private <T> MutableLiveData<T> observeOnce(final Observer<T> observer) {
+        final MutableLiveData<T> specificLiveData = new MutableLiveData<>();
+        specificLiveData.observeForever(new Observer<T>() {
+            @Override
+            public void onChanged(T t) {
+                specificLiveData.removeObserver(this);
+                observer.onChanged(t);
+            }
+        });
+        return specificLiveData;
+    }
+
+    /**
+     * 只监听一次的LiveData
+     * @param observer
+     */
+    public void observeOnce(MvpObserver<T> observer) {
+        observer.setLiveData(this);
+        observeForever(observer);
+    }
+
+
+    @Override
+    public void observeForever(@NonNull Observer<? super T> observer) {
+        super.observeForever(observer);
+    }
+}

+ 27 - 0
mvp/src/main/java/com/miekir/mvp/jetpack/MvpObserver.java

@@ -0,0 +1,27 @@
+package com.miekir.mvp.jetpack;
+
+
+import androidx.lifecycle.Observer;
+
+/**
+ * Copyright (C), 2019-2020, Miekir
+ * @author Miekir
+ * @date 2020/11/14 20:51
+ * Description: 
+ */
+public abstract class MvpObserver<T> implements Observer<T> {
+    private MvpLiveData<T> liveData;
+    public void setLiveData(MvpLiveData<T> liveData) {
+        this.liveData = liveData;
+    }
+
+    public abstract void onDataChanged(T t);
+
+    @Override
+    public void onChanged(T t) {
+        if (liveData != null) {
+            liveData.removeObserver(this);
+        }
+        onDataChanged(t);
+    }
+}

+ 13 - 3
mvp/src/main/java/com/miekir/mvp/presenter/BasePresenter.java

@@ -1,13 +1,16 @@
 package com.miekir.mvp.presenter;
 
 import androidx.lifecycle.MutableLiveData;
+import androidx.lifecycle.Observer;
 import androidx.lifecycle.ViewModel;
 
 import com.miekir.mvp.bean.DataResult;
 import com.miekir.mvp.constant.BaseMvpResponse;
-import com.miekir.mvp.model.DataSource;
 import com.miekir.mvp.constant.DialogAction;
 
+import java.util.ArrayList;
+import java.util.List;
+
 /**
  * Copyright (C), 2019-2020, Miekir
  *
@@ -21,11 +24,11 @@ public abstract class BasePresenter extends ViewModel {
      * ViewModel的生命周期和Activity保持一致;在onStart()、onResume()、onPause()时调用LiveData的setValue才会通知观察者
      * liveData在ViewModel(Presenter)创建,然后提供方法给Activity获取,方便取消观察
      */
-    public MutableLiveData<DataResult> liveData = new MutableLiveData<DataResult>();
+    private MutableLiveData<DataResult> liveData = new MutableLiveData<DataResult>();
     /**
      * 由于使用了AspectJ,这个变量名和属性不能改动,否则AspectJ会拿不到值
      */
-    public MutableLiveData<DataResult> dialogLiveData = new MutableLiveData<DataResult>();
+    private MutableLiveData<DataResult> dialogLiveData = new MutableLiveData<DataResult>();
 
     public MutableLiveData<DataResult> getLiveData() {
         return liveData;
@@ -34,6 +37,9 @@ public abstract class BasePresenter extends ViewModel {
         return dialogLiveData;
     }
 
+    private List<MutableLiveData<Object>> specificLiveDataList = new ArrayList<>();
+
+
     /**
      * 由于使用了AspectJ,这个方法名不能改动
      * 对弹出对话框此时进行计数,归零才dismiss
@@ -78,7 +84,11 @@ public abstract class BasePresenter extends ViewModel {
         onTaskCancel();
     }
 
+    /**
+     * 初始化
+     */
     public abstract void init();
+
     /**
      * 当任务被取消时
      */

+ 1 - 1
mvp/src/main/java/com/miekir/mvp/view/ViewHelper.java

@@ -183,7 +183,7 @@ public class ViewHelper {
      */
     public static void handleDataResult(Object object, List<Method> mDataMethodList, DataResult result) {
         Class<?> objParamClass = null;
-        if (result.getBean() != null) {
+        if (result != null && result.getBean() != null) {
             objParamClass = result.getBean().getClass();
         }
 

+ 1 - 1
network/build.gradle

@@ -51,7 +51,7 @@ android {
 
 dependencies {
     api project(path: ':mvp')
-    api project(path: ':common')
+    implementation project(path: ':common')
     implementation fileTree(dir: 'libs', include: ['*.jar'])
 
     implementation 'androidx.appcompat:appcompat:1.3.0-alpha01'