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

Commit f418f9e7 authored by Joshua Tsuji's avatar Joshua Tsuji
Browse files

Reposition the stack to a similar position upon rotation.

Fixes: 128691406
Test: atest SystemUITests
Change-Id: I2d73c88f06d759c2b7b71dc77d008a1e026ee959
parent 4bf85326
Loading
Loading
Loading
Loading
+12 −0
Original line number Diff line number Diff line
@@ -34,6 +34,7 @@ import android.app.INotificationManager;
import android.app.Notification;
import android.content.Context;
import android.content.pm.ParceledListSlice;
import android.content.res.Configuration;
import android.graphics.Rect;
import android.os.RemoteException;
import android.os.ServiceManager;
@@ -135,6 +136,9 @@ public class BubbleController implements BubbleExpandedView.OnBubbleBlockedListe
    // Used for determining view rect for touch interaction
    private Rect mTempRect = new Rect();

    /** Last known orientation, used to detect orientation changes in {@link #onConfigChanged}. */
    private int mOrientation = Configuration.ORIENTATION_UNDEFINED;

    /**
     * Listener to be notified when some states of the bubbles change.
     */
@@ -254,6 +258,14 @@ public class BubbleController implements BubbleExpandedView.OnBubbleBlockedListe
        }
    }

    @Override
    public void onConfigChanged(Configuration newConfig) {
        if (mStackView != null && newConfig != null && newConfig.orientation != mOrientation) {
            mStackView.onOrientationChanged();
            mOrientation = newConfig.orientation;
        }
    }

    /**
     * Set a listener to be notified when some states of the bubbles change.
     */
+31 −0
Original line number Diff line number Diff line
@@ -138,6 +138,16 @@ public class BubbleStackView extends FrameLayout {
    private Runnable mHideFlyout =
            () -> mFlyout.animate().alpha(0f).withEndAction(() -> mFlyout.setVisibility(GONE));

    /** Layout change listener that moves the stack to the nearest valid position on rotation. */
    private OnLayoutChangeListener mMoveStackToValidPositionOnLayoutListener;
    /** Whether the stack was on the left side of the screen prior to rotation. */
    private boolean mWasOnLeftBeforeRotation = false;
    /**
     * How far down the screen the stack was before rotation, in terms of percentage of the way down
     * the allowable region. Defaults to -1 if not set.
     */
    private float mVerticalPosPercentBeforeRotation = -1;

    private int mBubbleSize;
    private int mBubblePadding;
    private int mExpandedAnimateXDistance;
@@ -304,6 +314,15 @@ public class BubbleStackView extends FrameLayout {
            return view.onApplyWindowInsets(insets);
        });

        mMoveStackToValidPositionOnLayoutListener =
                (v, left, top, right, bottom, oldLeft, oldTop, oldRight, oldBottom) -> {
                    if (mVerticalPosPercentBeforeRotation >= 0) {
                        mStackAnimationController.moveStackToSimilarPositionAfterRotation(
                                mWasOnLeftBeforeRotation, mVerticalPosPercentBeforeRotation);
                    }
                    removeOnLayoutChangeListener(mMoveStackToValidPositionOnLayoutListener);
                };

        // This must be a separate OnDrawListener since it should be called for every draw.
        getViewTreeObserver().addOnDrawListener(mSystemGestureExcludeUpdater);
    }
@@ -318,6 +337,18 @@ public class BubbleStackView extends FrameLayout {
        }
    }

    /** Respond to the phone being rotated by repositioning the stack and hiding any flyouts. */
    public void onOrientationChanged() {
        final RectF allowablePos = mStackAnimationController.getAllowableStackPositionRegion();
        mWasOnLeftBeforeRotation = mStackAnimationController.isStackOnLeftSide();
        mVerticalPosPercentBeforeRotation =
                (mStackAnimationController.getStackPosition().y - allowablePos.top)
                        / (allowablePos.bottom - allowablePos.top);
        addOnLayoutChangeListener(mMoveStackToValidPositionOnLayoutListener);

        hideFlyoutImmediate();
    }

    @Override
    public void getBoundsOnScreen(Rect outRect, boolean clipToParent) {
        getBoundsOnScreen(outRect);
+15 −0
Original line number Diff line number Diff line
@@ -251,6 +251,21 @@ public class StackAnimationController extends
        return stackPos;
    }

    /**
     * Moves the stack in response to rotation. We keep it in the most similar position by keeping
     * it on the same side, and positioning it the same percentage of the way down the screen
     * (taking status bar/nav bar into account by using the allowable region's height).
     */
    public void moveStackToSimilarPositionAfterRotation(boolean wasOnLeft, float verticalPercent) {
        final RectF allowablePos = getAllowableStackPositionRegion();
        final float allowableRegionHeight = allowablePos.bottom - allowablePos.top;

        final float x = wasOnLeft ? allowablePos.left : allowablePos.right;
        final float y = (allowableRegionHeight * verticalPercent) + allowablePos.top;

        setStackPosition(new PointF(x, y));
    }

    /**
     * Flings the first bubble along the given property's axis, using the provided configuration
     * values. When the animation ends - either by hitting the min/max, or by friction sufficiently