Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4a67d569 authored by Wale Ogunwale's avatar Wale Ogunwale Committed by Android (Google) Code Review
Browse files

Merge "Moved window focus calculation to DisplayContent"

parents 00431f70 63d4ecc7
Loading
Loading
Loading
Loading
+64 −0
Original line number Diff line number Diff line
@@ -26,7 +26,10 @@ import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
import static android.view.WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
import static android.view.WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
import static android.view.WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL;
import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_STARTING;
import static android.view.WindowManager.LayoutParams.TYPE_TOAST;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_FOCUS;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_FOCUS_LIGHT;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_VISIBILITY;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_ORIENTATION;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
@@ -764,4 +767,65 @@ class DisplayContent {
            }
        }
    }

    WindowState findFocusedWindow() {
        final AppWindowToken focusedApp = mService.mFocusedApp;

        for (int i = mWindows.size() - 1; i >= 0; i--) {
            final WindowState win = mWindows.get(i);

            if (DEBUG_FOCUS) Slog.v(TAG_WM, "Looking for focus: " + i + " = " + win
                    + ", flags=" + win.mAttrs.flags + ", canReceive=" + win.canReceiveKeys());

            if (!win.canReceiveKeys()) {
                continue;
            }

            final AppWindowToken wtoken = win.mAppToken;

            // If this window's application has been removed, just skip it.
            if (wtoken != null && (wtoken.removed || wtoken.sendingToBottom)) {
                if (DEBUG_FOCUS) Slog.v(TAG_WM, "Skipping " + wtoken + " because "
                        + (wtoken.removed ? "removed" : "sendingToBottom"));
                continue;
            }

            if (focusedApp == null) {
                if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: focusedApp=null"
                        + " using new focus @ " + i + " = " + win);
                return win;
            }

            if (!focusedApp.windowsAreFocusable()) {
                // Current focused app windows aren't focusable...
                if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: focusedApp windows not"
                        + " focusable using new focus @ " + i + " = " + win);
                return win;
            }

            // Descend through all of the app tokens and find the first that either matches
            // win.mAppToken (return win) or mFocusedApp (return null).
            if (wtoken != null && win.mAttrs.type != TYPE_APPLICATION_STARTING) {
                final TaskStack focusedAppStack = focusedApp.mTask.mStack;
                final TaskStack appStack = wtoken.mTask.mStack;

                // TODO: Use WindowContainer.compareTo() once everything is using WindowContainer
                if ((focusedAppStack == appStack
                        && appStack.isFirstGreaterThanSecond(focusedApp, wtoken))
                        || mStacks.indexOf(focusedAppStack) > mStacks.indexOf(appStack)) {
                    // App stack below focused app stack. No focus for you!!!
                    if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM,
                            "findFocusedWindow: Reached focused app=" + focusedApp);
                    return null;
                }
            }

            if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: Found new focus @ "
                    + i + " = " + win);
            return win;
        }

        if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: No focusable windows.");
        return null;
    }
}
+5 −0
Original line number Diff line number Diff line
@@ -684,6 +684,11 @@ class Task implements DimLayer.DimLayerUser {
        return false;
    }

    // TODO: Use WindowContainer.compareTo() once everything is using WindowContainer
    boolean isFirstGreaterThanSecond(AppWindowToken first, AppWindowToken second) {
        return mAppTokens.indexOf(first) > mAppTokens.indexOf(second);
    }

    boolean fillsParent() {
        return mFullscreen || !StackId.isTaskResizeAllowed(mStack.mStackId);
    }
