Title: [204728] trunk
Revision
204728
Author
[email protected]
Date
2016-08-22 11:02:03 -0700 (Mon, 22 Aug 2016)

Log Message

<select> menu on iPad causes shifting of hit-testing areas
https://bugs.webkit.org/show_bug.cgi?id=150079

Reviewed by Tim Horton.

Source/WebKit2:

-isAssistingNode (aka the poorly named isEditable) is input into WebPageProxy::computeCustomFixedPositionRect(),
so when it changes we have to update visible rects. We were doing this on focus, but failing
to do it on blur.

Added the ability to test by:
1. Making it possible to initiate an animated scroll in the UI process
2. Adding callbacks for starting and ending interaction with a form control. Sadly
the "ending interaction" for <select> popovers on iPad isn't late enough, since we
have no way currently to know when the dimming view behind the popover animates out,
so for now the test keeps trying to tap a button.

Test: fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html

* UIProcess/API/Cocoa/WKWebView.mm:
(-[WKWebView _zoomToPoint:atScale:animated:]):
(-[WKWebView _scrollToRect:origin:minimumScrollDistance:]):
(-[WKWebView _scrollByContentOffset:]):
(-[WKWebView _zoomToFocusRect:selectionRect:fontSize:minimumScale:maximumScale:allowScaling:forceScroll:]):
(-[WKWebView didStartFormControlInteraction]):
(-[WKWebView didEndFormControlInteraction]):
* UIProcess/API/Cocoa/WKWebViewPrivate.h:
* UIProcess/ios/WKContentView.mm:
(-[WKContentView didUpdateVisibleRect:unobscuredRect:unobscuredRectInScrollViewCoordinates:obscuredInset:scale:minimumScale:inStableState:isChangingObscuredInsetsInteractively:enclosedInScrollableAncestorView:]):
* UIProcess/ios/WKContentViewInteraction.mm:
(-[WKContentView setIsEditable:]):
(-[WKContentView _startAssistingNode:userIsInteracting:blurPreviousNode:userObject:]):
(-[WKContentView _stopAssistingNode]):

Tools:

-isAssistingNode (aka the poorly named isEditable) is input into WebPageProxy::computeCustomFixedPositionRect(),
so when it changes we have to update visible rects. We were doing this on focus, but failing
to do it on blur.

Added the ability to test by:
1. Making it possible to initiate an animated scroll in the UI process
2. Adding callbacks for starting and ending interaction with a form control. Sadly
the "ending interaction" for <select> popovers on iPad isn't late enough, since we
have no way currently to know when the dimming view behind the popover animates out,
so for now the test keeps trying to tap a button.

* WebKitTestRunner/UIScriptContext/Bindings/UIScriptController.idl:
* WebKitTestRunner/UIScriptContext/UIScriptContext.h:
* WebKitTestRunner/UIScriptContext/UIScriptController.cpp:
(WTR::UIScriptController::setDidStartFormControlInteractionCallback):
(WTR::UIScriptController::didStartFormControlInteractionCallback):
(WTR::UIScriptController::setDidEndFormControlInteractionCallback):
(WTR::UIScriptController::didEndFormControlInteractionCallback):
(WTR::UIScriptController::scrollToOffset):
(WTR::UIScriptController::platformSetDidStartFormControlInteractionCallback):
(WTR::UIScriptController::platformSetDidEndFormControlInteractionCallback):
* WebKitTestRunner/UIScriptContext/UIScriptController.h:
* WebKitTestRunner/cocoa/TestRunnerWKWebView.h:
* WebKitTestRunner/cocoa/TestRunnerWKWebView.mm:
(-[TestRunnerWKWebView dealloc]):
(-[TestRunnerWKWebView didStartFormControlInteraction]):
(-[TestRunnerWKWebView didEndFormControlInteraction]):
* WebKitTestRunner/ios/UIScriptControllerIOS.mm:
(WTR::contentOffsetBoundedInValidRange):
(WTR::UIScriptController::scrollToOffset):
(WTR::UIScriptController::platformSetDidStartFormControlInteractionCallback):
(WTR::UIScriptController::platformSetDidEndFormControlInteractionCallback):

