Merge "Block offset requests prior to entering PiP" into rvc-qpr-dev
This commit is contained in:
@@ -94,6 +94,36 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
private static final int MSG_FINISH_RESIZE = 4;
|
private static final int MSG_FINISH_RESIZE = 4;
|
||||||
private static final int MSG_RESIZE_USER = 5;
|
private static final int MSG_RESIZE_USER = 5;
|
||||||
|
|
||||||
|
// Not a complete set of states but serves what we want right now.
|
||||||
|
private enum State {
|
||||||
|
UNDEFINED(0),
|
||||||
|
TASK_APPEARED(1),
|
||||||
|
ENTERING_PIP(2),
|
||||||
|
EXITING_PIP(3);
|
||||||
|
|
||||||
|
private final int mStateValue;
|
||||||
|
|
||||||
|
State(int value) {
|
||||||
|
mStateValue = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean isInPip() {
|
||||||
|
return mStateValue >= TASK_APPEARED.mStateValue
|
||||||
|
&& mStateValue != EXITING_PIP.mStateValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resize request can be initiated in other component, ignore if we are no longer in PIP,
|
||||||
|
* still waiting for animation or we're exiting from it.
|
||||||
|
*
|
||||||
|
* @return {@code true} if the resize request should be blocked/ignored.
|
||||||
|
*/
|
||||||
|
private boolean shouldBlockResizeRequest() {
|
||||||
|
return mStateValue < ENTERING_PIP.mStateValue
|
||||||
|
|| mStateValue == EXITING_PIP.mStateValue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private final Handler mMainHandler;
|
private final Handler mMainHandler;
|
||||||
private final Handler mUpdateHandler;
|
private final Handler mUpdateHandler;
|
||||||
private final PipBoundsHandler mPipBoundsHandler;
|
private final PipBoundsHandler mPipBoundsHandler;
|
||||||
@@ -188,8 +218,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
private ActivityManager.RunningTaskInfo mTaskInfo;
|
private ActivityManager.RunningTaskInfo mTaskInfo;
|
||||||
private WindowContainerToken mToken;
|
private WindowContainerToken mToken;
|
||||||
private SurfaceControl mLeash;
|
private SurfaceControl mLeash;
|
||||||
private boolean mInPip;
|
private State mState = State.UNDEFINED;
|
||||||
private boolean mExitingPip;
|
|
||||||
private @PipAnimationController.AnimationType int mOneShotAnimationType = ANIM_TYPE_BOUNDS;
|
private @PipAnimationController.AnimationType int mOneShotAnimationType = ANIM_TYPE_BOUNDS;
|
||||||
private PipSurfaceTransactionHelper.SurfaceControlTransactionFactory
|
private PipSurfaceTransactionHelper.SurfaceControlTransactionFactory
|
||||||
mSurfaceControlTransactionFactory;
|
mSurfaceControlTransactionFactory;
|
||||||
@@ -241,11 +270,11 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
public boolean isInPip() {
|
public boolean isInPip() {
|
||||||
return mInPip;
|
return mState.isInPip();
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isDeferringEnterPipAnimation() {
|
public boolean isDeferringEnterPipAnimation() {
|
||||||
return mInPip && mShouldDeferEnteringPip;
|
return mState.isInPip() && mShouldDeferEnteringPip;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -274,9 +303,9 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
* @param animationDurationMs duration in millisecond for the exiting PiP transition
|
* @param animationDurationMs duration in millisecond for the exiting PiP transition
|
||||||
*/
|
*/
|
||||||
public void exitPip(int animationDurationMs) {
|
public void exitPip(int animationDurationMs) {
|
||||||
if (!mInPip || mExitingPip || mToken == null) {
|
if (!mState.isInPip() || mState == State.EXITING_PIP || mToken == null) {
|
||||||
Log.wtf(TAG, "Not allowed to exitPip in current state"
|
Log.wtf(TAG, "Not allowed to exitPip in current state"
|
||||||
+ " mInPip=" + mInPip + " mExitingPip=" + mExitingPip + " mToken=" + mToken);
|
+ " mState=" + mState + " mToken=" + mToken);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -293,6 +322,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
? TRANSITION_DIRECTION_TO_SPLIT_SCREEN
|
? TRANSITION_DIRECTION_TO_SPLIT_SCREEN
|
||||||
: TRANSITION_DIRECTION_TO_FULLSCREEN;
|
: TRANSITION_DIRECTION_TO_FULLSCREEN;
|
||||||
if (orientationDiffers) {
|
if (orientationDiffers) {
|
||||||
|
mState = State.EXITING_PIP;
|
||||||
// Send started callback though animation is ignored.
|
// Send started callback though animation is ignored.
|
||||||
sendOnPipTransitionStarted(direction);
|
sendOnPipTransitionStarted(direction);
|
||||||
// Don't bother doing an animation if the display rotation differs or if it's in
|
// Don't bother doing an animation if the display rotation differs or if it's in
|
||||||
@@ -301,7 +331,6 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
WindowOrganizer.applyTransaction(wct);
|
WindowOrganizer.applyTransaction(wct);
|
||||||
// Send finished callback though animation is ignored.
|
// Send finished callback though animation is ignored.
|
||||||
sendOnPipTransitionFinished(direction);
|
sendOnPipTransitionFinished(direction);
|
||||||
mInPip = false;
|
|
||||||
} else {
|
} else {
|
||||||
final SurfaceControl.Transaction tx =
|
final SurfaceControl.Transaction tx =
|
||||||
mSurfaceControlTransactionFactory.getTransaction();
|
mSurfaceControlTransactionFactory.getTransaction();
|
||||||
@@ -320,11 +349,10 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
scheduleAnimateResizePip(mLastReportedBounds, destinationBounds,
|
scheduleAnimateResizePip(mLastReportedBounds, destinationBounds,
|
||||||
null /* sourceHintRect */, direction, animationDurationMs,
|
null /* sourceHintRect */, direction, animationDurationMs,
|
||||||
null /* updateBoundsCallback */);
|
null /* updateBoundsCallback */);
|
||||||
mInPip = false;
|
mState = State.EXITING_PIP;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
mExitingPip = true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void applyWindowingModeChangeOnExit(WindowContainerTransaction wct, int direction) {
|
private void applyWindowingModeChangeOnExit(WindowContainerTransaction wct, int direction) {
|
||||||
@@ -341,9 +369,9 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
* Removes PiP immediately.
|
* Removes PiP immediately.
|
||||||
*/
|
*/
|
||||||
public void removePip() {
|
public void removePip() {
|
||||||
if (!mInPip || mExitingPip || mToken == null) {
|
if (!mState.isInPip() || mToken == null) {
|
||||||
Log.wtf(TAG, "Not allowed to removePip in current state"
|
Log.wtf(TAG, "Not allowed to removePip in current state"
|
||||||
+ " mInPip=" + mInPip + " mExitingPip=" + mExitingPip + " mToken=" + mToken);
|
+ " mState=" + mState + " mToken=" + mToken);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -355,7 +383,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
.setDuration(mEnterExitAnimationDuration)
|
.setDuration(mEnterExitAnimationDuration)
|
||||||
.start());
|
.start());
|
||||||
mCompactState.remove(mToken.asBinder());
|
mCompactState.remove(mToken.asBinder());
|
||||||
mExitingPip = true;
|
mState = State.EXITING_PIP;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void removePipImmediately() {
|
private void removePipImmediately() {
|
||||||
@@ -377,8 +405,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
Objects.requireNonNull(info, "Requires RunningTaskInfo");
|
Objects.requireNonNull(info, "Requires RunningTaskInfo");
|
||||||
mTaskInfo = info;
|
mTaskInfo = info;
|
||||||
mToken = mTaskInfo.token;
|
mToken = mTaskInfo.token;
|
||||||
mInPip = true;
|
mState = State.TASK_APPEARED;
|
||||||
mExitingPip = false;
|
|
||||||
mLeash = leash;
|
mLeash = leash;
|
||||||
mCompactState.put(mToken.asBinder(),
|
mCompactState.put(mToken.asBinder(),
|
||||||
new PipWindowConfigurationCompact(mTaskInfo.configuration.windowConfiguration));
|
new PipWindowConfigurationCompact(mTaskInfo.configuration.windowConfiguration));
|
||||||
@@ -410,6 +437,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
scheduleAnimateResizePip(currentBounds, destinationBounds, sourceHintRect,
|
scheduleAnimateResizePip(currentBounds, destinationBounds, sourceHintRect,
|
||||||
TRANSITION_DIRECTION_TO_PIP, mEnterExitAnimationDuration,
|
TRANSITION_DIRECTION_TO_PIP, mEnterExitAnimationDuration,
|
||||||
null /* updateBoundsCallback */);
|
null /* updateBoundsCallback */);
|
||||||
|
mState = State.ENTERING_PIP;
|
||||||
} else if (mOneShotAnimationType == ANIM_TYPE_ALPHA) {
|
} else if (mOneShotAnimationType == ANIM_TYPE_ALPHA) {
|
||||||
enterPipWithAlphaAnimation(destinationBounds, mEnterExitAnimationDuration);
|
enterPipWithAlphaAnimation(destinationBounds, mEnterExitAnimationDuration);
|
||||||
mOneShotAnimationType = ANIM_TYPE_BOUNDS;
|
mOneShotAnimationType = ANIM_TYPE_BOUNDS;
|
||||||
@@ -455,6 +483,9 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
.setPipAnimationCallback(mPipAnimationCallback)
|
.setPipAnimationCallback(mPipAnimationCallback)
|
||||||
.setDuration(durationMs)
|
.setDuration(durationMs)
|
||||||
.start());
|
.start());
|
||||||
|
// mState is set right after the animation is kicked off to block any resize
|
||||||
|
// requests such as offsetPip that may have been called prior to the transition.
|
||||||
|
mState = State.ENTERING_PIP;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -507,7 +538,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void onTaskVanished(ActivityManager.RunningTaskInfo info) {
|
public void onTaskVanished(ActivityManager.RunningTaskInfo info) {
|
||||||
if (!mInPip) {
|
if (!mState.isInPip()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
final WindowContainerToken token = info.token;
|
final WindowContainerToken token = info.token;
|
||||||
@@ -518,8 +549,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
}
|
}
|
||||||
mShouldDeferEnteringPip = false;
|
mShouldDeferEnteringPip = false;
|
||||||
mPictureInPictureParams = null;
|
mPictureInPictureParams = null;
|
||||||
mInPip = false;
|
mState = State.UNDEFINED;
|
||||||
mExitingPip = false;
|
|
||||||
mPipUiEventLoggerLogger.setTaskInfo(null);
|
mPipUiEventLoggerLogger.setTaskInfo(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -554,7 +584,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onFixedRotationFinished(int displayId) {
|
public void onFixedRotationFinished(int displayId) {
|
||||||
if (mShouldDeferEnteringPip && mInPip) {
|
if (mShouldDeferEnteringPip && mState.isInPip()) {
|
||||||
final Rect destinationBounds = mPipBoundsHandler.getDestinationBounds(
|
final Rect destinationBounds = mPipBoundsHandler.getDestinationBounds(
|
||||||
mTaskInfo.topActivity, getAspectRatioOrDefault(mPictureInPictureParams),
|
mTaskInfo.topActivity, getAspectRatioOrDefault(mPictureInPictureParams),
|
||||||
null /* bounds */, getMinimalSize(mTaskInfo.topActivityInfo));
|
null /* bounds */, getMinimalSize(mTaskInfo.topActivityInfo));
|
||||||
@@ -575,7 +605,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
mPipAnimationController.getCurrentAnimator();
|
mPipAnimationController.getCurrentAnimator();
|
||||||
if (animator == null || !animator.isRunning()
|
if (animator == null || !animator.isRunning()
|
||||||
|| animator.getTransitionDirection() != TRANSITION_DIRECTION_TO_PIP) {
|
|| animator.getTransitionDirection() != TRANSITION_DIRECTION_TO_PIP) {
|
||||||
if (mInPip && fromRotation) {
|
if (mState.isInPip() && fromRotation) {
|
||||||
// If we are rotating while there is a current animation, immediately cancel the
|
// If we are rotating while there is a current animation, immediately cancel the
|
||||||
// animation (remove the listeners so we don't trigger the normal finish resize
|
// animation (remove the listeners so we don't trigger the normal finish resize
|
||||||
// call that should only happen on the update thread)
|
// call that should only happen on the update thread)
|
||||||
@@ -661,10 +691,10 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
private void scheduleAnimateResizePip(Rect currentBounds, Rect destinationBounds,
|
private void scheduleAnimateResizePip(Rect currentBounds, Rect destinationBounds,
|
||||||
Rect sourceHintRect, @PipAnimationController.TransitionDirection int direction,
|
Rect sourceHintRect, @PipAnimationController.TransitionDirection int direction,
|
||||||
int durationMs, Consumer<Rect> updateBoundsCallback) {
|
int durationMs, Consumer<Rect> updateBoundsCallback) {
|
||||||
if (!mInPip) {
|
if (!mState.isInPip()) {
|
||||||
// TODO: tend to use shouldBlockResizeRequest here as well but need to consider
|
// TODO: tend to use shouldBlockResizeRequest here as well but need to consider
|
||||||
// the fact that when in exitPip, scheduleAnimateResizePip is executed in the window
|
// the fact that when in exitPip, scheduleAnimateResizePip is executed in the window
|
||||||
// container transaction callback and we want to set the mExitingPip immediately.
|
// container transaction callback and we want to set the mState immediately.
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -721,7 +751,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
private void scheduleFinishResizePip(Rect destinationBounds,
|
private void scheduleFinishResizePip(Rect destinationBounds,
|
||||||
@PipAnimationController.TransitionDirection int direction,
|
@PipAnimationController.TransitionDirection int direction,
|
||||||
Consumer<Rect> updateBoundsCallback) {
|
Consumer<Rect> updateBoundsCallback) {
|
||||||
if (shouldBlockResizeRequest()) {
|
if (mState.shouldBlockResizeRequest()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -740,7 +770,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
mSurfaceTransactionHelper
|
mSurfaceTransactionHelper
|
||||||
.crop(tx, mLeash, destinationBounds)
|
.crop(tx, mLeash, destinationBounds)
|
||||||
.resetScale(tx, mLeash, destinationBounds)
|
.resetScale(tx, mLeash, destinationBounds)
|
||||||
.round(tx, mLeash, mInPip);
|
.round(tx, mLeash, mState.isInPip());
|
||||||
return tx;
|
return tx;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -749,7 +779,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
*/
|
*/
|
||||||
public void scheduleOffsetPip(Rect originalBounds, int offset, int duration,
|
public void scheduleOffsetPip(Rect originalBounds, int offset, int duration,
|
||||||
Consumer<Rect> updateBoundsCallback) {
|
Consumer<Rect> updateBoundsCallback) {
|
||||||
if (shouldBlockResizeRequest()) {
|
if (mState.shouldBlockResizeRequest()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (mShouldDeferEnteringPip) {
|
if (mShouldDeferEnteringPip) {
|
||||||
@@ -794,7 +824,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
final SurfaceControl.Transaction tx = mSurfaceControlTransactionFactory.getTransaction();
|
final SurfaceControl.Transaction tx = mSurfaceControlTransactionFactory.getTransaction();
|
||||||
mSurfaceTransactionHelper
|
mSurfaceTransactionHelper
|
||||||
.crop(tx, mLeash, destinationBounds)
|
.crop(tx, mLeash, destinationBounds)
|
||||||
.round(tx, mLeash, mInPip);
|
.round(tx, mLeash, mState.isInPip());
|
||||||
tx.apply();
|
tx.apply();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -925,16 +955,6 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
: params.getAspectRatio();
|
: params.getAspectRatio();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Resize request can be initiated in other component, ignore if we are no longer in PIP
|
|
||||||
* or we're exiting from it.
|
|
||||||
*
|
|
||||||
* @return {@code true} if the resize request should be blocked/ignored.
|
|
||||||
*/
|
|
||||||
private boolean shouldBlockResizeRequest() {
|
|
||||||
return !mInPip || mExitingPip;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sync with {@link #mSplitDivider} on destination bounds if PiP is going to split screen.
|
* Sync with {@link #mSplitDivider} on destination bounds if PiP is going to split screen.
|
||||||
*
|
*
|
||||||
@@ -963,7 +983,7 @@ public class PipTaskOrganizer extends TaskOrganizer implements
|
|||||||
pw.println(innerPrefix + "mToken=" + mToken
|
pw.println(innerPrefix + "mToken=" + mToken
|
||||||
+ " binder=" + (mToken != null ? mToken.asBinder() : null));
|
+ " binder=" + (mToken != null ? mToken.asBinder() : null));
|
||||||
pw.println(innerPrefix + "mLeash=" + mLeash);
|
pw.println(innerPrefix + "mLeash=" + mLeash);
|
||||||
pw.println(innerPrefix + "mInPip=" + mInPip);
|
pw.println(innerPrefix + "mState=" + mState);
|
||||||
pw.println(innerPrefix + "mOneShotAnimationType=" + mOneShotAnimationType);
|
pw.println(innerPrefix + "mOneShotAnimationType=" + mOneShotAnimationType);
|
||||||
pw.println(innerPrefix + "mPictureInPictureParams=" + mPictureInPictureParams);
|
pw.println(innerPrefix + "mPictureInPictureParams=" + mPictureInPictureParams);
|
||||||
pw.println(innerPrefix + "mLastReportedBounds=" + mLastReportedBounds);
|
pw.println(innerPrefix + "mLastReportedBounds=" + mLastReportedBounds);
|
||||||
|
|||||||
Reference in New Issue
Block a user