2016-04-05 9 views
3

Ich habe diesen Test, der etwa die Hälfte der Zeit funktioniert.Android Espresso flockig withId mit Text Test

@Test 
    public void thirdSwipe() { 
    onView(withId(R.id.pager)).perform(swipeLeft()); 
    onView(withId(R.id.pager)).perform(swipeLeft()); 
    onView(withId(R.id.pager)).perform(swipeLeft()); 
    onView(allOf(withId(R.id.hint_english_text), withText("dog 0a"))).check(matches(isDisplayed())); 
    } 

ich diesen Fehler:

android.support.test.espresso.base.DefaultFailureHandler$AssertionFailedWithCauseError: 'is displayed on the screen to the user' doesn't match the selected view. 
Expected: is displayed on the screen to the user 
Got: "TextView{id=2131427358, res-name=hint_english_text, visibility=VISIBLE, width=624, height=62, has-focus=false, has-focusable=false, has-window-focus=true, is-clickable=false, is-enabled=true, is-focused=false, is-focusable=false, is-layout-requested=false, is-selected=false, root-is-layout-requested=false, has-input-connection=false, x=20.0, y=20.0, text=dog 0a, input-type=0, ime-target=false, has-links=false}" 

Also, es sieht aus wie es die TextView mit "dog 0a" gefunden, aber es wird nicht erkannt. Ich habe bei anderen Fragen sah und ich den Text mit einem String gesetzt, das ist nur ein paar Zeilen aus meiner Klasse:

private String englishText; 
englishTextView.setText(englishText); 

Auch ich bin mit allOf(). Jede Hilfe wäre willkommen. Diese Ansicht ist innerhalb einer ViewPager Ansicht, so dass ich nicht sicher bin, ob der Test stattfindet, bevor die ViewPager Idyl ist, aber es sagt, dass es die Ansicht findet.

+0

Sie Animation ausschalten haben? – Youngjae

+0

Ja, ich habe die Animation ausgeschaltet. Tut mir leid, dass ich das nicht erwähnt habe. – flobacca

+0

hast du das Gerät gewechselt? für mich gibt nur Lollipop Gerät das richtige Ergebnis. – Youngjae

Antwort

4

Sie sind definitiv auf dem richtigen Weg mit dem Leerlaufproblem. Espresso kann nicht wissen, wann sich ein ViewPager nach einem Wischvorgang vollständig beruhigt hat. Wie der Fehler anzeigt, befindet sich die gesuchte Ansicht irgendwo in der Ansichtshierarchie, was bedeutet, dass sie gerendert wurde, aber Espresso erkennt, dass sie noch nicht auf dem Bildschirm angezeigt wird. Dies liegt daran, dass sich der ViewPager nicht vollständig auf der Seite eingerichtet hat, an der Sie interessiert sind.

Die nächste Frage wäre, wie man Espresso sagen soll, dass es auf den ViewPager warten soll. Dies ist ein etwas schwer zu lösendes Problem.

Ein Weg, um die Wahrscheinlichkeit dieses Problems zu beseitigen, ist eine Thread.sleep durchzuführen, die Espresso dazu zwingt, einige Zeit zu warten, mit der Hoffnung, dass der ViewPager sich einstellt, bevor das Warten vorbei ist. Während dies im Allgemeinen mit einer ausreichend langen Schlafdauer funktionieren kann, ist dies nicht ideal, da dies unnötige Zeit für Ihre Tests bedeutet.

Der beste Weg, dies zu tun, wäre ViewPager sagen uns, wenn es vollständig erledigt ist.

Wenn Sie sich einige der für ViewPager verfügbaren Listener ansehen, ist einer davon der OnPageChangeListener. Diese Klasse verfügt über einige Callback-Methoden: onPageScrolled, onPageScrollStateChanged und onPageSelected.

onPageSelected klingt wie ein guter Kandidat, aber wenn man einen genaueren Blick auf die Dokumentation für diese Methode nehmen, werden Sie feststellen, es sagt

/** 
* This method will be invoked when a new page becomes selected. Animation is not 
* necessarily complete. 
*/ 

So ist dies nicht zur Arbeit gehen.

onPageScrollStateChanged ist ein weiterer guter Kandidat. Dies meldet einige Zustandsänderungen in ViewPager, nämlich SCROLL_STATE_DRAGGING, SCROLL_STATE_SETTLING und SCROLL_STATE_IDLE. Mit diesem Callback können wir feststellen, wann der ViewPager im Leerlauf ist.

Wie Sie eine Instanz dieses Listeners an den ViewPager und Espresso anschließen, können Sie unter this implementation sehen, das von Espresso bereitgestellt wird, um Aktionen auf DrawerLayouts auszuführen und in ähnlicher Weise darauf zu warten, dass sie sich absetzen. Der Vorteil davon ist, dass Sie ein benutzerdefiniertes ViewAction-Objekt erstellen, das einen dieser Listener an den ViewPager anhängt, dann den Swipe ausführt und darauf wartet, dass der ViewPager meldet, dass er in SCROLL_STATE_IDLE gegangen ist.

Beachten Sie, dass diese Implementierung Reflexion verwendet ein DrawerListener vom DrawerLayout zu entfernen und wickelt, wenn ein solches vorhanden ist, bevor es selbst anbringen, aber dies ist nicht notwendig, im ViewPager Fall, wie ViewPager OnPageChangeListeners mehr daran befestigt hat.

0

dies funktioniert für mich

onView(allOf(
    withId(R.id.pagerimage), 
    ChildOf(withId(R.id.viewpager), 0) 
    )).check(matches(isDisplayed())) 
     .perform(swipeLeft());