Mark various SysUI PendingIntent sends "interactive"

Bug: 251902289
Test: atest SystemUITests
Change-Id: I97057d682de7245149d03e1f64730082f138ed9a
This commit is contained in:
Christopher Tate
2022-11-08 16:34:47 -08:00
parent e36b1ca477
commit a09944f75e
12 changed files with 63 additions and 12 deletions

View File

@@ -832,6 +832,20 @@ public final class PendingIntent implements Parcelable {
send(context, code, intent, null, null, null, null);
}
/**
* Perform the operation associated with this PendingIntent, supplying additional
* options for the operation.
*
* @param options Additional options the caller would like to provide to modify the
* sending behavior. May be built from an {@link ActivityOptions} to apply to an
* activity start.
*
* @hide
*/
public void send(Bundle options) throws CanceledException {
send(null, 0, null, null, null, null, options);
}
/**
* Perform the operation associated with this PendingIntent, allowing the
* caller to be notified when the send has completed.

View File

@@ -17,6 +17,7 @@
package com.android.systemui.plugins;
import android.annotation.Nullable;
import android.app.BroadcastOptions;
import android.app.PendingIntent;
import android.graphics.drawable.Drawable;
import android.view.View;
@@ -70,7 +71,9 @@ public interface GlobalActionsPanelPlugin extends Plugin {
/** Starts a PendingIntent, dismissing the keyguard if necessary. */
default void startPendingIntentDismissingKeyguard(PendingIntent pendingIntent) {
try {
pendingIntent.send();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
pendingIntent.send(options.toBundle());
} catch (PendingIntent.CanceledException e) {
// no-op
}

View File

@@ -156,6 +156,8 @@ class DetailDialog(
// Remove the task explicitly, since onRelease() callback will be executed after
// startActivity() below is called.
broadcastSender.closeSystemDialogs()
// not sent as interactive, lest the higher-importance activity launch
// be impacted
pendingIntent.send()
false
}

View File

@@ -16,6 +16,7 @@
package com.android.systemui.media.controls.pipeline
import android.app.BroadcastOptions
import android.app.Notification
import android.app.Notification.EXTRA_SUBSTITUTE_APP_NAME
import android.app.PendingIntent
@@ -1149,7 +1150,9 @@ class MediaDataManager(
private fun sendPendingIntent(intent: PendingIntent): Boolean {
return try {
intent.send()
val options = BroadcastOptions.makeBasic()
options.setInteractive(true)
intent.send(options.toBundle())
true
} catch (e: PendingIntent.CanceledException) {
Log.d(TAG, "Intent canceled", e)

View File

@@ -23,6 +23,7 @@ import static com.android.systemui.media.controls.models.recommendation.Smartspa
import android.animation.Animator;
import android.animation.AnimatorInflater;
import android.animation.AnimatorSet;
import android.app.BroadcastOptions;
import android.app.PendingIntent;
import android.app.WallpaperColors;
import android.app.smartspace.SmartspaceAction;
@@ -113,6 +114,8 @@ import com.android.systemui.util.ColorUtilKt;
import com.android.systemui.util.animation.TransitionLayout;
import com.android.systemui.util.time.SystemClock;
import dagger.Lazy;
import java.net.URISyntaxException;
import java.util.ArrayList;
import java.util.List;
@@ -120,7 +123,6 @@ import java.util.concurrent.Executor;
import javax.inject.Inject;
import dagger.Lazy;
import kotlin.Unit;
/**
@@ -621,7 +623,9 @@ public class MediaControlPanel {
device.getIntent().getIntent(), true);
} else {
try {
device.getIntent().send();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
device.getIntent().send(options.toBundle());
} catch (PendingIntent.CanceledException e) {
Log.e(TAG, "Device pending intent was canceled");
}

View File

@@ -16,12 +16,14 @@
package com.android.systemui.screenrecord;
import android.app.BroadcastOptions;
import android.app.Dialog;
import android.app.PendingIntent;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.UserHandle;
import android.util.Log;
@@ -57,6 +59,7 @@ public class RecordingController
private boolean mIsStarting;
private boolean mIsRecording;
private PendingIntent mStopIntent;
private final Bundle mInteractiveBroadcastOption;
private CountDownTimer mCountDownTimer = null;
private final Executor mMainExecutor;
private final BroadcastDispatcher mBroadcastDispatcher;
@@ -106,6 +109,10 @@ public class RecordingController
mBroadcastDispatcher = broadcastDispatcher;
mUserContextProvider = userContextProvider;
mUserTracker = userTracker;
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
mInteractiveBroadcastOption = options.toBundle();
}
/** Create a dialog to show screen recording options to the user. */
@@ -148,7 +155,7 @@ public class RecordingController
cb.onCountdownEnd();
}
try {
startIntent.send();
startIntent.send(mInteractiveBroadcastOption);
mUserTracker.addCallback(mUserChangedCallback, mMainExecutor);
IntentFilter stateFilter = new IntentFilter(INTENT_UPDATE_STATE);
@@ -202,7 +209,7 @@ public class RecordingController
public void stopRecording() {
try {
if (mStopIntent != null) {
mStopIntent.send();
mStopIntent.send(mInteractiveBroadcastOption);
} else {
Log.e(TAG, "Stop intent was null");
}

View File

@@ -18,6 +18,7 @@ package com.android.systemui.screenshot;
import static java.util.Objects.requireNonNull;
import android.app.BroadcastOptions;
import android.app.PendingIntent;
import android.content.Context;
import android.graphics.drawable.Icon;
@@ -96,7 +97,9 @@ public class OverlayActionChip extends FrameLayout {
public void setPendingIntent(PendingIntent intent, Runnable finisher) {
setOnClickListener(v -> {
try {
intent.send();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
intent.send(options.toBundle());
finisher.run();
} catch (PendingIntent.CanceledException e) {
Log.e(TAG, "Intent cancelled", e);

View File

@@ -34,6 +34,7 @@ import android.animation.AnimatorListenerAdapter;
import android.animation.AnimatorSet;
import android.animation.ValueAnimator;
import android.app.ActivityManager;
import android.app.BroadcastOptions;
import android.app.Notification;
import android.app.PendingIntent;
import android.content.Context;
@@ -53,6 +54,7 @@ import android.graphics.drawable.Drawable;
import android.graphics.drawable.Icon;
import android.graphics.drawable.InsetDrawable;
import android.graphics.drawable.LayerDrawable;
import android.os.Bundle;
import android.os.Looper;
import android.os.RemoteException;
import android.util.AttributeSet;
@@ -169,6 +171,7 @@ public class ScreenshotView extends FrameLayout implements
private long mDefaultTimeoutOfTimeoutHandler;
private ActionIntentExecutor mActionExecutor;
private FeatureFlags mFlags;
private final Bundle mInteractiveBroadcastOption;
private enum PendingInteraction {
PREVIEW,
@@ -195,6 +198,10 @@ public class ScreenshotView extends FrameLayout implements
mResources = mContext.getResources();
mInteractionJankMonitor = getInteractionJankMonitorInstance();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
mInteractiveBroadcastOption = options.toBundle();
mFixedSize = mResources.getDimensionPixelSize(R.dimen.overlay_x_scale);
// standard material ease
@@ -1092,7 +1099,7 @@ public class ScreenshotView extends FrameLayout implements
private void startSharedTransition(ActionTransition transition) {
try {
mPendingSharedTransition = true;
transition.action.actionIntent.send();
transition.action.actionIntent.send(mInteractiveBroadcastOption);
// fade out non-preview UI
createScreenshotFadeDismissAnimation().start();

View File

@@ -121,6 +121,7 @@ public interface CentralSurfaces extends Dumpable, ActivityStarter, LifecycleOwn
options.setLaunchDisplayId(displayId);
options.setCallerDisplayId(displayId);
options.setPendingIntentBackgroundActivityLaunchAllowed(true);
options.setInteractive(true);
return options.toBundle();
}

View File

@@ -16,6 +16,7 @@
package com.android.systemui.statusbar.tv.notifications;
import android.app.BroadcastOptions;
import android.app.Notification;
import android.app.PendingIntent;
import android.service.notification.StatusBarNotification;
@@ -100,7 +101,9 @@ public class TvNotificationAdapter extends RecyclerView.Adapter<RecyclerView.Vie
public void onClick(View v) {
try {
if (mPendingIntent != null) {
mPendingIntent.send();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
mPendingIntent.send(options.toBundle());
}
} catch (PendingIntent.CanceledException e) {
Log.d(TAG, "Pending intent canceled for : " + mPendingIntent);

View File

@@ -20,6 +20,7 @@ import static com.android.systemui.wallet.ui.WalletCardCarousel.CARD_ANIM_ALPHA_
import static com.android.systemui.wallet.ui.WalletCardCarousel.CARD_ANIM_ALPHA_DURATION;
import android.annotation.Nullable;
import android.app.BroadcastOptions;
import android.app.PendingIntent;
import android.content.Context;
import android.content.res.Configuration;
@@ -303,7 +304,10 @@ public class WalletView extends FrameLayout implements WalletCardCarousel.OnCard
? mDeviceLockedActionOnClickListener
: v -> {
try {
walletCard.getPendingIntent().send();
BroadcastOptions options = BroadcastOptions.makeBasic();
options.setInteractive(true);
walletCard.getPendingIntent().send(options.toBundle());
} catch (PendingIntent.CanceledException e) {
Log.w(TAG, "Error sending pending intent for wallet card.");
}

View File

@@ -107,7 +107,7 @@ public class RecordingControllerTest extends SysuiTestCase {
mController.startCountdown(0, 0, startIntent, null);
verify(mCallback).onCountdownEnd();
verify(startIntent).send();
verify(startIntent).send(any());
}
// Test that when recording is stopped, the stop intent is sent and listeners are notified.
@@ -125,7 +125,7 @@ public class RecordingControllerTest extends SysuiTestCase {
assertFalse(mController.isStarting());
assertFalse(mController.isRecording());
verify(stopIntent).send();
verify(stopIntent).send(any());
verify(mCallback).onRecordingEnd();
}