1 package android.platform.uiautomator_helpers
2 
3 import android.graphics.Rect
4 import android.platform.uiautomator_helpers.DeviceHelpers.uiDevice
5 import android.platform.uiautomator_helpers.SwipeUtils.calculateStartEndPoint
6 import android.platform.uiautomator_helpers.TracingUtils.trace
7 import androidx.test.uiautomator.Direction
8 import androidx.test.uiautomator.UiObject2
9 import androidx.test.uiautomator.Until
10 import java.time.Duration
11 
12 /**
13  * A scroll utility that should be used instead of [UiObject2.scroll] for more reliable scrolls.
14  *
15  * See [BetterSwipe] for more details on the problem of [UiObject2.scroll].
16  */
17 object BetterScroll {
18     private const val DEFAULT_PERCENTAGE = 0.8f
19     private val DEFAULT_WAIT_TIMEOUT = Duration.ofSeconds(1)
20 
21     /**
22      * Scrolls [percentage] of [rect] in the given [direction].
23      *
24      * Note that when direction is [Direction.DOWN], the scroll will be from the top to the bottom
25      * (to scroll down).
26      */
27     @JvmStatic
28     @JvmOverloads
scrollnull29     fun scroll(
30         rect: Rect,
31         direction: Direction,
32         percentage: Float = DEFAULT_PERCENTAGE,
33     ) {
34         val (start, stop) = calculateStartEndPoint(rect, direction, percentage)
35 
36         trace("Scrolling $start -> $stop") {
37             uiDevice.performActionAndWait(
38                 { BetterSwipe.from(start).to(stop).pause().release() },
39                 Until.scrollFinished(Direction.reverse(direction)),
40                 DEFAULT_WAIT_TIMEOUT.toMillis()
41             )
42         }
43     }
44 }
45