Loading packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinatorTest.java→packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinatorTest.java +5 −2 Original line number Diff line number Diff line Loading @@ -31,9 +31,9 @@ import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import androidx.test.ext.junit.runners.AndroidJUnit4; import androidx.test.filters.SmallTest; import com.android.compose.animation.scene.ObservableTransitionState; Loading @@ -57,6 +57,7 @@ import com.android.systemui.statusbar.notification.collection.NotificationEntryB import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifStabilityManager; import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.Pluggable; import com.android.systemui.statusbar.notification.collection.provider.VisualStabilityProvider; import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor; import com.android.systemui.statusbar.policy.HeadsUpManager; import com.android.systemui.util.concurrency.FakeExecutor; import com.android.systemui.util.kotlin.JavaAdapter; Loading @@ -75,7 +76,7 @@ import org.mockito.MockitoAnnotations; import org.mockito.verification.VerificationMode; @SmallTest @RunWith(AndroidTestingRunner.class) @RunWith(AndroidJUnit4.class) @TestableLooper.RunWithLooper public class VisualStabilityCoordinatorTest extends SysuiTestCase { Loading @@ -86,6 +87,7 @@ public class VisualStabilityCoordinatorTest extends SysuiTestCase { @Mock private WakefulnessLifecycle mWakefulnessLifecycle; @Mock private StatusBarStateController mStatusBarStateController; @Mock private Pluggable.PluggableListener<NotifStabilityManager> mInvalidateListener; @Mock private SeenNotificationsInteractor mSeenNotificationsInteractor; @Mock private HeadsUpManager mHeadsUpManager; @Mock private VisibilityLocationProvider mVisibilityLocationProvider; @Mock private VisualStabilityProvider mVisualStabilityProvider; Loading Loading @@ -121,6 +123,7 @@ public class VisualStabilityCoordinatorTest extends SysuiTestCase { mHeadsUpManager, mShadeAnimationInteractor, mJavaAdapter, mSeenNotificationsInteractor, mStatusBarStateController, mVisibilityLocationProvider, mVisualStabilityProvider, Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/KeyguardCoordinator.kt +67 −2 Original line number Diff line number Diff line Loading @@ -31,15 +31,20 @@ import com.android.systemui.keyguard.shared.model.KeyguardState import com.android.systemui.plugins.statusbar.StatusBarStateController import com.android.systemui.statusbar.StatusBarState import com.android.systemui.statusbar.expansionChanges import com.android.systemui.statusbar.notification.collection.GroupEntry import com.android.systemui.statusbar.notification.collection.ListEntry import com.android.systemui.statusbar.notification.collection.NotifPipeline import com.android.systemui.statusbar.notification.collection.NotificationEntry import com.android.systemui.statusbar.notification.collection.coordinator.dagger.CoordinatorScope import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifFilter import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifPromoter import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifSectioner import com.android.systemui.statusbar.notification.collection.notifcollection.NotifCollectionListener import com.android.systemui.statusbar.notification.collection.provider.SectionHeaderVisibilityProvider import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor import com.android.systemui.statusbar.notification.interruption.KeyguardNotificationVisibilityProvider import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype import com.android.systemui.statusbar.notification.stack.BUCKET_FOREGROUND_SERVICE import com.android.systemui.statusbar.policy.HeadsUpManager import com.android.systemui.statusbar.policy.headsUpEvents import com.android.systemui.util.asIndenting Loading Loading @@ -106,6 +111,10 @@ constructor( } private fun attachUnseenFilter(pipeline: NotifPipeline) { if (NotificationMinimalismPrototype.V2.isEnabled) { pipeline.addPromoter(unseenNotifPromoter) pipeline.addOnBeforeTransformGroupsListener(::pickOutTopUnseenNotif) } pipeline.addFinalizeFilter(unseenNotifFilter) pipeline.addCollectionListener(collectionListener) scope.launch { trackUnseenFilterSettingChanges() } Loading Loading @@ -263,7 +272,10 @@ constructor( } private fun unseenFeatureEnabled(): Flow<Boolean> { if (NotificationMinimalismPrototype.V1.isEnabled) { if ( NotificationMinimalismPrototype.V1.isEnabled || NotificationMinimalismPrototype.V2.isEnabled ) { return flowOf(true) } return secureSettings Loading Loading @@ -334,6 +346,57 @@ constructor( } } private fun pickOutTopUnseenNotif(list: List<ListEntry>) { if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) return // Only ever elevate a top unseen notification on keyguard, not even locked shade if (statusBarStateController.state != StatusBarState.KEYGUARD) { seenNotificationsInteractor.setTopUnseenNotification(null) return } // On keyguard pick the top-ranked unseen or ongoing notification to elevate seenNotificationsInteractor.setTopUnseenNotification( list .asSequence() .flatMap { when (it) { is NotificationEntry -> listOfNotNull(it) is GroupEntry -> it.children else -> error("unhandled type of $it") } } .filter { shouldIgnoreUnseenCheck(it) || it in unseenNotifications } .minByOrNull { it.ranking.rank } ) } @VisibleForTesting internal val unseenNotifPromoter = object : NotifPromoter("$TAG-unseen") { override fun shouldPromoteToTopLevel(child: NotificationEntry): Boolean = if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) false else seenNotificationsInteractor.isTopUnseenNotification(child) && NotificationMinimalismPrototype.V2.ungroupTopUnseen } val unseenNotifSectioner = object : NotifSectioner("Unseen", BUCKET_FOREGROUND_SERVICE) { override fun isInSection(entry: ListEntry): Boolean { if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) return false if ( seenNotificationsInteractor.isTopUnseenNotification(entry.representativeEntry) ) { return true } if (entry !is GroupEntry) { return false } return entry.children.any { seenNotificationsInteractor.isTopUnseenNotification(it) } } } @VisibleForTesting internal val unseenNotifFilter = object : NotifFilter("$TAG-unseen") { Loading @@ -351,7 +414,9 @@ constructor( * allow seen notifications to appear in the locked shade. */ private fun isOnKeyguard(): Boolean = if ( if (NotificationMinimalismPrototype.V2.isEnabled) { false // disable this feature under this prototype } else if ( NotificationMinimalismPrototype.V1.isEnabled && NotificationMinimalismPrototype.V1.showOnLockedShade ) { Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/NotifCoordinators.kt +54 −43 Original line number Diff line number Diff line Loading @@ -24,17 +24,20 @@ import com.android.systemui.statusbar.notification.collection.SortBySectionTimeF import com.android.systemui.statusbar.notification.collection.coordinator.dagger.CoordinatorScope import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifSectioner import com.android.systemui.statusbar.notification.collection.provider.SectionStyleProvider import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype import com.android.systemui.statusbar.notification.shared.NotificationsLiveDataStoreRefactor import javax.inject.Inject /** * Handles the attachment of [Coordinator]s to the [NotifPipeline] so that the * Coordinators can register their respective callbacks. * Handles the attachment of [Coordinator]s to the [NotifPipeline] so that the Coordinators can * register their respective callbacks. */ interface NotifCoordinators : Coordinator, PipelineDumpable @CoordinatorScope class NotifCoordinatorsImpl @Inject constructor( class NotifCoordinatorsImpl @Inject constructor( sectionStyleProvider: SectionStyleProvider, featureFlags: FeatureFlags, dataStoreCoordinator: DataStoreCoordinator, Loading Loading @@ -114,6 +117,9 @@ class NotifCoordinatorsImpl @Inject constructor( // Manually add Ordered Sections mOrderedSections.add(headsUpCoordinator.sectioner) // HeadsUp mOrderedSections.add(colorizedFgsCoordinator.sectioner) // ForegroundService if (NotificationMinimalismPrototype.V2.isEnabled) { mOrderedSections.add(keyguardCoordinator.unseenNotifSectioner) // Unseen (FGS) } mOrderedSections.add(conversationCoordinator.peopleAlertingSectioner) // People Alerting if (!SortBySectionTimeFlag.isEnabled) { mOrderedSections.add(conversationCoordinator.peopleSilentSectioner) // People Silent Loading @@ -124,22 +130,26 @@ class NotifCoordinatorsImpl @Inject constructor( sectionStyleProvider.setMinimizedSections(setOf(rankingCoordinator.minimizedSectioner)) if (SortBySectionTimeFlag.isEnabled) { sectionStyleProvider.setSilentSections(listOf( sectionStyleProvider.setSilentSections( listOf( rankingCoordinator.silentSectioner, rankingCoordinator.minimizedSectioner, )) ) ) } else { sectionStyleProvider.setSilentSections(listOf( sectionStyleProvider.setSilentSections( listOf( conversationCoordinator.peopleSilentSectioner, rankingCoordinator.silentSectioner, rankingCoordinator.minimizedSectioner, )) ) ) } } /** * Sends the pipeline to each coordinator when the pipeline is ready to accept * [Pluggable]s, [NotifCollectionListener]s and [NotifLifetimeExtender]s. * Sends the pipeline to each coordinator when the pipeline is ready to accept [Pluggable]s, * [NotifCollectionListener]s and [NotifLifetimeExtender]s. */ override fun attach(pipeline: NotifPipeline) { for (c in mCoreCoordinators) { Loading @@ -155,7 +165,8 @@ class NotifCoordinatorsImpl @Inject constructor( * As part of the NotifPipeline dumpable, dumps the list of coordinators; sections are omitted * as they are dumped in the RenderStageManager instead. */ override fun dumpPipeline(d: PipelineDumper) = with(d) { override fun dumpPipeline(d: PipelineDumper) = with(d) { dump("core coordinators", mCoreCoordinators) dump("normal coordinators", mCoordinators) } Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinator.java +14 −2 Original line number Diff line number Diff line Loading @@ -38,6 +38,8 @@ import com.android.systemui.statusbar.notification.collection.NotifPipeline; import com.android.systemui.statusbar.notification.collection.NotificationEntry; import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifStabilityManager; import com.android.systemui.statusbar.notification.collection.provider.VisualStabilityProvider; import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor; import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype; import com.android.systemui.statusbar.policy.HeadsUpManager; import com.android.systemui.util.Compile; import com.android.systemui.util.concurrency.DelayableExecutor; Loading @@ -63,6 +65,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { public static final boolean DEBUG = Compile.IS_DEBUG && Log.isLoggable(TAG, Log.VERBOSE); private final DelayableExecutor mDelayableExecutor; private final HeadsUpManager mHeadsUpManager; private final SeenNotificationsInteractor mSeenNotificationsInteractor; private final ShadeAnimationInteractor mShadeAnimationInteractor; private final StatusBarStateController mStatusBarStateController; private final JavaAdapter mJavaAdapter; Loading Loading @@ -101,6 +104,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { HeadsUpManager headsUpManager, ShadeAnimationInteractor shadeAnimationInteractor, JavaAdapter javaAdapter, SeenNotificationsInteractor seenNotificationsInteractor, StatusBarStateController statusBarStateController, VisibilityLocationProvider visibilityLocationProvider, VisualStabilityProvider visualStabilityProvider, Loading @@ -109,6 +113,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { mHeadsUpManager = headsUpManager; mShadeAnimationInteractor = shadeAnimationInteractor; mJavaAdapter = javaAdapter; mSeenNotificationsInteractor = seenNotificationsInteractor; mVisibilityLocationProvider = visibilityLocationProvider; mVisualStabilityProvider = visualStabilityProvider; mWakefulnessLifecycle = wakefulnessLifecycle; Loading Loading @@ -142,8 +147,15 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { private final NotifStabilityManager mNotifStabilityManager = new NotifStabilityManager("VisualStabilityCoordinator") { private boolean canMoveForHeadsUp(NotificationEntry entry) { return entry != null && mHeadsUpManager.isHeadsUpEntry(entry.getKey()) && !mVisibilityLocationProvider.isInVisibleLocation(entry); if (entry == null) { return false; } boolean isTopUnseen = NotificationMinimalismPrototype.V2.isEnabled() && mSeenNotificationsInteractor.isTopUnseenNotification(entry); if (isTopUnseen || mHeadsUpManager.isHeadsUpEntry(entry.getKey())) { return !mVisibilityLocationProvider.isInVisibleLocation(entry); } return false; } @Override Loading packages/SystemUI/src/com/android/systemui/statusbar/notification/data/repository/ActiveNotificationListRepository.kt +3 −0 Original line number Diff line number Diff line Loading @@ -41,6 +41,9 @@ class ActiveNotificationListRepository @Inject constructor() { /** Stats about the list of notifications attached to the shade */ val notifStats = MutableStateFlow(NotifStats.empty) /** The key of the top unseen notification */ val topUnseenNotificationKey = MutableStateFlow<String?>(null) } /** Represents the notification list, comprised of groups and individual notifications. */ Loading Loading
packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinatorTest.java→packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinatorTest.java +5 −2 Original line number Diff line number Diff line Loading @@ -31,9 +31,9 @@ import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import androidx.test.ext.junit.runners.AndroidJUnit4; import androidx.test.filters.SmallTest; import com.android.compose.animation.scene.ObservableTransitionState; Loading @@ -57,6 +57,7 @@ import com.android.systemui.statusbar.notification.collection.NotificationEntryB import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifStabilityManager; import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.Pluggable; import com.android.systemui.statusbar.notification.collection.provider.VisualStabilityProvider; import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor; import com.android.systemui.statusbar.policy.HeadsUpManager; import com.android.systemui.util.concurrency.FakeExecutor; import com.android.systemui.util.kotlin.JavaAdapter; Loading @@ -75,7 +76,7 @@ import org.mockito.MockitoAnnotations; import org.mockito.verification.VerificationMode; @SmallTest @RunWith(AndroidTestingRunner.class) @RunWith(AndroidJUnit4.class) @TestableLooper.RunWithLooper public class VisualStabilityCoordinatorTest extends SysuiTestCase { Loading @@ -86,6 +87,7 @@ public class VisualStabilityCoordinatorTest extends SysuiTestCase { @Mock private WakefulnessLifecycle mWakefulnessLifecycle; @Mock private StatusBarStateController mStatusBarStateController; @Mock private Pluggable.PluggableListener<NotifStabilityManager> mInvalidateListener; @Mock private SeenNotificationsInteractor mSeenNotificationsInteractor; @Mock private HeadsUpManager mHeadsUpManager; @Mock private VisibilityLocationProvider mVisibilityLocationProvider; @Mock private VisualStabilityProvider mVisualStabilityProvider; Loading Loading @@ -121,6 +123,7 @@ public class VisualStabilityCoordinatorTest extends SysuiTestCase { mHeadsUpManager, mShadeAnimationInteractor, mJavaAdapter, mSeenNotificationsInteractor, mStatusBarStateController, mVisibilityLocationProvider, mVisualStabilityProvider, Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/KeyguardCoordinator.kt +67 −2 Original line number Diff line number Diff line Loading @@ -31,15 +31,20 @@ import com.android.systemui.keyguard.shared.model.KeyguardState import com.android.systemui.plugins.statusbar.StatusBarStateController import com.android.systemui.statusbar.StatusBarState import com.android.systemui.statusbar.expansionChanges import com.android.systemui.statusbar.notification.collection.GroupEntry import com.android.systemui.statusbar.notification.collection.ListEntry import com.android.systemui.statusbar.notification.collection.NotifPipeline import com.android.systemui.statusbar.notification.collection.NotificationEntry import com.android.systemui.statusbar.notification.collection.coordinator.dagger.CoordinatorScope import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifFilter import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifPromoter import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifSectioner import com.android.systemui.statusbar.notification.collection.notifcollection.NotifCollectionListener import com.android.systemui.statusbar.notification.collection.provider.SectionHeaderVisibilityProvider import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor import com.android.systemui.statusbar.notification.interruption.KeyguardNotificationVisibilityProvider import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype import com.android.systemui.statusbar.notification.stack.BUCKET_FOREGROUND_SERVICE import com.android.systemui.statusbar.policy.HeadsUpManager import com.android.systemui.statusbar.policy.headsUpEvents import com.android.systemui.util.asIndenting Loading Loading @@ -106,6 +111,10 @@ constructor( } private fun attachUnseenFilter(pipeline: NotifPipeline) { if (NotificationMinimalismPrototype.V2.isEnabled) { pipeline.addPromoter(unseenNotifPromoter) pipeline.addOnBeforeTransformGroupsListener(::pickOutTopUnseenNotif) } pipeline.addFinalizeFilter(unseenNotifFilter) pipeline.addCollectionListener(collectionListener) scope.launch { trackUnseenFilterSettingChanges() } Loading Loading @@ -263,7 +272,10 @@ constructor( } private fun unseenFeatureEnabled(): Flow<Boolean> { if (NotificationMinimalismPrototype.V1.isEnabled) { if ( NotificationMinimalismPrototype.V1.isEnabled || NotificationMinimalismPrototype.V2.isEnabled ) { return flowOf(true) } return secureSettings Loading Loading @@ -334,6 +346,57 @@ constructor( } } private fun pickOutTopUnseenNotif(list: List<ListEntry>) { if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) return // Only ever elevate a top unseen notification on keyguard, not even locked shade if (statusBarStateController.state != StatusBarState.KEYGUARD) { seenNotificationsInteractor.setTopUnseenNotification(null) return } // On keyguard pick the top-ranked unseen or ongoing notification to elevate seenNotificationsInteractor.setTopUnseenNotification( list .asSequence() .flatMap { when (it) { is NotificationEntry -> listOfNotNull(it) is GroupEntry -> it.children else -> error("unhandled type of $it") } } .filter { shouldIgnoreUnseenCheck(it) || it in unseenNotifications } .minByOrNull { it.ranking.rank } ) } @VisibleForTesting internal val unseenNotifPromoter = object : NotifPromoter("$TAG-unseen") { override fun shouldPromoteToTopLevel(child: NotificationEntry): Boolean = if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) false else seenNotificationsInteractor.isTopUnseenNotification(child) && NotificationMinimalismPrototype.V2.ungroupTopUnseen } val unseenNotifSectioner = object : NotifSectioner("Unseen", BUCKET_FOREGROUND_SERVICE) { override fun isInSection(entry: ListEntry): Boolean { if (NotificationMinimalismPrototype.V2.isUnexpectedlyInLegacyMode()) return false if ( seenNotificationsInteractor.isTopUnseenNotification(entry.representativeEntry) ) { return true } if (entry !is GroupEntry) { return false } return entry.children.any { seenNotificationsInteractor.isTopUnseenNotification(it) } } } @VisibleForTesting internal val unseenNotifFilter = object : NotifFilter("$TAG-unseen") { Loading @@ -351,7 +414,9 @@ constructor( * allow seen notifications to appear in the locked shade. */ private fun isOnKeyguard(): Boolean = if ( if (NotificationMinimalismPrototype.V2.isEnabled) { false // disable this feature under this prototype } else if ( NotificationMinimalismPrototype.V1.isEnabled && NotificationMinimalismPrototype.V1.showOnLockedShade ) { Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/NotifCoordinators.kt +54 −43 Original line number Diff line number Diff line Loading @@ -24,17 +24,20 @@ import com.android.systemui.statusbar.notification.collection.SortBySectionTimeF import com.android.systemui.statusbar.notification.collection.coordinator.dagger.CoordinatorScope import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifSectioner import com.android.systemui.statusbar.notification.collection.provider.SectionStyleProvider import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype import com.android.systemui.statusbar.notification.shared.NotificationsLiveDataStoreRefactor import javax.inject.Inject /** * Handles the attachment of [Coordinator]s to the [NotifPipeline] so that the * Coordinators can register their respective callbacks. * Handles the attachment of [Coordinator]s to the [NotifPipeline] so that the Coordinators can * register their respective callbacks. */ interface NotifCoordinators : Coordinator, PipelineDumpable @CoordinatorScope class NotifCoordinatorsImpl @Inject constructor( class NotifCoordinatorsImpl @Inject constructor( sectionStyleProvider: SectionStyleProvider, featureFlags: FeatureFlags, dataStoreCoordinator: DataStoreCoordinator, Loading Loading @@ -114,6 +117,9 @@ class NotifCoordinatorsImpl @Inject constructor( // Manually add Ordered Sections mOrderedSections.add(headsUpCoordinator.sectioner) // HeadsUp mOrderedSections.add(colorizedFgsCoordinator.sectioner) // ForegroundService if (NotificationMinimalismPrototype.V2.isEnabled) { mOrderedSections.add(keyguardCoordinator.unseenNotifSectioner) // Unseen (FGS) } mOrderedSections.add(conversationCoordinator.peopleAlertingSectioner) // People Alerting if (!SortBySectionTimeFlag.isEnabled) { mOrderedSections.add(conversationCoordinator.peopleSilentSectioner) // People Silent Loading @@ -124,22 +130,26 @@ class NotifCoordinatorsImpl @Inject constructor( sectionStyleProvider.setMinimizedSections(setOf(rankingCoordinator.minimizedSectioner)) if (SortBySectionTimeFlag.isEnabled) { sectionStyleProvider.setSilentSections(listOf( sectionStyleProvider.setSilentSections( listOf( rankingCoordinator.silentSectioner, rankingCoordinator.minimizedSectioner, )) ) ) } else { sectionStyleProvider.setSilentSections(listOf( sectionStyleProvider.setSilentSections( listOf( conversationCoordinator.peopleSilentSectioner, rankingCoordinator.silentSectioner, rankingCoordinator.minimizedSectioner, )) ) ) } } /** * Sends the pipeline to each coordinator when the pipeline is ready to accept * [Pluggable]s, [NotifCollectionListener]s and [NotifLifetimeExtender]s. * Sends the pipeline to each coordinator when the pipeline is ready to accept [Pluggable]s, * [NotifCollectionListener]s and [NotifLifetimeExtender]s. */ override fun attach(pipeline: NotifPipeline) { for (c in mCoreCoordinators) { Loading @@ -155,7 +165,8 @@ class NotifCoordinatorsImpl @Inject constructor( * As part of the NotifPipeline dumpable, dumps the list of coordinators; sections are omitted * as they are dumped in the RenderStageManager instead. */ override fun dumpPipeline(d: PipelineDumper) = with(d) { override fun dumpPipeline(d: PipelineDumper) = with(d) { dump("core coordinators", mCoreCoordinators) dump("normal coordinators", mCoordinators) } Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/collection/coordinator/VisualStabilityCoordinator.java +14 −2 Original line number Diff line number Diff line Loading @@ -38,6 +38,8 @@ import com.android.systemui.statusbar.notification.collection.NotifPipeline; import com.android.systemui.statusbar.notification.collection.NotificationEntry; import com.android.systemui.statusbar.notification.collection.listbuilder.pluggable.NotifStabilityManager; import com.android.systemui.statusbar.notification.collection.provider.VisualStabilityProvider; import com.android.systemui.statusbar.notification.domain.interactor.SeenNotificationsInteractor; import com.android.systemui.statusbar.notification.shared.NotificationMinimalismPrototype; import com.android.systemui.statusbar.policy.HeadsUpManager; import com.android.systemui.util.Compile; import com.android.systemui.util.concurrency.DelayableExecutor; Loading @@ -63,6 +65,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { public static final boolean DEBUG = Compile.IS_DEBUG && Log.isLoggable(TAG, Log.VERBOSE); private final DelayableExecutor mDelayableExecutor; private final HeadsUpManager mHeadsUpManager; private final SeenNotificationsInteractor mSeenNotificationsInteractor; private final ShadeAnimationInteractor mShadeAnimationInteractor; private final StatusBarStateController mStatusBarStateController; private final JavaAdapter mJavaAdapter; Loading Loading @@ -101,6 +104,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { HeadsUpManager headsUpManager, ShadeAnimationInteractor shadeAnimationInteractor, JavaAdapter javaAdapter, SeenNotificationsInteractor seenNotificationsInteractor, StatusBarStateController statusBarStateController, VisibilityLocationProvider visibilityLocationProvider, VisualStabilityProvider visualStabilityProvider, Loading @@ -109,6 +113,7 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { mHeadsUpManager = headsUpManager; mShadeAnimationInteractor = shadeAnimationInteractor; mJavaAdapter = javaAdapter; mSeenNotificationsInteractor = seenNotificationsInteractor; mVisibilityLocationProvider = visibilityLocationProvider; mVisualStabilityProvider = visualStabilityProvider; mWakefulnessLifecycle = wakefulnessLifecycle; Loading Loading @@ -142,8 +147,15 @@ public class VisualStabilityCoordinator implements Coordinator, Dumpable { private final NotifStabilityManager mNotifStabilityManager = new NotifStabilityManager("VisualStabilityCoordinator") { private boolean canMoveForHeadsUp(NotificationEntry entry) { return entry != null && mHeadsUpManager.isHeadsUpEntry(entry.getKey()) && !mVisibilityLocationProvider.isInVisibleLocation(entry); if (entry == null) { return false; } boolean isTopUnseen = NotificationMinimalismPrototype.V2.isEnabled() && mSeenNotificationsInteractor.isTopUnseenNotification(entry); if (isTopUnseen || mHeadsUpManager.isHeadsUpEntry(entry.getKey())) { return !mVisibilityLocationProvider.isInVisibleLocation(entry); } return false; } @Override Loading
packages/SystemUI/src/com/android/systemui/statusbar/notification/data/repository/ActiveNotificationListRepository.kt +3 −0 Original line number Diff line number Diff line Loading @@ -41,6 +41,9 @@ class ActiveNotificationListRepository @Inject constructor() { /** Stats about the list of notifications attached to the shade */ val notifStats = MutableStateFlow(NotifStats.empty) /** The key of the top unseen notification */ val topUnseenNotificationKey = MutableStateFlow<String?>(null) } /** Represents the notification list, comprised of groups and individual notifications. */ Loading