LayoutTests:

This test:
1. Scrolls in the ui process, so that position:fixed kicks in
2. Taps on a <select>, which disabled position:fixed behavior
3. Chooses a <select> option, dismissing the <select>, which restores position:fixed behavior
4. Tries to tap a button inside position:fixed.

* fast/forms/ios/ipad/unfocus-inside-fixed-hittest-expected.txt: Added.
* fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html: Added.

Modified Paths

Added Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (204727 => 204728)


--- trunk/LayoutTests/ChangeLog	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/LayoutTests/ChangeLog	2016-08-22 18:02:03 UTC (rev 204728)
@@ -1,3 +1,19 @@
+2016-08-22  Simon Fraser  <[email protected]>
+
+        <select> menu on iPad causes shifting of hit-testing areas
+        https://bugs.webkit.org/show_bug.cgi?id=150079
+
+        Reviewed by Tim Horton.
+
+        This test:
+        1. Scrolls in the ui process, so that position:fixed kicks in
+        2. Taps on a <select>, which disabled position:fixed behavior
+        3. Chooses a <select> option, dismissing the <select>, which restores position:fixed behavior
+        4. Tries to tap a button inside position:fixed.
+
+        * fast/forms/ios/ipad/unfocus-inside-fixed-hittest-expected.txt: Added.
+        * fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html: Added.
+
 2016-08-22  Antti Koivisto  <[email protected]>
 
         Can't style descendants in shadow tree using the :host pseudo class

Added: trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest-expected.txt (0 => 204728)


--- trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest-expected.txt	                        (rev 0)
+++ trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest-expected.txt	2016-08-22 18:02:03 UTC (rev 204728)
@@ -0,0 +1,5 @@
+This is the top
+
+Click Me
+June
+PASS: hit testing found #target after select interation

Added: trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html (0 => 204728)


--- trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html	                        (rev 0)
+++ trunk/LayoutTests/fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html	2016-08-22 18:02:03 UTC (rev 204728)
@@ -0,0 +1,137 @@
+<!DOCTYPE html> <!-- webkit-test-runner [ useFlexibleViewport=true ] -->
+
+<html>
+<head>
+    <meta name="viewport" content="initial-scale=1.0, user-scalable=no">
+    <style>
+        body {
+            height: 1500px;
+        }
+        #container {
+            position: fixed;
+            top: 10px;
+            left: 10px;
+            bottom: 30px;
+            right: 10px;
+            background-color: rgba(0, 0, 0, 0.5);
+            padding: 10px;
+            box-sizing: border-box;
+            border: 5px solid black;
+        }
+        
+        select {
+            display: block;
+            margin: 500px 200px 20px 20px;
+        }
+        
+        button {
+            display: block;
+        }
+        
+    </style>
+    <script src=""
+    <script>
+        if (window.testRunner)
+            testRunner.waitUntilDone();
+
+        function getSingleTapUIScript(x, y)
+        {
+            return `
+                (function() {
+                    uiController.singleTapAtPoint(${x}, ${y}, function() {
+                        uiController.uiScriptComplete('');
+                    });
+                })();`
+        }
+
+        function getScrollDownUIScript(x, y)
+        {
+            return `
+                (function() {
+                    uiController.didEndScrollingCallback = function() {
+                        uiController.uiScriptComplete();
+                    };
+
+                    uiController.scrollToOffset(${x}, ${y});
+                })();`
+        }
+
+        function getTapOnSelectUIScript(x, y)
+        {
+            return `
+                (function() {
+                    uiController.didStartFormControlInteractionCallback = function() {
+                        uiController.selectFormAccessoryPickerRow(5);
+                    };
+
+                    uiController.didEndFormControlInteractionCallback = function() {
+                        uiController.uiScriptComplete();
+                    };
+
+                    uiController.singleTapAtPoint(${x}, ${y}, function() {
+                    });
+                })();`
+        }
+
+        var clicked = false;
+        function buttonClicked()
+        {
+            document.getElementById('result').textContent = 'PASS: hit testing found #target after select interation';
+            if (window.testRunner)
+                testRunner.notifyDone();
+        }
+
+        function tryTapOnButton()
+        {
+            var point = getPointInsideElement(document.getElementById('target'), 10, 10);
+            testRunner.runUIScript(getSingleTapUIScript(point.x, point.y), function() {
+            });
+            
+            // We have to keep retrying, because the dimming view behind the popover animates out,
+            // and we currently have no callback when that animation completes.
+            window.setTimeout(tryTapOnButton, 100);
+        }
+
+        function doTest()
+        {
+            if (!window.testRunner)
+                return;
+
+            testRunner.waitUntilDone();
+            testRunner.dumpAsText();
+
+            testRunner.runUIScript(getScrollDownUIScript(0, 500), function() {
+                var selectElement = document.getElementsByTagName('select')[0];
+                var point = getPointInsideElement(selectElement, 10, 10);
+                testRunner.runUIScript(getTapOnSelectUIScript(point.x, point.y), function() {
+                    document.getElementById('select-value').textContent = selectElement.value;
+                    tryTapOnButton();
+                });
+            });
+        }
+        
+        window.addEventListener('load', doTest, false);
+    </script>
+</head>
+<body>
+    <p>This is the top</p>
+    <div id="container">
+        <button id="target" _onclick_="buttonClicked()">Click Me</button>
+        <select>
+            <option>January</option>
+            <option>February</option>
+            <option>March</option>
+            <option>April</option>
+            <option>May</option>
+            <option>June</option>
+            <option>July</option>
+            <option>August</option>
+            <option>September</option>
+        </select>
+        <span id="select-value">Value goes here</span>
+        <div id="result">FAIL: should have hit-tested and found #target element</div>
+    </div>
+    
+</div>
+</body>
+</html>

Modified: trunk/Source/WebKit2/ChangeLog (204727 => 204728)


--- trunk/Source/WebKit2/ChangeLog	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Source/WebKit2/ChangeLog	2016-08-22 18:02:03 UTC (rev 204728)
@@ -1,3 +1,38 @@
+2016-08-22  Simon Fraser  <[email protected]>
+
+        <select> menu on iPad causes shifting of hit-testing areas
+        https://bugs.webkit.org/show_bug.cgi?id=150079
+
+        Reviewed by Tim Horton.
+
+        -isAssistingNode (aka the poorly named isEditable) is input into WebPageProxy::computeCustomFixedPositionRect(),
+        so when it changes we have to update visible rects. We were doing this on focus, but failing
+        to do it on blur.
+
+        Added the ability to test by:
+        1. Making it possible to initiate an animated scroll in the UI process
+        2. Adding callbacks for starting and ending interaction with a form control. Sadly
+        the "ending interaction" for <select> popovers on iPad isn't late enough, since we
+        have no way currently to know when the dimming view behind the popover animates out,
+        so for now the test keeps trying to tap a button.
+
+        Test: fast/forms/ios/ipad/unfocus-inside-fixed-hittest.html
+
+        * UIProcess/API/Cocoa/WKWebView.mm:
+        (-[WKWebView _zoomToPoint:atScale:animated:]):
+        (-[WKWebView _scrollToRect:origin:minimumScrollDistance:]):
+        (-[WKWebView _scrollByContentOffset:]):
+        (-[WKWebView _zoomToFocusRect:selectionRect:fontSize:minimumScale:maximumScale:allowScaling:forceScroll:]):
+        (-[WKWebView didStartFormControlInteraction]):
+        (-[WKWebView didEndFormControlInteraction]):
+        * UIProcess/API/Cocoa/WKWebViewPrivate.h:
+        * UIProcess/ios/WKContentView.mm:
+        (-[WKContentView didUpdateVisibleRect:unobscuredRect:unobscuredRectInScrollViewCoordinates:obscuredInset:scale:minimumScale:inStableState:isChangingObscuredInsetsInteractively:enclosedInScrollableAncestorView:]):
+        * UIProcess/ios/WKContentViewInteraction.mm:
+        (-[WKContentView setIsEditable:]):
+        (-[WKContentView _startAssistingNode:userIsInteracting:blurPreviousNode:userObject:]):
+        (-[WKContentView _stopAssistingNode]):
+
 2016-08-22  Daniel Bates  <[email protected]>
 
         [iOS] <a ping> and <area ping> tests time out

