| Differences between
and this patch
- a/Source/WebKit/ChangeLog +25 lines
Lines 1-3 a/Source/WebKit/ChangeLog_sec1
1
2019-03-28  Daniel Bates  <dabates@apple.com>
2
3
        [iPad] Should open popover when the spacebar is pressed
4
        https://bugs.webkit.org/show_bug.cgi?id=196360
5
        <rdar://problem/49389129>
6
7
        Reviewed by NOBODY (OOPS!).
8
9
        Pressing the spacebar should open the popover for a focused popup button (e.g. <select>) on iOS
10
        just like it does on the Mac.
11
12
        For now, we keep the iPhone behavior of blurring the element when the Done button is pressed and
13
        hence pressing spacebar does nothing (because there is no focused element).
14
15
        * UIProcess/ios/WKContentViewInteraction.h:
16
        * UIProcess/ios/WKContentViewInteraction.mm:
17
        (-[WKContentView accessoryOpen]): Added. Extracted the logic from -_elementDidFocus to scroll to
18
        the focused element, update the accessory and then tell the accessory to begin editing.
19
        (-[WKContentView _elementDidFocus:userIsInteracting:blurPreviousNode:changingActivityState:userObject:]):
20
        Write in terms of -accessoryOpen.
21
        * UIProcess/ios/forms/WKFormPeripheralBase.mm:
22
        (-[WKFormPeripheralBase handleKeyEvent:]): Interpret the spacebar when the peripheral is closed (!_editing)
23
        and call -accessoryOpen to ultimately call back to this peripheral to tell it to begin editing,
24
        which will cause the popover to appear again.
25
1
2019-03-28  Daniel Bates  <dabates@apple.com>
26
2019-03-28  Daniel Bates  <dabates@apple.com>
2
27
3
        [iOS] Should be able to dismiss picker or popover using the keyboard
28
        [iOS] Should be able to dismiss picker or popover using the keyboard
- a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.h -1 / +5 lines
Lines 428-434 FOR_EACH_PRIVATE_WKCONTENTVIEW_ACTION(DECLARE_WKCONTENTVIEW_ACTION_FOR_WEB_VIEW) a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.h_sec1
428
- (void)_showPlaybackTargetPicker:(BOOL)hasVideo fromRect:(const WebCore::IntRect&)elementRect routeSharingPolicy:(WebCore::RouteSharingPolicy)policy routingContextUID:(NSString *)contextUID;
428
- (void)_showPlaybackTargetPicker:(BOOL)hasVideo fromRect:(const WebCore::IntRect&)elementRect routeSharingPolicy:(WebCore::RouteSharingPolicy)policy routingContextUID:(NSString *)contextUID;
429
- (void)_showRunOpenPanel:(API::OpenPanelParameters*)parameters resultListener:(WebKit::WebOpenPanelResultListenerProxy*)listener;
429
- (void)_showRunOpenPanel:(API::OpenPanelParameters*)parameters resultListener:(WebKit::WebOpenPanelResultListenerProxy*)listener;
430
- (void)_showShareSheet:(const WebCore::ShareDataWithParsedURL&)shareData completionHandler:(WTF::CompletionHandler<void(bool)>&&)completionHandler;
430
- (void)_showShareSheet:(const WebCore::ShareDataWithParsedURL&)shareData completionHandler:(WTF::CompletionHandler<void(bool)>&&)completionHandler;
431
- (void)accessoryDone;
432
- (void)dismissFilePicker;
431
- (void)dismissFilePicker;
433
- (void)_didHandleKeyEvent:(::WebEvent *)event eventWasHandled:(BOOL)eventWasHandled;
432
- (void)_didHandleKeyEvent:(::WebEvent *)event eventWasHandled:(BOOL)eventWasHandled;
434
- (Vector<WebKit::OptionItem>&) focusedSelectElementOptions;
433
- (Vector<WebKit::OptionItem>&) focusedSelectElementOptions;
Lines 448-453 FOR_EACH_PRIVATE_WKCONTENTVIEW_ACTION(DECLARE_WKCONTENTVIEW_ACTION_FOR_WEB_VIEW) a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.h_sec2
448
- (void)_accessibilityClearSelection;
447
- (void)_accessibilityClearSelection;
449
- (WKFormInputSession *)_formInputSession;
448
- (WKFormInputSession *)_formInputSession;
450
449
450
// UIWebFormAccessoryDelegate protocol
451
- (void)accessoryDone;
452
453
- (void)accessoryOpen;
454
451
- (void)_requestDOMPasteAccessWithElementRect:(const WebCore::IntRect&)elementRect originIdentifier:(const String&)originIdentifier completionHandler:(CompletionHandler<void(WebCore::DOMPasteAccessResponse)>&&)completionHandler;
455
- (void)_requestDOMPasteAccessWithElementRect:(const WebCore::IntRect&)elementRect originIdentifier:(const String&)originIdentifier completionHandler:(CompletionHandler<void(WebCore::DOMPasteAccessResponse)>&&)completionHandler;
452
456
453
@property (nonatomic, readonly) WebKit::InteractionInformationAtPosition currentPositionInformation;
457
@property (nonatomic, readonly) WebKit::InteractionInformationAtPosition currentPositionInformation;
- a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.mm -3 / +10 lines
Lines 3800-3805 - (UIWebFormAccessory *)formAccessoryView a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.mm_sec1
3800
    return _formAccessoryView.get();
