Intereting Posts
Как отличить, если данный Контекстный объект является Контекстом Деятельности или Сервиса? ProgressBar Circle не показывает прогресс в android L (API 21) Разница между андроидом: ширина и андроид: layout_width Как объединить два mp3-файла в один (объединение / объединение) Пробейте отверстие в наложении прямоугольника с ускорением HW, включенным в представлении Как изменить размер содержимого веб-обозревателя в android? Соедините два аудиофайла и воспроизведите полученный файл Как проверить, установлен ли телефон Android? Отправка приложений на Android Market и Amazon Appstore Таблица абстрактных классов ActiveAndroid Установите режим наложения Actionbar во время выполнения на Android Проблема с памятью Viewpager Webview Являются ли поля чтения объекта Realm медленнее, чем объекты Java? Ошибка добавления предварительно созданного apk с разделяемыми библиотеками в AOSP Объедините покрытие jacoco от androidTest и теста

Espresso соответствует первому элементу, найденному, когда многие из них находятся в иерархии

Я пытаюсь написать функцию эспрессо для соответствия первому элементу espresso find в соответствии с моей функцией, даже если найдено несколько совпадающих элементов.

Пример: у меня есть список с ячейками, которые содержат цену товара. Я хочу иметь возможность переключать валюту на канадские доллары и проверять цены на товары в CAD.

Я использую эту функцию:

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

Это вызывает исключение AmbiguousViewMatcherException.

В этом случае мне все равно, сколько или несколько ячеек отображает САПР, я просто хочу проверить, что он отображается. Есть ли способ сделать эспрессо пройти этот тест, как только он встретит объект, отвечающий параметрам?

Solutions Collecting From Web of "Espresso соответствует первому элементу, найденному, когда многие из них находятся в иерархии"

Вы должны иметь возможность создавать пользовательский совпадение, которое соответствует только первому элементу со следующим кодом:

 private <T> Matcher<T> first(final Matcher<T> matcher) { return new BaseMatcher<T>() { 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"); } }; } 

Насколько я понимаю, в вашем сценарии все цены должны быть в CAD после того, как вы переключили валюту. Так что просто захват первого элемента и его проверка также должны решить вашу проблему:

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

Я создал этот помощник, если у вас много элементов с такими же характеристиками, как у одного и того же идентификатора, и если вы хотите не только первый элемент, но и хотите получить определенный элемент . Надеюсь это поможет:

  private static Matcher<View> getElementFromMatchAtPosition(final Matcher<View> matcher, final int position) { return new BaseMatcher<View>() { 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); } }; } 

Пример:

У вас много кнопок с одинаковым идентификатором из библиотеки, которую вы используете, вы хотите выбрать вторую кнопку.

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