Modified: trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebView.mm (204727 => 204728)


--- trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebView.mm	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebView.mm	2016-08-22 18:02:03 UTC (rev 204728)
@@ -1433,6 +1433,8 @@
     if (scale != zoomScale)
         _page->willStartUserTriggeredZooming();
 
+    LOG_WITH_STREAM(VisibleRects, stream << "_zoomToPoint:" << point << " scale: " << scale << " duration:" << duration);
+
     [_scrollView _zoomToCenter:point scale:scale duration:duration];
 }
 
@@ -1533,6 +1535,8 @@
 
     [_contentView willStartZoomOrScroll];
 
+    LOG_WITH_STREAM(VisibleRects, stream << "_scrollToRect: scrolling to " << [_scrollView contentOffset] + scrollViewOffsetDelta);
+
     [_scrollView setContentOffset:([_scrollView contentOffset] + scrollViewOffsetDelta) animated:YES];
     return true;
 }
@@ -1549,6 +1553,9 @@
     if (CGPointEqualToPoint(boundedOffset, currentOffset))
         return;
     [_contentView willStartZoomOrScroll];
+
+    LOG_WITH_STREAM(VisibleRects, stream << "_scrollByContentOffset: scrolling to " << boundedOffset);
+
     [_scrollView setContentOffset:boundedOffset animated:YES];
 }
 
@@ -1674,6 +1681,8 @@
     if (scale != contentZoomScale(self))
         _page->willStartUserTriggeredZooming();
 
+    LOG_WITH_STREAM(VisibleRects, stream << "_zoomToFocusRect: zooming to " << newCenter << " scale:" << scale);
+
     // The newCenter has been computed in the new scale, but _zoomToCenter expected the center to be in the original scale.
     newCenter.scale(1 / scale, 1 / scale);
     [_scrollView _zoomToCenter:newCenter
@@ -4527,6 +4536,16 @@
     [_contentView selectFormAccessoryPickerRow:rowIndex];
 }
 
+- (void)didStartFormControlInteraction
+{
+    // For subclasses to override.
+}
+
+- (void)didEndFormControlInteraction
+{
+    // For subclasses to override.
+}
+
 #endif // PLATFORM(IOS)
 
 #if PLATFORM(MAC)

Modified: trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebViewPrivate.h (204727 => 204728)


--- trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebViewPrivate.h	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebViewPrivate.h	2016-08-22 18:02:03 UTC (rev 204728)
@@ -264,6 +264,9 @@
 - (void)dismissFormAccessoryView WK_API_AVAILABLE(ios(WK_IOS_TBA));
 - (void)selectFormAccessoryPickerRow:(int)rowIndex WK_API_AVAILABLE(ios(WK_IOS_TBA));
 
+- (void)didStartFormControlInteraction WK_API_AVAILABLE(ios(WK_IOS_TBA));
+- (void)didEndFormControlInteraction WK_API_AVAILABLE(ios(WK_IOS_TBA));
+
 #endif
 
 #if !TARGET_OS_IPHONE

Modified: trunk/Source/WebKit2/UIProcess/ios/WKContentView.mm (204727 => 204728)