3800
    return _formAccessoryView.get();
3801
}
3801
}
3802
3802
3803
- (void)accessoryOpen
3804
{
3805
    if (!_inputPeripheral)
3806
        return;
3807
    [self _zoomToRevealFocusedElement];
3808
    [self _updateAccessory];
3809
    [_inputPeripheral beginEditing];
3810
}
3811
3803
- (void)_updateAccessory
3812
- (void)_updateAccessory
3804
{
3813
{
3805
    auto* accessoryView = self.formAccessoryView; // Creates one, if needed.
3814
    auto* accessoryView = self.formAccessoryView; // Creates one, if needed.
Lines 4983-4991 - (void)_elementDidFocus:(const WebKit::FocusedElementInformation&)information u a/Source/WebKit/UIProcess/ios/WKContentViewInteraction.mm_sec2
4983
        if (_inputPeripheral) {
4992
        if (_inputPeripheral) {
4984
            if (!self.isFirstResponder)
4993
            if (!self.isFirstResponder)
4985
                [self becomeFirstResponder];
4994
                [self becomeFirstResponder];
4986
            [self _zoomToRevealFocusedElement];
4995
            [self accessoryOpen];
4987
            [self _updateAccessory];
4988
            [_inputPeripheral beginEditing];
4989
        }
4996
        }
4990
        return;
4997
        return;
4991
    }
4998
    }
- a/Source/WebKit/UIProcess/ios/forms/WKFormPeripheralBase.mm +4 lines
Lines 84-89 - (BOOL)handleKeyEvent:(UIEvent *)event a/Source/WebKit/UIProcess/ios/forms/WKFormPeripheralBase.mm_sec1
84
        [_view accessoryDone];
84
        [_view accessoryDone];
85
        return YES;
85
        return YES;
86
    }
86
    }
87
    if (!_editing && keyEvent._keyCode == kHIDUsage_KeyboardSpacebar) {
88
        [_view accessoryOpen];
89
        return YES;
90
    }
87
    return NO;
91
    return NO;
88
}
92
}
89
93
- a/Tools/ChangeLog +36 lines
Lines 1-3 a/Tools/ChangeLog_sec1
1
2019-03-28  Daniel Bates  <dabates@apple.com>
2
3
        [iPad] Should open popover when the spacebar is pressed
4
        https://bugs.webkit.org/show_bug.cgi?id=196360
5
        <rdar://problem/49389129>
6
7
        Reviewed by NOBODY (OOPS!).
8
9
        Add testing infrastructure to support waiting for a popover to be presented or dismissed.
10
11
        * DumpRenderTree/ios/UIScriptControllerIOS.mm:
12
        (WTR::UIScriptController::isShowingPopover const): Added.
13
        (WTR::UIScriptController::platformSetWillPresentPopoverCallback): Added.
14
        (WTR::UIScriptController::platformSetDidDismissPopoverCallback): Added.
15
        * TestRunnerShared/UIScriptContext/Bindings/UIScriptController.idl:
16
        * TestRunnerShared/UIScriptContext/UIScriptContext.h:
17
        * TestRunnerShared/UIScriptContext/UIScriptController.cpp:
18
        (WTR::UIScriptController::setWillPresentPopoverCallback): Added.
19
        (WTR::UIScriptController::willPresentPopoverCallback const): Added.
20
        (WTR::UIScriptController::setDidDismissPopoverCallback): Added.
