use weak reference to activity when using threads

fixes #4366
This commit is contained in:
Daniel Gultsch 2022-09-09 19:06:37 +02:00
parent a95d0fa8d3
commit 82316d13b0
2 changed files with 66 additions and 36 deletions

View file

@ -18,6 +18,7 @@ import android.widget.Toast;
import androidx.databinding.DataBindingUtil;
import java.io.File;
import java.lang.ref.WeakReference;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;
@ -136,30 +137,41 @@ public class RecordingActivity extends Activity implements View.OnClickListener
}
}
if (saveFile) {
new Thread(
() -> {
new Thread(new Finisher(outputFileWrittenLatch, mOutputFile, this)).start();
}
}
private static class Finisher implements Runnable {
private final CountDownLatch latch;
private final File outputFile;
private final WeakReference<Activity> activityReference;
private Finisher(CountDownLatch latch, File outputFile, Activity activity) {
this.latch = latch;
this.outputFile = outputFile;
this.activityReference = new WeakReference<>(activity);
}
@Override
public void run() {
try {
if (!outputFileWrittenLatch.await(2, TimeUnit.SECONDS)) {
Log.d(
Config.LOGTAG,
"time out waiting for output file to be written");
if (!latch.await(5, TimeUnit.SECONDS)) {
Log.d(Config.LOGTAG, "time out waiting for output file to be written");
}
} catch (InterruptedException e) {
Log.d(
Config.LOGTAG,
"interrupted while waiting for output file to be written",
e);
} catch (final InterruptedException e) {
Log.d(Config.LOGTAG, "interrupted while waiting for output file to be written", e);
}
runOnUiThread(
final Activity activity = activityReference.get();
if (activity == null) {
return;
}
activity.runOnUiThread(
() -> {
setResult(
Activity.RESULT_OK,
new Intent()
.setData(Uri.fromFile(mOutputFile)));
finish();
activity.setResult(
Activity.RESULT_OK, new Intent().setData(Uri.fromFile(outputFile)));
activity.finish();
});
})
.start();
}
}

View file

@ -5,6 +5,7 @@ import static eu.siacs.conversations.utils.PermissionUtils.getFirstDenied;
import android.Manifest;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.app.PictureInPictureParams;
import android.content.ActivityNotFoundException;
import android.content.Context;
@ -297,10 +298,19 @@ public class RtpSessionActivity extends XmppActivity
}
private void checkMicrophoneAvailabilityAsync() {
new Thread(this::checkMicrophoneAvailability).start();
new Thread(new MicrophoneAvailabilityCheck(this)).start();
}
private void checkMicrophoneAvailability() {
private static class MicrophoneAvailabilityCheck implements Runnable {
private final WeakReference<Activity> activityReference;
private MicrophoneAvailabilityCheck(final Activity activity) {
this.activityReference = new WeakReference<>(activity);
}
@Override
public void run() {
final long start = SystemClock.elapsedRealtime();
final boolean isMicrophoneAvailable = AppRTCAudioManager.isMicrophoneAvailable();
final long stop = SystemClock.elapsedRealtime();
@ -308,11 +318,19 @@ public class RtpSessionActivity extends XmppActivity
if (isMicrophoneAvailable) {
return;
}
runOnUiThread(
final Activity activity = activityReference.get();
if (activity == null) {
return;
}
activity.runOnUiThread(
() ->
Toast.makeText(this, R.string.microphone_unavailable, Toast.LENGTH_LONG)
Toast.makeText(
activity,
R.string.microphone_unavailable,
Toast.LENGTH_LONG)
.show());
}
}
private void putScreenInCallMode() {
putScreenInCallMode(requireRtpConnection().getMedia());