Fix notification launch animation for split shade

The launchAnimationParams contain global coordinates. These need to be translated to local coordinates, since the NotificationStackScrollLayout does not have its origin at (0,0) in the split shade case.

Test: Manual, i.e. posting various types of notifications and analyzing the animations in screenrecordings.
Bug: 246932690
Change-Id: I9dd233d282d05fc25b3601180c775916ddb5197c
This commit is contained in:
Johannes Gallmann
2022-12-05 16:43:39 +01:00
parent ccafe39e56
commit d9aac37c80
4 changed files with 32 additions and 17 deletions

View File

@@ -27,8 +27,10 @@ class LaunchAnimationParameters(
/**
* The top position of the notification at the start of the animation. This is needed in order
* to keep the notification at its place when launching a notification that is clipped rounded.
* This value is in absolute screen coordinates.
*/
var startNotificationTop = 0f
var startNotificationTop = 0
var notificationParentTop = 0
var startClipTopAmount = 0
var parentStartClipTopAmount = 0
var progress = 0f

View File

@@ -92,11 +92,12 @@ class NotificationLaunchAnimatorController(
)
params.startTranslationZ = notification.translationZ
params.startNotificationTop = notification.translationY
params.startNotificationTop = location[1]
params.notificationParentTop = notificationListContainer
.getViewParentForNotification(notificationEntry).locationOnScreen[1]
params.startRoundedTopClipping = roundedTopClipping
params.startClipTopAmount = notification.clipTopAmount
if (notification.isChildInGroup) {
params.startNotificationTop += notification.notificationParent.translationY
val locationOnScreen = notification.notificationParent.locationOnScreen[1]
val parentRoundedClip = (clipStartLocation - locationOnScreen).coerceAtLeast(0)
params.parentStartRoundedTopClipping = parentRoundedClip

View File

@@ -2223,6 +2223,7 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
if (mNotificationParent != null) {
mNotificationParent.setClipTopAmount(0);
}
setTranslationX(0);
return;
}
@@ -2241,6 +2242,7 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
setTranslationZ(translationZ);
float extraWidthForClipping = params.getWidth() - getWidth();
setExtraWidthForClipping(extraWidthForClipping);
int top;
if (params.getStartRoundedTopClipping() > 0) {
// If we were clipping initially, let's interpolate from the start position to the
@@ -2248,20 +2250,22 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
float expandProgress = Interpolators.FAST_OUT_SLOW_IN.getInterpolation(
params.getProgress(0,
NotificationLaunchAnimatorController.ANIMATION_DURATION_TOP_ROUNDING));
float startTop = params.getStartNotificationTop();
top = (int) Math.min(MathUtils.lerp(startTop,
params.getTop(), expandProgress),
int startTop = params.getStartNotificationTop();
top = (int) Math.min(MathUtils.lerp(startTop, params.getTop(), expandProgress),
startTop);
} else {
top = params.getTop();
}
int actualHeight = params.getBottom() - top;
setActualHeight(actualHeight);
int notificationStackTop = params.getNotificationParentTop();
top -= notificationStackTop;
int startClipTopAmount = params.getStartClipTopAmount();
int clipTopAmount = (int) MathUtils.lerp(startClipTopAmount, 0, params.getProgress());
if (mNotificationParent != null) {
float parentY = mNotificationParent.getTranslationY();
top -= parentY;
float parentTranslationY = mNotificationParent.getTranslationY();
top -= parentTranslationY;
mNotificationParent.setTranslationZ(translationZ);
// When the expanding notification is below its parent, the parent must be clipped
@@ -2270,15 +2274,14 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
// pixels to show the expanding notification, while still taking the decreasing
// notification clipTopAmount into consideration, so 'top + clipTopAmount'.
int parentStartClipTopAmount = params.getParentStartClipTopAmount();
int parentClipTopAmount = Math.min(parentStartClipTopAmount,
top + clipTopAmount);
int parentClipTopAmount = Math.min(parentStartClipTopAmount, top + clipTopAmount);
mNotificationParent.setClipTopAmount(parentClipTopAmount);
mNotificationParent.setExtraWidthForClipping(extraWidthForClipping);
float clipBottom = Math.max(params.getBottom(),
parentY + mNotificationParent.getActualHeight()
float clipBottom = Math.max(params.getBottom() - notificationStackTop,
parentTranslationY + mNotificationParent.getActualHeight()
- mNotificationParent.getClipBottomAmount());
float clipTop = Math.min(params.getTop(), parentY);
float clipTop = Math.min(params.getTop() - notificationStackTop, parentTranslationY);
int minimumHeightForClipping = (int) (clipBottom - clipTop);
mNotificationParent.setMinimumHeightForClipping(minimumHeightForClipping);
} else if (startClipTopAmount != 0) {
@@ -2286,6 +2289,9 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
}
setTranslationY(top);
float absoluteCenterX = getLocationOnScreen()[0] + getWidth() / 2f - getTranslationX();
setTranslationX(params.getCenterX() - absoluteCenterX);
final float maxRadius = getMaxRadius();
mTopRoundnessDuringLaunchAnimation = params.getTopCornerRadius() / maxRadius;
mBottomRoundnessDuringLaunchAnimation = params.getBottomCornerRadius() / maxRadius;

View File

@@ -5772,14 +5772,20 @@ public class NotificationStackScrollLayout extends ViewGroup implements Dumpable
|| mExpandingNotificationRow == null) {
return;
}
int left = Math.min(mLaunchAnimationParams.getLeft(), mRoundedRectClippingLeft);
int right = Math.max(mLaunchAnimationParams.getRight(), mRoundedRectClippingRight);
int bottom = Math.max(mLaunchAnimationParams.getBottom(), mRoundedRectClippingBottom);
int[] absoluteCoords = new int[2];
getLocationOnScreen(absoluteCoords);
int left = Math.min(mLaunchAnimationParams.getLeft() - absoluteCoords[0],
mRoundedRectClippingLeft);
int right = Math.max(mLaunchAnimationParams.getRight() - absoluteCoords[0],
mRoundedRectClippingRight);
int bottom = Math.max(mLaunchAnimationParams.getBottom() - absoluteCoords[1],
mRoundedRectClippingBottom);
float expandProgress = Interpolators.FAST_OUT_SLOW_IN.getInterpolation(
mLaunchAnimationParams.getProgress(0,
NotificationLaunchAnimatorController.ANIMATION_DURATION_TOP_ROUNDING));
int top = (int) Math.min(MathUtils.lerp(mRoundedRectClippingTop,
mLaunchAnimationParams.getTop(), expandProgress),
mLaunchAnimationParams.getTop() - absoluteCoords[1], expandProgress),
mRoundedRectClippingTop);
float topRadius = mLaunchAnimationParams.getTopCornerRadius();
float bottomRadius = mLaunchAnimationParams.getBottomCornerRadius();