Espresso - 在列表视图中单击文本

时间:2014-04-09 14:34:06

标签: android android-testing android-espresso

我正在尝试使用Espresso点击列表视图中的文字。我知道他们有this guide,但我看不到如何通过查找文本来完成这项工作。这就是我试过的

Espresso.onData(Matchers.allOf(Matchers.is(Matchers.instanceOf(ListView.class)), Matchers.hasToString(Matchers.startsWith("ASDF")))).perform(ViewActions.click());

正如预期的那样,这不起作用。错误表示层次结构中没有视图。有谁知道如何选择一个字符串? (在这种情况下"ASDF")先谢谢。

由于@haffax

而更新

我收到了错误:

  

com.google.android.apps.common.testing.ui.espresso.AmbiguousViewMatcherException:'可从类中分配:class android.widget.AdapterView'匹配层次结构中的多个视图。

第二个错误

使用此代码

onData(hasToString(startsWith("ASDF"))).inAdapterView(withContentDescription("MapList")).perform(click());

我收到此错误

  

com.google.android.apps.common.testing.ui.espresso.PerformException:使用内容说明在视图'上执行'加载适配器数据'时出错:是“MapList”'。

     

引起:java.lang.RuntimeException:找不到匹配的数据:asString(以“ASDF”开头的字符串)


解决方案

  

昂达(任何())。inAdapterView(withContentDescription( “降序”))。atPosition(x)的.perform(点击())

3 个答案:

答案 0 :(得分:39)

问题是,您尝试将列表视图本身与instanceOf(ListView.class)作为onData()的参数进行匹配。 onData()要求数据匹配器匹配ListView的已调整数据,而不是ListView本身,而不是View返回的Adapter.getView(),但是实际数据。

如果您的生产代码中有类似的内容:

ListView listView = (ListView)findViewById(R.id.myListView);
ArrayAdapter<MyDataClass> adapter = getAdapterFromSomewhere();
listView.setAdapter(adapter);

然后Espresso.onData()的匹配器参数应匹配所需的MyDataClass实例。 所以,这样的事情应该有效:

onData(hasToString(startsWith("ASDF"))).perform(click());

(您可以使用org.hamcrest.Matchers

的方法使用其他匹配器)

如果您的活动中有多个适配器视图,您可以使用视图匹配器调用ViewMatchers.inAdapterView(),该视图匹配器指定AdapterView:

onData(hasToString(startsWith("ASDF")))
    .inAdapterView(withId(R.id.myListView))
    .perform(click());

答案 1 :(得分:2)

如果适配器具有自定义模型类,例如Item

public static Matcher<Object> withItemValue(final String value) {
        return new BoundedMatcher<Object, Item>(Item.class) {
            @Override
            public void describeTo(Description description) {
                description.appendText("has value " + value);
            }

            @Override
            public boolean matchesSafely(Item item) {
                return item.getName().toUpperCase().equals(String.valueOf(value));
            }
        };
    }

然后打电话给:

onData(withItemValue("DRINK1")).inAdapterView(withId(R.id.menu_item_grid)).perform(click());

答案 2 :(得分:0)

onData(hasEntry(equalTo(ListViewActivity.ROW_TEXT),is("List item: 25")))
        .onChildView(withId(R.id.rowTextView)).perform(click());

这对我来说最适合行文本数据..