summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/java/android/app/IActivityTaskManager.aidl8
-rw-r--r--packages/SystemUI/shared/src/com/android/systemui/shared/system/ActivityManagerWrapper.java18
-rw-r--r--services/core/java/com/android/server/policy/PhoneWindowManager.java3
-rw-r--r--services/core/java/com/android/server/wm/ActivityRecord.java11
-rw-r--r--services/core/java/com/android/server/wm/ActivityTaskManagerService.java11
-rw-r--r--services/core/java/com/android/server/wm/TaskSnapshotCache.java2
-rw-r--r--services/core/java/com/android/server/wm/TaskSnapshotController.java49
7 files changed, 85 insertions, 17 deletions
diff --git a/core/java/android/app/IActivityTaskManager.aidl b/core/java/android/app/IActivityTaskManager.aidl
index d701a5d81304..e2b1b8664d75 100644
--- a/core/java/android/app/IActivityTaskManager.aidl
+++ b/core/java/android/app/IActivityTaskManager.aidl
@@ -405,6 +405,14 @@ interface IActivityTaskManager {
void setDisablePreviewScreenshots(IBinder token, boolean disable);
/**
+ * It should only be called from home activity to remove its outdated snapshot. The home
+ * snapshot is used to speed up entering home from screen off. If the content of home activity
+ * is significantly different from before taking the snapshot, then the home activity can use
+ * this method to avoid inconsistent transition.
+ */
+ void invalidateHomeTaskSnapshot(IBinder homeToken);
+
+ /**
* Return the user id of last resumed activity.
*/
int getLastResumedActivityUserId();
diff --git a/packages/SystemUI/shared/src/com/android/systemui/shared/system/ActivityManagerWrapper.java b/packages/SystemUI/shared/src/com/android/systemui/shared/system/ActivityManagerWrapper.java
index 70f8e15eb83d..deaafca7a98c 100644
--- a/packages/SystemUI/shared/src/com/android/systemui/shared/system/ActivityManagerWrapper.java
+++ b/packages/SystemUI/shared/src/com/android/systemui/shared/system/ActivityManagerWrapper.java
@@ -28,6 +28,7 @@ import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECOND
import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
import android.annotation.NonNull;
+import android.app.Activity;
import android.app.ActivityManager;
import android.app.ActivityManager.RecentTaskInfo;
import android.app.ActivityManager.RunningTaskInfo;
@@ -161,6 +162,23 @@ public class ActivityManagerWrapper {
}
/**
+ * Removes the outdated snapshot of home task.
+ */
+ public void invalidateHomeTaskSnapshot(final Activity homeActivity) {
+ mBackgroundExecutor.submit(new Runnable() {
+ @Override
+ public void run() {
+ try {
+ ActivityTaskManager.getService().invalidateHomeTaskSnapshot(
+ homeActivity.getActivityToken());
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to invalidate home snapshot", e);
+ }
+ }
+ });
+ }
+
+ /**
* @return the activity label, badging if necessary.
*/
public String getBadgedActivityLabel(ActivityInfo info, int userId) {
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index 8435a8202762..c05b70413a40 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -157,6 +157,7 @@ import android.os.ServiceManager;
import android.os.StrictMode;
import android.os.SystemClock;
import android.os.SystemProperties;
+import android.os.Trace;
import android.os.UEventObserver;
import android.os.UserHandle;
import android.os.VibrationEffect;
@@ -4603,6 +4604,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
public void screenTurningOn(final ScreenOnListener screenOnListener) {
if (DEBUG_WAKEUP) Slog.i(TAG, "Screen turning on...");
+ Trace.asyncTraceBegin(Trace.TRACE_TAG_WINDOW_MANAGER, "screenTurningOn", 0 /* cookie */);
updateScreenOffSleepToken(false);
mDefaultDisplayPolicy.screenTurnedOn(screenOnListener);
@@ -4665,6 +4667,7 @@ public class PhoneWindowManager implements WindowManagerPolicy {
if (!mDefaultDisplayPolicy.finishScreenTurningOn()) {
return; // Spurious or not ready yet.
}
+ Trace.asyncTraceEnd(Trace.TRACE_TAG_WINDOW_MANAGER, "screenTurningOn", 0 /* cookie */);
final boolean enableScreen;
final boolean awake = mDefaultDisplayPolicy.isAwake();
diff --git a/services/core/java/com/android/server/wm/ActivityRecord.java b/services/core/java/com/android/server/wm/ActivityRecord.java
index 69c3967d8806..6de9dbd001d7 100644
--- a/services/core/java/com/android/server/wm/ActivityRecord.java
+++ b/services/core/java/com/android/server/wm/ActivityRecord.java
@@ -1640,6 +1640,17 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A
allowTaskSnapshot, activityCreated, fromRecents, snapshot);
if (type == STARTING_WINDOW_TYPE_SNAPSHOT) {
+ if (isActivityTypeHome()) {
+ // The snapshot of home is only used once because it won't be updated while screen
+ // is on (see {@link TaskSnapshotController#screenTurningOff}).
+ mWmService.mTaskSnapshotController.removeSnapshotCache(task.mTaskId);
+ // TODO(b/9684093): Use more general condition to specify the case.
+ if (mDisplayContent.mAppTransition
+ .getAppTransition() != WindowManager.TRANSIT_KEYGUARD_GOING_AWAY) {
+ // Only use snapshot of home as starting window when unlocking.
+ return false;
+ }
+ }
return createSnapshot(snapshot);
}
diff --git a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
index 9213e05042e0..f0bc4129f4ef 100644
--- a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
+++ b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
@@ -4572,6 +4572,17 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
}
}
+ @Override
+ public void invalidateHomeTaskSnapshot(IBinder token) {
+ synchronized (mGlobalLock) {
+ final ActivityRecord r = ActivityRecord.isInStackLocked(token);
+ if (r == null || !r.isActivityTypeHome()) {
+ return;
+ }
+ mWindowManager.mTaskSnapshotController.removeSnapshotCache(r.getTask().mTaskId);
+ }
+ }
+
/** Return the user id of the last resumed activity. */
@Override
public @UserIdInt
diff --git a/services/core/java/com/android/server/wm/TaskSnapshotCache.java b/services/core/java/com/android/server/wm/TaskSnapshotCache.java
index 5cbab5d1b1f5..7b0d841483bb 100644
--- a/services/core/java/com/android/server/wm/TaskSnapshotCache.java
+++ b/services/core/java/com/android/server/wm/TaskSnapshotCache.java
@@ -109,7 +109,7 @@ class TaskSnapshotCache {
removeRunningEntry(taskId);
}
- private void removeRunningEntry(int taskId) {
+ void removeRunningEntry(int taskId) {
final CacheEntry entry = mRunningCache.get(taskId);
if (entry != null) {
mAppTaskMap.remove(entry.topApp);
diff --git a/services/core/java/com/android/server/wm/TaskSnapshotController.java b/services/core/java/com/android/server/wm/TaskSnapshotController.java
index c1a36c49fc1a..12b2845e9d71 100644
--- a/services/core/java/com/android/server/wm/TaskSnapshotController.java
+++ b/services/core/java/com/android/server/wm/TaskSnapshotController.java
@@ -171,22 +171,30 @@ class TaskSnapshotController {
}
void snapshotTasks(ArraySet<Task> tasks) {
+ snapshotTasks(mTmpTasks, false /* allowSnapshotHome */);
+ }
+
+ private void snapshotTasks(ArraySet<Task> tasks, boolean allowSnapshotHome) {
for (int i = tasks.size() - 1; i >= 0; i--) {
final Task task = tasks.valueAt(i);
- final int mode = getSnapshotMode(task);
final TaskSnapshot snapshot;
- switch (mode) {
- case SNAPSHOT_MODE_NONE:
- continue;
- case SNAPSHOT_MODE_APP_THEME:
- snapshot = drawAppThemeSnapshot(task);
- break;
- case SNAPSHOT_MODE_REAL:
- snapshot = snapshotTask(task);
- break;
- default:
- snapshot = null;
- break;
+ final boolean snapshotHome = allowSnapshotHome && task.isActivityTypeHome();
+ if (snapshotHome) {
+ snapshot = snapshotTask(task);
+ } else {
+ switch (getSnapshotMode(task)) {
+ case SNAPSHOT_MODE_NONE:
+ continue;
+ case SNAPSHOT_MODE_APP_THEME:
+ snapshot = drawAppThemeSnapshot(task);
+ break;
+ case SNAPSHOT_MODE_REAL:
+ snapshot = snapshotTask(task);
+ break;
+ default:
+ snapshot = null;
+ break;
+ }
}
if (snapshot != null) {
final GraphicBuffer buffer = snapshot.getSnapshot();
@@ -196,8 +204,11 @@ class TaskSnapshotController {
+ buffer.getHeight());
} else {
mCache.putSnapshot(task, snapshot);
- mPersister.persistSnapshot(task.mTaskId, task.mUserId, snapshot);
- task.onSnapshotChanged(snapshot);
+ // Don't persist or notify the change for the temporal snapshot.
+ if (!snapshotHome) {
+ mPersister.persistSnapshot(task.mTaskId, task.mUserId, snapshot);
+ task.onSnapshotChanged(snapshot);
+ }
}
}
}
@@ -450,6 +461,10 @@ class TaskSnapshotController {
mPersister.onTaskRemovedFromRecents(taskId, userId);
}
+ void removeSnapshotCache(int taskId) {
+ mCache.removeRunningEntry(taskId);
+ }
+
/**
* See {@link TaskSnapshotPersister#removeObsoleteFiles}
*/
@@ -485,7 +500,9 @@ class TaskSnapshotController {
mTmpTasks.add(task);
}
});
- snapshotTasks(mTmpTasks);
+ // Allow taking snapshot of home when turning screen off to reduce the delay of
+ // unlocking/waking to home.
+ snapshotTasks(mTmpTasks, true /* allowSnapshotHome */);
}
} finally {
listener.onScreenOff();