退出Activity时清理bitmap

退出LiveActivity时,清理SVGA
新增检测到触发未捕获异常闪退时,直接退出不再重新加载
优化一处LiveActivity所持有的静态view,防止内存泄漏
更新SVGAPlayer库
This commit is contained in:
zlzw 2022-10-06 11:43:06 +08:00
parent 39b4a52ade
commit dd97d35851
12 changed files with 62 additions and 14 deletions

View File

@ -6,6 +6,7 @@ import android.content.Context;
import android.net.http.HttpResponseCache; import android.net.http.HttpResponseCache;
import android.os.Bundle; import android.os.Bundle;
import android.os.Message; import android.os.Message;
import android.os.Process;
import android.text.TextUtils; import android.text.TextUtils;
import android.util.Log; import android.util.Log;
@ -28,6 +29,7 @@ import com.yunbao.common.BuildConfig;
import com.yunbao.common.CommonAppConfig; import com.yunbao.common.CommonAppConfig;
import com.yunbao.common.CommonAppContext; import com.yunbao.common.CommonAppContext;
import com.yunbao.common.Constants; import com.yunbao.common.Constants;
import com.yunbao.common.glide.ImgLoader;
import com.yunbao.common.http.CommonHttpUtil; import com.yunbao.common.http.CommonHttpUtil;
import com.yunbao.common.http.HttpCallback; import com.yunbao.common.http.HttpCallback;
import com.yunbao.common.manager.imrongcloud.InstructorSendReward; import com.yunbao.common.manager.imrongcloud.InstructorSendReward;
@ -47,7 +49,9 @@ import com.yunbao.main.activity.MsgSettActivity;
import java.io.File; import java.io.File;
import java.io.IOException; import java.io.IOException;
import java.lang.ref.WeakReference;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List;
import io.rong.imkit.config.RongConfigCenter; import io.rong.imkit.config.RongConfigCenter;
import io.rong.imlib.RongIMClient; import io.rong.imlib.RongIMClient;
@ -72,6 +76,7 @@ public class AppContext extends CommonAppContext {
public static AppContext sInstance; public static AppContext sInstance;
public LiveImDeletUtil liveImDeletUtil; public LiveImDeletUtil liveImDeletUtil;
private final static List<WeakReference<Activity>> activities = new ArrayList<>();
private static final class AdjustLifecycleCallbacks implements ActivityLifecycleCallbacks { private static final class AdjustLifecycleCallbacks implements ActivityLifecycleCallbacks {
@Override @Override
@ -96,12 +101,12 @@ public class AppContext extends CommonAppContext {
@Override @Override
public void onActivityDestroyed(@NonNull Activity activity) { public void onActivityDestroyed(@NonNull Activity activity) {
activities.remove(activity);
} }
@Override @Override
public void onActivityCreated(@NonNull Activity activity, @Nullable Bundle savedInstanceState) { public void onActivityCreated(@NonNull Activity activity, @Nullable Bundle savedInstanceState) {
activities.add(new WeakReference<>(activity));
} }
@Override @Override
@ -115,7 +120,7 @@ public class AppContext extends CommonAppContext {
public void onCreate() { public void onCreate() {
super.onCreate(); super.onCreate();
//注册全局异常捕获 //注册全局异常捕获
// registerError(); registerError();
sInstance = this; sInstance = this;
L.setDeBug(BuildConfig.DEBUG); L.setDeBug(BuildConfig.DEBUG);
AppEventsLogger.activateApp(this); AppEventsLogger.activateApp(this);
@ -288,6 +293,14 @@ public class AppContext extends CommonAppContext {
.setMainCrashHandler((t, e) -> { .setMainCrashHandler((t, e) -> {
Log.e("ApplicationError", "主线程异常");//此处log只是展示当debug为true时主类内部log会打印异常信息 Log.e("ApplicationError", "主线程异常");//此处log只是展示当debug为true时主类内部log会打印异常信息
e.printStackTrace(); e.printStackTrace();
//闪退后finish所有Activity并且杀死进程
for (WeakReference<Activity> activity : activities) {
if (activity != null) {
activity.get().finish();
}
}
Process.killProcess(Process.myPid());
System.exit(0);
}) })
.setUncaughtCrashHandler((t, e) -> { .setUncaughtCrashHandler((t, e) -> {
Log.e("ApplicationError", "子线程异常");//此处log只是展示当debug为true时主类内部log会打印异常信息 Log.e("ApplicationError", "子线程异常");//此处log只是展示当debug为true时主类内部log会打印异常信息

View File

@ -46,7 +46,7 @@ public class NeverCrashUtils {
* 注意跨线程操作的可能 * 注意跨线程操作的可能
*/ */
public NeverCrashUtils setMainCrashHandler(MainCrashHandler mainCrashHandler) { public NeverCrashUtils setMainCrashHandler(MainCrashHandler mainCrashHandler) {
mainCrashHandler = mainCrashHandler; this.mainCrashHandler = mainCrashHandler;
return this; return this;
} }
@ -98,6 +98,7 @@ public class NeverCrashUtils {
Toast.makeText(application, "发生闪退", Toast.LENGTH_SHORT).show(); Toast.makeText(application, "发生闪退", Toast.LENGTH_SHORT).show();
// FileUtil.saveStringToFile(new File(application.getDir("files", Context.MODE_PRIVATE).getAbsolutePath()),throwableToString(e),"error.log"); // FileUtil.saveStringToFile(new File(application.getDir("files", Context.MODE_PRIVATE).getAbsolutePath()),throwableToString(e),"error.log");
getMainCrashHandler().mainException(Looper.getMainLooper().getThread(), e); getMainCrashHandler().mainException(Looper.getMainLooper().getThread(), e);
} }
} }
}); });

View File

@ -24,6 +24,7 @@ import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity; import androidx.appcompat.app.AppCompatActivity;
import com.yunbao.common.R; import com.yunbao.common.R;
import com.yunbao.common.glide.ImgLoader;
import com.yunbao.common.interfaces.LifeCycleListener; import com.yunbao.common.interfaces.LifeCycleListener;
import com.yunbao.common.utils.ClickUtil; import com.yunbao.common.utils.ClickUtil;
@ -136,6 +137,7 @@ public abstract class AbsActivity extends AppCompatActivity {
mLifeCycleListeners.clear(); mLifeCycleListeners.clear();
mLifeCycleListeners = null; mLifeCycleListeners = null;
} }
ImgLoader.clearMemory(this);
super.onDestroy(); super.onDestroy();
} }

View File

@ -3,8 +3,18 @@ package com.yunbao.common.utils;
import com.opensource.svgaplayer.SVGACallback; import com.opensource.svgaplayer.SVGACallback;
import com.opensource.svgaplayer.SVGAImageView; import com.opensource.svgaplayer.SVGAImageView;
import java.util.ArrayList;
import java.util.List;
public class SVGAViewUtils { public class SVGAViewUtils {
public static void playEndClear(SVGAImageView svga,boolean isClear){ private final static List<SVGAImageView> SVGA_CACHE = new ArrayList<>();
public static void playEndClear(SVGAImageView svga, boolean isClear) {
if (!isClear) {
if (!SVGA_CACHE.contains(svga)) {
SVGA_CACHE.add(svga);
}
}
svga.setCallback(new SVGACallback() { svga.setCallback(new SVGACallback() {
@Override @Override
public void onPause() { public void onPause() {
@ -14,7 +24,7 @@ public class SVGAViewUtils {
@Override @Override
public void onFinished() { public void onFinished() {
//动画结束后调用clear释放资源 //动画结束后调用clear释放资源
if(isClear) { if (isClear) {
svga.clear(); svga.clear();
} }
} }
@ -31,7 +41,21 @@ public class SVGAViewUtils {
}); });
svga.startAnimation(); svga.startAnimation();
} }
public static void playEndClear(SVGAImageView svga){
playEndClear(svga,true); public synchronized static void clearSVGA() {
for (SVGAImageView view : SVGA_CACHE) {
try {
if (view != null) {
view.clear();
}
} catch (Exception e) {
e.printStackTrace();
}
}
SVGA_CACHE.clear();
}
public static void playEndClear(SVGAImageView svga) {
playEndClear(svga, true);
} }
} }

Binary file not shown.

Binary file not shown.

View File

@ -1 +1 @@
apply plugin: 'com.android.library' apply plugin: 'img-optimizer' apply plugin: 'kotlin-android' android { compileSdkVersion rootProject.ext.android.compileSdkVersion buildToolsVersion rootProject.ext.android.buildToolsVersion aaptOptions.cruncherEnabled = false aaptOptions.useNewCruncher = false packagingOptions { pickFirst "lib/armeabi/libyuvutils.so" pickFirst "lib/arm64-v8a/libyuvutils.so" pickFirst "lib/armeabi-v7a/libyuvutils.so" pickFirst "lib/armeabi/libyuvtools.so" pickFirst "lib/arm64-v8a/libyuvtools.so" pickFirst "lib/armeabi-v7a/libyuvtools.so" exclude "lib/arm64-v8a/libmmcv_api_handgesture.so" exclude "lib/arm64-v8a/libmmcv_api_express.so" exclude "lib/arm64-v8a/libMediaEncoder.so" exclude "lib/arm64-v8a/libarcore_sdk_c.so" exclude "lib/arm64-v8a/libmediadecoder.so" exclude "lib/arm64-v8a/libMediaMuxer.so" exclude "lib/arm64-v8a/libarcore_sdk_jni.so" exclude "lib/arm64-v8a/libMediaUtils.so" exclude "lib/arm64-v8a/libcosmosffmpeg.so" } defaultConfig { minSdkVersion rootProject.ext.android.minSdkVersion targetSdkVersion rootProject.ext.android.targetSdkVersion versionCode rootProject.ext.android.versionCode versionName rootProject.ext.android.versionName manifestPlaceholders = rootProject.ext.manifestPlaceholders ndk { abiFilters "armeabi-v7a", "arm64-v8a" } javaCompileOptions { annotationProcessorOptions { arguments = [AROUTER_MODULE_NAME: project.getName()] } } } aaptOptions { cruncherEnabled = false useNewCruncher = false } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } kotlinOptions { allWarningsAsErrors = true } compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 } } repositories { flatDir { dirs 'libs', '../libs' } mavenCentral() } dependencies { implementation 'androidx.constraintlayout:constraintlayout:2.0.0' implementation fileTree(dir: 'libs', include: ['*.jar', '*.aar']) implementation (name:'../libs/beautysdk-202202241203',ext:'aar') implementation (name:'../libs/library-release',ext:'aar') //socket.io implementation('io.socket:socket.io-client:1.0.0') { exclude group: 'org.json', module: 'json' } //common api project(path: ':common') // api project(path:':FaceUnity')//新娱美颜 annotationProcessor rootProject.ext.dependencies["arouter-compiler"] //工具 api rootProject.ext.dependencies["blank-utilcode"] implementation 'com.eightbitlab:blurview:1.6.6' implementation 'com.google.code.gson:gson:2.8.6' implementation "com.getkeepsafe.relinker:relinker:1.4.4" } apply plugin: 'com.android.library' apply plugin: 'img-optimizer' apply plugin: 'kotlin-android' android { compileSdkVersion rootProject.ext.android.compileSdkVersion buildToolsVersion rootProject.ext.android.buildToolsVersion aaptOptions.cruncherEnabled = false aaptOptions.useNewCruncher = false packagingOptions { pickFirst "lib/armeabi/libyuvutils.so" pickFirst "lib/arm64-v8a/libyuvutils.so" pickFirst "lib/armeabi-v7a/libyuvutils.so" pickFirst "lib/armeabi/libyuvtools.so" pickFirst "lib/arm64-v8a/libyuvtools.so" pickFirst "lib/armeabi-v7a/libyuvtools.so" exclude "lib/arm64-v8a/libmmcv_api_handgesture.so" exclude "lib/arm64-v8a/libmmcv_api_express.so" exclude "lib/arm64-v8a/libMediaEncoder.so" exclude "lib/arm64-v8a/libarcore_sdk_c.so" exclude "lib/arm64-v8a/libmediadecoder.so" exclude "lib/arm64-v8a/libMediaMuxer.so" exclude "lib/arm64-v8a/libarcore_sdk_jni.so" exclude "lib/arm64-v8a/libMediaUtils.so" exclude "lib/arm64-v8a/libcosmosffmpeg.so" } defaultConfig { minSdkVersion rootProject.ext.android.minSdkVersion targetSdkVersion rootProject.ext.android.targetSdkVersion versionCode rootProject.ext.android.versionCode versionName rootProject.ext.android.versionName manifestPlaceholders = rootProject.ext.manifestPlaceholders ndk { abiFilters "armeabi-v7a", "arm64-v8a" } javaCompileOptions { annotationProcessorOptions { arguments = [AROUTER_MODULE_NAME: project.getName()] } } } aaptOptions { cruncherEnabled = false useNewCruncher = false } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } kotlinOptions { allWarningsAsErrors = true } compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 } } repositories { flatDir { dirs 'libs', '../libs' } mavenCentral() } dependencies { implementation 'androidx.constraintlayout:constraintlayout:2.0.0' implementation fileTree(dir: 'libs', include: ['*.jar', '*.aar']) implementation (name:'../libs/beautysdk-202202241203',ext:'aar') implementation (name:'../libs/svgaplayer-release-v1.1',ext:'aar') //socket.io implementation('io.socket:socket.io-client:1.0.0') { exclude group: 'org.json', module: 'json' } //common api project(path: ':common') // api project(path:':FaceUnity')//新娱美颜 annotationProcessor rootProject.ext.dependencies["arouter-compiler"] //工具 api rootProject.ext.dependencies["blank-utilcode"] implementation 'com.eightbitlab:blurview:1.6.6' implementation 'com.google.code.gson:gson:2.8.6' implementation "com.getkeepsafe.relinker:relinker:1.4.4" }

View File

@ -34,6 +34,7 @@ import com.yunbao.common.interfaces.KeyBoardHeightChangeListener;
import com.yunbao.common.utils.KeyBoardHeightUtil2; import com.yunbao.common.utils.KeyBoardHeightUtil2;
import com.yunbao.common.utils.L; import com.yunbao.common.utils.L;
import com.yunbao.common.utils.ProcessImageUtil; import com.yunbao.common.utils.ProcessImageUtil;
import com.yunbao.common.utils.SVGAViewUtils;
import com.yunbao.common.utils.ToastUtil; import com.yunbao.common.utils.ToastUtil;
import com.yunbao.common.utils.WordUtil; import com.yunbao.common.utils.WordUtil;
import com.yunbao.common.utils.formatBigNum; import com.yunbao.common.utils.formatBigNum;
@ -103,7 +104,7 @@ import java.util.Objects;
public abstract class LiveActivity extends AbsActivity implements SocketMessageListener, LiveShareDialogFragment.ActionListener, KeyBoardHeightChangeListener { public abstract class LiveActivity extends AbsActivity implements SocketMessageListener, LiveShareDialogFragment.ActionListener, KeyBoardHeightChangeListener {
public static ViewGroup mContainer; public ViewGroup mContainer;
protected ViewGroup mPageContainer; protected ViewGroup mPageContainer;
protected LiveRoomViewHolder mLiveRoomViewHolder; protected LiveRoomViewHolder mLiveRoomViewHolder;
protected AbsLiveViewHolder mLiveBottomViewHolder; protected AbsLiveViewHolder mLiveBottomViewHolder;
@ -1520,6 +1521,7 @@ public abstract class LiveActivity extends AbsActivity implements SocketMessageL
mLiveLuckGiftTipViewHolder = null; mLiveLuckGiftTipViewHolder = null;
// mMobShareUtil = null; // mMobShareUtil = null;
mImageUtil = null; mImageUtil = null;
SVGAViewUtils.clearSVGA();
L.e("LiveActivity--------release------>"); L.e("LiveActivity--------release------>");
Constants.isSend = "0"; Constants.isSend = "0";

View File

@ -172,6 +172,7 @@ public class LiveRyAnchorActivity extends LiveActivity implements LiveFunctionCl
mBeautySdkType = CommonAppConfig.getInstance().getBeautySdkType(); mBeautySdkType = CommonAppConfig.getInstance().getBeautySdkType();
mLivePushViewHolder = new LivePushRyViewHolder(mContext, (ViewGroup) findViewById(R.id.preview_container)); mLivePushViewHolder = new LivePushRyViewHolder(mContext, (ViewGroup) findViewById(R.id.preview_container));
mLivePushViewHolder.setLiveActivityContainer(mContainer);
mLivePushViewHolder.addToParent(); mLivePushViewHolder.addToParent();
mLivePushViewHolder.subscribeActivityLifeCycle(); mLivePushViewHolder.subscribeActivityLifeCycle();

View File

@ -102,6 +102,8 @@ public class LivePushRyViewHolder extends AbsRyLivePushViewHolder implements ITX
public static RCRTCRoom rtcRoom; public static RCRTCRoom rtcRoom;
public static RCRTCLiveInfo rcrtcLiveInfo; public static RCRTCLiveInfo rcrtcLiveInfo;
private ViewGroup liveActivityContainer;
public LivePushRyViewHolder(Context context, ViewGroup parentView) { public LivePushRyViewHolder(Context context, ViewGroup parentView) {
super(context, parentView); super(context, parentView);
this.contexts = context; this.contexts = context;
@ -112,6 +114,9 @@ public class LivePushRyViewHolder extends AbsRyLivePushViewHolder implements ITX
return R.layout.view_live_push_ry; return R.layout.view_live_push_ry;
} }
public void setLiveActivityContainer(ViewGroup liveActivityContainer) {
this.liveActivityContainer = liveActivityContainer;
}
/** /**
* 主房间事件监听 * 主房间事件监听
@ -194,7 +199,7 @@ public class LivePushRyViewHolder extends AbsRyLivePushViewHolder implements ITX
if (mLiveRyLinkMicPkPresenter != null) { if (mLiveRyLinkMicPkPresenter != null) {
mLiveRyLinkMicPkPresenter.onLinkDRMicPkApply(userBean); mLiveRyLinkMicPkPresenter.onLinkDRMicPkApply(userBean);
} else { } else {
mLiveRyLinkMicPkPresenter = new LiveRyLinkMicPkPresenter(mContext, mLivePushViewHolder, true, LiveActivity.mContainer); mLiveRyLinkMicPkPresenter = new LiveRyLinkMicPkPresenter(mContext, mLivePushViewHolder, true, liveActivityContainer);
mLiveRyLinkMicPkPresenter.onLinkDRMicPkApply(userBean); mLiveRyLinkMicPkPresenter.onLinkDRMicPkApply(userBean);
} }
} else if (extra.equals("LiveDRPK1")) { } else if (extra.equals("LiveDRPK1")) {

View File

@ -66,7 +66,7 @@ dependencies {
implementation 'androidx.constraintlayout:constraintlayout:1.1.3' implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation fileTree(include: ['*.jar'], dir: 'libs') implementation fileTree(include: ['*.jar'], dir: 'libs')
compileOnly files('../libs/beautysdk-202202241203.aar') compileOnly files('../libs/beautysdk-202202241203.aar')
compileOnly files('../libs/library-release.aar') compileOnly files('../libs/svgaplayer-release-v1.1.aar')
// //
api project(':live') api project(':live')
// //

View File

@ -544,7 +544,7 @@ public class MainListAdapter extends RefreshAdapter<ListBean> {
public void onComplete(SVGAVideoEntity videoItem) { public void onComplete(SVGAVideoEntity videoItem) {
SVGADrawable drawable = new SVGADrawable(videoItem); SVGADrawable drawable = new SVGADrawable(videoItem);
svga.setImageDrawable(drawable); svga.setImageDrawable(drawable);
svga.startAnimation(); SVGAViewUtils.playEndClear(svga,false);
} }
@Override @Override