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

Commit b9b16a74 authored by Wale Ogunwale's avatar Wale Ogunwale
Browse files

Display warning toast when we try to launch unresizeable app in split-screen

Bug: 26774816
Change-Id: Ia85d9d89758041661391018f04feb6f8db4e56d9
parent 513346d8
Loading
Loading
Loading
Loading
+4 −2
Original line number Diff line number Diff line
@@ -4003,8 +4003,10 @@
    <string name="lock_to_app_unlock_password">Ask for password before unpinning</string>

    <!-- Multi-Window strings -->
    <!-- Warning message when a non-resizeble tasks is docked. -->
    <string name="dock_non_resizeble_text">App is not resizeable, scroll it with two fingers.</string>
    <!-- Warning message when a non-resizeble tasks is docked whose display windows are cropped. -->
    <string name="dock_cropped_windows_text">App is not resizeable, scroll it with two fingers.</string>
    <!-- Warning message when we try to dock a non-resizeble tasks and launch it in fullscreen instead. -->
    <string name="dock_non_resizeble_failed_to_dock_text">App does not support split-screen.</string>

    <!-- Notification shown when device owner silently installs a package [CHAR LIMIT=NONE] -->
    <string name="package_installed_device_owner">Installed by your administrator</string>
+2 −1
Original line number Diff line number Diff line
@@ -610,7 +610,8 @@
  <java-symbol type="string" name="display_manager_overlay_display_name" />
  <java-symbol type="string" name="display_manager_overlay_display_secure_suffix" />
  <java-symbol type="string" name="display_manager_overlay_display_title" />
  <java-symbol type="string" name="dock_non_resizeble_text" />
  <java-symbol type="string" name="dock_cropped_windows_text" />
  <java-symbol type="string" name="dock_non_resizeble_failed_to_dock_text" />
  <java-symbol type="string" name="double_tap_toast" />
  <java-symbol type="string" name="durationDays" />
  <java-symbol type="string" name="durationDayHours" />
+13 −6
Original line number Diff line number Diff line
@@ -2204,7 +2204,6 @@ public final class ActivityStackSupervisor implements DisplayListener {
            // show up. We instead leave the task in its current stack or move it to the fullscreen
            // stack if it isn't currently in a stack.
            stackId = (prevStack != null) ? prevStack.mStackId : FULLSCREEN_WORKSPACE_STACK_ID;
            // TODO: display toast that activity doesn't support multi-window mode.
            Slog.w(TAG, "Can not move unresizeable task=" + task
                    + " to docked stack. Moving to stackId=" + stackId + " instead.");
        }
@@ -2254,6 +2253,7 @@ public final class ActivityStackSupervisor implements DisplayListener {
            // during the relaunch. If we end up not doing any relaunch, we clear the flags later.
            mWindowManager.setReplacingWindow(topActivity.appToken, animate);
        }
        final int preferredLaunchStackId = stackId;
        final ActivityStack stack = moveTaskToStackUncheckedLocked(
                task, stackId, toTop, forceFocus, "moveTaskToStack:" + reason);
        stackId = stack.mStackId;