21
        (WTR::UIScriptController::didDismissPopoverCallback const): Added.
22
        (WTR::UIScriptController::isShowingPopover const): Added.
23
        (WTR::UIScriptController::platformSetWillPresentPopoverCallback): Added.
24
        (WTR::UIScriptController::platformSetDidDismissPopoverCallback): Added.
25
        * TestRunnerShared/UIScriptContext/UIScriptController.h:
26
        * WebKitTestRunner/cocoa/TestRunnerWKWebView.h:
27
        * WebKitTestRunner/cocoa/TestRunnerWKWebView.mm:
28
        (-[TestRunnerWKWebView initWithFrame:configuration:]): Update some state.
29
        (-[TestRunnerWKWebView resetInteractionCallbacks]): Ditto.
30
        (-[TestRunnerWKWebView _willPresentPopover]): Added.
31
        (-[TestRunnerWKWebView _didDismissPopover]): Added.
32
        * WebKitTestRunner/ios/UIScriptControllerIOS.mm:
33
        (WTR::UIScriptController::isShowingPopover const): Added.
34
        (WTR::UIScriptController::platformSetWillPresentPopoverCallback): Added.
35
        (WTR::UIScriptController::platformSetDidDismissPopoverCallback): Added.
36
1
2019-03-28  Michael Catanzaro  <mcatanzaro@igalia.com>
37
2019-03-28  Michael Catanzaro  <mcatanzaro@igalia.com>
2
38
3
        [WPE][GTK] webkit_web_resource_get_data_finish can return NULL without setting error
39
        [WPE][GTK] webkit_web_resource_get_data_finish can return NULL without setting error
