1 /* 2 * Copyright (C) 2022 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.server.wm; 18 19 import static android.app.WindowConfiguration.WINDOWING_MODE_PINNED; 20 import static android.os.Trace.TRACE_TAG_WINDOW_MANAGER; 21 import static android.view.WindowManager.TRANSIT_CLOSE; 22 import static android.view.WindowManager.TRANSIT_FIRST_CUSTOM; 23 import static android.view.WindowManager.TRANSIT_OPEN; 24 import static android.view.WindowManager.TRANSIT_TO_BACK; 25 import static android.view.WindowManager.TRANSIT_TO_FRONT; 26 27 import android.os.Trace; 28 import android.view.WindowManager; 29 30 import java.io.PrintWriter; 31 import java.util.ArrayList; 32 33 /** 34 * Integrates common functionality from TaskSnapshotController and ActivitySnapshotController. 35 */ 36 class SnapshotController { 37 private final SnapshotPersistQueue mSnapshotPersistQueue; 38 final TaskSnapshotController mTaskSnapshotController; 39 final ActivitySnapshotController mActivitySnapshotController; 40 SnapshotController(WindowManagerService wms)41 SnapshotController(WindowManagerService wms) { 42 mSnapshotPersistQueue = new SnapshotPersistQueue(); 43 mTaskSnapshotController = new TaskSnapshotController(wms, mSnapshotPersistQueue); 44 mActivitySnapshotController = new ActivitySnapshotController(wms, mSnapshotPersistQueue); 45 } 46 systemReady()47 void systemReady() { 48 mSnapshotPersistQueue.systemReady(); 49 } 50 setPause(boolean paused)51 void setPause(boolean paused) { 52 mSnapshotPersistQueue.setPaused(paused); 53 } 54 onAppRemoved(ActivityRecord activity)55 void onAppRemoved(ActivityRecord activity) { 56 mTaskSnapshotController.onAppRemoved(activity); 57 mActivitySnapshotController.onAppRemoved(activity); 58 } 59 onAppDied(ActivityRecord activity)60 void onAppDied(ActivityRecord activity) { 61 mTaskSnapshotController.onAppDied(activity); 62 mActivitySnapshotController.onAppDied(activity); 63 } 64 notifyAppVisibilityChanged(ActivityRecord appWindowToken, boolean visible)65 void notifyAppVisibilityChanged(ActivityRecord appWindowToken, boolean visible) { 66 mActivitySnapshotController.notifyAppVisibilityChanged(appWindowToken, visible); 67 } 68 69 // For legacy transition, which won't support activity snapshot onTransitionStarting(DisplayContent displayContent)70 void onTransitionStarting(DisplayContent displayContent) { 71 mTaskSnapshotController.handleClosingApps(displayContent.mClosingApps); 72 } 73 74 // For shell transition, record snapshots before transaction start. onTransactionReady(@indowManager.TransitionType int type, ArrayList<Transition.ChangeInfo> changeInfos)75 void onTransactionReady(@WindowManager.TransitionType int type, 76 ArrayList<Transition.ChangeInfo> changeInfos) { 77 final boolean isTransitionOpen = isTransitionOpen(type); 78 final boolean isTransitionClose = isTransitionClose(type); 79 if (!isTransitionOpen && !isTransitionClose && type < TRANSIT_FIRST_CUSTOM) { 80 return; 81 } 82 for (int i = changeInfos.size() - 1; i >= 0; --i) { 83 Transition.ChangeInfo info = changeInfos.get(i); 84 // Intentionally skip record snapshot for changes originated from PiP. 85 if (info.mWindowingMode == WINDOWING_MODE_PINNED) continue; 86 if (info.mContainer.asTask() != null && !info.mContainer.isVisibleRequested()) { 87 mTaskSnapshotController.recordSnapshot(info.mContainer.asTask(), 88 false /* allowSnapshotHome */); 89 } 90 // Won't need to capture activity snapshot in close transition. 91 if (isTransitionClose) { 92 continue; 93 } 94 if (info.mContainer.asActivityRecord() != null 95 || info.mContainer.asTaskFragment() != null) { 96 final TaskFragment tf = info.mContainer.asTaskFragment(); 97 final ActivityRecord ar = tf != null ? tf.getTopMostActivity() 98 : info.mContainer.asActivityRecord(); 99 final boolean taskVis = ar != null && ar.getTask().isVisibleRequested(); 100 if (ar != null && !ar.isVisibleRequested() && taskVis) { 101 mActivitySnapshotController.recordSnapshot(ar); 102 } 103 } 104 } 105 } 106 onTransitionFinish(@indowManager.TransitionType int type, ArrayList<Transition.ChangeInfo> changeInfos)107 void onTransitionFinish(@WindowManager.TransitionType int type, 108 ArrayList<Transition.ChangeInfo> changeInfos) { 109 final boolean isTransitionOpen = isTransitionOpen(type); 110 final boolean isTransitionClose = isTransitionClose(type); 111 if (!isTransitionOpen && !isTransitionClose && type < TRANSIT_FIRST_CUSTOM 112 || (changeInfos.isEmpty())) { 113 return; 114 } 115 Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER, "SnapshotController_analysis"); 116 mActivitySnapshotController.beginSnapshotProcess(); 117 final ArrayList<WindowContainer> windows = new ArrayList<>(); 118 for (int i = changeInfos.size() - 1; i >= 0; --i) { 119 final WindowContainer wc = changeInfos.get(i).mContainer; 120 if (wc.asTask() == null && wc.asTaskFragment() == null 121 && wc.asActivityRecord() == null) { 122 continue; 123 } 124 windows.add(wc); 125 } 126 mActivitySnapshotController.handleTransitionFinish(windows); 127 mActivitySnapshotController.endSnapshotProcess(); 128 Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); 129 } 130 isTransitionOpen(int type)131 private static boolean isTransitionOpen(int type) { 132 return type == TRANSIT_OPEN || type == TRANSIT_TO_FRONT; 133 } isTransitionClose(int type)134 private static boolean isTransitionClose(int type) { 135 return type == TRANSIT_CLOSE || type == TRANSIT_TO_BACK; 136 } 137 dump(PrintWriter pw, String prefix)138 void dump(PrintWriter pw, String prefix) { 139 mTaskSnapshotController.dump(pw, prefix); 140 mActivitySnapshotController.dump(pw, prefix); 141 } 142 } 143