![](/img/trans.png)
[英]How to test launching new Activity with Espresso via OnClick action?
[英]How to update UI elements of an activity via Espresso test methods?
我正在嘗試為我的活動編寫一個測試用例。 我的活動中有一個方法可以更新我的UI。
public void setBooking(Booking booking)
{
if (booking == null)
{
return;
}
this.mBooking = booking;
this.mBookingExt.updateUI();
}
這是我的測試課:
@RunWith(AndroidJUnit4.class)
public class LocatingActivityTest
{
@Rule
public ActivityTestRule<BookingActivity> mActivityTestRule = new ActivityTestRule<>(BookingActivity.class);
private BookingActivity mBookingActivity;
@Before
public void setup()
{
mBookingActivity = mActivityTestRule.getActivity();
mBookingActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object
onView(withId(R.id.book_now)).perform(click());
}
@Test
public void viewsMustBeVisible()
{
onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.cancel_booking)).check(matches(isCompletelyDisplayed()));
}
}
運行測試時出現以下錯誤:
android.view.ViewRootImpl $ CalledFromWrongThreadException:只有創建視圖層次結構的原始線程才能觸摸其視圖。
我認為@Before
在UI線程上運行,所以不知道這個抱怨來自哪里! 這是我的參考 ( ActivityTestRule
擴展了UiThreadTestRule
)。
因此,我決定對類的體系結構進行一些更改。 因此setup()
和viewsMustBeVisible()
更改為:
@Before
public void setup()
{
mBookingTaxiActivity = mActivityTestRule.getActivity();
}
@UiThreadTest // from android.support.test.annotation.UiThreadTest
public void viewsMustBeVisible()
{
mBookingTaxiActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object
onView(withId(R.id.fab_booking)).perform(click());
onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
onView(withId(R.id.booking_book_now)).perform(click());
onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
}
但是,這次我遇到以下錯誤:
java.lang.Exception:沒有可運行的方法
最后,我更改了上述方法以在UI線程上運行測試:
@Test
public void viewsMustBeVisible()
{
mBookingTaxiActivity.runOnUiThread(new Runnable()
{
@Override
public void run()
{
mBookingTaxiActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object
onView(withId(R.id.fab_booking)).perform(click());
onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
onView(withId(R.id.booking_book_now)).perform(click());
onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
});
}
這里的問題是測試永遠不會完成。 我在等待6到7分鍾,其進度指示器仍在旋轉,似乎永遠無法完成。
我想我已經研究了更新我的Booking對象和UI元素的所有方法。
太酷了,幾個小時后我就不穿了。 我不確定有什么區別,但是我將UI線程移動到了Activity中。 新的測試方法看起來像這樣:
@Test
public void viewsMustBeVisible()
{
onView(withId(R.id.fab_booking)).perform(click());
mBookingTaxiActivity.setTestBooking(BookingTest.getStandardTaxi());
onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
onView(withId(R.id.booking_book_now)).perform(click());
onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
}
我在活動端創建了一個方法來更新我的對象:
// Required just for Testing purposes
@VisibleForTesting
public void setTestBooking(Booking booking)
{
if (booking == null)
{
return;
}
this.mBooking = booking;
this.runOnUiThread(new Runnable()
{
@Override
public void run()
{
BookingActivity.this.mBookingExt.updateUI();
findViewById(R.id.booking_book_now).setEnabled(true);
}
});
}
希望它對您有幫助。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.