- a/Tools/DumpRenderTree/ios/UIScriptControllerIOS.mm +13 lines
Lines 353-358 void UIScriptController::platformSetDidHideMenuCallback() a/Tools/DumpRenderTree/ios/UIScriptControllerIOS.mm_sec1
353
{
353
{
354
}
354
}
355
355
356
bool UIScriptController::isShowingPopover() const
357
{
358
    return false;
359
}
360
361
void UIScriptController::platformSetWillPresentPopoverCallback()
362
{
363
}
364
365
void UIScriptController::platformSetDidDismissPopoverCallback()
366
{
367
}
368
356
JSObjectRef UIScriptController::rectForMenuAction(JSStringRef) const
369
JSObjectRef UIScriptController::rectForMenuAction(JSStringRef) const
357
{
370
{
358
    return nullptr;
371
    return nullptr;
- a/Tools/TestRunnerShared/UIScriptContext/Bindings/UIScriptController.idl +4 lines
Lines 231-236 interface UIScriptController { a/Tools/TestRunnerShared/UIScriptContext/Bindings/UIScriptController.idl_sec1
231
    readonly attribute object menuRect;
231
    readonly attribute object menuRect;
232
    object rectForMenuAction(DOMString action);
232
    object rectForMenuAction(DOMString action);
233
233
234
    readonly attribute boolean isShowingPopover;
235
    attribute object willPresentPopoverCallback;
236
    attribute object didDismissPopoverCallback;
237
234
    attribute object willBeginZoomingCallback;
238
    attribute object willBeginZoomingCallback;
235
    attribute object didEndZoomingCallback;
239
    attribute object didEndZoomingCallback;
236
240
- a/Tools/TestRunnerShared/UIScriptContext/UIScriptContext.h +2 lines
Lines 56-61 typedef enum { a/Tools/TestRunnerShared/UIScriptContext/UIScriptContext.h_sec1
56
    CallbackTypeDidHideKeyboard,
56
    CallbackTypeDidHideKeyboard,
57
    CallbackTypeDidShowMenu,
57
    CallbackTypeDidShowMenu,
58
    CallbackTypeDidHideMenu,
58
    CallbackTypeDidHideMenu,
59
    CallbackTypeWillPresentPopover,
60
    CallbackTypeDidDismissPopover,
59
    CallbackTypeDidEndScrolling,
61
    CallbackTypeDidEndScrolling,
60
    CallbackTypeDidStartFormControlInteraction,
62
    CallbackTypeDidStartFormControlInteraction,
61
    CallbackTypeDidEndFormControlInteraction,
63
    CallbackTypeDidEndFormControlInteraction,
- a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.cpp +35 lines
Lines 227-232 JSValueRef UIScriptController::didHideMenuCallback() const a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.cpp_sec1
227
    return m_context->callbackWithID(CallbackTypeDidHideMenu);
227
    return m_context->callbackWithID(CallbackTypeDidHideMenu);
228
}
228
}
229
229
230
void UIScriptController::setWillPresentPopoverCallback(JSValueRef callback)
231
{
232
    m_context->registerCallback(callback, CallbackTypeWillPresentPopover);
233
    platformSetWillPresentPopoverCallback();
234
}
235
236
JSValueRef UIScriptController::willPresentPopoverCallback() const
237
{
238
    return m_context->callbackWithID(CallbackTypeWillPresentPopover);
239
}
240
241
void UIScriptController::setDidDismissPopoverCallback(JSValueRef callback)
242
{
243
    m_context->registerCallback(callback, CallbackTypeDidDismissPopover);
244
    platformSetDidDismissPopoverCallback();
245
}
246
247
JSValueRef UIScriptController::didDismissPopoverCallback() const
248
{
249
    return m_context->callbackWithID(CallbackTypeDidDismissPopover);
250
}
251
230
#if !PLATFORM(COCOA)
252
#if !PLATFORM(COCOA)
231
253
232
void UIScriptController::zoomToScale(double, JSValueRef)
254
void UIScriptController::zoomToScale(double, JSValueRef)
Lines 553-558 void UIScriptController::platformSetDidHideMenuCallback() a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.cpp_sec2
553
{
575
{
554
}
576
}
555
577
578
bool UIScriptController::isShowingPopover() const
579
{
580
    return false;
581
}
582
583
void UIScriptController::platformSetWillPresentPopoverCallback()
584
{
585
}
586
587
void UIScriptController::platformSetDidDismissPopoverCallback()
588
{
589
}
590
556
JSObjectRef UIScriptController::menuRect() const
591
JSObjectRef UIScriptController::menuRect() const
557
{
592
{
558
    return nullptr;
593
    return nullptr;
- a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.h -1 / +8 lines
Lines 166-175 public: a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.h_sec1
166
166
167
    void setDidHideMenuCallback(JSValueRef);
167
    void setDidHideMenuCallback(JSValueRef);
168
    JSValueRef didHideMenuCallback() const;
168
    JSValueRef didHideMenuCallback() const;
169
170
    void setDidShowMenuCallback(JSValueRef);
169
    void setDidShowMenuCallback(JSValueRef);
171
    JSValueRef didShowMenuCallback() const;
170
    JSValueRef didShowMenuCallback() const;
172
171
172
    bool isShowingPopover() const;
173
    void setDidDismissPopoverCallback(JSValueRef);
174
    JSValueRef didDismissPopoverCallback() const;
175
    void setWillPresentPopoverCallback(JSValueRef);
176
    JSValueRef willPresentPopoverCallback() const;
177
173
    bool isShowingMenu() const;
178
    bool isShowingMenu() const;
174
    JSObjectRef rectForMenuAction(JSStringRef action) const;
179
    JSObjectRef rectForMenuAction(JSStringRef action) const;
175
    JSObjectRef menuRect() const;
180
    JSObjectRef menuRect() const;
Lines 250-255 private: a/Tools/TestRunnerShared/UIScriptContext/UIScriptController.h_sec2
250
    void platformSetDidHideKeyboardCallback();
255
    void platformSetDidHideKeyboardCallback();
251
    void platformSetDidShowMenuCallback();
256
    void platformSetDidShowMenuCallback();
252
    void platformSetDidHideMenuCallback();
257
    void platformSetDidHideMenuCallback();
258
    void platformSetWillPresentPopoverCallback();
259
    void platformSetDidDismissPopoverCallback();
253
    void platformSetDidEndScrollingCallback();
260
    void platformSetDidEndScrollingCallback();
254
    void platformClearAllCallbacks();
261
    void platformClearAllCallbacks();
255
    void platformPlayBackEventStream(JSStringRef, JSValueRef);
262
    void platformPlayBackEventStream(JSStringRef, JSValueRef);
- a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h +3 lines
Lines 43-48 a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h_sec1
43
@property (nonatomic, copy) void (^didHideKeyboardCallback)(void);
43
@property (nonatomic, copy) void (^didHideKeyboardCallback)(void);
44
@property (nonatomic, copy) void (^didShowMenuCallback)(void);
44
@property (nonatomic, copy) void (^didShowMenuCallback)(void);
45
@property (nonatomic, copy) void (^didHideMenuCallback)(void);
45
@property (nonatomic, copy) void (^didHideMenuCallback)(void);
46
@property (nonatomic, copy) void (^willPresentPopoverCallback)(void);
47
@property (nonatomic, copy) void (^didDismissPopoverCallback)(void);
46
@property (nonatomic, copy) void (^didEndScrollingCallback)(void);
48
@property (nonatomic, copy) void (^didEndScrollingCallback)(void);
47
@property (nonatomic, copy) void (^rotationDidEndCallback)(void);
49
@property (nonatomic, copy) void (^rotationDidEndCallback)(void);
48
@property (nonatomic, copy) NSString *accessibilitySpeakSelectionContent;
50
@property (nonatomic, copy) NSString *accessibilitySpeakSelectionContent;
Lines 56-61 a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.h_sec2
56
58
57
@property (nonatomic, readonly, getter=isShowingKeyboard) BOOL showingKeyboard;
59
@property (nonatomic, readonly, getter=isShowingKeyboard) BOOL showingKeyboard;
58
@property (nonatomic, readonly, getter=isShowingMenu) BOOL showingMenu;
60
@property (nonatomic, readonly, getter=isShowingMenu) BOOL showingMenu;
61
@property (nonatomic, readonly, getter=isShowingPopover) BOOL showingPopover;
59
@property (nonatomic, assign) BOOL usesSafariLikeRotation;
62
@property (nonatomic, assign) BOOL usesSafariLikeRotation;
60
@property (nonatomic, readonly, getter=isInteractingWithFormControl) BOOL interactingWithFormControl;
63
@property (nonatomic, readonly, getter=isInteractingWithFormControl) BOOL interactingWithFormControl;
61
64
- a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm +25 lines
Lines 55-60 @property (nonatomic, copy) void (^zoomToScaleCompletionHandler)(void); a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm_sec1
55
@property (nonatomic, copy) void (^retrieveSpeakSelectionContentCompletionHandler)(void);
55
@property (nonatomic, copy) void (^retrieveSpeakSelectionContentCompletionHandler)(void);
56
@property (nonatomic, getter=isShowingKeyboard, setter=setIsShowingKeyboard:) BOOL showingKeyboard;
56
@property (nonatomic, getter=isShowingKeyboard, setter=setIsShowingKeyboard:) BOOL showingKeyboard;
57
@property (nonatomic, getter=isShowingMenu, setter=setIsShowingMenu:) BOOL showingMenu;
57
@property (nonatomic, getter=isShowingMenu, setter=setIsShowingMenu:) BOOL showingMenu;
58
@property (nonatomic, getter=isShowingPopover, setter=setIsShowingPopover:) BOOL showingPopover;
58
59
59
@end
60
@end
60
61
Lines 79-84 - (instancetype)initWithFrame:(CGRect)frame configuration:(WKWebViewConfiguratio a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm_sec2
79
        [center addObserver:self selector:@selector(_invokeHideKeyboardCallbackIfNecessary) name:UIKeyboardDidHideNotification object:nil];
80
        [center addObserver:self selector:@selector(_invokeHideKeyboardCallbackIfNecessary) name:UIKeyboardDidHideNotification object:nil];
80
        [center addObserver:self selector:@selector(_didShowMenu) name:UIMenuControllerDidShowMenuNotification object:nil];
81
        [center addObserver:self selector:@selector(_didShowMenu) name:UIMenuControllerDidShowMenuNotification object:nil];
81
        [center addObserver:self selector:@selector(_didHideMenu) name:UIMenuControllerDidHideMenuNotification object:nil];
82
        [center addObserver:self selector:@selector(_didHideMenu) name:UIMenuControllerDidHideMenuNotification object:nil];
83
        [center addObserver:self selector:@selector(_willPresentPopover) name:@"UIPopoverControllerWillPresentPopoverNotification" object:nil];
84
        [center addObserver:self selector:@selector(_didDismissPopover) name:@"UIPopoverControllerDidDismissPopoverNotification" object:nil];
82
        self.UIDelegate = self;
85
        self.UIDelegate = self;
83
    }
86
    }
84
    return self;
87
    return self;
Lines 141-146 - (void)resetInteractionCallbacks a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm_sec3
141
    self.didHideKeyboardCallback = nil;
144
    self.didHideKeyboardCallback = nil;
142
    self.didShowMenuCallback = nil;
145
    self.didShowMenuCallback = nil;
143
    self.didHideMenuCallback = nil;
146
    self.didHideMenuCallback = nil;
147
    self.willPresentPopoverCallback = nil;
148
    self.didDismissPopoverCallback = nil;
144
    self.didEndScrollingCallback = nil;
149
    self.didEndScrollingCallback = nil;
145
    self.rotationDidEndCallback = nil;
150
    self.rotationDidEndCallback = nil;
146
}
151
}
Lines 200-205 - (void)_didHideMenu a/Tools/WebKitTestRunner/cocoa/TestRunnerWKWebView.mm_sec4
200
        self.didHideMenuCallback();
205
        self.didHideMenuCallback();
201
}
206
}
202
207
208
- (void)_willPresentPopover
209
{
210
    if (self.showingPopover)
211
        return;
212
213
    self.showingPopover = YES;
214
    if (self.willPresentPopoverCallback)
215
        self.willPresentPopoverCallback();
216
}
217
218
- (void)_didDismissPopover
219
{
220
    if (!self.showingPopover)
221
        return;
222
223
    self.showingPopover = NO;
224
    if (self.didDismissPopoverCallback)
225
        self.didDismissPopoverCallback();
226
}
227
203
- (void)scrollViewWillBeginZooming:(UIScrollView *)scrollView withView:(UIView *)view
228
- (void)scrollViewWillBeginZooming:(UIScrollView *)scrollView withView:(UIView *)view
204
{
229
{
205
    [super scrollViewWillBeginZooming:scrollView withView:view];
230
    [super scrollViewWillBeginZooming:scrollView withView:view];
- a/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm +25 lines
Lines 907-912 void UIScriptController::platformSetDidHideMenuCallback() a/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm_sec1
907
    };
907
    };