--- trunk/Source/WebKit2/UIProcess/ios/WKContentView.mm	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Source/WebKit2/UIProcess/ios/WKContentView.mm	2016-08-22 18:02:03 UTC (rev 204728)
@@ -31,6 +31,7 @@
 #import "APIPageConfiguration.h"
 #import "AccessibilityIOS.h"
 #import "ApplicationStateTracker.h"
+#import "Logging.h"
 #import "PageClientImplIOS.h"
 #import "PrintInfo.h"
 #import "RemoteLayerTreeDrawingAreaProxy.h"
@@ -58,6 +59,7 @@
 #import <WebCore/NotImplemented.h>
 #import <WebCore/PlatformScreen.h>
 #import <WebCore/QuartzCoreSPI.h>
+#import <WebCore/TextStream.h>
 #import <wtf/CurrentTime.h>
 #import <wtf/RetainPtr.h>
 
@@ -377,6 +379,8 @@
 
     FloatRect fixedPositionRectForLayout = _page->computeCustomFixedPositionRect(unobscuredRect, zoomScale, WebPageProxy::UnobscuredRectConstraint::ConstrainedToDocumentRect);
 
+    LOG_WITH_STREAM(VisibleRects, stream << "didUpdateVisibleRect: visibleRect:" << visibleRect << " unobscuredRect:" << unobscuredRect << " fixedPositionRectForLayout:" << fixedPositionRectForLayout);
+
     VisibleContentRectUpdateInfo visibleContentRectUpdateInfo(
         visibleRect,
         unobscuredRect,

Modified: trunk/Source/WebKit2/UIProcess/ios/WKContentViewInteraction.mm (204727 => 204728)


--- trunk/Source/WebKit2/UIProcess/ios/WKContentViewInteraction.mm	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Source/WebKit2/UIProcess/ios/WKContentViewInteraction.mm	2016-08-22 18:02:03 UTC (rev 204728)
@@ -748,6 +748,15 @@
     return _isEditable;
 }
 
+- (BOOL)setIsEditable:(BOOL)isEditable
+{
+    if (isEditable == _isEditable)
+        return NO;
+
+    _isEditable = isEditable;
+    return YES;
+}
+
 - (BOOL)canBecomeFirstResponder
 {
     if (_resigningFirstResponder)
@@ -3579,7 +3588,7 @@
     if (_assistedNodeInformation.elementType == information.elementType && _assistedNodeInformation.elementRect == information.elementRect)
         return;
 
-    _isEditable = YES;
+    BOOL editableChanged = [self setIsEditable:YES];
     _assistedNodeInformation = information;
     _inputPeripheral = nil;
     _traits = nil;
@@ -3600,7 +3609,8 @@
         break;
     }
     
-    if (information.insideFixedPosition)
+    // The custom fixed position rect behavior is affected by -isAssistingNode, so if that changes we need to recompute rects.
+    if (editableChanged)
         [_webView _updateVisibleContentRects];
     
     [self _displayFormNodeInputView];
@@ -3612,6 +3622,8 @@
         _formInputSession = adoptNS([[WKFormInputSession alloc] initWithContentView:self focusedElementInfo:focusedElementInfo.get() userObject:userObject]);
         [inputDelegate _webView:_webView didStartInputSession:_formInputSession.get()];
     }
+    
+    [_webView didStartFormControlInteraction];
 }
 
 - (void)_stopAssistingNode
@@ -3618,7 +3630,9 @@
 {
     [_formInputSession invalidate];
     _formInputSession = nil;
-    _isEditable = NO;
+
+    BOOL editableChanged = [self setIsEditable:NO];
+
     _assistedNodeInformation.elementType = InputType::None;
     _inputPeripheral = nil;
 
@@ -3628,6 +3642,12 @@
     [self _updateAccessory];
     // The name is misleading, but this actually clears the selection views and removes any selection.
     [_webSelectionAssistant resignedFirstResponder];
+
+    // The custom fixed position rect behavior is affected by -isAssistingNode, so if that changes we need to recompute rects.
+    if (editableChanged)
+        [_webView _updateVisibleContentRects];
+
+    [_webView didEndFormControlInteraction];
 }
 
 - (void)_selectionChanged

