OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/android/vr_shell/vr_shell_gl.h" | 5 #include "chrome/browser/android/vr_shell/vr_shell_gl.h" |
6 | 6 |
7 #include "base/memory/ptr_util.h" | 7 #include "base/memory/ptr_util.h" |
8 #include "base/metrics/histogram_macros.h" | 8 #include "base/metrics/histogram_macros.h" |
9 #include "base/threading/thread_task_runner_handle.h" | 9 #include "base/threading/thread_task_runner_handle.h" |
10 #include "chrome/browser/android/vr_shell/ui_elements.h" | 10 #include "chrome/browser/android/vr_shell/ui_elements.h" |
11 #include "chrome/browser/android/vr_shell/ui_interface.h" | |
12 #include "chrome/browser/android/vr_shell/ui_scene.h" | 11 #include "chrome/browser/android/vr_shell/ui_scene.h" |
13 #include "chrome/browser/android/vr_shell/vr_controller.h" | 12 #include "chrome/browser/android/vr_shell/vr_controller.h" |
14 #include "chrome/browser/android/vr_shell/vr_gl_util.h" | 13 #include "chrome/browser/android/vr_shell/vr_gl_util.h" |
15 #include "chrome/browser/android/vr_shell/vr_input_manager.h" | 14 #include "chrome/browser/android/vr_shell/vr_input_manager.h" |
16 #include "chrome/browser/android/vr_shell/vr_math.h" | 15 #include "chrome/browser/android/vr_shell/vr_math.h" |
17 #include "chrome/browser/android/vr_shell/vr_shell.h" | 16 #include "chrome/browser/android/vr_shell/vr_shell.h" |
18 #include "chrome/browser/android/vr_shell/vr_shell_renderer.h" | 17 #include "chrome/browser/android/vr_shell/vr_shell_renderer.h" |
19 #include "third_party/WebKit/public/platform/WebInputEvent.h" | 18 #include "third_party/WebKit/public/platform/WebInputEvent.h" |
20 #include "ui/gfx/vsync_provider.h" | 19 #include "ui/gfx/vsync_provider.h" |
21 #include "ui/gl/android/scoped_java_surface.h" | 20 #include "ui/gl/android/scoped_java_surface.h" |
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
170 } | 169 } |
171 | 170 |
172 int64_t TimeInMicroseconds() { | 171 int64_t TimeInMicroseconds() { |
173 return std::chrono::duration_cast<std::chrono::microseconds>( | 172 return std::chrono::duration_cast<std::chrono::microseconds>( |
174 std::chrono::steady_clock::now().time_since_epoch()).count(); | 173 std::chrono::steady_clock::now().time_since_epoch()).count(); |
175 } | 174 } |
176 | 175 |
177 } // namespace | 176 } // namespace |
178 | 177 |
179 VrShellGl::VrShellGl( | 178 VrShellGl::VrShellGl( |
180 VrShell* vr_shell, | |
181 const base::WeakPtr<VrShell>& weak_vr_shell, | 179 const base::WeakPtr<VrShell>& weak_vr_shell, |
182 const base::WeakPtr<VrInputManager>& content_input_manager, | 180 const base::WeakPtr<VrInputManager>& content_input_manager, |
183 const base::WeakPtr<VrInputManager>& ui_input_manager, | 181 const base::WeakPtr<VrInputManager>& ui_input_manager, |
184 scoped_refptr<base::SingleThreadTaskRunner> main_thread_task_runner, | 182 scoped_refptr<base::SingleThreadTaskRunner> main_thread_task_runner, |
185 gvr_context* gvr_api) | 183 gvr_context* gvr_api, |
186 : task_runner_(base::ThreadTaskRunnerHandle::Get()), | 184 bool initially_web_vr) |
187 vr_shell_(vr_shell), | 185 : web_vr_mode_(initially_web_vr), |
| 186 task_runner_(base::ThreadTaskRunnerHandle::Get()), |
188 weak_vr_shell_(weak_vr_shell), | 187 weak_vr_shell_(weak_vr_shell), |
189 content_input_manager_(content_input_manager), | 188 content_input_manager_(content_input_manager), |
190 ui_input_manager_(ui_input_manager), | 189 ui_input_manager_(ui_input_manager), |
191 main_thread_task_runner_(std::move(main_thread_task_runner)), | 190 main_thread_task_runner_(std::move(main_thread_task_runner)), |
192 weak_ptr_factory_(this) { | 191 weak_ptr_factory_(this) { |
193 GvrInit(gvr_api); | 192 GvrInit(gvr_api); |
194 } | 193 } |
195 | 194 |
196 VrShellGl::~VrShellGl() { | 195 VrShellGl::~VrShellGl() { |
197 draw_task_.Cancel(); | 196 draw_task_.Cancel(); |
(...skipping 182 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
380 webvr_right_viewport_.get()); | 379 webvr_right_viewport_.get()); |
381 webvr_right_viewport_->SetSourceBufferIndex(kFramePrimaryBuffer); | 380 webvr_right_viewport_->SetSourceBufferIndex(kFramePrimaryBuffer); |
382 | 381 |
383 main_thread_task_runner_->PostTask(FROM_HERE, base::Bind( | 382 main_thread_task_runner_->PostTask(FROM_HERE, base::Bind( |
384 &VrShell::GvrDelegateReady, weak_vr_shell_)); | 383 &VrShell::GvrDelegateReady, weak_vr_shell_)); |
385 } | 384 } |
386 | 385 |
387 void VrShellGl::UpdateController(const gvr::Vec3f& forward_vector) { | 386 void VrShellGl::UpdateController(const gvr::Vec3f& forward_vector) { |
388 controller_->UpdateState(); | 387 controller_->UpdateState(); |
389 | 388 |
390 #if defined(ENABLE_VR_SHELL) | |
391 // TODO(mthiesse): Fix menu button handling, which should be posted to the UI | |
392 // thread instead of handled here. | |
393 | 389 |
394 // Note that button up/down state is transient, so ButtonUpHappened only | 390 // Note that button up/down state is transient, so ButtonUpHappened only |
395 // returns true for a single frame (and we're guaranteed not to miss it). | 391 // returns true for a single frame (and we're guaranteed not to miss it). |
396 if (controller_->ButtonUpHappened( | 392 if (controller_->ButtonUpHappened( |
397 gvr::ControllerButton::GVR_CONTROLLER_BUTTON_APP)) { | 393 gvr::ControllerButton::GVR_CONTROLLER_BUTTON_APP)) { |
398 // html_interface_->SetMenuMode(!html_interface_->GetMenuMode()); | 394 main_thread_task_runner_->PostTask( |
| 395 FROM_HERE, base::Bind(&VrShell::AppButtonPressed, weak_vr_shell_)); |
| 396 } |
399 | 397 |
400 // TODO(mthiesse): The page is no longer visible when in menu mode. We | 398 if (web_vr_mode_) { |
401 // should unfocus or otherwise let it know it's hidden. | |
402 // if (html_interface_->GetMode() == UiInterface::Mode::WEB_VR) { | |
403 // const auto&& task = html_interface_->GetMenuMode() ? | |
404 // &device::GvrDeviceProvider::OnDisplayBlur : | |
405 // &device::GvrDeviceProvider::OnDisplayFocus; | |
406 // main_thread_task_runner_->PostTask( | |
407 // FROM_HERE, base::Bind(task, delegate_->GetDeviceProvider())); | |
408 // } | |
409 } | |
410 #endif | |
411 if (vr_shell_->GetUiInterface()->GetMode() == UiInterface::Mode::WEB_VR) { | |
412 // Process screen touch events for Cardboard button compatibility. | 399 // Process screen touch events for Cardboard button compatibility. |
413 // Also send tap events for controller "touchpad click" events. | 400 // Also send tap events for controller "touchpad click" events. |
414 if (touch_pending_ || controller_->ButtonUpHappened( | 401 if (touch_pending_ || controller_->ButtonUpHappened( |
415 gvr::ControllerButton::GVR_CONTROLLER_BUTTON_CLICK)) { | 402 gvr::ControllerButton::GVR_CONTROLLER_BUTTON_CLICK)) { |
416 touch_pending_ = false; | 403 touch_pending_ = false; |
417 std::unique_ptr<WebGestureEvent> gesture(new WebGestureEvent()); | 404 std::unique_ptr<WebGestureEvent> gesture(new WebGestureEvent()); |
418 gesture->sourceDevice = blink::WebGestureDeviceTouchpad; | 405 gesture->sourceDevice = blink::WebGestureDeviceTouchpad; |
419 gesture->timeStampSeconds = | 406 gesture->timeStampSeconds = |
420 (base::TimeTicks::Now() - base::TimeTicks()).InSecondsF(); | 407 (base::TimeTicks::Now() - base::TimeTicks()).InSecondsF(); |
421 gesture->type = WebInputEvent::GestureTapDown; | 408 gesture->type = WebInputEvent::GestureTapDown; |
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
632 } | 619 } |
633 | 620 |
634 frame.BindBuffer(kFramePrimaryBuffer); | 621 frame.BindBuffer(kFramePrimaryBuffer); |
635 | 622 |
636 // Update the render position of all UI elements (including desktop). | 623 // Update the render position of all UI elements (including desktop). |
637 const float screen_tilt = kDesktopScreenTiltDefault * M_PI / 180.0f; | 624 const float screen_tilt = kDesktopScreenTiltDefault * M_PI / 180.0f; |
638 scene_->UpdateTransforms(screen_tilt, TimeInMicroseconds()); | 625 scene_->UpdateTransforms(screen_tilt, TimeInMicroseconds()); |
639 | 626 |
640 UpdateController(GetForwardVector(head_pose)); | 627 UpdateController(GetForwardVector(head_pose)); |
641 | 628 |
642 if (vr_shell_->GetUiInterface()->GetMode() == UiInterface::Mode::WEB_VR) { | 629 if (web_vr_mode_) { |
643 DrawWebVr(); | 630 DrawWebVr(); |
644 | 631 |
645 // When using async reprojection, we need to know which pose was used in | 632 // When using async reprojection, we need to know which pose was used in |
646 // the WebVR app for drawing this frame. Due to unknown amounts of | 633 // the WebVR app for drawing this frame. Due to unknown amounts of |
647 // buffering in the compositor and SurfaceTexture, we read the pose number | 634 // buffering in the compositor and SurfaceTexture, we read the pose number |
648 // from a corner pixel. There's no point in doing this for legacy | 635 // from a corner pixel. There's no point in doing this for legacy |
649 // distortion rendering since that doesn't need a pose, and reading back | 636 // distortion rendering since that doesn't need a pose, and reading back |
650 // pixels is an expensive operation. TODO(klausw,crbug.com/655722): stop | 637 // pixels is an expensive operation. TODO(klausw,crbug.com/655722): stop |
651 // doing this once we have working no-compositor rendering for WebVR. | 638 // doing this once we have working no-compositor rendering for WebVR. |
652 if (gvr_api_->GetAsyncReprojectionEnabled()) { | 639 if (gvr_api_->GetAsyncReprojectionEnabled()) { |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
690 if (!rect->visible) { | 677 if (!rect->visible) { |
691 continue; | 678 continue; |
692 } | 679 } |
693 if (rect->lock_to_fov) { | 680 if (rect->lock_to_fov) { |
694 head_locked_elements.push_back(rect.get()); | 681 head_locked_elements.push_back(rect.get()); |
695 } else { | 682 } else { |
696 world_elements.push_back(rect.get()); | 683 world_elements.push_back(rect.get()); |
697 } | 684 } |
698 } | 685 } |
699 | 686 |
700 if (vr_shell_->GetUiInterface()->GetMode() == UiInterface::Mode::WEB_VR) { | 687 if (web_vr_mode_) { |
701 // WebVR is incompatible with 3D world compositing since the | 688 // WebVR is incompatible with 3D world compositing since the |
702 // depth buffer was already populated with unknown scaling - the | 689 // depth buffer was already populated with unknown scaling - the |
703 // WebVR app has full control over zNear/zFar. Just leave the | 690 // WebVR app has full control over zNear/zFar. Just leave the |
704 // existing content in place in the primary buffer without | 691 // existing content in place in the primary buffer without |
705 // clearing. Currently, there aren't any world elements in WebVR | 692 // clearing. Currently, there aren't any world elements in WebVR |
706 // mode, this will need further testing if those get added | 693 // mode, this will need further testing if those get added |
707 // later. | 694 // later. |
708 } else { | 695 } else { |
709 // Non-WebVR mode, enable depth testing and clear the primary buffers. | 696 // Non-WebVR mode, enable depth testing and clear the primary buffers. |
710 glEnable(GL_CULL_FACE); | 697 glEnable(GL_CULL_FACE); |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
766 glViewport(pixel_rect.left, pixel_rect.bottom, | 753 glViewport(pixel_rect.left, pixel_rect.bottom, |
767 pixel_rect.right - pixel_rect.left, | 754 pixel_rect.right - pixel_rect.left, |
768 pixel_rect.top - pixel_rect.bottom); | 755 pixel_rect.top - pixel_rect.bottom); |
769 | 756 |
770 const gvr::Mat4f render_matrix = MatrixMul( | 757 const gvr::Mat4f render_matrix = MatrixMul( |
771 PerspectiveMatrixFromView( | 758 PerspectiveMatrixFromView( |
772 buffer_viewport_->GetSourceFov(), kZNear, kZFar), | 759 buffer_viewport_->GetSourceFov(), kZNear, kZFar), |
773 view_matrix); | 760 view_matrix); |
774 | 761 |
775 DrawElements(render_matrix, elements); | 762 DrawElements(render_matrix, elements); |
776 if (head_pose != nullptr && | 763 if (head_pose != nullptr && !web_vr_mode_) { |
777 vr_shell_->GetUiInterface()->GetMode() != UiInterface::Mode::WEB_VR) { | |
778 DrawCursor(render_matrix); | 764 DrawCursor(render_matrix); |
779 } | 765 } |
780 } | 766 } |
781 } | 767 } |
782 | 768 |
783 void VrShellGl::DrawElements( | 769 void VrShellGl::DrawElements( |
784 const gvr::Mat4f& render_matrix, | 770 const gvr::Mat4f& render_matrix, |
785 const std::vector<const ContentRectangle*>& elements) { | 771 const std::vector<const ContentRectangle*>& elements) { |
786 for (const auto& rect : elements) { | 772 for (const auto& rect : elements) { |
787 Rectf copy_rect; | 773 Rectf copy_rect; |
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
909 | 895 |
910 void VrShellGl::OnResume() { | 896 void VrShellGl::OnResume() { |
911 gvr_api_->RefreshViewerProfile(); | 897 gvr_api_->RefreshViewerProfile(); |
912 gvr_api_->ResumeTracking(); | 898 gvr_api_->ResumeTracking(); |
913 controller_->OnResume(); | 899 controller_->OnResume(); |
914 draw_task_.Reset(base::Bind(&VrShellGl::DrawFrame, base::Unretained(this))); | 900 draw_task_.Reset(base::Bind(&VrShellGl::DrawFrame, base::Unretained(this))); |
915 ScheduleNextDrawFrame(); | 901 ScheduleNextDrawFrame(); |
916 } | 902 } |
917 | 903 |
918 void VrShellGl::SetWebVrMode(bool enabled) { | 904 void VrShellGl::SetWebVrMode(bool enabled) { |
919 if (enabled) { | 905 web_vr_mode_ = enabled; |
920 vr_shell_->GetUiInterface()->SetMode(UiInterface::Mode::WEB_VR); | |
921 } else { | |
922 vr_shell_->GetUiInterface()->SetMode(UiInterface::Mode::STANDARD); | |
923 } | |
924 } | 906 } |
925 | 907 |
926 void VrShellGl::UpdateWebVRTextureBounds(const gvr::Rectf& left_bounds, | 908 void VrShellGl::UpdateWebVRTextureBounds(const gvr::Rectf& left_bounds, |
927 const gvr::Rectf& right_bounds) { | 909 const gvr::Rectf& right_bounds) { |
928 webvr_left_viewport_->SetSourceUv(left_bounds); | 910 webvr_left_viewport_->SetSourceUv(left_bounds); |
929 webvr_right_viewport_->SetSourceUv(right_bounds); | 911 webvr_right_viewport_->SetSourceUv(right_bounds); |
930 } | 912 } |
931 | 913 |
932 gvr::GvrApi* VrShellGl::gvr_api() { | 914 gvr::GvrApi* VrShellGl::gvr_api() { |
933 return gvr_api_.get(); | 915 return gvr_api_.get(); |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
986 void VrShellGl::ForceExitVr() { | 968 void VrShellGl::ForceExitVr() { |
987 main_thread_task_runner_->PostTask( | 969 main_thread_task_runner_->PostTask( |
988 FROM_HERE, base::Bind(&VrShell::ForceExitVr, weak_vr_shell_)); | 970 FROM_HERE, base::Bind(&VrShell::ForceExitVr, weak_vr_shell_)); |
989 } | 971 } |
990 | 972 |
991 void VrShellGl::UpdateScene(std::unique_ptr<base::ListValue> commands) { | 973 void VrShellGl::UpdateScene(std::unique_ptr<base::ListValue> commands) { |
992 scene_->HandleCommands(std::move(commands), TimeInMicroseconds()); | 974 scene_->HandleCommands(std::move(commands), TimeInMicroseconds()); |
993 } | 975 } |
994 | 976 |
995 } // namespace vr_shell | 977 } // namespace vr_shell |
OLD | NEW |