908
}
908
}
909
909
910
bool UIScriptController::isShowingPopover() const
911
{
912
    return TestController::singleton().mainWebView()->platformView().showingPopover;
913
}
914
915
void UIScriptController::platformSetWillPresentPopoverCallback()
916
{
917
    TestController::singleton().mainWebView()->platformView().willPresentPopoverCallback = ^{
918
        if (!m_context)
919
            return;
920
        m_context->fireCallback(CallbackTypeWillPresentPopover);
921
    };
922
}
923
924
void UIScriptController::platformSetDidDismissPopoverCallback()
925
{
926
    TestController::singleton().mainWebView()->platformView().didDismissPopoverCallback = ^{
927
        if (!m_context)
928
            return;
929
        m_context->fireCallback(CallbackTypeDidDismissPopover);
930
    };
931
}
932
910
JSObjectRef UIScriptController::rectForMenuAction(JSStringRef jsAction) const
933
JSObjectRef UIScriptController::rectForMenuAction(JSStringRef jsAction) const
911
{
934
{
912
    auto action = adoptCF(JSStringCopyCFString(kCFAllocatorDefault, jsAction));
935
    auto action = adoptCF(JSStringCopyCFString(kCFAllocatorDefault, jsAction));
Lines 974-979 void UIScriptController::platformClearAllCallbacks() a/Tools/WebKitTestRunner/ios/UIScriptControllerIOS.mm_sec2
974
    webView.willBeginZoomingCallback = nil;
997
    webView.willBeginZoomingCallback = nil;
975
    webView.didHideKeyboardCallback = nil;
998
    webView.didHideKeyboardCallback = nil;
976
    webView.didShowKeyboardCallback = nil;
999
    webView.didShowKeyboardCallback = nil;
1000
    webView.willPresentPopoverCallback = nil;
1001
    webView.didDismissPopoverCallback = nil;
977
    webView.didEndScrollingCallback = nil;
1002
    webView.didEndScrollingCallback = nil;
978
    webView.rotationDidEndCallback = nil;
1003
    webView.rotationDidEndCallback = nil;
979
}
1004
}
- a/LayoutTests/ChangeLog +19 lines
Lines 1-3 a/LayoutTests/ChangeLog_sec1
1
2019-03-28  Daniel Bates  <dabates@apple.com>
2
3
        [iPad] Should open popover when the spacebar is pressed