+11 −0
Original line number Diff line number Diff line
@@ -1309,6 +1309,17 @@ public class TaskStack implements DimLayer.DimLayerUser,
        }
    }

    // TODO: Use WindowContainer.compareTo() once everything is using WindowContainer
    boolean isFirstGreaterThanSecond(AppWindowToken first, AppWindowToken second) {
        final Task firstTask = first.mTask;
        final Task secondTask = second.mTask;

        if (firstTask == secondTask) {
            return firstTask.isFirstGreaterThanSecond(first, second);
        }
        return mTasks.indexOf(first) > mTasks.indexOf(second);
    }

    // TODO: Remove once switched to use WindowContainer
    int getOrientation() {
        if (!StackId.canSpecifyOrientation(mStackId)) {
+66 −1
Original line number Diff line number Diff line
@@ -31,7 +31,7 @@ import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
 * The test class is {@link WindowContainerTests} which must be kept up-to-date and ran anytime
 * changes are made to this class.
 */
class WindowContainer {
class WindowContainer implements Comparable<WindowContainer> {

    // The parent of this window container.
    private WindowContainer mParent = null;
@@ -47,6 +47,10 @@ class WindowContainer {
        return mParent;
    }

    // Temp. holders for a chain of containers we are currently processing.
    private final LinkedList<WindowContainer> mTmpChain1 = new LinkedList();
    private final LinkedList<WindowContainer> mTmpChain2 = new LinkedList();

    /**
     * Adds the input window container has a child of this container in order based on the input
     * comparator.
@@ -311,4 +315,65 @@ class WindowContainer {
    boolean fillsParent() {
        return false;
    }

    /**
     * Returns -1, 0, or 1 depending on if the input container is greater than, equal to, or lesser
     * than the input container in terms of z-order.
     */
    @Override
    public int compareTo(WindowContainer other) {
        if (this == other) {
            return 0;
        }

        if (mParent != null && mParent == other.mParent) {
            final LinkedList<WindowContainer> list = mParent.mChildren;
            return list.indexOf(this) > list.indexOf(other) ? 1 : -1;
        }

        final LinkedList<WindowContainer> thisParentChain = mTmpChain1;
        final LinkedList<WindowContainer> otherParentChain = mTmpChain2;
        getParents(thisParentChain);
        other.getParents(otherParentChain);

        // Find the common ancestor of both containers.
        WindowContainer commonAncestor = null;
        WindowContainer thisTop = thisParentChain.peekLast();
        WindowContainer otherTop = otherParentChain.peekLast();
        while (thisTop != null && otherTop != null && thisTop == otherTop) {
            commonAncestor = thisParentChain.removeLast();
            otherParentChain.removeLast();
            thisTop = thisParentChain.peekLast();
            otherTop = otherParentChain.peekLast();
        }

        // Containers don't belong to the same hierarchy???
        if (commonAncestor == null) {
            throw new IllegalArgumentException("No in the same hierarchy this="
                    + thisParentChain + " other=" + otherParentChain);
        }

        // Children are always considered greater than their parents, so if one of the containers
        // we are comparing it the parent of the other then whichever is the child is greater.
        if (commonAncestor == this) {
            return -1;
        } else if (commonAncestor == other) {
            return 1;
        }

        // The position of the first non-common ancestor in the common ancestor list determines
        // which is greater the which.
        final LinkedList<WindowContainer> list = commonAncestor.mChildren;
        return list.indexOf(thisParentChain.peekLast()) > list.indexOf(otherParentChain.peekLast())
                ? 1 : -1;
    }

    private void getParents(LinkedList<WindowContainer> parents) {
        parents.clear();
        WindowContainer current = this;
        do {
            parents.addLast(current);
            current = current.mParent;
        } while (current != null);
    }
}
+2 −64
Original line number Diff line number Diff line
@@ -3638,8 +3638,7 @@ public class WindowManagerService extends IWindowManager.Stub
                }
                if (mAppTransition.getAppTransition() == AppTransition.TRANSIT_TASK_OPEN_BEHIND) {
                    // We're launchingBehind, add the launching activity to mOpeningApps.
                    final WindowState win =
                            findFocusedWindowLocked(getDefaultDisplayContentLocked());
                    final WindowState win = getDefaultDisplayContentLocked().findFocusedWindow();
                    if (win != null) {
                        final AppWindowToken focusedToken = win.mAppToken;
                        if (focusedToken != null) {
@@ -8772,7 +8771,7 @@ public class WindowManagerService extends IWindowManager.Stub
        final int displayCount = mDisplayContents.size();
        for (int i = 0; i < displayCount; i++) {
            final DisplayContent displayContent = mDisplayContents.valueAt(i);
            WindowState win = findFocusedWindowLocked(displayContent);
            final WindowState win = displayContent.findFocusedWindow();
            if (win != null) {
                return win;
            }
@@ -8780,67 +8779,6 @@ public class WindowManagerService extends IWindowManager.Stub
        return null;
    }

    WindowState findFocusedWindowLocked(DisplayContent displayContent) {
        final WindowList windows = displayContent.getWindowList();
        for (int i = windows.size() - 1; i >= 0; i--) {
            final WindowState win = windows.get(i);

            if (localLOGV || DEBUG_FOCUS) Slog.v(
                TAG_WM, "Looking for focus: " + i
                + " = " + win
                + ", flags=" + win.mAttrs.flags
                + ", canReceive=" + win.canReceiveKeys());

            if (!win.canReceiveKeys()) {
                continue;
            }

            AppWindowToken wtoken = win.mAppToken;

            // If this window's application has been removed, just skip it.
            if (wtoken != null && (wtoken.removed || wtoken.sendingToBottom)) {
                if (DEBUG_FOCUS) Slog.v(TAG_WM, "Skipping " + wtoken + " because "
                        + (wtoken.removed ? "removed" : "sendingToBottom"));
                continue;
            }

            // Descend through all of the app tokens and find the first that either matches
            // win.mAppToken (return win) or mFocusedApp (return null).
            if (wtoken != null && win.mAttrs.type != TYPE_APPLICATION_STARTING &&
                    mFocusedApp != null) {
                ArrayList<Task> tasks = displayContent.getTasks();
                for (int taskNdx = tasks.size() - 1; taskNdx >= 0; --taskNdx) {
                    AppTokenList tokens = tasks.get(taskNdx).mAppTokens;
                    int tokenNdx = tokens.size() - 1;
                    for ( ; tokenNdx >= 0; --tokenNdx) {
                        final AppWindowToken token = tokens.get(tokenNdx);
                        if (wtoken == token) {
                            break;
                        }
                        if (mFocusedApp == token && token.windowsAreFocusable()) {
                            // Whoops, we are below the focused app whose windows are focusable...
                            // No focus for you!!!
                            if (localLOGV || DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM,
                                    "findFocusedWindow: Reached focused app=" + mFocusedApp);
                            return null;
                        }
                    }
                    if (tokenNdx >= 0) {
                        // Early exit from loop, must have found the matching token.
                        break;
                    }
                }
            }

            if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: Found new focus @ " + i +
                        " = " + win);
            return win;
        }

        if (DEBUG_FOCUS_LIGHT) Slog.v(TAG_WM, "findFocusedWindow: No focusable windows.");
        return null;
    }

    void startFreezingDisplayLocked(boolean inTransaction, int exitAnim, int enterAnim) {
        if (mDisplayFrozen) {
            return;
Loading