功能以及显示效果简介
需求:在双屏显示中,把启动的应用从其中一个屏幕中移动到另一个屏幕中。
操作:通过双指按压应用使其移动,如果移动的距离过小,我们就不移动到另一屏幕,否则移动到另一屏。
功能分析
多屏中移动应用至另一屏本质就是Task的移动。
从窗口层级结构的角度来说,就是把Display1中的DefaultTaskDisplayArea上的Task,移动到Display2中的DefaultTaskDisplayArea上
关键代码知识点
移动Task至另一屏幕
代码路径:frameworks/base/services/core/java/com/android/server/wm/RootWindowContainer.java
/**
* Move root task with all its existing content to specified display.
*
* @param rootTaskId Id of root task to move.
* @param displayId Id of display to move root task to.
* @param onTop Indicates whether container should be place on top or on bottom.
*/
void moveRootTaskToDisplay(int rootTaskId, int displayId, boolean onTop) {
final DisplayContent displayContent = getDisplayContentOrCreate(displayId);
if (displayContent == null) {
throw new IllegalArgumentException("moveRootTaskToDisplay: Unknown displayId="
+ displayId);
}
moveRootTaskToTaskDisplayArea(rootTaskId, displayContent.getDefaultTaskDisplayArea(),
onTop);
}
/**
* Move root task with all its existing content to specified task display area.
*
* @param rootTaskId Id of root task to move.
* @param taskDisplayArea The task display area to move root task to.
* @param onTop Indicates whether container should be place on top or on bottom.
*/
void moveRootTaskToTaskDisplayArea(int rootTaskId, TaskDisplayArea taskDisplayArea,
boolean onTop) {
final Task rootTask = getRootTask(rootTaskId);
if (rootTask == null) {
throw new IllegalArgumentException("moveRootTaskToTaskDisplayArea: Unknown rootTaskId="
+ rootTaskId);
}
final TaskDisplayArea currentTaskDisplayArea = rootTask.getDisplayArea();
if (currentTaskDisplayArea == null) {
throw new IllegalStateException("moveRootTaskToTaskDisplayArea: rootTask=" + rootTask
+ " is not attached to any task display area.");
}
if (taskDisplayArea == null) {
throw new IllegalArgumentException(
"moveRootTaskToTaskDisplayArea: Unknown taskDisplayArea=" + taskDisplayArea);
}
if (currentTaskDisplayArea == taskDisplayArea) {
throw new IllegalArgumentException("Trying to move rootTask=" + rootTask
+ " to its current taskDisplayArea=" + taskDisplayArea);
}
rootTask.reparent(taskDisplayArea, onTop);
// Resume focusable root task after reparenting to another display area.
rootTask.resumeNextFocusAfterReparent();
// TODO(multi-display): resize rootTasks properly if moved from split-screen.
}