head01
head01

Reputation: 581

Android - testing Google Map info window click

I'm writing tests for my app and I'm stuck with testing GoogleMap. Clicking on Marker was easy using UiAutomator, but it seems that it's impossible to click on info window.

This is how I make test click on Marker:

UiDevice device = UiDevice.getInstance(InstrumentationRegistry.getInstrumentation());
UiObject marker = device.findObject(new UiSelector().descriptionContains(MARKER_TITLE));

I've tried using Android Device Monitor and dumping view hierarchy but it seems like that view (info window) isn't there.

Here is how the screen that I'm trying to test looks like: https://i.sstatic.net/FuxHG.png

Any idea on how to click on info window using Espresso or UiAutomator?

Upvotes: 2

Views: 1705

Answers (3)

Mr-IDE
Mr-IDE

Reputation: 7641

As mentioned by Diego Torres Milano, you can't use Espresso, because the InfoWindow is drawn as an image. But you can use UIAutomator, and assume that the Marker will be animated to the center of the screen after being clicked:

app/build.gradle

androidTestImplementation "androidx.test.uiautomator:uiautomator:2.1.3" // UIAutomator
androidTestImplementation 'androidx.test.ext:junit:1.1.1' // For @RunWith(AndroidJUnit4::class)
androidTestImplementation 'androidx.test:runner:1.1.1'
androidTestImplementation 'androidx.test:rules:1.1.1' // For UI Tests that use ActivityTestRule
androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.1' // Espresso

MapViewTest.kt

@RunWith(AndroidJUnit4::class)
class MapViewTest {
  @Rule
  @JvmField
  val activityRule: ActivityTestRule<MapViewActivity> 
    = ActivityTestRule(MapViewActivity::class.java)

  @Test
  fun mapViewUITest() {
    val twoSeconds = 2000
    val fiveSeconds = 5000

    // Wait for the Map View to load
    waitFor(fiveSeconds)

    // First of all, click on the Marker, using UIAutomator
    val device = UiDevice.getInstance(getInstrumentation())
    val marker = device.findObject(UiSelector().descriptionContains("My Marker Title"))
    marker.click()
  
    // After a marker is clicked, the MapView will automatically move the map
    // to position the Marker at the center of the screen, at 43% screen height.
    // So wait for the animation to finish first.
    waitFor(twoSeconds)
  
    // Calculate the (x,y) position of the InfoWindow, using the screen size
    val display = activityRule.activity.windowManager.defaultDisplay
    val size = Point()
    display.getRealSize(size)
    val screenWidth = size.x
    val screenHeight = size.y
    val x = screenWidth / 2
    val y = (screenHeight * 0.43).toInt()
  
    // Click on the InfoWindow, using UIAutomator
    device.click(x, y)
    waitFor(twoSeconds)

    // Add further UI tests with Espresso
  }
  
  private fun waitFor(duration: Int) = Thread.sleep(duration.toLong())
}

Upvotes: 0

Diego Torres Milano
Diego Torres Milano

Reputation: 69218

The info window that is drawn is not a live view. The view is rendered as an image (using View.draw(Canvas)) at the time it is returned. This means that you won't be able to find it as an Object.

As you can listen to a generic click event on the whole info window, you might be able to touch is using its coordinates calculated as an offset from the marker.

Upvotes: 1

Rilwan
Rilwan

Reputation: 2301

Some webviews cant be automated using uiautomator. Whatever ui elements appearing in uiautomatorviewer can automate. Just check uiautomatorviewer first. If it does not appear in viewer, one work around is adb shell input tap <x> <y>. where x,y are coordinates on your screen.

Upvotes: 0

Related Questions