4
        https://bugs.webkit.org/show_bug.cgi?id=196360
5
        <rdar://problem/49389129>
6
7
        Reviewed by NOBODY (OOPS!).
8
9
        Add an iPad-specific test to ensure that pressing the spacebar opens the popover and scrolls
10
        the form control into view.
11
12
        * fast/forms/ios/ipad/open-picker-using-keyboard-expected.txt: Added.
13
        * fast/forms/ios/ipad/open-picker-using-keyboard.html: Added.
14
        * platform/ios/TestExpectations: Skip tests in fast/forms/ios/ipad. We will unskip for iPad below.
15
        * platform/ipad/TestExpectations: Mark tests in fast/forms/ios/ipad as PASS so we run them.
16
        * resources/ui-helper.js:
17
        (window.UIHelper.waitForPopoverToPresent):
18
        (window.UIHelper.waitForPopoverToDismiss):
19
1
2019-03-28  Daniel Bates  <dabates@apple.com>
20
2019-03-28  Daniel Bates  <dabates@apple.com>
2
21
3
        [iOS] Should be able to dismiss picker or popover using the keyboard
22
        [iOS] Should be able to dismiss picker or popover using the keyboard
- a/LayoutTests/fast/forms/ios/ipad/open-picker-using-keyboard-expected.txt +22 lines
Line 0 a/LayoutTests/fast/forms/ios/ipad/open-picker-using-keyboard-expected.txt_sec1
1
Tests that pressing the spacebar and Escape to open and close the popover work, do not cause a value change, and that we scroll the form control into view when the popover is opened.
2
3
On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
4
5
6
7
After tab focused:
8
PASS document.getElementById("test").value is "First"
9
10
After dismissing popover by pressing Escape:
11
PASS document.getElementById("test").value is "First"
12
13
After opening popover by pressing spacebar:
14
PASS document.getElementById("test").value is "First"
15
16
After scrolling the page and pressing spacebar:
17
PASS window.scrollY is non-zero.
18
PASS window.scrollY is 0
19
PASS successfullyParsed is true
20
21
TEST COMPLETE
22
- a/LayoutTests/fast/forms/ios/ipad/open-picker-using-keyboard.html +107 lines
Line 0 a/LayoutTests/fast/forms/ios/ipad/open-picker-using-keyboard.html_sec1
1
<!DOCTYPE html>
2
<html>
3
<head>
4
<meta name="viewport" content="width=800">
5
<script src="../../../../resources/js-test.js"></script>
6
<script src="../../../../resources/ui-helper.js"></script>
7
</head>
8
<body style="height: 4096px">
9
<!-- Place the test container above the console output to avoid the need to compensate for page scroll. -->
10
<div id="test-container">
11
    <p><select id="test">
