Commit 27fd4897 authored by mthiesse's avatar mthiesse Committed by Commit bot

Clean up VR Shell mode transitions (and fix potential webvr startup race).

BUG=668541
CQ_INCLUDE_TRYBOTS=master.tryserver.chromium.linux:closure_compilation

Review-Url: https://codereview.chromium.org/2536873002
Cr-Commit-Position: refs/heads/master@{#435010}
parent 338b38e0
...@@ -16,7 +16,7 @@ public interface VrShell { ...@@ -16,7 +16,7 @@ public interface VrShell {
/** /**
* Performs native VrShell initialization. * Performs native VrShell initialization.
*/ */
void initializeNative(Tab currentTab, VrShellDelegate delegate); void initializeNative(Tab currentTab, VrShellDelegate delegate, boolean forWebVR);
/** /**
* Pauses VrShell. * Pauses VrShell.
......
...@@ -154,10 +154,7 @@ public class VrShellDelegate { ...@@ -154,10 +154,7 @@ public class VrShellDelegate {
return; return;
} }
if (enterVR()) { if (enterVR()) {
if (mRequestedWebVR) { if (mRequestedWebVR) nativeSetPresentResult(mNativeVrShellDelegate, true);
nativeSetPresentResult(mNativeVrShellDelegate, true);
mVrShell.setWebVrModeEnabled(true);
}
} else { } else {
if (mRequestedWebVR) nativeSetPresentResult(mNativeVrShellDelegate, false); if (mRequestedWebVR) nativeSetPresentResult(mNativeVrShellDelegate, false);
if (!mVrDaydreamApi.exitFromVr(EXIT_VR_RESULT, new Intent())) { if (!mVrDaydreamApi.exitFromVr(EXIT_VR_RESULT, new Intent())) {
...@@ -186,7 +183,7 @@ public class VrShellDelegate { ...@@ -186,7 +183,7 @@ public class VrShellDelegate {
mTab.addObserver(mTabObserver); mTab.addObserver(mTabObserver);
addVrViews(); addVrViews();
setupVrModeWindowFlags(); setupVrModeWindowFlags();
mVrShell.initializeNative(mTab, this); mVrShell.initializeNative(mTab, this, mRequestedWebVR);
mVrShell.setCloseButtonListener(new Runnable() { mVrShell.setCloseButtonListener(new Runnable() {
@Override @Override
public void run() { public void run() {
......
...@@ -108,7 +108,7 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr ...@@ -108,7 +108,7 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr
} }
@Override @Override
public void initializeNative(Tab currentTab, VrShellDelegate delegate) { public void initializeNative(Tab currentTab, VrShellDelegate delegate, boolean forWebVR) {
assert currentTab.getContentViewCore() != null; assert currentTab.getContentViewCore() != null;
mTab = currentTab; mTab = currentTab;
mContentCVC = mTab.getContentViewCore(); mContentCVC = mTab.getContentViewCore();
...@@ -122,8 +122,8 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr ...@@ -122,8 +122,8 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr
uiContentView, mUiContents, mUiVrWindowAndroid); uiContentView, mUiContents, mUiVrWindowAndroid);
mNativeVrShell = nativeInit(mContentCVC.getWebContents(), mNativeVrShell = nativeInit(mContentCVC.getWebContents(),
mContentVrWindowAndroid.getNativePointer(), mContentVrWindowAndroid.getNativePointer(), mUiContents,
mUiContents, mUiVrWindowAndroid.getNativePointer()); mUiVrWindowAndroid.getNativePointer(), forWebVR);
mGlSurfaceView.setOnTouchListener(new View.OnTouchListener() { mGlSurfaceView.setOnTouchListener(new View.OnTouchListener() {
@Override @Override
@SuppressLint("ClickableViewAccessibility") @SuppressLint("ClickableViewAccessibility")
...@@ -362,7 +362,7 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr ...@@ -362,7 +362,7 @@ public class VrShellImpl extends GvrLayout implements GLSurfaceView.Renderer, Vr
} }
private native long nativeInit(WebContents contentWebContents, long nativeContentWindowAndroid, private native long nativeInit(WebContents contentWebContents, long nativeContentWindowAndroid,
WebContents uiWebContents, long nativeUiWindowAndroid); WebContents uiWebContents, long nativeUiWindowAndroid, boolean forWebVR);
private native void nativeSetDelegate(long nativeVrShell, VrShellDelegate delegate); private native void nativeSetDelegate(long nativeVrShell, VrShellDelegate delegate);
private native void nativeGvrInit(long nativeVrShell, long nativeGvrApi); private native void nativeGvrInit(long nativeVrShell, long nativeGvrApi);
private native void nativeDestroy(long nativeVrShell); private native void nativeDestroy(long nativeVrShell);
......
...@@ -9,15 +9,31 @@ ...@@ -9,15 +9,31 @@
namespace vr_shell { namespace vr_shell {
UiInterface::UiInterface() { UiInterface::UiInterface(Mode initial_mode) {
SetMode(Mode::STANDARD); SetMode(initial_mode);
} }
UiInterface::~UiInterface() {} UiInterface::~UiInterface() {}
void UiInterface::SetMode(Mode mode) { void UiInterface::SetMode(Mode mode) {
mode_ = mode; mode_ = mode;
updates_.SetInteger("mode", static_cast<int>(mode)); FlushModeState();
}
void UiInterface::SetMenuMode(bool enabled) {
menu_mode_ = enabled;
FlushModeState();
}
void UiInterface::SetCinemaMode(bool enabled) {
cinema_mode_ = enabled;
FlushModeState();
}
void UiInterface::FlushModeState() {
updates_.SetInteger("mode", static_cast<int>(mode_));
updates_.SetBoolean("menuMode", menu_mode_);
updates_.SetBoolean("cinemaMode", cinema_mode_);
FlushUpdates(); FlushUpdates();
} }
......
...@@ -23,16 +23,19 @@ class UiInterface { ...@@ -23,16 +23,19 @@ class UiInterface {
public: public:
enum Mode { enum Mode {
STANDARD, STANDARD,
WEB_VR, WEB_VR
MENU,
CINEMA,
}; };
UiInterface(); explicit UiInterface(Mode initial_mode);
virtual ~UiInterface(); virtual ~UiInterface();
void SetMode(Mode mode); void SetMode(Mode mode);
Mode GetMode() { return mode_; } Mode GetMode() { return mode_; }
void SetMenuMode(bool enabled);
bool GetMenuMode() { return menu_mode_; }
void SetCinemaMode(bool enabled);
bool GetCinemaMode() { return cinema_mode_; }
void SetSecureOrigin(bool secure); void SetSecureOrigin(bool secure);
void SetLoading(bool loading); void SetLoading(bool loading);
void SetURL(const GURL& url); void SetURL(const GURL& url);
...@@ -43,8 +46,11 @@ class UiInterface { ...@@ -43,8 +46,11 @@ class UiInterface {
private: private:
void FlushUpdates(); void FlushUpdates();
void FlushModeState();
Mode mode_; Mode mode_;
bool menu_mode_ = false;
bool cinema_mode_ = false;
UiCommandHandler* handler_; UiCommandHandler* handler_;
bool loaded_ = false; bool loaded_ = false;
base::DictionaryValue updates_; base::DictionaryValue updates_;
......
...@@ -151,7 +151,8 @@ VrShell::VrShell(JNIEnv* env, ...@@ -151,7 +151,8 @@ VrShell::VrShell(JNIEnv* env,
content::WebContents* main_contents, content::WebContents* main_contents,
ui::WindowAndroid* content_window, ui::WindowAndroid* content_window,
content::WebContents* ui_contents, content::WebContents* ui_contents,
ui::WindowAndroid* ui_window) ui::WindowAndroid* ui_window,
bool for_web_vr)
: WebContentsObserver(ui_contents), : WebContentsObserver(ui_contents),
main_contents_(main_contents), main_contents_(main_contents),
ui_contents_(ui_contents), ui_contents_(ui_contents),
...@@ -162,7 +163,11 @@ VrShell::VrShell(JNIEnv* env, ...@@ -162,7 +163,11 @@ VrShell::VrShell(JNIEnv* env,
g_instance = this; g_instance = this;
j_vr_shell_.Reset(env, obj); j_vr_shell_.Reset(env, obj);
scene_.reset(new UiScene); scene_.reset(new UiScene);
html_interface_.reset(new UiInterface);
if (for_web_vr)
metrics_helper_->SetWebVREnabled(true);
html_interface_.reset(new UiInterface(
for_web_vr ? UiInterface::Mode::WEB_VR : UiInterface::Mode::STANDARD));
content_compositor_.reset(new VrCompositor(content_window, false)); content_compositor_.reset(new VrCompositor(content_window, false));
ui_compositor_.reset(new VrCompositor(ui_window, true)); ui_compositor_.reset(new VrCompositor(ui_window, true));
vr_web_contents_observer_.reset( vr_web_contents_observer_.reset(
...@@ -230,7 +235,6 @@ void VrShell::GvrInit(JNIEnv* env, ...@@ -230,7 +235,6 @@ void VrShell::GvrInit(JNIEnv* env,
base::AutoLock lock(gvr_init_lock_); base::AutoLock lock(gvr_init_lock_);
// set the initial webvr state // set the initial webvr state
metrics_helper_->SetWebVREnabled(webvr_mode_);
metrics_helper_->SetVRActive(true); metrics_helper_->SetVRActive(true);
gvr_api_ = gvr_api_ =
...@@ -349,26 +353,17 @@ void VrShell::UpdateController(const gvr::Vec3f& forward_vector) { ...@@ -349,26 +353,17 @@ void VrShell::UpdateController(const gvr::Vec3f& forward_vector) {
// Note that button up/down state is transient, so IsButtonUp only returns // Note that button up/down state is transient, so IsButtonUp only returns
// true for a single frame (and we're guaranteed not to miss it). // true for a single frame (and we're guaranteed not to miss it).
if (controller_->IsButtonUp( if (controller_->IsButtonUp(
gvr::ControllerButton::GVR_CONTROLLER_BUTTON_APP)) { gvr::ControllerButton::GVR_CONTROLLER_BUTTON_APP)) {
if (html_interface_->GetMode() == UiInterface::Mode::MENU) { html_interface_->SetMenuMode(!html_interface_->GetMenuMode());
// Temporary: Hit app button a second time to exit menu mode.
if (webvr_mode_) { // TODO(mthiesse): The page is no longer visible when in menu mode. We
html_interface_->SetMode(UiInterface::Mode::WEB_VR); // should unfocus or otherwise let it know it's hidden.
main_thread_task_runner_->PostTask( if (html_interface_->GetMode() == UiInterface::Mode::WEB_VR) {
FROM_HERE, base::Bind(&device::GvrDeviceProvider::OnDisplayFocus, const auto&& task = html_interface_->GetMenuMode() ?
delegate_->GetDeviceProvider())); &device::GvrDeviceProvider::OnDisplayBlur :
} else { &device::GvrDeviceProvider::OnDisplayFocus;
html_interface_->SetMode(UiInterface::Mode::STANDARD); main_thread_task_runner_->PostTask(
} FROM_HERE, base::Bind(task, delegate_->GetDeviceProvider()));
} else {
if (html_interface_->GetMode() == UiInterface::Mode::WEB_VR) {
main_thread_task_runner_->PostTask(
FROM_HERE, base::Bind(&device::GvrDeviceProvider::OnDisplayBlur,
delegate_->GetDeviceProvider()));
}
html_interface_->SetMode(UiInterface::Mode::MENU);
// TODO(mthiesse): The page is no longer visible here. We should unfocus
// or otherwise let it know it's hidden.
} }
} }
#endif #endif
...@@ -903,8 +898,7 @@ void VrShell::OnDomContentsLoaded() { ...@@ -903,8 +898,7 @@ void VrShell::OnDomContentsLoaded() {
void VrShell::SetWebVrMode(JNIEnv* env, void VrShell::SetWebVrMode(JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj, const base::android::JavaParamRef<jobject>& obj,
bool enabled) { bool enabled) {
webvr_mode_ = enabled; metrics_helper_->SetWebVREnabled(enabled);
metrics_helper_->SetWebVREnabled(webvr_mode_);
if (enabled) { if (enabled) {
html_interface_->SetMode(UiInterface::Mode::WEB_VR); html_interface_->SetMode(UiInterface::Mode::WEB_VR);
} else { } else {
...@@ -916,8 +910,7 @@ void VrShell::SetWebVRSecureOrigin(bool secure_origin) { ...@@ -916,8 +910,7 @@ void VrShell::SetWebVRSecureOrigin(bool secure_origin) {
html_interface_->SetSecureOrigin(secure_origin); html_interface_->SetSecureOrigin(secure_origin);
} }
void VrShell::SubmitWebVRFrame() { void VrShell::SubmitWebVRFrame() {}
}
void VrShell::UpdateWebVRTextureBounds(const gvr::Rectf& left_bounds, void VrShell::UpdateWebVRTextureBounds(const gvr::Rectf& left_bounds,
const gvr::Rectf& right_bounds) { const gvr::Rectf& right_bounds) {
...@@ -1018,8 +1011,7 @@ void VrShell::DoUiAction(const UiAction action) { ...@@ -1018,8 +1011,7 @@ void VrShell::DoUiAction(const UiAction action) {
#if defined(ENABLE_VR_SHELL_UI_DEV) #if defined(ENABLE_VR_SHELL_UI_DEV)
case RELOAD_UI: case RELOAD_UI:
ui_contents_->GetController().Reload(false); ui_contents_->GetController().Reload(false);
html_interface_.reset(new UiInterface); html_interface_.reset(new UiInterface(UiInterface::Mode::STANDARD));
html_interface_->SetMode(UiInterface::Mode::STANDARD);
vr_web_contents_observer_->SetUiInterface(html_interface_.get()); vr_web_contents_observer_->SetUiInterface(html_interface_.get());
break; break;
#endif #endif
...@@ -1045,12 +1037,14 @@ jlong Init(JNIEnv* env, ...@@ -1045,12 +1037,14 @@ jlong Init(JNIEnv* env,
const JavaParamRef<jobject>& content_web_contents, const JavaParamRef<jobject>& content_web_contents,
jlong content_window_android, jlong content_window_android,
const JavaParamRef<jobject>& ui_web_contents, const JavaParamRef<jobject>& ui_web_contents,
jlong ui_window_android) { jlong ui_window_android,
jboolean for_web_vr) {
return reinterpret_cast<intptr_t>(new VrShell( return reinterpret_cast<intptr_t>(new VrShell(
env, obj, content::WebContents::FromJavaWebContents(content_web_contents), env, obj, content::WebContents::FromJavaWebContents(content_web_contents),
reinterpret_cast<ui::WindowAndroid*>(content_window_android), reinterpret_cast<ui::WindowAndroid*>(content_window_android),
content::WebContents::FromJavaWebContents(ui_web_contents), content::WebContents::FromJavaWebContents(ui_web_contents),
reinterpret_cast<ui::WindowAndroid*>(ui_window_android))); reinterpret_cast<ui::WindowAndroid*>(ui_window_android),
for_web_vr));
} }
} // namespace vr_shell } // namespace vr_shell
...@@ -61,7 +61,8 @@ class VrShell : public device::GvrDelegate, content::WebContentsObserver { ...@@ -61,7 +61,8 @@ class VrShell : public device::GvrDelegate, content::WebContentsObserver {
content::WebContents* main_contents, content::WebContents* main_contents,
ui::WindowAndroid* content_window, ui::WindowAndroid* content_window,
content::WebContents* ui_contents, content::WebContents* ui_contents,
ui::WindowAndroid* ui_window); ui::WindowAndroid* ui_window,
bool for_web_vr);
void UpdateCompositorLayers(JNIEnv* env, void UpdateCompositorLayers(JNIEnv* env,
const base::android::JavaParamRef<jobject>& obj); const base::android::JavaParamRef<jobject>& obj);
...@@ -196,8 +197,6 @@ class VrShell : public device::GvrDelegate, content::WebContentsObserver { ...@@ -196,8 +197,6 @@ class VrShell : public device::GvrDelegate, content::WebContentsObserver {
int content_tex_height_ = 0; int content_tex_height_ = 0;
gvr::Sizei content_tex_pixels_for_webvr_ = {0, 0}; gvr::Sizei content_tex_pixels_for_webvr_ = {0, 0};
bool webvr_mode_ = false;
// The pose ring buffer size must be a power of two to avoid glitches when // The pose ring buffer size must be a power of two to avoid glitches when
// the pose index wraps around. It should be large enough to handle the // the pose index wraps around. It should be large enough to handle the
// current backlog of poses which is 2-3 frames. // current backlog of poses which is 2-3 frames.
......
...@@ -46,13 +46,7 @@ void VrWebContentsObserver::DidFinishNavigation( ...@@ -46,13 +46,7 @@ void VrWebContentsObserver::DidFinishNavigation(
void VrWebContentsObserver::DidToggleFullscreenModeForTab( void VrWebContentsObserver::DidToggleFullscreenModeForTab(
bool entered_fullscreen, bool will_cause_resize) { bool entered_fullscreen, bool will_cause_resize) {
// TODO(amp): Use will_cause_resize to signal ui of pending size changes. // TODO(amp): Use will_cause_resize to signal ui of pending size changes.
int mode = ui_interface_->GetMode(); ui_interface_->SetCinemaMode(entered_fullscreen);
if (entered_fullscreen && mode == UiInterface::Mode::STANDARD) {
ui_interface_->SetMode(UiInterface::Mode::CINEMA);
}
if (!entered_fullscreen && mode == UiInterface::Mode::CINEMA) {
ui_interface_->SetMode(UiInterface::Mode::STANDARD);
}
} }
} // namespace vr_shell } // namespace vr_shell
...@@ -125,11 +125,12 @@ var vrShellUi = (function() { ...@@ -125,11 +125,12 @@ var vrShellUi = (function() {
let descriptors = [ let descriptors = [
['#back', function() { ['#back', function() {
// If we are in cinema mode, revert to standard mode on back press. // If we are in cinema mode, revert to standard mode on back press.
if (sceneManager.mode == api.Mode.CINEMA) { if (sceneManager.cinemaMode) {
// TODO(crbug/644511): Send a message back to native to handle // TODO(crbug/644511): Send a message back to native to handle
// switching back to standard mode and out of full screen instead // switching back to standard mode and out of full screen instead
// of only changing the mode here. // of only changing the mode here.
sceneManager.setMode(api.Mode.STANDARD); sceneManager.setMode(sceneManager.mode, sceneManager.menuMode,
false /* Cinema Mode */);
} else { } else {
api.doAction(api.Action.HISTORY_BACK); api.doAction(api.Action.HISTORY_BACK);
} }
...@@ -390,6 +391,8 @@ var vrShellUi = (function() { ...@@ -390,6 +391,8 @@ var vrShellUi = (function() {
class SceneManager { class SceneManager {
constructor() { constructor() {
this.mode = api.Mode.UNKNOWN; this.mode = api.Mode.UNKNOWN;
this.menuMode = false;
this.cinemaMode = false;
this.contentQuad = new ContentQuad(); this.contentQuad = new ContentQuad();
let contentId = this.contentQuad.getElementId(); let contentId = this.contentQuad.getElementId();
...@@ -399,17 +402,17 @@ var vrShellUi = (function() { ...@@ -399,17 +402,17 @@ var vrShellUi = (function() {
this.omnibox = new Omnibox(contentId); this.omnibox = new Omnibox(contentId);
} }
setMode(mode) { setMode(mode, menuMode, cinemaMode) {
this.mode = mode; this.mode = mode;
this.contentQuad.setEnabled( this.menuMode = menuMode;
mode == api.Mode.STANDARD || mode == api.Mode.CINEMA); this.cinemaMode = cinemaMode;
this.contentQuad.setCinemaMode(mode == api.Mode.CINEMA);
this.contentQuad.setEnabled(mode == api.Mode.STANDARD && !menuMode);
this.contentQuad.setCinemaMode(cinemaMode);
// TODO(crbug/643815): Set aspect ratio on content quad when available. // TODO(crbug/643815): Set aspect ratio on content quad when available.
// TODO(amp): Don't show controls in CINEMA mode once MENU mode lands. // TODO(amp): Don't show controls in CINEMA mode once MENU mode lands.
this.controls.setEnabled( this.controls.setEnabled(mode == api.Mode.STANDARD && !menuMode);
mode == api.Mode.STANDARD || mode == api.Mode.CINEMA); this.omnibox.setEnabled(mode == api.Mode.STANDARD && !menuMode);
this.omnibox.setEnabled(
mode == api.Mode.STANDARD || mode == api.Mode.CINEMA);
this.secureOriginWarnings.setEnabled(mode == api.Mode.WEB_VR); this.secureOriginWarnings.setEnabled(mode == api.Mode.WEB_VR);
} }
...@@ -432,7 +435,7 @@ var vrShellUi = (function() { ...@@ -432,7 +435,7 @@ var vrShellUi = (function() {
function command(dict) { function command(dict) {
if ('mode' in dict) { if ('mode' in dict) {
sceneManager.setMode(dict['mode']); sceneManager.setMode(dict['mode'], dict['menuMode'], dict['cinemaMode']);
} }
if ('secureOrigin' in dict) { if ('secureOrigin' in dict) {
sceneManager.setSecureOrigin(dict['secureOrigin']); sceneManager.setSecureOrigin(dict['secureOrigin']);
......
...@@ -83,8 +83,6 @@ var api = (function() { ...@@ -83,8 +83,6 @@ var api = (function() {
'UNKNOWN': -1, 'UNKNOWN': -1,
'STANDARD': 0, 'STANDARD': 0,
'WEB_VR': 1, 'WEB_VR': 1,
'MENU': 2,
'CINEMA': 3
}); });
/** /**
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment