summaryrefslogtreecommitdiffstats
path: root/WebKit
diff options
context:
space:
mode:
authorLeon Scroggins <scroggo@google.com>2010-05-03 14:21:02 +0100
committerLeon Scroggins <scroggo@google.com>2010-05-05 14:56:43 -0400
commit1cc2f5523913bd14a01c0c85710dcd6f0d7b5bb8 (patch)
tree6b54bab07b61f358f3fd0edc52bc135946a299d3 /WebKit
parent7e3fdd33ac8153016019ccdc7b5bb9ec788776fa (diff)
downloadexternal_webkit-1cc2f5523913bd14a01c0c85710dcd6f0d7b5bb8.zip
external_webkit-1cc2f5523913bd14a01c0c85710dcd6f0d7b5bb8.tar.gz
external_webkit-1cc2f5523913bd14a01c0c85710dcd6f0d7b5bb8.tar.bz2
Enable contentEditable.
WebViewCore.cpp: Open the keyboard when a contentEditable element is put into focus by a click. In key(), return whether the selection changed if a contentEditable element is in focus. CacheBuilder.cpp: Add root contentEditable elements to the navigation tree. CachedNode.h: Include contentEditable elements as elements that want key events. CachedNodeType.h Add a type for contentEditable. WebView.cpp: Do not call setFollowedLink for contentEditable, so that the orange selection ring stays around the field. Add a check to determine whether the page should handle shift and arrow keys. Bug 1788820 Caveats: Does not ensure that the caret remains on screen. Frame::revealSelection is called, but we ignore it for other reasons. Need to investigate that. The cursor will blink if the contentEditable node has focus, even if the user has not clicked on it or has moved to a different input field. Further, while in this state, the user can input text. Requires a change to frameworks/base Change-Id: Ife39254f46dcc1046a075eee2fda6cf4879b4ee8
Diffstat (limited to 'WebKit')
-rw-r--r--WebKit/android/jni/WebViewCore.cpp22
-rw-r--r--WebKit/android/nav/CacheBuilder.cpp7
-rw-r--r--WebKit/android/nav/CachedNode.h3
-rw-r--r--WebKit/android/nav/CachedNodeType.h3
-rw-r--r--WebKit/android/nav/WebView.cpp19
5 files changed, 47 insertions, 7 deletions
diff --git a/WebKit/android/jni/WebViewCore.cpp b/WebKit/android/jni/WebViewCore.cpp
index 14fd44e..56b0601 100644
--- a/WebKit/android/jni/WebViewCore.cpp
+++ b/WebKit/android/jni/WebViewCore.cpp
@@ -1985,12 +1985,25 @@ void WebViewCore::listBoxRequest(WebCoreReply* reply, const uint16_t** labels, s
bool WebViewCore::key(const PlatformKeyboardEvent& event)
{
- WebCore::EventHandler* eventHandler = m_mainFrame->eventHandler();
+ WebCore::EventHandler* eventHandler;
WebCore::Node* focusNode = currentFocus();
- if (focusNode)
- eventHandler = focusNode->document()->frame()->eventHandler();
DBG_NAV_LOGD("keyCode=%s unichar=%d focusNode=%p",
event.keyIdentifier().utf8().data(), event.unichar(), focusNode);
+ if (focusNode) {
+ WebCore::Frame* frame = focusNode->document()->frame();
+ eventHandler = frame->eventHandler();
+ if (focusNode->isContentEditable()) {
+ // keyEvent will return true even if the contentEditable did not
+ // change its selection. In the case that it does not, we want to
+ // return false so that the key will be sent back to our navigation
+ // system.
+ VisibleSelection old = frame->selection()->selection();
+ eventHandler->keyEvent(event);
+ return frame->selection()->selection() != old;
+ }
+ } else {
+ eventHandler = m_mainFrame->eventHandler();
+ }
return eventHandler->keyEvent(event);
}
@@ -2195,6 +2208,9 @@ bool WebViewCore::handleMouseClick(WebCore::Frame* framePtr, WebCore::Node* node
} else {
requestKeyboard(false);
}
+ } else if (focusNode->isContentEditable()) {
+ setFocusControllerActive(framePtr, true);
+ requestKeyboard(true);
}
}
return handled;
diff --git a/WebKit/android/nav/CacheBuilder.cpp b/WebKit/android/nav/CacheBuilder.cpp
index b98b31f..c5f7b12 100644
--- a/WebKit/android/nav/CacheBuilder.cpp
+++ b/WebKit/android/nav/CacheBuilder.cpp
@@ -1112,6 +1112,13 @@ void CacheBuilder::BuildFrame(Frame* root, Frame* frame,
type = PLUGIN_CACHEDNODETYPE;
goto keepNode;
}
+ // Only use the root contentEditable element
+ if (node->isContentEditable() && !node->parent()->isContentEditable()) {
+ bounds = absBounds;
+ takesFocus = true;
+ type = CONTENT_EDITABLE_CACHEDNODETYPE;
+ goto keepNode;
+ }
if (nodeRenderer->isRenderBlock()) {
RenderBlock* renderBlock = (RenderBlock*) nodeRenderer;
if (renderBlock->hasColumns()) {
diff --git a/WebKit/android/nav/CachedNode.h b/WebKit/android/nav/CachedNode.h
index b707ac1..09f53c3 100644
--- a/WebKit/android/nav/CachedNode.h
+++ b/WebKit/android/nav/CachedNode.h
@@ -108,6 +108,7 @@ public:
int index() const { return mIndex; }
void init(WebCore::Node* node);
bool isAnchor() const { return mType == ANCHOR_CACHEDNODETYPE; }
+ bool isContentEditable() const { return mType == CONTENT_EDITABLE_CACHEDNODETYPE; }
bool isCursor() const { return mIsCursor; }
bool isArea() const { return mType == AREA_CACHEDNODETYPE; }
bool isFocus() const { return mIsFocus; }
@@ -174,7 +175,7 @@ public:
const CachedNode* traverseNextNode() const { return mLast ? NULL : &this[1]; }
bool useBounds() const { return mUseBounds; }
bool useHitBounds() const { return mUseHitBounds; }
- bool wantsKeyEvents() const { return isTextInput() || isPlugin(); }
+ bool wantsKeyEvents() const { return isTextInput() || isPlugin() || isContentEditable(); }
private:
friend class CacheBuilder;
WebCore::String mExport;
diff --git a/WebKit/android/nav/CachedNodeType.h b/WebKit/android/nav/CachedNodeType.h
index 8334b2f..8bc9328 100644
--- a/WebKit/android/nav/CachedNodeType.h
+++ b/WebKit/android/nav/CachedNodeType.h
@@ -38,7 +38,8 @@ enum CachedNodeType {
FRAME_CACHEDNODETYPE,
PLUGIN_CACHEDNODETYPE,
TEXT_INPUT_CACHEDNODETYPE,
- SELECT_CACHEDNODETYPE
+ SELECT_CACHEDNODETYPE,
+ CONTENT_EDITABLE_CACHEDNODETYPE
};
enum CachedNodeBits {
diff --git a/WebKit/android/nav/WebView.cpp b/WebKit/android/nav/WebView.cpp
index d5c0758..fff0ea3 100644
--- a/WebKit/android/nav/WebView.cpp
+++ b/WebKit/android/nav/WebView.cpp
@@ -882,7 +882,7 @@ bool motionUp(int x, int y, int slop)
viewInvalidate();
if (!result->isTextInput()) {
clearTextEntry();
- if (!result->isSelect())
+ if (!result->isSelect() && !result->isContentEditable())
setFollowedLink(true);
if (syntheticLink)
overrideUrlLoading(result->getExport());
@@ -1263,6 +1263,19 @@ static const CachedInput* getInputCandidate(JNIEnv *env, jobject obj)
return cursor ? frame->textInput(cursor) : 0;
}
+static jboolean nativePageShouldHandleShiftAndArrows(JNIEnv *env, jobject obj)
+{
+ const CachedNode* focus = getFocusNode(env, obj);
+ if (!focus) return false;
+ // Plugins handle shift and arrows whether or not they have focus.
+ if (focus->isPlugin()) return true;
+ const CachedNode* cursor = getCursorNode(env, obj);
+ // ContentEditable nodes should only receive shift and arrows if they have
+ // both the cursor and the focus.
+ return cursor && cursor->nodePointer() == focus->nodePointer()
+ && cursor->isContentEditable();
+}
+
static jboolean nativeCursorMatchesFocus(JNIEnv *env, jobject obj)
{
const CachedNode* cursor = getCursorNode(env, obj);
@@ -1636,7 +1649,7 @@ static void nativeSetFindIsEmpty(JNIEnv *env, jobject obj)
static void nativeSetFollowedLink(JNIEnv *env, jobject obj, bool followed)
{
const CachedNode* cursor = getCursorNode(env, obj);
- if (cursor && !cursor->isSelect()) {
+ if (cursor && !cursor->isSelect() && ! cursor->isContentEditable()) {
WebView* view = GET_NATIVE_VIEW(env, obj);
LOG_ASSERT(view, "view not set in %s", __FUNCTION__);
view->setFollowedLink(followed);
@@ -1901,6 +1914,8 @@ static JNINativeMethod gJavaWebViewMethods[] = {
(void*) nativeCreate },
{ "nativeCursorFramePointer", "()I",
(void*) nativeCursorFramePointer },
+ { "nativePageShouldHandleShiftAndArrows", "()Z",
+ (void*) nativePageShouldHandleShiftAndArrows },
{ "nativeCursorMatchesFocus", "()Z",
(void*) nativeCursorMatchesFocus },
{ "nativeCursorNodeBounds", "()Landroid/graphics/Rect;",