12
        <option>First</option>
13
        <option>Second</option>
14
    </select></p>
15
</div>
16
<p id="description"></p>
17
<div id="console"></div>
18
<script>
19
window.jsTestIsAsync = true;
20
21
let expectedValue;
22
23
const modifierDisplayNameMap = {
24
    "altKey": "Option",
25
    "ctrlKey": "Control",
26
    "metaKey": "Command",
27
    "shiftKey": "Shift",
28
    "capsLockKey": "Caps Lock",
29
}
30
31
class KeyCommand {
32
    constructor(key, modifiers = [])
33
    {
34
        this.key = key;
35
        this.modifiers = modifiers;
36
    }
37
38
    toString()
39
    {
40
        let readableCommand = this.modifiers.map((modifier) => modifierDisplayNameMap[modifier]);
41
        readableCommand.push(this.key);
42
        return readableCommand.join(" + ");
43
    }
44
}
45
46
function done()
47
{
48
    let testContainer = document.getElementById("test-container");
49
    document.body.removeChild(testContainer);
50
    finishJSTest()
51
}
52
53
async function runTest()
54
{
55
    if (!window.testRunner) {
56
        testFailed("Must be run in WebKitTestRunner.");
57
        done();
58
        return;
59
    }
60
61
    async function testScrollIntoView() {
62
        shouldBeNonZero("window.scrollY");
63
        async function handleScroll() {
64
            if (window.scrollY)
65
                return;
66
            shouldBeZero("window.scrollY");
67
            await UIHelper.waitForPopoverToPresent();
68
            UIHelper.keyDown("escape");
69
            await UIHelper.waitForPopoverToDismiss();
70
            done();
71
        }
72
        // The scroll initiated by pressing the spacebar is animated. Multiple scroll events are
73
        // dispatched. We want to wait until the page scrolls to the top before continuing to ensure
74
        // consistent test results.
75
        window.addEventListener("scroll", handleScroll);
76
        UIHelper.keyDown(" ");
77
    }
78
79
    async function handleFocus() {
80
        debug("<br>After tab focused:");
81
        shouldBeEqualToString('document.getElementById("test").value', expectedValue);
82
        debug("<br>After dismissing popover by pressing Escape:");
83
        UIHelper.keyDown("escape");
84
        await UIHelper.waitForPopoverToDismiss();
85
        shouldBeEqualToString('document.getElementById("test").value', expectedValue);
86
        debug("<br>After opening popover by pressing spacebar:");
87
        UIHelper.keyDown(" ");
88
        await UIHelper.waitForPopoverToPresent();
89
        shouldBeEqualToString('document.getElementById("test").value', expectedValue);
90
        UIHelper.keyDown("escape");
91
        await UIHelper.waitForPopoverToDismiss();
92
        debug("<br>After scrolling the page and pressing spacebar:");
93
        window.addEventListener("scroll", testScrollIntoView, { once: true });
94
        window.scrollTo(0, document.body.scrollHeight); // Scroll to the bottom of the page.
95
    }
96
    let elementToTest = document.getElementById("test");
97
    expectedValue = elementToTest.value;
98
    elementToTest.addEventListener("focus", handleFocus, { once: true });
99
    UIHelper.keyDown("\t", ["altKey"]);
100
}
101
102
description("Tests that pressing the spacebar and Escape to open and close the popover work, do not cause a value change, and that we scroll the form control into view when the popover is opened.");
103
104
runTest();
105
</script>
106
</body>
107
</html>
- a/LayoutTests/platform/ios/TestExpectations +1 lines
Lines 25-30 http/tests/gzip-content-encoding [ Pass ] a/LayoutTests/platform/ios/TestExpectations_sec1
25
25
26
# iPad-specific tests skipped here and re-enabled in platform/ipad
26
# iPad-specific tests skipped here and re-enabled in platform/ipad
27
fast/events/ios/ipad [ Skip ]
27
fast/events/ios/ipad [ Skip ]
28
fast/forms/ios/ipad [ Skip ]
28
29
29
###
30
###
30
# Unsupported and disabled features
31
# Unsupported and disabled features
- a/LayoutTests/platform/ipad/TestExpectations +2 lines
Lines 1-3 a/LayoutTests/platform/ipad/TestExpectations_sec1
1
fast/forms/ios/ipad [ Pass ]
2
1
# iPads don't zoom when form elements are focused
3
# iPads don't zoom when form elements are focused
2
fast/forms/ios/accessory-bar-navigation.html [ Skip ]
4
fast/forms/ios/accessory-bar-navigation.html [ Skip ]
3
fast/forms/ios/choose-select-option.html [ Skip ]
5
fast/forms/ios/choose-select-option.html [ Skip ]
- a/LayoutTests/resources/ui-helper.js +32 lines
Lines 382-387 window.UIHelper = class UIHelper { a/LayoutTests/resources/ui-helper.js_sec1
382
        });
