Merge "New Pipeline: Implement lifetime extension for guts"
This commit is contained in:
committed by
Android (Google) Code Review
commit
9560c9a648
@@ -523,7 +523,9 @@ public class NotifCollection implements Dumpable {
|
||||
}
|
||||
}
|
||||
|
||||
private void onEndLifetimeExtension(NotifLifetimeExtender extender, NotificationEntry entry) {
|
||||
private void onEndLifetimeExtension(
|
||||
@NonNull NotifLifetimeExtender extender,
|
||||
@NonNull NotificationEntry entry) {
|
||||
Assert.isMainThread();
|
||||
if (!mAttached) {
|
||||
return;
|
||||
|
||||
@@ -0,0 +1,126 @@
|
||||
/*
|
||||
* Copyright (C) 2021 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.android.systemui.statusbar.notification.collection.coordinator
|
||||
|
||||
import android.util.ArraySet
|
||||
import com.android.systemui.Dumpable
|
||||
import com.android.systemui.dagger.SysUISingleton
|
||||
import com.android.systemui.dump.DumpManager
|
||||
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.notifcollection.NotifLifetimeExtender
|
||||
import com.android.systemui.statusbar.notification.collection.notifcollection.NotifLifetimeExtender.OnEndLifetimeExtensionCallback
|
||||
import com.android.systemui.statusbar.notification.row.NotificationGuts
|
||||
import com.android.systemui.statusbar.notification.row.NotificationGutsManager
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewListener
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewManager
|
||||
import java.io.FileDescriptor
|
||||
import java.io.PrintWriter
|
||||
import javax.inject.Inject
|
||||
|
||||
private const val TAG = "GutsCoordinator"
|
||||
|
||||
/**
|
||||
* Coordinates the guts displayed by the [NotificationGutsManager] with the pipeline.
|
||||
* Specifically, this just adds the lifetime extension necessary to keep guts from disappearing.
|
||||
*/
|
||||
@SysUISingleton
|
||||
class GutsCoordinator @Inject constructor(
|
||||
private val notifGutsViewManager: NotifGutsViewManager,
|
||||
private val logger: GutsCoordinatorLogger,
|
||||
dumpManager: DumpManager
|
||||
) : Coordinator, Dumpable {
|
||||
|
||||
/** Keys of any Notifications for which we've been told the guts are open */
|
||||
private val notifsWithOpenGuts = ArraySet<String>()
|
||||
|
||||
/** Keys of any Notifications we've extended the lifetime for, based on guts */
|
||||
private val notifsExtendingLifetime = ArraySet<String>()
|
||||
|
||||
/** Callback for ending lifetime extension */
|
||||
private var onEndLifetimeExtensionCallback: OnEndLifetimeExtensionCallback? = null
|
||||
|
||||
init {
|
||||
dumpManager.registerDumpable(TAG, this)
|
||||
}
|
||||
|
||||
override fun attach(pipeline: NotifPipeline) {
|
||||
notifGutsViewManager.setGutsListener(mGutsListener)
|
||||
pipeline.addNotificationLifetimeExtender(mLifetimeExtender)
|
||||
}
|
||||
|
||||
override fun dump(fd: FileDescriptor, pw: PrintWriter, args: Array<String>) {
|
||||
pw.println(" notifsWithOpenGuts: ${notifsWithOpenGuts.size}")
|
||||
for (key in notifsWithOpenGuts) {
|
||||
pw.println(" * $key")
|
||||
}
|
||||
pw.println(" notifsExtendingLifetime: ${notifsExtendingLifetime.size}")
|
||||
for (key in notifsExtendingLifetime) {
|
||||
pw.println(" * $key")
|
||||
}
|
||||
pw.println(" onEndLifetimeExtensionCallback: $onEndLifetimeExtensionCallback")
|
||||
}
|
||||
|
||||
private val mLifetimeExtender: NotifLifetimeExtender = object : NotifLifetimeExtender {
|
||||
override fun getName(): String {
|
||||
return TAG
|
||||
}
|
||||
|
||||
override fun setCallback(callback: OnEndLifetimeExtensionCallback) {
|
||||
onEndLifetimeExtensionCallback = callback
|
||||
}
|
||||
|
||||
override fun shouldExtendLifetime(entry: NotificationEntry, reason: Int): Boolean {
|
||||
val isShowingGuts = isCurrentlyShowingGuts(entry)
|
||||
if (isShowingGuts) {
|
||||
notifsExtendingLifetime.add(entry.key)
|
||||
}
|
||||
return isShowingGuts
|
||||
}
|
||||
|
||||
override fun cancelLifetimeExtension(entry: NotificationEntry) {
|
||||
notifsExtendingLifetime.remove(entry.key)
|
||||
}
|
||||
}
|
||||
|
||||
private val mGutsListener: NotifGutsViewListener = object : NotifGutsViewListener {
|
||||
override fun onGutsOpen(entry: NotificationEntry, guts: NotificationGuts) {
|
||||
logger.logGutsOpened(entry.key, guts)
|
||||
if (guts.isLeavebehind) {
|
||||
// leave-behind guts should not extend the lifetime of the notification
|
||||
closeGutsAndEndLifetimeExtension(entry)
|
||||
} else {
|
||||
notifsWithOpenGuts.add(entry.key)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onGutsClose(entry: NotificationEntry) {
|
||||
logger.logGutsClosed(entry.key)
|
||||
closeGutsAndEndLifetimeExtension(entry)
|
||||
}
|
||||
}
|
||||
|
||||
private fun isCurrentlyShowingGuts(entry: ListEntry) =
|
||||
notifsWithOpenGuts.contains(entry.key)
|
||||
|
||||
private fun closeGutsAndEndLifetimeExtension(entry: NotificationEntry) {
|
||||
notifsWithOpenGuts.remove(entry.key)
|
||||
if (notifsExtendingLifetime.remove(entry.key)) {
|
||||
onEndLifetimeExtensionCallback?.onEndLifetimeExtension(mLifetimeExtender, entry)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
package com.android.systemui.statusbar.notification.collection.coordinator
|
||||
|
||||
import com.android.systemui.log.LogBuffer
|
||||
import com.android.systemui.log.LogLevel
|
||||
import com.android.systemui.log.dagger.NotificationLog
|
||||
import com.android.systemui.statusbar.notification.row.NotificationGuts
|
||||
import javax.inject.Inject
|
||||
|
||||
private const val TAG = "GutsCoordinator"
|
||||
|
||||
class GutsCoordinatorLogger @Inject constructor(
|
||||
@NotificationLog private val buffer: LogBuffer
|
||||
) {
|
||||
|
||||
fun logGutsOpened(key: String, guts: NotificationGuts) {
|
||||
buffer.log(TAG, LogLevel.DEBUG, {
|
||||
str1 = key
|
||||
str2 = guts::class.simpleName
|
||||
bool1 = guts.isLeavebehind
|
||||
}, {
|
||||
"Guts of type $str2 (leave behind: $bool1) opened for class $str1"
|
||||
})
|
||||
}
|
||||
|
||||
fun logGutsClosed(key: String) {
|
||||
buffer.log(TAG, LogLevel.DEBUG, {
|
||||
str1 = key
|
||||
}, {
|
||||
"Guts closed for class $str1"
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -19,7 +19,8 @@ package com.android.systemui.statusbar.notification.collection.coordinator;
|
||||
import static com.android.systemui.statusbar.NotificationRemoteInputManager.FORCE_REMOTE_INPUT_HISTORY;
|
||||
import static com.android.systemui.statusbar.notification.interruption.HeadsUpController.alertAgain;
|
||||
|
||||
import android.annotation.Nullable;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import com.android.systemui.dagger.SysUISingleton;
|
||||
import com.android.systemui.statusbar.NotificationRemoteInputManager;
|
||||
@@ -164,17 +165,17 @@ public class HeadsUpCoordinator implements Coordinator {
|
||||
|
||||
private final NotifLifetimeExtender mLifetimeExtender = new NotifLifetimeExtender() {
|
||||
@Override
|
||||
public String getName() {
|
||||
public @NonNull String getName() {
|
||||
return TAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCallback(OnEndLifetimeExtensionCallback callback) {
|
||||
public void setCallback(@NonNull OnEndLifetimeExtensionCallback callback) {
|
||||
mEndLifetimeExtension = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean shouldExtendLifetime(NotificationEntry entry, int reason) {
|
||||
public boolean shouldExtendLifetime(@NonNull NotificationEntry entry, int reason) {
|
||||
boolean isShowingHun = isCurrentlyShowingHun(entry);
|
||||
if (isShowingHun) {
|
||||
mNotifExtendingLifetime = entry;
|
||||
@@ -183,7 +184,7 @@ public class HeadsUpCoordinator implements Coordinator {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void cancelLifetimeExtension(NotificationEntry entry) {
|
||||
public void cancelLifetimeExtension(@NonNull NotificationEntry entry) {
|
||||
if (Objects.equals(mNotifExtendingLifetime, entry)) {
|
||||
mNotifExtendingLifetime = null;
|
||||
}
|
||||
|
||||
@@ -57,6 +57,7 @@ public class NotifCoordinators implements Dumpable {
|
||||
DeviceProvisionedCoordinator deviceProvisionedCoordinator,
|
||||
BubbleCoordinator bubbleCoordinator,
|
||||
HeadsUpCoordinator headsUpCoordinator,
|
||||
GutsCoordinator gutsCoordinator,
|
||||
ConversationCoordinator conversationCoordinator,
|
||||
PreparationCoordinator preparationCoordinator,
|
||||
MediaCoordinator mediaCoordinator,
|
||||
@@ -83,6 +84,7 @@ public class NotifCoordinators implements Dumpable {
|
||||
|
||||
if (featureFlags.isNewNotifPipelineRenderingEnabled()) {
|
||||
mCoordinators.add(headsUpCoordinator);
|
||||
mCoordinators.add(gutsCoordinator);
|
||||
mCoordinators.add(preparationCoordinator);
|
||||
}
|
||||
|
||||
|
||||
@@ -16,6 +16,8 @@
|
||||
|
||||
package com.android.systemui.statusbar.notification.collection.notifcollection;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import com.android.systemui.statusbar.notification.collection.NotifCollection;
|
||||
import com.android.systemui.statusbar.notification.collection.NotifCollection.CancellationReason;
|
||||
import com.android.systemui.statusbar.notification.collection.NotificationEntry;
|
||||
@@ -26,14 +28,14 @@ import com.android.systemui.statusbar.notification.collection.NotificationEntry;
|
||||
*/
|
||||
public interface NotifLifetimeExtender {
|
||||
/** Name to associate with this extender (for the purposes of debugging) */
|
||||
String getName();
|
||||
@NonNull String getName();
|
||||
|
||||
/**
|
||||
* Called on the extender immediately after it has been registered. The extender should hang on
|
||||
* to this callback and execute it whenever it no longer needs to extend the lifetime of a
|
||||
* notification.
|
||||
*/
|
||||
void setCallback(OnEndLifetimeExtensionCallback callback);
|
||||
void setCallback(@NonNull OnEndLifetimeExtensionCallback callback);
|
||||
|
||||
/**
|
||||
* Called by the NotifCollection whenever a notification has been retracted (by the app) or
|
||||
@@ -43,7 +45,7 @@ public interface NotifLifetimeExtender {
|
||||
* called on all lifetime extenders even if earlier ones return true (in other words, multiple
|
||||
* lifetime extenders can be extending a notification at the same time).
|
||||
*/
|
||||
boolean shouldExtendLifetime(NotificationEntry entry, @CancellationReason int reason);
|
||||
boolean shouldExtendLifetime(@NonNull NotificationEntry entry, @CancellationReason int reason);
|
||||
|
||||
/**
|
||||
* Called by the NotifCollection to inform a lifetime extender that its extension of a notif
|
||||
@@ -51,7 +53,7 @@ public interface NotifLifetimeExtender {
|
||||
* lifetime extension). The extender should clean up any references it has to the notif in
|
||||
* question.
|
||||
*/
|
||||
void cancelLifetimeExtension(NotificationEntry entry);
|
||||
void cancelLifetimeExtension(@NonNull NotificationEntry entry);
|
||||
|
||||
/** Callback for notifying the NotifCollection that a lifetime extension has expired.*/
|
||||
interface OnEndLifetimeExtensionCallback {
|
||||
@@ -59,6 +61,8 @@ public interface NotifLifetimeExtender {
|
||||
* Stop extending the lifetime of `entry` with `extender` and then immediately re-evaluates
|
||||
* whether to continue lifetime extending this notification or to remove it.
|
||||
*/
|
||||
void onEndLifetimeExtension(NotifLifetimeExtender extender, NotificationEntry entry);
|
||||
void onEndLifetimeExtension(
|
||||
@NonNull NotifLifetimeExtender extender,
|
||||
@NonNull NotificationEntry entry);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright (C) 2021 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.android.systemui.statusbar.notification.collection.render
|
||||
|
||||
import com.android.systemui.statusbar.notification.collection.NotificationEntry
|
||||
import com.android.systemui.statusbar.notification.row.NotificationGuts
|
||||
|
||||
/**
|
||||
* Interface for listening to guts open and close events.
|
||||
*/
|
||||
interface NotifGutsViewListener {
|
||||
/** A notification's guts are being opened */
|
||||
fun onGutsOpen(entry: NotificationEntry, guts: NotificationGuts)
|
||||
|
||||
/** A notification's guts are being closed */
|
||||
fun onGutsClose(entry: NotificationEntry)
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
/*
|
||||
* Copyright (C) 2021 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.android.systemui.statusbar.notification.collection.render
|
||||
|
||||
/** A type which provides open and close guts events to a single listener */
|
||||
interface NotifGutsViewManager {
|
||||
/**
|
||||
* @param listener the object that will listen to open and close guts events
|
||||
*/
|
||||
fun setGutsListener(listener: NotifGutsViewListener?)
|
||||
}
|
||||
@@ -58,6 +58,7 @@ import com.android.systemui.statusbar.notification.collection.render.GroupExpans
|
||||
import com.android.systemui.statusbar.notification.collection.render.GroupExpansionManagerImpl;
|
||||
import com.android.systemui.statusbar.notification.collection.render.GroupMembershipManager;
|
||||
import com.android.systemui.statusbar.notification.collection.render.GroupMembershipManagerImpl;
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewManager;
|
||||
import com.android.systemui.statusbar.notification.init.NotificationsController;
|
||||
import com.android.systemui.statusbar.notification.init.NotificationsControllerImpl;
|
||||
import com.android.systemui.statusbar.notification.init.NotificationsControllerStub;
|
||||
@@ -169,6 +170,14 @@ public interface NotificationsModule {
|
||||
dumpManager);
|
||||
}
|
||||
|
||||
/** Provides an instance of {@link NotifGutsViewManager} */
|
||||
@SysUISingleton
|
||||
@Provides
|
||||
static NotifGutsViewManager provideNotifGutsViewManager(
|
||||
NotificationGutsManager notificationGutsManager) {
|
||||
return notificationGutsManager;
|
||||
}
|
||||
|
||||
/** Provides an instance of {@link VisualStabilityManager} */
|
||||
@SysUISingleton
|
||||
@Provides
|
||||
|
||||
@@ -65,6 +65,8 @@ import com.android.systemui.statusbar.notification.NotificationActivityStarter;
|
||||
import com.android.systemui.statusbar.notification.NotificationEntryManager;
|
||||
import com.android.systemui.statusbar.notification.collection.NotificationEntry;
|
||||
import com.android.systemui.statusbar.notification.collection.provider.HighPriorityProvider;
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewListener;
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewManager;
|
||||
import com.android.systemui.statusbar.notification.dagger.NotificationsModule;
|
||||
import com.android.systemui.statusbar.notification.row.NotificationInfo.CheckSaveListener;
|
||||
import com.android.systemui.statusbar.notification.stack.NotificationListContainer;
|
||||
@@ -83,7 +85,8 @@ import dagger.Lazy;
|
||||
* Handles various NotificationGuts related tasks, such as binding guts to a row, opening and
|
||||
* closing guts, and keeping track of the currently exposed notification guts.
|
||||
*/
|
||||
public class NotificationGutsManager implements Dumpable, NotificationLifetimeExtender {
|
||||
public class NotificationGutsManager implements Dumpable, NotificationLifetimeExtender,
|
||||
NotifGutsViewManager {
|
||||
private static final String TAG = "NotificationGutsManager";
|
||||
|
||||
// Must match constant in Settings. Used to highlight preferences when linking to Settings.
|
||||
@@ -123,7 +126,6 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
private final Optional<BubblesManager> mBubblesManagerOptional;
|
||||
private Runnable mOpenRunnable;
|
||||
private final INotificationManager mNotificationManager;
|
||||
private final NotificationEntryManager mNotificationEntryManager;
|
||||
private final PeopleSpaceWidgetManager mPeopleSpaceWidgetManager;
|
||||
private final LauncherApps mLauncherApps;
|
||||
private final ShortcutManager mShortcutManager;
|
||||
@@ -131,6 +133,7 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
private final UiEventLogger mUiEventLogger;
|
||||
private final ShadeController mShadeController;
|
||||
private final AppWidgetManager mAppWidgetManager;
|
||||
private NotifGutsViewListener mGutsListener;
|
||||
|
||||
/**
|
||||
* Injected constructor. See {@link NotificationsModule}.
|
||||
@@ -161,7 +164,6 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
mAccessibilityManager = accessibilityManager;
|
||||
mHighPriorityProvider = highPriorityProvider;
|
||||
mNotificationManager = notificationManager;
|
||||
mNotificationEntryManager = notificationEntryManager;
|
||||
mPeopleSpaceWidgetManager = peopleSpaceWidgetManager;
|
||||
mLauncherApps = launcherApps;
|
||||
mShortcutManager = shortcutManager;
|
||||
@@ -258,10 +260,10 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
@VisibleForTesting
|
||||
protected boolean bindGuts(final ExpandableNotificationRow row,
|
||||
NotificationMenuRowPlugin.MenuItem item) {
|
||||
StatusBarNotification sbn = row.getEntry().getSbn();
|
||||
NotificationEntry entry = row.getEntry();
|
||||
|
||||
row.setGutsView(item);
|
||||
row.setTag(sbn.getPackageName());
|
||||
row.setTag(entry.getSbn().getPackageName());
|
||||
row.getGuts().setClosedListener((NotificationGuts g) -> {
|
||||
row.onGutsClosed();
|
||||
if (!g.willBeRemoved() && !row.isRemoved()) {
|
||||
@@ -272,7 +274,10 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
mNotificationGutsExposed = null;
|
||||
mGutsMenuItem = null;
|
||||
}
|
||||
String key = sbn.getKey();
|
||||
if (mGutsListener != null) {
|
||||
mGutsListener.onGutsClose(entry);
|
||||
}
|
||||
String key = entry.getKey();
|
||||
if (key.equals(mKeyToRemoveOnGutsClosed)) {
|
||||
mKeyToRemoveOnGutsClosed = null;
|
||||
if (mNotificationLifetimeFinishedCallback != null) {
|
||||
@@ -650,6 +655,10 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
needsFalsingProtection,
|
||||
row::onGutsOpened);
|
||||
|
||||
if (mGutsListener != null) {
|
||||
mGutsListener.onGutsOpen(row.getEntry(), guts);
|
||||
}
|
||||
|
||||
row.closeRemoteInput();
|
||||
mListContainer.onHeightChanged(row, true /* needsAnimation */);
|
||||
mGutsMenuItem = menuItem;
|
||||
@@ -695,10 +704,17 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
|
||||
@Override
|
||||
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
|
||||
pw.println("NotificationGutsManager state:");
|
||||
pw.print(" mKeyToRemoveOnGutsClosed: ");
|
||||
pw.print(" mKeyToRemoveOnGutsClosed (legacy): ");
|
||||
pw.println(mKeyToRemoveOnGutsClosed);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param gutsListener the listener for open and close guts events
|
||||
*/
|
||||
public void setGutsListener(NotifGutsViewListener gutsListener) {
|
||||
mGutsListener = gutsListener;
|
||||
}
|
||||
|
||||
public interface OnSettingsClickListener {
|
||||
public void onSettingsClick(String key);
|
||||
}
|
||||
|
||||
@@ -60,6 +60,7 @@ import android.util.ArrayMap;
|
||||
import android.util.ArraySet;
|
||||
import android.util.Pair;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.test.filters.SmallTest;
|
||||
|
||||
import com.android.internal.statusbar.IStatusBarService;
|
||||
@@ -1405,25 +1406,26 @@ public class NotifCollectionTest extends SysuiTestCase {
|
||||
mName = name;
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public String getName() {
|
||||
return mName;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setCallback(OnEndLifetimeExtensionCallback callback) {
|
||||
public void setCallback(@NonNull OnEndLifetimeExtensionCallback callback) {
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean shouldExtendLifetime(
|
||||
NotificationEntry entry,
|
||||
@NonNull NotificationEntry entry,
|
||||
@CancellationReason int reason) {
|
||||
return shouldExtendLifetime;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void cancelLifetimeExtension(NotificationEntry entry) {
|
||||
public void cancelLifetimeExtension(@NonNull NotificationEntry entry) {
|
||||
if (onCancelLifetimeExtension != null) {
|
||||
onCancelLifetimeExtension.run();
|
||||
}
|
||||
|
||||
@@ -0,0 +1,117 @@
|
||||
/*
|
||||
* Copyright (C) 2021 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package com.android.systemui.statusbar.notification.collection.coordinator
|
||||
|
||||
import android.testing.AndroidTestingRunner
|
||||
import android.testing.TestableLooper.RunWithLooper
|
||||
import androidx.test.filters.SmallTest
|
||||
import com.android.systemui.SysuiTestCase
|
||||
import com.android.systemui.dump.DumpManager
|
||||
import com.android.systemui.statusbar.notification.collection.NotifPipeline
|
||||
import com.android.systemui.statusbar.notification.collection.NotificationEntry
|
||||
import com.android.systemui.statusbar.notification.collection.NotificationEntryBuilder
|
||||
import com.android.systemui.statusbar.notification.collection.notifcollection.NotifLifetimeExtender
|
||||
import com.android.systemui.statusbar.notification.collection.notifcollection.NotifLifetimeExtender.OnEndLifetimeExtensionCallback
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewListener
|
||||
import com.android.systemui.statusbar.notification.collection.render.NotifGutsViewManager
|
||||
import com.android.systemui.statusbar.notification.row.NotificationGuts
|
||||
import com.android.systemui.util.mockito.argumentCaptor
|
||||
import com.google.common.truth.Truth.assertThat
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
import org.mockito.Mock
|
||||
import org.mockito.Mockito.mock
|
||||
import org.mockito.Mockito.verify
|
||||
import org.mockito.MockitoAnnotations.initMocks
|
||||
|
||||
@SmallTest
|
||||
@RunWith(AndroidTestingRunner::class)
|
||||
@RunWithLooper
|
||||
class GutsCoordinatorTest : SysuiTestCase() {
|
||||
private lateinit var coordinator: GutsCoordinator
|
||||
private lateinit var notifLifetimeExtender: NotifLifetimeExtender
|
||||
private lateinit var notifGutsViewListener: NotifGutsViewListener
|
||||
|
||||
private lateinit var entry1: NotificationEntry
|
||||
private lateinit var entry2: NotificationEntry
|
||||
|
||||
@Mock private lateinit var notifGutsViewManager: NotifGutsViewManager
|
||||
@Mock private lateinit var pipeline: NotifPipeline
|
||||
@Mock private lateinit var dumpManager: DumpManager
|
||||
@Mock private lateinit var logger: GutsCoordinatorLogger
|
||||
@Mock private lateinit var lifetimeExtenderCallback: OnEndLifetimeExtensionCallback
|
||||
|
||||
@Before
|
||||
fun setUp() {
|
||||
initMocks(this)
|
||||
coordinator = GutsCoordinator(notifGutsViewManager, logger, dumpManager)
|
||||
coordinator.attach(pipeline)
|
||||
notifLifetimeExtender = argumentCaptor<NotifLifetimeExtender>().let {
|
||||
verify(pipeline).addNotificationLifetimeExtender(it.capture())
|
||||
it.value!!
|
||||
}
|
||||
notifGutsViewListener = argumentCaptor<NotifGutsViewListener>().let {
|
||||
verify(notifGutsViewManager).setGutsListener(it.capture())
|
||||
it.value!!
|
||||
}
|
||||
notifLifetimeExtender.setCallback(lifetimeExtenderCallback)
|
||||
entry1 = NotificationEntryBuilder().setId(1).build()
|
||||
entry2 = NotificationEntryBuilder().setId(2).build()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun testSimpleLifetimeExtension() {
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
notifGutsViewListener.onGutsOpen(entry1, mock(NotificationGuts::class.java))
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isTrue()
|
||||
notifGutsViewListener.onGutsClose(entry1)
|
||||
verify(lifetimeExtenderCallback).onEndLifetimeExtension(notifLifetimeExtender, entry1)
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun testDoubleOpenLifetimeExtension() {
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
notifGutsViewListener.onGutsOpen(entry1, mock(NotificationGuts::class.java))
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isTrue()
|
||||
notifGutsViewListener.onGutsOpen(entry1, mock(NotificationGuts::class.java))
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isTrue()
|
||||
notifGutsViewListener.onGutsClose(entry1)
|
||||
verify(lifetimeExtenderCallback).onEndLifetimeExtension(notifLifetimeExtender, entry1)
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun testTwoEntryLifetimeExtension() {
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry2, 0)).isFalse()
|
||||
notifGutsViewListener.onGutsOpen(entry1, mock(NotificationGuts::class.java))
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isTrue()
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry2, 0)).isFalse()
|
||||
notifGutsViewListener.onGutsOpen(entry2, mock(NotificationGuts::class.java))
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isTrue()
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry2, 0)).isTrue()
|
||||
notifGutsViewListener.onGutsClose(entry1)
|
||||
verify(lifetimeExtenderCallback).onEndLifetimeExtension(notifLifetimeExtender, entry1)
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry2, 0)).isTrue()
|
||||
notifGutsViewListener.onGutsClose(entry2)
|
||||
verify(lifetimeExtenderCallback).onEndLifetimeExtension(notifLifetimeExtender, entry2)
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry1, 0)).isFalse()
|
||||
assertThat(notifLifetimeExtender.shouldExtendLifetime(entry2, 0)).isFalse()
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user