Espresso匹配第一个元素,当许多人在层次结构中时

我正在尝试根据我的function编写一个espresso函数来匹配第一个espressofind的元素,即使find了多个匹配的项目。

例如:我有一个包含商品价格的单元格的列表视图。 我希望能够将货币兑换成加元并validation商品价格是否为加元。

我正在使用这个function:

onView(anyOf(withId(R.id.product_price), withText(endsWith("CAD")))) .check(matches( isDisplayed())); 

这会抛出AmbiguousViewMatcherException。

在这种情况下,我不关心有多少或几个单元格显示CAD,我只是想validation它是否显示。 有没有办法让espresso在遇到符合参数的物体时立即通过此测试

Solutions Collecting From Web of "Espresso匹配第一个元素,当许多人在层次结构中时"

您应该能够使用以下代码创建仅在第一个项目上匹配的自定义匹配器:

 private  Matcher first(final Matcher matcher) { return new BaseMatcher() { boolean isFirst = true; @Override public boolean matches(final Object item) { if (isFirst && matcher.matches(item)) { isFirst = false; return true; } return false; } @Override public void describeTo(final Description description) { description.appendText("should return first matching item"); } }; } 

我创建了这个匹配器,以防你有许多具有相同特征的元素,例如相同的id, 如果你不想只是第一个元素 ,而是想要一个特定的元素 。 希望这可以帮助:

  private static Matcher getElementFromMatchAtPosition(final Matcher matcher, final int position) { return new BaseMatcher() { int counter = 0; @Override public boolean matches(final Object item) { if (matcher.matches(item)) { if(counter == position) { counter++; return true; } counter++; } return false; } @Override public void describeTo(final Description description) { description.appendText("Element at hierarchy position "+position); } }; } 

例:

您有许多按钮具有相同ID,您正在使用的库中,您想要选择第二个按钮。

  ViewInteraction colorButton = onView( allOf( getElementFromMatchAtPosition(allOf(withId(R.id.color)), 2), isDisplayed())); colorButton.perform(click()); 

根据我的理解,在您的方案中,在您切换货币后所有价格都应该是加元。 所以只需抓住第一个项目并validation它也可以解决您的问题:

 onData(anything()) .atPosition(0) .onChildView(allOf(withId(R.id.product_price), withText(endsWith("CAD")))) .check(matches(isDisplayed()));