diff --git a/test-runner/android/test/ActivityUnitTestCase.java b/test-runner/android/test/ActivityUnitTestCase.java
new file mode 100644
index 0000000..dfd8fc2
--- /dev/null
+++ b/test-runner/android/test/ActivityUnitTestCase.java
@@ -0,0 +1,340 @@
+/*
+ * Copyright (C) 2008 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.test;
+
+import android.app.Activity;
+import android.app.Application;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.content.pm.ActivityInfo;
+import android.os.Bundle;
+import android.os.IBinder;
+import android.test.mock.MockApplication;
+import android.view.Window;
+
+/**
+ * This class provides isolated testing of a single activity.  The activity under test will
+ * be created with minimal connection to the system infrastructure, and you can inject mocked or 
+ * wrappered versions of many of Activity's dependencies.  Most of the work is handled
+ * automatically here by {@link #setUp} and {@link #tearDown}.
+ * 
+ * <p>If you prefer a functional test, see {@link android.test.ActivityInstrumentationTestCase}.
+ * 
+ * <p>It must be noted that, as a true unit test, your Activity will not be running in the
+ * normal system and will not participate in the normal interactions with other Activities.  
+ * The following methods should not be called in this configuration - most of them will throw
+ * exceptions:
+ * <ul>
+ * <li>{@link android.app.Activity#createPendingResult(int, Intent, int)}</li>
+ * <li>{@link android.app.Activity#startActivityIfNeeded(Intent, int)}</li>
+ * <li>{@link android.app.Activity#startActivityFromChild(Activity, Intent, int)}</li>
+ * <li>{@link android.app.Activity#startNextMatchingActivity(Intent)}</li>
+ * <li>{@link android.app.Activity#getCallingActivity()}</li>
+ * <li>{@link android.app.Activity#getCallingPackage()}</li>
+ * <li>{@link android.app.Activity#createPendingResult(int, Intent, int)}</li>
+ * <li>{@link android.app.Activity#getTaskId()}</li>
+ * <li>{@link android.app.Activity#isTaskRoot()}</li>
+ * <li>{@link android.app.Activity#moveTaskToBack(boolean)}</li>
+ * <li>{@link android.app.Activity#setPersistent(boolean)}</li>
+ * </ul>
+ * 
+ * <p>The following methods may be called but will not do anything.  For test purposes, you can use 
+ * the methods {@link #getStartedActivityIntent()} and {@link #getStartedActivityRequest()} to 
+ * inspect the parameters that they were called with.
+ * <ul>
+ * <li>{@link android.app.Activity#startActivity(Intent)}</li>
+ * <li>{@link android.app.Activity#startActivityForResult(Intent, int)}</li>
+ * </ul>
+ *
+ * <p>The following methods may be called but will not do anything.  For test purposes, you can use 
+ * the methods {@link #isFinishCalled()} and {@link #getFinishedActivityRequest()} to inspect the 
+ * parameters that they were called with.
+ * <ul>
+ * <li>{@link android.app.Activity#finish()}</li>
+ * <li>{@link android.app.Activity#finishFromChild(Activity child)}</li>
+ * <li>{@link android.app.Activity#finishActivity(int requestCode)}</li>
+ * </ul>
+ *
+ */
+public abstract class ActivityUnitTestCase<T extends Activity> 
+        extends ActivityTestCase {
+
+    private Class<T> mActivityClass;
+
+    private Context mActivityContext;
+    private Application mApplication;
+    private MockParent mMockParent;
+
+    private boolean mAttached = false;
+    private boolean mCreated = false;
+
+    public ActivityUnitTestCase(Class<T> activityClass) {
+        mActivityClass = activityClass;
+    }
+
+    @Override
+    public T getActivity() {
+        return (T) super.getActivity();
+    }
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+
+        // default value for target context, as a default
+      mActivityContext = getInstrumentation().getTargetContext();
+    }
+    
+    /**
+     * Start the activity under test, in the same way as if it was started by
+     * {@link android.content.Context#startActivity Context.startActivity()}, providing the 
+     * arguments it supplied.  When you use this method to start the activity, it will automatically
+     * be stopped by {@link #tearDown}.
+     * 
+     * <p>This method will call onCreate(), but if you wish to further exercise Activity life 
+     * cycle methods, you must call them yourself from your test case.
+     * 
+     * <p><i>Do not call from your setUp() method.  You must call this method from each of your
+     * test methods.</i>
+     *  
+     * @param intent The Intent as if supplied to {@link android.content.Context#startActivity}.
+     * @param savedInstanceState The instance state, if you are simulating this part of the life
+     * cycle.  Typically null.
+     * @param lastNonConfigurationInstance This Object will be available to the 
+     * Activity if it calls {@link android.app.Activity#getLastNonConfigurationInstance()}.  
+     * Typically null.
+     * @return Returns the Activity that was created
+     */
+    protected T startActivity(Intent intent, Bundle savedInstanceState,
+            Object lastNonConfigurationInstance) {
+        assertFalse("Activity already created", mCreated);
+        
+        if (!mAttached) {
+            assertNotNull(mActivityClass);
+            setActivity(null);
+            T newActivity = null;
+            try {
+                IBinder token = null;
+                if (mApplication == null) {
+                    setApplication(new MockApplication());
+                }
+                ComponentName cn = new ComponentName(mActivityClass.getPackage().getName(), 
+                        mActivityClass.getName());
+                intent.setComponent(cn);
+                ActivityInfo info = null;
+                CharSequence title = mActivityClass.getName();
+                mMockParent = new MockParent();
+                String id = null;
+                        
+                newActivity = (T) getInstrumentation().newActivity(mActivityClass, mActivityContext,
+                        token, mApplication, intent, info, title, mMockParent, id,
+                        lastNonConfigurationInstance);
+            } catch (Exception e) {
+                assertNotNull(newActivity);
+            }
+            
+            assertNotNull(newActivity);
+            setActivity(newActivity);
+            
+            mAttached = true;
+        }
+        
+        T result = getActivity();
+        if (result != null) {
+            getInstrumentation().callActivityOnCreate(getActivity(), savedInstanceState);
+            mCreated = true;
+        }
+        return result;
+    }
+    
+    @Override
+    protected void tearDown() throws Exception {
+        
+        setActivity(null);
+        
+        // Scrub out members - protects against memory leaks in the case where someone 
+        // creates a non-static inner class (thus referencing the test case) and gives it to
+        // someone else to hold onto
+        scrubClass(ActivityInstrumentationTestCase.class);
+
+        super.tearDown();
+    }
+    
+    /**
+     * Set the application for use during the test.  You must call this function before calling 
+     * {@link #startActivity}.  If your test does not call this method,
+     * @param application The Application object that will be injected into the Activity under test.
+     */
+    public void setApplication(Application application) {
+        mApplication = application;
+    }
+
+    /**
+     * If you wish to inject a Mock, Isolated, or otherwise altered context, you can do so
+     * here.  You must call this function before calling {@link #startActivity}.  If you wish to
+     * obtain a real Context, as a building block, use getInstrumentation().getTargetContext().
+     */
+    public void setActivityContext(Context activityContext) {
+        mActivityContext = activityContext;
+    }
+
+    /**
+     * This method will return the value if your Activity under test calls 
+     * {@link android.app.Activity#setRequestedOrientation}.
+     */
+    public int getRequestedOrientation() {
+        if (mMockParent != null) {
+            return mMockParent.mRequestedOrientation;
+        }
+        return 0;
+    }
+    
+    /**
+     * This method will return the launch intent if your Activity under test calls 
+     * {@link android.app.Activity#startActivity(Intent)} or 
+     * {@link android.app.Activity#startActivityForResult(Intent, int)}.
+     * @return The Intent provided in the start call, or null if no start call was made.
+     */
+    public Intent getStartedActivityIntent() {
+        if (mMockParent != null) {
+            return mMockParent.mStartedActivityIntent;
+        }
+        return null;
+    }
+    
+    /**
+     * This method will return the launch request code if your Activity under test calls 
+     * {@link android.app.Activity#startActivityForResult(Intent, int)}.
+     * @return The request code provided in the start call, or -1 if no start call was made.
+     */
+    public int getStartedActivityRequest() {
+        if (mMockParent != null) {
+            return mMockParent.mStartedActivityRequest;
+        }
+        return 0;
+    }
+
+    /**
+     * This method will notify you if the Activity under test called 
+     * {@link android.app.Activity#finish()}, 
+     * {@link android.app.Activity#finishFromChild(Activity)}, or 
+     * {@link android.app.Activity#finishActivity(int)}.
+     * @return Returns true if one of the listed finish methods was called.
+     */
+    public boolean isFinishCalled() {
+        if (mMockParent != null) {
+            return mMockParent.mFinished;
+        }
+        return false;
+    }
+    
+    /**
+     * This method will return the request code if the Activity under test called 
+     * {@link android.app.Activity#finishActivity(int)}.
+     * @return The request code provided in the start call, or -1 if no finish call was made.
+     */
+    public int getFinishedActivityRequest() {
+        if (mMockParent != null) {
+            return mMockParent.mFinishedActivityRequest;
+        }
+        return 0;
+    }
+    
+    /**
+     * This mock Activity represents the "parent" activity.  By injecting this, we allow the user
+     * to call a few more Activity methods, including:
+     * <ul>
+     * <li>{@link android.app.Activity#getRequestedOrientation()}</li>
+     * <li>{@link android.app.Activity#setRequestedOrientation(int)}</li>
+     * <li>{@link android.app.Activity#finish()}</li>
+     * <li>{@link android.app.Activity#finishActivity(int requestCode)}</li>
+     * <li>{@link android.app.Activity#finishFromChild(Activity child)}</li>
+     * </ul>
+     * 
+     * TODO: Make this overrideable, and the unit test can look for calls to other methods
+     */
+    private static class MockParent extends Activity {
+
+        public int mRequestedOrientation = 0;
+        public Intent mStartedActivityIntent = null;
+        public int mStartedActivityRequest = -1;
+        public boolean mFinished = false;
+        public int mFinishedActivityRequest = -1;
+
+        /**
+         * Implementing in the parent allows the user to call this function on the tested activity.
+         */
+        @Override
+        public void setRequestedOrientation(int requestedOrientation) {
+            mRequestedOrientation = requestedOrientation;
+        }
+
+        /**
+         * Implementing in the parent allows the user to call this function on the tested activity.
+         */
+        @Override
+        public int getRequestedOrientation() {
+            return mRequestedOrientation;
+        }
+
+        /**
+         * By returning null here, we inhibit the creation of any "container" for the window.
+         */
+        @Override
+        public Window getWindow() {
+            return null;
+        }
+        
+        /**
+         * By defining this in the parent, we allow the tested activity to call
+         * <ul>
+         * <li>{@link android.app.Activity#startActivity(Intent)}</li>
+         * <li>{@link android.app.Activity#startActivityForResult(Intent, int)}</li>
+         * </ul>
+         */
+        @Override
+        public void startActivityFromChild(Activity child, Intent intent, int requestCode) {
+            mStartedActivityIntent = intent;
+            mStartedActivityRequest = requestCode;
+        }
+        
+        /**
+         * By defining this in the parent, we allow the tested activity to call
+         * <ul>
+         * <li>{@link android.app.Activity#finish()}</li>
+         * <li>{@link android.app.Activity#finishFromChild(Activity child)}</li>
+         * </ul>
+         */
+        @Override
+        public void finishFromChild(Activity child) {
+            mFinished = true;
+        }
+
+        /**
+         * By defining this in the parent, we allow the tested activity to call
+         * <ul>
+         * <li>{@link android.app.Activity#finishActivity(int requestCode)}</li>
+         * </ul>
+         */
+        @Override
+        public void finishActivityFromChild(Activity child, int requestCode) {
+            mFinished = true;
+            mFinishedActivityRequest = requestCode;
+        }
+    }
+}
