Loading core/proto/android/server/windowmanagerservice.proto +28 −3 Original line number Diff line number Diff line Loading @@ -150,9 +150,9 @@ message DisplayContentProto { // Will be removed soon. optional PinnedStackControllerProto pinned_stack_controller = 5 [deprecated=true]; /* non app windows */ repeated WindowTokenProto above_app_windows = 6; repeated WindowTokenProto below_app_windows = 7; repeated WindowTokenProto ime_windows = 8; repeated WindowTokenProto above_app_windows = 6 [deprecated=true]; repeated WindowTokenProto below_app_windows = 7 [deprecated=true]; repeated WindowTokenProto ime_windows = 8 [deprecated=true]; optional int32 dpi = 9; optional .android.view.DisplayInfoProto display_info = 10; optional int32 rotation = 11; Loading @@ -165,8 +165,33 @@ message DisplayContentProto { repeated IdentifierProto closing_apps = 18; repeated IdentifierProto changing_apps = 19; repeated WindowTokenProto overlay_windows = 20; optional DisplayAreaProto root_display_area = 21; } /* represents DisplayArea object */ message DisplayAreaProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; optional WindowContainerProto window_container = 1; optional string name = 2 [ (.android.privacy).dest = DEST_EXPLICIT ]; repeated DisplayAreaChildProto children = 3; } /* represents a generic child of a DisplayArea */ message DisplayAreaChildProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; /* At most one of the following should be present: */ /* represents a DisplayArea child */ optional DisplayAreaProto display_area = 1; /* represents a WindowToken child */ optional WindowTokenProto window = 2; /* represents an unknown child - the class name is recorded */ repeated string unknown = 3; } /* represents DisplayFrames */ message DisplayFramesProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; Loading data/etc/services.core.protolog.json +12 −6 Original line number Diff line number Diff line Loading @@ -1573,12 +1573,6 @@ "group": "WM_ERROR", "at": "com\/android\/server\/wm\/WindowManagerService.java" }, "1004585481": { "message": "%s forcing orientation to %d for display id=%d", "level": "VERBOSE", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayContent.java" }, "1051545910": { "message": "Exit animation finished in %s: remove=%b", "level": "VERBOSE", Loading Loading @@ -1717,6 +1711,12 @@ "group": "WM_DEBUG_IME", "at": "com\/android\/server\/wm\/ImeInsetsSourceProvider.java" }, "1389009035": { "message": "NonAppWindowContainer cannot set orientation: %s", "level": "WARN", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayContent.java" }, "1401700824": { "message": "Window drawn win=%s", "level": "DEBUG", Loading Loading @@ -1891,6 +1891,12 @@ "group": "WM_DEBUG_STARTING_WINDOW", "at": "com\/android\/server\/wm\/ActivityRecord.java" }, "1674747211": { "message": "%s forcing orientation to %d for display id=%d", "level": "VERBOSE", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayArea.java" }, "1677260366": { "message": "Finish starting %s: first real window is shown, no animation", "level": "VERBOSE", Loading services/core/java/com/android/server/wm/DisplayArea.java 0 → 100644 +265 −0 Original line number Diff line number Diff line /* * Copyright (C) 2020 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server.wm; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_BEHIND; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSET; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; import static android.view.WindowManager.TRANSIT_KEYGUARD_UNOCCLUDE; import static android.view.WindowManagerPolicyConstants.APPLICATION_LAYER; import static com.android.internal.util.Preconditions.checkState; import static com.android.server.wm.DisplayAreaChildProto.DISPLAY_AREA; import static com.android.server.wm.DisplayAreaChildProto.UNKNOWN; import static com.android.server.wm.DisplayAreaChildProto.WINDOW; import static com.android.server.wm.DisplayAreaProto.CHILDREN; import static com.android.server.wm.DisplayAreaProto.NAME; import static com.android.server.wm.DisplayAreaProto.WINDOW_CONTAINER; import static com.android.server.wm.ProtoLogGroup.WM_DEBUG_ORIENTATION; import android.graphics.Rect; import android.util.proto.ProtoOutputStream; import com.android.server.policy.WindowManagerPolicy; import com.android.server.protolog.common.ProtoLog; import java.util.Comparator; import java.util.function.Predicate; /** * Container for grouping WindowContainer below DisplayContent. * * DisplayAreas are managed by a {@link DisplayAreaPolicy}, and can override configurations and * can be leashed. * * DisplayAreas can contain nested DisplayAreas. * * DisplayAreas come in three flavors, to ensure that windows have the right Z-Order: * - BELOW_TASKS: Can only contain BELOW_TASK DisplayAreas and WindowTokens that go below tasks. * - ABOVE_TASKS: Can only contain ABOVE_TASK DisplayAreas and WindowTokens that go above tasks. * - ANY: Can contain any kind of DisplayArea, and any kind of WindowToken or the Task container. * Cannot have a sibling that is of type ANY. * * @param <T> type of the children of the DisplayArea. */ public class DisplayArea<T extends WindowContainer> extends WindowContainer<T> { protected final Type mType; private final String mName; DisplayArea(WindowManagerService wms, Type type, String name) { super(wms); // TODO(display-area): move this up to ConfigurationContainer mOrientation = SCREEN_ORIENTATION_UNSET; mType = type; mName = name; } @Override void onChildPositionChanged(WindowContainer child) { super.onChildPositionChanged(child); // Verify that we have proper ordering Type.checkChild(mType, Type.typeOf(child)); if (child instanceof ActivityStack) { // TODO(display-area): ActivityStacks are type ANY, but are allowed to have siblings. // They might need a separate type. return; } for (int i = 1; i < getChildCount(); i++) { final WindowContainer top = getChildAt(i - 1); final WindowContainer bottom = getChildAt(i); if (child == top || child == bottom) { Type.checkSiblings(Type.typeOf(top), Type.typeOf(bottom)); } } } @Override boolean fillsParent() { return true; } @Override String getName() { return mName; } @Override public final void dumpDebug(ProtoOutputStream proto, long fieldId, int logLevel) { final long token = proto.start(fieldId); super.dumpDebug(proto, WINDOW_CONTAINER, logLevel); proto.write(NAME, mName); for (int i = 0; i < getChildCount(); i++) { final long childToken = proto.start(CHILDREN); final T child = getChildAt(i); if (child instanceof ActivityStack) { // TODO(display-area): Dump stacks & tasks here, instead of in DisplayContent's // dumpDebug. For now, skip them here to avoid dumping them as UNKNOWN. } else if (child instanceof WindowToken) { ((WindowToken) child).dumpDebug(proto, WINDOW, logLevel); } else if (child instanceof DisplayArea) { child.dumpDebug(proto, DISPLAY_AREA, logLevel); } else { proto.write(UNKNOWN, child.getClass().getSimpleName()); } proto.end(childToken); } proto.end(token); } /** * DisplayArea that contains WindowTokens, and orders them according to their type. */ public static class Tokens extends DisplayArea<WindowToken> { int mLastKeyguardForcedOrientation = SCREEN_ORIENTATION_UNSPECIFIED; private final Comparator<WindowToken> mWindowComparator = Comparator.comparingInt(WindowToken::getWindowLayerFromType); private final Predicate<WindowState> mGetOrientingWindow = w -> { final WindowManagerPolicy policy = mWmService.mPolicy; if (policy.isKeyguardHostWindow(w.mAttrs)) { if (mWmService.mKeyguardGoingAway) { return false; } // Consider unoccluding only when all unknown visibilities have been // resolved, as otherwise we just may be starting another occluding activity. final boolean isUnoccluding = mDisplayContent.mAppTransition.getAppTransition() == TRANSIT_KEYGUARD_UNOCCLUDE && mDisplayContent.mUnknownAppVisibilityController.allResolved(); // If keyguard is showing, or we're unoccluding, force the keyguard's orientation, // even if SystemUI hasn't updated the attrs yet. if (policy.isKeyguardShowingAndNotOccluded() || isUnoccluding) { return true; } } final int req = w.mAttrs.screenOrientation; if (req == SCREEN_ORIENTATION_UNSPECIFIED || req == SCREEN_ORIENTATION_BEHIND || req == SCREEN_ORIENTATION_UNSET) { return false; } return true; }; Tokens(WindowManagerService wms, Type type, String name) { super(wms, type, name); } void addChild(WindowToken token) { addChild(token, mWindowComparator); } @Override int getOrientation(int candidate) { // Find a window requesting orientation. final WindowState win = getWindow(mGetOrientingWindow); if (win == null) { return candidate; } int req = win.mAttrs.screenOrientation; ProtoLog.v(WM_DEBUG_ORIENTATION, "%s forcing orientation to %d for display id=%d", win, req, mDisplayContent.getDisplayId()); if (mWmService.mPolicy.isKeyguardHostWindow(win.mAttrs)) { // SystemUI controls the Keyguard orientation asynchronously, and mAttrs may be // stale. We record / use the last known override. if (req != SCREEN_ORIENTATION_UNSET && req != SCREEN_ORIENTATION_UNSPECIFIED) { mLastKeyguardForcedOrientation = req; } else { req = mLastKeyguardForcedOrientation; } } return req; } } /** * Top-most DisplayArea under DisplayContent. */ public static class Root extends DisplayArea<DisplayArea> { private final Dimmer mDimmer = new Dimmer(this); private final Rect mTmpDimBoundsRect = new Rect(); Root(WindowManagerService wms) { super(wms, Type.ANY, "DisplayArea.Root"); } @Override Dimmer getDimmer() { return mDimmer; } @Override void prepareSurfaces() { mDimmer.resetDimStates(); super.prepareSurfaces(); getBounds(mTmpDimBoundsRect); if (mDimmer.updateDims(getPendingTransaction(), mTmpDimBoundsRect)) { scheduleAnimation(); } } } enum Type { /** Can only contain WindowTokens above the APPLICATION_LAYER. */ ABOVE_TASKS, /** Can only contain WindowTokens below the APPLICATION_LAYER. */ BELOW_TASKS, /** Can contain anything. */ ANY; static void checkSiblings(Type bottom, Type top) { checkState(!(bottom == ANY && top == ANY), "ANY cannot be a sibling of ANY"); checkState(!(bottom != BELOW_TASKS && top == BELOW_TASKS), bottom + " must be above BELOW_TASKS"); checkState(!(bottom == ABOVE_TASKS && top != ABOVE_TASKS), top + " must be below ABOVE_TASKS"); } static void checkChild(Type parent, Type child) { switch (parent) { case ABOVE_TASKS: checkState(child == ABOVE_TASKS, "ABOVE_TASKS can only contain ABOVE_TASKS"); break; case BELOW_TASKS: checkState(child == BELOW_TASKS, "BELOW_TASKS can only contain BELOW_TASKS"); break; } } static Type typeOf(WindowContainer c) { if (c instanceof DisplayArea) { return ((DisplayArea) c).mType; } else if (c instanceof WindowToken && !(c instanceof ActivityRecord)) { return typeOf((WindowToken) c); } else if (c instanceof ActivityStack) { return ANY; } else { throw new IllegalArgumentException("Unknown container: " + c); } } private static Type typeOf(WindowToken c) { return c.getWindowLayerFromType() < APPLICATION_LAYER ? BELOW_TASKS : ABOVE_TASKS; } } } services/core/java/com/android/server/wm/DisplayAreaPolicy.java 0 → 100644 +123 −0 Original line number Diff line number Diff line /* * Copyright (C) 2020 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server.wm; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD; import com.android.server.wm.DisplayContent.TaskContainers; /** * Policy that manages DisplayAreas. */ public abstract class DisplayAreaPolicy { protected final WindowManagerService mWmService; protected final DisplayContent mContent; /** * The root DisplayArea. Attach all DisplayAreas to this area (directly or indirectly). */ protected final DisplayArea.Root mRoot; /** * The IME container. The IME's windows are automatically added to this container. */ protected final DisplayArea<? extends WindowContainer> mImeContainer; /** * The Tasks container. Tasks etc. are automatically added to this container. */ protected final TaskContainers mTaskContainers; DisplayAreaPolicy(WindowManagerService wmService, DisplayContent content, DisplayArea.Root root, DisplayArea<? extends WindowContainer> imeContainer, TaskContainers taskContainers) { mWmService = wmService; mContent = content; mRoot = root; mImeContainer = imeContainer; mTaskContainers = taskContainers; } /** * Called to ask the policy to set up the DisplayArea hierarchy. At a minimum this must: * * - attach mImeContainer to mRoot (or one of its descendants) * - attach mTaskStacks to mRoot (or one of its descendants) * * Additionally, this is the right place to set up any other DisplayAreas as desired. */ public abstract void attachDisplayAreas(); /** * Called to ask the policy to attach the given WindowToken to the DisplayArea hierarchy. * * This must attach the token to mRoot (or one of its descendants). */ public abstract void addWindow(WindowToken token); /** * Default policy that has no special features. */ public static class Default extends DisplayAreaPolicy { public Default(WindowManagerService wmService, DisplayContent content, DisplayArea.Root root, DisplayArea<? extends WindowContainer> imeContainer, TaskContainers taskContainers) { super(wmService, content, root, imeContainer, taskContainers); } private final DisplayArea.Tokens mBelow = new DisplayArea.Tokens(mWmService, DisplayArea.Type.BELOW_TASKS, "BelowTasks"); private final DisplayArea<DisplayArea> mAbove = new DisplayArea<>(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasks"); private final DisplayArea.Tokens mAboveBelowIme = new DisplayArea.Tokens(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasksBelowIme"); private final DisplayArea.Tokens mAboveAboveIme = new DisplayArea.Tokens(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasksAboveIme"); @Override public void attachDisplayAreas() { mRoot.addChild(mBelow, 0); mRoot.addChild(mTaskContainers, 1); mRoot.addChild(mAbove, 2); mAbove.addChild(mAboveBelowIme, 0); mAbove.addChild(mImeContainer, 1); mAbove.addChild(mAboveAboveIme, 2); } @Override public void addWindow(WindowToken token) { switch (DisplayArea.Type.typeOf(token)) { case ABOVE_TASKS: if (token.getWindowLayerFromType() < mWmService.mPolicy.getWindowLayerFromTypeLw(TYPE_INPUT_METHOD)) { mAboveBelowIme.addChild(token); } else { mAboveAboveIme.addChild(token); } break; case BELOW_TASKS: mBelow.addChild(token); break; default: throw new IllegalArgumentException("don't know how to sort " + token); } } } } services/core/java/com/android/server/wm/DisplayContent.java +26 −137 File changed.Preview size limit exceeded, changes collapsed. Show changes Loading
core/proto/android/server/windowmanagerservice.proto +28 −3 Original line number Diff line number Diff line Loading @@ -150,9 +150,9 @@ message DisplayContentProto { // Will be removed soon. optional PinnedStackControllerProto pinned_stack_controller = 5 [deprecated=true]; /* non app windows */ repeated WindowTokenProto above_app_windows = 6; repeated WindowTokenProto below_app_windows = 7; repeated WindowTokenProto ime_windows = 8; repeated WindowTokenProto above_app_windows = 6 [deprecated=true]; repeated WindowTokenProto below_app_windows = 7 [deprecated=true]; repeated WindowTokenProto ime_windows = 8 [deprecated=true]; optional int32 dpi = 9; optional .android.view.DisplayInfoProto display_info = 10; optional int32 rotation = 11; Loading @@ -165,8 +165,33 @@ message DisplayContentProto { repeated IdentifierProto closing_apps = 18; repeated IdentifierProto changing_apps = 19; repeated WindowTokenProto overlay_windows = 20; optional DisplayAreaProto root_display_area = 21; } /* represents DisplayArea object */ message DisplayAreaProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; optional WindowContainerProto window_container = 1; optional string name = 2 [ (.android.privacy).dest = DEST_EXPLICIT ]; repeated DisplayAreaChildProto children = 3; } /* represents a generic child of a DisplayArea */ message DisplayAreaChildProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; /* At most one of the following should be present: */ /* represents a DisplayArea child */ optional DisplayAreaProto display_area = 1; /* represents a WindowToken child */ optional WindowTokenProto window = 2; /* represents an unknown child - the class name is recorded */ repeated string unknown = 3; } /* represents DisplayFrames */ message DisplayFramesProto { option (.android.msg_privacy).dest = DEST_AUTOMATIC; Loading
data/etc/services.core.protolog.json +12 −6 Original line number Diff line number Diff line Loading @@ -1573,12 +1573,6 @@ "group": "WM_ERROR", "at": "com\/android\/server\/wm\/WindowManagerService.java" }, "1004585481": { "message": "%s forcing orientation to %d for display id=%d", "level": "VERBOSE", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayContent.java" }, "1051545910": { "message": "Exit animation finished in %s: remove=%b", "level": "VERBOSE", Loading Loading @@ -1717,6 +1711,12 @@ "group": "WM_DEBUG_IME", "at": "com\/android\/server\/wm\/ImeInsetsSourceProvider.java" }, "1389009035": { "message": "NonAppWindowContainer cannot set orientation: %s", "level": "WARN", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayContent.java" }, "1401700824": { "message": "Window drawn win=%s", "level": "DEBUG", Loading Loading @@ -1891,6 +1891,12 @@ "group": "WM_DEBUG_STARTING_WINDOW", "at": "com\/android\/server\/wm\/ActivityRecord.java" }, "1674747211": { "message": "%s forcing orientation to %d for display id=%d", "level": "VERBOSE", "group": "WM_DEBUG_ORIENTATION", "at": "com\/android\/server\/wm\/DisplayArea.java" }, "1677260366": { "message": "Finish starting %s: first real window is shown, no animation", "level": "VERBOSE", Loading
services/core/java/com/android/server/wm/DisplayArea.java 0 → 100644 +265 −0 Original line number Diff line number Diff line /* * Copyright (C) 2020 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server.wm; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_BEHIND; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSET; import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; import static android.view.WindowManager.TRANSIT_KEYGUARD_UNOCCLUDE; import static android.view.WindowManagerPolicyConstants.APPLICATION_LAYER; import static com.android.internal.util.Preconditions.checkState; import static com.android.server.wm.DisplayAreaChildProto.DISPLAY_AREA; import static com.android.server.wm.DisplayAreaChildProto.UNKNOWN; import static com.android.server.wm.DisplayAreaChildProto.WINDOW; import static com.android.server.wm.DisplayAreaProto.CHILDREN; import static com.android.server.wm.DisplayAreaProto.NAME; import static com.android.server.wm.DisplayAreaProto.WINDOW_CONTAINER; import static com.android.server.wm.ProtoLogGroup.WM_DEBUG_ORIENTATION; import android.graphics.Rect; import android.util.proto.ProtoOutputStream; import com.android.server.policy.WindowManagerPolicy; import com.android.server.protolog.common.ProtoLog; import java.util.Comparator; import java.util.function.Predicate; /** * Container for grouping WindowContainer below DisplayContent. * * DisplayAreas are managed by a {@link DisplayAreaPolicy}, and can override configurations and * can be leashed. * * DisplayAreas can contain nested DisplayAreas. * * DisplayAreas come in three flavors, to ensure that windows have the right Z-Order: * - BELOW_TASKS: Can only contain BELOW_TASK DisplayAreas and WindowTokens that go below tasks. * - ABOVE_TASKS: Can only contain ABOVE_TASK DisplayAreas and WindowTokens that go above tasks. * - ANY: Can contain any kind of DisplayArea, and any kind of WindowToken or the Task container. * Cannot have a sibling that is of type ANY. * * @param <T> type of the children of the DisplayArea. */ public class DisplayArea<T extends WindowContainer> extends WindowContainer<T> { protected final Type mType; private final String mName; DisplayArea(WindowManagerService wms, Type type, String name) { super(wms); // TODO(display-area): move this up to ConfigurationContainer mOrientation = SCREEN_ORIENTATION_UNSET; mType = type; mName = name; } @Override void onChildPositionChanged(WindowContainer child) { super.onChildPositionChanged(child); // Verify that we have proper ordering Type.checkChild(mType, Type.typeOf(child)); if (child instanceof ActivityStack) { // TODO(display-area): ActivityStacks are type ANY, but are allowed to have siblings. // They might need a separate type. return; } for (int i = 1; i < getChildCount(); i++) { final WindowContainer top = getChildAt(i - 1); final WindowContainer bottom = getChildAt(i); if (child == top || child == bottom) { Type.checkSiblings(Type.typeOf(top), Type.typeOf(bottom)); } } } @Override boolean fillsParent() { return true; } @Override String getName() { return mName; } @Override public final void dumpDebug(ProtoOutputStream proto, long fieldId, int logLevel) { final long token = proto.start(fieldId); super.dumpDebug(proto, WINDOW_CONTAINER, logLevel); proto.write(NAME, mName); for (int i = 0; i < getChildCount(); i++) { final long childToken = proto.start(CHILDREN); final T child = getChildAt(i); if (child instanceof ActivityStack) { // TODO(display-area): Dump stacks & tasks here, instead of in DisplayContent's // dumpDebug. For now, skip them here to avoid dumping them as UNKNOWN. } else if (child instanceof WindowToken) { ((WindowToken) child).dumpDebug(proto, WINDOW, logLevel); } else if (child instanceof DisplayArea) { child.dumpDebug(proto, DISPLAY_AREA, logLevel); } else { proto.write(UNKNOWN, child.getClass().getSimpleName()); } proto.end(childToken); } proto.end(token); } /** * DisplayArea that contains WindowTokens, and orders them according to their type. */ public static class Tokens extends DisplayArea<WindowToken> { int mLastKeyguardForcedOrientation = SCREEN_ORIENTATION_UNSPECIFIED; private final Comparator<WindowToken> mWindowComparator = Comparator.comparingInt(WindowToken::getWindowLayerFromType); private final Predicate<WindowState> mGetOrientingWindow = w -> { final WindowManagerPolicy policy = mWmService.mPolicy; if (policy.isKeyguardHostWindow(w.mAttrs)) { if (mWmService.mKeyguardGoingAway) { return false; } // Consider unoccluding only when all unknown visibilities have been // resolved, as otherwise we just may be starting another occluding activity. final boolean isUnoccluding = mDisplayContent.mAppTransition.getAppTransition() == TRANSIT_KEYGUARD_UNOCCLUDE && mDisplayContent.mUnknownAppVisibilityController.allResolved(); // If keyguard is showing, or we're unoccluding, force the keyguard's orientation, // even if SystemUI hasn't updated the attrs yet. if (policy.isKeyguardShowingAndNotOccluded() || isUnoccluding) { return true; } } final int req = w.mAttrs.screenOrientation; if (req == SCREEN_ORIENTATION_UNSPECIFIED || req == SCREEN_ORIENTATION_BEHIND || req == SCREEN_ORIENTATION_UNSET) { return false; } return true; }; Tokens(WindowManagerService wms, Type type, String name) { super(wms, type, name); } void addChild(WindowToken token) { addChild(token, mWindowComparator); } @Override int getOrientation(int candidate) { // Find a window requesting orientation. final WindowState win = getWindow(mGetOrientingWindow); if (win == null) { return candidate; } int req = win.mAttrs.screenOrientation; ProtoLog.v(WM_DEBUG_ORIENTATION, "%s forcing orientation to %d for display id=%d", win, req, mDisplayContent.getDisplayId()); if (mWmService.mPolicy.isKeyguardHostWindow(win.mAttrs)) { // SystemUI controls the Keyguard orientation asynchronously, and mAttrs may be // stale. We record / use the last known override. if (req != SCREEN_ORIENTATION_UNSET && req != SCREEN_ORIENTATION_UNSPECIFIED) { mLastKeyguardForcedOrientation = req; } else { req = mLastKeyguardForcedOrientation; } } return req; } } /** * Top-most DisplayArea under DisplayContent. */ public static class Root extends DisplayArea<DisplayArea> { private final Dimmer mDimmer = new Dimmer(this); private final Rect mTmpDimBoundsRect = new Rect(); Root(WindowManagerService wms) { super(wms, Type.ANY, "DisplayArea.Root"); } @Override Dimmer getDimmer() { return mDimmer; } @Override void prepareSurfaces() { mDimmer.resetDimStates(); super.prepareSurfaces(); getBounds(mTmpDimBoundsRect); if (mDimmer.updateDims(getPendingTransaction(), mTmpDimBoundsRect)) { scheduleAnimation(); } } } enum Type { /** Can only contain WindowTokens above the APPLICATION_LAYER. */ ABOVE_TASKS, /** Can only contain WindowTokens below the APPLICATION_LAYER. */ BELOW_TASKS, /** Can contain anything. */ ANY; static void checkSiblings(Type bottom, Type top) { checkState(!(bottom == ANY && top == ANY), "ANY cannot be a sibling of ANY"); checkState(!(bottom != BELOW_TASKS && top == BELOW_TASKS), bottom + " must be above BELOW_TASKS"); checkState(!(bottom == ABOVE_TASKS && top != ABOVE_TASKS), top + " must be below ABOVE_TASKS"); } static void checkChild(Type parent, Type child) { switch (parent) { case ABOVE_TASKS: checkState(child == ABOVE_TASKS, "ABOVE_TASKS can only contain ABOVE_TASKS"); break; case BELOW_TASKS: checkState(child == BELOW_TASKS, "BELOW_TASKS can only contain BELOW_TASKS"); break; } } static Type typeOf(WindowContainer c) { if (c instanceof DisplayArea) { return ((DisplayArea) c).mType; } else if (c instanceof WindowToken && !(c instanceof ActivityRecord)) { return typeOf((WindowToken) c); } else if (c instanceof ActivityStack) { return ANY; } else { throw new IllegalArgumentException("Unknown container: " + c); } } private static Type typeOf(WindowToken c) { return c.getWindowLayerFromType() < APPLICATION_LAYER ? BELOW_TASKS : ABOVE_TASKS; } } }
services/core/java/com/android/server/wm/DisplayAreaPolicy.java 0 → 100644 +123 −0 Original line number Diff line number Diff line /* * Copyright (C) 2020 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server.wm; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD; import com.android.server.wm.DisplayContent.TaskContainers; /** * Policy that manages DisplayAreas. */ public abstract class DisplayAreaPolicy { protected final WindowManagerService mWmService; protected final DisplayContent mContent; /** * The root DisplayArea. Attach all DisplayAreas to this area (directly or indirectly). */ protected final DisplayArea.Root mRoot; /** * The IME container. The IME's windows are automatically added to this container. */ protected final DisplayArea<? extends WindowContainer> mImeContainer; /** * The Tasks container. Tasks etc. are automatically added to this container. */ protected final TaskContainers mTaskContainers; DisplayAreaPolicy(WindowManagerService wmService, DisplayContent content, DisplayArea.Root root, DisplayArea<? extends WindowContainer> imeContainer, TaskContainers taskContainers) { mWmService = wmService; mContent = content; mRoot = root; mImeContainer = imeContainer; mTaskContainers = taskContainers; } /** * Called to ask the policy to set up the DisplayArea hierarchy. At a minimum this must: * * - attach mImeContainer to mRoot (or one of its descendants) * - attach mTaskStacks to mRoot (or one of its descendants) * * Additionally, this is the right place to set up any other DisplayAreas as desired. */ public abstract void attachDisplayAreas(); /** * Called to ask the policy to attach the given WindowToken to the DisplayArea hierarchy. * * This must attach the token to mRoot (or one of its descendants). */ public abstract void addWindow(WindowToken token); /** * Default policy that has no special features. */ public static class Default extends DisplayAreaPolicy { public Default(WindowManagerService wmService, DisplayContent content, DisplayArea.Root root, DisplayArea<? extends WindowContainer> imeContainer, TaskContainers taskContainers) { super(wmService, content, root, imeContainer, taskContainers); } private final DisplayArea.Tokens mBelow = new DisplayArea.Tokens(mWmService, DisplayArea.Type.BELOW_TASKS, "BelowTasks"); private final DisplayArea<DisplayArea> mAbove = new DisplayArea<>(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasks"); private final DisplayArea.Tokens mAboveBelowIme = new DisplayArea.Tokens(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasksBelowIme"); private final DisplayArea.Tokens mAboveAboveIme = new DisplayArea.Tokens(mWmService, DisplayArea.Type.ABOVE_TASKS, "AboveTasksAboveIme"); @Override public void attachDisplayAreas() { mRoot.addChild(mBelow, 0); mRoot.addChild(mTaskContainers, 1); mRoot.addChild(mAbove, 2); mAbove.addChild(mAboveBelowIme, 0); mAbove.addChild(mImeContainer, 1); mAbove.addChild(mAboveAboveIme, 2); } @Override public void addWindow(WindowToken token) { switch (DisplayArea.Type.typeOf(token)) { case ABOVE_TASKS: if (token.getWindowLayerFromType() < mWmService.mPolicy.getWindowLayerFromTypeLw(TYPE_INPUT_METHOD)) { mAboveBelowIme.addChild(token); } else { mAboveAboveIme.addChild(token); } break; case BELOW_TASKS: mBelow.addChild(token); break; default: throw new IllegalArgumentException("don't know how to sort " + token); } } } }
services/core/java/com/android/server/wm/DisplayContent.java +26 −137 File changed.Preview size limit exceeded, changes collapsed. Show changes