[Media TTT] Refactor the command line interface into its own class and
use sealed classes for the chip states. The sealed class doesn't do anything in this CL, but it will become useful in future CLs. Sample command: adb shell cmd statusbar media-ttt-chip-add Tablet TransferInitiated Bug: 203800327 Test: MediaTttCommandLineHelperTest, MediaTttChipControllerTest Test: Re-tested adb commands and they still trigger the correct UIs Change-Id: Iffd53c5648dac0307d282158122365613fb7b653
This commit is contained in:
@@ -24,6 +24,7 @@ import com.android.systemui.SystemUIAppComponentFactory;
|
||||
import com.android.systemui.dump.DumpManager;
|
||||
import com.android.systemui.keyguard.KeyguardSliceProvider;
|
||||
import com.android.systemui.media.taptotransfer.MediaTttChipController;
|
||||
import com.android.systemui.media.taptotransfer.MediaTttCommandLineHelper;
|
||||
import com.android.systemui.people.PeopleProvider;
|
||||
import com.android.systemui.statusbar.policy.ConfigurationController;
|
||||
import com.android.systemui.unfold.SysUIUnfoldComponent;
|
||||
@@ -133,6 +134,7 @@ public interface SysUIComponent {
|
||||
getNaturalRotationUnfoldProgressProvider().ifPresent(o -> o.init());
|
||||
// No init method needed, just needs to be gotten so that it's created.
|
||||
getMediaTttChipController();
|
||||
getMediaTttCommandLineHelper();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -182,6 +184,9 @@ public interface SysUIComponent {
|
||||
/** */
|
||||
Optional<MediaTttChipController> getMediaTttChipController();
|
||||
|
||||
/** */
|
||||
Optional<MediaTttCommandLineHelper> getMediaTttCommandLineHelper();
|
||||
|
||||
/**
|
||||
* Member injection into the supplied argument.
|
||||
*/
|
||||
|
||||
@@ -25,6 +25,7 @@ import com.android.systemui.media.MediaHierarchyManager;
|
||||
import com.android.systemui.media.MediaHost;
|
||||
import com.android.systemui.media.MediaHostStatesManager;
|
||||
import com.android.systemui.media.taptotransfer.MediaTttChipController;
|
||||
import com.android.systemui.media.taptotransfer.MediaTttCommandLineHelper;
|
||||
import com.android.systemui.media.taptotransfer.MediaTttFlags;
|
||||
import com.android.systemui.statusbar.commandline.CommandRegistry;
|
||||
|
||||
@@ -78,11 +79,23 @@ public interface MediaModule {
|
||||
static Optional<MediaTttChipController> providesMediaTttChipController(
|
||||
MediaTttFlags mediaTttFlags,
|
||||
Context context,
|
||||
CommandRegistry commandRegistry,
|
||||
WindowManager windowManager) {
|
||||
if (!mediaTttFlags.isMediaTttEnabled()) {
|
||||
return Optional.empty();
|
||||
}
|
||||
return Optional.of(new MediaTttChipController(commandRegistry, context, windowManager));
|
||||
return Optional.of(new MediaTttChipController(context, windowManager));
|
||||
}
|
||||
|
||||
/** */
|
||||
@Provides
|
||||
@SysUISingleton
|
||||
static Optional<MediaTttCommandLineHelper> providesMediaTttCommandLineHelper(
|
||||
MediaTttFlags mediaTttFlags,
|
||||
CommandRegistry commandRegistry,
|
||||
MediaTttChipController mediaTttChipController) {
|
||||
if (!mediaTttFlags.isMediaTttEnabled()) {
|
||||
return Optional.empty();
|
||||
}
|
||||
return Optional.of(new MediaTttCommandLineHelper(commandRegistry, mediaTttChipController));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,13 +24,8 @@ import android.view.View
|
||||
import android.view.WindowManager
|
||||
import android.widget.LinearLayout
|
||||
import android.widget.TextView
|
||||
import androidx.annotation.StringRes
|
||||
import androidx.annotation.VisibleForTesting
|
||||
import com.android.systemui.R
|
||||
import com.android.systemui.dagger.SysUISingleton
|
||||
import com.android.systemui.statusbar.commandline.Command
|
||||
import com.android.systemui.statusbar.commandline.CommandRegistry
|
||||
import java.io.PrintWriter
|
||||
import javax.inject.Inject
|
||||
|
||||
/**
|
||||
@@ -41,14 +36,9 @@ import javax.inject.Inject
|
||||
*/
|
||||
@SysUISingleton
|
||||
class MediaTttChipController @Inject constructor(
|
||||
commandRegistry: CommandRegistry,
|
||||
private val context: Context,
|
||||
private val windowManager: WindowManager,
|
||||
) {
|
||||
init {
|
||||
commandRegistry.registerCommand(ADD_CHIP_COMMAND_TAG) { AddChipCommand() }
|
||||
commandRegistry.registerCommand(REMOVE_CHIP_COMMAND_TAG) { RemoveChipCommand() }
|
||||
}
|
||||
|
||||
private val windowLayoutParams = WindowManager.LayoutParams().apply {
|
||||
width = WindowManager.LayoutParams.WRAP_CONTENT
|
||||
@@ -65,7 +55,8 @@ class MediaTttChipController @Inject constructor(
|
||||
/** The chip view currently being displayed. Null if the chip is not being displayed. */
|
||||
private var chipView: LinearLayout? = null
|
||||
|
||||
private fun displayChip(chipType: ChipType, otherDeviceName: String) {
|
||||
/** Displays the chip view for the given state. */
|
||||
fun displayChip(chipState: MediaTttChipState) {
|
||||
val oldChipView = chipView
|
||||
if (chipView == null) {
|
||||
chipView = LayoutInflater
|
||||
@@ -76,16 +67,16 @@ class MediaTttChipController @Inject constructor(
|
||||
|
||||
// Text
|
||||
currentChipView.requireViewById<TextView>(R.id.text).apply {
|
||||
text = context.getString(chipType.chipText, otherDeviceName)
|
||||
text = context.getString(chipState.chipText, chipState.otherDeviceName)
|
||||
}
|
||||
|
||||
// Loading
|
||||
val showLoading = chipType == ChipType.TRANSFER_INITIATED
|
||||
val showLoading = chipState is TransferInitiated
|
||||
currentChipView.requireViewById<View>(R.id.loading).visibility =
|
||||
if (showLoading) { View.VISIBLE } else { View.GONE }
|
||||
|
||||
// Undo
|
||||
val showUndo = chipType == ChipType.TRANSFER_SUCCEEDED
|
||||
val showUndo = chipState is TransferSucceeded
|
||||
currentChipView.requireViewById<View>(R.id.undo).visibility =
|
||||
if (showUndo) { View.VISIBLE } else { View.GONE }
|
||||
|
||||
@@ -94,53 +85,10 @@ class MediaTttChipController @Inject constructor(
|
||||
}
|
||||
}
|
||||
|
||||
private fun removeChip() {
|
||||
/** Hides the chip. */
|
||||
fun removeChip() {
|
||||
if (chipView == null) { return }
|
||||
windowManager.removeView(chipView)
|
||||
chipView = null
|
||||
}
|
||||
|
||||
@VisibleForTesting
|
||||
enum class ChipType(
|
||||
@StringRes internal val chipText: Int
|
||||
) {
|
||||
MOVE_CLOSER_TO_TRANSFER(R.string.media_move_closer_to_transfer),
|
||||
TRANSFER_INITIATED(R.string.media_transfer_playing),
|
||||
TRANSFER_SUCCEEDED(R.string.media_transfer_playing),
|
||||
}
|
||||
|
||||
inner class AddChipCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) {
|
||||
val chipTypeArg = args[1]
|
||||
ChipType.values().forEach {
|
||||
if (it.name == chipTypeArg) {
|
||||
displayChip(it, otherDeviceName = args[0])
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
pw.println("Chip type must be one of " +
|
||||
ChipType.values().map { it.name }.reduce { acc, s -> "$acc, $s" })
|
||||
}
|
||||
|
||||
override fun help(pw: PrintWriter) {
|
||||
pw.println(
|
||||
"Usage: adb shell cmd statusbar $ADD_CHIP_COMMAND_TAG <deviceName> <chipType>"
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
inner class RemoveChipCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) = removeChip()
|
||||
override fun help(pw: PrintWriter) {
|
||||
pw.println("Usage: adb shell cmd statusbar $REMOVE_CHIP_COMMAND_TAG")
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
@VisibleForTesting
|
||||
const val ADD_CHIP_COMMAND_TAG = "media-ttt-chip-add"
|
||||
@VisibleForTesting
|
||||
const val REMOVE_CHIP_COMMAND_TAG = "media-ttt-chip-remove"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* 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.media.taptotransfer
|
||||
|
||||
import androidx.annotation.StringRes
|
||||
import com.android.systemui.R
|
||||
|
||||
/**
|
||||
* A class that stores all the information necessary to display the media tap-to-transfer chip in
|
||||
* certain states.
|
||||
*
|
||||
* This is a sealed class where each subclass represents a specific chip state. Each subclass can
|
||||
* contain additional information that is necessary for only that state.
|
||||
*/
|
||||
sealed class MediaTttChipState(
|
||||
/** A string resource for the text that the chip should display. */
|
||||
@StringRes internal val chipText: Int,
|
||||
/** The name of the other device involved in the transfer. */
|
||||
internal val otherDeviceName: String
|
||||
)
|
||||
|
||||
/**
|
||||
* A state representing that the two devices are close but not close enough to initiate a transfer.
|
||||
* The chip will instruct the user to move closer in order to initiate the transfer.
|
||||
*/
|
||||
class MoveCloserToTransfer(
|
||||
otherDeviceName: String
|
||||
) : MediaTttChipState(R.string.media_move_closer_to_transfer, otherDeviceName)
|
||||
|
||||
/**
|
||||
* A state representing that a transfer has been initiated (but not completed).
|
||||
*/
|
||||
class TransferInitiated(
|
||||
otherDeviceName: String
|
||||
) : MediaTttChipState(R.string.media_transfer_playing, otherDeviceName)
|
||||
|
||||
/**
|
||||
* A state representing that a transfer has been successfully completed.
|
||||
*/
|
||||
class TransferSucceeded(
|
||||
otherDeviceName: String
|
||||
) : MediaTttChipState(R.string.media_transfer_playing, otherDeviceName)
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* 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.media.taptotransfer
|
||||
|
||||
import androidx.annotation.VisibleForTesting
|
||||
import com.android.systemui.dagger.SysUISingleton
|
||||
import com.android.systemui.statusbar.commandline.Command
|
||||
import com.android.systemui.statusbar.commandline.CommandRegistry
|
||||
import java.io.PrintWriter
|
||||
import javax.inject.Inject
|
||||
|
||||
/**
|
||||
* A helper class to test the media tap-to-transfer chip via the command line. See inner classes for
|
||||
* command usages.
|
||||
*/
|
||||
@SysUISingleton
|
||||
class MediaTttCommandLineHelper @Inject constructor(
|
||||
commandRegistry: CommandRegistry,
|
||||
private val mediaTttChipController: MediaTttChipController
|
||||
) {
|
||||
init {
|
||||
commandRegistry.registerCommand(ADD_CHIP_COMMAND_TAG) { AddChipCommand() }
|
||||
commandRegistry.registerCommand(REMOVE_CHIP_COMMAND_TAG) { RemoveChipCommand() }
|
||||
}
|
||||
|
||||
inner class AddChipCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) {
|
||||
val otherDeviceName = args[0]
|
||||
when (args[1]) {
|
||||
MOVE_CLOSER_TO_TRANSFER_COMMAND_NAME -> {
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(otherDeviceName))
|
||||
}
|
||||
TRANSFER_INITIATED_COMMAND_NAME -> {
|
||||
mediaTttChipController.displayChip(TransferInitiated(otherDeviceName))
|
||||
}
|
||||
TRANSFER_SUCCEEDED_COMMAND_NAME -> {
|
||||
mediaTttChipController.displayChip(TransferSucceeded(otherDeviceName))
|
||||
}
|
||||
else -> {
|
||||
pw.println("Chip type must be one of " +
|
||||
"$MOVE_CLOSER_TO_TRANSFER_COMMAND_NAME, " +
|
||||
"$TRANSFER_INITIATED_COMMAND_NAME, " +
|
||||
TRANSFER_SUCCEEDED_COMMAND_NAME
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun help(pw: PrintWriter) {
|
||||
pw.println(
|
||||
"Usage: adb shell cmd statusbar $ADD_CHIP_COMMAND_TAG <deviceName> <chipStatus>"
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
inner class RemoveChipCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) {
|
||||
mediaTttChipController.removeChip()
|
||||
}
|
||||
override fun help(pw: PrintWriter) {
|
||||
pw.println("Usage: adb shell cmd statusbar $REMOVE_CHIP_COMMAND_TAG")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@VisibleForTesting
|
||||
const val ADD_CHIP_COMMAND_TAG = "media-ttt-chip-add"
|
||||
@VisibleForTesting
|
||||
const val REMOVE_CHIP_COMMAND_TAG = "media-ttt-chip-remove"
|
||||
@VisibleForTesting
|
||||
val MOVE_CLOSER_TO_TRANSFER_COMMAND_NAME = MoveCloserToTransfer::class.simpleName!!
|
||||
@VisibleForTesting
|
||||
val TRANSFER_INITIATED_COMMAND_NAME = TransferInitiated::class.simpleName!!
|
||||
@VisibleForTesting
|
||||
val TRANSFER_SUCCEEDED_COMMAND_NAME = TransferSucceeded::class.simpleName!!
|
||||
@@ -23,8 +23,6 @@ import android.widget.TextView
|
||||
import androidx.test.filters.SmallTest
|
||||
import com.android.systemui.R
|
||||
import com.android.systemui.SysuiTestCase
|
||||
import com.android.systemui.statusbar.commandline.Command
|
||||
import com.android.systemui.statusbar.commandline.CommandRegistry
|
||||
import com.android.systemui.util.mockito.any
|
||||
import com.google.common.truth.Truth.assertThat
|
||||
import org.junit.Before
|
||||
@@ -35,83 +33,58 @@ import org.mockito.Mockito.never
|
||||
import org.mockito.Mockito.reset
|
||||
import org.mockito.Mockito.verify
|
||||
import org.mockito.MockitoAnnotations
|
||||
import java.io.PrintWriter
|
||||
import java.io.StringWriter
|
||||
import java.util.concurrent.Executor
|
||||
|
||||
@SmallTest
|
||||
class MediaTttChipControllerTest : SysuiTestCase() {
|
||||
|
||||
private lateinit var mediaTttChipController: MediaTttChipController
|
||||
|
||||
private val inlineExecutor = Executor { command -> command.run() }
|
||||
private val commandRegistry = CommandRegistry(context, inlineExecutor)
|
||||
private val pw = PrintWriter(StringWriter())
|
||||
|
||||
@Mock
|
||||
private lateinit var windowManager: WindowManager
|
||||
|
||||
@Before
|
||||
fun setUp() {
|
||||
MockitoAnnotations.initMocks(this)
|
||||
mediaTttChipController = MediaTttChipController(commandRegistry, context, windowManager)
|
||||
}
|
||||
|
||||
@Test(expected = IllegalStateException::class)
|
||||
fun constructor_addCommmandAlreadyRegistered() {
|
||||
// Since creating the chip controller should automatically register the add command, it
|
||||
// should throw when registering it again.
|
||||
commandRegistry.registerCommand(
|
||||
MediaTttChipController.ADD_CHIP_COMMAND_TAG
|
||||
) { EmptyCommand() }
|
||||
}
|
||||
|
||||
@Test(expected = IllegalStateException::class)
|
||||
fun constructor_removeCommmandAlreadyRegistered() {
|
||||
// Since creating the chip controller should automatically register the remove command, it
|
||||
// should throw when registering it again.
|
||||
commandRegistry.registerCommand(
|
||||
MediaTttChipController.REMOVE_CHIP_COMMAND_TAG
|
||||
) { EmptyCommand() }
|
||||
mediaTttChipController = MediaTttChipController(context, windowManager)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun addChipCommand_chipAdded() {
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
fun displayChip_chipAdded() {
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
|
||||
verify(windowManager).addView(any(), any())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun addChipCommand_twice_chipNotAddedTwice() {
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
fun displayChip_twice_chipNotAddedTwice() {
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
reset(windowManager)
|
||||
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
verify(windowManager, never()).addView(any(), any())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun removeChipCommand_chipRemoved() {
|
||||
fun removeChip_chipRemoved() {
|
||||
// First, add the chip
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
|
||||
// Then, remove it
|
||||
commandRegistry.onShellCommand(pw, arrayOf(MediaTttChipController.REMOVE_CHIP_COMMAND_TAG))
|
||||
mediaTttChipController.removeChip()
|
||||
|
||||
verify(windowManager).removeView(any())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun removeChipCommand_noAdd_viewNotRemoved() {
|
||||
commandRegistry.onShellCommand(pw, arrayOf(MediaTttChipController.REMOVE_CHIP_COMMAND_TAG))
|
||||
fun removeChip_noAdd_viewNotRemoved() {
|
||||
mediaTttChipController.removeChip()
|
||||
|
||||
verify(windowManager, never()).removeView(any())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun moveCloserToTransfer_chipTextContainsDeviceName_noLoadingIcon_noUndo() {
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
|
||||
val chipView = getChipView()
|
||||
assertThat(chipView.getChipText()).contains(DEVICE_NAME)
|
||||
@@ -121,7 +94,7 @@ class MediaTttChipControllerTest : SysuiTestCase() {
|
||||
|
||||
@Test
|
||||
fun transferInitiated_chipTextContainsDeviceName_loadingIcon_noUndo() {
|
||||
commandRegistry.onShellCommand(pw, getTransferInitiatedCommand())
|
||||
mediaTttChipController.displayChip(TransferInitiated(DEVICE_NAME))
|
||||
|
||||
val chipView = getChipView()
|
||||
assertThat(chipView.getChipText()).contains(DEVICE_NAME)
|
||||
@@ -131,7 +104,7 @@ class MediaTttChipControllerTest : SysuiTestCase() {
|
||||
|
||||
@Test
|
||||
fun transferSucceeded_chipTextContainsDeviceName_noLoadingIcon_undo() {
|
||||
commandRegistry.onShellCommand(pw, getTransferSucceededCommand())
|
||||
mediaTttChipController.displayChip(TransferSucceeded(DEVICE_NAME))
|
||||
|
||||
val chipView = getChipView()
|
||||
assertThat(chipView.getChipText()).contains(DEVICE_NAME)
|
||||
@@ -141,57 +114,36 @@ class MediaTttChipControllerTest : SysuiTestCase() {
|
||||
|
||||
@Test
|
||||
fun changeFromCloserToTransferToTransferInitiated_loadingIconAppears() {
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
commandRegistry.onShellCommand(pw, getTransferInitiatedCommand())
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
mediaTttChipController.displayChip(TransferInitiated(DEVICE_NAME))
|
||||
|
||||
assertThat(getChipView().getLoadingIconVisibility()).isEqualTo(View.VISIBLE)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun changeFromTransferInitiatedToTransferSucceeded_loadingIconDisappears() {
|
||||
commandRegistry.onShellCommand(pw, getTransferInitiatedCommand())
|
||||
commandRegistry.onShellCommand(pw, getTransferSucceededCommand())
|
||||
mediaTttChipController.displayChip(TransferInitiated(DEVICE_NAME))
|
||||
mediaTttChipController.displayChip(TransferSucceeded(DEVICE_NAME))
|
||||
|
||||
assertThat(getChipView().getLoadingIconVisibility()).isEqualTo(View.GONE)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun changeFromTransferInitiatedToTransferSucceeded_undoButtonAppears() {
|
||||
commandRegistry.onShellCommand(pw, getTransferInitiatedCommand())
|
||||
commandRegistry.onShellCommand(pw, getTransferSucceededCommand())
|
||||
mediaTttChipController.displayChip(TransferInitiated(DEVICE_NAME))
|
||||
mediaTttChipController.displayChip(TransferSucceeded(DEVICE_NAME))
|
||||
|
||||
assertThat(getChipView().getUndoButtonVisibility()).isEqualTo(View.VISIBLE)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun changeFromTransferSucceededToMoveCloser_undoButtonDisappears() {
|
||||
commandRegistry.onShellCommand(pw, getTransferSucceededCommand())
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
mediaTttChipController.displayChip(TransferSucceeded(DEVICE_NAME))
|
||||
mediaTttChipController.displayChip(MoveCloserToTransfer(DEVICE_NAME))
|
||||
|
||||
assertThat(getChipView().getUndoButtonVisibility()).isEqualTo(View.GONE)
|
||||
}
|
||||
|
||||
private fun getMoveCloserToTransferCommand(): Array<String> =
|
||||
arrayOf(
|
||||
MediaTttChipController.ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
MediaTttChipController.ChipType.MOVE_CLOSER_TO_TRANSFER.name
|
||||
)
|
||||
|
||||
private fun getTransferInitiatedCommand(): Array<String> =
|
||||
arrayOf(
|
||||
MediaTttChipController.ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
MediaTttChipController.ChipType.TRANSFER_INITIATED.name
|
||||
)
|
||||
|
||||
private fun getTransferSucceededCommand(): Array<String> =
|
||||
arrayOf(
|
||||
MediaTttChipController.ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
MediaTttChipController.ChipType.TRANSFER_SUCCEEDED.name
|
||||
)
|
||||
|
||||
private fun LinearLayout.getChipText(): String =
|
||||
(this.requireViewById<TextView>(R.id.text)).text as String
|
||||
|
||||
@@ -206,14 +158,6 @@ class MediaTttChipControllerTest : SysuiTestCase() {
|
||||
verify(windowManager).addView(viewCaptor.capture(), any())
|
||||
return viewCaptor.value as LinearLayout
|
||||
}
|
||||
|
||||
class EmptyCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) {
|
||||
}
|
||||
|
||||
override fun help(pw: PrintWriter) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private const val DEVICE_NAME = "My Tablet"
|
||||
|
||||
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* 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.media.taptotransfer
|
||||
|
||||
import androidx.test.filters.SmallTest
|
||||
import com.android.systemui.SysuiTestCase
|
||||
import com.android.systemui.statusbar.commandline.Command
|
||||
import com.android.systemui.statusbar.commandline.CommandRegistry
|
||||
import com.android.systemui.util.mockito.any
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
import org.mockito.Mock
|
||||
import org.mockito.Mockito.verify
|
||||
import org.mockito.MockitoAnnotations
|
||||
import java.io.PrintWriter
|
||||
import java.io.StringWriter
|
||||
import java.util.concurrent.Executor
|
||||
|
||||
@SmallTest
|
||||
class MediaTttCommandLineHelperTest : SysuiTestCase() {
|
||||
|
||||
private val inlineExecutor = Executor { command -> command.run() }
|
||||
private val commandRegistry = CommandRegistry(context, inlineExecutor)
|
||||
private val pw = PrintWriter(StringWriter())
|
||||
|
||||
private lateinit var mediaTttCommandLineHelper: MediaTttCommandLineHelper
|
||||
|
||||
@Mock
|
||||
private lateinit var mediaTttChipController: MediaTttChipController
|
||||
|
||||
@Before
|
||||
fun setUp() {
|
||||
MockitoAnnotations.initMocks(this)
|
||||
mediaTttCommandLineHelper =
|
||||
MediaTttCommandLineHelper(commandRegistry, mediaTttChipController)
|
||||
}
|
||||
|
||||
@Test(expected = IllegalStateException::class)
|
||||
fun constructor_addCommandAlreadyRegistered() {
|
||||
// Since creating the chip controller should automatically register the add command, it
|
||||
// should throw when registering it again.
|
||||
commandRegistry.registerCommand(
|
||||
ADD_CHIP_COMMAND_TAG
|
||||
) { EmptyCommand() }
|
||||
}
|
||||
|
||||
@Test(expected = IllegalStateException::class)
|
||||
fun constructor_removeCommandAlreadyRegistered() {
|
||||
// Since creating the chip controller should automatically register the remove command, it
|
||||
// should throw when registering it again.
|
||||
commandRegistry.registerCommand(
|
||||
REMOVE_CHIP_COMMAND_TAG
|
||||
) { EmptyCommand() }
|
||||
}
|
||||
|
||||
@Test
|
||||
fun moveCloserToTransfer_chipDisplayWithCorrectState() {
|
||||
commandRegistry.onShellCommand(pw, getMoveCloserToTransferCommand())
|
||||
|
||||
verify(mediaTttChipController).displayChip(any(MoveCloserToTransfer::class.java))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun transferInitiated_chipDisplayWithCorrectState() {
|
||||
commandRegistry.onShellCommand(pw, getTransferInitiatedCommand())
|
||||
|
||||
verify(mediaTttChipController).displayChip(any(TransferInitiated::class.java))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun transferSucceeded_chipDisplayWithCorrectState() {
|
||||
commandRegistry.onShellCommand(pw, getTransferSucceededCommand())
|
||||
|
||||
verify(mediaTttChipController).displayChip(any(TransferSucceeded::class.java))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun removeCommand_chipRemoved() {
|
||||
commandRegistry.onShellCommand(pw, arrayOf(REMOVE_CHIP_COMMAND_TAG))
|
||||
|
||||
verify(mediaTttChipController).removeChip()
|
||||
}
|
||||
|
||||
private fun getMoveCloserToTransferCommand(): Array<String> =
|
||||
arrayOf(
|
||||
ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
MOVE_CLOSER_TO_TRANSFER_COMMAND_NAME
|
||||
)
|
||||
|
||||
private fun getTransferInitiatedCommand(): Array<String> =
|
||||
arrayOf(
|
||||
ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
TRANSFER_INITIATED_COMMAND_NAME
|
||||
)
|
||||
|
||||
private fun getTransferSucceededCommand(): Array<String> =
|
||||
arrayOf(
|
||||
ADD_CHIP_COMMAND_TAG,
|
||||
DEVICE_NAME,
|
||||
TRANSFER_SUCCEEDED_COMMAND_NAME
|
||||
)
|
||||
|
||||
class EmptyCommand : Command {
|
||||
override fun execute(pw: PrintWriter, args: List<String>) {
|
||||
}
|
||||
|
||||
override fun help(pw: PrintWriter) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private const val DEVICE_NAME = "My Tablet"
|
||||
Reference in New Issue
Block a user