summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/java/android/app/Activity.java10
-rw-r--r--core/java/android/app/ActivityClient.java8
-rw-r--r--core/java/android/app/ActivityThread.java17
-rw-r--r--core/java/android/app/ClientTransactionHandler.java2
-rw-r--r--core/java/android/app/IActivityClientController.aidl1
-rw-r--r--core/java/android/app/LocalActivityManager.java3
-rw-r--r--core/java/android/app/servertransaction/LaunchActivityItem.java34
-rw-r--r--core/java/android/app/servertransaction/StartActivityItem.java22
-rw-r--r--core/java/android/app/servertransaction/TransactionExecutor.java3
-rw-r--r--core/java/android/app/servertransaction/TransactionExecutorHelper.java2
-rw-r--r--core/tests/coretests/src/android/app/servertransaction/ObjectPoolTests.java18
-rw-r--r--core/tests/coretests/src/android/app/servertransaction/TestUtils.java11
-rw-r--r--core/tests/coretests/src/android/app/servertransaction/TransactionParcelTests.java10
-rw-r--r--core/tests/mockingcoretests/src/android/app/activity/ActivityThreadClientTest.java7
-rw-r--r--services/core/java/com/android/server/wm/ActivityClientController.java18
-rw-r--r--services/core/java/com/android/server/wm/ActivityRecord.java116
-rw-r--r--services/core/java/com/android/server/wm/ActivityStartController.java2
-rw-r--r--services/core/java/com/android/server/wm/ActivityStarter.java2
-rw-r--r--services/core/java/com/android/server/wm/ActivityTaskSupervisor.java11
-rw-r--r--services/core/java/com/android/server/wm/ResetTargetTaskHelper.java3
-rw-r--r--services/core/java/com/android/server/wm/Task.java9
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java30
22 files changed, 197 insertions, 142 deletions
diff --git a/core/java/android/app/Activity.java b/core/java/android/app/Activity.java
index 294a363bc52f..55df824b1243 100644
--- a/core/java/android/app/Activity.java
+++ b/core/java/android/app/Activity.java
@@ -890,6 +890,9 @@ public class Activity extends ContextThemeWrapper
@UnsupportedAppUsage
final FragmentController mFragments = FragmentController.createController(new HostCallbacks());
+ /** The options for scene transition. */
+ ActivityOptions mPendingOptions;
+
private static final class ManagedCursor {
ManagedCursor(Cursor cursor) {
mCursor = cursor;
@@ -7258,7 +7261,7 @@ public class Activity extends ContextThemeWrapper
}
/**
- * Retrieve the ActivityOptions passed in from the launching activity or passed back
+ * Takes the ActivityOptions passed in from the launching activity or passed back
* from an activity launched by this activity in its call to {@link
* #convertToTranslucent(TranslucentConversionListener, ActivityOptions)}
*
@@ -7267,7 +7270,10 @@ public class Activity extends ContextThemeWrapper
*/
@UnsupportedAppUsage
ActivityOptions getActivityOptions() {
- return ActivityOptions.fromBundle(ActivityClient.getInstance().getActivityOptions(mToken));
+ final ActivityOptions options = mPendingOptions;
+ // The option only applies once.
+ mPendingOptions = null;
+ return options;
}
/**
diff --git a/core/java/android/app/ActivityClient.java b/core/java/android/app/ActivityClient.java
index 64d795c013c9..d465b220f854 100644
--- a/core/java/android/app/ActivityClient.java
+++ b/core/java/android/app/ActivityClient.java
@@ -237,14 +237,6 @@ public class ActivityClient {
}
}
- Bundle getActivityOptions(IBinder token) {
- try {
- return getActivityClientController().getActivityOptions(token);
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
- }
-
public void setRequestedOrientation(IBinder token, int requestedOrientation) {
try {
getActivityClientController().setRequestedOrientation(token, requestedOrientation);
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index 69482bc8615b..2fe1711bdbd4 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -567,6 +567,9 @@ public final class ActivityThread extends ClientTransactionHandler {
@UnsupportedAppUsage
boolean mPreserveWindow;
+ /** The options for scene transition. */
+ ActivityOptions mActivityOptions;
+
/**
* If non-null, the activity is launching with a specified rotation, the adjustments should
* be consumed before activity creation.
@@ -587,8 +590,8 @@ public final class ActivityThread extends ClientTransactionHandler {
ActivityInfo info, Configuration overrideConfig, CompatibilityInfo compatInfo,
String referrer, IVoiceInteractor voiceInteractor, Bundle state,
PersistableBundle persistentState, List<ResultInfo> pendingResults,
- List<ReferrerIntent> pendingNewIntents, boolean isForward,
- ProfilerInfo profilerInfo, ClientTransactionHandler client,
+ List<ReferrerIntent> pendingNewIntents, ActivityOptions activityOptions,
+ boolean isForward, ProfilerInfo profilerInfo, ClientTransactionHandler client,
IBinder assistToken, FixedRotationAdjustments fixedRotationAdjustments) {
this.token = token;
this.assistToken = assistToken;
@@ -607,6 +610,7 @@ public final class ActivityThread extends ClientTransactionHandler {
this.overrideConfig = overrideConfig;
this.packageInfo = client.getPackageInfoNoCheck(activityInfo.applicationInfo,
compatInfo);
+ mActivityOptions = activityOptions;
mPendingFixedRotationAdjustments = fixedRotationAdjustments;
init();
}
@@ -3469,6 +3473,10 @@ public final class ActivityThread extends ClientTransactionHandler {
activity.setTheme(theme);
}
+ if (r.mActivityOptions != null) {
+ activity.mPendingOptions = r.mActivityOptions;
+ r.mActivityOptions = null;
+ }
activity.mCalled = false;
if (r.isPersistable()) {
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
@@ -3509,7 +3517,7 @@ public final class ActivityThread extends ClientTransactionHandler {
@Override
public void handleStartActivity(ActivityClientRecord r,
- PendingTransactionActions pendingActions) {
+ PendingTransactionActions pendingActions, ActivityOptions activityOptions) {
final Activity activity = r.activity;
if (!r.stopped) {
throw new IllegalStateException("Can't start activity that is not stopped.");
@@ -3520,6 +3528,9 @@ public final class ActivityThread extends ClientTransactionHandler {
}
unscheduleGcIdler();
+ if (activityOptions != null) {
+ activity.mPendingOptions = activityOptions;
+ }
// Start
activity.performStart("handleStartActivity");
diff --git a/core/java/android/app/ClientTransactionHandler.java b/core/java/android/app/ClientTransactionHandler.java
index ac50676ff46b..0e1c827145d2 100644
--- a/core/java/android/app/ClientTransactionHandler.java
+++ b/core/java/android/app/ClientTransactionHandler.java
@@ -164,7 +164,7 @@ public abstract class ClientTransactionHandler {
/** Perform activity start. */
public abstract void handleStartActivity(@NonNull ActivityClientRecord r,
- PendingTransactionActions pendingActions);
+ PendingTransactionActions pendingActions, ActivityOptions activityOptions);
/** Get package info. */
public abstract LoadedApk getPackageInfoNoCheck(ApplicationInfo ai,
diff --git a/core/java/android/app/IActivityClientController.aidl b/core/java/android/app/IActivityClientController.aidl
index e1e0a8a534a8..b9a203c3f0ba 100644
--- a/core/java/android/app/IActivityClientController.aidl
+++ b/core/java/android/app/IActivityClientController.aidl
@@ -60,7 +60,6 @@ interface IActivityClientController {
String getCallingPackage(in IBinder token);
int getLaunchedFromUid(in IBinder token);
String getLaunchedFromPackage(in IBinder token);
- Bundle getActivityOptions(in IBinder token);
void setRequestedOrientation(in IBinder token, int requestedOrientation);
int getRequestedOrientation(in IBinder token);
diff --git a/core/java/android/app/LocalActivityManager.java b/core/java/android/app/LocalActivityManager.java
index 2e7c9f11ac66..74e61250f109 100644
--- a/core/java/android/app/LocalActivityManager.java
+++ b/core/java/android/app/LocalActivityManager.java
@@ -178,7 +178,8 @@ public class LocalActivityManager {
pendingActions = null;
}
- mActivityThread.handleStartActivity(clientRecord, pendingActions);
+ mActivityThread.handleStartActivity(clientRecord, pendingActions,
+ null /* activityOptions */);
r.curState = STARTED;
if (desiredState == RESUMED) {
diff --git a/core/java/android/app/servertransaction/LaunchActivityItem.java b/core/java/android/app/servertransaction/LaunchActivityItem.java
index 3758cb49e2d0..73a9ceccecee 100644
--- a/core/java/android/app/servertransaction/LaunchActivityItem.java
+++ b/core/java/android/app/servertransaction/LaunchActivityItem.java
@@ -21,6 +21,7 @@ import static android.os.Trace.TRACE_TAG_ACTIVITY_MANAGER;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.app.ActivityClient;
+import android.app.ActivityOptions;
import android.app.ActivityThread.ActivityClientRecord;
import android.app.ClientTransactionHandler;
import android.app.IActivityClientController;
@@ -66,6 +67,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
private PersistableBundle mPersistentState;
private List<ResultInfo> mPendingResults;
private List<ReferrerIntent> mPendingNewIntents;
+ private ActivityOptions mActivityOptions;
private boolean mIsForward;
private ProfilerInfo mProfilerInfo;
private IBinder mAssistToken;
@@ -92,8 +94,8 @@ public class LaunchActivityItem extends ClientTransactionItem {
Trace.traceBegin(TRACE_TAG_ACTIVITY_MANAGER, "activityStart");
ActivityClientRecord r = new ActivityClientRecord(token, mIntent, mIdent, mInfo,
mOverrideConfig, mCompatInfo, mReferrer, mVoiceInteractor, mState, mPersistentState,
- mPendingResults, mPendingNewIntents, mIsForward,
- mProfilerInfo, client, mAssistToken, mFixedRotationAdjustments);
+ mPendingResults, mPendingNewIntents, mActivityOptions, mIsForward, mProfilerInfo,
+ client, mAssistToken, mFixedRotationAdjustments);
client.handleLaunchActivity(r, pendingActions, null /* customIntent */);
Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
}
@@ -114,8 +116,9 @@ public class LaunchActivityItem extends ClientTransactionItem {
Configuration curConfig, Configuration overrideConfig, CompatibilityInfo compatInfo,
String referrer, IVoiceInteractor voiceInteractor, int procState, Bundle state,
PersistableBundle persistentState, List<ResultInfo> pendingResults,
- List<ReferrerIntent> pendingNewIntents, boolean isForward, ProfilerInfo profilerInfo,
- IBinder assistToken, IActivityClientController activityClientController,
+ List<ReferrerIntent> pendingNewIntents, ActivityOptions activityOptions,
+ boolean isForward, ProfilerInfo profilerInfo, IBinder assistToken,
+ IActivityClientController activityClientController,
FixedRotationAdjustments fixedRotationAdjustments) {
LaunchActivityItem instance = ObjectPool.obtain(LaunchActivityItem.class);
if (instance == null) {
@@ -123,8 +126,8 @@ public class LaunchActivityItem extends ClientTransactionItem {
}
setValues(instance, intent, ident, info, curConfig, overrideConfig, compatInfo, referrer,
voiceInteractor, procState, state, persistentState, pendingResults,
- pendingNewIntents, isForward, profilerInfo, assistToken, activityClientController,
- fixedRotationAdjustments);
+ pendingNewIntents, activityOptions, isForward, profilerInfo, assistToken,
+ activityClientController, fixedRotationAdjustments);
return instance;
}
@@ -132,7 +135,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
@Override
public void recycle() {
setValues(this, null, 0, null, null, null, null, null, null, 0, null, null, null, null,
- false, null, null, null, null);
+ null, false, null, null, null, null);
ObjectPool.recycle(this);
}
@@ -155,6 +158,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
dest.writePersistableBundle(mPersistentState);
dest.writeTypedList(mPendingResults, flags);
dest.writeTypedList(mPendingNewIntents, flags);
+ dest.writeBundle(mActivityOptions != null ? mActivityOptions.toBundle() : null);
dest.writeBoolean(mIsForward);
dest.writeTypedObject(mProfilerInfo, flags);
dest.writeStrongBinder(mAssistToken);
@@ -172,7 +176,8 @@ public class LaunchActivityItem extends ClientTransactionItem {
in.readBundle(getClass().getClassLoader()),
in.readPersistableBundle(getClass().getClassLoader()),
in.createTypedArrayList(ResultInfo.CREATOR),
- in.createTypedArrayList(ReferrerIntent.CREATOR), in.readBoolean(),
+ in.createTypedArrayList(ReferrerIntent.CREATOR),
+ ActivityOptions.fromBundle(in.readBundle()), in.readBoolean(),
in.readTypedObject(ProfilerInfo.CREATOR),
in.readStrongBinder(),
IActivityClientController.Stub.asInterface(in.readStrongBinder()),
@@ -210,6 +215,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
&& areBundlesEqualRoughly(mPersistentState, other.mPersistentState)
&& Objects.equals(mPendingResults, other.mPendingResults)
&& Objects.equals(mPendingNewIntents, other.mPendingNewIntents)
+ && (mActivityOptions == null) == (other.mActivityOptions == null)
&& mIsForward == other.mIsForward
&& Objects.equals(mProfilerInfo, other.mProfilerInfo)
&& Objects.equals(mAssistToken, other.mAssistToken)
@@ -230,6 +236,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
result = 31 * result + getRoughBundleHashCode(mPersistentState);
result = 31 * result + Objects.hashCode(mPendingResults);
result = 31 * result + Objects.hashCode(mPendingNewIntents);
+ result = 31 * result + (mActivityOptions != null ? 1 : 0);
result = 31 * result + (mIsForward ? 1 : 0);
result = 31 * result + Objects.hashCode(mProfilerInfo);
result = 31 * result + Objects.hashCode(mAssistToken);
@@ -268,9 +275,9 @@ public class LaunchActivityItem extends ClientTransactionItem {
+ ",curConfig=" + mCurConfig + ",overrideConfig=" + mOverrideConfig
+ ",referrer=" + mReferrer + ",procState=" + mProcState + ",state=" + mState
+ ",persistentState=" + mPersistentState + ",pendingResults=" + mPendingResults
- + ",pendingNewIntents=" + mPendingNewIntents + ",profilerInfo=" + mProfilerInfo
- + ",assistToken=" + mAssistToken + ",rotationAdj=" + mFixedRotationAdjustments
- + "}";
+ + ",pendingNewIntents=" + mPendingNewIntents + ",options=" + mActivityOptions
+ + ",profilerInfo=" + mProfilerInfo + ",assistToken=" + mAssistToken
+ + ",rotationAdj=" + mFixedRotationAdjustments + "}";
}
// Using the same method to set and clear values to make sure we don't forget anything
@@ -279,8 +286,8 @@ public class LaunchActivityItem extends ClientTransactionItem {
CompatibilityInfo compatInfo, String referrer, IVoiceInteractor voiceInteractor,
int procState, Bundle state, PersistableBundle persistentState,
List<ResultInfo> pendingResults, List<ReferrerIntent> pendingNewIntents,
- boolean isForward, ProfilerInfo profilerInfo, IBinder assistToken,
- IActivityClientController activityClientController,
+ ActivityOptions activityOptions, boolean isForward, ProfilerInfo profilerInfo,
+ IBinder assistToken, IActivityClientController activityClientController,
FixedRotationAdjustments fixedRotationAdjustments) {
instance.mIntent = intent;
instance.mIdent = ident;
@@ -295,6 +302,7 @@ public class LaunchActivityItem extends ClientTransactionItem {
instance.mPersistentState = persistentState;
instance.mPendingResults = pendingResults;
instance.mPendingNewIntents = pendingNewIntents;
+ instance.mActivityOptions = activityOptions;
instance.mIsForward = isForward;
instance.mProfilerInfo = profilerInfo;
instance.mAssistToken = assistToken;
diff --git a/core/java/android/app/servertransaction/StartActivityItem.java b/core/java/android/app/servertransaction/StartActivityItem.java
index 483f9de58a1c..15f65f6d9d26 100644
--- a/core/java/android/app/servertransaction/StartActivityItem.java
+++ b/core/java/android/app/servertransaction/StartActivityItem.java
@@ -20,6 +20,7 @@ import static android.os.Trace.TRACE_TAG_ACTIVITY_MANAGER;
import android.annotation.NonNull;
import android.annotation.Nullable;
+import android.app.ActivityOptions;
import android.app.ActivityThread.ActivityClientRecord;
import android.app.ClientTransactionHandler;
import android.os.Parcel;
@@ -33,11 +34,13 @@ public class StartActivityItem extends ActivityLifecycleItem {
private static final String TAG = "StartActivityItem";
+ private ActivityOptions mActivityOptions;
+
@Override
public void execute(ClientTransactionHandler client, ActivityClientRecord r,
PendingTransactionActions pendingActions) {
Trace.traceBegin(TRACE_TAG_ACTIVITY_MANAGER, "startActivityItem");
- client.handleStartActivity(r, pendingActions);
+ client.handleStartActivity(r, pendingActions, mActivityOptions);
Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
}
@@ -52,11 +55,12 @@ public class StartActivityItem extends ActivityLifecycleItem {
private StartActivityItem() {}
/** Obtain an instance initialized with provided params. */
- public static StartActivityItem obtain() {
+ public static StartActivityItem obtain(ActivityOptions activityOptions) {
StartActivityItem instance = ObjectPool.obtain(StartActivityItem.class);
if (instance == null) {
instance = new StartActivityItem();
}
+ instance.mActivityOptions = activityOptions;
return instance;
}
@@ -64,6 +68,7 @@ public class StartActivityItem extends ActivityLifecycleItem {
@Override
public void recycle() {
super.recycle();
+ mActivityOptions = null;
ObjectPool.recycle(this);
}
@@ -73,12 +78,12 @@ public class StartActivityItem extends ActivityLifecycleItem {
/** Write to Parcel. */
@Override
public void writeToParcel(Parcel dest, int flags) {
- // Empty
+ dest.writeBundle(mActivityOptions != null ? mActivityOptions.toBundle() : null);
}
/** Read from Parcel. */
private StartActivityItem(Parcel in) {
- // Empty
+ mActivityOptions = ActivityOptions.fromBundle(in.readBundle());
}
public static final @NonNull Creator<StartActivityItem> CREATOR =
@@ -100,17 +105,20 @@ public class StartActivityItem extends ActivityLifecycleItem {
if (o == null || getClass() != o.getClass()) {
return false;
}
- return true;
+ final StartActivityItem other = (StartActivityItem) o;
+ return (mActivityOptions == null) == (other.mActivityOptions == null);
}
@Override
public int hashCode() {
- return 17;
+ int result = 17;
+ result = 31 * result + (mActivityOptions != null ? 1 : 0);
+ return result;
}
@Override
public String toString() {
- return "StartActivityItem{}";
+ return "StartActivityItem{options=" + mActivityOptions + "}";
}
}
diff --git a/core/java/android/app/servertransaction/TransactionExecutor.java b/core/java/android/app/servertransaction/TransactionExecutor.java
index 3dcf2cb5f13e..25ff8a78a0c8 100644
--- a/core/java/android/app/servertransaction/TransactionExecutor.java
+++ b/core/java/android/app/servertransaction/TransactionExecutor.java
@@ -218,7 +218,8 @@ public class TransactionExecutor {
null /* customIntent */);
break;
case ON_START:
- mTransactionHandler.handleStartActivity(r, mPendingActions);
+ mTransactionHandler.handleStartActivity(r, mPendingActions,
+ null /* activityOptions */);
break;
case ON_RESUME:
mTransactionHandler.handleResumeActivity(r, false /* finalStateRequest */,
diff --git a/core/java/android/app/servertransaction/TransactionExecutorHelper.java b/core/java/android/app/servertransaction/TransactionExecutorHelper.java
index 56bf59b52f74..92f7dee0b0ad 100644
--- a/core/java/android/app/servertransaction/TransactionExecutorHelper.java
+++ b/core/java/android/app/servertransaction/TransactionExecutorHelper.java
@@ -186,7 +186,7 @@ public class TransactionExecutorHelper {
switch (prevState) {
// TODO(lifecycler): Extend to support all possible states.
case ON_START:
- lifecycleItem = StartActivityItem.obtain();
+ lifecycleItem = StartActivityItem.obtain(null /* activityOptions */);
break;
case ON_PAUSE:
lifecycleItem = PauseActivityItem.obtain();
diff --git a/core/tests/coretests/src/android/app/servertransaction/ObjectPoolTests.java b/core/tests/coretests/src/android/app/servertransaction/ObjectPoolTests.java
index b2b34d64b12c..50b52eb2a0ea 100644
--- a/core/tests/coretests/src/android/app/servertransaction/ObjectPoolTests.java
+++ b/core/tests/coretests/src/android/app/servertransaction/ObjectPoolTests.java
@@ -23,9 +23,11 @@ import static android.app.servertransaction.TestUtils.resultInfoList;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotEquals;
import static org.junit.Assert.assertNotSame;
import static org.junit.Assert.assertSame;
+import android.app.ActivityOptions;
import android.app.servertransaction.TestUtils.LaunchActivityItemBuilder;
import android.content.Intent;
import android.content.pm.ActivityInfo;
@@ -247,6 +249,22 @@ public class ObjectPoolTests {
}
@Test
+ public void testRecycleStartActivityItem() {
+ StartActivityItem emptyItem = StartActivityItem.obtain(null /* activityOptions */);
+ StartActivityItem item = StartActivityItem.obtain(ActivityOptions.makeBasic());
+ assertNotSame(item, emptyItem);
+ assertNotEquals(item, emptyItem);
+
+ item.recycle();
+ assertEquals(item, emptyItem);
+
+ StartActivityItem item2 = StartActivityItem.obtain(
+ ActivityOptions.makeBasic().setLaunchDisplayId(10));
+ assertSame(item, item2);
+ assertNotEquals(item2, emptyItem);
+ }
+
+ @Test
public void testRecycleStopItem() {
StopActivityItem emptyItem = StopActivityItem.obtain(0);
StopActivityItem item = StopActivityItem.obtain(4);
diff --git a/core/tests/coretests/src/android/app/servertransaction/TestUtils.java b/core/tests/coretests/src/android/app/servertransaction/TestUtils.java
index 7e9933c8d9df..02e75dd76a07 100644
--- a/core/tests/coretests/src/android/app/servertransaction/TestUtils.java
+++ b/core/tests/coretests/src/android/app/servertransaction/TestUtils.java
@@ -18,6 +18,7 @@ package android.app.servertransaction;
import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
+import android.app.ActivityOptions;
import android.app.ProfilerInfo;
import android.app.ResultInfo;
import android.content.Intent;
@@ -104,6 +105,7 @@ class TestUtils {
private PersistableBundle mPersistentState;
private List<ResultInfo> mPendingResults;
private List<ReferrerIntent> mPendingNewIntents;
+ private ActivityOptions mActivityOptions;
private boolean mIsForward;
private ProfilerInfo mProfilerInfo;
private IBinder mAssistToken;
@@ -174,6 +176,11 @@ class TestUtils {
return this;
}
+ LaunchActivityItemBuilder setActivityOptions(ActivityOptions activityOptions) {
+ mActivityOptions = activityOptions;
+ return this;
+ }
+
LaunchActivityItemBuilder setIsForward(boolean isForward) {
mIsForward = isForward;
return this;
@@ -198,8 +205,8 @@ class TestUtils {
return LaunchActivityItem.obtain(mIntent, mIdent, mInfo,
mCurConfig, mOverrideConfig, mCompatInfo, mReferrer, mVoiceInteractor,
mProcState, mState, mPersistentState, mPendingResults, mPendingNewIntents,
- mIsForward, mProfilerInfo, mAssistToken, null /* activityClientController */,
- mFixedRotationAdjustments);
+ mActivityOptions, mIsForward, mProfilerInfo, mAssistToken,
+ null /* activityClientController */, mFixedRotationAdjustments);
}
}
}
diff --git a/core/tests/coretests/src/android/app/servertransaction/TransactionParcelTests.java b/core/tests/coretests/src/android/app/servertransaction/TransactionParcelTests.java
index e1c7146908d6..5705dd530c16 100644
--- a/core/tests/coretests/src/android/app/servertransaction/TransactionParcelTests.java
+++ b/core/tests/coretests/src/android/app/servertransaction/TransactionParcelTests.java
@@ -24,6 +24,7 @@ import static android.app.servertransaction.TestUtils.resultInfoList;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
+import android.app.ActivityOptions;
import android.app.ContentProviderHolder;
import android.app.IApplicationThread;
import android.app.IInstrumentationWatcher;
@@ -200,9 +201,10 @@ public class TransactionParcelTests {
.setIntent(intent).setIdent(ident).setInfo(activityInfo).setCurConfig(config())
.setOverrideConfig(overrideConfig).setCompatInfo(compat).setReferrer(referrer)
.setProcState(procState).setState(bundle).setPersistentState(persistableBundle)
- .setPendingResults(resultInfoList()).setPendingNewIntents(referrerIntentList())
- .setIsForward(true).setAssistToken(new Binder())
- .setFixedRotationAdjustments(fixedRotationAdjustments).build();
+ .setPendingResults(resultInfoList()).setActivityOptions(ActivityOptions.makeBasic())
+ .setPendingNewIntents(referrerIntentList()).setIsForward(true)
+ .setAssistToken(new Binder()).setFixedRotationAdjustments(fixedRotationAdjustments)
+ .build();
writeAndPrepareForReading(item);
@@ -273,7 +275,7 @@ public class TransactionParcelTests {
@Test
public void testStart() {
// Write to parcel
- StartActivityItem item = StartActivityItem.obtain();
+ StartActivityItem item = StartActivityItem.obtain(ActivityOptions.makeBasic());
writeAndPrepareForReading(item);
// Read from parcel and assert
diff --git a/core/tests/mockingcoretests/src/android/app/activity/ActivityThreadClientTest.java b/core/tests/mockingcoretests/src/android/app/activity/ActivityThreadClientTest.java
index a74f580b65e6..d2b20b4298d9 100644
--- a/core/tests/mockingcoretests/src/android/app/activity/ActivityThreadClientTest.java
+++ b/core/tests/mockingcoretests/src/android/app/activity/ActivityThreadClientTest.java
@@ -242,7 +242,7 @@ public class ActivityThreadClientTest {
}
private void startActivity(ActivityClientRecord r) {
- mThread.handleStartActivity(r, null /* pendingActions */);
+ mThread.handleStartActivity(r, null /* pendingActions */, null /* activityOptions */);
}
private void resumeActivity(ActivityClientRecord r) {
@@ -295,8 +295,9 @@ public class ActivityThreadClientTest {
0 /* ident */, info, new Configuration(),
CompatibilityInfo.DEFAULT_COMPATIBILITY_INFO, null /* referrer */,
null /* voiceInteractor */, null /* state */, null /* persistentState */,
- null /* pendingResults */, null /* pendingNewIntents */, true /* isForward */,
- null /* profilerInfo */, mThread /* client */, null /* asssitToken */,
+ null /* pendingResults */, null /* pendingNewIntents */,
+ null /* activityOptions */, true /* isForward */, null /* profilerInfo */,
+ mThread /* client */, null /* asssitToken */,
null /* fixedRotationAdjustments */);
}
diff --git a/services/core/java/com/android/server/wm/ActivityClientController.java b/services/core/java/com/android/server/wm/ActivityClientController.java
index a61e08aa1c81..e333f3814a61 100644
--- a/services/core/java/com/android/server/wm/ActivityClientController.java
+++ b/services/core/java/com/android/server/wm/ActivityClientController.java
@@ -42,7 +42,6 @@ import static com.android.server.wm.Task.ActivityState.DESTROYING;
import android.annotation.NonNull;
import android.app.Activity;
import android.app.ActivityManager;
-import android.app.ActivityOptions;
import android.app.ActivityTaskManager;
import android.app.IActivityClientController;
import android.app.PictureInPictureParams;
@@ -557,23 +556,6 @@ class ActivityClientController extends IActivityClientController.Stub {
}
@Override
- public Bundle getActivityOptions(IBinder token) {
- final long origId = Binder.clearCallingIdentity();
- try {
- synchronized (mGlobalLock) {
- final ActivityRecord r = ActivityRecord.isInRootTaskLocked(token);
- if (r == null) {
- return null;
- }
- final ActivityOptions activityOptions = r.takeOptionsLocked(true /* fromClient */);
- return activityOptions != null ? activityOptions.toBundle() : null;
- }
- } finally {
- Binder.restoreCallingIdentity(origId);
- }
- }
-
- @Override
public void setRequestedOrientation(IBinder token, int requestedOrientation) {
final long origId = Binder.clearCallingIdentity();
try {
diff --git a/services/core/java/com/android/server/wm/ActivityRecord.java b/services/core/java/com/android/server/wm/ActivityRecord.java
index ef845c843c5f..16538962d910 100644
--- a/services/core/java/com/android/server/wm/ActivityRecord.java
+++ b/services/core/java/com/android/server/wm/ActivityRecord.java
@@ -284,6 +284,7 @@ import android.view.DisplayInfo;
import android.view.IAppTransitionAnimationSpecsFuture;
import android.view.IApplicationToken;
import android.view.InputApplicationHandle;
+import android.view.RemoteAnimationAdapter;
import android.view.RemoteAnimationDefinition;
import android.view.RemoteAnimationTarget;
import android.view.SurfaceControl;
@@ -462,7 +463,10 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
HashSet<WeakReference<PendingIntentRecord>> pendingResults; // all pending intents for this act
ArrayList<ReferrerIntent> newIntents; // any pending new intents for single-top mode
Intent mLastNewIntent; // the last new intent we delivered to client
- ActivityOptions pendingOptions; // most recently given options
+ /** The most recently given options. */
+ private ActivityOptions mPendingOptions;
+ /** Non-null if {@link #mPendingOptions} specifies the remote animation. */
+ private RemoteAnimationAdapter mPendingRemoteAnimation;
ActivityOptions returningOptions; // options that are coming back via convertToTranslucent
AppTimeTracker appTimeTracker; // set if we are tracking the time in this app/task/activity
ActivityServiceConnectionsHolder mServiceConnectionsHolder; // Service connections.
@@ -882,8 +886,13 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
}
}
}
- if (pendingOptions != null) {
- pw.print(prefix); pw.print("pendingOptions="); pw.println(pendingOptions);
+ if (mPendingOptions != null) {
+ pw.print(prefix); pw.print("pendingOptions="); pw.println(mPendingOptions);
+ }
+ if (mPendingRemoteAnimation != null) {
+ pw.print(prefix);
+ pw.print("pendingRemoteAnimationCallingPid=");
+ pw.println(mPendingRemoteAnimation.getCallingPid());
}
if (appTimeTracker != null) {
appTimeTracker.dumpWithHeader(pw, prefix, false);
@@ -1633,8 +1642,8 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
lockTaskLaunchMode = getLockTaskLaunchMode(aInfo, options);
if (options != null) {
- pendingOptions = options;
- final PendingIntent usageReport = pendingOptions.getUsageTimeReport();
+ setOptions(options);
+ final PendingIntent usageReport = options.getUsageTimeReport();
if (usageReport != null) {
appTimeTracker = new AppTimeTracker(usageReport);
}
@@ -2206,7 +2215,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
if (task != null && !finishing) {
task = null;
}
- clearOptionsLocked();
+ abortAndClearOptionsAnimation();
}
}
@@ -2993,7 +3002,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
}
finishing = true;
if (stopped) {
- clearOptionsLocked();
+ abortAndClearOptionsAnimation();
}
mAtmService.getTransitionController().requestTransitionIfNeeded(TRANSIT_CLOSE, this);
}
@@ -3861,33 +3870,47 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
void updateOptionsLocked(ActivityOptions options) {
if (options != null) {
if (DEBUG_TRANSITION) Slog.i(TAG, "Update options for " + this);
- if (pendingOptions != null) {
- pendingOptions.abort();
+ if (mPendingOptions != null) {
+ mPendingOptions.abort();
}
- pendingOptions = options;
+ setOptions(options);
}
}
- void applyOptionsLocked() {
- if (pendingOptions != null
- && pendingOptions.getAnimationType() != ANIM_SCENE_TRANSITION) {
- if (DEBUG_TRANSITION) Slog.i(TAG, "Applying options for " + this);
- applyOptionsLocked(pendingOptions, intent);
- if (task == null) {
- clearOptionsLocked(false /* withAbort */);
- } else {
- // This will clear the options for all the ActivityRecords for this Task.
- task.forAllActivities((r) -> {
- r.clearOptionsLocked(false /* withAbort */);
- });
+ private void setOptions(@NonNull ActivityOptions options) {
+ mPendingOptions = options;
+ if (options.getAnimationType() == ANIM_REMOTE_ANIMATION) {
+ mPendingRemoteAnimation = options.getRemoteAnimationAdapter();
+ }
+ }
+
+ void applyOptionsAnimation() {
+ if (DEBUG_TRANSITION) Slog.i(TAG, "Applying options for " + this);
+ if (mPendingRemoteAnimation != null) {
+ mDisplayContent.mAppTransition.overridePendingAppTransitionRemote(
+ mPendingRemoteAnimation);
+ } else {
+ if (mPendingOptions == null
+ || mPendingOptions.getAnimationType() == ANIM_SCENE_TRANSITION) {
+ // Scene transition will run on the client side.
+ return;
}
+ applyOptionsAnimation(mPendingOptions, intent);
+ }
+ if (task == null) {
+ clearOptionsAnimation();
+ } else {
+ // This will clear the options for all the ActivityRecords for this Task.
+ task.forAllActivities((r) -> {
+ r.clearOptionsAnimation();
+ });
}
}
/**
* Apply override app transition base on options & animation type.
*/
- void applyOptionsLocked(ActivityOptions pendingOptions, Intent intent) {
+ private void applyOptionsAnimation(ActivityOptions pendingOptions, Intent intent) {
final int animationType = pendingOptions.getAnimationType();
final DisplayContent displayContent = getDisplayContent();
switch (animationType) {
@@ -3969,10 +3992,6 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
displayContent.mAppTransition
.overridePendingAppTransitionStartCrossProfileApps();
break;
- case ANIM_REMOTE_ANIMATION:
- displayContent.mAppTransition.overridePendingAppTransitionRemote(
- pendingOptions.getRemoteAnimationAdapter());
- break;
case ANIM_NONE:
case ANIM_UNDEFINED:
break;
@@ -4033,35 +4052,32 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
}
}
- void clearOptionsLocked() {
- clearOptionsLocked(true /* withAbort */);
+ void abortAndClearOptionsAnimation() {
+ if (mPendingOptions != null) {
+ mPendingOptions.abort();
+ }
+ clearOptionsAnimation();
}
- void clearOptionsLocked(boolean withAbort) {
- if (withAbort && pendingOptions != null) {
- pendingOptions.abort();
- }
- pendingOptions = null;
+ void clearOptionsAnimation() {
+ mPendingOptions = null;
+ mPendingRemoteAnimation = null;
}
- ActivityOptions takeOptionsLocked(boolean fromClient) {
+ ActivityOptions getOptions() {
+ return mPendingOptions;
+ }
+
+ ActivityOptions takeOptions() {
if (DEBUG_TRANSITION) Slog.i(TAG, "Taking options for " + this + " callers="
+ Debug.getCallers(6));
- ActivityOptions opts = pendingOptions;
-
- // If we are trying to take activity options from the client, do not null it out if it's a
- // remote animation as the client doesn't need it ever. This is a workaround when client is
- // faster to take the options than we are to resume the next activity.
- // TODO (b/132432864): Fix the root cause of these transition preparing/applying options
- // timing somehow
- if (!fromClient || opts == null || opts.getRemoteAnimationAdapter() == null) {
- pendingOptions = null;
- }
+ final ActivityOptions opts = mPendingOptions;
+ mPendingOptions = null;
return opts;
}
boolean allowMoveToFront() {
- return pendingOptions == null || !pendingOptions.getAvoidMoveToFront();
+ return mPendingOptions == null || !mPendingOptions.getAvoidMoveToFront();
}
void removeUriPermissionsLocked() {
@@ -4883,7 +4899,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
try {
mAtmService.getLifecycleManager().scheduleTransaction(app.getThread(), appToken,
- StartActivityItem.obtain());
+ StartActivityItem.obtain(takeOptions()));
} catch (Exception e) {
Slog.w(TAG, "Exception thrown sending start: " + intent.getComponent(), e);
}
@@ -5204,7 +5220,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
notifyAppStopped();
if (finishing) {
- clearOptionsLocked();
+ abortAndClearOptionsAnimation();
} else {
if (deferRelaunchUntilPaused) {
destroyImmediately("stop-config");
@@ -5838,8 +5854,8 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
// We don't show starting window for overlay activities.
return;
}
- if (pendingOptions != null
- && pendingOptions.getAnimationType() == ActivityOptions.ANIM_SCENE_TRANSITION) {
+ if (mPendingOptions != null
+ && mPendingOptions.getAnimationType() == ActivityOptions.ANIM_SCENE_TRANSITION) {
// Don't show starting window when using shared element transition.
return;
}
diff --git a/services/core/java/com/android/server/wm/ActivityStartController.java b/services/core/java/com/android/server/wm/ActivityStartController.java
index f9e85cdd8d8a..2dd8c597450e 100644
--- a/services/core/java/com/android/server/wm/ActivityStartController.java
+++ b/services/core/java/com/android/server/wm/ActivityStartController.java
@@ -528,7 +528,7 @@ public class ActivityStartController {
"pendingActivityLaunch");
try {
starter.startResolvedActivity(pal.r, pal.sourceRecord, null, null, pal.startFlags,
- resume, pal.r.pendingOptions, null, pal.intentGrants);
+ resume, pal.r.getOptions(), null, pal.intentGrants);
} catch (Exception e) {
Slog.e(TAG, "Exception during pending activity launch pal=" + pal, e);
pal.sendErrorResult(e.getMessage());
diff --git a/services/core/java/com/android/server/wm/ActivityStarter.java b/services/core/java/com/android/server/wm/ActivityStarter.java
index e30cd05c79a0..5289f8604f36 100644
--- a/services/core/java/com/android/server/wm/ActivityStarter.java
+++ b/services/core/java/com/android/server/wm/ActivityStarter.java
@@ -1258,7 +1258,7 @@ class ActivityStarter {
}
// We pretend to the caller that it was really started to make it backward compatible, but
// they will just get a cancel result.
- ActivityOptions.abort(r.pendingOptions);
+ ActivityOptions.abort(r.getOptions());
return true;
}
diff --git a/services/core/java/com/android/server/wm/ActivityTaskSupervisor.java b/services/core/java/com/android/server/wm/ActivityTaskSupervisor.java
index 16f415fd9781..9d291b12c2c9 100644
--- a/services/core/java/com/android/server/wm/ActivityTaskSupervisor.java
+++ b/services/core/java/com/android/server/wm/ActivityTaskSupervisor.java
@@ -868,8 +868,8 @@ public class ActivityTaskSupervisor implements RecentTasks.Callbacks {
mergedConfiguration.getOverrideConfiguration(), r.compat,
r.launchedFromPackage, task.voiceInteractor, proc.getReportedProcState(),
r.getSavedState(), r.getPersistentSavedState(), results, newIntents,
- dc.isNextTransitionForward(), proc.createProfilerInfoIfNeeded(),
- r.assistToken, activityClientController,
+ r.takeOptions(), dc.isNextTransitionForward(),
+ proc.createProfilerInfoIfNeeded(), r.assistToken, activityClientController,
r.createFixedRotationAdjustmentsIfNeeded()));
// Set desired final state.
@@ -2566,9 +2566,10 @@ public class ActivityTaskSupervisor implements RecentTasks.Callbacks {
try {
mService.moveTaskToFrontLocked(null /* appThread */, null /* callingPackage */,
task.mTaskId, 0, options);
- // Apply options to prevent pendingOptions be taken by client to make sure
- // the override pending app transition will be applied immediately.
- targetActivity.applyOptionsLocked();
+ // Apply options to prevent pendingOptions be taken when scheduling activity
+ // lifecycle transaction to make sure the override pending app transition will
+ // be applied immediately.
+ targetActivity.applyOptionsAnimation();
} finally {
mActivityMetricsLogger.notifyActivityLaunched(launchingState,
START_TASK_TO_FRONT, targetActivity, activityOptions);
diff --git a/services/core/java/com/android/server/wm/ResetTargetTaskHelper.java b/services/core/java/com/android/server/wm/ResetTargetTaskHelper.java
index 17cb8905f260..fc347bc609d1 100644
--- a/services/core/java/com/android/server/wm/ResetTargetTaskHelper.java
+++ b/services/core/java/com/android/server/wm/ResetTargetTaskHelper.java
@@ -267,8 +267,9 @@ class ResetTargetTaskHelper {
private boolean takeOption(ActivityRecord p, boolean noOptions) {
mCanMoveOptions = false;
if (noOptions && mTopOptions == null) {
- mTopOptions = p.takeOptionsLocked(false /* fromClient */);
+ mTopOptions = p.getOptions();
if (mTopOptions != null) {
+ p.clearOptionsAnimation();
noOptions = false;
}
}
diff --git a/services/core/java/com/android/server/wm/Task.java b/services/core/java/com/android/server/wm/Task.java
index 2290c23be513..81cbd61d62d7 100644
--- a/services/core/java/com/android/server/wm/Task.java
+++ b/services/core/java/com/android/server/wm/Task.java
@@ -1926,8 +1926,9 @@ class Task extends WindowContainer<WindowContainer> {
if (r == boundaryActivity) return true;
if (!r.finishing) {
- final ActivityOptions opts = r.takeOptionsLocked(false /* fromClient */);
+ final ActivityOptions opts = r.getOptions();
if (opts != null) {
+ r.clearOptionsAnimation();
// TODO: Why is this updating the boundary activity vs. the current activity???
boundaryActivity.updateOptionsLocked(opts);
}
@@ -6247,9 +6248,9 @@ class Task extends WindowContainer<WindowContainer> {
}
if (anim) {
- next.applyOptionsLocked();
+ next.applyOptionsAnimation();
} else {
- next.clearOptionsLocked();
+ next.abortAndClearOptionsAnimation();
}
mTaskSupervisor.mNoAnimActivities.clear();
@@ -6356,7 +6357,7 @@ class Task extends WindowContainer<WindowContainer> {
mAtmService.getAppWarningsLocked().onResumeActivity(next);
next.app.setPendingUiCleanAndForceProcessStateUpTo(mAtmService.mTopProcessState);
- next.clearOptionsLocked();
+ next.abortAndClearOptionsAnimation();
transaction.setLifecycleStateRequest(
ResumeActivityItem.obtain(next.app.getReportedProcState(),
dc.isNextTransitionForward()));
diff --git a/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java b/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
index b50e50b89683..39e3bffd3349 100644
--- a/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
@@ -254,26 +254,26 @@ public class ActivityRecordTests extends WindowTestsBase {
// Set and apply options for ActivityRecord. Pending options should be cleared
activity.updateOptionsLocked(activityOptions);
- activity.applyOptionsLocked();
- assertNull(activity.pendingOptions);
+ activity.applyOptionsAnimation();
+ assertNull(activity.getOptions());
// Set options for two ActivityRecords in same Task. Apply one ActivityRecord options.
// Pending options should be cleared for both ActivityRecords
ActivityRecord activity2 = new ActivityBuilder(mAtm).setTask(activity.getTask()).build();
activity2.updateOptionsLocked(activityOptions);
activity.updateOptionsLocked(activityOptions);
- activity.applyOptionsLocked();
- assertNull(activity.pendingOptions);
- assertNull(activity2.pendingOptions);
+ activity.applyOptionsAnimation();
+ assertNull(activity.getOptions());
+ assertNull(activity2.getOptions());
// Set options for two ActivityRecords in separate Tasks. Apply one ActivityRecord options.
// Pending options should be cleared for only ActivityRecord that was applied
activity2 = new ActivityBuilder(mAtm).setCreateTask(true).build();
activity2.updateOptionsLocked(activityOptions);
activity.updateOptionsLocked(activityOptions);
- activity.applyOptionsLocked();
- assertNull(activity.pendingOptions);
- assertNotNull(activity2.pendingOptions);
+ activity.applyOptionsAnimation();
+ assertNull(activity.getOptions());
+ assertNotNull(activity2.getOptions());
}
@Test
@@ -653,21 +653,21 @@ public class ActivityRecordTests extends WindowTestsBase {
public void onAnimationStart(RemoteAnimationTarget[] apps,
RemoteAnimationTarget[] wallpapers,
IRemoteAnimationFinishedCallback finishedCallback) {
-
}
@Override
public void onAnimationCancelled() {
-
}
}, 0, 0));
activity.updateOptionsLocked(opts);
- assertNotNull(activity.takeOptionsLocked(true /* fromClient */));
- assertNotNull(activity.pendingOptions);
+ assertNotNull(activity.takeOptions());
+ assertNull(activity.getOptions());
+
+ final AppTransition appTransition = activity.mDisplayContent.mAppTransition;
+ spyOn(appTransition);
+ activity.applyOptionsAnimation();
- activity.updateOptionsLocked(ActivityOptions.makeBasic());
- assertNotNull(activity.takeOptionsLocked(false /* fromClient */));
- assertNull(activity.pendingOptions);
+ verify(appTransition).overridePendingAppTransitionRemote(any());
}
@Test