Migrate all image file pickers to ActivityResultLauncher

startActivityForResult is deprecated and the new API is nicer. Also, we can use the same launcher types in various places.
This commit is contained in:
Torsten Grote
2021-06-25 16:56:22 -03:00
parent d662ae49ee
commit 1adf408ade
13 changed files with 149 additions and 163 deletions

View File

@@ -11,8 +11,5 @@ public interface RequestCodes {
int REQUEST_DOZE_WHITELISTING = 9;
int REQUEST_UNLOCK = 11;
int REQUEST_KEYGUARD_UNLOCK = 12;
int REQUEST_ATTACH_IMAGE = 13;
int REQUEST_SAVE_ATTACHMENT = 14;
int REQUEST_AVATAR_IMAGE = 15;
}

View File

@@ -17,7 +17,7 @@ import org.briarproject.briar.android.contact.add.nearby.AddContactState.Failed;
import org.briarproject.briar.android.contact.add.nearby.AddNearbyContactViewModel.BluetoothDecision;
import org.briarproject.briar.android.fragment.BaseFragment;
import org.briarproject.briar.android.fragment.BaseFragment.BaseFragmentListener;
import org.briarproject.briar.android.util.RequestBluetoothDiscoverable;
import org.briarproject.briar.android.util.ActivityLaunchers.RequestBluetoothDiscoverable;
import java.util.logging.Logger;

View File

@@ -14,7 +14,7 @@ import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault;
import org.briarproject.briar.R;
import org.briarproject.briar.android.activity.BaseActivity;
import org.briarproject.briar.android.contact.ContactItem;
import org.briarproject.briar.android.util.RequestBluetoothDiscoverable;
import org.briarproject.briar.android.util.ActivityLaunchers.RequestBluetoothDiscoverable;
import javax.inject.Inject;

View File

