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

Side by Side Diff: content/renderer/render_view_impl.cc

Issue 10885004: Implement disambiguation popup (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Created 8 years, 3 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
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/renderer/render_view_impl.h" 5 #include "content/renderer/render_view_impl.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cmath> 8 #include <cmath>
9 #include <string> 9 #include <string>
10 #include <vector> 10 #include <vector>
(...skipping 337 matching lines...) Expand 10 before | Expand all | Expand 10 after
348 348
349 static const size_t kExtraCharsBeforeAndAfterSelection = 100; 349 static const size_t kExtraCharsBeforeAndAfterSelection = 100;
350 350
351 // The maximum number of popups that can be spawned from one page. 351 // The maximum number of popups that can be spawned from one page.
352 static const int kMaximumNumberOfUnacknowledgedPopups = 25; 352 static const int kMaximumNumberOfUnacknowledgedPopups = 25;
353 353
354 static const float kScalingIncrement = 0.1f; 354 static const float kScalingIncrement = 0.1f;
355 355
356 static const float kScalingIncrementForGesture = 0.01f; 356 static const float kScalingIncrementForGesture = 0.01f;
357 357
358 // The amount of padding to add to the disambiguation popup to show
359 // content around the possible elements, adding some context.
360 static const int kDisambiguationPopupPadding = 8;
361
362 // Constants used for fitting the disambiguation popup inside the bounds of
363 // the view. Note that there are mirror constants in PopupZoomer.java.
364 static const int kDisambiguationPopupBoundsMargin = 25;
365
366 // The smallest allowable touch target used for disambiguation popup.
367 // This value is used to determine the minimum amount we need to scale to
368 // make all targets touchable.
369 static const int kDisambiguationPopupMinimumTouchSize = 40;
370 static const float kDisambiguationPopupMaxScale = 5.0;
371 static const float kDisambiguationPopupMinScale = 2.0;
372
358 #if defined(OS_ANDROID) 373 #if defined(OS_ANDROID)
359 // Delay between tapping in content and launching the associated android intent. 374 // Delay between tapping in content and launching the associated android intent.
360 // Used to allow users see what has been recognized as content. 375 // Used to allow users see what has been recognized as content.
361 static const size_t kContentIntentDelayMilliseconds = 700; 376 static const size_t kContentIntentDelayMilliseconds = 700;
362 #endif 377 #endif
363 378
364 static RenderViewImpl* FromRoutingID(int32 routing_id) { 379 static RenderViewImpl* FromRoutingID(int32 routing_id) {
365 return static_cast<RenderViewImpl*>( 380 return static_cast<RenderViewImpl*>(
366 ChildThread::current()->ResolveRoute(routing_id)); 381 ChildThread::current()->ResolveRoute(routing_id));
367 } 382 }
(...skipping 632 matching lines...) Expand 10 before | Expand all | Expand 10 after
1000 IPC_MESSAGE_HANDLER(ViewMsg_ContextMenuClosed, OnContextMenuClosed) 1015 IPC_MESSAGE_HANDLER(ViewMsg_ContextMenuClosed, OnContextMenuClosed)
1001 // TODO(viettrungluu): Move to a separate message filter. 1016 // TODO(viettrungluu): Move to a separate message filter.
1002 #if defined(OS_MACOSX) 1017 #if defined(OS_MACOSX)
1003 IPC_MESSAGE_HANDLER(ViewMsg_SetInLiveResize, OnSetInLiveResize) 1018 IPC_MESSAGE_HANDLER(ViewMsg_SetInLiveResize, OnSetInLiveResize)
1004 #endif 1019 #endif
1005 IPC_MESSAGE_HANDLER(ViewMsg_SetHistoryLengthAndPrune, 1020 IPC_MESSAGE_HANDLER(ViewMsg_SetHistoryLengthAndPrune,
1006 OnSetHistoryLengthAndPrune) 1021 OnSetHistoryLengthAndPrune)
1007 IPC_MESSAGE_HANDLER(ViewMsg_EnableViewSourceMode, OnEnableViewSourceMode) 1022 IPC_MESSAGE_HANDLER(ViewMsg_EnableViewSourceMode, OnEnableViewSourceMode)
1008 IPC_MESSAGE_HANDLER(JavaBridgeMsg_Init, OnJavaBridgeInit) 1023 IPC_MESSAGE_HANDLER(JavaBridgeMsg_Init, OnJavaBridgeInit)
1009 IPC_MESSAGE_HANDLER(ViewMsg_SetAccessibilityMode, OnSetAccessibilityMode) 1024 IPC_MESSAGE_HANDLER(ViewMsg_SetAccessibilityMode, OnSetAccessibilityMode)
1025 IPC_MESSAGE_HANDLER(ViewMsg_ReleaseDisambiguationPopupDIB,
1026 OnReleaseDisambiguationPopupDIB)
1010 1027
1011 // Have the super handle all other messages. 1028 // Have the super handle all other messages.
1012 IPC_MESSAGE_UNHANDLED(handled = RenderWidget::OnMessageReceived(message)) 1029 IPC_MESSAGE_UNHANDLED(handled = RenderWidget::OnMessageReceived(message))
1013 IPC_END_MESSAGE_MAP() 1030 IPC_END_MESSAGE_MAP()
1014 1031
1015 if (!msg_is_ok) { 1032 if (!msg_is_ok) {
1016 // The message had a handler, but its deserialization failed. 1033 // The message had a handler, but its deserialization failed.
1017 // Kill the renderer to avoid potential spoofing attacks. 1034 // Kill the renderer to avoid potential spoofing attacks.
1018 CHECK(false) << "Unable to deserialize message in RenderViewImpl."; 1035 CHECK(false) << "Unable to deserialize message in RenderViewImpl.";
1019 } 1036 }
(...skipping 4865 matching lines...) Expand 10 before | Expand all | Expand 10 after
5885 bool RenderViewImpl::WebWidgetHandlesCompositorScheduling() const { 5902 bool RenderViewImpl::WebWidgetHandlesCompositorScheduling() const {
5886 return !!RenderThreadImpl::current()->compositor_thread(); 5903 return !!RenderThreadImpl::current()->compositor_thread();
5887 } 5904 }
5888 5905
5889 void RenderViewImpl::OnJavaBridgeInit() { 5906 void RenderViewImpl::OnJavaBridgeInit() {
5890 DCHECK(!java_bridge_dispatcher_); 5907 DCHECK(!java_bridge_dispatcher_);
5891 #if defined(ENABLE_JAVA_BRIDGE) 5908 #if defined(ENABLE_JAVA_BRIDGE)
5892 java_bridge_dispatcher_ = new JavaBridgeDispatcher(this); 5909 java_bridge_dispatcher_ = new JavaBridgeDispatcher(this);
5893 #endif 5910 #endif
5894 } 5911 }
5912
5913 // Compute the scaling factor to ensure the smallest touch candidate reaches
darin (slow to review) 2012/08/30 17:39:23 render_view_impl.cc is already packed with code fo
trchen 2012/08/30 21:15:22 That sounds like a great idea. I think splitting i
5914 // a certain clickable size after zooming
5915 static float FindOptimalScaleFactor(const WebVector<WebRect>& target_rects) {
5916 using std::min;
5917 using std::max;
5918 if (!target_rects.size()) // shall never reach
5919 return kDisambiguationPopupMinScale;
5920 int smallest_target = min(target_rects[0].width, target_rects[0].height);
5921 for (size_t i = 1; i < target_rects.size(); i++) {
5922 smallest_target = min(smallest_target, target_rects[i].width);
5923 smallest_target = min(smallest_target, target_rects[i].height);
5924 }
5925 smallest_target = max(smallest_target, 1);
5926 return min(kDisambiguationPopupMaxScale, max(kDisambiguationPopupMinScale,
5927 static_cast<float>(kDisambiguationPopupMinimumTouchSize)
5928 / smallest_target));
5929 }
5930
5931 static void TrimEdges(int *e1, int *e2, int max_combined) {
5932 if (*e1 + *e2 <= max_combined)
5933 return;
5934
5935 if (std::min(*e1, *e2) * 2 >= max_combined) {
5936 *e1 = *e2 = max_combined / 2;
5937 } else if (*e1 > *e2) {
5938 *e1 = max_combined - *e2;
5939 } else
5940 *e2 = max_combined - *e1;
5941 }
5942
5943 // Ensure the disambiguation popup fits inside the screen,
5944 // clip the edges farthest to the touch point if needed.
5945 static gfx::Rect CropZoomArea(const gfx::Rect& zoom_rect,
5946 const gfx::Size& viewport_size,
5947 const gfx::Point& touch_point,
5948 float scale) {
5949 gfx::Size max_size = viewport_size;
5950 max_size.Enlarge(-2 * kDisambiguationPopupBoundsMargin,
5951 -2 * kDisambiguationPopupBoundsMargin);
5952 max_size = max_size.Scale(1.0 / scale);
5953
5954 int left = touch_point.x() - zoom_rect.x();
5955 int right = zoom_rect.right() - touch_point.x();
5956 int top = touch_point.y() - zoom_rect.y();
5957 int bottom = zoom_rect.bottom() - touch_point.y();
5958 TrimEdges(&left, &right, max_size.width());
5959 TrimEdges(&top, &bottom, max_size.height());
5960
5961 return gfx::Rect(touch_point.x() - left,
5962 touch_point.y() - top,
5963 left + right,
5964 top + bottom);
5965 }
5966
5967 bool RenderViewImpl::handleDisambiguationPopup(
darin (slow to review) 2012/08/30 17:39:23 why is this function named "handleDisambiguationPo
trchen 2012/08/30 21:15:22 Yea... I agree the naming is confusing here. Up t
5968 const WebKit::WebGestureEvent& event,
5969 const WebVector<WebRect>& target_rects) {
5970 gfx::Rect zoom_rect = event.boundingBox;
5971 for (size_t i = 0; i < target_rects.size(); i++)
5972 zoom_rect = zoom_rect.Union(gfx::Rect(target_rects[i]));
5973 zoom_rect.Inset(-kDisambiguationPopupPadding, -kDisambiguationPopupPadding);
5974 zoom_rect = zoom_rect.Intersect(gfx::Rect(GetSize()));
5975
5976 float scale = FindOptimalScaleFactor(target_rects);
5977 zoom_rect = CropZoomArea(
5978 zoom_rect, GetSize(), gfx::Point(event.x, event.y), scale);
5979
5980 gfx::Size canvas_size = zoom_rect.size();
5981 canvas_size = canvas_size.Scale(scale);
5982
5983 TransportDIB* transport_dib = NULL;
5984 {
5985 scoped_ptr<skia::PlatformCanvas> canvas(
5986 RenderProcess::current()->GetDrawingCanvas(&transport_dib,
5987 gfx::Rect(canvas_size)));
5988 if (!canvas.get())
5989 return false;
5990
5991 canvas->scale(scale, scale);
5992
5993 canvas->translate(-zoom_rect.x(), -zoom_rect.y());
5994 webwidget_->paint(webkit_glue::ToWebCanvas(canvas.get()), zoom_rect,
5995 WebWidget::ForceSoftwareRenderingAndIgnoreGPUResidentContent);
5996 }
5997 Send(new ViewHostMsg_MultipleTargetsTouched(routing_id_,
5998 zoom_rect,
5999 canvas_size,
6000 transport_dib->id()));
6001
6002 return true;
6003 }
6004
6005 void RenderViewImpl::OnReleaseDisambiguationPopupDIB(
6006 TransportDIB::Handle dib_handle) {
6007 TransportDIB* dib = TransportDIB::CreateWithHandle(dib_handle);
6008 RenderProcess::current()->ReleaseTransportDIB(dib);
6009 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698