Loading core/java/com/android/internal/app/ChooserActivity.java +14 −15 Original line number Diff line number Diff line Loading @@ -3023,28 +3023,31 @@ public class ChooserActivity extends ResolverActivity implements return shouldShowTabs() && (mMultiProfilePagerAdapter.getListAdapterForUserHandle( UserHandle.of(UserHandle.myUserId())).getCount() > 0 || shouldShowContentPreviewWhenEmpty()) || shouldShowStickyContentPreviewWhenEmpty()) && shouldShowContentPreview(); } /** * This method could be used to override the default behavior when we hide the preview area * when the current tab doesn't have any items. * This method could be used to override the default behavior when we hide the sticky preview * area when the current tab doesn't have any items. * * @return true if we want to show the content preview area even if the tab for the current * user is empty * @return {@code true} if we want to show the sticky content preview area even if the tab for * the current user is empty */ protected boolean shouldShowContentPreviewWhenEmpty() { protected boolean shouldShowStickyContentPreviewWhenEmpty() { return false; } /** * @return true if we want to show the content preview area */ protected boolean shouldShowContentPreview() { @Override public boolean shouldShowContentPreview() { return isSendAction(getTargetIntent()); } @Override public boolean shouldShowServiceTargets() { return shouldShowContentPreview() && !ActivityManager.isLowRamDeviceStatic(); } private void updateStickyContentPreview() { if (shouldShowStickyContentPreviewNoOrientationCheck()) { // The sticky content preview is only shown when we show the work and personal tabs. Loading Loading @@ -3406,11 +3409,7 @@ public class ChooserActivity extends ResolverActivity implements // There can be at most one row in the listview, that is internally // a ViewGroup with 2 rows public int getServiceTargetRowCount() { if (shouldShowContentPreview() && !ActivityManager.isLowRamDeviceStatic()) { return 1; } return 0; return shouldShowServiceTargets() ? 1 : 0; } public int getAzLabelRowCount() { Loading core/java/com/android/internal/app/ChooserListAdapter.java +5 −4 Original line number Diff line number Diff line Loading @@ -19,7 +19,6 @@ package com.android.internal.app; import static com.android.internal.app.ChooserActivity.TARGET_TYPE_SHORTCUTS_FROM_PREDICTION_SERVICE; import static com.android.internal.app.ChooserActivity.TARGET_TYPE_SHORTCUTS_FROM_SHORTCUT_MANAGER; import android.app.ActivityManager; import android.app.prediction.AppPredictor; import android.content.ComponentName; import android.content.Context; Loading Loading @@ -425,11 +424,9 @@ public class ChooserListAdapter extends ResolverListAdapter { } public int getServiceTargetCount() { if (mChooserListCommunicator.isSendAction(mChooserListCommunicator.getTargetIntent()) && !ActivityManager.isLowRamDeviceStatic()) { if (mChooserListCommunicator.shouldShowServiceTargets()) { return Math.min(mServiceTargets.size(), mChooserListCommunicator.getMaxRankedTargets()); } return 0; } Loading Loading @@ -771,6 +768,10 @@ public class ChooserListAdapter extends ResolverListAdapter { void sendListViewUpdateMessage(UserHandle userHandle); boolean isSendAction(Intent targetIntent); boolean shouldShowContentPreview(); boolean shouldShowServiceTargets(); } /** Loading core/tests/coretests/src/com/android/internal/app/ChooserListAdapterTest.kt +97 −35 Original line number Diff line number Diff line Loading @@ -19,8 +19,12 @@ package com.android.internal.app import android.content.ComponentName import android.content.Context import android.content.Intent import android.content.pm.ActivityInfo import android.content.pm.ApplicationInfo import android.content.pm.PackageManager import android.content.pm.ResolveInfo import android.content.pm.ShortcutInfo import android.graphics.drawable.Icon import android.os.Bundle import android.os.UserHandle import android.service.chooser.ChooserTarget Loading @@ -32,12 +36,15 @@ import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.platform.app.InstrumentationRegistry import com.android.internal.R import com.android.internal.app.ChooserListAdapter.LoadDirectShareIconTask import com.android.internal.app.chooser.DisplayResolveInfo import com.android.internal.app.chooser.SelectableTargetInfo import com.android.internal.app.chooser.SelectableTargetInfo.SelectableTargetInfoCommunicator import com.android.internal.app.chooser.TargetInfo import com.android.server.testutils.any import com.android.server.testutils.mock import com.android.server.testutils.whenever import com.google.common.truth.Truth.assertThat import org.junit.Before import org.junit.Test import org.junit.runner.RunWith import org.mockito.Mockito.anyInt Loading @@ -46,22 +53,25 @@ import org.mockito.Mockito.verify @RunWith(AndroidJUnit4::class) class ChooserListAdapterTest { private val packageManager = mock<PackageManager> { whenever(resolveActivity(any(), anyInt())).thenReturn(mock()) } private val packageManager = mock<PackageManager> { whenever(resolveActivity(any(), anyInt())).thenReturn(mock()) } private val context = InstrumentationRegistry.getInstrumentation().getContext() private val resolverListController = mock<ResolverListController>() private val chooserListCommunicator = mock<ChooserListAdapter.ChooserListCommunicator> { private val chooserListCommunicator = mock<ChooserListAdapter.ChooserListCommunicator> { whenever(maxRankedTargets).thenReturn(0) } private val selectableTargetInfoCommunicator = mock<SelectableTargetInfoCommunicator> { whenever(targetIntent).thenReturn(mock()) } mock<SelectableTargetInfoCommunicator> { whenever(targetIntent).thenReturn(mock()) } private val chooserActivityLogger = mock<ChooserActivityLogger>() @Before fun setUp() { whenever(resolverListController.userHandle).thenReturn(UserHandle.CURRENT) } private fun createChooserListAdapter( taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask = createTaskProvider() ) = ChooserListAdapterOverride( context, Loading Loading @@ -98,9 +108,8 @@ class ChooserListAdapterTest { view.tag = viewHolderOne val targetInfo = createSelectableTargetInfo() val iconTaskOne = mock<LoadDirectShareIconTask>() val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } val testSubject = createChooserListAdapter { testTaskProvider.invoke() } testSubject.testViewBind(view, targetInfo, 0) Loading @@ -114,6 +123,65 @@ class ChooserListAdapterTest { verify(testTaskProvider, times(1)).invoke() } @Test fun getServiceTargetCount_shouldNotShowServiceTargets_returnsZero() { whenever(chooserListCommunicator.shouldShowServiceTargets()).thenReturn(false) val adapter = createChooserListAdapter() whenever(chooserListCommunicator.maxRankedTargets).thenReturn(10) addServiceTargets(adapter, targetCount = 50) assertThat(adapter.serviceTargetCount).isEqualTo(0) } private fun createTaskProvider(): (SelectableTargetInfo?) -> LoadDirectShareIconTask { val iconTaskOne = mock<LoadDirectShareIconTask>() val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } return { testTaskProvider.invoke() } } private fun addServiceTargets(adapter: ChooserListAdapter, targetCount: Int) { val origTarget = DisplayResolveInfo( Intent(), createResolveInfo(), Intent(), ResolverListAdapter.ResolveInfoPresentationGetter(context, 200, createResolveInfo()) ) val targets = mutableListOf<ChooserTarget>() for (i in 1..targetCount) { val score = 1f val componentName = ComponentName("chooser.list.adapter", "Test$i") val extras = Bundle() val icon: Icon? = null targets += ChooserTarget("Title $i", icon, score, componentName, extras) } val directShareToShortcutInfos = mapOf<ChooserTarget, ShortcutInfo>() adapter.addServiceResults( origTarget, targets, ChooserActivity.TARGET_TYPE_DEFAULT, directShareToShortcutInfos ) } private fun createResolveInfo(): ResolveInfo { val applicationInfo = ApplicationInfo().apply { packageName = "chooser.list.adapter" name = "ChooserListAdapterTestApplication" } val activityInfo = ActivityInfo().apply { packageName = applicationInfo.packageName name = "ChooserListAdapterTest" } activityInfo.applicationInfo = applicationInfo val resolveInfo = ResolveInfo() resolveInfo.activityInfo = activityInfo return resolveInfo } private fun createSelectableTargetInfo(): SelectableTargetInfo = SelectableTargetInfo( context, Loading @@ -125,13 +193,7 @@ class ChooserListAdapterTest { ) private fun createChooserTarget(): ChooserTarget = ChooserTarget( "Title", null, 1f, ComponentName("package", "package.Class"), Bundle() ) ChooserTarget("Title", null, 1f, ComponentName("package", "package.Class"), Bundle()) private fun createView(): View { val view = FrameLayout(context) Loading Loading @@ -164,7 +226,8 @@ private class ChooserListAdapterOverride( chooserActivityLogger: ChooserActivityLogger?, initialIntentsUserHandle: UserHandle?, private val taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask ) : ChooserListAdapter( ) : ChooserListAdapter( context, payloadIntents, initialIntents, Loading @@ -179,8 +242,7 @@ private class ChooserListAdapterOverride( ) { override fun createLoadDirectShareIconTask( info: SelectableTargetInfo? ): LoadDirectShareIconTask = taskProvider.invoke(info) ): LoadDirectShareIconTask = taskProvider.invoke(info) fun testViewBind(view: View?, info: TargetInfo?, position: Int) { onBindView(view, info, position) Loading packages/SystemUI/src/com/android/systemui/media/MediaProjectionAppSelectorActivity.kt +3 −1 Original line number Diff line number Diff line Loading @@ -274,7 +274,9 @@ class MediaProjectionAppSelectorActivity( recentsViewController.hasRecentTasks } override fun shouldShowContentPreviewWhenEmpty() = shouldShowContentPreview() override fun shouldShowStickyContentPreviewWhenEmpty() = shouldShowContentPreview() override fun shouldShowServiceTargets() = false private fun hasWorkProfile() = mMultiProfilePagerAdapter.count > 1 Loading Loading
core/java/com/android/internal/app/ChooserActivity.java +14 −15 Original line number Diff line number Diff line Loading @@ -3023,28 +3023,31 @@ public class ChooserActivity extends ResolverActivity implements return shouldShowTabs() && (mMultiProfilePagerAdapter.getListAdapterForUserHandle( UserHandle.of(UserHandle.myUserId())).getCount() > 0 || shouldShowContentPreviewWhenEmpty()) || shouldShowStickyContentPreviewWhenEmpty()) && shouldShowContentPreview(); } /** * This method could be used to override the default behavior when we hide the preview area * when the current tab doesn't have any items. * This method could be used to override the default behavior when we hide the sticky preview * area when the current tab doesn't have any items. * * @return true if we want to show the content preview area even if the tab for the current * user is empty * @return {@code true} if we want to show the sticky content preview area even if the tab for * the current user is empty */ protected boolean shouldShowContentPreviewWhenEmpty() { protected boolean shouldShowStickyContentPreviewWhenEmpty() { return false; } /** * @return true if we want to show the content preview area */ protected boolean shouldShowContentPreview() { @Override public boolean shouldShowContentPreview() { return isSendAction(getTargetIntent()); } @Override public boolean shouldShowServiceTargets() { return shouldShowContentPreview() && !ActivityManager.isLowRamDeviceStatic(); } private void updateStickyContentPreview() { if (shouldShowStickyContentPreviewNoOrientationCheck()) { // The sticky content preview is only shown when we show the work and personal tabs. Loading Loading @@ -3406,11 +3409,7 @@ public class ChooserActivity extends ResolverActivity implements // There can be at most one row in the listview, that is internally // a ViewGroup with 2 rows public int getServiceTargetRowCount() { if (shouldShowContentPreview() && !ActivityManager.isLowRamDeviceStatic()) { return 1; } return 0; return shouldShowServiceTargets() ? 1 : 0; } public int getAzLabelRowCount() { Loading
core/java/com/android/internal/app/ChooserListAdapter.java +5 −4 Original line number Diff line number Diff line Loading @@ -19,7 +19,6 @@ package com.android.internal.app; import static com.android.internal.app.ChooserActivity.TARGET_TYPE_SHORTCUTS_FROM_PREDICTION_SERVICE; import static com.android.internal.app.ChooserActivity.TARGET_TYPE_SHORTCUTS_FROM_SHORTCUT_MANAGER; import android.app.ActivityManager; import android.app.prediction.AppPredictor; import android.content.ComponentName; import android.content.Context; Loading Loading @@ -425,11 +424,9 @@ public class ChooserListAdapter extends ResolverListAdapter { } public int getServiceTargetCount() { if (mChooserListCommunicator.isSendAction(mChooserListCommunicator.getTargetIntent()) && !ActivityManager.isLowRamDeviceStatic()) { if (mChooserListCommunicator.shouldShowServiceTargets()) { return Math.min(mServiceTargets.size(), mChooserListCommunicator.getMaxRankedTargets()); } return 0; } Loading Loading @@ -771,6 +768,10 @@ public class ChooserListAdapter extends ResolverListAdapter { void sendListViewUpdateMessage(UserHandle userHandle); boolean isSendAction(Intent targetIntent); boolean shouldShowContentPreview(); boolean shouldShowServiceTargets(); } /** Loading
core/tests/coretests/src/com/android/internal/app/ChooserListAdapterTest.kt +97 −35 Original line number Diff line number Diff line Loading @@ -19,8 +19,12 @@ package com.android.internal.app import android.content.ComponentName import android.content.Context import android.content.Intent import android.content.pm.ActivityInfo import android.content.pm.ApplicationInfo import android.content.pm.PackageManager import android.content.pm.ResolveInfo import android.content.pm.ShortcutInfo import android.graphics.drawable.Icon import android.os.Bundle import android.os.UserHandle import android.service.chooser.ChooserTarget Loading @@ -32,12 +36,15 @@ import androidx.test.ext.junit.runners.AndroidJUnit4 import androidx.test.platform.app.InstrumentationRegistry import com.android.internal.R import com.android.internal.app.ChooserListAdapter.LoadDirectShareIconTask import com.android.internal.app.chooser.DisplayResolveInfo import com.android.internal.app.chooser.SelectableTargetInfo import com.android.internal.app.chooser.SelectableTargetInfo.SelectableTargetInfoCommunicator import com.android.internal.app.chooser.TargetInfo import com.android.server.testutils.any import com.android.server.testutils.mock import com.android.server.testutils.whenever import com.google.common.truth.Truth.assertThat import org.junit.Before import org.junit.Test import org.junit.runner.RunWith import org.mockito.Mockito.anyInt Loading @@ -46,22 +53,25 @@ import org.mockito.Mockito.verify @RunWith(AndroidJUnit4::class) class ChooserListAdapterTest { private val packageManager = mock<PackageManager> { whenever(resolveActivity(any(), anyInt())).thenReturn(mock()) } private val packageManager = mock<PackageManager> { whenever(resolveActivity(any(), anyInt())).thenReturn(mock()) } private val context = InstrumentationRegistry.getInstrumentation().getContext() private val resolverListController = mock<ResolverListController>() private val chooserListCommunicator = mock<ChooserListAdapter.ChooserListCommunicator> { private val chooserListCommunicator = mock<ChooserListAdapter.ChooserListCommunicator> { whenever(maxRankedTargets).thenReturn(0) } private val selectableTargetInfoCommunicator = mock<SelectableTargetInfoCommunicator> { whenever(targetIntent).thenReturn(mock()) } mock<SelectableTargetInfoCommunicator> { whenever(targetIntent).thenReturn(mock()) } private val chooserActivityLogger = mock<ChooserActivityLogger>() @Before fun setUp() { whenever(resolverListController.userHandle).thenReturn(UserHandle.CURRENT) } private fun createChooserListAdapter( taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask = createTaskProvider() ) = ChooserListAdapterOverride( context, Loading Loading @@ -98,9 +108,8 @@ class ChooserListAdapterTest { view.tag = viewHolderOne val targetInfo = createSelectableTargetInfo() val iconTaskOne = mock<LoadDirectShareIconTask>() val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } val testSubject = createChooserListAdapter { testTaskProvider.invoke() } testSubject.testViewBind(view, targetInfo, 0) Loading @@ -114,6 +123,65 @@ class ChooserListAdapterTest { verify(testTaskProvider, times(1)).invoke() } @Test fun getServiceTargetCount_shouldNotShowServiceTargets_returnsZero() { whenever(chooserListCommunicator.shouldShowServiceTargets()).thenReturn(false) val adapter = createChooserListAdapter() whenever(chooserListCommunicator.maxRankedTargets).thenReturn(10) addServiceTargets(adapter, targetCount = 50) assertThat(adapter.serviceTargetCount).isEqualTo(0) } private fun createTaskProvider(): (SelectableTargetInfo?) -> LoadDirectShareIconTask { val iconTaskOne = mock<LoadDirectShareIconTask>() val testTaskProvider = mock<() -> LoadDirectShareIconTask> { whenever(invoke()).thenReturn(iconTaskOne) } return { testTaskProvider.invoke() } } private fun addServiceTargets(adapter: ChooserListAdapter, targetCount: Int) { val origTarget = DisplayResolveInfo( Intent(), createResolveInfo(), Intent(), ResolverListAdapter.ResolveInfoPresentationGetter(context, 200, createResolveInfo()) ) val targets = mutableListOf<ChooserTarget>() for (i in 1..targetCount) { val score = 1f val componentName = ComponentName("chooser.list.adapter", "Test$i") val extras = Bundle() val icon: Icon? = null targets += ChooserTarget("Title $i", icon, score, componentName, extras) } val directShareToShortcutInfos = mapOf<ChooserTarget, ShortcutInfo>() adapter.addServiceResults( origTarget, targets, ChooserActivity.TARGET_TYPE_DEFAULT, directShareToShortcutInfos ) } private fun createResolveInfo(): ResolveInfo { val applicationInfo = ApplicationInfo().apply { packageName = "chooser.list.adapter" name = "ChooserListAdapterTestApplication" } val activityInfo = ActivityInfo().apply { packageName = applicationInfo.packageName name = "ChooserListAdapterTest" } activityInfo.applicationInfo = applicationInfo val resolveInfo = ResolveInfo() resolveInfo.activityInfo = activityInfo return resolveInfo } private fun createSelectableTargetInfo(): SelectableTargetInfo = SelectableTargetInfo( context, Loading @@ -125,13 +193,7 @@ class ChooserListAdapterTest { ) private fun createChooserTarget(): ChooserTarget = ChooserTarget( "Title", null, 1f, ComponentName("package", "package.Class"), Bundle() ) ChooserTarget("Title", null, 1f, ComponentName("package", "package.Class"), Bundle()) private fun createView(): View { val view = FrameLayout(context) Loading Loading @@ -164,7 +226,8 @@ private class ChooserListAdapterOverride( chooserActivityLogger: ChooserActivityLogger?, initialIntentsUserHandle: UserHandle?, private val taskProvider: (SelectableTargetInfo?) -> LoadDirectShareIconTask ) : ChooserListAdapter( ) : ChooserListAdapter( context, payloadIntents, initialIntents, Loading @@ -179,8 +242,7 @@ private class ChooserListAdapterOverride( ) { override fun createLoadDirectShareIconTask( info: SelectableTargetInfo? ): LoadDirectShareIconTask = taskProvider.invoke(info) ): LoadDirectShareIconTask = taskProvider.invoke(info) fun testViewBind(view: View?, info: TargetInfo?, position: Int) { onBindView(view, info, position) Loading
packages/SystemUI/src/com/android/systemui/media/MediaProjectionAppSelectorActivity.kt +3 −1 Original line number Diff line number Diff line Loading @@ -274,7 +274,9 @@ class MediaProjectionAppSelectorActivity( recentsViewController.hasRecentTasks } override fun shouldShowContentPreviewWhenEmpty() = shouldShowContentPreview() override fun shouldShowStickyContentPreviewWhenEmpty() = shouldShowContentPreview() override fun shouldShowServiceTargets() = false private fun hasWorkProfile() = mMultiProfilePagerAdapter.count > 1 Loading