Modified: trunk/Tools/ChangeLog (204727 => 204728)


--- trunk/Tools/ChangeLog	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/ChangeLog	2016-08-22 18:02:03 UTC (rev 204728)
@@ -1,3 +1,43 @@
+2016-08-22  Simon Fraser  <[email protected]>
+
+        <select> menu on iPad causes shifting of hit-testing areas
+        https://bugs.webkit.org/show_bug.cgi?id=150079
+
+        Reviewed by Tim Horton.
+
+        -isAssistingNode (aka the poorly named isEditable) is input into WebPageProxy::computeCustomFixedPositionRect(),
+        so when it changes we have to update visible rects. We were doing this on focus, but failing
+        to do it on blur.
+
+        Added the ability to test by:
+        1. Making it possible to initiate an animated scroll in the UI process
+        2. Adding callbacks for starting and ending interaction with a form control. Sadly
+        the "ending interaction" for <select> popovers on iPad isn't late enough, since we
+        have no way currently to know when the dimming view behind the popover animates out,
+        so for now the test keeps trying to tap a button.
+
+        * WebKitTestRunner/UIScriptContext/Bindings/UIScriptController.idl:
+        * WebKitTestRunner/UIScriptContext/UIScriptContext.h:
+        * WebKitTestRunner/UIScriptContext/UIScriptController.cpp:
+        (WTR::UIScriptController::setDidStartFormControlInteractionCallback):
+        (WTR::UIScriptController::didStartFormControlInteractionCallback):
+        (WTR::UIScriptController::setDidEndFormControlInteractionCallback):
+        (WTR::UIScriptController::didEndFormControlInteractionCallback):
+        (WTR::UIScriptController::scrollToOffset):
+        (WTR::UIScriptController::platformSetDidStartFormControlInteractionCallback):
+        (WTR::UIScriptController::platformSetDidEndFormControlInteractionCallback):
+        * WebKitTestRunner/UIScriptContext/UIScriptController.h:
+        * WebKitTestRunner/cocoa/TestRunnerWKWebView.h:
+        * WebKitTestRunner/cocoa/TestRunnerWKWebView.mm:
+        (-[TestRunnerWKWebView dealloc]):
+        (-[TestRunnerWKWebView didStartFormControlInteraction]):
+        (-[TestRunnerWKWebView didEndFormControlInteraction]):
+        * WebKitTestRunner/ios/UIScriptControllerIOS.mm:
+        (WTR::contentOffsetBoundedInValidRange):
+        (WTR::UIScriptController::scrollToOffset):
+        (WTR::UIScriptController::platformSetDidStartFormControlInteractionCallback):
+        (WTR::UIScriptController::platformSetDidEndFormControlInteractionCallback):
+
 2016-08-22  Carlos Alberto Lopez Perez  <[email protected]>
 
         [EFL][GTK] Script process-linux-coredump is not needed, switch back to use the kernel core dumper instead.

