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

Commit 8e9e8de4 authored by Craig Mautner's avatar Craig Mautner Committed by Android (Google) Code Review
Browse files

Merge "Modify StackBox and TaskStack methods."

parents b7c430d5 00af9fe6
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -1991,7 +1991,7 @@ final class ActivityStack {
                group.tokens.add(r.appToken);
            }
        }
        mService.mWindowManager.validateAppTokens(mValidateAppTokens);
        mService.mWindowManager.validateAppTokens(mStackId, mValidateAppTokens);
    }

    /**
+35 −5
Original line number Diff line number Diff line
@@ -80,7 +80,7 @@ class DisplayContent {
     */
    final AppTokenList mExitingAppTokens = new AppTokenList();

    ArrayList<StackBox> mStackBoxes = new ArrayList<StackBox>();
    private ArrayList<StackBox> mStackBoxes = new ArrayList<StackBox>();

    /**
     * Sorted most recent at top, oldest at [0].
@@ -113,6 +113,11 @@ class DisplayContent {
        return mDisplayInfo;
    }

    /**
     * Retrieve the tasks on this display in stack order from the topmost TaskStack down.
     * Note that the order of TaskStacks in the same StackBox is defined within StackBox.
     * @return All the Tasks, in order, on this display.
     */
    ArrayList<Task> getTasks() {
        mTmpTasks.clear();
        int numBoxes = mStackBoxes.size();
@@ -126,6 +131,7 @@ class DisplayContent {
        mDisplay.getDisplayInfo(mDisplayInfo);
    }

    /** @return The number of tokens in all of the Tasks on this display. */
    int numTokens() {
        getTasks();
        int count = 0;
@@ -135,6 +141,7 @@ class DisplayContent {
        return count;
    }

    /** Refer to {@link WindowManagerService#createStack(int, int, int, float)} */
    TaskStack createStack(int stackId, int relativeStackId, int position, float weight) {
        TaskStack newStack = null;
        if (mStackBoxes.isEmpty()) {
@@ -150,8 +157,7 @@ class DisplayContent {
                if (position == StackBox.TASK_STACK_GOES_OVER
                        || position == StackBox.TASK_STACK_GOES_UNDER) {
                    // Position indicates a new box is added at top level only.
                    final TaskStack stack = box.mStack;
                    if (stack != null && stack.mStackId == relativeStackId) {
                    if (box.contains(relativeStackId)) {
                        final int offset = position == StackBox.TASK_STACK_GOES_OVER ? 1 : 0;
                        StackBox newBox = new StackBox(this, box.mBounds);
                        newStack = new TaskStack(stackId, newBox);
@@ -167,13 +173,15 @@ class DisplayContent {
                    }
                }
            }
            if (stackBoxNdx >= 0) {
                throw new IllegalArgumentException("createStack: stackId " + stackId + " not found.");
            if (stackBoxNdx < 0) {
                throw new IllegalArgumentException("createStack: stackId " + relativeStackId
                        + " not found.");
            }
        }
        return newStack;
    }

    /** Refer to {@link WindowManagerService#resizeStack(int, float)} */
    boolean resizeStack(int stackId, float weight) {
        int stackBoxNdx;
        for (stackBoxNdx = mStackBoxes.size() - 1; stackBoxNdx >= 0; --stackBoxNdx) {
@@ -185,6 +193,24 @@ class DisplayContent {
        return false;
    }

    /**
     * Reorder a StackBox within mStackBox. The StackBox to reorder is the one containing the
     * specified TaskStack.
     * @param stackId The TaskStack to reorder.
     * @param toTop Move to the top of all StackBoxes if true, to the bottom if false. Only the
     * topmost layer of StackBoxes, those in mStackBoxes can be reordered.
     */
    void moveStackBox(int stackId, boolean toTop) {
        for (int stackBoxNdx = mStackBoxes.size() - 1; stackBoxNdx >= 0; --stackBoxNdx) {
            final StackBox box = mStackBoxes.get(stackBoxNdx);
            if (box.contains(stackId)) {
                mStackBoxes.remove(box);
                mStackBoxes.add(toTop ? mStackBoxes.size() : 0, box);
                return;
            }
        }
    }

    public void dump(String prefix, PrintWriter pw) {
        pw.print(prefix); pw.print("Display: mDisplayId="); pw.println(mDisplayId);
        final String subPrefix = "  " + prefix;
@@ -209,6 +235,10 @@ class DisplayContent {
            pw.print("-"); pw.print(mDisplayInfo.largestNominalAppWidth);
            pw.print("x"); pw.println(mDisplayInfo.largestNominalAppHeight);
            pw.print(subPrefix); pw.print("layoutNeeded="); pw.println(layoutNeeded);
            for (int boxNdx = 0; boxNdx < mStackBoxes.size(); ++boxNdx) {
                pw.print(prefix); pw.print("StackBox #"); pw.println(boxNdx);
                mStackBoxes.get(boxNdx).dump(prefix + "  ", pw);
            }
            int ndx = numTokens();
            if (ndx > 0) {
                pw.println();
+87 −68
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@ package com.android.server.wm;

import android.graphics.Rect;

import java.io.PrintWriter;
import java.util.ArrayList;

public class StackBox {
@@ -29,15 +30,32 @@ public class StackBox {
    public static final int TASK_STACK_GOES_OVER = 4;
    public static final int TASK_STACK_GOES_UNDER = 5;

    /** The display this box sits in. */
    final DisplayContent mDisplayContent;

    /** Non-null indicates this is mFirst or mSecond of a parent StackBox. Null indicates this
     * is this entire size of mDisplayContent. */
    StackBox mParent;
    boolean mVertical;

    /** First child, this is null exactly when mStack is non-null. */
    StackBox mFirst;

    /** Second child, this is null exactly when mStack is non-null. */
    StackBox mSecond;
    float mWeight;

    /** Stack of Tasks, this is null exactly when mFirst and mSecond are non-null. */
    TaskStack mStack;

    /** Content limits relative to the DisplayContent this sits in. */
    Rect mBounds;

    /** Relative orientation of mFirst and mSecond. */
    boolean mVertical;

    /** Dirty flag. Something inside this or some descendant of this has changed. */
    boolean layoutNeeded;

    /** Used to keep from reallocating a temporary array to hold the list of Tasks below */
    ArrayList<Task> mTmpTasks = new ArrayList<Task>();

    StackBox(DisplayContent displayContent, Rect bounds) {
@@ -62,6 +80,28 @@ public class StackBox {
        }
    }

    /**
     * Detremine if a particular TaskStack is in this StackBox or any of its descendants.
     * @param stackId The TaskStack being considered.
     * @return true if the specified TaskStack is in this box or its descendants. False otherwise.
     */
    boolean contains(int stackId) {
        if (mStack != null) {
            return mStack.mStackId == stackId;
        }
        return mFirst.contains(stackId) || mSecond.contains(stackId);
    }

    /**
     * Create a new TaskStack relative to a specified one by splitting the StackBox containing
     * the specified TaskStack into two children. The size and position each of the new StackBoxes
     * is determined by the passed parameters.
     * @param stackId The id of the new TaskStack to create.
     * @param relativeStackId The id of the TaskStack to place the new one next to.
     * @param position One of the static TASK_STACK_GOES_xxx positions defined in this class.
     * @param weight The percentage size of the parent StackBox to devote to the new TaskStack.
     * @return The new TaskStack.
     */
    TaskStack split(int stackId, int relativeStackId, int position, float weight) {
        if (mStack != null) {
            if (mStack.mStackId == relativeStackId) {
@@ -112,6 +152,7 @@ public class StackBox {
                mStack = null;
                return stack;
            }
            // Not the intended TaskStack.
            return null;
        }

@@ -123,51 +164,11 @@ public class StackBox {
        return mSecond.split(stackId, relativeStackId, position, weight);
    }

    TaskStack merge(int position) {
        TaskStack stack = null;
        if (mFirst != null) {
            switch (position) {
                default:
                case TASK_STACK_GOES_BEFORE:
                case TASK_STACK_GOES_ABOVE:
                    stack = mFirst.merge(position);
                    stack.merge(mSecond.merge(position));
                    break;
                case TASK_STACK_GOES_AFTER:
                case TASK_STACK_GOES_BELOW:
                    stack = mSecond.merge(position);
                    stack.merge(mFirst.merge(position));
                    break;
            }
            return stack;
        }
        return mStack;
    }

    boolean merge(int stackId, int position, StackBox primary, StackBox secondary) {
        TaskStack stack = primary.mStack;
        if (stack != null && stack.mStackId == stackId) {
            stack.merge(secondary.merge(position));
            mStack = stack;
            mFirst = null;
            mSecond = null;
            return true;
        }
        return false;
    }

    boolean merge(int stackId, int position) {
        if (mFirst != null) {
            if (merge(stackId, position, mFirst, mSecond)
                    || merge(stackId, position, mSecond, mFirst)
                    || mFirst.merge(stackId, position)
                    || mSecond.merge(stackId, position)) {
                return true;
            }
        }
        return false;
    }

    /**
     * @return List of all Tasks underneath this StackBox. The order is currently mFirst followed
     * by mSecond putting mSecond Tasks more recent than mFirst Tasks.
     * TODO: Change to MRU ordering.
     */
    ArrayList<Task> getTasks() {
        mTmpTasks.clear();
        if (mStack != null) {
@@ -179,37 +180,55 @@ public class StackBox {
        return mTmpTasks;
    }

    void absorb(StackBox box) {
        mFirst = box.mFirst;
        mSecond = box.mSecond;
        mStack = box.mStack;
    /** Combine a child StackBox into its parent.
     * @param child The surviving child to be merge up into this StackBox. */
    void absorb(StackBox child) {
        mFirst = child.mFirst;
        mSecond = child.mSecond;
        mStack = child.mStack;
        layoutNeeded = true;
    }

    void removeStack() {
        if (mParent != null) {
    /** Return the stackId of the first mFirst StackBox with a non-null mStack */
    int getStackId() {
        if (mStack != null) {
            return mStack.mStackId;
        }
        return mFirst.getStackId();
    }

    /** Remove this box and propagate its sibling's content up to their parent.
     * @return The first stackId of the resulting StackBox. */
    int removeStack() {
        if (mParent.mFirst == this) {
            mParent.absorb(mParent.mSecond);
        } else {
            mParent.absorb(mParent.mFirst);
        }
        mParent.makeDirty();
        }
        return getStackId();
    }

    boolean addTaskToStack(Task task, int stackId, boolean toTop) {
        if (mStack != null) {
            if (mStack.mStackId == stackId) {
                mStack.addTask(task, toTop);
                return true;
            }
    /** TODO: */
    boolean resize(int stackId, float weight) {
        return false;
    }
        return mFirst.addTaskToStack(task, stackId, toTop)
                || mSecond.addTaskToStack(task, stackId, toTop);
    }

    boolean resize(int stackId, float weight) {
        return false;
    public void dump(String prefix, PrintWriter pw) {
        pw.print(prefix); pw.print("mParent="); pw.println(mParent);
        pw.print(prefix); pw.print("mFirst="); pw.println(mFirst);
        pw.print(prefix); pw.print("mSecond="); pw.println(mSecond);
        pw.print(prefix); pw.print("mBounds="); pw.print(mBounds.toShortString());
            pw.print("mVertical="); pw.print(mVertical);
            pw.print("layoutNeeded="); pw.println(layoutNeeded);
        if (mStack != null) {
            pw.print(prefix); pw.print("mStack="); pw.println(mStack);
            mStack.dump(prefix + "  ", pw);
        } else {
            pw.print(prefix); pw.print("mFirst="); pw.println(mStack);
            mFirst.dump(prefix + "  ", pw);
            pw.print(prefix); pw.print("mSecond="); pw.println(mStack);
            mSecond.dump(prefix + "  ", pw);
        }
    }
}
+34 −3
Original line number Diff line number Diff line
@@ -16,14 +16,22 @@

package com.android.server.wm;

import java.io.PrintWriter;
import java.util.ArrayList;

public class TaskStack {
    /** Unique identifier */
    final int mStackId;
    final DisplayContent mDisplayContent;

    /** The display this stack sits under. */
    private final DisplayContent mDisplayContent;

    /** The Tasks that define this stack. Oldest Tasks are at the bottom. The ordering must match
     * mTaskHistory in the ActivityStack with the same mStackId */
    private ArrayList<Task> mTasks = new ArrayList<Task>();
    int mLayer;
    StackBox mParent;

    /** The StackBox this sits in. */
    private final StackBox mParent;

    TaskStack(int stackId, StackBox parent) {
        mStackId = stackId;
@@ -46,9 +54,15 @@ public class TaskStack {
        return taskLists;
    }

    /**
     * Put a Task in this stack. Used for adding and moving.
     * @param task The task to add.
     * @param toTop Whether to add it to the top or bottom.
     */
    void addTask(Task task, boolean toTop) {
        mParent.makeDirty();
        mTasks.add(toTop ? mTasks.size() : 0, task);
        mDisplayContent.moveStackBox(mStackId, toTop);
    }

    void moveTaskToTop(Task task) {
@@ -61,6 +75,12 @@ public class TaskStack {
        addTask(task, false);
    }

    /**
     * Delete a Task from this stack. If it is the last Task in the stack, remove this stack from
     * its parent StackBox and merge the parent.
     * @param task The Task to delete.
     * @return True if #task was in this stack.
     */
    boolean removeTask(Task task) {
        mParent.makeDirty();
        if (mTasks.remove(task)) {
@@ -72,6 +92,10 @@ public class TaskStack {
        return false;
    }

    int remove() {
        return mParent.removeStack();
    }

    int numTokens() {
        int count = 0;
        for (int taskNdx = mTasks.size() - 1; taskNdx >= 0; --taskNdx) {
@@ -79,4 +103,11 @@ public class TaskStack {
        }
        return count;
    }

    public void dump(String prefix, PrintWriter pw) {
        pw.print(prefix); pw.print("mStackId="); pw.println(mStackId);
        for (int taskNdx = 0; taskNdx < mTasks.size(); ++taskNdx) {
            pw.print(prefix); pw.println(mTasks.get(taskNdx));
        }
    }
}
+15 −3
Original line number Diff line number Diff line
@@ -3169,7 +3169,7 @@ public class WindowManagerService extends IWindowManager.Stub
    // Application Window Tokens
    // -------------------------------------------------------------

    public void validateAppTokens(List<TaskGroup> tasks) {
    public void validateAppTokens(int stackId, List<TaskGroup> tasks) {
        synchronized (mWindowMap) {
            int t = tasks.size() - 1;
            if (t < 0) {
@@ -3186,7 +3186,7 @@ public class WindowManagerService extends IWindowManager.Stub
                return;
            }

            final ArrayList<Task> localTasks = displayContent.getTasks();
            final ArrayList<Task> localTasks = mStackIdToStack.get(stackId).getTasks();
            int taskNdx;
            for (taskNdx = localTasks.size() - 1; taskNdx >= 0 && t >= 0; --taskNdx, --t) {
                AppTokenList localTokens = localTasks.get(taskNdx).mAppTokens;
@@ -3230,6 +3230,10 @@ public class WindowManagerService extends IWindowManager.Stub
        }
    }

    public void validateStackOrder(Integer[] remoteStackIds) {
        // TODO:
    }

    boolean checkCallingPermission(String permission, String func) {
        // Quick check: if the calling permission is me, it's all okay.
        if (Binder.getCallingPid() == Process.myPid()) {
@@ -4685,10 +4689,18 @@ public class WindowManagerService extends IWindowManager.Stub
            TaskStack stack = getDefaultDisplayContentLocked().createStack(stackId,
                    relativeStackId, position, weight);
            mStackIdToStack.put(stackId, stack);
            performLayoutAndPlaceSurfacesLocked();
        }
    }

    public int removeStack(int stackId) {
        final TaskStack stack = mStackIdToStack.get(stackId);
        if (stack != null) {
            mStackIdToStack.delete(stackId);
            return stack.remove();
        }
        return -1;
    }

    public void moveTaskToStack(int taskId, int stackId, boolean toTop) {
        synchronized (mWindowMap) {
            Task task = mTaskIdToTask.get(taskId);