Merge "Update recent tasks split pairs from split controller" into sc-v2-dev
This commit is contained in:
@@ -240,8 +240,12 @@ public abstract class WMShellBaseModule {
|
|||||||
@WMSingleton
|
@WMSingleton
|
||||||
@Provides
|
@Provides
|
||||||
static FullscreenTaskListener provideFullscreenTaskListener(
|
static FullscreenTaskListener provideFullscreenTaskListener(
|
||||||
SyncTransactionQueue syncQueue, Optional<FullscreenUnfoldController> controller) {
|
SyncTransactionQueue syncQueue,
|
||||||
return new FullscreenTaskListener(syncQueue, controller);
|
Optional<FullscreenUnfoldController> optionalFullscreenUnfoldController,
|
||||||
|
Optional<RecentTasksController> recentTasksOptional
|
||||||
|
) {
|
||||||
|
return new FullscreenTaskListener(syncQueue, optionalFullscreenUnfoldController,
|
||||||
|
recentTasksOptional);
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
@@ -490,12 +494,13 @@ public abstract class WMShellBaseModule {
|
|||||||
DisplayImeController displayImeController,
|
DisplayImeController displayImeController,
|
||||||
DisplayInsetsController displayInsetsController, Transitions transitions,
|
DisplayInsetsController displayInsetsController, Transitions transitions,
|
||||||
TransactionPool transactionPool, IconProvider iconProvider,
|
TransactionPool transactionPool, IconProvider iconProvider,
|
||||||
|
Optional<RecentTasksController> recentTasks,
|
||||||
Provider<Optional<StageTaskUnfoldController>> stageTaskUnfoldControllerProvider) {
|
Provider<Optional<StageTaskUnfoldController>> stageTaskUnfoldControllerProvider) {
|
||||||
if (ActivityTaskManager.supportsSplitScreenMultiWindow(context)) {
|
if (ActivityTaskManager.supportsSplitScreenMultiWindow(context)) {
|
||||||
return Optional.of(new SplitScreenController(shellTaskOrganizer, syncQueue, context,
|
return Optional.of(new SplitScreenController(shellTaskOrganizer, syncQueue, context,
|
||||||
rootTaskDisplayAreaOrganizer, mainExecutor, displayImeController,
|
rootTaskDisplayAreaOrganizer, mainExecutor, displayImeController,
|
||||||
displayInsetsController, transitions, transactionPool, iconProvider,
|
displayInsetsController, transitions, transactionPool, iconProvider,
|
||||||
stageTaskUnfoldControllerProvider));
|
recentTasks, stageTaskUnfoldControllerProvider));
|
||||||
} else {
|
} else {
|
||||||
return Optional.empty();
|
return Optional.empty();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ import com.android.internal.protolog.common.ProtoLog;
|
|||||||
import com.android.wm.shell.ShellTaskOrganizer;
|
import com.android.wm.shell.ShellTaskOrganizer;
|
||||||
import com.android.wm.shell.common.SyncTransactionQueue;
|
import com.android.wm.shell.common.SyncTransactionQueue;
|
||||||
import com.android.wm.shell.protolog.ShellProtoLogGroup;
|
import com.android.wm.shell.protolog.ShellProtoLogGroup;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
import java.io.PrintWriter;
|
import java.io.PrintWriter;
|
||||||
@@ -47,15 +48,23 @@ public class FullscreenTaskListener implements ShellTaskOrganizer.TaskListener {
|
|||||||
private static final String TAG = "FullscreenTaskListener";
|
private static final String TAG = "FullscreenTaskListener";
|
||||||
|
|
||||||
private final SyncTransactionQueue mSyncQueue;
|
private final SyncTransactionQueue mSyncQueue;
|
||||||
|
private final FullscreenUnfoldController mFullscreenUnfoldController;
|
||||||
|
private final Optional<RecentTasksController> mRecentTasksOptional;
|
||||||
|
|
||||||
private final SparseArray<TaskData> mDataByTaskId = new SparseArray<>();
|
private final SparseArray<TaskData> mDataByTaskId = new SparseArray<>();
|
||||||
private final AnimatableTasksListener mAnimatableTasksListener = new AnimatableTasksListener();
|
private final AnimatableTasksListener mAnimatableTasksListener = new AnimatableTasksListener();
|
||||||
private final FullscreenUnfoldController mFullscreenUnfoldController;
|
|
||||||
|
|
||||||
public FullscreenTaskListener(SyncTransactionQueue syncQueue,
|
public FullscreenTaskListener(SyncTransactionQueue syncQueue,
|
||||||
Optional<FullscreenUnfoldController> unfoldController) {
|
Optional<FullscreenUnfoldController> unfoldController) {
|
||||||
|
this(syncQueue, unfoldController, Optional.empty());
|
||||||
|
}
|
||||||
|
|
||||||
|
public FullscreenTaskListener(SyncTransactionQueue syncQueue,
|
||||||
|
Optional<FullscreenUnfoldController> unfoldController,
|
||||||
|
Optional<RecentTasksController> recentTasks) {
|
||||||
mSyncQueue = syncQueue;
|
mSyncQueue = syncQueue;
|
||||||
mFullscreenUnfoldController = unfoldController.orElse(null);
|
mFullscreenUnfoldController = unfoldController.orElse(null);
|
||||||
|
mRecentTasksOptional = recentTasks;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -79,6 +88,7 @@ public class FullscreenTaskListener implements ShellTaskOrganizer.TaskListener {
|
|||||||
});
|
});
|
||||||
|
|
||||||
mAnimatableTasksListener.onTaskAppeared(taskInfo);
|
mAnimatableTasksListener.onTaskAppeared(taskInfo);
|
||||||
|
updateRecentsForVisibleFullscreenTask(taskInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -86,6 +96,7 @@ public class FullscreenTaskListener implements ShellTaskOrganizer.TaskListener {
|
|||||||
if (Transitions.ENABLE_SHELL_TRANSITIONS) return;
|
if (Transitions.ENABLE_SHELL_TRANSITIONS) return;
|
||||||
|
|
||||||
mAnimatableTasksListener.onTaskInfoChanged(taskInfo);
|
mAnimatableTasksListener.onTaskInfoChanged(taskInfo);
|
||||||
|
updateRecentsForVisibleFullscreenTask(taskInfo);
|
||||||
|
|
||||||
final TaskData data = mDataByTaskId.get(taskInfo.taskId);
|
final TaskData data = mDataByTaskId.get(taskInfo.taskId);
|
||||||
final Point positionInParent = taskInfo.positionInParent;
|
final Point positionInParent = taskInfo.positionInParent;
|
||||||
@@ -111,6 +122,15 @@ public class FullscreenTaskListener implements ShellTaskOrganizer.TaskListener {
|
|||||||
taskInfo.taskId);
|
taskInfo.taskId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void updateRecentsForVisibleFullscreenTask(RunningTaskInfo taskInfo) {
|
||||||
|
mRecentTasksOptional.ifPresent(recentTasks -> {
|
||||||
|
if (taskInfo.isVisible) {
|
||||||
|
// Remove any persisted splits if either tasks are now made fullscreen and visible
|
||||||
|
recentTasks.removeSplitPair(taskInfo.taskId);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void attachChildSurfaceToTask(int taskId, SurfaceControl.Builder b) {
|
public void attachChildSurfaceToTask(int taskId, SurfaceControl.Builder b) {
|
||||||
if (!mDataByTaskId.contains(taskId)) {
|
if (!mDataByTaskId.contains(taskId)) {
|
||||||
|
|||||||
@@ -66,6 +66,7 @@ import com.android.wm.shell.common.TransactionPool;
|
|||||||
import com.android.wm.shell.common.annotations.ExternalThread;
|
import com.android.wm.shell.common.annotations.ExternalThread;
|
||||||
import com.android.wm.shell.common.split.SplitLayout.SplitPosition;
|
import com.android.wm.shell.common.split.SplitLayout.SplitPosition;
|
||||||
import com.android.wm.shell.draganddrop.DragAndDropPolicy;
|
import com.android.wm.shell.draganddrop.DragAndDropPolicy;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.transition.LegacyTransitions;
|
import com.android.wm.shell.transition.LegacyTransitions;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
@@ -124,16 +125,31 @@ public class SplitScreenController implements DragAndDropPolicy.Starter,
|
|||||||
private final TransactionPool mTransactionPool;
|
private final TransactionPool mTransactionPool;
|
||||||
private final SplitscreenEventLogger mLogger;
|
private final SplitscreenEventLogger mLogger;
|
||||||
private final IconProvider mIconProvider;
|
private final IconProvider mIconProvider;
|
||||||
|
private final Optional<RecentTasksController> mRecentTasksOptional;
|
||||||
private final Provider<Optional<StageTaskUnfoldController>> mUnfoldControllerProvider;
|
private final Provider<Optional<StageTaskUnfoldController>> mUnfoldControllerProvider;
|
||||||
|
|
||||||
private StageCoordinator mStageCoordinator;
|
private StageCoordinator mStageCoordinator;
|
||||||
|
|
||||||
|
// TODO(b/205019015): Remove after we clean up downstream modules
|
||||||
|
public SplitScreenController(ShellTaskOrganizer shellTaskOrganizer,
|
||||||
|
SyncTransactionQueue syncQueue, Context context,
|
||||||
|
RootTaskDisplayAreaOrganizer rootTDAOrganizer,
|
||||||
|
ShellExecutor mainExecutor, DisplayImeController displayImeController,
|
||||||
|
DisplayInsetsController displayInsetsController,
|
||||||
|
Transitions transitions, TransactionPool transactionPool, IconProvider iconProvider,
|
||||||
|
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
||||||
|
this(shellTaskOrganizer, syncQueue, context, rootTDAOrganizer, mainExecutor,
|
||||||
|
displayImeController, displayInsetsController, transitions, transactionPool,
|
||||||
|
iconProvider, Optional.empty(), unfoldControllerProvider);
|
||||||
|
}
|
||||||
|
|
||||||
public SplitScreenController(ShellTaskOrganizer shellTaskOrganizer,
|
public SplitScreenController(ShellTaskOrganizer shellTaskOrganizer,
|
||||||
SyncTransactionQueue syncQueue, Context context,
|
SyncTransactionQueue syncQueue, Context context,
|
||||||
RootTaskDisplayAreaOrganizer rootTDAOrganizer,
|
RootTaskDisplayAreaOrganizer rootTDAOrganizer,
|
||||||
ShellExecutor mainExecutor, DisplayImeController displayImeController,
|
ShellExecutor mainExecutor, DisplayImeController displayImeController,
|
||||||
DisplayInsetsController displayInsetsController,
|
DisplayInsetsController displayInsetsController,
|
||||||
Transitions transitions, TransactionPool transactionPool, IconProvider iconProvider,
|
Transitions transitions, TransactionPool transactionPool, IconProvider iconProvider,
|
||||||
|
Optional<RecentTasksController> recentTasks,
|
||||||
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
||||||
mTaskOrganizer = shellTaskOrganizer;
|
mTaskOrganizer = shellTaskOrganizer;
|
||||||
mSyncQueue = syncQueue;
|
mSyncQueue = syncQueue;
|
||||||
@@ -147,6 +163,7 @@ public class SplitScreenController implements DragAndDropPolicy.Starter,
|
|||||||
mUnfoldControllerProvider = unfoldControllerProvider;
|
mUnfoldControllerProvider = unfoldControllerProvider;
|
||||||
mLogger = new SplitscreenEventLogger();
|
mLogger = new SplitscreenEventLogger();
|
||||||
mIconProvider = iconProvider;
|
mIconProvider = iconProvider;
|
||||||
|
mRecentTasksOptional = recentTasks;
|
||||||
}
|
}
|
||||||
|
|
||||||
public SplitScreen asSplitScreen() {
|
public SplitScreen asSplitScreen() {
|
||||||
@@ -169,7 +186,7 @@ public class SplitScreenController implements DragAndDropPolicy.Starter,
|
|||||||
mStageCoordinator = new StageCoordinator(mContext, DEFAULT_DISPLAY, mSyncQueue,
|
mStageCoordinator = new StageCoordinator(mContext, DEFAULT_DISPLAY, mSyncQueue,
|
||||||
mRootTDAOrganizer, mTaskOrganizer, mDisplayImeController,
|
mRootTDAOrganizer, mTaskOrganizer, mDisplayImeController,
|
||||||
mDisplayInsetsController, mTransitions, mTransactionPool, mLogger,
|
mDisplayInsetsController, mTransitions, mTransactionPool, mLogger,
|
||||||
mIconProvider, mUnfoldControllerProvider);
|
mIconProvider, mRecentTasksOptional, mUnfoldControllerProvider);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
package com.android.wm.shell.splitscreen;
|
package com.android.wm.shell.splitscreen;
|
||||||
|
|
||||||
import static android.app.ActivityOptions.KEY_LAUNCH_ROOT_TASK_TOKEN;
|
import static android.app.ActivityOptions.KEY_LAUNCH_ROOT_TASK_TOKEN;
|
||||||
|
import static android.app.ActivityTaskManager.INVALID_TASK_ID;
|
||||||
import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
|
import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
|
||||||
import static android.view.WindowManager.LayoutParams.TYPE_DOCK_DIVIDER;
|
import static android.view.WindowManager.LayoutParams.TYPE_DOCK_DIVIDER;
|
||||||
import static android.view.WindowManager.TRANSIT_OPEN;
|
import static android.view.WindowManager.TRANSIT_OPEN;
|
||||||
@@ -92,6 +93,7 @@ import com.android.wm.shell.common.split.SplitLayout;
|
|||||||
import com.android.wm.shell.common.split.SplitLayout.SplitPosition;
|
import com.android.wm.shell.common.split.SplitLayout.SplitPosition;
|
||||||
import com.android.wm.shell.common.split.SplitWindowManager;
|
import com.android.wm.shell.common.split.SplitWindowManager;
|
||||||
import com.android.wm.shell.protolog.ShellProtoLogGroup;
|
import com.android.wm.shell.protolog.ShellProtoLogGroup;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.splitscreen.SplitScreenController.ExitReason;
|
import com.android.wm.shell.splitscreen.SplitScreenController.ExitReason;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
@@ -147,6 +149,10 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
private final DisplayInsetsController mDisplayInsetsController;
|
private final DisplayInsetsController mDisplayInsetsController;
|
||||||
private final SplitScreenTransitions mSplitTransitions;
|
private final SplitScreenTransitions mSplitTransitions;
|
||||||
private final SplitscreenEventLogger mLogger;
|
private final SplitscreenEventLogger mLogger;
|
||||||
|
private final Optional<RecentTasksController> mRecentTasks;
|
||||||
|
// Tracks whether we should update the recent tasks. Only allow this to happen in between enter
|
||||||
|
// and exit, since exit itself can trigger a number of changes that update the stages.
|
||||||
|
private boolean mShouldUpdateRecents;
|
||||||
private boolean mExitSplitScreenOnHide;
|
private boolean mExitSplitScreenOnHide;
|
||||||
private boolean mKeyguardOccluded;
|
private boolean mKeyguardOccluded;
|
||||||
|
|
||||||
@@ -191,6 +197,7 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
DisplayInsetsController displayInsetsController, Transitions transitions,
|
DisplayInsetsController displayInsetsController, Transitions transitions,
|
||||||
TransactionPool transactionPool, SplitscreenEventLogger logger,
|
TransactionPool transactionPool, SplitscreenEventLogger logger,
|
||||||
IconProvider iconProvider,
|
IconProvider iconProvider,
|
||||||
|
Optional<RecentTasksController> recentTasks,
|
||||||
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
||||||
mContext = context;
|
mContext = context;
|
||||||
mDisplayId = displayId;
|
mDisplayId = displayId;
|
||||||
@@ -198,6 +205,7 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
mRootTDAOrganizer = rootTDAOrganizer;
|
mRootTDAOrganizer = rootTDAOrganizer;
|
||||||
mTaskOrganizer = taskOrganizer;
|
mTaskOrganizer = taskOrganizer;
|
||||||
mLogger = logger;
|
mLogger = logger;
|
||||||
|
mRecentTasks = recentTasks;
|
||||||
mMainUnfoldController = unfoldControllerProvider.get().orElse(null);
|
mMainUnfoldController = unfoldControllerProvider.get().orElse(null);
|
||||||
mSideUnfoldController = unfoldControllerProvider.get().orElse(null);
|
mSideUnfoldController = unfoldControllerProvider.get().orElse(null);
|
||||||
|
|
||||||
@@ -238,6 +246,7 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
DisplayInsetsController displayInsetsController, SplitLayout splitLayout,
|
DisplayInsetsController displayInsetsController, SplitLayout splitLayout,
|
||||||
Transitions transitions, TransactionPool transactionPool,
|
Transitions transitions, TransactionPool transactionPool,
|
||||||
SplitscreenEventLogger logger,
|
SplitscreenEventLogger logger,
|
||||||
|
Optional<RecentTasksController> recentTasks,
|
||||||
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
Provider<Optional<StageTaskUnfoldController>> unfoldControllerProvider) {
|
||||||
mContext = context;
|
mContext = context;
|
||||||
mDisplayId = displayId;
|
mDisplayId = displayId;
|
||||||
@@ -255,6 +264,7 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
mMainUnfoldController = unfoldControllerProvider.get().orElse(null);
|
mMainUnfoldController = unfoldControllerProvider.get().orElse(null);
|
||||||
mSideUnfoldController = unfoldControllerProvider.get().orElse(null);
|
mSideUnfoldController = unfoldControllerProvider.get().orElse(null);
|
||||||
mLogger = logger;
|
mLogger = logger;
|
||||||
|
mRecentTasks = recentTasks;
|
||||||
transitions.addHandler(this);
|
transitions.addHandler(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -560,12 +570,23 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
|
|
||||||
private void applyExitSplitScreen(StageTaskListener childrenToTop,
|
private void applyExitSplitScreen(StageTaskListener childrenToTop,
|
||||||
WindowContainerTransaction wct, @ExitReason int exitReason) {
|
WindowContainerTransaction wct, @ExitReason int exitReason) {
|
||||||
|
mRecentTasks.ifPresent(recentTasks -> {
|
||||||
|
// Notify recents if we are exiting in a way that breaks the pair, and disable further
|
||||||
|
// updates to splits in the recents until we enter split again
|
||||||
|
if (shouldBreakPairedTaskInRecents(exitReason) && mShouldUpdateRecents) {
|
||||||
|
recentTasks.removeSplitPair(mMainStage.getTopVisibleChildTaskId());
|
||||||
|
recentTasks.removeSplitPair(mSideStage.getTopVisibleChildTaskId());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
mShouldUpdateRecents = false;
|
||||||
|
|
||||||
mSideStage.removeAllTasks(wct, childrenToTop == mSideStage);
|
mSideStage.removeAllTasks(wct, childrenToTop == mSideStage);
|
||||||
mMainStage.deactivate(wct, childrenToTop == mMainStage);
|
mMainStage.deactivate(wct, childrenToTop == mMainStage);
|
||||||
mTaskOrganizer.applyTransaction(wct);
|
mTaskOrganizer.applyTransaction(wct);
|
||||||
mSyncQueue.runInSync(t -> t
|
mSyncQueue.runInSync(t -> t
|
||||||
.setWindowCrop(mMainStage.mRootLeash, null)
|
.setWindowCrop(mMainStage.mRootLeash, null)
|
||||||
.setWindowCrop(mSideStage.mRootLeash, null));
|
.setWindowCrop(mSideStage.mRootLeash, null));
|
||||||
|
|
||||||
// Hide divider and reset its position.
|
// Hide divider and reset its position.
|
||||||
setDividerVisibility(false);
|
setDividerVisibility(false);
|
||||||
mSplitLayout.resetDividerPosition();
|
mSplitLayout.resetDividerPosition();
|
||||||
@@ -579,6 +600,23 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns whether the split pair in the recent tasks list should be broken.
|
||||||
|
*/
|
||||||
|
private boolean shouldBreakPairedTaskInRecents(@ExitReason int exitReason) {
|
||||||
|
switch (exitReason) {
|
||||||
|
// One of the apps doesn't support MW
|
||||||
|
case EXIT_REASON_APP_DOES_NOT_SUPPORT_MULTIWINDOW:
|
||||||
|
// User has explicitly dragged the divider to dismiss split
|
||||||
|
case EXIT_REASON_DRAG_DIVIDER:
|
||||||
|
// Either of the split apps have finished
|
||||||
|
case EXIT_REASON_APP_FINISHED:
|
||||||
|
return true;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Unlike exitSplitScreen, this takes a stagetype vs an actual stage-reference and populates
|
* Unlike exitSplitScreen, this takes a stagetype vs an actual stage-reference and populates
|
||||||
* an existing WindowContainerTransaction (rather than applying immediately). This is intended
|
* an existing WindowContainerTransaction (rather than applying immediately). This is intended
|
||||||
@@ -645,12 +683,28 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
mLogger.logSideStageAppChange(getSideStagePosition(), mSideStage.getTopChildTaskUid(),
|
mLogger.logSideStageAppChange(getSideStagePosition(), mSideStage.getTopChildTaskUid(),
|
||||||
mSplitLayout.isLandscape());
|
mSplitLayout.isLandscape());
|
||||||
}
|
}
|
||||||
|
updateRecentTasksSplitPair();
|
||||||
|
|
||||||
for (int i = mListeners.size() - 1; i >= 0; --i) {
|
for (int i = mListeners.size() - 1; i >= 0; --i) {
|
||||||
mListeners.get(i).onTaskStageChanged(taskId, stage, visible);
|
mListeners.get(i).onTaskStageChanged(taskId, stage, visible);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void updateRecentTasksSplitPair() {
|
||||||
|
if (!mShouldUpdateRecents) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
mRecentTasks.ifPresent(recentTasks -> {
|
||||||
|
int mainStageTopTaskId = mMainStage.getTopVisibleChildTaskId();
|
||||||
|
int sideStageTopTaskId = mSideStage.getTopVisibleChildTaskId();
|
||||||
|
if (mainStageTopTaskId != INVALID_TASK_ID && sideStageTopTaskId != INVALID_TASK_ID) {
|
||||||
|
// Update the pair for the top tasks
|
||||||
|
recentTasks.addSplitPair(mainStageTopTaskId, sideStageTopTaskId);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
private void sendSplitVisibilityChanged() {
|
private void sendSplitVisibilityChanged() {
|
||||||
for (int i = mListeners.size() - 1; i >= 0; --i) {
|
for (int i = mListeners.size() - 1; i >= 0; --i) {
|
||||||
final SplitScreen.SplitScreenListener l = mListeners.get(i);
|
final SplitScreen.SplitScreenListener l = mListeners.get(i);
|
||||||
@@ -784,14 +838,18 @@ class StageCoordinator implements SplitLayout.SplitLayoutHandler,
|
|||||||
mSyncQueue.queue(wct);
|
mSyncQueue.queue(wct);
|
||||||
mSyncQueue.runInSync(t -> updateSurfaceBounds(mSplitLayout, t));
|
mSyncQueue.runInSync(t -> updateSurfaceBounds(mSplitLayout, t));
|
||||||
}
|
}
|
||||||
if (!mLogger.hasStartedSession() && mMainStageListener.mHasChildren
|
if (mMainStageListener.mHasChildren && mSideStageListener.mHasChildren) {
|
||||||
&& mSideStageListener.mHasChildren) {
|
mShouldUpdateRecents = true;
|
||||||
|
updateRecentTasksSplitPair();
|
||||||
|
|
||||||
|
if (!mLogger.hasStartedSession()) {
|
||||||
mLogger.logEnter(mSplitLayout.getDividerPositionAsFraction(),
|
mLogger.logEnter(mSplitLayout.getDividerPositionAsFraction(),
|
||||||
getMainStagePosition(), mMainStage.getTopChildTaskUid(),
|
getMainStagePosition(), mMainStage.getTopChildTaskUid(),
|
||||||
getSideStagePosition(), mSideStage.getTopChildTaskUid(),
|
getSideStagePosition(), mSideStage.getTopChildTaskUid(),
|
||||||
mSplitLayout.isLandscape());
|
mSplitLayout.isLandscape());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@VisibleForTesting
|
@VisibleForTesting
|
||||||
IBinder onSnappedToDismissTransition(boolean mainStageToTop) {
|
IBinder onSnappedToDismissTransition(boolean mainStageToTop) {
|
||||||
|
|||||||
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
package com.android.wm.shell.splitscreen;
|
package com.android.wm.shell.splitscreen;
|
||||||
|
|
||||||
|
import static android.app.ActivityTaskManager.INVALID_TASK_ID;
|
||||||
import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
|
import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
|
||||||
import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
|
import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
|
||||||
import static android.app.WindowConfiguration.WINDOWING_MODE_MULTI_WINDOW;
|
import static android.app.WindowConfiguration.WINDOWING_MODE_MULTI_WINDOW;
|
||||||
@@ -112,6 +113,19 @@ class StageTaskListener implements ShellTaskOrganizer.TaskListener {
|
|||||||
return mChildrenTaskInfo.contains(taskId);
|
return mChildrenTaskInfo.contains(taskId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the top visible child task's id.
|
||||||
|
*/
|
||||||
|
int getTopVisibleChildTaskId() {
|
||||||
|
for (int i = mChildrenTaskInfo.size() - 1; i >= 0; --i) {
|
||||||
|
final ActivityManager.RunningTaskInfo info = mChildrenTaskInfo.valueAt(i);
|
||||||
|
if (info.isVisible) {
|
||||||
|
return info.taskId;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return INVALID_TASK_ID;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the top activity uid for the top child task.
|
* Returns the top activity uid for the top child task.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ import android.view.SurfaceControl;
|
|||||||
import androidx.test.filters.SmallTest;
|
import androidx.test.filters.SmallTest;
|
||||||
|
|
||||||
import com.android.wm.shell.common.SyncTransactionQueue;
|
import com.android.wm.shell.common.SyncTransactionQueue;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
|
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
@@ -52,6 +53,8 @@ public class FullscreenTaskListenerTest {
|
|||||||
@Mock
|
@Mock
|
||||||
private FullscreenUnfoldController mUnfoldController;
|
private FullscreenUnfoldController mUnfoldController;
|
||||||
@Mock
|
@Mock
|
||||||
|
private RecentTasksController mRecentTasksController;
|
||||||
|
@Mock
|
||||||
private SurfaceControl mSurfaceControl;
|
private SurfaceControl mSurfaceControl;
|
||||||
|
|
||||||
private Optional<FullscreenUnfoldController> mFullscreenUnfoldController;
|
private Optional<FullscreenUnfoldController> mFullscreenUnfoldController;
|
||||||
@@ -62,7 +65,8 @@ public class FullscreenTaskListenerTest {
|
|||||||
public void setup() {
|
public void setup() {
|
||||||
MockitoAnnotations.initMocks(this);
|
MockitoAnnotations.initMocks(this);
|
||||||
mFullscreenUnfoldController = Optional.of(mUnfoldController);
|
mFullscreenUnfoldController = Optional.of(mUnfoldController);
|
||||||
mListener = new FullscreenTaskListener(mSyncQueue, mFullscreenUnfoldController);
|
mListener = new FullscreenTaskListener(mSyncQueue, mFullscreenUnfoldController,
|
||||||
|
Optional.empty());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
|
|||||||
@@ -36,6 +36,7 @@ import com.android.wm.shell.common.DisplayInsetsController;
|
|||||||
import com.android.wm.shell.common.SyncTransactionQueue;
|
import com.android.wm.shell.common.SyncTransactionQueue;
|
||||||
import com.android.wm.shell.common.TransactionPool;
|
import com.android.wm.shell.common.TransactionPool;
|
||||||
import com.android.wm.shell.common.split.SplitLayout;
|
import com.android.wm.shell.common.split.SplitLayout;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
@@ -72,10 +73,11 @@ public class SplitTestUtils {
|
|||||||
DisplayInsetsController insetsController, SplitLayout splitLayout,
|
DisplayInsetsController insetsController, SplitLayout splitLayout,
|
||||||
Transitions transitions, TransactionPool transactionPool,
|
Transitions transitions, TransactionPool transactionPool,
|
||||||
SplitscreenEventLogger logger,
|
SplitscreenEventLogger logger,
|
||||||
|
Optional<RecentTasksController> recentTasks,
|
||||||
Provider<Optional<StageTaskUnfoldController>> unfoldController) {
|
Provider<Optional<StageTaskUnfoldController>> unfoldController) {
|
||||||
super(context, displayId, syncQueue, rootTDAOrganizer, taskOrganizer, mainStage,
|
super(context, displayId, syncQueue, rootTDAOrganizer, taskOrganizer, mainStage,
|
||||||
sideStage, imeController, insetsController, splitLayout, transitions,
|
sideStage, imeController, insetsController, splitLayout, transitions,
|
||||||
transactionPool, logger, unfoldController);
|
transactionPool, logger, recentTasks, unfoldController);
|
||||||
|
|
||||||
// Prepare default TaskDisplayArea for testing.
|
// Prepare default TaskDisplayArea for testing.
|
||||||
mDisplayAreaInfo = new DisplayAreaInfo(
|
mDisplayAreaInfo = new DisplayAreaInfo(
|
||||||
|
|||||||
@@ -66,6 +66,7 @@ import com.android.wm.shell.common.ShellExecutor;
|
|||||||
import com.android.wm.shell.common.SyncTransactionQueue;
|
import com.android.wm.shell.common.SyncTransactionQueue;
|
||||||
import com.android.wm.shell.common.TransactionPool;
|
import com.android.wm.shell.common.TransactionPool;
|
||||||
import com.android.wm.shell.common.split.SplitLayout;
|
import com.android.wm.shell.common.split.SplitLayout;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
@@ -120,8 +121,7 @@ public class SplitTransitionTests extends ShellTestCase {
|
|||||||
mStageCoordinator = new SplitTestUtils.TestStageCoordinator(mContext, DEFAULT_DISPLAY,
|
mStageCoordinator = new SplitTestUtils.TestStageCoordinator(mContext, DEFAULT_DISPLAY,
|
||||||
mSyncQueue, mRootTDAOrganizer, mTaskOrganizer, mMainStage, mSideStage,
|
mSyncQueue, mRootTDAOrganizer, mTaskOrganizer, mMainStage, mSideStage,
|
||||||
mDisplayImeController, mDisplayInsetsController, mSplitLayout, mTransitions,
|
mDisplayImeController, mDisplayInsetsController, mSplitLayout, mTransitions,
|
||||||
mTransactionPool,
|
mTransactionPool, mLogger, Optional.empty(), Optional::empty);
|
||||||
mLogger, Optional::empty);
|
|
||||||
mSplitScreenTransitions = mStageCoordinator.getSplitTransitions();
|
mSplitScreenTransitions = mStageCoordinator.getSplitTransitions();
|
||||||
doAnswer((Answer<IBinder>) invocation -> mock(IBinder.class))
|
doAnswer((Answer<IBinder>) invocation -> mock(IBinder.class))
|
||||||
.when(mTransitions).startTransition(anyInt(), any(), any());
|
.when(mTransitions).startTransition(anyInt(), any(), any());
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ import com.android.wm.shell.common.DisplayInsetsController;
|
|||||||
import com.android.wm.shell.common.SyncTransactionQueue;
|
import com.android.wm.shell.common.SyncTransactionQueue;
|
||||||
import com.android.wm.shell.common.TransactionPool;
|
import com.android.wm.shell.common.TransactionPool;
|
||||||
import com.android.wm.shell.common.split.SplitLayout;
|
import com.android.wm.shell.common.split.SplitLayout;
|
||||||
|
import com.android.wm.shell.recents.RecentTasksController;
|
||||||
import com.android.wm.shell.transition.Transitions;
|
import com.android.wm.shell.transition.Transitions;
|
||||||
|
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
@@ -198,7 +199,8 @@ public class StageCoordinatorTests extends ShellTestCase {
|
|||||||
return new SplitTestUtils.TestStageCoordinator(mContext, DEFAULT_DISPLAY,
|
return new SplitTestUtils.TestStageCoordinator(mContext, DEFAULT_DISPLAY,
|
||||||
mSyncQueue, mRootTDAOrganizer, mTaskOrganizer, mMainStage, mSideStage,
|
mSyncQueue, mRootTDAOrganizer, mTaskOrganizer, mMainStage, mSideStage,
|
||||||
mDisplayImeController, mDisplayInsetsController, splitLayout,
|
mDisplayImeController, mDisplayInsetsController, splitLayout,
|
||||||
mTransitions, mTransactionPool, mLogger, new UnfoldControllerProvider());
|
mTransitions, mTransactionPool, mLogger, Optional.empty(),
|
||||||
|
new UnfoldControllerProvider());
|
||||||
}
|
}
|
||||||
|
|
||||||
private class UnfoldControllerProvider implements
|
private class UnfoldControllerProvider implements
|
||||||
|
|||||||
Reference in New Issue
Block a user