Modified: trunk/Tools/WebKitTestRunner/UIScriptContext/Bindings/UIScriptController.idl (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/UIScriptContext/Bindings/UIScriptController.idl	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/UIScriptContext/Bindings/UIScriptController.idl	2016-08-22 18:02:03 UTC (rev 204728)
@@ -45,6 +45,10 @@
     // Equivalent of pressing the Done button in the form accessory bar.
     void dismissFormAccessoryView();
 
+    // Form control handling
+    attribute object didStartFormControlInteractionCallback;
+    attribute object didEndFormControlInteractionCallback;
+
     // <select> picker
     void selectFormAccessoryPickerRow(long rowIndex);
 
@@ -58,6 +62,7 @@
     attribute object willBeginZoomingCallback;
     attribute object didEndZoomingCallback;
 
+    void scrollToOffset(long x, long y); // Initiate an animated scroll in the UI process.
     attribute object didEndScrollingCallback;
 
     // View state

Modified: trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptContext.h (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptContext.h	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptContext.h	2016-08-22 18:02:03 UTC (rev 204728)
@@ -47,6 +47,8 @@
     CallbackTypeDidShowKeyboard,
     CallbackTypeDidHideKeyboard,
     CallbackTypeDidEndScrolling,
+    CallbackTypeDidStartFormControlInteraction,
+    CallbackTypeDidEndFormControlInteraction,
     CallbackTypeNonPersistent = firstNonPersistentCallbackID
 } CallbackType;
 

Modified: trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.cpp (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.cpp	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.cpp	2016-08-22 18:02:03 UTC (rev 204728)
@@ -58,6 +58,28 @@
 }
 #endif
 
+void UIScriptController::setDidStartFormControlInteractionCallback(JSValueRef callback)
+{
+    m_context->registerCallback(callback, CallbackTypeDidStartFormControlInteraction);
+    platformSetDidStartFormControlInteractionCallback();
+}
+
+JSValueRef UIScriptController::didStartFormControlInteractionCallback() const
+{
+    return m_context->callbackWithID(CallbackTypeDidStartFormControlInteraction);
+}
+
+void UIScriptController::setDidEndFormControlInteractionCallback(JSValueRef callback)
+{
+    m_context->registerCallback(callback, CallbackTypeDidEndFormControlInteraction);
+    platformSetDidEndFormControlInteractionCallback();
+}
+
+JSValueRef UIScriptController::didEndFormControlInteractionCallback() const
+{
+    return m_context->callbackWithID(CallbackTypeDidEndFormControlInteraction);
+}
+
 void UIScriptController::setWillBeginZoomingCallback(JSValueRef callback)
 {
     m_context->registerCallback(callback, CallbackTypeWillBeginZooming);
@@ -158,6 +180,10 @@
 {
 }
 
+void UIScriptController::scrollToOffset(long x, long y)
+{
+}
+
 void UIScriptController::keyboardAccessoryBarNext()
 {
 }
@@ -186,6 +212,14 @@
     return nullptr;
 }
 
+void UIScriptController::platformSetDidStartFormControlInteractionCallback()
+{
+}
+
+void UIScriptController::platformSetDidEndFormControlInteractionCallback()
+{
+}
+
 void UIScriptController::platformSetWillBeginZoomingCallback()
 {
 }

Modified: trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.h (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.h	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/UIScriptContext/UIScriptController.h	2016-08-22 18:02:03 UTC (rev 204728)
@@ -62,7 +62,15 @@
     
     void dismissFormAccessoryView();
     void selectFormAccessoryPickerRow(long);
+    
+    void scrollToOffset(long x, long y);
 
+    void setDidStartFormControlInteractionCallback(JSValueRef);
+    JSValueRef didStartFormControlInteractionCallback() const;
+
+    void setDidEndFormControlInteractionCallback(JSValueRef);
+    JSValueRef didEndFormControlInteractionCallback() const;
+
     void setWillBeginZoomingCallback(JSValueRef);
     JSValueRef willBeginZoomingCallback() const;
 
@@ -88,7 +96,9 @@
 
 private:
     UIScriptController(UIScriptContext&);
-    
+
+    void platformSetDidStartFormControlInteractionCallback();
+    void platformSetDidEndFormControlInteractionCallback();
     void platformSetWillBeginZoomingCallback();
     void platformSetDidEndZoomingCallback();
     void platformSetDidShowKeyboardCallback();

Modified: trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h	2016-08-22 18:02:03 UTC (rev 204728)
@@ -31,6 +31,8 @@
 
 #if PLATFORM(IOS)
 
+@property (nonatomic, copy) void (^didStartFormControlInteractionCallback)(void);
+@property (nonatomic, copy) void (^didEndFormControlInteractionCallback)(void);
 @property (nonatomic, copy) void (^willBeginZoomingCallback)(void);
 @property (nonatomic, copy) void (^didEndZoomingCallback)(void);
 @property (nonatomic, copy) void (^didShowKeyboardCallback)(void);

Modified: trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm	2016-08-22 18:02:03 UTC (rev 204728)
@@ -73,6 +73,8 @@
 {
     [[NSNotificationCenter defaultCenter] removeObserver:self];
 
+    self.didStartFormControlInteractionCallback = nil;
+    self.didEndFormControlInteractionCallback = nil;
     self.willBeginZoomingCallback = nil;
     self.didEndZoomingCallback = nil;
     self.didShowKeyboardCallback = nil;
@@ -85,6 +87,18 @@
     [super dealloc];
 }
 
+- (void)didStartFormControlInteraction
+{
+    if (self.didStartFormControlInteractionCallback)
+        self.didStartFormControlInteractionCallback();
+}
+
+- (void)didEndFormControlInteraction
+{
+    if (self.didEndFormControlInteractionCallback)
+        self.didEndFormControlInteractionCallback();
+}
+
 - (void)zoomToScale:(double)scale animated:(BOOL)animated completionHandler:(void (^)(void))completionHandler
 {
     ASSERT(!self.zoomToScaleCompletionHandler);

Modified: trunk/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm (204727 => 204728)


--- trunk/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm	2016-08-22 17:26:22 UTC (rev 204727)
+++ trunk/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm	2016-08-22 18:02:03 UTC (rev 204728)
@@ -187,6 +187,28 @@
     [webView selectFormAccessoryPickerRow:rowIndex];
 }
 
+static CGPoint contentOffsetBoundedInValidRange(UIScrollView *scrollView, CGPoint contentOffset)
+{
+    UIEdgeInsets contentInsets = scrollView.contentInset;
+    CGSize contentSize = scrollView.contentSize;
+    CGSize scrollViewSize = scrollView.bounds.size;
+
+    CGFloat maxHorizontalOffset = contentSize.width + contentInsets.right - scrollViewSize.width;
+    contentOffset.x = std::min(maxHorizontalOffset, contentOffset.x);
+    contentOffset.x = std::max(-contentInsets.left, contentOffset.x);
+
+    CGFloat maxVerticalOffset = contentSize.height + contentInsets.bottom - scrollViewSize.height;
+    contentOffset.y = std::min(maxVerticalOffset, contentOffset.y);
+    contentOffset.y = std::max(-contentInsets.top, contentOffset.y);
+    return contentOffset;
+}
+
+void UIScriptController::scrollToOffset(long x, long y)
+{
+    TestRunnerWKWebView *webView = TestController::singleton().mainWebView()->platformView();
+    [webView.scrollView setContentOffset:contentOffsetBoundedInValidRange(webView.scrollView, CGPointMake(x, y)) animated:YES];
+}
+
 void UIScriptController::keyboardAccessoryBarNext()
 {
     TestRunnerWKWebView *webView = TestController::singleton().mainWebView()->platformView();
@@ -221,6 +243,26 @@
     return m_context->objectFromRect(wkRect);
 }
 
+void UIScriptController::platformSetDidStartFormControlInteractionCallback()
+{
+    TestRunnerWKWebView *webView = TestController::singleton().mainWebView()->platformView();
+    webView.didStartFormControlInteractionCallback = ^{
+        if (!m_context)
+            return;
+        m_context->fireCallback(CallbackTypeDidStartFormControlInteraction);
+    };
+}
+
+void UIScriptController::platformSetDidEndFormControlInteractionCallback()
+{
+    TestRunnerWKWebView *webView = TestController::singleton().mainWebView()->platformView();
+    webView.didEndFormControlInteractionCallback = ^{
+        if (!m_context)
+            return;
+        m_context->fireCallback(CallbackTypeDidEndFormControlInteraction);
+    };
+}
+
 void UIScriptController::platformSetWillBeginZoomingCallback()
 {
     TestRunnerWKWebView *webView = TestController::singleton().mainWebView()->platformView();
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to