@@ -2286,9 +2286,7 @@ public final class ActivityStackSupervisor implements DisplayListener {
        ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
        resumeFocusedStackTopActivityLocked();

        if (!task.isResizeable() && isStackDockedInEffect(stackId)) {
            showNonResizeableDockToast(taskId);
        }
        showNonResizeableDockToastIfNeeded(task, preferredLaunchStackId, stackId);
    }

    boolean moveTopStackActivityToPinnedStackLocked(int stackId, Rect bounds) {
@@ -3240,8 +3238,17 @@ public final class ActivityStackSupervisor implements DisplayListener {
        }
    }

    void showNonResizeableDockToast(int taskId) {
        mWindowManager.scheduleShowNonResizeableDockToast(taskId);
    void showNonResizeableDockToastIfNeeded(
            TaskRecord task, int preferredStackId, int actualStackId) {
        if (!isStackDockedInEffect(actualStackId) && preferredStackId != DOCKED_STACK_ID) {
            return;
        }

        if (!task.canGoInDockedStack() || task.inCropWindowsResizeMode()) {
            // Display warning toast if we tried to put a non-dockable task in the docked stack or
            // the task is running in cropped window mode.
            mWindowManager.scheduleShowNonResizeableDockToast(task.taskId);
        }
    }

    void showLockTaskToast() {
+4 −4
Original line number Diff line number Diff line
@@ -1004,10 +1004,10 @@ class ActivityStarter {
        }
        mSupervisor.updateUserStackLocked(mStartActivity.userId, mTargetStack);

        if (!mStartActivity.task.isResizeable()
                && mSupervisor.isStackDockedInEffect(mTargetStack.mStackId)) {
            mSupervisor.showNonResizeableDockToast(mStartActivity.task.taskId);
        }
        final int preferredLaunchStackId =
                (mOptions != null) ? mOptions.getLaunchStackId() : INVALID_STACK_ID;
        mSupervisor.showNonResizeableDockToastIfNeeded(
                mStartActivity.task, preferredLaunchStackId, mTargetStack.mStackId);

        return START_SUCCESS;
    }
+52 −32
Original line number Diff line number Diff line
@@ -19,9 +19,11 @@ package com.android.server.wm;
import static android.app.ActivityManager.StackId.DOCKED_STACK_ID;
import static android.app.ActivityManager.StackId.FREEFORM_WORKSPACE_STACK_ID;
import static android.app.ActivityManager.StackId.HOME_STACK_ID;
import static android.content.pm.ActivityInfo.RESIZE_MODE_UNRESIZEABLE;
import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
import static android.app.ActivityManager.RESIZE_MODE_SYSTEM_SCREEN_ROTATION;
import static android.content.pm.ActivityInfo.RESIZE_MODE_CROP_WINDOWS;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_RESIZE;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_STACK;
@@ -41,12 +43,14 @@ import android.util.Slog;
import android.view.DisplayInfo;
import android.view.Surface;

import com.android.internal.R;
import com.android.server.EventLogTags;

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

class Task implements DimLayer.DimLayerUser {
    static final String TAG = TAG_WITH_CLASS_NAME ? "Task" : TAG_WM;
    // Return value from {@link setBounds} indicating no change was made to the Task bounds.
    static final int BOUNDS_CHANGE_NONE = 0;
    // Return value from {@link setBounds} indicating the position of the Task bounds changed.
@@ -129,35 +133,51 @@ class Task implements DimLayer.DimLayerUser {

        mShowNonResizeableDockToast = false;

        if (isResizeable()) {
            Slog.wtf(TAG,
                    "Trying to show non-resizeable toast when task is resizeable task=" + this);
            return;
        }

        if (mResizeMode == RESIZE_MODE_UNRESIZEABLE) {
            final String text =
                    mService.mContext.getString(R.string.dock_non_resizeble_failed_to_dock_text);
            mService.mH.obtainMessage(SHOW_NON_RESIZEABLE_DOCK_TOAST, 0, 0, text).sendToTarget();
            return;
        }

        final int dockSide = mStack.getDockSide();
        if (!inCropWindowsResizeMode() || dockSide == DOCKED_INVALID) {
            return;
        }

        int xOffset = 0;
        int yOffset = 0;
        if (dockSide != DOCKED_INVALID) {
        mStack.getBounds(mTmpRect);

        if (dockSide == DOCKED_LEFT || dockSide == DOCKED_RIGHT) {
                // The toast was originally placed at the bottom and centered. To place it
                // at the bottom-center of the stack, we offset it horizontally by the diff
                // between the center of the stack bounds vs. the center of the screen.
            // The toast was originally placed at the bottom and centered. To place it at the
            // bottom-center of the stack, we offset it horizontally by the diff between the center
            // of the stack bounds vs. the center of the screen.
            displayContent.getLogicalDisplayRect(mTmpRect2);
            xOffset = mTmpRect.centerX() - mTmpRect2.centerX();
        } else if (dockSide == DOCKED_TOP) {
                // The toast was originally placed at the bottom and centered. To place it
                // at the bottom center of the top stack, we offset it vertically by the diff
                // between the bottom of the stack bounds vs. the bottom of the content rect.
            // The toast was originally placed at the bottom and centered. To place it at the bottom
            // center of the top stack, we offset it vertically by the diff between the bottom of
            // the stack bounds vs. the bottom of the content rect.
            //
                // Note here we use the content rect instead of the display rect, as we want
                // the toast's distance to the dock divider (when it's placed at the top half)
                // to be the same as it's distance to the top of the navigation bar (when it's
                // placed at the bottom).
            // Note here we use the content rect instead of the display rect, as we want the toast's
            // distance to the dock divider (when it's placed at the top half) to be the same as
            // it's distance to the top of the navigation bar (when it's placed at the bottom).

            // We don't adjust for DOCKED_BOTTOM case since it's already at the bottom.
            displayContent.getContentRect(mTmpRect2);
            yOffset = mTmpRect2.bottom - mTmpRect.bottom;
        }
            mService.mH.obtainMessage(
                    SHOW_NON_RESIZEABLE_DOCK_TOAST, xOffset, yOffset).sendToTarget();
        }
        final String text =
                mService.mContext.getString(R.string.dock_cropped_windows_text);
        mService.mH.obtainMessage(SHOW_NON_RESIZEABLE_DOCK_TOAST,
                xOffset, yOffset, text).sendToTarget();
    }

    void addAppToken(int addPos, AppWindowToken wtoken, int resizeMode, boolean homeTask) {
@@ -190,11 +210,11 @@ class Task implements DimLayer.DimLayerUser {

    void removeLocked() {
        if (hasAppTokensAlive() && mStack.isAnimating()) {
            if (DEBUG_STACK) Slog.i(TAG_WM, "removeTask: deferring removing taskId=" + mTaskId);
            if (DEBUG_STACK) Slog.i(TAG, "removeTask: deferring removing taskId=" + mTaskId);
            mDeferRemoval = true;
            return;
        }
        if (DEBUG_STACK) Slog.i(TAG_WM, "removeTask: removing taskId=" + mTaskId);
        if (DEBUG_STACK) Slog.i(TAG, "removeTask: removing taskId=" + mTaskId);
        EventLog.writeEvent(EventLogTags.WM_TASK_REMOVED, mTaskId, "removeTask");
        mDeferRemoval = false;
        DisplayContent content = getDisplayContent();
@@ -209,7 +229,7 @@ class Task implements DimLayer.DimLayerUser {
        if (stack == mStack) {
            return;
        }
        if (DEBUG_STACK) Slog.i(TAG_WM, "moveTaskToStack: removing taskId=" + mTaskId
        if (DEBUG_STACK) Slog.i(TAG, "moveTaskToStack: removing taskId=" + mTaskId
                + " from stack=" + mStack);
        EventLog.writeEvent(EventLogTags.WM_TASK_REMOVED, mTaskId, "moveTask");
        if (mStack != null) {
@@ -220,7 +240,7 @@ class Task implements DimLayer.DimLayerUser {

    void positionTaskInStack(TaskStack stack, int position, Rect bounds, Configuration config) {
        if (mStack != null && stack != mStack) {
            if (DEBUG_STACK) Slog.i(TAG_WM, "positionTaskInStack: removing taskId=" + mTaskId
            if (DEBUG_STACK) Slog.i(TAG, "positionTaskInStack: removing taskId=" + mTaskId
                    + " from stack=" + mStack);
            EventLog.writeEvent(EventLogTags.WM_TASK_REMOVED, mTaskId, "moveTask");
            mStack.removeTask(this);
@@ -566,7 +586,7 @@ class Task implements DimLayer.DimLayerUser {
            for (int winNdx = windows.size() - 1; winNdx >= 0; --winNdx) {
                final WindowState win = windows.get(winNdx);
                if (!resizingWindows.contains(win)) {
                    if (DEBUG_RESIZE) Slog.d(TAG_WM, "resizeWindows: Resizing " + win);
                    if (DEBUG_RESIZE) Slog.d(TAG, "resizeWindows: Resizing " + win);
                    resizingWindows.add(win);
                }
            }
@@ -578,7 +598,7 @@ class Task implements DimLayer.DimLayerUser {
            final ArrayList<WindowState> windows = mAppTokens.get(activityNdx).allAppWindows;
            for (int winNdx = windows.size() - 1; winNdx >= 0; --winNdx) {
                final WindowState win = windows.get(winNdx);
                if (DEBUG_RESIZE) Slog.d(TAG_WM, "moveWindows: Moving " + win);
                if (DEBUG_RESIZE) Slog.d(TAG, "moveWindows: Moving " + win);
                win.mMovedByResize = true;
            }
        }
Loading