Loading packages/SystemUI/compose/features/src/com/android/systemui/notifications/ui/composable/Notifications.kt +5 −11 Original line number Diff line number Diff line Loading @@ -68,7 +68,6 @@ import androidx.compose.ui.layout.onGloballyPositioned import androidx.compose.ui.layout.onPlaced import androidx.compose.ui.layout.onSizeChanged import androidx.compose.ui.layout.positionInWindow import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.res.dimensionResource import androidx.compose.ui.unit.Dp Loading @@ -82,7 +81,6 @@ import com.android.compose.animation.scene.LowestZIndexContentPicker import com.android.compose.animation.scene.NestedScrollBehavior import com.android.compose.animation.scene.SceneScope import com.android.compose.modifiers.thenIf import com.android.internal.policy.SystemBarUtils import com.android.systemui.common.ui.compose.windowinsets.LocalRawScreenHeight import com.android.systemui.common.ui.compose.windowinsets.LocalScreenCornerRadius import com.android.systemui.res.R Loading Loading @@ -137,14 +135,16 @@ fun SceneScope.HeadsUpNotificationSpace( .notificationHeadsUpHeight(stackScrollView) .debugBackground(viewModel, DEBUG_HUN_COLOR) .onGloballyPositioned { coordinates: LayoutCoordinates -> val positionInWindow = coordinates.positionInWindow() val boundsInWindow = coordinates.boundsInWindow() debugLog(viewModel) { "HUNS onGloballyPositioned:" + " size=${coordinates.size}" + " bounds=$boundsInWindow" } // Note: boundsInWindow doesn't scroll off the screen stackScrollView.setHeadsUpTop(boundsInWindow.top) // Note: boundsInWindow doesn't scroll off the screen, so use positionInWindow // for top bound, which can scroll off screen while snoozing stackScrollView.setHeadsUpTop(positionInWindow.y) stackScrollView.setHeadsUpBottom(boundsInWindow.bottom) } ) Loading @@ -159,16 +159,10 @@ fun SceneScope.SnoozeableHeadsUpNotificationSpace( stackScrollView: NotificationScrollView, viewModel: NotificationsPlaceholderViewModel, ) { val context = LocalContext.current val density = LocalDensity.current val statusBarHeight = SystemBarUtils.getStatusBarHeight(context) val headsUpPadding = with(density) { dimensionResource(id = R.dimen.heads_up_status_bar_padding).roundToPx() } val isHeadsUp by viewModel.isHeadsUpOrAnimatingAway.collectAsStateWithLifecycle(false) var scrollOffset by remember { mutableFloatStateOf(0f) } val minScrollOffset = -(statusBarHeight + headsUpPadding.toFloat()) val minScrollOffset = -(stackScrollView.getHeadsUpInset().toFloat()) val maxScrollOffset = 0f val scrollableState = rememberScrollableState { delta -> Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/AmbientState.java +20 −0 Original line number Diff line number Diff line Loading @@ -139,6 +139,9 @@ public class AmbientState implements Dumpable { /** Fraction of shade expansion. */ private float mExpansionFraction; /** Fraction of QS expansion. 0 when in shade, 1 when in QS. */ private float mQsExpansionFraction; /** Height of the notifications panel when expansion completes. */ private float mStackEndHeight; Loading Loading @@ -207,6 +210,14 @@ public class AmbientState implements Dumpable { mExpansionFraction = expansionFraction; } /** * @param expansionFraction Fraction of QS expansion. */ public void setQsExpansionFraction(float expansionFraction) { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return; mQsExpansionFraction = expansionFraction; } /** * @param isSwipingUp Whether we are swiping up. */ Loading Loading @@ -257,6 +268,14 @@ public class AmbientState implements Dumpable { return mExpansionFraction; } /** * @return Fraction of QS expansion. */ public float getQsExpansionFraction() { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return 0f; return mQsExpansionFraction; } /** * @see #getStackHeight() */ Loading Loading @@ -837,6 +856,7 @@ public class AmbientState implements Dumpable { pw.println("mAppearFraction=" + mAppearFraction); pw.println("mAppearing=" + mAppearing); pw.println("mExpansionFraction=" + mExpansionFraction); pw.println("mQsExpansionFraction=" + mQsExpansionFraction); pw.println("mExpandingVelocity=" + mExpandingVelocity); pw.println("mOverScrollTopAmount=" + mOverScrollTopAmount); pw.println("mOverScrollBottomAmount=" + mOverScrollBottomAmount); Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationStackScrollLayout.java +12 −0 Original line number Diff line number Diff line Loading @@ -1244,6 +1244,7 @@ public class NotificationStackScrollLayout @Override public void setHeadsUpTop(float headsUpTop) { mAmbientState.setHeadsUpTop(headsUpTop); requestChildrenUpdate(); } @Override Loading Loading @@ -1563,6 +1564,12 @@ public class NotificationStackScrollLayout } } @Override public void setQsExpandFraction(float expandFraction) { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return; mAmbientState.setQsExpansionFraction(expandFraction); } /** * Update the height of the panel. * Loading Loading @@ -2534,6 +2541,11 @@ public class NotificationStackScrollLayout return getTopHeadsUpIntrinsicHeight(); } @Override public int getHeadsUpInset() { return mHeadsUpInset; } /** * Calculate the gap height between two different views * Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationStackScrollLayoutController.java +28 −1 Original line number Diff line number Diff line Loading @@ -132,6 +132,7 @@ import com.android.systemui.statusbar.notification.stack.ui.viewbinder.Notificat import com.android.systemui.statusbar.phone.HeadsUpAppearanceController; import com.android.systemui.statusbar.phone.HeadsUpNotificationViewControllerEmptyImpl; import com.android.systemui.statusbar.phone.HeadsUpTouchHelper; import com.android.systemui.statusbar.phone.HeadsUpTouchHelper.HeadsUpNotificationViewController; import com.android.systemui.statusbar.phone.KeyguardBypassController; import com.android.systemui.statusbar.policy.ConfigurationController; import com.android.systemui.statusbar.policy.ConfigurationController.ConfigurationListener; Loading Loading @@ -773,7 +774,7 @@ public class NotificationStackScrollLayoutController implements Dumpable { mHeadsUpManager, statusBarService.get(), getHeadsUpCallback(), new HeadsUpNotificationViewControllerEmptyImpl() getHeadsUpNotificationViewController() ); } mNotificationRoundnessManager = notificationRoundnessManager; Loading Loading @@ -1851,6 +1852,32 @@ public class NotificationStackScrollLayoutController implements Dumpable { return mTouchHandler; } private HeadsUpNotificationViewController getHeadsUpNotificationViewController() { HeadsUpNotificationViewController headsUpViewController; if (SceneContainerFlag.isEnabled()) { headsUpViewController = new HeadsUpNotificationViewController() { @Override public void setHeadsUpDraggingStartingHeight(int startHeight) { // do nothing } @Override public void setTrackedHeadsUp(ExpandableNotificationRow expandableNotificationRow) { setTrackingHeadsUp(expandableNotificationRow); } @Override public void startExpand(float newX, float newY, boolean startTracking, float expandedHeight) { // do nothing } }; } else { headsUpViewController = new HeadsUpNotificationViewControllerEmptyImpl(); } return headsUpViewController; } @Override public void dump(@NonNull PrintWriter pw, @NonNull String[] args) { pw.println("mMaxAlphaFromView=" + mMaxAlphaFromView); Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/StackScrollAlgorithm.java +25 −9 Original line number Diff line number Diff line Loading @@ -16,8 +16,6 @@ package com.android.systemui.statusbar.notification.stack; import static androidx.core.math.MathUtils.clamp; import android.annotation.NonNull; import android.annotation.Nullable; import android.content.Context; Loading Loading @@ -890,7 +888,14 @@ public class StackScrollAlgorithm { continue; } ExpandableViewState childState = row.getViewState(); if (topHeadsUpEntry == null && row.mustStayOnScreen() && !childState.headsUpIsVisible) { boolean shouldSetTopHeadsUpEntry; if (SceneContainerFlag.isEnabled()) { shouldSetTopHeadsUpEntry = row.isHeadsUp(); } else { shouldSetTopHeadsUpEntry = row.mustStayOnScreen(); } if (topHeadsUpEntry == null && shouldSetTopHeadsUpEntry && !childState.headsUpIsVisible) { topHeadsUpEntry = row; childState.location = ExpandableViewState.LOCATION_FIRST_HUN; } Loading @@ -898,7 +903,7 @@ public class StackScrollAlgorithm { float unmodifiedEndLocation = childState.getYTranslation() + childState.height; if (mIsExpanded) { if (SceneContainerFlag.isEnabled()) { if (shouldHunBeVisibleWhenScrolled(row.mustStayOnScreen(), if (shouldHunBeVisibleWhenScrolled(row.isHeadsUp(), childState.headsUpIsVisible, row.showingPulsing(), ambientState.isOnKeyguard(), row.getEntry().isStickyAndNotDemoted())) { // the height of this child before clamping it to the top Loading @@ -909,10 +914,19 @@ public class StackScrollAlgorithm { /* viewState = */ childState ); float baseZ = ambientState.getBaseZHeight(); if (headsUpTranslation < ambientState.getStackTop()) { // HUN displayed above the stack top, it needs a fix shadow childState.setZTranslation(baseZ + mPinnedZTranslationExtra); } else { if (headsUpTranslation > ambientState.getStackTop() && row.isAboveShelf()) { // HUN displayed outside of the stack during transition from Gone/LS; // add a shadow that corresponds to the transition progress. float fraction = 1 - ambientState.getExpansionFraction(); childState.setZTranslation(baseZ + fraction * mPinnedZTranslationExtra); } else if (headsUpTranslation < ambientState.getStackTop() && row.isAboveShelf()) { // HUN displayed outside of the stack during transition from QS; // add a shadow that corresponds to the transition progress. float fraction = ambientState.getQsExpansionFraction(); childState.setZTranslation(baseZ + fraction * mPinnedZTranslationExtra); } else if (headsUpTranslation > ambientState.getStackTop()) { // HUN displayed within the stack, add a shadow if it overlaps with // other elements. // Loading @@ -927,6 +941,8 @@ public class StackScrollAlgorithm { /* baseZ = */ baseZ, /* viewState = */ childState ); } else { childState.setZTranslation(baseZ); } if (isTopEntry && row.isAboveShelf()) { clampHunToMaxTranslation( Loading Loading @@ -1081,7 +1097,7 @@ public class StackScrollAlgorithm { if (scrollingContentTopPadding > 0f) { // scrollingContentTopPadding makes a gap between the bottom of the HUN and the top // of the scrolling content. Use this to animate to the full shadow. shadowFraction = clamp(overlap / scrollingContentTopPadding, 0f, 1f); shadowFraction = Math.clamp(overlap / scrollingContentTopPadding, 0f, 1f); } if (overlap > 0.0f) { Loading Loading
packages/SystemUI/compose/features/src/com/android/systemui/notifications/ui/composable/Notifications.kt +5 −11 Original line number Diff line number Diff line Loading @@ -68,7 +68,6 @@ import androidx.compose.ui.layout.onGloballyPositioned import androidx.compose.ui.layout.onPlaced import androidx.compose.ui.layout.onSizeChanged import androidx.compose.ui.layout.positionInWindow import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.res.dimensionResource import androidx.compose.ui.unit.Dp Loading @@ -82,7 +81,6 @@ import com.android.compose.animation.scene.LowestZIndexContentPicker import com.android.compose.animation.scene.NestedScrollBehavior import com.android.compose.animation.scene.SceneScope import com.android.compose.modifiers.thenIf import com.android.internal.policy.SystemBarUtils import com.android.systemui.common.ui.compose.windowinsets.LocalRawScreenHeight import com.android.systemui.common.ui.compose.windowinsets.LocalScreenCornerRadius import com.android.systemui.res.R Loading Loading @@ -137,14 +135,16 @@ fun SceneScope.HeadsUpNotificationSpace( .notificationHeadsUpHeight(stackScrollView) .debugBackground(viewModel, DEBUG_HUN_COLOR) .onGloballyPositioned { coordinates: LayoutCoordinates -> val positionInWindow = coordinates.positionInWindow() val boundsInWindow = coordinates.boundsInWindow() debugLog(viewModel) { "HUNS onGloballyPositioned:" + " size=${coordinates.size}" + " bounds=$boundsInWindow" } // Note: boundsInWindow doesn't scroll off the screen stackScrollView.setHeadsUpTop(boundsInWindow.top) // Note: boundsInWindow doesn't scroll off the screen, so use positionInWindow // for top bound, which can scroll off screen while snoozing stackScrollView.setHeadsUpTop(positionInWindow.y) stackScrollView.setHeadsUpBottom(boundsInWindow.bottom) } ) Loading @@ -159,16 +159,10 @@ fun SceneScope.SnoozeableHeadsUpNotificationSpace( stackScrollView: NotificationScrollView, viewModel: NotificationsPlaceholderViewModel, ) { val context = LocalContext.current val density = LocalDensity.current val statusBarHeight = SystemBarUtils.getStatusBarHeight(context) val headsUpPadding = with(density) { dimensionResource(id = R.dimen.heads_up_status_bar_padding).roundToPx() } val isHeadsUp by viewModel.isHeadsUpOrAnimatingAway.collectAsStateWithLifecycle(false) var scrollOffset by remember { mutableFloatStateOf(0f) } val minScrollOffset = -(statusBarHeight + headsUpPadding.toFloat()) val minScrollOffset = -(stackScrollView.getHeadsUpInset().toFloat()) val maxScrollOffset = 0f val scrollableState = rememberScrollableState { delta -> Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/AmbientState.java +20 −0 Original line number Diff line number Diff line Loading @@ -139,6 +139,9 @@ public class AmbientState implements Dumpable { /** Fraction of shade expansion. */ private float mExpansionFraction; /** Fraction of QS expansion. 0 when in shade, 1 when in QS. */ private float mQsExpansionFraction; /** Height of the notifications panel when expansion completes. */ private float mStackEndHeight; Loading Loading @@ -207,6 +210,14 @@ public class AmbientState implements Dumpable { mExpansionFraction = expansionFraction; } /** * @param expansionFraction Fraction of QS expansion. */ public void setQsExpansionFraction(float expansionFraction) { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return; mQsExpansionFraction = expansionFraction; } /** * @param isSwipingUp Whether we are swiping up. */ Loading Loading @@ -257,6 +268,14 @@ public class AmbientState implements Dumpable { return mExpansionFraction; } /** * @return Fraction of QS expansion. */ public float getQsExpansionFraction() { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return 0f; return mQsExpansionFraction; } /** * @see #getStackHeight() */ Loading Loading @@ -837,6 +856,7 @@ public class AmbientState implements Dumpable { pw.println("mAppearFraction=" + mAppearFraction); pw.println("mAppearing=" + mAppearing); pw.println("mExpansionFraction=" + mExpansionFraction); pw.println("mQsExpansionFraction=" + mQsExpansionFraction); pw.println("mExpandingVelocity=" + mExpandingVelocity); pw.println("mOverScrollTopAmount=" + mOverScrollTopAmount); pw.println("mOverScrollBottomAmount=" + mOverScrollBottomAmount); Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationStackScrollLayout.java +12 −0 Original line number Diff line number Diff line Loading @@ -1244,6 +1244,7 @@ public class NotificationStackScrollLayout @Override public void setHeadsUpTop(float headsUpTop) { mAmbientState.setHeadsUpTop(headsUpTop); requestChildrenUpdate(); } @Override Loading Loading @@ -1563,6 +1564,12 @@ public class NotificationStackScrollLayout } } @Override public void setQsExpandFraction(float expandFraction) { if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) return; mAmbientState.setQsExpansionFraction(expandFraction); } /** * Update the height of the panel. * Loading Loading @@ -2534,6 +2541,11 @@ public class NotificationStackScrollLayout return getTopHeadsUpIntrinsicHeight(); } @Override public int getHeadsUpInset() { return mHeadsUpInset; } /** * Calculate the gap height between two different views * Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationStackScrollLayoutController.java +28 −1 Original line number Diff line number Diff line Loading @@ -132,6 +132,7 @@ import com.android.systemui.statusbar.notification.stack.ui.viewbinder.Notificat import com.android.systemui.statusbar.phone.HeadsUpAppearanceController; import com.android.systemui.statusbar.phone.HeadsUpNotificationViewControllerEmptyImpl; import com.android.systemui.statusbar.phone.HeadsUpTouchHelper; import com.android.systemui.statusbar.phone.HeadsUpTouchHelper.HeadsUpNotificationViewController; import com.android.systemui.statusbar.phone.KeyguardBypassController; import com.android.systemui.statusbar.policy.ConfigurationController; import com.android.systemui.statusbar.policy.ConfigurationController.ConfigurationListener; Loading Loading @@ -773,7 +774,7 @@ public class NotificationStackScrollLayoutController implements Dumpable { mHeadsUpManager, statusBarService.get(), getHeadsUpCallback(), new HeadsUpNotificationViewControllerEmptyImpl() getHeadsUpNotificationViewController() ); } mNotificationRoundnessManager = notificationRoundnessManager; Loading Loading @@ -1851,6 +1852,32 @@ public class NotificationStackScrollLayoutController implements Dumpable { return mTouchHandler; } private HeadsUpNotificationViewController getHeadsUpNotificationViewController() { HeadsUpNotificationViewController headsUpViewController; if (SceneContainerFlag.isEnabled()) { headsUpViewController = new HeadsUpNotificationViewController() { @Override public void setHeadsUpDraggingStartingHeight(int startHeight) { // do nothing } @Override public void setTrackedHeadsUp(ExpandableNotificationRow expandableNotificationRow) { setTrackingHeadsUp(expandableNotificationRow); } @Override public void startExpand(float newX, float newY, boolean startTracking, float expandedHeight) { // do nothing } }; } else { headsUpViewController = new HeadsUpNotificationViewControllerEmptyImpl(); } return headsUpViewController; } @Override public void dump(@NonNull PrintWriter pw, @NonNull String[] args) { pw.println("mMaxAlphaFromView=" + mMaxAlphaFromView); Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/StackScrollAlgorithm.java +25 −9 Original line number Diff line number Diff line Loading @@ -16,8 +16,6 @@ package com.android.systemui.statusbar.notification.stack; import static androidx.core.math.MathUtils.clamp; import android.annotation.NonNull; import android.annotation.Nullable; import android.content.Context; Loading Loading @@ -890,7 +888,14 @@ public class StackScrollAlgorithm { continue; } ExpandableViewState childState = row.getViewState(); if (topHeadsUpEntry == null && row.mustStayOnScreen() && !childState.headsUpIsVisible) { boolean shouldSetTopHeadsUpEntry; if (SceneContainerFlag.isEnabled()) { shouldSetTopHeadsUpEntry = row.isHeadsUp(); } else { shouldSetTopHeadsUpEntry = row.mustStayOnScreen(); } if (topHeadsUpEntry == null && shouldSetTopHeadsUpEntry && !childState.headsUpIsVisible) { topHeadsUpEntry = row; childState.location = ExpandableViewState.LOCATION_FIRST_HUN; } Loading @@ -898,7 +903,7 @@ public class StackScrollAlgorithm { float unmodifiedEndLocation = childState.getYTranslation() + childState.height; if (mIsExpanded) { if (SceneContainerFlag.isEnabled()) { if (shouldHunBeVisibleWhenScrolled(row.mustStayOnScreen(), if (shouldHunBeVisibleWhenScrolled(row.isHeadsUp(), childState.headsUpIsVisible, row.showingPulsing(), ambientState.isOnKeyguard(), row.getEntry().isStickyAndNotDemoted())) { // the height of this child before clamping it to the top Loading @@ -909,10 +914,19 @@ public class StackScrollAlgorithm { /* viewState = */ childState ); float baseZ = ambientState.getBaseZHeight(); if (headsUpTranslation < ambientState.getStackTop()) { // HUN displayed above the stack top, it needs a fix shadow childState.setZTranslation(baseZ + mPinnedZTranslationExtra); } else { if (headsUpTranslation > ambientState.getStackTop() && row.isAboveShelf()) { // HUN displayed outside of the stack during transition from Gone/LS; // add a shadow that corresponds to the transition progress. float fraction = 1 - ambientState.getExpansionFraction(); childState.setZTranslation(baseZ + fraction * mPinnedZTranslationExtra); } else if (headsUpTranslation < ambientState.getStackTop() && row.isAboveShelf()) { // HUN displayed outside of the stack during transition from QS; // add a shadow that corresponds to the transition progress. float fraction = ambientState.getQsExpansionFraction(); childState.setZTranslation(baseZ + fraction * mPinnedZTranslationExtra); } else if (headsUpTranslation > ambientState.getStackTop()) { // HUN displayed within the stack, add a shadow if it overlaps with // other elements. // Loading @@ -927,6 +941,8 @@ public class StackScrollAlgorithm { /* baseZ = */ baseZ, /* viewState = */ childState ); } else { childState.setZTranslation(baseZ); } if (isTopEntry && row.isAboveShelf()) { clampHunToMaxTranslation( Loading Loading @@ -1081,7 +1097,7 @@ public class StackScrollAlgorithm { if (scrollingContentTopPadding > 0f) { // scrollingContentTopPadding makes a gap between the bottom of the HUN and the top // of the scrolling content. Use this to animate to the full shadow. shadowFraction = clamp(overlap / scrollingContentTopPadding, 0f, 1f); shadowFraction = Math.clamp(overlap / scrollingContentTopPadding, 0f, 1f); } if (overlap > 0.0f) { Loading