Merge "Add a CTS test for multinetwork features." into lmp-dev
diff --git a/tests/tests/admin/src/android/admin/cts/DevicePolicyManagerTest.java b/tests/tests/admin/src/android/admin/cts/DevicePolicyManagerTest.java
index e953305..f62ac60 100644
--- a/tests/tests/admin/src/android/admin/cts/DevicePolicyManagerTest.java
+++ b/tests/tests/admin/src/android/admin/cts/DevicePolicyManagerTest.java
@@ -19,7 +19,9 @@
import android.app.admin.DevicePolicyManager;
import android.content.ComponentName;
import android.content.Context;
+import android.content.Intent;
import android.content.pm.PackageManager;
+import android.provider.Settings;
import android.test.AndroidTestCase;
import android.util.Log;
@@ -220,4 +222,198 @@
assertFalse(mDevicePolicyManager.resetPassword("abcd", 0));
assertTrue(mDevicePolicyManager.resetPassword("abcd123", 0));
}
+
+ public void testCreateUser_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testCreateUser_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.createUser(mComponent, "user name");
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testRemoveUser_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testRemoveUser_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.removeUser(mComponent, null);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetApplicationBlocked_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetApplicationBlocked_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setApplicationBlocked(mComponent, "com.google.anything", true);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetApplicationsBlocked_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetApplicationsBlocked_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ Intent pdfViewIntent = new Intent(Intent.ACTION_VIEW).setType("application/pdf");
+ mDevicePolicyManager.setApplicationsBlocked(mComponent, pdfViewIntent, true);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testIsApplicationBlocked_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testIsApplicationBlocked_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.isApplicationBlocked(mComponent, "com.google.anything");
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetGlobalSetting_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetGlobalSetting_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setGlobalSetting(mComponent,
+ Settings.Global.WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON, "1");
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetSecureSetting_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetSecureSetting_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setSecureSetting(mComponent,
+ Settings.Secure.INSTALL_NON_MARKET_APPS, "1");
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetMasterVolumeMuted_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetMasterVolumeMuted_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setMasterVolumeMuted(mComponent, true);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testIsMasterVolumeMuted_failIfNotDeviceOrProfileOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetMasterVolumeMuted_failIfNotDeviceOrProfileOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.isMasterVolumeMuted(mComponent);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertProfileOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetRecommendedGlobalProxy_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetRecommendedGlobalProxy_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setRecommendedGlobalProxy(mComponent, null);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSetLockTaskPackages_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSetLockTaskPackages_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.setLockTaskPackages(new String[] {"package"});
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ }
+ }
+
+ public void testClearDeviceOwnerApp_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testClearDeviceOwnerApp_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.clearDeviceOwnerApp("android.deviceadmin.cts");
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testSwitchUser_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testSwitchUser_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.switchUser(mComponent, null);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ public void testCreateAndInitializeUser_failIfNotDeviceOwner() {
+ if (!mDeviceAdmin) {
+ Log.w(TAG, "Skipping testCreateAndInitializeUser_failIfNotDeviceOwner");
+ return;
+ }
+ try {
+ mDevicePolicyManager.createAndInitializeUser(mComponent, "name", "admin name",
+ mComponent, null);
+ fail("did not throw expected SecurityException");
+ } catch (SecurityException e) {
+ assertDeviceOwnerMessage(e.getMessage());
+ }
+ }
+
+ private void assertDeviceOwnerMessage(String message) {
+ assertTrue("message is: "+ message, message.contains("does not own the device")
+ || message.contains("can only be called by the device owner"));
+ }
+
+ private void assertProfileOwnerMessage(String message) {
+ assertTrue(message.contains("does not own the profile"));
+ }
}
diff --git a/tests/tests/animation/src/android/animation/cts/AnimationActivity.java b/tests/tests/animation/src/android/animation/cts/AnimationActivity.java
index 555ab15..225a97e 100644
--- a/tests/tests/animation/src/android/animation/cts/AnimationActivity.java
+++ b/tests/tests/animation/src/android/animation/cts/AnimationActivity.java
@@ -145,6 +145,11 @@
view.animateBall();
}
+ public void startSingleAnimation(Animator animator) {
+ animator.setTarget(view.newBall);
+ animator.start();
+ }
+
public void startAnimation(ValueAnimator valueAnimator){
view.bounceYAnimator = valueAnimator;
view.startColorAnimator();
diff --git a/tests/tests/animation/src/android/animation/cts/PropertyValuesHolderTest.java b/tests/tests/animation/src/android/animation/cts/PropertyValuesHolderTest.java
index 26db933..200ebce 100644
--- a/tests/tests/animation/src/android/animation/cts/PropertyValuesHolderTest.java
+++ b/tests/tests/animation/src/android/animation/cts/PropertyValuesHolderTest.java
@@ -16,15 +16,21 @@
package android.animation.cts;
import android.animation.Animator;
+import android.animation.AnimatorListenerAdapter;
import android.animation.ArgbEvaluator;
+import android.animation.Keyframe;
import android.animation.ObjectAnimator;
import android.animation.PropertyValuesHolder;
import android.animation.ValueAnimator;
+import android.graphics.drawable.ShapeDrawable;
import android.test.ActivityInstrumentationTestCase2;
import android.util.Property;
import android.view.View;
import android.view.animation.AccelerateInterpolator;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
+
public class PropertyValuesHolderTest extends
ActivityInstrumentationTestCase2<AnimationActivity> {
private AnimationActivity mActivity;
@@ -86,6 +92,113 @@
assertResults(yArray, mStartY, mEndY);
}
+ private ObjectAnimator createAnimator(Keyframe... keyframes) {
+ PropertyValuesHolder pVHolder = PropertyValuesHolder.ofKeyframe(mProperty, keyframes);
+ ObjectAnimator objAnimator = ObjectAnimator.ofPropertyValuesHolder(mObject,pVHolder);
+ objAnimator.setDuration(mDuration);
+ objAnimator.setInterpolator(new AccelerateInterpolator());
+ return objAnimator;
+ }
+
+ private void waitUntilFinished(ObjectAnimator objectAnimator, long timeoutMilliseconds)
+ throws InterruptedException {
+ final CountDownLatch latch = new CountDownLatch(1);
+ objectAnimator.addListener(new AnimatorListenerAdapter() {
+ @Override
+ public void onAnimationEnd(Animator animation) {
+ super.onAnimationEnd(animation);
+ latch.countDown();
+ }
+ });
+ latch.await(timeoutMilliseconds, TimeUnit.MILLISECONDS);
+ getInstrumentation().waitForIdleSync();
+ }
+
+ private void setTarget(final Animator animator, final Object target) throws Throwable {
+ runTestOnUiThread(new Runnable() {
+ @Override
+ public void run() {
+ animator.setTarget(target);
+ }
+ });
+ }
+
+ private void startSingleAnimation(final Animator animator) throws Throwable {
+ runTestOnUiThread(new Runnable() {
+ @Override
+ public void run() {
+ mActivity.startSingleAnimation(animator);
+ }
+ });
+ }
+
+ public void testResetValues() throws Throwable {
+ final float initialY = mActivity.view.newBall.getY();
+ Keyframe emptyKeyframe1 = Keyframe.ofFloat(.0f);
+ ObjectAnimator objAnimator1 = createAnimator(emptyKeyframe1, Keyframe.ofFloat(1f, 100f));
+ startSingleAnimation(objAnimator1);
+ assertTrue("Keyframe should be assigned a value", emptyKeyframe1.hasValue());
+ assertEquals("Keyframe should get the value from the target", emptyKeyframe1.getValue(),
+ initialY);
+ waitUntilFinished(objAnimator1, mDuration * 2);
+ assertEquals(100f, mActivity.view.newBall.getY());
+ startSingleAnimation(objAnimator1);
+ waitUntilFinished(objAnimator1, mDuration * 2);
+
+ // run another ObjectAnimator that will move the Y value to something else
+ Keyframe emptyKeyframe2 = Keyframe.ofFloat(.0f);
+ ObjectAnimator objAnimator2 = createAnimator(emptyKeyframe2, Keyframe.ofFloat(1f, 200f));
+ startSingleAnimation(objAnimator2);
+ assertTrue("Keyframe should be assigned a value", emptyKeyframe2.hasValue());
+ assertEquals("Keyframe should get the value from the target", emptyKeyframe2.getValue(), 100f);
+ waitUntilFinished(objAnimator2, mDuration * 2);
+ assertEquals(200f, mActivity.view.newBall.getY());
+
+ // re-run first object animator. since its target did not change, it should have the same
+ // start value for kf1
+ startSingleAnimation(objAnimator1);
+ assertEquals(emptyKeyframe1.getValue(), initialY);
+ waitUntilFinished(objAnimator1, mDuration * 2);
+
+ Keyframe fullKeyframe = Keyframe.ofFloat(.0f, 333f);
+ ObjectAnimator objAnimator3 = createAnimator(fullKeyframe, Keyframe.ofFloat(1f, 500f));
+ startSingleAnimation(objAnimator3);
+ assertEquals("When keyframe has value, should not be assigned from the target object",
+ fullKeyframe.getValue(), 333f);
+ waitUntilFinished(objAnimator3, mDuration * 2);
+
+ // now, null out the target of the first animator
+ float updatedY = mActivity.view.newBall.getY();
+ setTarget(objAnimator1, null);
+ startSingleAnimation(objAnimator1);
+ assertTrue("Keyframe should get a value", emptyKeyframe1.hasValue());
+ assertEquals("Keyframe should get the updated Y value", emptyKeyframe1.getValue(), updatedY);
+ waitUntilFinished(objAnimator1, mDuration * 2);
+ assertEquals("Animation should run as expected", 100f, mActivity.view.newBall.getY());
+
+ // now, reset the target of the fully defined animation.
+ setTarget(objAnimator3, null);
+ startSingleAnimation(objAnimator3);
+ assertEquals("When keyframe is fully defined, its value should not change when target is"
+ + " reset", fullKeyframe.getValue(), 333f);
+ waitUntilFinished(objAnimator3, mDuration * 2);
+
+ // run the other one to change Y value
+ startSingleAnimation(objAnimator2);
+ waitUntilFinished(objAnimator2, mDuration * 2);
+ // now, set another target w/ the same View type. it should still reset
+ ShapeHolder view = new ShapeHolder(new ShapeDrawable());
+ updatedY = mActivity.view.newBall.getY();
+ setTarget(objAnimator1, view);
+ startSingleAnimation(objAnimator1);
+ assertTrue("Keyframe should get a value when target is set to another view of the same"
+ + " class", emptyKeyframe1.hasValue());
+ assertEquals("Keyframe should get the updated Y value when target is set to another view"
+ + " of the same class", emptyKeyframe1.getValue(), updatedY);
+ waitUntilFinished(objAnimator1, mDuration * 2);
+ assertEquals("Animation should run as expected", 100f, mActivity.view.newBall.getY());
+ }
+
public void testOffloat() throws Throwable {
float[] values = {mStartY, mEndY};
PropertyValuesHolder pVHolder = PropertyValuesHolder.ofFloat(mProperty, values);
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/CanvasCompareActivityTest.java b/tests/tests/uirendering/src/android/uirendering/cts/CanvasCompareActivityTest.java
index c822ef2..0b205f5 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/CanvasCompareActivityTest.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/CanvasCompareActivityTest.java
@@ -61,7 +61,9 @@
@Override
public void setUp() {
mDifferenceVisualizer = new PassFailVisualizer();
- mRenderScript = RenderScript.create(getActivity().getApplicationContext());
+ if (USE_RS) {
+ mRenderScript = RenderScript.create(getActivity().getApplicationContext());
+ }
}
/**
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/DisplayModifier.java b/tests/tests/uirendering/src/android/uirendering/cts/DisplayModifier.java
index a884c5f..2f44e4a 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/DisplayModifier.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/DisplayModifier.java
@@ -18,6 +18,7 @@
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.PorterDuff;
+import android.graphics.PorterDuffColorFilter;
import android.graphics.PorterDuffXfermode;
import android.graphics.RectF;
@@ -38,6 +39,9 @@
};
private static final int NUM_PARALLEL_LINES = 24;
private static final float[] gLinePts = new float[NUM_PARALLEL_LINES * 8 + gTriPts.length];
+ private static final int FILTER_COLOR = 0xFFBB0000;
+ protected static final int MODIFIER_WIDTH = 180;
+ protected static final int MODIFIER_HEIGHT = 180;
static {
int index;
@@ -256,6 +260,25 @@
paint.setShader(ResourceModifier.instance().scaledShader);
}
});
+ put("composeShader", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setShader(ResourceModifier.instance().composeShader);
+ }
+ });
+ put("bad composeShader", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setShader(ResourceModifier.instance().nestedComposeShader);
+ }
+ });
+ put("bad composeShader 2", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setShader(
+ ResourceModifier.instance().doubleGradientComposeShader);
+ }
+ });
put("horGradient", new DisplayModifier() {
@Override
public void modifyDrawing(Paint paint, Canvas canvas) {
@@ -286,25 +309,6 @@
paint.setShader(ResourceModifier.instance().sweepGradient);
}
});
- put("composeShader", new DisplayModifier() {
- @Override
- public void modifyDrawing(Paint paint, Canvas canvas) {
- paint.setShader(ResourceModifier.instance().composeShader);
- }
- });
- put("bad composeShader", new DisplayModifier() {
- @Override
- public void modifyDrawing(Paint paint, Canvas canvas) {
- paint.setShader(ResourceModifier.instance().nestedComposeShader);
- }
- });
- put("bad composeShader 2", new DisplayModifier() {
- @Override
- public void modifyDrawing(Paint paint, Canvas canvas) {
- paint.setShader(
- ResourceModifier.instance().doubleGradientComposeShader);
- }
- });
}
});
@@ -391,6 +395,102 @@
}
});
+ put("colorfilters", new LinkedHashMap<String, DisplayModifier>() {
+ {
+ put("SRC", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SRC));
+ }
+ });
+ put("DST", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.DST));
+ }
+ });
+ put("SRC_OVER", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SRC_OVER));
+ }
+ });
+ put("DST_OVER", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.DST_OVER));
+ }
+ });
+ put("SRC_IN", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SRC_IN));
+ }
+ });
+ put("DST_IN", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.DST_IN));
+ }
+ });
+ put("SRC_OUT", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SRC_OUT));
+ }
+ });
+ put("DST_OUT", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.DST_OUT));
+ }
+ });
+ put("SRC_ATOP", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SRC_ATOP));
+ }
+ });
+ put("DST_ATOP", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.DST_ATOP));
+ }
+ });
+ put("XOR", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.XOR));
+ }
+ });
+ put("MULTIPLY", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.MULTIPLY));
+ }
+ });
+ put("SCREEN", new DisplayModifier() {
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ paint.setColorFilter(new PorterDuffColorFilter(FILTER_COLOR,
+ PorterDuff.Mode.SCREEN));
+ }
+ });
+ }
+ });
+
// FINAL MAP: DOES ACTUAL DRAWING
put("drawing", new LinkedHashMap<String, DisplayModifier>() {
{
@@ -474,17 +574,18 @@
abstract public void modifyDrawing(Paint paint, Canvas canvas);
public static class Accessor {
- public final static int AA_MASK = 0x1 << 0;
- public final static int STYLE_MASK = 0x1 << 1;
- public final static int STROKE_WIDTH_MASK = 0x1 << 2;
- public final static int STROKE_CAP_MASK = 0x1 << 3;
- public final static int STROKE_JOIN_MASK = 0x1 << 4;
- public final static int TRANSFORM_MASK = 0x1 << 5;
- public final static int SHADER_MASK = 0x1 << 6;
- public final static int XFERMODE_MASK = 0x1 << 7;
- public final static int SHAPES_MASK = 0x1 << 8;
- public final static int ALL_OPTIONS_MASK = 0x1FF;
- public final static int SHAPES_INDEX = 8;
+ public final static int AA_MASK = 0x1 << 0;
+ public final static int STYLE_MASK = 0x1 << 1;
+ public final static int STROKE_WIDTH_MASK = 0x1 << 2;
+ public final static int STROKE_CAP_MASK = 0x1 << 3;
+ public final static int STROKE_JOIN_MASK = 0x1 << 4;
+ public final static int TRANSFORM_MASK = 0x1 << 5;
+ public final static int SHADER_MASK = 0x1 << 6;
+ public final static int XFERMODE_MASK = 0x1 << 7;
+ public final static int COLOR_FILTER_MASK = 0x1 << 8;
+ public final static int SHAPES_MASK = 0x1 << 9;
+ public final static int ALL_OPTIONS_MASK = (0x1 << 10) - 1;
+ public final static int SHAPES_INDEX = 9;
public final static int XFERMODE_INDEX = 7;
private final int mMask;
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/SweepTests.java b/tests/tests/uirendering/src/android/uirendering/cts/SweepTests.java
index e92fc1e..1a9b6a1 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/SweepTests.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/SweepTests.java
@@ -18,14 +18,21 @@
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
+import android.graphics.LinearGradient;
import android.graphics.Paint;
import android.graphics.Point;
+import android.graphics.PorterDuff;
+import android.graphics.Rect;
import android.graphics.RectF;
+import android.graphics.Shader;
import android.test.suitebuilder.annotation.SmallTest;
import android.uirendering.cts.differencecalculators.DifferenceCalculator;
import android.uirendering.cts.differencecalculators.MSSIMCalculator;
import android.uirendering.cts.differencecalculators.SamplePointsCalculator;
+import java.util.LinkedHashMap;
+import java.util.Map;
+
/**
* Test cases of all combination of resource modifications.
*/
@@ -36,29 +43,11 @@
public static final int MULTIPLY_COLOR = 0xFF668844;
public static final int SCREEN_COLOR = 0xFFFFEEFF;
- /**
- * There are 4 locations we care about in XFermode testing.
- *
- * 1) Both empty
- * 2) Only src, dst empty
- * 3) Both src + dst
- * 4) Only dst, src empty
- */
- private final int[][] XFERMODE_COLOR_ARRAYS = new int[][] {
- {BG_COLOR, BG_COLOR, SRC_COLOR, SRC_COLOR},
- {BG_COLOR, DST_COLOR, DST_COLOR, BG_COLOR},
- {BG_COLOR, DST_COLOR, SRC_COLOR, SRC_COLOR},
- {BG_COLOR, DST_COLOR, DST_COLOR, SRC_COLOR},
- {BG_COLOR, BG_COLOR, SRC_COLOR, BG_COLOR},
- {BG_COLOR, BG_COLOR, DST_COLOR, BG_COLOR},
- {BG_COLOR, BG_COLOR, BG_COLOR, SRC_COLOR},
- {BG_COLOR, DST_COLOR, BG_COLOR, BG_COLOR},
- {BG_COLOR, DST_COLOR, SRC_COLOR, BG_COLOR},
- {BG_COLOR, BG_COLOR, DST_COLOR, SRC_COLOR},
- {BG_COLOR, DST_COLOR, BG_COLOR, SRC_COLOR},
- {BG_COLOR, BG_COLOR, MULTIPLY_COLOR, BG_COLOR},
- {BG_COLOR, DST_COLOR, SCREEN_COLOR, SRC_COLOR}
- };
+ public static final int FILTER_COLOR = 0xFFBB0000;
+ public static final int RECT0_COLOR = 0x33808080;
+ public static final int RECT1_COLOR = 0x66808080;
+ public static final int RECT2_COLOR = 0x99808080;
+ public static final int RECT3_COLOR = 0xCC808080;
// These points are in pairs, the first being the lower left corner, the second is only in the
// Destination bitmap, the third is the intersection of the two bitmaps, and the fourth is in
@@ -67,9 +56,71 @@
new Point(1, 160), new Point(50, 50), new Point(70, 70), new Point(140, 140)
};
+ /**
+ * There are 4 locations we care about in any filter testing.
+ *
+ * 1) Both empty
+ * 2) Only src, dst empty
+ * 3) Both src + dst
+ * 4) Only dst, src empty
+ */
+ private final Map<PorterDuff.Mode, int[]> XFERMODE_COLOR_MAP = new LinkedHashMap<PorterDuff.Mode, int[]>() {
+ {
+ put(PorterDuff.Mode.SRC, new int[] {
+ BG_COLOR, BG_COLOR, SRC_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.DST, new int[] {
+ BG_COLOR, DST_COLOR, DST_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.SRC_OVER, new int[] {
+ BG_COLOR, DST_COLOR, SRC_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.DST_OVER, new int[] {
+ BG_COLOR, DST_COLOR, DST_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.SRC_IN, new int[] {
+ BG_COLOR, BG_COLOR, SRC_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.DST_IN, new int[] {
+ BG_COLOR, BG_COLOR, DST_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.SRC_OUT, new int[] {
+ BG_COLOR, BG_COLOR, BG_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.DST_OUT, new int[] {
+ BG_COLOR, DST_COLOR, BG_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.SRC_ATOP, new int[] {
+ BG_COLOR, DST_COLOR, SRC_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.DST_ATOP, new int[] {
+ BG_COLOR, BG_COLOR, DST_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.XOR, new int[] {
+ BG_COLOR, DST_COLOR, BG_COLOR, SRC_COLOR
+ });
+
+ put(PorterDuff.Mode.MULTIPLY, new int[] {
+ BG_COLOR, BG_COLOR, MULTIPLY_COLOR, BG_COLOR
+ });
+
+ put(PorterDuff.Mode.SCREEN, new int[] {
+ BG_COLOR, DST_COLOR, SCREEN_COLOR, SRC_COLOR
+ });
+ }
+ };
+
private final static DisplayModifier XFERMODE_MODIFIER = new DisplayModifier() {
- private final static int mWidth = 180;
- private final static int mHeight = 180;
private final RectF mSrcRect = new RectF(60, 60, 160, 160);
private final RectF mDstRect = new RectF(20, 20, 120, 120);
private final Bitmap mSrcBitmap = createSrc();
@@ -80,14 +131,13 @@
// Draw the background
canvas.drawColor(Color.WHITE);
- int sc = canvas.saveLayer(0, 0, mWidth, mHeight, null);
canvas.drawBitmap(mDstBitmap, 0, 0, null);
canvas.drawBitmap(mSrcBitmap, 0, 0, paint);
- canvas.restoreToCount(sc);
}
private Bitmap createSrc() {
- Bitmap srcB = Bitmap.createBitmap(mWidth, mHeight, Bitmap.Config.ARGB_8888);
+ Bitmap srcB = Bitmap.createBitmap(MODIFIER_WIDTH, MODIFIER_HEIGHT,
+ Bitmap.Config.ARGB_8888);
Canvas srcCanvas = new Canvas(srcB);
Paint srcPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
srcPaint.setColor(SRC_COLOR);
@@ -96,7 +146,8 @@
}
private Bitmap createDst() {
- Bitmap dstB = Bitmap.createBitmap(mWidth, mHeight, Bitmap.Config.ARGB_8888);
+ Bitmap dstB = Bitmap.createBitmap(MODIFIER_WIDTH, MODIFIER_HEIGHT,
+ Bitmap.Config.ARGB_8888);
Canvas dstCanvas = new Canvas(dstB);
Paint dstPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
dstPaint.setColor(DST_COLOR);
@@ -105,6 +156,120 @@
}
};
+
+ // We care about one point in each of the four rectangles of different alpha values, as well as
+ // the area outside the rectangles
+ private final static Point[] COLOR_FILTER_ALPHA_POINTS = new Point[] {
+ new Point(15, 90), new Point(45, 90), new Point(75, 90), new Point(105, 90),
+ new Point(135, 90)
+ };
+
+ private final Map<PorterDuff.Mode, int[]> COLOR_FILTER_ALPHA_MAP = new LinkedHashMap<PorterDuff.Mode, int[]>() {
+ {
+ put(PorterDuff.Mode.SRC, new int[] {
+ FILTER_COLOR, FILTER_COLOR, FILTER_COLOR, FILTER_COLOR, FILTER_COLOR
+ });
+
+ put(PorterDuff.Mode.DST, new int[] {
+ 0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.SRC_OVER, new int[] {
+ 0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000, 0xFFBB0000
+ });
+
+ put(PorterDuff.Mode.DST_OVER, new int[] {
+ 0xFFAF1A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000
+ });
+
+ put(PorterDuff.Mode.SRC_IN, new int[] {
+ 0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC83333, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.DST_IN, new int[] {
+ 0xFFE6E6E6, 0xFFCCCCCC, 0xFFB3B3B3, 0xFF999999, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.SRC_OUT, new int[] {
+ 0xFFC83333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000
+ });
+
+ put(PorterDuff.Mode.DST_OUT, new int[] {
+ 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.SRC_ATOP, new int[] {
+ 0xFFF1CCCC, 0xFFE49999, 0xFFD66666, 0xFFC93333, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.DST_ATOP, new int[] {
+ 0xFFB01A1A, 0xFFA33333, 0xFF984D4D, 0xFF8B6666, 0xFFBB0000
+ });
+
+ put(PorterDuff.Mode.XOR, new int[] {
+ 0xFFC93333, 0xFFD66666, 0xFFE49999, 0xFFF1CCCC, 0xFFBB0000
+ });
+
+ put(PorterDuff.Mode.MULTIPLY, new int[] {
+ 0xFFDFCCCC, 0xFFBE9999, 0xFF9E6666, 0xFF7E3333, 0xFFFFFFFF
+ });
+
+ put(PorterDuff.Mode.SCREEN, new int[] {
+ 0xFFC21A1A, 0xFFC93333, 0xFFD04D4D, 0xFFD66666, 0xFFBB0000
+ });
+ }
+ };
+
+ private final static DisplayModifier COLOR_FILTER_ALPHA_MODIFIER = new DisplayModifier() {
+ private final static int mBlockWidths = 30;
+ private final int[] mColorValues = new int[] {RECT0_COLOR, RECT1_COLOR, RECT2_COLOR,
+ RECT3_COLOR};
+
+ private final Bitmap mBitmap = createQuadRectBitmap();
+
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ canvas.drawBitmap(mBitmap, 0, 0, paint);
+ }
+
+ private Bitmap createQuadRectBitmap() {
+ Bitmap bitmap = Bitmap.createBitmap(MODIFIER_WIDTH, MODIFIER_HEIGHT,
+ Bitmap.Config.ARGB_8888);
+ Canvas canvas = new Canvas(bitmap);
+ Paint paint = new Paint();
+ for (int i = 0 ; i < 4 ; i++) {
+ paint.setColor(mColorValues[i]);
+ canvas.drawRect(i * mBlockWidths, 0, (i + 1) * mBlockWidths, MODIFIER_HEIGHT, paint);
+ }
+ return bitmap;
+ }
+ };
+
+ private final static DisplayModifier COLOR_FILTER_GRADIENT_MODIFIER = new DisplayModifier() {
+ private final Rect mBounds = new Rect(30, 30, 150, 150);
+ private final int[] mColors = new int[] {
+ Color.RED, Color.GREEN, Color.BLUE
+ };
+
+ private final Bitmap mBitmap = createGradient();
+
+ @Override
+ public void modifyDrawing(Paint paint, Canvas canvas) {
+ canvas.drawBitmap(mBitmap, 0, 0, paint);
+ }
+
+ private Bitmap createGradient() {
+ LinearGradient gradient = new LinearGradient(30, 90, 150, 90, mColors, null,
+ Shader.TileMode.REPEAT);
+ Bitmap bitmap = Bitmap.createBitmap(MODIFIER_WIDTH, MODIFIER_HEIGHT,
+ Bitmap.Config.ARGB_8888);
+ Paint p = new Paint();
+ p.setShader(gradient);
+ Canvas c = new Canvas(bitmap);
+ c.drawRect(mBounds, p);
+ return bitmap;
+ }
+ };
+
/**
* In this case, a lower number would mean it is easier to pass the test. In terms of MSSIM,
* a 1 would indicate that the images are exactly the same, where as 0.1 is vastly different.
@@ -128,19 +293,44 @@
}
@SmallTest
- public void testShaderDraws() {
+ public void testBasicShaders() {
DifferenceCalculator[] calculators = new DifferenceCalculator[1];
calculators[0] = new MSSIMCalculator(HIGH_THRESHOLD);
sweepModifiersForMask(DisplayModifier.Accessor.SHADER_MASK, mCircleDrawModifier,
- calculators);
+ calculators);
+ }
+
+ @SmallTest
+ public void testColorFilterUsingGradient() {
+ DifferenceCalculator[] calculators = new DifferenceCalculator[1];
+ calculators[0] = new MSSIMCalculator(HIGH_THRESHOLD);
+ sweepModifiersForMask(DisplayModifier.Accessor.COLOR_FILTER_MASK,
+ COLOR_FILTER_GRADIENT_MODIFIER, calculators);
+ }
+
+ @SmallTest
+ public void testColorFiltersAlphas() {
+ DifferenceCalculator[] calculators =
+ new DifferenceCalculator[COLOR_FILTER_ALPHA_MAP.keySet().size()];
+ int index = 0;
+ for (PorterDuff.Mode mode: COLOR_FILTER_ALPHA_MAP.keySet()) {
+ calculators[index] = new SamplePointsCalculator(COLOR_FILTER_ALPHA_POINTS,
+ COLOR_FILTER_ALPHA_MAP.get(mode));
+ index++;
+ }
+ sweepModifiersForMask(DisplayModifier.Accessor.COLOR_FILTER_MASK,
+ COLOR_FILTER_ALPHA_MODIFIER, calculators);
}
@SmallTest
public void testXfermodes() {
- DifferenceCalculator[] calculators = new DifferenceCalculator[XFERMODE_COLOR_ARRAYS.length];
- for (int i = 0 ; i < XFERMODE_COLOR_ARRAYS.length ; i++) {
- calculators[i] = new SamplePointsCalculator(XFERMODE_TEST_POINTS,
- XFERMODE_COLOR_ARRAYS[i]);
+ DifferenceCalculator[] calculators =
+ new DifferenceCalculator[XFERMODE_COLOR_MAP.keySet().size()];
+ int index = 0;
+ for (PorterDuff.Mode mode: XFERMODE_COLOR_MAP.keySet()) {
+ calculators[index] = new SamplePointsCalculator(XFERMODE_TEST_POINTS,
+ XFERMODE_COLOR_MAP.get(mode));
+ index++;
}
sweepModifiersForMask(DisplayModifier.Accessor.XFERMODE_MASK, XFERMODE_MODIFIER,
calculators);
diff --git a/tests/tests/uirendering/src/android/uirendering/cts/differencecalculators/MSSIMCalculator.java b/tests/tests/uirendering/src/android/uirendering/cts/differencecalculators/MSSIMCalculator.java
index 9e6a0c1..3facdd9 100644
--- a/tests/tests/uirendering/src/android/uirendering/cts/differencecalculators/MSSIMCalculator.java
+++ b/tests/tests/uirendering/src/android/uirendering/cts/differencecalculators/MSSIMCalculator.java
@@ -33,13 +33,13 @@
public class MSSIMCalculator extends BaseRenderScriptCalculator{
// These values were taken from the publication
public static final boolean DEBUG = false;
- public static final String TAG = "MSSIM";
+ public static final String TAG_NAME = "MSSIM";
public static final double CONSTANT_L = 254;
public static final double CONSTANT_K1 = 0.00001;
public static final double CONSTANT_K2 = 0.00003;
public static final double CONSTANT_C1 = Math.pow(CONSTANT_L * CONSTANT_K1, 2);
public static final double CONSTANT_C2 = Math.pow(CONSTANT_L * CONSTANT_K2, 2);
- public static final int WINDOW_SIZE = 3;
+ public static final int WINDOW_SIZE = 10;
private double mThreshold;
private ScriptC_MSSIMCalculator mScript;
@@ -73,13 +73,16 @@
}
}
- if (windows == 0) { //if they were both white screens then we are good
+ if (windows == 0) {
return true;
}
SSIMTotal /= windows;
- Log.d(TAG, "MSSIM : " + SSIMTotal);
+ if (DEBUG) {
+ Log.d(TAG_NAME, "MSSIM = " + SSIMTotal);
+ Log.d(TAG_NAME, "Number of Windows : " + windows);
+ }
return (SSIMTotal >= mThreshold);
}
@@ -105,7 +108,9 @@
float MSSIM = sum1DFloatAllocation(outputAllocation);
MSSIM /= height;
- Log.d(TAG, "MSSIM RS : " + MSSIM);
+ if (DEBUG) {
+ Log.d(TAG_NAME, "MSSIM RS : " + MSSIM);
+ }
return (MSSIM >= mThreshold);
}