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

Commit 76ba2ec7 authored by Graciela Wissen Putri's avatar Graciela Wissen Putri
Browse files

[2/n] Independent back per display in projected mode

In projected mode, system back should affect only apps in the display
that the back originated from, even if the app is not currently the top
focused window.

Flag: com.android.window.flags.enable_independent_back_in_projected
Bug: 401530192
Test: atest BackNavigationControllerTests
Change-Id: I6ef243c0bda9097a61a1da6be9b86895793075e3
parent fb4bcf40
Loading
Loading
Loading
Loading
+6 −0
Original line number Diff line number Diff line
@@ -16,6 +16,8 @@

package android.window;

import static android.view.Display.INVALID_DISPLAY;

import android.annotation.NonNull;
import android.os.Parcel;
import android.os.Parcelable;
@@ -28,6 +30,8 @@ import java.util.ArrayList;
 * @hide
 */
public class BackAnimationAdapter implements Parcelable {
    /** The display id where the back gesture is started. */
    public int mOriginDisplayId = INVALID_DISPLAY;
    private final IBackAnimationRunner mRunner;
    private int[] mSupportedAnimators;

@@ -39,6 +43,7 @@ public class BackAnimationAdapter implements Parcelable {
        mRunner = IBackAnimationRunner.Stub.asInterface(in.readStrongBinder());
        mSupportedAnimators = new int[in.readInt()];
        in.readIntArray(mSupportedAnimators);
        mOriginDisplayId = in.readInt();
    }