@@ -4,6 +4,7 @@ import android.annotation.SuppressLint;
import android.content.DialogInterface;
import android.content.Intent;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Bundle;
import android.os.Parcelable;
import android.transition.Slide;
@@ -54,6 +55,8 @@ import org.briarproject.briar.android.fragment.BaseFragment.BaseFragmentListener
import org.briarproject.briar.android.introduction.IntroductionActivity;
import org.briarproject.briar.android.privategroup.conversation.GroupActivity;
import org.briarproject.briar.android.removabledrive.RemovableDriveActivity;
import org.briarproject.briar.android.util.ActivityLaunchers.GetImageAdvanced;
import org.briarproject.briar.android.util.ActivityLaunchers.GetMultipleImagesAdvanced;
import org.briarproject.briar.android.util.BriarSnackbarBuilder;
import org.briarproject.briar.android.view.BriarRecyclerView;
import org.briarproject.briar.android.view.ImagePreview;
@@ -92,6 +95,7 @@ import java.util.logging.Logger;
import javax.inject.Inject;
import androidx.activity.result.ActivityResultLauncher;
import androidx.annotation.Nullable;
import androidx.annotation.UiThread;
import androidx.appcompat.app.AlertDialog;
@@ -121,6 +125,7 @@ import static android.widget.Toast.LENGTH_SHORT;
import static androidx.core.app.ActivityOptionsCompat.makeSceneTransitionAnimation;
import static androidx.lifecycle.Lifecycle.State.STARTED;
import static androidx.recyclerview.widget.SortedList.INVALID_POSITION;
import static java.util.Collections.singletonList;
import static java.util.Collections.sort;
import static java.util.Objects.requireNonNull;
import static java.util.logging.Level.INFO;
@@ -132,7 +137,6 @@ import static org.briarproject.bramble.util.LogUtils.now;
import static org.briarproject.bramble.util.StringUtils.fromHexString;
import static org.briarproject.bramble.util.StringUtils.isNullOrEmpty;
import static org.briarproject.bramble.util.StringUtils.join;
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_ATTACH_IMAGE;
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_INTRODUCTION;
import static org.briarproject.briar.android.conversation.ImageActivity.ATTACHMENTS;
import static org.briarproject.briar.android.conversation.ImageActivity.ATTACHMENT_POSITION;
@@ -192,6 +196,12 @@ public class ConversationActivity extends BriarActivity
requireNonNull(name);
loadMessages();
};
private final ActivityResultLauncher<String> launcher = SDK_INT >= 18 ?
registerForActivityResult(new GetMultipleImagesAdvanced(),
this::onImagesChosen) :
registerForActivityResult(new GetImageAdvanced(), uri -> {
if (uri != null) onImagesChosen(singletonList(uri));
});
private AttachmentRetriever attachmentRetriever;
private ConversationViewModel viewModel;
@@ -314,9 +324,6 @@ public class ConversationActivity extends BriarActivity
.make(list, R.string.introduction_sent,
Snackbar.LENGTH_SHORT)
.show();
} else if (request == REQUEST_ATTACH_IMAGE && result == RESULT_OK) {
// TODO: remove cast when removing feature flag
((TextAttachmentController) sendController).onImageReceived(data);
}
}
@@ -769,8 +776,13 @@ public class ConversationActivity extends BriarActivity
}
@Override
public void onAttachImage(Intent intent) {
startActivityForResult(intent, REQUEST_ATTACH_IMAGE);
public void onAttachImageClicked() {
launcher.launch("image/*");
}
private void onImagesChosen(@Nullable List<Uri> uris) {
// TODO: remove cast when removing feature flag
((TextAttachmentController) sendController).onImageReceived(uris);
}
@Override

View File

@@ -2,6 +2,7 @@ package org.briarproject.briar.android.conversation;
import android.content.DialogInterface.OnClickListener;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.transition.Fade;
import android.transition.Transition;
@@ -21,6 +22,7 @@ import org.briarproject.briar.R;
import org.briarproject.briar.android.activity.ActivityComponent;
import org.briarproject.briar.android.activity.BriarActivity;
import org.briarproject.briar.android.attachment.AttachmentItem;
import org.briarproject.briar.android.util.ActivityLaunchers.CreateDocumentAdvanced;
import org.briarproject.briar.android.util.BriarSnackbarBuilder;
import org.briarproject.briar.android.view.PullDownLayout;
@@ -28,6 +30,7 @@ import java.util.List;
import javax.inject.Inject;
import androidx.activity.result.ActivityResultLauncher;
import androidx.annotation.Nullable;
import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AlertDialog.Builder;
@@ -38,9 +41,6 @@ import androidx.fragment.app.FragmentStatePagerAdapter;
import androidx.lifecycle.ViewModelProvider;
import androidx.viewpager.widget.ViewPager;
import static android.content.Intent.ACTION_CREATE_DOCUMENT;
import static android.content.Intent.CATEGORY_OPENABLE;
import static android.content.Intent.EXTRA_TITLE;
import static android.graphics.Color.TRANSPARENT;
import static android.os.Build.VERSION.SDK_INT;
import static android.view.View.GONE;
@@ -51,7 +51,6 @@ import static android.view.View.VISIBLE;
import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
import static com.google.android.material.snackbar.Snackbar.LENGTH_LONG;
import static java.util.Objects.requireNonNull;
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_SAVE_ATTACHMENT;
import static org.briarproject.briar.android.util.UiUtils.formatDateAbsolute;
import static org.briarproject.briar.android.util.UiUtils.getDialogIcon;
@@ -80,6 +79,10 @@ public class ImageActivity extends BriarActivity
private List<AttachmentItem> attachments;
private MessageId conversationMessageId;
private final ActivityResultLauncher<String> launcher =
registerForActivityResult(new CreateDocumentAdvanced(),
this::onImageUriSelected);
@Override
public void injectActivity(ActivityComponent component) {
component.inject(this);
@@ -177,16 +180,6 @@ public class ImageActivity extends BriarActivity
layout.getViewTreeObserver().removeOnGlobalLayoutListener(this);
}
@Override
protected void onActivityResult(int request, int result,
@Nullable Intent data) {
super.onActivityResult(request, result, data);
if (request == REQUEST_SAVE_ATTACHMENT && result == RESULT_OK &&
data != null) {
viewModel.saveImage(getVisibleAttachment(), data.getData());
}
}
@Override
public void onPullStart() {
appBarLayout.animate()
@@ -270,8 +263,9 @@ public class ImageActivity extends BriarActivity
private void showSaveImageDialog() {
OnClickListener okListener = (dialog, which) -> {
if (SDK_INT >= 19) {
Intent intent = getCreationIntent();
startActivityForResult(intent, REQUEST_SAVE_ATTACHMENT);
String name = viewModel.getFileName() + "." +
getVisibleAttachment().getExtension();
launcher.launch(name);
} else {
viewModel.saveImage(getVisibleAttachment());
}
@@ -285,13 +279,9 @@ public class ImageActivity extends BriarActivity
builder.show();
}
@RequiresApi(api = 19)
private Intent getCreationIntent() {
Intent intent = new Intent(ACTION_CREATE_DOCUMENT);
intent.addCategory(CATEGORY_OPENABLE);
intent.setType(getVisibleAttachment().getMimeType());
intent.putExtra(EXTRA_TITLE, viewModel.getFileName());
return intent;
private void onImageUriSelected(@Nullable Uri uri) {
if (uri == null) return;
viewModel.saveImage(getVisibleAttachment(), uri);
}
private void onImageSaveStateChanged(@Nullable Boolean error) {

View File

@@ -33,7 +33,6 @@ import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.concurrent.Executor;
import java.util.logging.Logger;
@@ -45,6 +44,7 @@ import androidx.annotation.UiThread;
import static android.media.MediaScannerConnection.scanFile;
import static android.os.Environment.DIRECTORY_PICTURES;
import static android.os.Environment.getExternalStoragePublicDirectory;
import static java.util.Locale.US;
import static java.util.Objects.requireNonNull;
import static java.util.logging.Level.WARNING;
import static java.util.logging.Logger.getLogger;
@@ -111,7 +111,7 @@ public class ImageViewModel extends DbViewModel implements EventListener {
}
@UiThread
public void expectAttachments(List<AttachmentItem> attachments) {
void expectAttachments(List<AttachmentItem> attachments) {
for (AttachmentItem item : attachments) {
// no need to track items that are in a final state already
if (item.getState().isFinal()) continue;
@@ -226,8 +226,7 @@ public class ImageViewModel extends DbViewModel implements EventListener {
}
String getFileName() {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd",
Locale.getDefault());
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HHmmss", US);
return sdf.format(new Date());
}

View File

@@ -1,7 +1,6 @@
package org.briarproject.briar.android.removabledrive;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.view.LayoutInflater;
@@ -15,11 +14,11 @@ import android.widget.Toast;
import org.briarproject.bramble.api.nullsafety.MethodsNotNullByDefault;
import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault;
import org.briarproject.briar.R;
import org.briarproject.briar.android.util.ActivityLaunchers.GetContentAdvanced;
import javax.inject.Inject;
import androidx.activity.result.ActivityResultLauncher;
import androidx.activity.result.contract.ActivityResultContracts.GetContent;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
@@ -28,7 +27,6 @@ import androidx.lifecycle.ViewModelProvider;
import static android.view.View.VISIBLE;
import static android.widget.Toast.LENGTH_LONG;
import static org.briarproject.briar.android.AppModule.getAndroidComponent;
import static org.briarproject.briar.android.util.UiUtils.putShowAdvancedExtra;
@MethodsNotNullByDefault
@ParametersNotNullByDefault
@@ -36,22 +34,9 @@ public class ReceiveFragment extends Fragment {
final static String TAG = ReceiveFragment.class.getName();
private static class GetFile extends GetContent {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
return i;
}
}
// TODO we can pass an extra named DocumentsContract.EXTRA_INITIAL_URI
// to have the file-picker start on the usb-stick -- if get hold of URI
// of the same. USB manager API?
// Overall, passing this extra requires extending the ready-made
// contracts and overriding createIntent.
private final ActivityResultLauncher<String> launcher =
registerForActivityResult(new GetFile(), this::onDocumentChosen);
registerForActivityResult(new GetContentAdvanced(),
this::onDocumentChosen);
@Inject
ViewModelProvider.Factory viewModelFactory;

View File

@@ -1,7 +1,6 @@
package org.briarproject.briar.android.removabledrive;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.view.LayoutInflater;
@@ -16,11 +15,11 @@ import org.briarproject.bramble.api.nullsafety.MethodsNotNullByDefault;
import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault;
import org.briarproject.bramble.api.plugin.file.RemovableDriveTask;
import org.briarproject.briar.R;
import org.briarproject.briar.android.util.ActivityLaunchers.CreateDocumentAdvanced;
import javax.inject.Inject;
import androidx.activity.result.ActivityResultLauncher;
import androidx.activity.result.contract.ActivityResultContracts.CreateDocument;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
@@ -30,7 +29,6 @@ import static android.os.Build.VERSION.SDK_INT;
import static android.view.View.VISIBLE;
import static android.widget.Toast.LENGTH_LONG;
import static org.briarproject.briar.android.AppModule.getAndroidComponent;
import static org.briarproject.briar.android.util.UiUtils.putShowAdvancedExtra;
@MethodsNotNullByDefault
@ParametersNotNullByDefault
@@ -38,15 +36,6 @@ public class SendFragment extends Fragment {
final static String TAG = SendFragment.class.getName();
private static class CreateDocumentAdvanced extends CreateDocument {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
return i;
}
}
private final ActivityResultLauncher<String> launcher =
registerForActivityResult(new CreateDocumentAdvanced(),
this::onDocumentCreated);

View File

@@ -1,7 +1,6 @@
package org.briarproject.briar.android.settings;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.view.View;
@@ -9,9 +8,11 @@ import android.view.View;
import org.briarproject.bramble.api.nullsafety.MethodsNotNullByDefault;
import org.briarproject.bramble.api.nullsafety.ParametersNotNullByDefault;
import org.briarproject.briar.R;
import org.briarproject.briar.android.util.ActivityLaunchers.GetImageAdvanced;
import javax.inject.Inject;
import androidx.activity.result.ActivityResultLauncher;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.DialogFragment;
@@ -20,12 +21,9 @@ import androidx.preference.Preference;
import androidx.preference.PreferenceFragmentCompat;
import androidx.preference.PreferenceGroup;
import static android.app.Activity.RESULT_OK;
import static java.util.Objects.requireNonNull;
import static org.briarproject.briar.android.AppModule.getAndroidComponent;
import static org.briarproject.briar.android.TestingConstants.IS_DEBUG_BUILD;
import static org.briarproject.briar.android.activity.RequestCodes.REQUEST_AVATAR_IMAGE;
import static org.briarproject.briar.android.util.UiUtils.createSelectImageIntent;
import static org.briarproject.briar.android.util.UiUtils.triggerFeedback;
@MethodsNotNullByDefault
@@ -45,6 +43,10 @@ public class SettingsFragment extends PreferenceFragmentCompat {
private SettingsViewModel viewModel;
private AvatarPreference prefAvatar;
private final ActivityResultLauncher<String> launcher =
registerForActivityResult(new GetImageAdvanced(),
this::onImageSelected);
@Override
public void onAttach(@NonNull Context context) {
super.onAttach(context);
@@ -60,8 +62,7 @@ public class SettingsFragment extends PreferenceFragmentCompat {
prefAvatar = requireNonNull(findPreference(PREF_KEY_AVATAR));
if (viewModel.shouldEnableProfilePictures()) {
prefAvatar.setOnPreferenceClickListener(preference -> {
Intent intent = createSelectImageIntent(false);
startActivityForResult(intent, REQUEST_AVATAR_IMAGE);
launcher.launch("image/*");
return true;
});
} else {
@@ -102,20 +103,11 @@ public class SettingsFragment extends PreferenceFragmentCompat {
requireActivity().setTitle(R.string.settings_button);
}
@Override
public void onActivityResult(int request, int result,
@Nullable Intent data) {
super.onActivityResult(request, result, data);
if (request == REQUEST_AVATAR_IMAGE && result == RESULT_OK) {
if (data == null) return;
Uri uri = data.getData();
if (uri == null) return;
DialogFragment dialog =
ConfirmAvatarDialogFragment.newInstance(uri);
dialog.show(getParentFragmentManager(),
ConfirmAvatarDialogFragment.TAG);
}
private void onImageSelected(@Nullable Uri uri) {
if (uri == null) return;
DialogFragment dialog = ConfirmAvatarDialogFragment.newInstance(uri);
dialog.show(getParentFragmentManager(),
ConfirmAvatarDialogFragment.TAG);
}
}

View File

@@ -0,0 +1,88 @@
package org.briarproject.briar.android.util;
import android.annotation.TargetApi;
import android.content.Context;
import android.content.Intent;
import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import androidx.activity.result.contract.ActivityResultContract;
import androidx.activity.result.contract.ActivityResultContracts.CreateDocument;
import androidx.activity.result.contract.ActivityResultContracts.GetContent;
import androidx.activity.result.contract.ActivityResultContracts.GetMultipleContents;
import androidx.annotation.Nullable;
import static android.app.Activity.RESULT_CANCELED;
import static android.bluetooth.BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE;
import static android.bluetooth.BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION;
import static android.content.Intent.EXTRA_MIME_TYPES;
import static android.os.Build.VERSION.SDK_INT;
import static org.briarproject.bramble.util.AndroidUtils.getSupportedImageContentTypes;
@NotNullByDefault
public class ActivityLaunchers {
public static class CreateDocumentAdvanced extends CreateDocument {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
return i;
}
}
public static class GetContentAdvanced extends GetContent {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
return i;
}
}
public static class GetImageAdvanced extends GetContent {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
i.setType("image/*");
if (SDK_INT >= 19)
i.putExtra(EXTRA_MIME_TYPES, getSupportedImageContentTypes());
return i;
}
}
@TargetApi(18)
public static class GetMultipleImagesAdvanced extends GetMultipleContents {
@Override
public Intent createIntent(Context context, String input) {
Intent i = super.createIntent(context, input);
putShowAdvancedExtra(i);
i.setType("image/*");
if (SDK_INT >= 19)
i.putExtra(EXTRA_MIME_TYPES, getSupportedImageContentTypes());
return i;
}
}
public static class RequestBluetoothDiscoverable
extends ActivityResultContract<Integer, Boolean> {
@Override
public Intent createIntent(Context context, Integer duration) {
Intent i = new Intent(ACTION_REQUEST_DISCOVERABLE);
i.putExtra(EXTRA_DISCOVERABLE_DURATION, duration);
return i;
}
@Override
public Boolean parseResult(int resultCode, @Nullable Intent intent) {
return resultCode != RESULT_CANCELED;
}
}
private static void putShowAdvancedExtra(Intent i) {
i.putExtra(SDK_INT <= 28 ? "android.content.extra.SHOW_ADVANCED" :
"android.provider.extra.SHOW_ADVANCED", true);
}
}

View File

@@ -1,31 +0,0 @@
package org.briarproject.briar.android.util;
import android.content.Context;
import android.content.Intent;
import org.briarproject.bramble.api.nullsafety.NotNullByDefault;
import androidx.activity.result.contract.ActivityResultContract;
import androidx.annotation.Nullable;
import static android.app.Activity.RESULT_CANCELED;
import static android.bluetooth.BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE;
import static android.bluetooth.BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION;
@NotNullByDefault
public class RequestBluetoothDiscoverable
extends ActivityResultContract<Integer, Boolean> {
@Override
public Intent createIntent(Context context, Integer duration) {
Intent i = new Intent(ACTION_REQUEST_DISCOVERABLE);
i.putExtra(EXTRA_DISCOVERABLE_DURATION, duration);
return i;
}
@Override
public Boolean parseResult(int resultCode, @Nullable Intent intent) {
return resultCode != RESULT_CANCELED;
}
}

View File

@@ -67,12 +67,7 @@ import androidx.vectordrawable.graphics.drawable.VectorDrawableCompat;
import static android.content.Context.KEYGUARD_SERVICE;
import static android.content.Context.POWER_SERVICE;
import static android.content.Intent.ACTION_GET_CONTENT;
import static android.content.Intent.ACTION_OPEN_DOCUMENT;
import static android.content.Intent.CATEGORY_DEFAULT;
import static android.content.Intent.CATEGORY_OPENABLE;
import static android.content.Intent.EXTRA_ALLOW_MULTIPLE;
import static android.content.Intent.EXTRA_MIME_TYPES;
import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
import static android.os.Build.MANUFACTURER;
import static android.os.Build.VERSION.SDK_INT;
@@ -107,7 +102,6 @@ import static androidx.core.view.ViewCompat.LAYOUT_DIRECTION_RTL;
import static java.util.Objects.requireNonNull;
import static java.util.concurrent.TimeUnit.DAYS;
import static java.util.logging.Level.WARNING;
import static org.briarproject.bramble.util.AndroidUtils.getSupportedImageContentTypes;
import static org.briarproject.bramble.util.LogUtils.logException;
import static org.briarproject.briar.BuildConfig.APPLICATION_ID;
import static org.briarproject.briar.android.TestingConstants.EXPIRY_DATE;
@@ -310,18 +304,6 @@ public class UiUtils {
};
}
public static Intent createSelectImageIntent(boolean allowMultiple) {
Intent intent = new Intent(SDK_INT >= 19 ?
ACTION_OPEN_DOCUMENT : ACTION_GET_CONTENT);
intent.setType("image/*");
intent.addCategory(CATEGORY_OPENABLE);
if (SDK_INT >= 19)
intent.putExtra(EXTRA_MIME_TYPES, getSupportedImageContentTypes());
if (allowMultiple && SDK_INT >= 18)
intent.putExtra(EXTRA_ALLOW_MULTIPLE, true);
return intent;
}
public static void showOnboardingDialog(Context ctx, String text) {
new AlertDialog.Builder(ctx, R.style.OnboardingDialogTheme)
.setMessage(text)

View File

@@ -1,7 +1,6 @@
package org.briarproject.briar.android.view;
import android.app.Activity;
import android.content.ClipData;
import android.content.Context;
import android.content.Intent;
import android.graphics.drawable.Drawable;
@@ -15,13 +14,13 @@ import org.briarproject.briar.R;
import org.briarproject.briar.android.attachment.AttachmentItemResult;
import org.briarproject.briar.android.attachment.AttachmentManager;
import org.briarproject.briar.android.attachment.AttachmentResult;
import org.briarproject.briar.android.util.UiUtils;
import org.briarproject.briar.android.view.ImagePreview.ImagePreviewListener;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import androidx.activity.result.ActivityResultLauncher;
import androidx.annotation.Nullable;
import androidx.annotation.UiThread;
import androidx.appcompat.app.AlertDialog.Builder;
@@ -31,7 +30,6 @@ import androidx.lifecycle.Observer;
import androidx.vectordrawable.graphics.drawable.VectorDrawableCompat;
import uk.co.samuelwall.materialtaptargetprompt.MaterialTapTargetPrompt;
import static android.os.Build.VERSION.SDK_INT;
import static android.view.View.GONE;
import static android.widget.Toast.LENGTH_LONG;
import static androidx.core.content.ContextCompat.getColor;
@@ -143,38 +141,23 @@ public class TextAttachmentController extends TextSendController
builder.show();
return;
}
Intent intent = UiUtils.createSelectImageIntent(true);
if (attachmentListener.getLifecycle().getCurrentState() != DESTROYED) {
attachmentListener.onAttachImage(intent);
attachmentListener.onAttachImageClicked();
}
}
/**
* This is called with the result Intent returned by the Activity started
* with {@link UiUtils#createSelectImageIntent(boolean)}.
* <p>
* This method must be called at most once per call to
* {@link AttachmentListener#onAttachImage(Intent)}.
* Normally, this is true if called from
* {@link AttachmentListener#onAttachImageClicked()}.
* Normally, this is true if called from the launcher equivalent of
* {@link Activity#onActivityResult(int, int, Intent)} since this is called
* at most once per call to
* {@link Activity#startActivityForResult(Intent, int)}.
* at most once per call to {@link ActivityResultLauncher#launch(Object)}.
*/
@SuppressWarnings("JavadocReference")
public void onImageReceived(@Nullable Intent resultData) {
if (resultData == null) return;
public void onImageReceived(@Nullable List<Uri> newUris) {
if (newUris == null) return;
if (loadingUris || !imageUris.isEmpty()) throw new AssertionError();
List<Uri> newUris = new ArrayList<>();
if (resultData.getData() != null) {
newUris.add(resultData.getData());
onNewUris(false, newUris);
} else if (SDK_INT >= 18 && resultData.getClipData() != null) {
ClipData clipData = resultData.getClipData();
for (int i = 0; i < clipData.getItemCount(); i++) {
newUris.add(clipData.getItemAt(i).getUri());
}
onNewUris(false, newUris);
}
onNewUris(false, newUris);
}
private void onNewUris(boolean restart, List<Uri> newUris) {
@@ -329,7 +312,7 @@ public class TextAttachmentController extends TextSendController
@UiThread
public interface AttachmentListener extends SendListener {
void onAttachImage(Intent intent);
void onAttachImageClicked();
void onTooManyAttachments();
}