package com.ms_square.debugoverlay;
import android.app.Activity;
import android.app.Application;
import android.app.Instrumentation;
import android.content.Intent;
import android.graphics.Color;
import android.support.annotation.NonNull;
import android.support.test.InstrumentationRegistry;
import android.support.test.rule.ActivityTestRule;
import android.util.Log;
import com.google.android.libraries.cloudtesting.screenshots.ScreenShotter;
import com.ms_square.debugoverlay.modules.CpuUsageModule;
import com.ms_square.debugoverlay.modules.FpsModule;
import com.ms_square.debugoverlay.modules.LogcatLine;
import com.ms_square.debugoverlay.modules.LogcatLineColorScheme;
import com.ms_square.debugoverlay.modules.LogcatLineFilter;
import com.ms_square.debugoverlay.modules.LogcatModule;
import com.ms_square.debugoverlay.modules.MemInfoModule;
import com.ms_square.debugoverlay.sample.IPAddressModule;
import com.ms_square.debugoverlay.sample.MainActivity;
import com.ms_square.debugoverlay.sample.ScrollingActivity;
import org.hamcrest.Matchers;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import static android.support.test.espresso.Espresso.onView;
import static android.support.test.espresso.action.ViewActions.click;
import static android.support.test.espresso.matcher.ViewMatchers.withId;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThat;
/**
* Not yet complete or good enough, but covers some common scenarios as a staring point.
* TODO: use UiAutomation's takeScreenshot() for screen captures?
*/
abstract class DebugOverlayInstrumentedTest {
private static final String TAG = DebugOverlayInstrumentedTest.class.getSimpleName();
DebugOverlay debugOverlay;
@Before
public void setUp() {
DebugOverlay.enableDebugLogging(true);
}
@After
public void tearDown() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
if (debugOverlay != null) {
debugOverlay.uninstall();
}
}
});
}
@Test
public void useDefaultApplication() {
assertEquals("Application", getApplication().getClass().getSimpleName());
}
@Test
public void installCpuModule() throws Exception {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new CpuUsageModule())
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installCustomModule() throws Exception {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new IPAddressModule(getApplication()))
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installModulesTopEnd() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new CpuUsageModule(),
new MemInfoModule(getApplication()),
new FpsModule())
.position(Position.TOP_END)
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installModulesBottomEnd() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new CpuUsageModule(),
new MemInfoModule(getApplication()),
new FpsModule())
.position(Position.BOTTOM_END)
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installLogcatModule() {
DebugOverlay.enableDebugLogging(false);
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new CpuUsageModule(),
new MemInfoModule(getApplication()),
new FpsModule(),
new LogcatModule(10))
.position(Position.BOTTOM)
.build();
debugOverlay.install();
}
});
waitForOverlay();
Log.v(TAG, "hello world V");
Log.d(TAG, "hello world D");
Log.i(TAG, "hello world I");
Log.w(TAG, "hello world W");
Log.e(TAG, "hello world E");
Log.wtf(TAG, "hello world WTF");
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
DebugOverlay.enableDebugLogging(true);
}
@Test
public void installLogcatModuleWCustomColor() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new LogcatModule(10, new LogcatLineColorScheme() {
@Override
public int getTextColor(LogcatLine.Priority priority, @NonNull String tag) {
return Color.CYAN;
}
}))
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installLogcatModuleWCustomFilter() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new LogcatModule(10, new LogcatLineFilter.SimpleLogcatLineFilter(LogcatLine.Priority.INFO)))
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void installModulesCustomStyle() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.modules(new CpuUsageModule(),
new MemInfoModule(getApplication()),
new FpsModule())
.position(Position.TOP_START)
.bgColor(Color.parseColor("#60000000"))
.textColor(Color.MAGENTA)
.textSize(14f)
.textAlpha(.8f)
.build();
debugOverlay.install();
}
});
waitForOverlay();
}
@Test
public void startSecondActivity() {
getInstrumentation().runOnMainSync(new Runnable() {
@Override
public void run() {
debugOverlay = new DebugOverlay.Builder(getApplication())
.allowSystemLayer(testSystemLayer())
.build();
debugOverlay.install();
}
});
waitForOverlay();
Instrumentation.ActivityMonitor monitor = new Instrumentation.ActivityMonitor(ScrollingActivity.class.getCanonicalName(),
null, false);
getInstrumentation().addMonitor(monitor);
try {
onView(withId(com.ms_square.debugoverlay.sample.R.id.fab)).perform(click());
Activity nextActivity = monitor.waitForActivityWithTimeout(5000);
assertThat(nextActivity, Matchers.is(Matchers.notNullValue()));
takeActivityScreenShot(nextActivity);
nextActivity.finish();
} finally {
getInstrumentation().removeMonitor(monitor);
}
}
abstract ActivityTestRule getActivityRule();
abstract boolean testSystemLayer();
void waitForOverlay() {
waitForOverlay(5000);
}
void waitForOverlay(long millis) {
if (!testSystemLayer()) {
Instrumentation.ActivityMonitor monitor = new Instrumentation.ActivityMonitor(MainActivity.class.getCanonicalName(),
null, false);
getInstrumentation().addMonitor(monitor);
getActivityRule().launchActivity(new Intent(getApplication(), MainActivity.class));
try {
monitor.waitForActivityWithTimeout(5000);
} finally {
getInstrumentation().removeMonitor(monitor);
}
}
try {
Thread.currentThread().sleep(millis);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Instrumentation getInstrumentation() {
return InstrumentationRegistry.getInstrumentation();
}
Application getApplication() {
return (Application) getInstrumentation().getTargetContext().getApplicationContext();
}
void takeActivityScreenShot(Activity activity) {
// This only captures the main application window. See captured videos in FireBase to check
// what's being displayed in the overlay.
// Note that test method name is automatically captured and appended by the lib
ScreenShotter.takeScreenshot(getClass().getSimpleName(), activity);
}
}