Add sendLongClick methods to GestureScope
Adds two overloads, one without arguments that performs a long click in
the middle of the component, and one that accepts a position where the
long click must be performed.
Bug: 146553670
Test: ./gradlew ui:ui-test:cC
Change-Id: Ic7db9ad532d241f1f3e354cd7b7e55dac6eaaded
diff --git a/ui/ui-test/src/androidTest/java/androidx/ui/test/SendLongClickTest.kt b/ui/ui-test/src/androidTest/java/androidx/ui/test/SendLongClickTest.kt
new file mode 100644
index 0000000..9d4ebb9
--- /dev/null
+++ b/ui/ui-test/src/androidTest/java/androidx/ui/test/SendLongClickTest.kt
@@ -0,0 +1,175 @@
+/*
+ * Copyright 2019 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 androidx.ui.test
+
+import androidx.compose.Composable
+import androidx.test.filters.MediumTest
+import androidx.ui.core.Alignment
+import androidx.ui.core.PointerInputWrapper
+import androidx.ui.core.PxPosition
+import androidx.ui.core.TestTag
+import androidx.ui.core.WithDensity
+import androidx.ui.core.gesture.LongPressGestureDetector
+import androidx.ui.core.gesture.LongPressTimeout
+import androidx.ui.core.milliseconds
+import androidx.ui.core.px
+import androidx.ui.foundation.shape.DrawShape
+import androidx.ui.foundation.shape.RectangleShape
+import androidx.ui.graphics.Color
+import androidx.ui.layout.Align
+import androidx.ui.layout.Container
+import androidx.ui.semantics.Semantics
+import androidx.ui.test.util.PointerInputRecorder
+import androidx.ui.test.util.areAlmostEqualTo
+import androidx.ui.test.util.assertOnlyLastEventIsUp
+import androidx.ui.test.util.assertTimestampsAreIncreasing
+import androidx.ui.test.util.recordedDuration
+import com.google.common.truth.Truth.assertThat
+import org.junit.Rule
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.junit.runners.JUnit4
+import org.junit.runners.Parameterized
+
+private const val tag = "widget"
+private val width = 100.px
+private val height = 100.px
+private val expectedDuration = LongPressTimeout + 100.milliseconds
+
+@Composable
+private fun Ui(recorder: PointerInputRecorder, onLongPress: (PxPosition) -> Unit) {
+ Align(alignment = Alignment.BottomRight) {
+ TestTag(tag) {
+ Semantics {
+ LongPressGestureDetector( {
+ PointerInputWrapper(
+ pointerInputHandler = recorder::onPointerInput,
+ cancelHandler = {}
+ ) {
+ WithDensity {
+ Container(width = width.toDp(), height = height.toDp()) {
+ DrawShape(RectangleShape, Color.Yellow)
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+}
+
+/**
+ * Tests [GestureScope.sendLongClick] without arguments. Verifies that the click is in the middle
+ * of the component, that the gesture has a duration of 600 milliseconds and that all input
+ * events were on the same location.
+ */
+@MediumTest
+@RunWith(JUnit4::class)
+class SendLongClickWithoutArgumentsTest {
+
+ @get:Rule
+ val composeTestRule = createComposeRule(disableTransitions = true)
+
+ private val recorder = PointerInputRecorder()
+ private val recordedLongClicks = mutableListOf<PxPosition>()
+ private val expectedPosition = PxPosition(width / 2, height / 2)
+
+ private fun recordLongPress(position: PxPosition) {
+ recordedLongClicks.add(position)
+ }
+
+ @Test
+ fun testLongClick() {
+ // Given some content
+ composeTestRule.setContent { Ui(recorder, ::recordLongPress) }
+
+ // When we inject a long click
+ findByTag(tag).doGesture { sendLongClick() }
+
+ // Then we record 1 long click
+ assertThat(recordedLongClicks).hasSize(1)
+
+ // And all events are at the click location
+ composeTestRule.runOnUiThread {
+ recorder.run {
+ assertTimestampsAreIncreasing()
+ assertOnlyLastEventIsUp()
+ events.areAlmostEqualTo(expectedPosition)
+ assertThat(recordedDuration).isEqualTo(expectedDuration)
+ }
+ }
+ }
+}
+
+/**
+ * Tests [GestureScope.sendLongClick] with arguments. Verifies that the click is in the middle
+ * of the component, that the gesture has a duration of 600 milliseconds and that all input
+ * events were on the same location.
+ */
+@MediumTest
+@RunWith(Parameterized::class)
+class SendLongClickWithArgumentsTest(private val config: TestConfig) {
+ data class TestConfig(
+ val position: PxPosition
+ )
+
+ companion object {
+ @JvmStatic
+ @Parameterized.Parameters(name = "{0}")
+ fun createTestSet(): List<TestConfig> {
+ return mutableListOf<TestConfig>().apply {
+ for (x in listOf(1.px, width / 4)) {
+ for (y in listOf(1.px, height / 4)) {
+ add(TestConfig(PxPosition(x, y)))
+ }
+ }
+ }
+ }
+ }
+
+ @get:Rule
+ val composeTestRule = createComposeRule(disableTransitions = true)
+
+ private val recorder = PointerInputRecorder()
+ private val recordedLongClicks = mutableListOf<PxPosition>()
+
+ private fun recordLongPress(position: PxPosition) {
+ recordedLongClicks.add(position)
+ }
+
+ @Test
+ fun testLongClick() {
+ // Given some content
+ composeTestRule.setContent { Ui(recorder, ::recordLongPress) }
+
+ // When we inject a long click
+ findByTag(tag).doGesture { sendLongClick(config.position) }
+
+ // Then we record 1 long click
+ assertThat(recordedLongClicks).hasSize(1)
+
+ // And all events are at the click location
+ composeTestRule.runOnUiThread {
+ recorder.run {
+ assertTimestampsAreIncreasing()
+ assertOnlyLastEventIsUp()
+ events.areAlmostEqualTo(config.position)
+ assertThat(recordedDuration).isEqualTo(expectedDuration)
+ }
+ }
+ }
+}