summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Karthik Ravi Shankar <karthikrs@google.com> 2017-03-08 18:30:19 -0800
committer Karthik Ravi Shankar <karthikrs@google.com> 2017-03-31 08:37:05 -0700
commit99493dbc94989d4493ca6acb0db265a02f49f62e (patch)
tree51027bd546651df503e5e4e78244b342abd985d6
parent79a973f643c7f9e54b698da0fcee8e6152a0d805 (diff)
Launch 2D activities in VR mode
When in VR mode, launch all activities into the virtual display ID as provided by the Compatibility display. This includes two cases - - New activity launches - Existing activity in the background. Testing Done: Tested with PlanarVirtualDisplay app and Settings, Calculator and GestureApp with different intent flags. Bug: 36071574 Bug: 36071445 Test: android.server.cts.ActivityManagerDisplayTests Test: #testVrActivityLaunch Test: #testVrActivityReLaunch Change-Id: Ic590a7cbd6f9b339dc83b22a8ffb1252219ef22e Signed-off-by: Karthik Ravi Shankar <karthikrs@google.com>
-rw-r--r--core/java/android/app/ActivityManagerInternal.java7
-rw-r--r--services/core/java/com/android/server/am/ActivityManagerService.java20
-rw-r--r--services/core/java/com/android/server/am/ActivityStarter.java56
-rw-r--r--services/core/java/com/android/server/vr/CompatibilityDisplay.java16
-rw-r--r--services/core/java/com/android/server/vr/VrManagerService.java5
5 files changed, 96 insertions, 8 deletions
diff --git a/core/java/android/app/ActivityManagerInternal.java b/core/java/android/app/ActivityManagerInternal.java
index dbcdecc168c7..65cb5f492285 100644
--- a/core/java/android/app/ActivityManagerInternal.java
+++ b/core/java/android/app/ActivityManagerInternal.java
@@ -241,4 +241,11 @@ public abstract class ActivityManagerInternal {
* {@param procStateSeq}.
*/
public abstract void notifyNetworkPolicyRulesUpdated(int uid, long procStateSeq);
+
+ /**
+ * Called after virtual display Id is updated by
+ * {@link com.android.server.vr.CompatibilityDisplay} with a specific
+ * {@param compatibilityDisplayId}.
+ */
+ public abstract void setVrCompatibilityDisplayId(int vrCompatibilityDisplayId);
}
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index ead1b26a0a1f..f5d9c1cf297b 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -59,6 +59,7 @@ import static android.provider.Settings.Global.WAIT_FOR_DEBUGGER;
import static android.provider.Settings.System.FONT_SCALE;
import static android.service.voice.VoiceInteractionSession.SHOW_SOURCE_APPLICATION;
import static android.view.Display.DEFAULT_DISPLAY;
+import static android.view.Display.INVALID_DISPLAY;
import static com.android.internal.util.XmlUtils.readBooleanAttribute;
import static com.android.internal.util.XmlUtils.readIntAttribute;
import static com.android.internal.util.XmlUtils.readLongAttribute;
@@ -689,6 +690,9 @@ public class ActivityManagerService extends IActivityManager.Stub
}
};
+ // VR Compatibility Display Id.
+ int mVrCompatibilityDisplayId = INVALID_DISPLAY;
+
// Whether we should use SCHED_FIFO for UI and RenderThreads.
private boolean mUseFifoUiScheduling = false;
@@ -23526,6 +23530,22 @@ public class ActivityManagerService extends IActivityManager.Stub
}
}
}
+
+ /**
+ * Called after virtual display Id is updated by
+ * {@link com.android.server.vr.CompatibilityDisplay} with a specific
+ * {@param vrCompatibilityDisplayId}.
+ */
+ @Override
+ public void setVrCompatibilityDisplayId(int vrCompatibilityDisplayId) {
+ if (DEBUG_STACK) {
+ Slog.d(TAG, "setVrCompatibilityDisplayId called for: " +
+ vrCompatibilityDisplayId);
+ }
+ synchronized (ActivityManagerService.this) {
+ mVrCompatibilityDisplayId = vrCompatibilityDisplayId;
+ }
+ }
}
/**
diff --git a/services/core/java/com/android/server/am/ActivityStarter.java b/services/core/java/com/android/server/am/ActivityStarter.java
index 9258539f4268..68036f3af61a 100644
--- a/services/core/java/com/android/server/am/ActivityStarter.java
+++ b/services/core/java/com/android/server/am/ActivityStarter.java
@@ -125,8 +125,10 @@ import android.view.Display;
import com.android.internal.app.HeavyWeightSwitcherActivity;
import com.android.internal.app.IVoiceInteractor;
+import com.android.server.LocalServices;
import com.android.server.am.ActivityStackSupervisor.PendingActivityLaunch;
import com.android.server.pm.InstantAppResolver;
+import com.android.server.vr.VrManagerInternal;
import com.android.server.wm.WindowManagerService;
import java.util.ArrayList;
@@ -192,6 +194,8 @@ class ActivityStarter {
private IVoiceInteractionSession mVoiceSession;
private IVoiceInteractor mVoiceInteractor;
+ private boolean mUsingVrCompatibilityDisplay;
+
private void reset() {
mStartActivity = null;
mIntent = null;
@@ -229,12 +233,15 @@ class ActivityStarter {
mVoiceSession = null;
mVoiceInteractor = null;
+
+ mUsingVrCompatibilityDisplay = false;
}
ActivityStarter(ActivityManagerService service, ActivityStackSupervisor supervisor) {
mService = service;
mSupervisor = supervisor;
mInterceptor = new ActivityStartInterceptor(mService, mSupervisor);
+ mUsingVrCompatibilityDisplay = false;
}
final int startActivityLocked(IApplicationThread caller, Intent intent, Intent ephemeralIntent,
@@ -1208,10 +1215,7 @@ class ActivityStarter {
mVoiceSession = voiceSession;
mVoiceInteractor = voiceInteractor;
- mSourceDisplayId = sourceRecord != null ? sourceRecord.getDisplayId() : INVALID_DISPLAY;
- if (mSourceDisplayId == INVALID_DISPLAY) {
- mSourceDisplayId = DEFAULT_DISPLAY;
- }
+ mSourceDisplayId = getSourceDisplayId(mSourceRecord, mStartActivity);
mLaunchBounds = getOverrideBounds(r, options, inTask);
@@ -1466,6 +1470,36 @@ class ActivityStarter {
}
/**
+ * Returns the ID of the display to use for a new activity. If the source activity has
+ * a explicit display ID set, use that to launch the activity. If not and the device is in VR
+ * mode, then return the Vr mode's virtual display ID.
+ */
+ private int getSourceDisplayId(ActivityRecord sourceRecord, ActivityRecord startingActivity) {
+ int displayId = sourceRecord != null ? sourceRecord.getDisplayId() : INVALID_DISPLAY;
+ // If the activity has a displayId set explicitly, launch it on the same displayId.
+ if (displayId != INVALID_DISPLAY) {
+ return displayId;
+ }
+
+ // Check if the Activity is a VR activity. If so, the activity should be launched in
+ // main display.
+ if (startingActivity != null && startingActivity.requestedVrComponent != null) {
+ return DEFAULT_DISPLAY;
+ }
+
+ // Get the virtual display id from ActivityManagerService.
+ displayId = mService.mVrCompatibilityDisplayId;
+ if (displayId != INVALID_DISPLAY) {
+ if (DEBUG_STACK) {
+ Slog.d(TAG, "getSourceDisplayId :" + displayId);
+ }
+ mUsingVrCompatibilityDisplay = true;
+ return displayId;
+ }
+ return DEFAULT_DISPLAY;
+ }
+
+ /**
* Figure out which task and activity to bring to front when we have found an existing matching
* activity record in history. May also clear the task if needed.
* @param intentActivity Existing matching activity.
@@ -2073,8 +2107,18 @@ class ActivityStarter {
return mSupervisor.getValidLaunchStackOnDisplay(launchDisplayId, r);
}
- if ((launchFlags & FLAG_ACTIVITY_LAUNCH_ADJACENT) == 0
- || mSourceDisplayId != DEFAULT_DISPLAY) {
+ // If we are using Vr compatibility display, find the virtual display stack.
+ if (mUsingVrCompatibilityDisplay) {
+ ActivityStack as = mSupervisor.getValidLaunchStackOnDisplay(mSourceDisplayId, r);
+ if (DEBUG_STACK) {
+ Slog.v(TAG, "Launch stack for app: " + r.toString() +
+ ", on virtual display stack:" + as.toString());
+ }
+ return as;
+ }
+
+ if (((launchFlags & FLAG_ACTIVITY_LAUNCH_ADJACENT) == 0)
+ || mSourceDisplayId != DEFAULT_DISPLAY) {
return null;
}
// Otherwise handle adjacent launch.
diff --git a/services/core/java/com/android/server/vr/CompatibilityDisplay.java b/services/core/java/com/android/server/vr/CompatibilityDisplay.java
index a8d622353636..ae1d50ff1f71 100644
--- a/services/core/java/com/android/server/vr/CompatibilityDisplay.java
+++ b/services/core/java/com/android/server/vr/CompatibilityDisplay.java
@@ -2,6 +2,7 @@ package com.android.server.vr;
import static android.view.Display.INVALID_DISPLAY;
+import android.app.ActivityManagerInternal;
import android.app.Service;
import android.content.BroadcastReceiver;
import android.content.Context;
@@ -48,6 +49,7 @@ class CompatibilityDisplay {
private final static String DEBUG_EXTRA_SURFACE =
"com.android.server.vr.CompatibilityDisplay.EXTRA_SURFACE";
+ private final ActivityManagerInternal mActivityManagerInternal;
private final DisplayManager mDisplayManager;
private final IVrManager mVrManager;
private final Object mVdLock = new Object();
@@ -74,8 +76,10 @@ class CompatibilityDisplay {
private boolean mIsVrModeOverrideEnabled;
private boolean mIsVrModeEnabled;
- public CompatibilityDisplay(DisplayManager displayManager, IVrManager vrManager) {
+ public CompatibilityDisplay(DisplayManager displayManager,
+ ActivityManagerInternal activityManagerInternal, IVrManager vrManager) {
mDisplayManager = displayManager;
+ mActivityManagerInternal = activityManagerInternal;
mVrManager = vrManager;
}
@@ -200,6 +204,15 @@ class CompatibilityDisplay {
mVirtualDisplay = mDisplayManager.createVirtualDisplay("VR 2D Display", WIDTH, HEIGHT,
DPI, null /* Surface */, 0 /* flags */);
+
+ if (mVirtualDisplay != null) {
+ mActivityManagerInternal.setVrCompatibilityDisplayId(
+ mVirtualDisplay.getDisplay().getDisplayId());
+ } else {
+ Log.w(TAG, "Virtual display id is null after createVirtualDisplay");
+ mActivityManagerInternal.setVrCompatibilityDisplayId(INVALID_DISPLAY);
+ return;
+ }
}
if (DEBUG) {
@@ -222,6 +235,7 @@ class CompatibilityDisplay {
} else {
Log.i(TAG, "Stopping Virtual Display");
synchronized (mVdLock) {
+ mActivityManagerInternal.setVrCompatibilityDisplayId(INVALID_DISPLAY);
setSurfaceLocked(null); // clean up and release the surface first.
if (mVirtualDisplay != null) {
mVirtualDisplay.release();
diff --git a/services/core/java/com/android/server/vr/VrManagerService.java b/services/core/java/com/android/server/vr/VrManagerService.java
index 731f53f37af2..324faff8e781 100644
--- a/services/core/java/com/android/server/vr/VrManagerService.java
+++ b/services/core/java/com/android/server/vr/VrManagerService.java
@@ -18,6 +18,7 @@ package com.android.server.vr;
import static android.view.Display.INVALID_DISPLAY;
import android.Manifest;
+import android.app.ActivityManagerInternal;
import android.app.ActivityManager;
import android.app.AppOpsManager;
import android.app.NotificationManager;
@@ -54,6 +55,7 @@ import android.util.Slog;
import android.util.SparseArray;
import com.android.internal.R;
+import com.android.server.LocalServices;
import com.android.server.SystemConfig;
import com.android.server.SystemService;
import com.android.server.utils.ManagedApplicationService.PendingEvent;
@@ -594,7 +596,8 @@ public class VrManagerService extends SystemService implements EnabledComponentC
DisplayManager dm =
(DisplayManager) getContext().getSystemService(Context.DISPLAY_SERVICE);
- mCompatibilityDisplay = new CompatibilityDisplay(dm, mVrManager);
+ ActivityManagerInternal ami = LocalServices.getService(ActivityManagerInternal.class);
+ mCompatibilityDisplay = new CompatibilityDisplay(dm, ami, mVrManager);
mCompatibilityDisplay.init(getContext());
} else if (phase == SystemService.PHASE_THIRD_PARTY_APPS_CAN_START) {
synchronized (mLock) {