    public IBackAnimationRunner getRunner() {
@@ -64,6 +69,7 @@ public class BackAnimationAdapter implements Parcelable {
        dest.writeStrongInterface(mRunner);
        dest.writeInt(mSupportedAnimators.length);
        dest.writeIntArray(mSupportedAnimators);
        dest.writeInt(mOriginDisplayId);
    }

    public static final @android.annotation.NonNull Creator<BackAnimationAdapter> CREATOR =
+7 −0
Original line number Diff line number Diff line
@@ -94,6 +94,13 @@ public final class BackNavigationInfo implements Parcelable {
     */
    public static final String KEY_TOUCH_GESTURE_TRANSFERRED = "TouchGestureTransferred";

    /**
     * Key to access the displayId passed in result bundle that represents on which display
     * the back gesture has been triggered.
     * @hide
     */
    public static final String KEY_DISPLAY_ID = "DisplayId";


    /**
     * Defines the type of back destinations a back even can lead to. This is used to define the
+2 −1
Original line number Diff line number Diff line
@@ -42,7 +42,8 @@ public interface BackAnimation {
            float touchX,
            float touchY,
            int keyAction,
            @BackEvent.SwipeEdge int swipeEdge);
            @BackEvent.SwipeEdge int swipeEdge,
            int displayId);

    /**
     * Called when the back swipe threshold is crossed.
+22 −12
Original line number Diff line number Diff line
@@ -17,11 +17,13 @@
package com.android.wm.shell.back;

import static android.app.ActivityTaskManager.INVALID_TASK_ID;
import static android.view.Display.INVALID_DISPLAY;
import static android.view.RemoteAnimationTarget.MODE_CLOSING;
import static android.view.RemoteAnimationTarget.MODE_OPENING;
import static android.view.WindowManager.TRANSIT_CHANGE;
import static android.view.WindowManager.TRANSIT_CLOSE_PREPARE_BACK_NAVIGATION;
import static android.window.BackEvent.EDGE_NONE;
import static android.window.DesktopExperienceFlags.ENABLE_INDEPENDENT_BACK_IN_PROJECTED;
import static android.window.TransitionInfo.FLAG_BACK_GESTURE_ANIMATED;
import static android.window.TransitionInfo.FLAG_IS_WALLPAPER;
import static android.window.TransitionInfo.FLAG_MOVED_TO_TOP;
@@ -329,10 +331,11 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
                float touchX,
                float touchY,
                int keyAction,
                @BackEvent.SwipeEdge int swipeEdge
                @BackEvent.SwipeEdge int swipeEdge,
                int displayId
        ) {
            mShellExecutor.execute(
                    () -> onMotionEvent(touchX, touchY, keyAction, swipeEdge));
                    () -> onMotionEvent(touchX, touchY, keyAction, swipeEdge, displayId));
        }

        @Override
@@ -479,7 +482,12 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
            float touchX,
            float touchY,
            int keyAction,
            @BackEvent.SwipeEdge int swipeEdge) {
            @BackEvent.SwipeEdge int swipeEdge,
            int displayId) {

        if (ENABLE_INDEPENDENT_BACK_IN_PROJECTED.isTrue()) {
            mBackAnimationAdapter.mOriginDisplayId = displayId;
        }

        BackTouchTracker activeTouchTracker = getActiveTracker();
        if (activeTouchTracker != null) {
@@ -640,21 +648,23 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
        dispatchOnBackProgressed(mActiveCallback, backEvent);
    }

    private void injectBackKey() {
    private void injectBackKey(int displayId) {
        ProtoLog.d(WM_SHELL_BACK_PREVIEW, "injectBackKey");
        sendBackEvent(KeyEvent.ACTION_DOWN);
        sendBackEvent(KeyEvent.ACTION_UP);
        sendBackEvent(KeyEvent.ACTION_DOWN, displayId);
        sendBackEvent(KeyEvent.ACTION_UP, displayId);
    }

    @SuppressLint("MissingPermission")
    private void sendBackEvent(int action) {
    private void sendBackEvent(int action, int displayId) {
        final long when = SystemClock.uptimeMillis();
        final KeyEvent ev = new KeyEvent(when, when, action, KeyEvent.KEYCODE_BACK, 0 /* repeat */,
                0 /* metaState */, KeyCharacterMap.VIRTUAL_KEYBOARD, 0 /* scancode */,
                KeyEvent.FLAG_FROM_SYSTEM | KeyEvent.FLAG_VIRTUAL_HARD_KEY,
                InputDevice.SOURCE_KEYBOARD);
        if (ENABLE_INDEPENDENT_BACK_IN_PROJECTED.isTrue()) {
            ev.setDisplayId(displayId);
        }

        ev.setDisplayId(mContext.getDisplay().getDisplayId());
        if (!mContext.getSystemService(InputManager.class)
                .injectInputEvent(ev, InputManager.INJECT_INPUT_EVENT_MODE_ASYNC)) {
            ProtoLog.e(WM_SHELL_BACK_PREVIEW, "Inject input event fail");
@@ -840,7 +850,7 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
            }
            mCurrentTracker.reset();
            if (triggerBack) {
                injectBackKey();
                injectBackKey(mBackAnimationAdapter.mOriginDisplayId);
            }
            finishBackNavigation(triggerBack);
            return;
@@ -969,7 +979,7 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
        if (mCurrentTracker.isFinished() && mCurrentTracker.getTriggerBack()) {
            ProtoLog.d(WM_SHELL_BACK_PREVIEW, "resetTouchTracker -> start queued back navigation "
                    + "AND post commit animation");
            injectBackKey();
            injectBackKey(mBackAnimationAdapter.mOriginDisplayId);
            finishBackNavigation(true);
            mCurrentTracker.reset();
        } else if (!mCurrentTracker.isFinished()) {
@@ -1165,9 +1175,9 @@ public class BackAnimationController implements RemoteCallable<BackAnimationCont
                                Log.w(TAG, "Back gesture is running, ignore request");
                                return;
                            }
                            onMotionEvent(0, 0, KeyEvent.ACTION_DOWN, EDGE_NONE);
                            onMotionEvent(0, 0, KeyEvent.ACTION_DOWN, EDGE_NONE, INVALID_DISPLAY);
                            setTriggerBack(true);
                            onMotionEvent(0, 0, KeyEvent.ACTION_UP, EDGE_NONE);
                            onMotionEvent(0, 0, KeyEvent.ACTION_UP, EDGE_NONE, INVALID_DISPLAY);
                        });
                    } else {
                        Log.w(TAG, "Unsupported gesture " + event + " received!");
+3 −1
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
package com.android.wm.shell.back;

import static android.app.ActivityTaskManager.INVALID_TASK_ID;
import static android.view.Display.DEFAULT_DISPLAY;
import static android.view.WindowManager.TRANSIT_CLOSE;
import static android.view.WindowManager.TRANSIT_CLOSE_PREPARE_BACK_NAVIGATION;
import static android.view.WindowManager.TRANSIT_OPEN;
@@ -881,7 +882,8 @@ public class BackAnimationControllerTest extends ShellTestCase {
                /* touchX */ coordinate,
                /* touchY */ coordinate,
                /* keyAction */ actionDown,
                /* swipeEdge */ BackEvent.EDGE_LEFT);
                /* swipeEdge */ BackEvent.EDGE_LEFT,
                /* displayId */ DEFAULT_DISPLAY);
    }

    /**
Loading