diff --git a/res/values/strings.xml b/res/values/strings.xml
index 50556de6e0b..21ab9179933 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -8935,6 +8935,9 @@
This app has not posted any notifications
+
+ Show unused categories
+
Additional settings in the app
diff --git a/res/xml/app_notification_settings.xml b/res/xml/app_notification_settings.xml
index f96a375224e..091de7536da 100644
--- a/res/xml/app_notification_settings.xml
+++ b/res/xml/app_notification_settings.xml
@@ -55,6 +55,11 @@
android:key="channels"
android:layout="@layout/empty_view" />
+
+
sentByChannel;
public NotificationsSentState sentByApp;
+ public boolean showAllChannels = true;
}
}
diff --git a/src/com/android/settings/notification/app/AppNotificationSettings.java b/src/com/android/settings/notification/app/AppNotificationSettings.java
index 89756b7b839..3d3f3429e9a 100644
--- a/src/com/android/settings/notification/app/AppNotificationSettings.java
+++ b/src/com/android/settings/notification/app/AppNotificationSettings.java
@@ -16,16 +16,10 @@
package com.android.settings.notification.app;
-import static com.android.server.notification.Flags.notificationHideUnusedChannels;
-
-
import android.app.settings.SettingsEnums;
import android.content.Context;
import android.text.TextUtils;
import android.util.Log;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
import com.android.internal.widget.LockPatternUtils;
import com.android.settings.R;
@@ -107,38 +101,8 @@ public class AppNotificationSettings extends NotificationSettings {
mControllers.add(new BubbleSummaryPreferenceController(context, mBackend));
mControllers.add(new NotificationsOffPreferenceController(context));
mControllers.add(new DeletedChannelsPreferenceController(context, mBackend));
+ mControllers.add(new ShowMorePreferenceController(
+ context, mDependentFieldListener, mBackend));
return new ArrayList<>(mControllers);
}
-
- private final int SHOW_ALL_CHANNELS = 1;
-
- @Override
- public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
- if (notificationHideUnusedChannels()) {
- menu.add(Menu.NONE, SHOW_ALL_CHANNELS, Menu.NONE,
- mShowAll ? R.string.hide_unused_channels : R.string.show_unused_channels);
- }
- super.onCreateOptionsMenu(menu, inflater);
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- if (!notificationHideUnusedChannels()) {
- return super.onOptionsItemSelected(item);
- }
- switch (item.getItemId()) {
- case SHOW_ALL_CHANNELS:
- mShowAll = !mShowAll;
- item.setTitle(mShowAll
- ? R.string.hide_unused_channels
- : R.string.show_unused_channels);
- ChannelListPreferenceController list =
- use(ChannelListPreferenceController.class);
- list.setShowAll(mShowAll);
- list.updateState(findPreference(list.getPreferenceKey()));
- return true;
- default:
- return super.onOptionsItemSelected(item);
- }
- }
}
diff --git a/src/com/android/settings/notification/app/ChannelListPreferenceController.java b/src/com/android/settings/notification/app/ChannelListPreferenceController.java
index 70775926e9b..b8dfb6a7069 100644
--- a/src/com/android/settings/notification/app/ChannelListPreferenceController.java
+++ b/src/com/android/settings/notification/app/ChannelListPreferenceController.java
@@ -59,8 +59,6 @@ public class ChannelListPreferenceController extends NotificationPreferenceContr
private List mChannelGroupList;
private PreferenceCategory mPreference;
- private boolean mShowAll;
-
public ChannelListPreferenceController(Context context, NotificationBackend backend) {
super(context, backend);
}
@@ -100,7 +98,7 @@ public class ChannelListPreferenceController extends NotificationPreferenceContr
@Override
protected Void doInBackground(Void... unused) {
if (notificationHideUnusedChannels()) {
- if (mShowAll) {
+ if (mAppRow.showAllChannels) {
mChannelGroupList = mBackend.getGroups(mAppRow.pkg, mAppRow.uid).getList();
} else {
mChannelGroupList = mBackend.getGroupsWithRecentBlockedFilter(mAppRow.pkg,
@@ -123,10 +121,6 @@ public class ChannelListPreferenceController extends NotificationPreferenceContr
}.execute();
}
- protected void setShowAll(boolean showAll) {
- mShowAll = showAll;
- }
-
/**
* Update the preferences group to match the
* @param groupPrefsList
diff --git a/src/com/android/settings/notification/app/DeletedChannelsPreferenceController.java b/src/com/android/settings/notification/app/DeletedChannelsPreferenceController.java
index 6a1d4cb1247..07b7fdab01d 100644
--- a/src/com/android/settings/notification/app/DeletedChannelsPreferenceController.java
+++ b/src/com/android/settings/notification/app/DeletedChannelsPreferenceController.java
@@ -16,6 +16,8 @@
package com.android.settings.notification.app;
+import static com.android.server.notification.Flags.notificationHideUnusedChannels;
+
import android.content.Context;
import androidx.preference.Preference;
@@ -44,6 +46,9 @@ public class DeletedChannelsPreferenceController extends NotificationPreferenceC
if (!super.isAvailable()) {
return false;
}
+ if (notificationHideUnusedChannels()) {
+ return false;
+ }
// only visible on app screen
if (mChannel != null || hasValidGroup()) {
return false;
diff --git a/src/com/android/settings/notification/app/ShowMorePreferenceController.java b/src/com/android/settings/notification/app/ShowMorePreferenceController.java
new file mode 100644
index 00000000000..dbc279a6c8b
--- /dev/null
+++ b/src/com/android/settings/notification/app/ShowMorePreferenceController.java
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2024 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.settings.notification.app;
+
+import static com.android.server.notification.Flags.notificationHideUnusedChannels;
+
+import android.content.Context;
+
+import androidx.annotation.NonNull;
+import androidx.preference.Preference;
+import androidx.preference.PreferenceScreen;
+
+import com.android.settings.notification.NotificationBackend;
+
+import org.jetbrains.annotations.NotNull;
+
+public class ShowMorePreferenceController extends NotificationPreferenceController {
+
+ private static final String KEY = "more";
+ private NotificationSettings.DependentFieldListener mDependentFieldListener;
+
+ public ShowMorePreferenceController(Context context,
+ NotificationSettings.DependentFieldListener dependentFieldListener,
+ NotificationBackend backend) {
+ super(context, backend);
+ mDependentFieldListener = dependentFieldListener;
+ }
+
+ @Override
+ public String getPreferenceKey() {
+ return KEY;
+ }
+
+ @Override
+ public boolean isAvailable() {
+ if (!notificationHideUnusedChannels()) {
+ return false;
+ }
+ if (mAppRow == null) {
+ return false;
+ }
+ if (mAppRow.banned || mAppRow.showAllChannels) {
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ boolean isIncludedInFilter() {
+ return false;
+ }
+
+ @Override
+ public void updateState(Preference preference) {
+ preference.setOnPreferenceClickListener(preference1 -> {
+ mAppRow.showAllChannels = true;
+ mDependentFieldListener.onFieldValueChanged();
+ return true;
+ });
+ }
+}
diff --git a/tests/robotests/src/com/android/settings/notification/app/DeletedChannelsPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/app/DeletedChannelsPreferenceControllerTest.java
index 5c9de7cb30b..267b8d74616 100644
--- a/tests/robotests/src/com/android/settings/notification/app/DeletedChannelsPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/app/DeletedChannelsPreferenceControllerTest.java
@@ -31,12 +31,17 @@ import android.app.NotificationChannelGroup;
import android.app.NotificationManager;
import android.content.Context;
import android.os.UserManager;
+import android.platform.test.annotations.DisableFlags;
+import android.platform.test.annotations.EnableFlags;
+import android.platform.test.flag.junit.SetFlagsRule;
import androidx.preference.Preference;
+import com.android.server.notification.Flags;
import com.android.settings.notification.NotificationBackend;
import org.junit.Before;
+import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.ArgumentCaptor;
@@ -60,6 +65,8 @@ public class DeletedChannelsPreferenceControllerTest {
private UserManager mUm;
private DeletedChannelsPreferenceController mController;
+ @Rule
+ public final SetFlagsRule mSetFlagsRule = new SetFlagsRule();
@Before
public void setUp() {
@@ -109,6 +116,16 @@ public class DeletedChannelsPreferenceControllerTest {
}
@Test
+ @EnableFlags(Flags.FLAG_NOTIFICATION_HIDE_UNUSED_CHANNELS)
+ public void isAvailable_notIfFlagEnabled() {
+ when(mBackend.getDeletedChannelCount(any(), anyInt())).thenReturn(1);
+ mController.onResume(
+ new NotificationBackend.AppRow(), null, null, null, null, null, new ArrayList<>());
+ assertFalse(mController.isAvailable());
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_NOTIFICATION_HIDE_UNUSED_CHANNELS)
public void isAvailable_appScreen() {
when(mBackend.getDeletedChannelCount(any(), anyInt())).thenReturn(1);
mController.onResume(
diff --git a/tests/robotests/src/com/android/settings/notification/app/ShowMorePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/app/ShowMorePreferenceControllerTest.java
new file mode 100644
index 00000000000..611c80a48f1
--- /dev/null
+++ b/tests/robotests/src/com/android/settings/notification/app/ShowMorePreferenceControllerTest.java
@@ -0,0 +1,113 @@
+/*
+ * Copyright (C) 2024 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.settings.notification.app;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.junit.Assert.assertFalse;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+
+import android.app.NotificationChannelGroup;
+import android.app.NotificationManager;
+import android.content.Context;
+import android.os.UserManager;
+import android.platform.test.annotations.EnableFlags;
+import android.platform.test.flag.junit.SetFlagsRule;
+
+import androidx.preference.Preference;
+
+import com.android.server.notification.Flags;
+import com.android.settings.notification.NotificationBackend;
+
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+import org.robolectric.RobolectricTestRunner;
+import org.robolectric.RuntimeEnvironment;
+import org.robolectric.shadows.ShadowApplication;
+
+@RunWith(RobolectricTestRunner.class)
+@EnableFlags(Flags.FLAG_NOTIFICATION_HIDE_UNUSED_CHANNELS)
+public class ShowMorePreferenceControllerTest {
+
+ private Context mContext;
+ @Mock
+ private NotificationBackend mBackend;
+ @Mock
+ private NotificationManager mNm;
+ @Mock
+ private UserManager mUm;
+ @Mock
+ private NotificationSettings.DependentFieldListener mDependentFieldListener;
+
+ private ShowMorePreferenceController mController;
+ @Rule
+ public final SetFlagsRule mSetFlagsRule = new SetFlagsRule();
+
+ @Before
+ public void setUp() {
+ MockitoAnnotations.initMocks(this);
+ ShadowApplication shadowApplication = ShadowApplication.getInstance();
+ shadowApplication.setSystemService(Context.NOTIFICATION_SERVICE, mNm);
+ shadowApplication.setSystemService(Context.USER_SERVICE, mUm);
+ mContext = RuntimeEnvironment.application;
+ mController = new ShowMorePreferenceController(mContext, mDependentFieldListener, mBackend);
+ }
+
+ @Test
+ public void noCrashIfNoOnResume() {
+ mController.isAvailable();
+ mController.updateState(mock(Preference.class));
+ }
+
+ @Test
+ public void isAvailable_notIfAppBlocked() {
+ NotificationBackend.AppRow appRow = new NotificationBackend.AppRow();
+ appRow.banned = true;
+ appRow.showAllChannels = false;
+ mController.onResume(appRow, null, null, null, null, null, null);
+ assertFalse(mController.isAvailable());
+ }
+
+ @Test
+ public void isAvailable_notIfShowingAll() {
+ NotificationBackend.AppRow appRow = new NotificationBackend.AppRow();
+ mController.onResume(appRow, null, mock(NotificationChannelGroup.class), null, null, null,
+ null);
+ assertFalse(mController.isAvailable());
+ }
+
+ @Test
+ public void updateState() {
+ NotificationBackend.AppRow appRow = new NotificationBackend.AppRow();
+ appRow.banned = false;
+ appRow.showAllChannels = false;
+ mController.onResume(appRow, null, null, null, null, null, null);
+
+ Preference pref = new Preference(mContext);
+ mController.updateState(pref);
+
+ pref.performClick();
+
+ verify(mDependentFieldListener).onFieldValueChanged();
+ assertThat(appRow.showAllChannels).isTrue();
+ }
+}