summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authormazda@chromium.org <mazda@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2011-10-03 09:02:24 +0000
committermazda@chromium.org <mazda@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2011-10-03 09:02:24 +0000
commit2d0f2e95d4a44967424a7bb735d5263da3dea581 (patch)
tree9b2868014f1f58f4d369e73b162c75ccecabda0f
parent219e07987f9ec4e40418b251b4960681af726d53 (diff)
downloadchromium_src-2d0f2e95d4a44967424a7bb735d5263da3dea581.zip
chromium_src-2d0f2e95d4a44967424a7bb735d5263da3dea581.tar.gz
chromium_src-2d0f2e95d4a44967424a7bb735d5263da3dea581.tar.bz2
Show keyboard when the focused editable field is touched inside the web content area.
When an editable fieled is touched and the focus is moved to the element, NOTIFICATION_FOCUS_CHANGED_IN_PAGE is sent. However, if the field is already focused, no notification is sent. But keyboard should be shown in such a case. This CL - Adds NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED notification, which is sent when the focused editable field is touched, - Adds ChromeViewHostMsg_FocusedEditableNodeTouched IPC message, which is sent from renderer to browser when a touch released on the focused editable field, - Changes RenderWidget to handle touch events in OnHandleInputEvent, and - Handles NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED in KeyboardWidget to show keyboard. BUG=none TEST=Manual Review URL: http://codereview.chromium.org/7923005 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@103694 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/renderer_host/chrome_render_view_host_observer.cc9
-rw-r--r--chrome/browser/renderer_host/chrome_render_view_host_observer.h1
-rw-r--r--chrome/browser/ui/virtual_keyboard/virtual_keyboard_manager.cc32
-rw-r--r--chrome/common/chrome_notification_types.h5
-rw-r--r--chrome/common/render_messages.h4
-rw-r--r--chrome/renderer/chrome_render_view_observer.cc31
-rw-r--r--chrome/renderer/chrome_render_view_observer.h1
-rw-r--r--content/renderer/render_view.cc5
-rw-r--r--content/renderer/render_view.h2
-rw-r--r--content/renderer/render_view_observer.h2
-rw-r--r--content/renderer/render_widget.cc3
-rw-r--r--content/renderer/render_widget.h5
12 files changed, 100 insertions, 0 deletions
diff --git a/chrome/browser/renderer_host/chrome_render_view_host_observer.cc b/chrome/browser/renderer_host/chrome_render_view_host_observer.cc
index 6b573b5..6d1a8e27 100644
--- a/chrome/browser/renderer_host/chrome_render_view_host_observer.cc
+++ b/chrome/browser/renderer_host/chrome_render_view_host_observer.cc
@@ -53,6 +53,8 @@ bool ChromeRenderViewHostObserver::OnMessageReceived(
IPC_BEGIN_MESSAGE_MAP(ChromeRenderViewHostObserver, message)
IPC_MESSAGE_HANDLER(ChromeViewHostMsg_DomOperationResponse,
OnDomOperationResponse)
+ IPC_MESSAGE_HANDLER(ChromeViewHostMsg_FocusedEditableNodeTouched,
+ OnFocusedEditableNodeTouched)
IPC_MESSAGE_UNHANDLED(handled = false)
IPC_END_MESSAGE_MAP()
return handled;
@@ -152,3 +154,10 @@ void ChromeRenderViewHostObserver::OnDomOperationResponse(
Source<RenderViewHost>(render_view_host()),
Details<DomOperationNotificationDetails>(&details));
}
+
+void ChromeRenderViewHostObserver::OnFocusedEditableNodeTouched() {
+ NotificationService::current()->Notify(
+ chrome::NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED,
+ Source<RenderViewHost>(render_view_host()),
+ NotificationService::NoDetails());
+}
diff --git a/chrome/browser/renderer_host/chrome_render_view_host_observer.h b/chrome/browser/renderer_host/chrome_render_view_host_observer.h
index 5a5eaa8..e5e83dc 100644
--- a/chrome/browser/renderer_host/chrome_render_view_host_observer.h
+++ b/chrome/browser/renderer_host/chrome_render_view_host_observer.h
@@ -39,6 +39,7 @@ class ChromeRenderViewHostObserver : public RenderViewHostObserver {
void OnDomOperationResponse(const std::string& json_string,
int automation_id);
+ void OnFocusedEditableNodeTouched();
chrome_browser_net::Predictor* predictor_;
diff --git a/chrome/browser/ui/virtual_keyboard/virtual_keyboard_manager.cc b/chrome/browser/ui/virtual_keyboard/virtual_keyboard_manager.cc
index e8a35a9..31550cb 100644
--- a/chrome/browser/ui/virtual_keyboard/virtual_keyboard_manager.cc
+++ b/chrome/browser/ui/virtual_keyboard/virtual_keyboard_manager.cc
@@ -11,8 +11,11 @@
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/profiles/profile_manager.h"
#include "chrome/browser/tabs/tab_strip_model.h"
+#include "chrome/browser/ui/browser.h"
+#include "chrome/browser/ui/browser_window.h"
#include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h"
#include "chrome/browser/ui/views/dom_view.h"
+#include "chrome/browser/ui/views/frame/browser_view.h"
#include "chrome/common/chrome_notification_types.h"
#include "chrome/common/extensions/extension_messages.h"
#include "chrome/common/url_constants.h"
@@ -86,6 +89,10 @@ class KeyboardWidget
// Sets the target widget, adds/removes Widget::Observer, reparents etc.
void SetTarget(Widget* target);
+ // Returns the widget of the active browser, or NULL if there is no such
+ // widget.
+ views::Widget* GetBrowserWidget();
+
// Overridden from views::Widget.
virtual bool OnKeyEvent(const views::KeyEvent& event) OVERRIDE;
@@ -180,6 +187,9 @@ KeyboardWidget::KeyboardWidget()
views::TextInputTypeTracker::GetInstance()->AddTextInputTypeObserver(this);
registrar_.Add(this,
+ chrome::NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED,
+ NotificationService::AllSources());
+ registrar_.Add(this,
chrome::NOTIFICATION_HIDE_KEYBOARD_INVOKED,
NotificationService::AllSources());
registrar_.Add(this,
@@ -210,6 +220,8 @@ KeyboardWidget::~KeyboardWidget() {
}
void KeyboardWidget::ShowKeyboardForWidget(views::Widget* widget) {
+ if (target_ == widget && IsVisible())
+ return;
SetTarget(widget);
transform_.reset(new ui::InterpolatedTranslation(
@@ -256,6 +268,16 @@ void KeyboardWidget::SetTarget(views::Widget* target) {
}
}
+views::Widget* KeyboardWidget::GetBrowserWidget() {
+ Browser* browser = GetBrowser();
+ if (!browser)
+ return NULL;
+ BrowserView* view = BrowserView::GetBrowserViewForBrowser(browser);
+ if (!view)
+ return NULL;
+ return view->GetWidget();
+}
+
bool KeyboardWidget::OnKeyEvent(const views::KeyEvent& event) {
return target_ ? target_->OnKeyEvent(event) : false;
}
@@ -384,6 +406,16 @@ void KeyboardWidget::Observe(int type,
const NotificationSource& source,
const NotificationDetails& details) {
switch (type) {
+ case chrome::NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED: {
+ // In case the keyboard hid itself and the focus is still in an editable
+ // field, and the user touches the field, then we want to show the
+ // keyboard again.
+ views::Widget* widget = GetBrowserWidget();
+ if (widget)
+ ShowKeyboardForWidget(widget);
+ break;
+ }
+
case chrome::NOTIFICATION_HIDE_KEYBOARD_INVOKED: {
Hide();
break;
diff --git a/chrome/common/chrome_notification_types.h b/chrome/common/chrome_notification_types.h
index 523d392..aeafa8e 100644
--- a/chrome/common/chrome_notification_types.h
+++ b/chrome/common/chrome_notification_types.h
@@ -121,6 +121,11 @@ enum NotificationType {
// The source is the ExtensionTabHelper SetAppExtension was invoked on.
NOTIFICATION_TAB_CONTENTS_APPLICATION_EXTENSION_CHANGED,
+ // Notification posted when the element that is focused and currently accepts
+ // keyboard input inside the webpage has been touched. The source is the
+ // RenderViewHost and the details are not used.
+ NOTIFICATION_FOCUSED_EDITABLE_NODE_TOUCHED,
+
// Stuff inside the tabs ---------------------------------------------------
// Notification from TabContents that we have received a response from the
diff --git a/chrome/common/render_messages.h b/chrome/common/render_messages.h
index 84d1cff..6bd830a 100644
--- a/chrome/common/render_messages.h
+++ b/chrome/common/render_messages.h
@@ -526,6 +526,10 @@ IPC_MESSAGE_ROUTED0(ChromeViewHostMsg_DidBlockDisplayingInsecureContent)
// a secure origin by a security policy. The page may appear incomplete.
IPC_MESSAGE_ROUTED0(ChromeViewHostMsg_DidBlockRunningInsecureContent)
+// Message sent from renderer to the browser when the element that is focused
+// and currently accepts keyboard input inside the webpage has been touched.
+IPC_MESSAGE_ROUTED0(ChromeViewHostMsg_FocusedEditableNodeTouched)
+
// Suggest results -----------------------------------------------------------
IPC_MESSAGE_ROUTED3(ChromeViewHostMsg_SetSuggestions,
diff --git a/chrome/renderer/chrome_render_view_observer.cc b/chrome/renderer/chrome_render_view_observer.cc
index 4016919..444eb07 100644
--- a/chrome/renderer/chrome_render_view_observer.cc
+++ b/chrome/renderer/chrome_render_view_observer.cc
@@ -30,10 +30,12 @@
#include "net/base/data_url.h"
#include "skia/ext/image_operations.h"
#include "skia/ext/platform_canvas.h"
+#include "third_party/WebKit/Source/WebKit/chromium/public/WebAccessibilityObject.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebCString.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebDataSource.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebDocument.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebFrame.h"
+#include "third_party/WebKit/Source/WebKit/chromium/public/WebInputEvent.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebRect.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebSize.h"
#include "third_party/WebKit/Source/WebKit/chromium/public/WebString.h"
@@ -48,6 +50,7 @@
#include "webkit/glue/webkit_glue.h"
#include "v8/include/v8-testing.h"
+using WebKit::WebAccessibilityObject;
using WebKit::WebCString;
using WebKit::WebDataSource;
using WebKit::WebFrame;
@@ -56,6 +59,7 @@ using WebKit::WebRect;
using WebKit::WebSecurityOrigin;
using WebKit::WebSize;
using WebKit::WebString;
+using WebKit::WebTouchEvent;
using WebKit::WebURL;
using WebKit::WebURLRequest;
using WebKit::WebView;
@@ -723,6 +727,33 @@ void ChromeRenderViewObserver::DidClearWindowObject(WebFrame* frame) {
}
}
+void ChromeRenderViewObserver::DidHandleTouchEvent(const WebTouchEvent& event) {
+ // TODO(mazda): Consider using WebKit::WebInputEvent::GestureTap event when
+ // it's implemented. Only sends the message on touch end event
+ // for now.
+ if (event.type != WebKit::WebInputEvent::TouchEnd)
+ return;
+ // Ignore the case of multiple touches
+ if (event.touchesLength != 1)
+ return;
+ if (render_view()->webview()->textInputType() == WebKit::WebTextInputTypeNone)
+ return;
+ WebKit::WebNode node = render_view()->GetFocusedNode();
+ if (node.isNull())
+ return;
+ WebKit::WebAccessibilityObject accessibility =
+ render_view()->webview()->accessibilityObject();
+ if (accessibility.isNull())
+ return;
+ const WebKit::WebTouchPoint point = event.touches[0];
+ accessibility = accessibility.hitTest(point.position);
+ if (accessibility.isNull())
+ return;
+ if (accessibility.node() == node)
+ render_view()->Send(new ChromeViewHostMsg_FocusedEditableNodeTouched(
+ render_view()->routing_id()));
+}
+
void ChromeRenderViewObserver::CapturePageInfo(int load_id,
bool preliminary_capture) {
if (load_id != render_view()->page_id())
diff --git a/chrome/renderer/chrome_render_view_observer.h b/chrome/renderer/chrome_render_view_observer.h
index cf1497e..a52c311 100644
--- a/chrome/renderer/chrome_render_view_observer.h
+++ b/chrome/renderer/chrome_render_view_observer.h
@@ -68,6 +68,7 @@ class ChromeRenderViewObserver : public RenderViewObserver,
virtual void DidCommitProvisionalLoad(WebKit::WebFrame* frame,
bool is_new_navigation) OVERRIDE;
virtual void DidClearWindowObject(WebKit::WebFrame* frame) OVERRIDE;
+ virtual void DidHandleTouchEvent(const WebKit::WebTouchEvent& event) OVERRIDE;
// WebKit::WebPermissionClient implementation.
virtual bool allowDatabase(WebKit::WebFrame* frame,
diff --git a/content/renderer/render_view.cc b/content/renderer/render_view.cc
index 8d08fab..91d9c2d 100644
--- a/content/renderer/render_view.cc
+++ b/content/renderer/render_view.cc
@@ -223,6 +223,7 @@ using WebKit::WebStorageQuotaType;
using WebKit::WebString;
using WebKit::WebTextAffinity;
using WebKit::WebTextDirection;
+using WebKit::WebTouchEvent;
using WebKit::WebURL;
using WebKit::WebURLError;
using WebKit::WebURLRequest;
@@ -3948,6 +3949,10 @@ void RenderView::DidHandleMouseEvent(const WebKit::WebMouseEvent& event) {
FOR_EACH_OBSERVER(RenderViewObserver, observers_, DidHandleMouseEvent(event));
}
+void RenderView::DidHandleTouchEvent(const WebTouchEvent& event) {
+ FOR_EACH_OBSERVER(RenderViewObserver, observers_, DidHandleTouchEvent(event));
+}
+
void RenderView::OnWasHidden() {
RenderWidget::OnWasHidden();
diff --git a/content/renderer/render_view.h b/content/renderer/render_view.h
index 245e196..31a3141 100644
--- a/content/renderer/render_view.h
+++ b/content/renderer/render_view.h
@@ -134,6 +134,7 @@ class WebPlugin;
class WebSpeechInputController;
class WebSpeechInputListener;
class WebStorageNamespace;
+class WebTouchEvent;
class WebURLLoader;
class WebURLRequest;
class WebView;
@@ -649,6 +650,7 @@ class RenderView : public RenderWidget,
virtual bool WillHandleMouseEvent(
const WebKit::WebMouseEvent& event) OVERRIDE;
virtual void DidHandleMouseEvent(const WebKit::WebMouseEvent& event);
+ virtual void DidHandleTouchEvent(const WebKit::WebTouchEvent& event);
virtual void OnSetFocus(bool enable);
virtual void OnWasHidden();
virtual void OnWasRestored(bool needs_repainting);
diff --git a/content/renderer/render_view_observer.h b/content/renderer/render_view_observer.h
index de5dda5..6f42f86 100644
--- a/content/renderer/render_view_observer.h
+++ b/content/renderer/render_view_observer.h
@@ -21,6 +21,7 @@ class WebMediaPlayerClient;
class WebMouseEvent;
class WebNode;
class WebString;
+class WebTouchEvent;
class WebURL;
struct WebURLError;
}
@@ -67,6 +68,7 @@ class CONTENT_EXPORT RenderViewObserver : public IPC::Channel::Listener,
// These match the RenderView methods.
virtual void DidHandleMouseEvent(const WebKit::WebMouseEvent& event) {}
+ virtual void DidHandleTouchEvent(const WebKit::WebTouchEvent& event) {}
virtual void WillCreateMediaPlayer(WebKit::WebFrame* frame,
WebKit::WebMediaPlayerClient* client) {}
diff --git a/content/renderer/render_widget.cc b/content/renderer/render_widget.cc
index 2f0dfc2..b57c11c 100644
--- a/content/renderer/render_widget.cc
+++ b/content/renderer/render_widget.cc
@@ -58,6 +58,7 @@ using WebKit::WebRect;
using WebKit::WebScreenInfo;
using WebKit::WebSize;
using WebKit::WebTextDirection;
+using WebKit::WebTouchEvent;
using WebKit::WebVector;
using WebKit::WebWidget;
@@ -493,6 +494,8 @@ void RenderWidget::OnHandleInputEvent(const IPC::Message& message) {
DidHandleKeyEvent();
if (WebInputEvent::isMouseEventType(input_event->type))
DidHandleMouseEvent(*(static_cast<const WebMouseEvent*>(input_event)));
+ if (WebInputEvent::isTouchEventType(input_event->type))
+ DidHandleTouchEvent(*(static_cast<const WebTouchEvent*>(input_event)));
}
}
diff --git a/content/renderer/render_widget.h b/content/renderer/render_widget.h
index f44f289..624888b 100644
--- a/content/renderer/render_widget.h
+++ b/content/renderer/render_widget.h
@@ -46,6 +46,7 @@ class PlatformCanvas;
namespace WebKit {
class WebInputEvent;
class WebMouseEvent;
+class WebTouchEvent;
class WebWidget;
struct WebPopupMenuInfo;
}
@@ -314,6 +315,10 @@ class CONTENT_EXPORT RenderWidget
// just handled.
virtual void DidHandleMouseEvent(const WebKit::WebMouseEvent& event) {}
+ // Called by OnHandleInputEvent() to notify subclasses that a touch event was
+ // just handled.
+ virtual void DidHandleTouchEvent(const WebKit::WebTouchEvent& event) {}
+
// Routing ID that allows us to communicate to the parent browser process
// RenderWidgetHost. When MSG_ROUTING_NONE, no messages may be sent.
int32 routing_id_;