382
        });
383
    }
383
    }
384
384
385
    static waitForPopoverToPresent()
386
    {
387
        if (!this.isWebKit2() || !this.isIOS())
388
            return Promise.resolve();
389
390
        return new Promise(resolve => {
391
            testRunner.runUIScript(`
392
                (function() {
393
                    if (uiController.isShowingPopover)
394
                        uiController.uiScriptComplete();
395
                    else
396
                        uiController.willPresentPopoverCallback = () => uiController.uiScriptComplete();
397
                })()`, resolve);
398
        });
399
    }
400
401
    static waitForPopoverToDismiss()
402
    {
403
        if (!this.isWebKit2() || !this.isIOS())
404
            return Promise.resolve();
405
406
        return new Promise(resolve => {
407
            testRunner.runUIScript(`
408
                (function() {
409
                    if (uiController.isShowingPopover)
410
                        uiController.didDismissPopoverCallback = () => uiController.uiScriptComplete();
411
                    else
412
                        uiController.uiScriptComplete();
413
                })()`, resolve);
414
        });
415
    }
416
385
    static waitForKeyboardToHide()
417
    static waitForKeyboardToHide()
386
    {
418
    {
387
        if (!this.isWebKit2() || !this.isIOS())
419
        if (!this.isWebKit2() || !this.isIOS())

Return to Bug 196360