Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(691)

Side by Side Diff: content/browser/web_contents/web_contents_view_aura.cc

Issue 12346002: overscroll: Fix an issue where the overscroll window could get stuck. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: fix-tests Created 7 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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 "content/browser/web_contents/web_contents_view_aura.h" 5 #include "content/browser/web_contents/web_contents_view_aura.h"
6 6
7 #include "base/auto_reset.h" 7 #include "base/auto_reset.h"
8 #include "base/metrics/histogram.h" 8 #include "base/metrics/histogram.h"
9 #include "base/utf_string_conversions.h" 9 #include "base/utf_string_conversions.h"
10 #include "content/browser/renderer_host/dip_util.h" 10 #include "content/browser/renderer_host/dip_util.h"
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
93 } 93 }
94 94
95 // The window delegate for the overscroll window. This redirects trackpad events 95 // The window delegate for the overscroll window. This redirects trackpad events
96 // to the web-contents window. The delegate destroys itself when the window is 96 // to the web-contents window. The delegate destroys itself when the window is
97 // destroyed. 97 // destroyed.
98 class OverscrollWindowDelegate : public aura::WindowDelegate { 98 class OverscrollWindowDelegate : public aura::WindowDelegate {
99 public: 99 public:
100 OverscrollWindowDelegate(WebContentsImpl* web_contents, 100 OverscrollWindowDelegate(WebContentsImpl* web_contents,
101 OverscrollMode overscroll_mode) 101 OverscrollMode overscroll_mode)
102 : web_contents_(web_contents), 102 : web_contents_(web_contents),
103 show_shadow_(false) { 103 show_shadow_(false),
104 forward_events_(true) {
104 const NavigationControllerImpl& controller = web_contents->GetController(); 105 const NavigationControllerImpl& controller = web_contents->GetController();
105 const NavigationEntryImpl* entry = NULL; 106 const NavigationEntryImpl* entry = NULL;
106 if (ShouldNavigateForward(controller, overscroll_mode)) { 107 if (ShouldNavigateForward(controller, overscroll_mode)) {
107 entry = NavigationEntryImpl::FromNavigationEntry( 108 entry = NavigationEntryImpl::FromNavigationEntry(
108 controller.GetEntryAtOffset(1)); 109 controller.GetEntryAtOffset(1));
109 } else if (ShouldNavigateBack(controller, overscroll_mode)) { 110 } else if (ShouldNavigateBack(controller, overscroll_mode)) {
110 entry = NavigationEntryImpl::FromNavigationEntry( 111 entry = NavigationEntryImpl::FromNavigationEntry(
111 controller.GetEntryAtOffset(-1)); 112 controller.GetEntryAtOffset(-1));
112 } 113 }
113 if (!entry || !entry->screenshot()) 114 if (!entry || !entry->screenshot())
114 return; 115 return;
115 116
116 std::vector<gfx::ImagePNGRep> image_reps; 117 std::vector<gfx::ImagePNGRep> image_reps;
117 image_reps.push_back(gfx::ImagePNGRep(entry->screenshot(), 118 image_reps.push_back(gfx::ImagePNGRep(entry->screenshot(),
118 ui::GetScaleFactorForNativeView(web_contents_window()))); 119 ui::GetScaleFactorForNativeView(web_contents_window())));
119 image_ = gfx::Image(image_reps); 120 image_ = gfx::Image(image_reps);
120 if (image_.AsImageSkia().size() != web_contents_window()->bounds().size()) 121 if (image_.AsImageSkia().size() != web_contents_window()->bounds().size())
121 image_ = gfx::Image(); 122 image_ = gfx::Image();
122 } 123 }
123 124
124 bool has_screenshot() const { return !image_.IsEmpty(); } 125 bool has_screenshot() const { return !image_.IsEmpty(); }
125 126
126 void set_show_shadow(bool show) { 127 void set_show_shadow(bool show) {
127 show_shadow_ = show; 128 show_shadow_ = show;
128 } 129 }
129 130
131 void stop_forwarding_events() { forward_events_ = false; }
132
130 private: 133 private:
131 virtual ~OverscrollWindowDelegate() {} 134 virtual ~OverscrollWindowDelegate() {}
132 135
133 aura::Window* web_contents_window() { 136 aura::Window* web_contents_window() {
134 return web_contents_->GetView()->GetContentNativeView(); 137 return web_contents_->GetView()->GetContentNativeView();
135 } 138 }
136 139
137 // aura::WindowDelegate implementation: 140 // aura::WindowDelegate implementation:
138 virtual gfx::Size GetMinimumSize() const OVERRIDE { 141 virtual gfx::Size GetMinimumSize() const OVERRIDE {
139 return gfx::Size(); 142 return gfx::Size();
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
217 220
218 virtual void GetHitTestMask(gfx::Path* mask) const OVERRIDE { 221 virtual void GetHitTestMask(gfx::Path* mask) const OVERRIDE {
219 } 222 }
220 223
221 virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE { 224 virtual scoped_refptr<ui::Texture> CopyTexture() OVERRIDE {
222 return scoped_refptr<ui::Texture>(); 225 return scoped_refptr<ui::Texture>();
223 } 226 }
224 227
225 // Overridden from ui::EventHandler. 228 // Overridden from ui::EventHandler.
226 virtual void OnScrollEvent(ui::ScrollEvent* event) OVERRIDE { 229 virtual void OnScrollEvent(ui::ScrollEvent* event) OVERRIDE {
227 if (web_contents_window()) 230 if (forward_events_ && web_contents_window())
228 web_contents_window()->delegate()->OnScrollEvent(event); 231 web_contents_window()->delegate()->OnScrollEvent(event);
229 } 232 }
230 233
231 virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE { 234 virtual void OnGestureEvent(ui::GestureEvent* event) OVERRIDE {
232 if (web_contents_window()) 235 if (forward_events_ && web_contents_window())
233 web_contents_window()->delegate()->OnGestureEvent(event); 236 web_contents_window()->delegate()->OnGestureEvent(event);
234 } 237 }
235 238
236 WebContents* web_contents_; 239 WebContents* web_contents_;
237 gfx::Image image_; 240 gfx::Image image_;
238 bool show_shadow_; 241 bool show_shadow_;
239 242
243 // The window is displayed both during the gesture, and after the gesture
244 // while the navigation is in progress. During the gesture, it is necessary to
245 // forward input events to the content page (e.g. when the overscroll window
246 // slides under the cursor and starts receiving scroll events). However, once
247 // the gesture is complete, and the window is being displayed as an overlay
248 // window during navigation, events should not be forwarded anymore.
249 bool forward_events_;
250
240 DISALLOW_COPY_AND_ASSIGN(OverscrollWindowDelegate); 251 DISALLOW_COPY_AND_ASSIGN(OverscrollWindowDelegate);
241 }; 252 };
242 253
243 // Listens to all mouse drag events during a drag and drop and sends them to 254 // Listens to all mouse drag events during a drag and drop and sends them to
244 // the renderer. 255 // the renderer.
245 class WebDragSourceAura : public MessageLoopForUI::Observer, 256 class WebDragSourceAura : public MessageLoopForUI::Observer,
246 public NotificationObserver { 257 public NotificationObserver {
247 public: 258 public:
248 WebDragSourceAura(aura::Window* window, WebContentsImpl* contents) 259 WebDragSourceAura(aura::Window* window, WebContentsImpl* contents)
249 : window_(window), 260 : window_(window),
(...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after
590 // screenshot window on top of the page until the page has completed loading and 601 // screenshot window on top of the page until the page has completed loading and
591 // painting. 602 // painting.
592 class OverscrollNavigationOverlay : 603 class OverscrollNavigationOverlay :
593 public RenderWidgetHostViewAura::PaintObserver { 604 public RenderWidgetHostViewAura::PaintObserver {
594 public: 605 public:
595 OverscrollNavigationOverlay() 606 OverscrollNavigationOverlay()
596 : view_(NULL), 607 : view_(NULL),
597 loading_complete_(false), 608 loading_complete_(false),
598 received_paint_update_(false), 609 received_paint_update_(false),
599 compositor_updated_(false), 610 compositor_updated_(false),
600 has_screenshot_(false) { 611 has_screenshot_(false),
612 need_paint_update_(true) {
601 } 613 }
602 614
603 virtual ~OverscrollNavigationOverlay() { 615 virtual ~OverscrollNavigationOverlay() {
604 if (view_) 616 if (view_)
605 view_->set_paint_observer(NULL); 617 view_->set_paint_observer(NULL);
606 } 618 }
607 619
608 bool has_window() const { return !!window_.get(); } 620 bool has_window() const { return !!window_.get(); }
609 621
610 void StartObservingView(RenderWidgetHostViewAura* view) { 622 void StartObservingView(RenderWidgetHostViewAura* view) {
(...skipping 11 matching lines...) Expand all
622 window_->parent()->StackChildAtTop(window_.get()); 634 window_->parent()->StackChildAtTop(window_.get());
623 } 635 }
624 636
625 void SetOverlayWindow(scoped_ptr<aura::Window> window, bool has_screenshot) { 637 void SetOverlayWindow(scoped_ptr<aura::Window> window, bool has_screenshot) {
626 window_ = window.Pass(); 638 window_ = window.Pass();
627 if (window_.get() && window_->parent()) 639 if (window_.get() && window_->parent())
628 window_->parent()->StackChildAtTop(window_.get()); 640 window_->parent()->StackChildAtTop(window_.get());
629 has_screenshot_ = has_screenshot; 641 has_screenshot_ = has_screenshot;
630 } 642 }
631 643
644 void SetupForTesting() {
645 need_paint_update_ = false;
646 }
647
632 private: 648 private:
633 // Stop observing the page if the page-load has completed and the page has 649 // Stop observing the page if the page-load has completed and the page has
634 // been painted. 650 // been painted.
635 void StopObservingIfDone() { 651 void StopObservingIfDone() {
636 // If there is a screenshot displayed in the overlay window, then wait for 652 // If there is a screenshot displayed in the overlay window, then wait for
637 // the navigated page to complete loading and some paint update before 653 // the navigated page to complete loading and some paint update before
638 // hiding the overlay. 654 // hiding the overlay.
639 // If there is no screenshot in the overlay window, then hide this view 655 // If there is no screenshot in the overlay window, then hide this view
640 // as soon as there is any new painting notification. 656 // as soon as there is any new painting notification.
641 if (!received_paint_update_ || (has_screenshot_ && !loading_complete_)) 657 if ((need_paint_update_ && !received_paint_update_) ||
658 (has_screenshot_ && !loading_complete_)) {
642 return; 659 return;
660 }
643 661
644 window_.reset(); 662 window_.reset();
645 if (view_) { 663 if (view_) {
646 view_->set_paint_observer(NULL); 664 view_->set_paint_observer(NULL);
647 view_ = NULL; 665 view_ = NULL;
648 } 666 }
649 } 667 }
650 668
651 // Overridden from RenderWidgetHostViewAura::PaintObserver: 669 // Overridden from RenderWidgetHostViewAura::PaintObserver:
652 virtual void OnPaintComplete() OVERRIDE { 670 virtual void OnPaintComplete() OVERRIDE {
(...skipping 21 matching lines...) Expand all
674 view_ = NULL; 692 view_ = NULL;
675 } 693 }
676 694
677 scoped_ptr<aura::Window> window_; 695 scoped_ptr<aura::Window> window_;
678 RenderWidgetHostViewAura* view_; 696 RenderWidgetHostViewAura* view_;
679 bool loading_complete_; 697 bool loading_complete_;
680 bool received_paint_update_; 698 bool received_paint_update_;
681 bool compositor_updated_; 699 bool compositor_updated_;
682 bool has_screenshot_; 700 bool has_screenshot_;
683 701
702 // During tests, the aura windows don't get any paint updates. So the overlay
703 // container keeps waiting for a paint update it never receives, causing a
704 // timeout. So during tests, disable the wait for paint updates.
705 bool need_paint_update_;
706
684 DISALLOW_COPY_AND_ASSIGN(OverscrollNavigationOverlay); 707 DISALLOW_COPY_AND_ASSIGN(OverscrollNavigationOverlay);
685 }; 708 };
686 709
687 class WebContentsViewAura::WindowObserver 710 class WebContentsViewAura::WindowObserver
688 : public aura::WindowObserver, public aura::RootWindowObserver { 711 : public aura::WindowObserver, public aura::RootWindowObserver {
689 public: 712 public:
690 explicit WindowObserver(WebContentsViewAura* view) 713 explicit WindowObserver(WebContentsViewAura* view)
691 : view_(view), 714 : view_(view),
692 parent_(NULL) { 715 parent_(NULL) {
693 view_->window_->AddObserver(this); 716 view_->window_->AddObserver(this);
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
851 874
852 window_observer_.reset(); 875 window_observer_.reset();
853 #if defined(OS_WIN) 876 #if defined(OS_WIN)
854 child_window_observer_.reset(); 877 child_window_observer_.reset();
855 #endif 878 #endif
856 // Window needs a valid delegate during its destructor, so we explicitly 879 // Window needs a valid delegate during its destructor, so we explicitly
857 // delete it here. 880 // delete it here.
858 window_.reset(); 881 window_.reset();
859 } 882 }
860 883
884 void WebContentsViewAura::SetupOverlayWindowForTesting() {
885 if (navigation_overlay_.get())
886 navigation_overlay_->SetupForTesting();
887 }
888
861 void WebContentsViewAura::SizeChangedCommon(const gfx::Size& size) { 889 void WebContentsViewAura::SizeChangedCommon(const gfx::Size& size) {
862 if (web_contents_->GetInterstitialPage()) 890 if (web_contents_->GetInterstitialPage())
863 web_contents_->GetInterstitialPage()->SetSize(size); 891 web_contents_->GetInterstitialPage()->SetSize(size);
864 RenderWidgetHostView* rwhv = 892 RenderWidgetHostView* rwhv =
865 web_contents_->GetRenderWidgetHostView(); 893 web_contents_->GetRenderWidgetHostView();
866 if (rwhv) 894 if (rwhv)
867 rwhv->SetSize(size); 895 rwhv->SetSize(size);
868 } 896 }
869 897
870 void WebContentsViewAura::EndDrag(WebKit::WebDragOperationsMask ops) { 898 void WebContentsViewAura::EndDrag(WebKit::WebDragOperationsMask ops) {
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after
1044 OVERSCROLL_CONFIG_HORIZ_RESIST_AFTER); 1072 OVERSCROLL_CONFIG_HORIZ_RESIST_AFTER);
1045 int scroll = GetResistedScrollAmount(abs(delta_x), 1073 int scroll = GetResistedScrollAmount(abs(delta_x),
1046 static_cast<int>(threshold)); 1074 static_cast<int>(threshold));
1047 return gfx::Vector2d(delta_x < 0 ? -scroll : scroll, 0); 1075 return gfx::Vector2d(delta_x < 0 ? -scroll : scroll, 0);
1048 } 1076 }
1049 1077
1050 void WebContentsViewAura::PrepareOverscrollNavigationOverlay() { 1078 void WebContentsViewAura::PrepareOverscrollNavigationOverlay() {
1051 OverscrollWindowDelegate* delegate = static_cast<OverscrollWindowDelegate*>( 1079 OverscrollWindowDelegate* delegate = static_cast<OverscrollWindowDelegate*>(
1052 overscroll_window_->delegate()); 1080 overscroll_window_->delegate());
1053 delegate->set_show_shadow(false); 1081 delegate->set_show_shadow(false);
1082 delegate->stop_forwarding_events();
1054 overscroll_window_->SchedulePaintInRect( 1083 overscroll_window_->SchedulePaintInRect(
1055 gfx::Rect(overscroll_window_->bounds().size())); 1084 gfx::Rect(overscroll_window_->bounds().size()));
1056 navigation_overlay_->SetOverlayWindow(overscroll_window_.Pass(), 1085 navigation_overlay_->SetOverlayWindow(overscroll_window_.Pass(),
1057 delegate->has_screenshot()); 1086 delegate->has_screenshot());
1058 navigation_overlay_->StartObservingView(static_cast< 1087 navigation_overlay_->StartObservingView(static_cast<
1059 RenderWidgetHostViewAura*>(web_contents_->GetRenderWidgetHostView())); 1088 RenderWidgetHostViewAura*>(web_contents_->GetRenderWidgetHostView()));
1060 } 1089 }
1061 1090
1062 void WebContentsViewAura::UpdateOverscrollWindowBrightness(float delta_x) { 1091 void WebContentsViewAura::UpdateOverscrollWindowBrightness(float delta_x) {
1063 if (!overscroll_change_brightness_) 1092 if (!overscroll_change_brightness_)
(...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after
1372 } 1401 }
1373 1402
1374 ResetOverscrollTransform(); 1403 ResetOverscrollTransform();
1375 } 1404 }
1376 1405
1377 void WebContentsViewAura::OnOverscrollModeChange(OverscrollMode old_mode, 1406 void WebContentsViewAura::OnOverscrollModeChange(OverscrollMode old_mode,
1378 OverscrollMode new_mode) { 1407 OverscrollMode new_mode) {
1379 // Reset any in-progress overscroll animation first. 1408 // Reset any in-progress overscroll animation first.
1380 ResetOverscrollTransform(); 1409 ResetOverscrollTransform();
1381 1410
1382 if (new_mode == OVERSCROLL_NONE) { 1411 if (new_mode == OVERSCROLL_NONE ||
1412 (navigation_overlay_.get() && navigation_overlay_->has_window())) {
1383 current_overscroll_gesture_ = OVERSCROLL_NONE; 1413 current_overscroll_gesture_ = OVERSCROLL_NONE;
1384 } else { 1414 } else {
1385 // Cleanup state of the content window first, because that can reset the 1415 // Cleanup state of the content window first, because that can reset the
1386 // value of |current_overscroll_gesture_|. 1416 // value of |current_overscroll_gesture_|.
1387 PrepareContentWindowForOverscroll(); 1417 PrepareContentWindowForOverscroll();
1388 1418
1389 current_overscroll_gesture_ = new_mode; 1419 current_overscroll_gesture_ = new_mode;
1390 PrepareOverscrollWindow(); 1420 PrepareOverscrollWindow();
1391 1421
1392 UMA_HISTOGRAM_ENUMERATION("Overscroll.Started", new_mode, OVERSCROLL_COUNT); 1422 UMA_HISTOGRAM_ENUMERATION("Overscroll.Started", new_mode, OVERSCROLL_COUNT);
(...skipping 208 matching lines...) Expand 10 before | Expand all | Expand 10 after
1601 event.location(), 1631 event.location(),
1602 gfx::Screen::GetScreenFor(GetNativeView())->GetCursorScreenPoint(), 1632 gfx::Screen::GetScreenFor(GetNativeView())->GetCursorScreenPoint(),
1603 ConvertAuraEventFlagsToWebInputEventModifiers(event.flags())); 1633 ConvertAuraEventFlagsToWebInputEventModifiers(event.flags()));
1604 if (drag_dest_delegate_) 1634 if (drag_dest_delegate_)
1605 drag_dest_delegate_->OnDrop(); 1635 drag_dest_delegate_->OnDrop();
1606 current_drop_data_.reset(); 1636 current_drop_data_.reset();
1607 return current_drag_op_; 1637 return current_drag_op_;
1608 } 1638 }
1609 1639
1610 } // namespace content 1640 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698