Merge changes I477f34de,I74b0d66c,I3c93e472 into sc-v2-dev
* changes: Animate the pointer when IME comes up Hide the overflow when the IME comes up sometimes Shift bubbles for IME on large screens
This commit is contained in:
@@ -422,14 +422,6 @@ public class Bubble implements BubbleViewProvider {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void setExpandedContentAlpha(float alpha) {
|
|
||||||
if (mExpandedView != null) {
|
|
||||||
mExpandedView.setAlpha(alpha);
|
|
||||||
mExpandedView.setTaskViewAlpha(alpha);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set visibility of bubble in the expanded state.
|
* Set visibility of bubble in the expanded state.
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -144,7 +144,6 @@ public class BubbleController {
|
|||||||
|
|
||||||
private BubbleLogger mLogger;
|
private BubbleLogger mLogger;
|
||||||
private BubbleData mBubbleData;
|
private BubbleData mBubbleData;
|
||||||
private View mBubbleScrim;
|
|
||||||
@Nullable private BubbleStackView mStackView;
|
@Nullable private BubbleStackView mStackView;
|
||||||
private BubbleIconFactory mBubbleIconFactory;
|
private BubbleIconFactory mBubbleIconFactory;
|
||||||
private BubblePositioner mBubblePositioner;
|
private BubblePositioner mBubblePositioner;
|
||||||
@@ -1372,8 +1371,9 @@ public class BubbleController {
|
|||||||
private class BubblesImeListener extends PinnedStackListenerForwarder.PinnedTaskListener {
|
private class BubblesImeListener extends PinnedStackListenerForwarder.PinnedTaskListener {
|
||||||
@Override
|
@Override
|
||||||
public void onImeVisibilityChanged(boolean imeVisible, int imeHeight) {
|
public void onImeVisibilityChanged(boolean imeVisible, int imeHeight) {
|
||||||
|
mBubblePositioner.setImeVisible(imeVisible, imeHeight);
|
||||||
if (mStackView != null) {
|
if (mStackView != null) {
|
||||||
mStackView.onImeVisibilityChanged(imeVisible, imeHeight);
|
mStackView.animateForIme(imeVisible);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -398,6 +398,7 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
updatePointerView();
|
updatePointerView();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Updates the size and visuals of the pointer. **/
|
||||||
private void updatePointerView() {
|
private void updatePointerView() {
|
||||||
LayoutParams lp = (LayoutParams) mPointerView.getLayoutParams();
|
LayoutParams lp = (LayoutParams) mPointerView.getLayoutParams();
|
||||||
if (mCurrentPointer == mLeftPointer || mCurrentPointer == mRightPointer) {
|
if (mCurrentPointer == mLeftPointer || mCurrentPointer == mRightPointer) {
|
||||||
@@ -524,9 +525,8 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
if (mTaskView != null) {
|
if (mTaskView != null) {
|
||||||
mTaskView.setAlpha(alpha);
|
mTaskView.setAlpha(alpha);
|
||||||
}
|
}
|
||||||
if (mManageButton != null && mManageButton.getVisibility() == View.VISIBLE) {
|
mPointerView.setAlpha(alpha);
|
||||||
mManageButton.setAlpha(alpha);
|
setAlpha(alpha);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -545,6 +545,7 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
mIsContentVisible = visibility;
|
mIsContentVisible = visibility;
|
||||||
if (mTaskView != null && !mIsAlphaAnimating) {
|
if (mTaskView != null && !mIsAlphaAnimating) {
|
||||||
mTaskView.setAlpha(visibility ? 1f : 0f);
|
mTaskView.setAlpha(visibility ? 1f : 0f);
|
||||||
|
mPointerView.setAlpha(visibility ? 1f : 0f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -689,7 +690,7 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
* the bubble if showing vertically.
|
* the bubble if showing vertically.
|
||||||
* @param onLeft whether the stack was on the left side of the screen when expanded.
|
* @param onLeft whether the stack was on the left side of the screen when expanded.
|
||||||
*/
|
*/
|
||||||
public void setPointerPosition(float bubblePosition, boolean onLeft) {
|
public void setPointerPosition(float bubblePosition, boolean onLeft, boolean animate) {
|
||||||
// Pointer gets drawn in the padding
|
// Pointer gets drawn in the padding
|
||||||
final boolean showVertically = mPositioner.showBubblesVertically();
|
final boolean showVertically = mPositioner.showBubblesVertically();
|
||||||
final float paddingLeft = (showVertically && onLeft)
|
final float paddingLeft = (showVertically && onLeft)
|
||||||
@@ -710,6 +711,8 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
: pointerPosition;
|
: pointerPosition;
|
||||||
// Post because we need the width of the view
|
// Post because we need the width of the view
|
||||||
post(() -> {
|
post(() -> {
|
||||||
|
mCurrentPointer = showVertically ? onLeft ? mLeftPointer : mRightPointer : mTopPointer;
|
||||||
|
updatePointerView();
|
||||||
float pointerY;
|
float pointerY;
|
||||||
float pointerX;
|
float pointerX;
|
||||||
if (showVertically) {
|
if (showVertically) {
|
||||||
@@ -721,11 +724,13 @@ public class BubbleExpandedView extends LinearLayout {
|
|||||||
pointerY = mPointerOverlap;
|
pointerY = mPointerOverlap;
|
||||||
pointerX = bubbleCenter - (mPointerWidth / 2f);
|
pointerX = bubbleCenter - (mPointerWidth / 2f);
|
||||||
}
|
}
|
||||||
|
if (animate) {
|
||||||
|
mPointerView.animate().translationX(pointerX).translationY(pointerY).start();
|
||||||
|
} else {
|
||||||
mPointerView.setTranslationY(pointerY);
|
mPointerView.setTranslationY(pointerY);
|
||||||
mPointerView.setTranslationX(pointerX);
|
mPointerView.setTranslationX(pointerX);
|
||||||
mCurrentPointer = showVertically ? onLeft ? mLeftPointer : mRightPointer : mTopPointer;
|
|
||||||
updatePointerView();
|
|
||||||
mPointerView.setVisibility(VISIBLE);
|
mPointerView.setVisibility(VISIBLE);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -154,10 +154,6 @@ class BubbleOverflow(
|
|||||||
return dotPath
|
return dotPath
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun setExpandedContentAlpha(alpha: Float) {
|
|
||||||
expandedView?.alpha = alpha
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun setTaskViewVisibility(visible: Boolean) {
|
override fun setTaskViewVisibility(visible: Boolean) {
|
||||||
// Overflow does not have a TaskView.
|
// Overflow does not have a TaskView.
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,13 +70,16 @@ public class BubblePositioner {
|
|||||||
|
|
||||||
private Context mContext;
|
private Context mContext;
|
||||||
private WindowManager mWindowManager;
|
private WindowManager mWindowManager;
|
||||||
private Rect mPositionRect;
|
|
||||||
private Rect mScreenRect;
|
private Rect mScreenRect;
|
||||||
private @Surface.Rotation int mRotation = Surface.ROTATION_0;
|
private @Surface.Rotation int mRotation = Surface.ROTATION_0;
|
||||||
private Insets mInsets;
|
private Insets mInsets;
|
||||||
|
private boolean mImeVisible;
|
||||||
|
private int mImeHeight;
|
||||||
|
private boolean mIsLargeScreen;
|
||||||
|
|
||||||
|
private Rect mPositionRect;
|
||||||
private int mDefaultMaxBubbles;
|
private int mDefaultMaxBubbles;
|
||||||
private int mMaxBubbles;
|
private int mMaxBubbles;
|
||||||
|
|
||||||
private int mBubbleSize;
|
private int mBubbleSize;
|
||||||
private int mSpacingBetweenBubbles;
|
private int mSpacingBetweenBubbles;
|
||||||
|
|
||||||
@@ -98,7 +101,6 @@ public class BubblePositioner {
|
|||||||
private PointF mRestingStackPosition;
|
private PointF mRestingStackPosition;
|
||||||
private int[] mPaddings = new int[4];
|
private int[] mPaddings = new int[4];
|
||||||
|
|
||||||
private boolean mIsLargeScreen;
|
|
||||||
private boolean mShowingInTaskbar;
|
private boolean mShowingInTaskbar;
|
||||||
private @TaskbarPosition int mTaskbarPosition = TASKBAR_POSITION_NONE;
|
private @TaskbarPosition int mTaskbarPosition = TASKBAR_POSITION_NONE;
|
||||||
private int mTaskbarIconSize;
|
private int mTaskbarIconSize;
|
||||||
@@ -302,6 +304,17 @@ public class BubblePositioner {
|
|||||||
return mMaxBubbles;
|
return mMaxBubbles;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** The height for the IME if it's visible. **/
|
||||||
|
public int getImeHeight() {
|
||||||
|
return mImeVisible ? mImeHeight : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Sets whether the IME is visible. **/
|
||||||
|
public void setImeVisible(boolean visible, int height) {
|
||||||
|
mImeVisible = visible;
|
||||||
|
mImeHeight = height;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Calculates the padding for the bubble expanded view.
|
* Calculates the padding for the bubble expanded view.
|
||||||
*
|
*
|
||||||
@@ -357,7 +370,7 @@ public class BubblePositioner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** Gets the y position of the expanded view if it was top-aligned. */
|
/** Gets the y position of the expanded view if it was top-aligned. */
|
||||||
private float getExpandedViewYTopAligned() {
|
public float getExpandedViewYTopAligned() {
|
||||||
final int top = getAvailableRect().top;
|
final int top = getAvailableRect().top;
|
||||||
if (showBubblesVertically()) {
|
if (showBubblesVertically()) {
|
||||||
return top - mPointerWidth + mExpandedViewPadding;
|
return top - mPointerWidth + mExpandedViewPadding;
|
||||||
@@ -366,10 +379,6 @@ public class BubblePositioner {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public float getExpandedBubblesY() {
|
|
||||||
return getAvailableRect().top + mExpandedViewPadding;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Calculate the maximum height the expanded view can be depending on where it's placed on
|
* Calculate the maximum height the expanded view can be depending on where it's placed on
|
||||||
* the screen and the size of the elements around it (e.g. padding, pointer, manage button).
|
* the screen and the size of the elements around it (e.g. padding, pointer, manage button).
|
||||||
@@ -464,18 +473,21 @@ public class BubblePositioner {
|
|||||||
: bubblePosition + (normalizedSize / 2f) - mPointerWidth;
|
: bubblePosition + (normalizedSize / 2f) - mPointerWidth;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private int getExpandedStackSize(int numberOfBubbles) {
|
||||||
|
return (numberOfBubbles * mBubbleSize)
|
||||||
|
+ ((numberOfBubbles - 1) * mSpacingBetweenBubbles);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the position of the bubble on-screen when the stack is expanded.
|
* Returns the position of the bubble on-screen when the stack is expanded.
|
||||||
*
|
*
|
||||||
* @param index the index of the bubble in the stack.
|
* @param index the index of the bubble in the stack.
|
||||||
* @param numberOfBubbles the total number of bubbles in the stack.
|
* @param state state information about the stack to help with calculations.
|
||||||
* @param onLeftEdge whether the stack would rest on the left edge of the screen when collapsed.
|
* @return the position of the bubble on-screen when the stack is expanded.
|
||||||
* @return the x, y position of the bubble on-screen when the stack is expanded.
|
|
||||||
*/
|
*/
|
||||||
public PointF getExpandedBubbleXY(int index, int numberOfBubbles, boolean onLeftEdge) {
|
public PointF getExpandedBubbleXY(int index, BubbleStackView.StackViewState state) {
|
||||||
final float positionInRow = index * (mBubbleSize + mSpacingBetweenBubbles);
|
final float positionInRow = index * (mBubbleSize + mSpacingBetweenBubbles);
|
||||||
final float expandedStackSize = (numberOfBubbles * mBubbleSize)
|
final float expandedStackSize = getExpandedStackSize(state.numberOfBubbles);
|
||||||
+ ((numberOfBubbles - 1) * mSpacingBetweenBubbles);
|
|
||||||
final float centerPosition = showBubblesVertically()
|
final float centerPosition = showBubblesVertically()
|
||||||
? mPositionRect.centerY()
|
? mPositionRect.centerY()
|
||||||
: mPositionRect.centerX();
|
: mPositionRect.centerX();
|
||||||
@@ -491,16 +503,65 @@ public class BubblePositioner {
|
|||||||
int right = mIsLargeScreen
|
int right = mIsLargeScreen
|
||||||
? mPositionRect.right - mExpandedViewLargeScreenInset + mExpandedViewPadding
|
? mPositionRect.right - mExpandedViewLargeScreenInset + mExpandedViewPadding
|
||||||
: mPositionRect.right - mBubbleSize;
|
: mPositionRect.right - mBubbleSize;
|
||||||
x = onLeftEdge
|
x = state.onLeft
|
||||||
? left
|
? left
|
||||||
: right;
|
: right;
|
||||||
} else {
|
} else {
|
||||||
y = mPositionRect.top + mExpandedViewPadding;
|
y = mPositionRect.top + mExpandedViewPadding;
|
||||||
x = rowStart + positionInRow;
|
x = rowStart + positionInRow;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (showBubblesVertically() && mImeVisible) {
|
||||||
|
return new PointF(x, getExpandedBubbleYForIme(index, state.numberOfBubbles));
|
||||||
|
}
|
||||||
return new PointF(x, y);
|
return new PointF(x, y);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the position of the bubble on-screen when the stack is expanded and the IME
|
||||||
|
* is showing.
|
||||||
|
*
|
||||||
|
* @param index the index of the bubble in the stack.
|
||||||
|
* @param numberOfBubbles the total number of bubbles in the stack.
|
||||||
|
* @return y position of the bubble on-screen when the stack is expanded.
|
||||||
|
*/
|
||||||
|
private float getExpandedBubbleYForIme(int index, int numberOfBubbles) {
|
||||||
|
final float top = getAvailableRect().top + mExpandedViewPadding;
|
||||||
|
if (!showBubblesVertically()) {
|
||||||
|
// Showing horizontally: align to top
|
||||||
|
return top;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Showing vertically: might need to translate the bubbles above the IME.
|
||||||
|
// Subtract spacing here to provide a margin between top of IME and bottom of bubble row.
|
||||||
|
final float bottomInset = getImeHeight() + mInsets.bottom - (mSpacingBetweenBubbles * 2);
|
||||||
|
final float expandedStackSize = getExpandedStackSize(numberOfBubbles);
|
||||||
|
final float centerPosition = showBubblesVertically()
|
||||||
|
? mPositionRect.centerY()
|
||||||
|
: mPositionRect.centerX();
|
||||||
|
final float rowBottom = centerPosition + (expandedStackSize / 2f);
|
||||||
|
final float rowTop = centerPosition - (expandedStackSize / 2f);
|
||||||
|
float rowTopForIme = rowTop;
|
||||||
|
if (rowBottom > bottomInset) {
|
||||||
|
// We overlap with IME, must shift the bubbles
|
||||||
|
float translationY = rowBottom - bottomInset;
|
||||||
|
rowTopForIme = Math.max(rowTop - translationY, top);
|
||||||
|
if (rowTop - translationY < top) {
|
||||||
|
// Even if we shift the bubbles, they will still overlap with the IME.
|
||||||
|
// Hide the overflow for a lil more space:
|
||||||
|
final float expandedStackSizeNoO = getExpandedStackSize(numberOfBubbles - 1);
|
||||||
|
final float centerPositionNoO = showBubblesVertically()
|
||||||
|
? mPositionRect.centerY()
|
||||||
|
: mPositionRect.centerX();
|
||||||
|
final float rowBottomNoO = centerPositionNoO + (expandedStackSizeNoO / 2f);
|
||||||
|
final float rowTopNoO = centerPositionNoO - (expandedStackSizeNoO / 2f);
|
||||||
|
translationY = rowBottomNoO - bottomInset;
|
||||||
|
rowTopForIme = rowTopNoO - translationY;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return rowTopForIme + (index * (mBubbleSize + mSpacingBetweenBubbles));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return the width of the bubble flyout (message originating from the bubble).
|
* @return the width of the bubble flyout (message originating from the bubble).
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -28,6 +28,8 @@ import static com.android.wm.shell.bubbles.BubblePositioner.NUM_VISIBLE_WHEN_RES
|
|||||||
|
|
||||||
import android.animation.Animator;
|
import android.animation.Animator;
|
||||||
import android.animation.AnimatorListenerAdapter;
|
import android.animation.AnimatorListenerAdapter;
|
||||||
|
import android.animation.AnimatorSet;
|
||||||
|
import android.animation.ObjectAnimator;
|
||||||
import android.animation.ValueAnimator;
|
import android.animation.ValueAnimator;
|
||||||
import android.annotation.SuppressLint;
|
import android.annotation.SuppressLint;
|
||||||
import android.content.ContentResolver;
|
import android.content.ContentResolver;
|
||||||
@@ -188,6 +190,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
};
|
};
|
||||||
private final BubbleController mBubbleController;
|
private final BubbleController mBubbleController;
|
||||||
private final BubbleData mBubbleData;
|
private final BubbleData mBubbleData;
|
||||||
|
private StackViewState mStackViewState = new StackViewState();
|
||||||
|
|
||||||
private final ValueAnimator mDismissBubbleAnimator;
|
private final ValueAnimator mDismissBubbleAnimator;
|
||||||
|
|
||||||
@@ -246,7 +249,6 @@ public class BubbleStackView extends FrameLayout
|
|||||||
private int mBubbleTouchPadding;
|
private int mBubbleTouchPadding;
|
||||||
private int mExpandedViewPadding;
|
private int mExpandedViewPadding;
|
||||||
private int mCornerRadius;
|
private int mCornerRadius;
|
||||||
private int mImeOffset;
|
|
||||||
@Nullable private BubbleViewProvider mExpandedBubble;
|
@Nullable private BubbleViewProvider mExpandedBubble;
|
||||||
private boolean mIsExpanded;
|
private boolean mIsExpanded;
|
||||||
|
|
||||||
@@ -757,7 +759,6 @@ public class BubbleStackView extends FrameLayout
|
|||||||
mBubbleSize = res.getDimensionPixelSize(R.dimen.bubble_size);
|
mBubbleSize = res.getDimensionPixelSize(R.dimen.bubble_size);
|
||||||
mBubbleElevation = res.getDimensionPixelSize(R.dimen.bubble_elevation);
|
mBubbleElevation = res.getDimensionPixelSize(R.dimen.bubble_elevation);
|
||||||
mBubbleTouchPadding = res.getDimensionPixelSize(R.dimen.bubble_touch_padding);
|
mBubbleTouchPadding = res.getDimensionPixelSize(R.dimen.bubble_touch_padding);
|
||||||
mImeOffset = res.getDimensionPixelSize(R.dimen.pip_ime_offset);
|
|
||||||
|
|
||||||
mExpandedViewPadding = res.getDimensionPixelSize(R.dimen.bubble_expanded_view_padding);
|
mExpandedViewPadding = res.getDimensionPixelSize(R.dimen.bubble_expanded_view_padding);
|
||||||
int elevation = res.getDimensionPixelSize(R.dimen.bubble_elevation);
|
int elevation = res.getDimensionPixelSize(R.dimen.bubble_elevation);
|
||||||
@@ -779,7 +780,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
this::animateShadows /* onStackAnimationFinished */, mPositioner);
|
this::animateShadows /* onStackAnimationFinished */, mPositioner);
|
||||||
|
|
||||||
mExpandedAnimationController = new ExpandedAnimationController(mPositioner,
|
mExpandedAnimationController = new ExpandedAnimationController(mPositioner,
|
||||||
onBubbleAnimatedOut);
|
onBubbleAnimatedOut, this);
|
||||||
mSurfaceSynchronizer = synchronizer != null ? synchronizer : DEFAULT_SURFACE_SYNCHRONIZER;
|
mSurfaceSynchronizer = synchronizer != null ? synchronizer : DEFAULT_SURFACE_SYNCHRONIZER;
|
||||||
|
|
||||||
// Force LTR by default since most of the Bubbles UI is positioned manually by the user, or
|
// Force LTR by default since most of the Bubbles UI is positioned manually by the user, or
|
||||||
@@ -890,7 +891,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
// Re-draw bubble row and pointer for new orientation.
|
// Re-draw bubble row and pointer for new orientation.
|
||||||
beforeExpandedViewAnimation();
|
beforeExpandedViewAnimation();
|
||||||
updateOverflowVisibility();
|
updateOverflowVisibility();
|
||||||
updatePointerPosition();
|
updatePointerPosition(false /* forIme */);
|
||||||
mExpandedAnimationController.expandFromStack(() -> {
|
mExpandedAnimationController.expandFromStack(() -> {
|
||||||
afterExpandedViewAnimation();
|
afterExpandedViewAnimation();
|
||||||
} /* after */);
|
} /* after */);
|
||||||
@@ -968,7 +969,8 @@ public class BubbleStackView extends FrameLayout
|
|||||||
});
|
});
|
||||||
mExpandedViewAlphaAnimator.addUpdateListener(valueAnimator -> {
|
mExpandedViewAlphaAnimator.addUpdateListener(valueAnimator -> {
|
||||||
if (mExpandedBubble != null) {
|
if (mExpandedBubble != null) {
|
||||||
mExpandedBubble.setExpandedContentAlpha((float) valueAnimator.getAnimatedValue());
|
mExpandedBubble.getExpandedView().setTaskViewAlpha(
|
||||||
|
(float) valueAnimator.getAnimatedValue());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -1558,7 +1560,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
} else {
|
} else {
|
||||||
bubble.cleanupViews();
|
bubble.cleanupViews();
|
||||||
}
|
}
|
||||||
updatePointerPosition();
|
updatePointerPosition(false /* forIme */);
|
||||||
updateExpandedView();
|
updateExpandedView();
|
||||||
logBubbleEvent(bubble, FrameworkStatsLog.BUBBLE_UICHANGED__ACTION__DISMISSED);
|
logBubbleEvent(bubble, FrameworkStatsLog.BUBBLE_UICHANGED__ACTION__DISMISSED);
|
||||||
return;
|
return;
|
||||||
@@ -1599,7 +1601,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
.map(b -> b.getIconView()).collect(Collectors.toList());
|
.map(b -> b.getIconView()).collect(Collectors.toList());
|
||||||
mStackAnimationController.animateReorder(bubbleViews, reorder);
|
mStackAnimationController.animateReorder(bubbleViews, reorder);
|
||||||
}
|
}
|
||||||
updatePointerPosition();
|
updatePointerPosition(false /* forIme */);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1670,7 +1672,6 @@ public class BubbleStackView extends FrameLayout
|
|||||||
private void showNewlySelectedBubble(BubbleViewProvider bubbleToSelect) {
|
private void showNewlySelectedBubble(BubbleViewProvider bubbleToSelect) {
|
||||||
final BubbleViewProvider previouslySelected = mExpandedBubble;
|
final BubbleViewProvider previouslySelected = mExpandedBubble;
|
||||||
mExpandedBubble = bubbleToSelect;
|
mExpandedBubble = bubbleToSelect;
|
||||||
updatePointerPosition();
|
|
||||||
|
|
||||||
if (mIsExpanded) {
|
if (mIsExpanded) {
|
||||||
hideCurrentInputMethod();
|
hideCurrentInputMethod();
|
||||||
@@ -1762,6 +1763,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
* not.
|
* not.
|
||||||
*/
|
*/
|
||||||
void hideCurrentInputMethod() {
|
void hideCurrentInputMethod() {
|
||||||
|
mPositioner.setImeVisible(false, 0);
|
||||||
mBubbleController.hideCurrentInputMethod();
|
mBubbleController.hideCurrentInputMethod();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1864,7 +1866,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
updateBadges(false /* setBadgeForCollapsedStack */);
|
updateBadges(false /* setBadgeForCollapsedStack */);
|
||||||
mBubbleContainer.setActiveController(mExpandedAnimationController);
|
mBubbleContainer.setActiveController(mExpandedAnimationController);
|
||||||
updateOverflowVisibility();
|
updateOverflowVisibility();
|
||||||
updatePointerPosition();
|
updatePointerPosition(false /* forIme */);
|
||||||
mExpandedAnimationController.expandFromStack(() -> {
|
mExpandedAnimationController.expandFromStack(() -> {
|
||||||
if (mIsExpanded && mExpandedBubble.getExpandedView() != null) {
|
if (mIsExpanded && mExpandedBubble.getExpandedView() != null) {
|
||||||
maybeShowManageEdu();
|
maybeShowManageEdu();
|
||||||
@@ -1876,8 +1878,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
} else {
|
} else {
|
||||||
index = getBubbleIndex(mExpandedBubble);
|
index = getBubbleIndex(mExpandedBubble);
|
||||||
}
|
}
|
||||||
PointF p = mPositioner.getExpandedBubbleXY(index, mBubbleContainer.getChildCount(),
|
PointF p = mPositioner.getExpandedBubbleXY(index, getState());
|
||||||
mStackOnLeftOrWillBe);
|
|
||||||
final float translationY = mPositioner.getExpandedViewY(mExpandedBubble,
|
final float translationY = mPositioner.getExpandedViewY(mExpandedBubble,
|
||||||
mPositioner.showBubblesVertically() ? p.y : p.x);
|
mPositioner.showBubblesVertically() ? p.y : p.x);
|
||||||
mExpandedViewContainer.setTranslationX(0f);
|
mExpandedViewContainer.setTranslationX(0f);
|
||||||
@@ -1928,7 +1929,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
mExpandedViewContainer.setAnimationMatrix(mExpandedViewContainerMatrix);
|
mExpandedViewContainer.setAnimationMatrix(mExpandedViewContainerMatrix);
|
||||||
|
|
||||||
if (mExpandedBubble.getExpandedView() != null) {
|
if (mExpandedBubble.getExpandedView() != null) {
|
||||||
mExpandedBubble.setExpandedContentAlpha(0f);
|
mExpandedBubble.getExpandedView().setTaskViewAlpha(0f);
|
||||||
|
|
||||||
// We'll be starting the alpha animation after a slight delay, so set this flag early
|
// We'll be starting the alpha animation after a slight delay, so set this flag early
|
||||||
// here.
|
// here.
|
||||||
@@ -2011,8 +2012,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
index = mBubbleData.getBubbles().indexOf(mExpandedBubble);
|
index = mBubbleData.getBubbles().indexOf(mExpandedBubble);
|
||||||
}
|
}
|
||||||
// Value the bubble is animating from (back into the stack).
|
// Value the bubble is animating from (back into the stack).
|
||||||
final PointF p = mPositioner.getExpandedBubbleXY(index,
|
final PointF p = mPositioner.getExpandedBubbleXY(index, getState());
|
||||||
mBubbleContainer.getChildCount(), mStackOnLeftOrWillBe);
|
|
||||||
if (mPositioner.showBubblesVertically()) {
|
if (mPositioner.showBubblesVertically()) {
|
||||||
float pivotX;
|
float pivotX;
|
||||||
float pivotY = p.y + mBubbleSize / 2f;
|
float pivotY = p.y + mBubbleSize / 2f;
|
||||||
@@ -2109,7 +2109,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
PointF p = mPositioner.getExpandedBubbleXY(isOverflow
|
PointF p = mPositioner.getExpandedBubbleXY(isOverflow
|
||||||
? mBubbleContainer.getChildCount() - 1
|
? mBubbleContainer.getChildCount() - 1
|
||||||
: mBubbleData.getBubbles().indexOf(mExpandedBubble),
|
: mBubbleData.getBubbles().indexOf(mExpandedBubble),
|
||||||
mBubbleContainer.getChildCount(), mStackOnLeftOrWillBe);
|
getState());
|
||||||
mExpandedViewContainer.setAlpha(1f);
|
mExpandedViewContainer.setAlpha(1f);
|
||||||
mExpandedViewContainer.setVisibility(View.VISIBLE);
|
mExpandedViewContainer.setVisibility(View.VISIBLE);
|
||||||
|
|
||||||
@@ -2187,9 +2187,20 @@ public class BubbleStackView extends FrameLayout
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Moves the bubbles out of the way if they're going to be over the keyboard. */
|
/**
|
||||||
public void onImeVisibilityChanged(boolean visible, int height) {
|
* Updates the stack based for IME changes. When collapsed it'll move the stack if it
|
||||||
mStackAnimationController.setImeHeight(visible ? height + mImeOffset : 0);
|
* overlaps where they IME would be. When expanded it'll shift the expanded bubbles
|
||||||
|
* if they might overlap with the IME (this only happens for large screens).
|
||||||
|
*/
|
||||||
|
public void animateForIme(boolean visible) {
|
||||||
|
if ((mIsExpansionAnimating || mIsBubbleSwitchAnimating) && mIsExpanded) {
|
||||||
|
// This will update the animation so the bubbles move to position for the IME
|
||||||
|
mExpandedAnimationController.expandFromStack(() -> {
|
||||||
|
updatePointerPosition(false /* forIme */);
|
||||||
|
afterExpandedViewAnimation();
|
||||||
|
} /* after */);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!mIsExpanded && getBubbleCount() > 0) {
|
if (!mIsExpanded && getBubbleCount() > 0) {
|
||||||
final float stackDestinationY =
|
final float stackDestinationY =
|
||||||
@@ -2208,9 +2219,20 @@ public class BubbleStackView extends FrameLayout
|
|||||||
FLYOUT_IME_ANIMATION_SPRING_CONFIG)
|
FLYOUT_IME_ANIMATION_SPRING_CONFIG)
|
||||||
.start();
|
.start();
|
||||||
}
|
}
|
||||||
} else if (mIsExpanded && mExpandedBubble != null
|
} else if (mPositioner.showBubblesVertically() && mIsExpanded
|
||||||
&& mExpandedBubble.getExpandedView() != null) {
|
&& mExpandedBubble != null && mExpandedBubble.getExpandedView() != null) {
|
||||||
mExpandedBubble.getExpandedView().setImeVisible(visible);
|
mExpandedBubble.getExpandedView().setImeVisible(visible);
|
||||||
|
List<Animator> animList = new ArrayList();
|
||||||
|
for (int i = 0; i < mBubbleContainer.getChildCount(); i++) {
|
||||||
|
View child = mBubbleContainer.getChildAt(i);
|
||||||
|
float transY = mPositioner.getExpandedBubbleXY(i, getState()).y;
|
||||||
|
ObjectAnimator anim = ObjectAnimator.ofFloat(child, TRANSLATION_Y, transY);
|
||||||
|
animList.add(anim);
|
||||||
|
}
|
||||||
|
updatePointerPosition(true /* forIme */);
|
||||||
|
AnimatorSet set = new AnimatorSet();
|
||||||
|
set.playTogether(animList);
|
||||||
|
set.start();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2514,7 +2536,7 @@ public class BubbleStackView extends FrameLayout
|
|||||||
// Account for the IME in the touchable region so that the touchable region of the
|
// Account for the IME in the touchable region so that the touchable region of the
|
||||||
// Bubble window doesn't obscure the IME. The touchable region affects which areas
|
// Bubble window doesn't obscure the IME. The touchable region affects which areas
|
||||||
// of the screen can be excluded by lower windows (IME is just above the embedded task)
|
// of the screen can be excluded by lower windows (IME is just above the embedded task)
|
||||||
outRect.bottom -= (int) mStackAnimationController.getImeHeight();
|
outRect.bottom -= mPositioner.getImeHeight();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mFlyout.getVisibility() == View.VISIBLE) {
|
if (mFlyout.getVisibility() == View.VISIBLE) {
|
||||||
@@ -2773,13 +2795,13 @@ public class BubbleStackView extends FrameLayout
|
|||||||
}
|
}
|
||||||
if (mExpandedBubble != null && mExpandedBubble.getExpandedView() != null) {
|
if (mExpandedBubble != null && mExpandedBubble.getExpandedView() != null) {
|
||||||
PointF p = mPositioner.getExpandedBubbleXY(getBubbleIndex(mExpandedBubble),
|
PointF p = mPositioner.getExpandedBubbleXY(getBubbleIndex(mExpandedBubble),
|
||||||
mBubbleContainer.getChildCount(), mStackOnLeftOrWillBe);
|
getState());
|
||||||
mExpandedViewContainer.setTranslationY(mPositioner.getExpandedViewY(mExpandedBubble,
|
mExpandedViewContainer.setTranslationY(mPositioner.getExpandedViewY(mExpandedBubble,
|
||||||
mPositioner.showBubblesVertically() ? p.y : p.x));
|
mPositioner.showBubblesVertically() ? p.y : p.x));
|
||||||
mExpandedViewContainer.setTranslationX(0f);
|
mExpandedViewContainer.setTranslationX(0f);
|
||||||
mExpandedBubble.getExpandedView().updateView(
|
mExpandedBubble.getExpandedView().updateView(
|
||||||
mExpandedViewContainer.getLocationOnScreen());
|
mExpandedViewContainer.getLocationOnScreen());
|
||||||
updatePointerPosition();
|
updatePointerPosition(false /* forIme */);
|
||||||
}
|
}
|
||||||
|
|
||||||
mStackOnLeftOrWillBe = mStackAnimationController.isStackOnLeftSide();
|
mStackOnLeftOrWillBe = mStackAnimationController.isStackOnLeftSide();
|
||||||
@@ -2850,7 +2872,13 @@ public class BubbleStackView extends FrameLayout
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updatePointerPosition() {
|
/**
|
||||||
|
* Updates the position of the pointer based on the expanded bubble.
|
||||||
|
*
|
||||||
|
* @param forIme whether the position is being updated due to the ime appearing, in this case
|
||||||
|
* the pointer is animated to the location.
|
||||||
|
*/
|
||||||
|
private void updatePointerPosition(boolean forIme) {
|
||||||
if (mExpandedBubble == null || mExpandedBubble.getExpandedView() == null) {
|
if (mExpandedBubble == null || mExpandedBubble.getExpandedView() == null) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -2858,13 +2886,12 @@ public class BubbleStackView extends FrameLayout
|
|||||||
if (index == -1) {
|
if (index == -1) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
PointF bubblePosition = mPositioner.getExpandedBubbleXY(index,
|
PointF position = mPositioner.getExpandedBubbleXY(index, getState());
|
||||||
mBubbleContainer.getChildCount(),
|
float bubblePosition = mPositioner.showBubblesVertically()
|
||||||
mStackOnLeftOrWillBe);
|
? position.y
|
||||||
mExpandedBubble.getExpandedView().setPointerPosition(mPositioner.showBubblesVertically()
|
: position.x;
|
||||||
? bubblePosition.y
|
mExpandedBubble.getExpandedView().setPointerPosition(bubblePosition,
|
||||||
: bubblePosition.x,
|
mStackOnLeftOrWillBe, forIme /* animate */);
|
||||||
mStackOnLeftOrWillBe);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -2947,6 +2974,26 @@ public class BubbleStackView extends FrameLayout
|
|||||||
return bubbles;
|
return bubbles;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @return the current stack state. */
|
||||||
|
public StackViewState getState() {
|
||||||
|
mStackViewState.numberOfBubbles = mBubbleContainer.getChildCount();
|
||||||
|
mStackViewState.selectedIndex = getBubbleIndex(mExpandedBubble);
|
||||||
|
mStackViewState.onLeft = mStackOnLeftOrWillBe;
|
||||||
|
return mStackViewState;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Holds some commonly queried information about the stack.
|
||||||
|
*/
|
||||||
|
public static class StackViewState {
|
||||||
|
// Number of bubbles (including the overflow itself) in the stack.
|
||||||
|
public int numberOfBubbles;
|
||||||
|
// The selected index if the stack is expanded.
|
||||||
|
public int selectedIndex;
|
||||||
|
// Whether the stack is resting on the left or right side of the screen when collapsed.
|
||||||
|
public boolean onLeft;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Representation of stack position that uses relative properties rather than absolute
|
* Representation of stack position that uses relative properties rather than absolute
|
||||||
* coordinates. This is used to maintain similar stack positions across configuration changes.
|
* coordinates. This is used to maintain similar stack positions across configuration changes.
|
||||||
|
|||||||
@@ -28,12 +28,6 @@ import androidx.annotation.Nullable;
|
|||||||
public interface BubbleViewProvider {
|
public interface BubbleViewProvider {
|
||||||
@Nullable BubbleExpandedView getExpandedView();
|
@Nullable BubbleExpandedView getExpandedView();
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the alpha of the expanded view content. This will be applied to both the expanded view
|
|
||||||
* container itself (the manage button, etc.) as well as the TaskView within it.
|
|
||||||
*/
|
|
||||||
void setExpandedContentAlpha(float alpha);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sets whether the contents of the bubble's TaskView should be visible.
|
* Sets whether the contents of the bubble's TaskView should be visible.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -21,7 +21,6 @@ import static com.android.wm.shell.bubbles.BubblePositioner.NUM_VISIBLE_WHEN_RES
|
|||||||
import android.content.res.Resources;
|
import android.content.res.Resources;
|
||||||
import android.graphics.Path;
|
import android.graphics.Path;
|
||||||
import android.graphics.PointF;
|
import android.graphics.PointF;
|
||||||
import android.graphics.Rect;
|
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
@@ -33,6 +32,7 @@ import com.android.wm.shell.R;
|
|||||||
import com.android.wm.shell.animation.Interpolators;
|
import com.android.wm.shell.animation.Interpolators;
|
||||||
import com.android.wm.shell.animation.PhysicsAnimator;
|
import com.android.wm.shell.animation.PhysicsAnimator;
|
||||||
import com.android.wm.shell.bubbles.BubblePositioner;
|
import com.android.wm.shell.bubbles.BubblePositioner;
|
||||||
|
import com.android.wm.shell.bubbles.BubbleStackView;
|
||||||
import com.android.wm.shell.common.magnetictarget.MagnetizedObject;
|
import com.android.wm.shell.common.magnetictarget.MagnetizedObject;
|
||||||
|
|
||||||
import com.google.android.collect.Sets;
|
import com.google.android.collect.Sets;
|
||||||
@@ -124,12 +124,15 @@ public class ExpandedAnimationController
|
|||||||
|
|
||||||
private BubblePositioner mPositioner;
|
private BubblePositioner mPositioner;
|
||||||
|
|
||||||
|
private BubbleStackView mBubbleStackView;
|
||||||
|
|
||||||
public ExpandedAnimationController(BubblePositioner positioner,
|
public ExpandedAnimationController(BubblePositioner positioner,
|
||||||
Runnable onBubbleAnimatedOutAction) {
|
Runnable onBubbleAnimatedOutAction, BubbleStackView stackView) {
|
||||||
mPositioner = positioner;
|
mPositioner = positioner;
|
||||||
updateResources();
|
updateResources();
|
||||||
mOnBubbleAnimatedOutAction = onBubbleAnimatedOutAction;
|
mOnBubbleAnimatedOutAction = onBubbleAnimatedOutAction;
|
||||||
mCollapsePoint = mPositioner.getDefaultStartPosition();
|
mCollapsePoint = mPositioner.getDefaultStartPosition();
|
||||||
|
mBubbleStackView = stackView;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -239,10 +242,7 @@ public class ExpandedAnimationController
|
|||||||
final Path path = new Path();
|
final Path path = new Path();
|
||||||
path.moveTo(bubble.getTranslationX(), bubble.getTranslationY());
|
path.moveTo(bubble.getTranslationX(), bubble.getTranslationY());
|
||||||
|
|
||||||
boolean onLeft = mPositioner.isStackOnLeft(mCollapsePoint);
|
final PointF p = mPositioner.getExpandedBubbleXY(index, mBubbleStackView.getState());
|
||||||
final PointF p = mPositioner.getExpandedBubbleXY(index,
|
|
||||||
mLayout.getChildCount(),
|
|
||||||
onLeft);
|
|
||||||
if (expanding) {
|
if (expanding) {
|
||||||
// If we're expanding, first draw a line from the bubble's current position to where
|
// If we're expanding, first draw a line from the bubble's current position to where
|
||||||
// it'll end up
|
// it'll end up
|
||||||
@@ -364,7 +364,7 @@ public class ExpandedAnimationController
|
|||||||
bubbleView.setTranslationY(y);
|
bubbleView.setTranslationY(y);
|
||||||
}
|
}
|
||||||
|
|
||||||
final float expandedY = mPositioner.getExpandedBubblesY();
|
final float expandedY = mPositioner.getExpandedViewYTopAligned();
|
||||||
final boolean draggedOutEnough =
|
final boolean draggedOutEnough =
|
||||||
y > expandedY + mBubbleSizePx || y < expandedY - mBubbleSizePx;
|
y > expandedY + mBubbleSizePx || y < expandedY - mBubbleSizePx;
|
||||||
if (draggedOutEnough != mBubbleDraggedOutEnough) {
|
if (draggedOutEnough != mBubbleDraggedOutEnough) {
|
||||||
@@ -410,8 +410,7 @@ public class ExpandedAnimationController
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
final int index = mLayout.indexOfChild(bubbleView);
|
final int index = mLayout.indexOfChild(bubbleView);
|
||||||
final PointF p = mPositioner.getExpandedBubbleXY(index, mLayout.getChildCount(),
|
final PointF p = mPositioner.getExpandedBubbleXY(index, mBubbleStackView.getState());
|
||||||
mPositioner.isStackOnLeft(mCollapsePoint));
|
|
||||||
animationForChildAtIndex(index)
|
animationForChildAtIndex(index)
|
||||||
.position(p.x, p.y)
|
.position(p.x, p.y)
|
||||||
.withPositionStartVelocities(velX, velY)
|
.withPositionStartVelocities(velX, velY)
|
||||||
@@ -429,16 +428,6 @@ public class ExpandedAnimationController
|
|||||||
updateBubblePositions();
|
updateBubblePositions();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Animates the bubbles to the y position. Used in response to IME showing.
|
|
||||||
*/
|
|
||||||
public void updateYPosition(Runnable after) {
|
|
||||||
if (mLayout == null) return;
|
|
||||||
animationsForChildrenFromIndex(
|
|
||||||
0, (i, anim) -> anim.translationY(mPositioner.getExpandedBubblesY()))
|
|
||||||
.startAll(after);
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Description of current animation controller state. */
|
/** Description of current animation controller state. */
|
||||||
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
|
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
|
||||||
pw.println("ExpandedAnimationController state:");
|
pw.println("ExpandedAnimationController state:");
|
||||||
@@ -496,30 +485,28 @@ public class ExpandedAnimationController
|
|||||||
startOrUpdatePathAnimation(false /* expanding */);
|
startOrUpdatePathAnimation(false /* expanding */);
|
||||||
} else {
|
} else {
|
||||||
boolean onLeft = mPositioner.isStackOnLeft(mCollapsePoint);
|
boolean onLeft = mPositioner.isStackOnLeft(mCollapsePoint);
|
||||||
final PointF p = mPositioner.getExpandedBubbleXY(index,
|
final PointF p = mPositioner.getExpandedBubbleXY(index, mBubbleStackView.getState());
|
||||||
mLayout.getChildCount(),
|
|
||||||
onLeft);
|
|
||||||
if (mPositioner.showBubblesVertically()) {
|
if (mPositioner.showBubblesVertically()) {
|
||||||
child.setTranslationY(p.y);
|
child.setTranslationY(p.y);
|
||||||
} else {
|
} else {
|
||||||
child.setTranslationX(p.x);
|
child.setTranslationX(p.x);
|
||||||
}
|
}
|
||||||
if (!mPreparingToCollapse) {
|
|
||||||
// Only animate if we're not collapsing as that animation will handle placing the
|
if (mPreparingToCollapse) {
|
||||||
|
// Don't animate if we're collapsing, as that animation will handle placing the
|
||||||
// new bubble in the stacked position.
|
// new bubble in the stacked position.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (mPositioner.showBubblesVertically()) {
|
if (mPositioner.showBubblesVertically()) {
|
||||||
Rect availableRect = mPositioner.getAvailableRect();
|
|
||||||
float fromX = onLeft
|
float fromX = onLeft
|
||||||
? -mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR
|
? p.x - mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR
|
||||||
: availableRect.right + mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR;
|
: p.x + mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR;
|
||||||
animationForChild(child)
|
animationForChild(child)
|
||||||
.translationX(fromX, p.y)
|
.translationX(fromX, p.y)
|
||||||
.start();
|
.start();
|
||||||
} else {
|
} else {
|
||||||
// Only animate if we're not collapsing as that animation will handle placing
|
float fromY = p.y - mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR;
|
||||||
// the new bubble in the stacked position.
|
|
||||||
float fromY = mPositioner.getExpandedBubblesY() - mBubbleSizePx
|
|
||||||
* ANIMATE_TRANSLATION_FACTOR;
|
|
||||||
animationForChild(child)
|
animationForChild(child)
|
||||||
.translationY(fromY, p.y)
|
.translationY(fromY, p.y)
|
||||||
.start();
|
.start();
|
||||||
@@ -527,7 +514,6 @@ public class ExpandedAnimationController
|
|||||||
updateBubblePositions();
|
updateBubblePositions();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
void onChildRemoved(View child, int index, Runnable finishRemoval) {
|
void onChildRemoved(View child, int index, Runnable finishRemoval) {
|
||||||
@@ -572,7 +558,6 @@ public class ExpandedAnimationController
|
|||||||
if (mAnimatingExpand || mAnimatingCollapse) {
|
if (mAnimatingExpand || mAnimatingCollapse) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
boolean onLeft = mPositioner.isStackOnLeft(mCollapsePoint);
|
|
||||||
for (int i = 0; i < mLayout.getChildCount(); i++) {
|
for (int i = 0; i < mLayout.getChildCount(); i++) {
|
||||||
final View bubble = mLayout.getChildAt(i);
|
final View bubble = mLayout.getChildAt(i);
|
||||||
|
|
||||||
@@ -582,7 +567,7 @@ public class ExpandedAnimationController
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
final PointF p = mPositioner.getExpandedBubbleXY(i, mLayout.getChildCount(), onLeft);
|
final PointF p = mPositioner.getExpandedBubbleXY(i, mBubbleStackView.getState());
|
||||||
animationForChild(bubble)
|
animationForChild(bubble)
|
||||||
.translationX(p.x)
|
.translationX(p.x)
|
||||||
.translationY(p.y)
|
.translationY(p.y)
|
||||||
|
|||||||
@@ -127,9 +127,6 @@ public class StackAnimationController extends
|
|||||||
/** Whether or not the stack's start position has been set. */
|
/** Whether or not the stack's start position has been set. */
|
||||||
private boolean mStackMovedToStartPosition = false;
|
private boolean mStackMovedToStartPosition = false;
|
||||||
|
|
||||||
/** The height of the most recently visible IME. */
|
|
||||||
private float mImeHeight = 0f;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The Y position of the stack before the IME became visible, or {@link Float#MIN_VALUE} if the
|
* The Y position of the stack before the IME became visible, or {@link Float#MIN_VALUE} if the
|
||||||
* IME is not visible or the user moved the stack since the IME became visible.
|
* IME is not visible or the user moved the stack since the IME became visible.
|
||||||
@@ -173,7 +170,7 @@ public class StackAnimationController extends
|
|||||||
*/
|
*/
|
||||||
private boolean mSpringToTouchOnNextMotionEvent = false;
|
private boolean mSpringToTouchOnNextMotionEvent = false;
|
||||||
|
|
||||||
/** Horizontal offset of bubbles in the stack. */
|
/** Offset of bubbles in the stack (i.e. how much they overlap). */
|
||||||
private float mStackOffset;
|
private float mStackOffset;
|
||||||
/** Offset between stack y and animation y for bubble swap. */
|
/** Offset between stack y and animation y for bubble swap. */
|
||||||
private float mSwapAnimationOffset;
|
private float mSwapAnimationOffset;
|
||||||
@@ -521,16 +518,6 @@ public class StackAnimationController extends
|
|||||||
removeEndActionForProperty(DynamicAnimation.TRANSLATION_Y);
|
removeEndActionForProperty(DynamicAnimation.TRANSLATION_Y);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Save the current IME height so that we know where the stack bounds should be. */
|
|
||||||
public void setImeHeight(int imeHeight) {
|
|
||||||
mImeHeight = imeHeight;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Returns the current IME height that the stack is offset by. */
|
|
||||||
public float getImeHeight() {
|
|
||||||
return mImeHeight;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Animates the stack either away from the newly visible IME, or back to its original position
|
* Animates the stack either away from the newly visible IME, or back to its original position
|
||||||
* due to the IME going away.
|
* due to the IME going away.
|
||||||
@@ -589,11 +576,14 @@ public class StackAnimationController extends
|
|||||||
*/
|
*/
|
||||||
public RectF getAllowableStackPositionRegion() {
|
public RectF getAllowableStackPositionRegion() {
|
||||||
final RectF allowableRegion = new RectF(mPositioner.getAvailableRect());
|
final RectF allowableRegion = new RectF(mPositioner.getAvailableRect());
|
||||||
|
final int imeHeight = mPositioner.getImeHeight();
|
||||||
|
final float bottomPadding = getBubbleCount() > 1
|
||||||
|
? mBubblePaddingTop + mStackOffset
|
||||||
|
: mBubblePaddingTop;
|
||||||
allowableRegion.left -= mBubbleOffscreen;
|
allowableRegion.left -= mBubbleOffscreen;
|
||||||
allowableRegion.top += mBubblePaddingTop;
|
allowableRegion.top += mBubblePaddingTop;
|
||||||
allowableRegion.right += mBubbleOffscreen - mBubbleSize;
|
allowableRegion.right += mBubbleOffscreen - mBubbleSize;
|
||||||
allowableRegion.bottom -= mBubblePaddingTop + mBubbleSize
|
allowableRegion.bottom -= imeHeight + bottomPadding + mBubbleSize;
|
||||||
+ (mImeHeight != UNSET ? mImeHeight + mBubblePaddingTop : 0f);
|
|
||||||
return allowableRegion;
|
return allowableRegion;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -16,10 +16,12 @@
|
|||||||
|
|
||||||
package com.android.wm.shell.bubbles.animation;
|
package com.android.wm.shell.bubbles.animation;
|
||||||
|
|
||||||
|
import static com.android.dx.mockito.inline.extended.ExtendedMockito.spyOn;
|
||||||
|
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.mockito.Mockito.mock;
|
import static org.mockito.Mockito.mock;
|
||||||
import static org.mockito.Mockito.verify;
|
import static org.mockito.Mockito.verify;
|
||||||
import static com.android.dx.mockito.inline.extended.ExtendedMockito.spyOn;
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
import android.annotation.SuppressLint;
|
import android.annotation.SuppressLint;
|
||||||
import android.content.res.Configuration;
|
import android.content.res.Configuration;
|
||||||
@@ -37,6 +39,7 @@ import androidx.test.filters.SmallTest;
|
|||||||
|
|
||||||
import com.android.wm.shell.R;
|
import com.android.wm.shell.R;
|
||||||
import com.android.wm.shell.bubbles.BubblePositioner;
|
import com.android.wm.shell.bubbles.BubblePositioner;
|
||||||
|
import com.android.wm.shell.bubbles.BubbleStackView;
|
||||||
|
|
||||||
import org.junit.Before;
|
import org.junit.Before;
|
||||||
import org.junit.Ignore;
|
import org.junit.Ignore;
|
||||||
@@ -56,18 +59,22 @@ public class ExpandedAnimationControllerTest extends PhysicsAnimationLayoutTestC
|
|||||||
private int mStackOffset;
|
private int mStackOffset;
|
||||||
private PointF mExpansionPoint;
|
private PointF mExpansionPoint;
|
||||||
private BubblePositioner mPositioner;
|
private BubblePositioner mPositioner;
|
||||||
|
private BubbleStackView.StackViewState mStackViewState;
|
||||||
|
|
||||||
@SuppressLint("VisibleForTests")
|
@SuppressLint("VisibleForTests")
|
||||||
@Before
|
@Before
|
||||||
public void setUp() throws Exception {
|
public void setUp() throws Exception {
|
||||||
super.setUp();
|
super.setUp();
|
||||||
|
|
||||||
|
BubbleStackView stackView = mock(BubbleStackView.class);
|
||||||
|
when(stackView.getState()).thenReturn(getStackViewState());
|
||||||
mPositioner = new BubblePositioner(getContext(), mock(WindowManager.class));
|
mPositioner = new BubblePositioner(getContext(), mock(WindowManager.class));
|
||||||
mPositioner.updateInternal(Configuration.ORIENTATION_PORTRAIT,
|
mPositioner.updateInternal(Configuration.ORIENTATION_PORTRAIT,
|
||||||
Insets.of(0, 0, 0, 0),
|
Insets.of(0, 0, 0, 0),
|
||||||
new Rect(0, 0, mDisplayWidth, mDisplayHeight));
|
new Rect(0, 0, mDisplayWidth, mDisplayHeight));
|
||||||
mExpandedController = new ExpandedAnimationController(mPositioner,
|
mExpandedController = new ExpandedAnimationController(mPositioner,
|
||||||
mOnBubbleAnimatedOutAction);
|
mOnBubbleAnimatedOutAction,
|
||||||
|
stackView);
|
||||||
spyOn(mExpandedController);
|
spyOn(mExpandedController);
|
||||||
|
|
||||||
addOneMoreThanBubbleLimitBubbles();
|
addOneMoreThanBubbleLimitBubbles();
|
||||||
@@ -78,6 +85,13 @@ public class ExpandedAnimationControllerTest extends PhysicsAnimationLayoutTestC
|
|||||||
mExpansionPoint = new PointF(100, 100);
|
mExpansionPoint = new PointF(100, 100);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public BubbleStackView.StackViewState getStackViewState() {
|
||||||
|
mStackViewState.numberOfBubbles = mLayout.getChildCount();
|
||||||
|
mStackViewState.selectedIndex = 0;
|
||||||
|
mStackViewState.onLeft = mPositioner.isStackOnLeft(mExpansionPoint);
|
||||||
|
return mStackViewState;
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@Ignore
|
@Ignore
|
||||||
public void testExpansionAndCollapse() throws InterruptedException {
|
public void testExpansionAndCollapse() throws InterruptedException {
|
||||||
@@ -141,12 +155,10 @@ public class ExpandedAnimationControllerTest extends PhysicsAnimationLayoutTestC
|
|||||||
|
|
||||||
/** Check that children are in the correct positions for being expanded. */
|
/** Check that children are in the correct positions for being expanded. */
|
||||||
private void testBubblesInCorrectExpandedPositions() {
|
private void testBubblesInCorrectExpandedPositions() {
|
||||||
boolean onLeft = mPositioner.isStackOnLeft(mExpansionPoint);
|
|
||||||
// Check all the visible bubbles to see if they're in the right place.
|
// Check all the visible bubbles to see if they're in the right place.
|
||||||
for (int i = 0; i < mLayout.getChildCount(); i++) {
|
for (int i = 0; i < mLayout.getChildCount(); i++) {
|
||||||
PointF expectedPosition = mPositioner.getExpandedBubbleXY(i,
|
PointF expectedPosition = mPositioner.getExpandedBubbleXY(i,
|
||||||
mLayout.getChildCount(),
|
getStackViewState());
|
||||||
onLeft);
|
|
||||||
assertEquals(expectedPosition.x,
|
assertEquals(expectedPosition.x,
|
||||||
mLayout.getChildAt(i).getTranslationX(),
|
mLayout.getChildAt(i).getTranslationX(),
|
||||||
2f);
|
2f);
|
||||||
|
|||||||
Reference in New Issue
Block a user