For anyone who wants Activity
, but that without need to re-write all tests to run on UI-thread, a fairly straightforward Java way to get it:
Waiting for UI
Assume you want to test if a dialog is shown after some delay, the onActivity(...)
hook runs on UI-thread, which means waiting in there would cause the dialog to be nerver shown.
- In such cases you need to keep a strong-reference to
ActivityScenario
(as that prevents Activity close).
- Test should wait for
onActivity(...)
hook to be called, then keep passed Activity's reference.
- Finally, move test logic out of
onActivity(...)
hook.
Example
private ActivityScenario mActivityScenario;
@After
public void tearDown() throws Exception {
if (mActivityScenario != null) {
mActivityScenario.close();
}
mActivityScenario = null;
}
@Override
public Activity getActivity() {
if (mActivityScenario == null) {
mActivityScenario = ActivityScenario.launch(getActivityClassForScenario());
}
return tryAcquireScenarioActivity(mActivityScenario);
}
protected static Activity tryAcquireScenarioActivity(ActivityScenario activityScenario) {
Semaphore activityResource = new Semaphore(0);
Activity[] scenarioActivity = new Activity[1];
activityScenario.onActivity(activity -> {
scenarioActivity[0] = activity;
activityResource.release();
});
try {
activityResource.tryAcquire(15000, TimeUnit.MILLISECONDS);
} catch (InterruptedException e) {
Assert.fail("Failed to acquire activity scenario semaphore");
}
Assert.assertNotNull("Scenario Activity should be non-null", scenarioActivity[0]);
return scenarioActivity[0];
}