Changeset 216335 in webkit


Ignore:
Timestamp:
May 6, 2017 7:53:51 PM (7 years ago)
Author:
Simon Fraser
Message:

[iOS WK2] Make rotation tests more reliable
https://bugs.webkit.org/show_bug.cgi?id=171778

Reviewed by Tim Horton.

Source/WebKit2:

Switching between "safari-style" rotation and normal rotation left state on the WKWebView
that would cause later viewport-sensitive tests to fail. The WKWebView would be left
with override layout parameters, and an override orientation, and these caused viewport
size to leak into later tests, and WebCore orientation to not get reset correctly.

Also, WKWebView was unregistering for UIWindowDidRotateNotification notifications when
an override orientation was set, and would never re-register, causing lost orientationchanged
events.

Fix by exposing WKWebView SPI to clear the various bits of overide state. Also don't unregister
from the UIWindowDidRotateNotification notification; it's already ignored anyway if it fires.

Also wait for a visible content rect update after resizing the WKWebVeiw between tests, to make sure
the WebProcess is caught up before proceeding with the test.

  • UIProcess/API/Cocoa/WKWebView.mm:

(-[WKWebView _setInterfaceOrientationOverride:]):
(-[WKWebView _clearInterfaceOrientationOverride]):
(-[WKWebView _beginAnimatedResizeWithUpdates:]):
(-[WKWebView _clearOverrideLayoutParameters]):

  • UIProcess/API/Cocoa/WKWebViewPrivate.h:

Tools:

Switching between "safari-style" rotation and normal rotation left state on the WKWebView
that would cause later viewport-sensitive tests to fail. The WKWebView would be left
with override layout parameters, and an override orientation, and these caused viewport
size to leak into later tests, and WebCore orientation to not get reset correctly.

Also, WKWebView was unregistering for UIWindowDidRotateNotification notifications when
an override orientation was set, and would never re-register, causing lost orientationchanged
events.

Fix by exposing WKWebView SPI to clear the various bits of overide state. Also don't unregister
from the UIWindowDidRotateNotification notification; it's already ignored anyway if it fires.

Also wait for a visible content rect update after resizing the WKWebVeiw between tests, to make sure
the WebProcess is caught up before proceeding with the test.

  • WebKitTestRunner/ios/PlatformWebViewIOS.mm:

(-[PlatformWebViewController viewWillTransitionToSize:withTransitionCoordinator:]):

  • WebKitTestRunner/ios/TestControllerIOS.mm:

(WTR::TestController::platformResetStateToConsistentValues):
(WTR::TestController::platformConfigureViewForTest):

LayoutTests:

New baseline.

  • fast/events/ios/rotation/zz-no-rotation-expected.txt:
  • fast/events/ios/rotation/zz-no-rotation.html:
Location:
trunk
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r216334 r216335  
     12017-05-06  Simon Fraser  <simon.fraser@apple.com>
     2
     3        [iOS WK2] Make rotation tests more reliable
     4        https://bugs.webkit.org/show_bug.cgi?id=171778
     5
     6        Reviewed by Tim Horton.
     7
     8        New baseline.
     9
     10        * fast/events/ios/rotation/zz-no-rotation-expected.txt:
     11        * fast/events/ios/rotation/zz-no-rotation.html:
     12
    1132017-05-06  Chris Dumez  <cdumez@apple.com>
    214
  • trunk/LayoutTests/fast/events/ios/rotation/zz-no-rotation-expected.txt

    r216291 r216335  
    33TEST COMPLETE
    44PASS window.innerWidth is 320
    5 PASS window.innerHeight is 568
     5PASS window.innerHeight is 548
    66This test checks that the view is not left in a rotated state after the previous tests.
  • trunk/LayoutTests/fast/events/ios/rotation/zz-no-rotation.html

    r216291 r216335  
    99        {
    1010            shouldBe("window.innerWidth", "320");
    11             shouldBe("window.innerHeight", "568");
     11            shouldBe("window.innerHeight", "548");
    1212        }
    1313        window.addEventListener('load', doTest, false);
  • trunk/Source/WebKit2/ChangeLog

    r216328 r216335  
     12017-05-06  Simon Fraser  <simon.fraser@apple.com>
     2
     3        [iOS WK2] Make rotation tests more reliable
     4        https://bugs.webkit.org/show_bug.cgi?id=171778
     5
     6        Reviewed by Tim Horton.
     7
     8        Switching between "safari-style" rotation and normal rotation left state on the WKWebView
     9        that would cause later viewport-sensitive tests to fail. The WKWebView would be left
     10        with override layout parameters, and an override orientation, and these caused viewport
     11        size to leak into later tests, and WebCore orientation to not get reset correctly.
     12
     13        Also, WKWebView was unregistering for UIWindowDidRotateNotification notifications when
     14        an override orientation was set, and would never re-register, causing lost orientationchanged
     15        events.
     16
     17        Fix by exposing WKWebView SPI to clear the various bits of overide state. Also don't unregister
     18        from the UIWindowDidRotateNotification notification; it's already ignored anyway if it fires.
     19
     20        Also wait for a visible content rect update after resizing the WKWebVeiw between tests, to make sure
     21        the WebProcess is caught up before proceeding with the test.
     22
     23        * UIProcess/API/Cocoa/WKWebView.mm:
     24        (-[WKWebView _setInterfaceOrientationOverride:]):
     25        (-[WKWebView _clearInterfaceOrientationOverride]):
     26        (-[WKWebView _beginAnimatedResizeWithUpdates:]):
     27        (-[WKWebView _clearOverrideLayoutParameters]):
     28        * UIProcess/API/Cocoa/WKWebViewPrivate.h:
     29
    1302017-05-06  Konstantin Tokarev  <annulen@yandex.ru>
    231
  • trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebView.mm

    r216249 r216335  
    45634563- (void)_setInterfaceOrientationOverride:(UIInterfaceOrientation)interfaceOrientation
    45644564{
    4565     if (!_overridesInterfaceOrientation)
    4566         [[NSNotificationCenter defaultCenter] removeObserver:self name:UIWindowDidRotateNotification object:nil];
    4567 
    45684565    _overridesInterfaceOrientation = YES;
    45694566
     
    45814578    ASSERT(_overridesInterfaceOrientation);
    45824579    return _interfaceOrientationOverride;
     4580}
     4581
     4582- (void)_clearInterfaceOrientationOverride
     4583{
     4584    _overridesInterfaceOrientation = NO;
     4585    _interfaceOrientationOverride = UIInterfaceOrientationPortrait;
    45834586}
    45844587
     
    46774680        if (_overridesInterfaceOrientation)
    46784681            _page->setDeviceOrientation(newOrientation);
     4682
    46794683        [self _scheduleVisibleContentRectUpdate];
    46804684        return;
     
    49164920}
    49174921
     4922- (void)_clearOverrideLayoutParameters
     4923{
     4924    _overridesMinimumLayoutSize = NO;
     4925    _minimumLayoutSizeOverride = CGSizeZero;
     4926   
     4927    _overridesMaximumUnobscuredSize = NO;
     4928    _maximumUnobscuredSizeOverride = CGSizeZero;
     4929}
     4930
    49184931- (UIView *)_viewForFindUI
    49194932{
  • trunk/Source/WebKit2/UIProcess/API/Cocoa/WKWebViewPrivate.h

    r216197 r216335  
    191191- (void)_overrideLayoutParametersWithMinimumLayoutSize:(CGSize)minimumLayoutSize maximumUnobscuredSizeOverride:(CGSize)maximumUnobscuredSizeOverride WK_API_AVAILABLE(ios(9_0));
    192192
     193- (void)_clearOverrideLayoutParameters;
     194- (void)_clearInterfaceOrientationOverride;
     195
    193196- (UIView *)_viewForFindUI;
    194197
  • trunk/Tools/ChangeLog

    r216326 r216335  
     12017-05-06  Simon Fraser  <simon.fraser@apple.com>
     2
     3        [iOS WK2] Make rotation tests more reliable
     4        https://bugs.webkit.org/show_bug.cgi?id=171778
     5
     6        Reviewed by Tim Horton.
     7
     8        Switching between "safari-style" rotation and normal rotation left state on the WKWebView
     9        that would cause later viewport-sensitive tests to fail. The WKWebView would be left
     10        with override layout parameters, and an override orientation, and these caused viewport
     11        size to leak into later tests, and WebCore orientation to not get reset correctly.
     12
     13        Also, WKWebView was unregistering for UIWindowDidRotateNotification notifications when
     14        an override orientation was set, and would never re-register, causing lost orientationchanged
     15        events.
     16
     17        Fix by exposing WKWebView SPI to clear the various bits of overide state. Also don't unregister
     18        from the UIWindowDidRotateNotification notification; it's already ignored anyway if it fires.
     19
     20        Also wait for a visible content rect update after resizing the WKWebVeiw between tests, to make sure
     21        the WebProcess is caught up before proceeding with the test.
     22
     23        * WebKitTestRunner/ios/PlatformWebViewIOS.mm:
     24        (-[PlatformWebViewController viewWillTransitionToSize:withTransitionCoordinator:]):
     25        * WebKitTestRunner/ios/TestControllerIOS.mm:
     26        (WTR::TestController::platformResetStateToConsistentValues):
     27        (WTR::TestController::platformConfigureViewForTest):
     28
    1292017-05-06  Csaba Osztrogonác  <ossy@webkit.org>
    230
  • trunk/Tools/WebKitTestRunner/ios/PlatformWebViewIOS.mm

    r216291 r216335  
    109109@end
    110110
    111 @interface PlatformWebViewController : UIViewController
    112 @end
    113 
    114 @implementation PlatformWebViewController
    115 
    116 - (void)viewWillTransitionToSize:(CGSize)toSize withTransitionCoordinator:(id <UIViewControllerTransitionCoordinator>)coordinator
    117 {
    118     [super viewWillTransitionToSize:toSize withTransitionCoordinator:coordinator];
    119    
    120     TestRunnerWKWebView *webView = WTR::TestController::singleton().mainWebView()->platformView();
    121    
    122     if (webView.usesSafariLikeRotation)
    123         [webView _setInterfaceOrientationOverride:[[UIApplication sharedApplication] statusBarOrientation]];
    124        
    125     [coordinator animateAlongsideTransition: ^(id<UIViewControllerTransitionCoordinatorContext> context) {
    126         if (webView.usesSafariLikeRotation) {
    127             [webView _beginAnimatedResizeWithUpdates:^{
    128                 auto size = self.view.bounds.size;
    129                 webView.frame = self.view.bounds;
    130                 [webView _overrideLayoutParametersWithMinimumLayoutSize:size maximumUnobscuredSizeOverride:size];
    131                 [webView _setInterfaceOrientationOverride:[[UIApplication sharedApplication] statusBarOrientation]];
    132             }];
    133         } else
    134             webView.frame = self.view.bounds;
    135     } completion:^(id<UIViewControllerTransitionCoordinatorContext> context) {
    136         webView.frame = self.view.bounds;
    137         if (webView.usesSafariLikeRotation)
    138             [webView _endAnimatedResize];
    139            
    140         [webView _didEndRotation];
    141     }];
    142 }
    143 
    144 @end
    145 
    146111namespace WTR {
    147112
     
    150115    HeightRespectsStatusBar
    151116};
     117
     118static CGRect viewRectForWindowRect(CGRect, PlatformWebView::WebViewSizingMode);
     119
     120} // namespace WTR
     121
     122@interface PlatformWebViewController : UIViewController
     123@end
     124
     125@implementation PlatformWebViewController
     126
     127- (void)viewWillTransitionToSize:(CGSize)toSize withTransitionCoordinator:(id <UIViewControllerTransitionCoordinator>)coordinator
     128{
     129    [super viewWillTransitionToSize:toSize withTransitionCoordinator:coordinator];
     130
     131    TestRunnerWKWebView *webView = WTR::TestController::singleton().mainWebView()->platformView();
     132
     133    if (webView.usesSafariLikeRotation)
     134        [webView _setInterfaceOrientationOverride:[[UIApplication sharedApplication] statusBarOrientation]];
     135
     136    [coordinator animateAlongsideTransition: ^(id<UIViewControllerTransitionCoordinatorContext> context) {
     137        // This code assumes that we should take the status bar into account, which we only do for flexible viewport tests,
     138        // but it only makes sense to test rotation with a flexible viewport anyway.
     139        if (webView.usesSafariLikeRotation) {
     140            [webView _beginAnimatedResizeWithUpdates:^{
     141                webView.frame = viewRectForWindowRect(self.view.bounds, WTR::PlatformWebView::WebViewSizingMode::HeightRespectsStatusBar);
     142                [webView _overrideLayoutParametersWithMinimumLayoutSize:webView.frame.size maximumUnobscuredSizeOverride:webView.frame.size];
     143                [webView _setInterfaceOrientationOverride:[[UIApplication sharedApplication] statusBarOrientation]];
     144            }];
     145        } else
     146            webView.frame = viewRectForWindowRect(self.view.bounds, WTR::PlatformWebView::WebViewSizingMode::HeightRespectsStatusBar);
     147    } completion:^(id<UIViewControllerTransitionCoordinatorContext> context) {
     148        webView.frame = viewRectForWindowRect(self.view.bounds, WTR::PlatformWebView::WebViewSizingMode::HeightRespectsStatusBar);
     149        if (webView.usesSafariLikeRotation)
     150            [webView _endAnimatedResize];
     151
     152        [webView _didEndRotation];
     153    }];
     154}
     155
     156@end
     157
     158namespace WTR {
    152159
    153160static CGRect viewRectForWindowRect(CGRect windowRect, PlatformWebView::WebViewSizingMode mode)
  • trunk/Tools/WebKitTestRunner/ios/TestControllerIOS.mm

    r216291 r216335  
    8383    [[UIDevice currentDevice] setOrientation:UIDeviceOrientationPortrait animated:NO];
    8484   
    85     if (PlatformWebView* webView = mainWebView()) {
    86         webView->platformView()._stableStateOverride = nil;
    87         webView->platformView().usesSafariLikeRotation = NO;
    88         UIScrollView *scrollView = webView->platformView().scrollView;
     85    if (PlatformWebView* platformWebView = mainWebView()) {
     86        TestRunnerWKWebView *webView = platformWebView->platformView();
     87        webView._stableStateOverride = nil;
     88        webView.usesSafariLikeRotation = NO;
     89        webView.overrideSafeAreaInsets = UIEdgeInsetsZero;
     90        [webView _clearOverrideLayoutParameters];
     91        [webView _clearInterfaceOrientationOverride];
     92
     93        UIScrollView *scrollView = webView.scrollView;
    8994        [scrollView _removeAllAnimations:YES];
    9095        [scrollView setZoomScale:1 animated:NO];
    9196        [scrollView setContentOffset:CGPointZero];
    92 
    93         webView->platformView().overrideSafeAreaInsets = UIEdgeInsetsZero;
    9497    }
    9598}
     
    97100void TestController::platformConfigureViewForTest(const TestInvocation& test)
    98101{
    99     if (test.options().useFlexibleViewport) {
    100         CGRect screenBounds = [UIScreen mainScreen].bounds;
    101         mainWebView()->resizeTo(screenBounds.size.width, screenBounds.size.height, PlatformWebView::WebViewSizingMode::HeightRespectsStatusBar);
    102         // We also pass data to InjectedBundle::beginTesting() to have it call
    103         // WKBundlePageSetUseTestingViewportConfiguration(false).
     102    if (!test.options().useFlexibleViewport)
     103        return;
     104       
     105    TestRunnerWKWebView *webView = mainWebView()->platformView();
     106    CGRect screenBounds = [UIScreen mainScreen].bounds;
     107   
     108    CGSize oldSize = webView.bounds.size;
     109    mainWebView()->resizeTo(screenBounds.size.width, screenBounds.size.height, PlatformWebView::WebViewSizingMode::HeightRespectsStatusBar);
     110    CGSize newSize = webView.bounds.size;
     111   
     112    if (!CGSizeEqualToSize(oldSize, newSize)) {
     113        __block bool doneResizing = false;
     114        [webView _doAfterNextVisibleContentRectUpdate: ^{
     115            doneResizing = true;
     116        }];
     117
     118        platformRunUntil(doneResizing, 10);
     119        if (!doneResizing)
     120            WTFLogAlways("Timed out waiting for view resize to complete in platformConfigureViewForTest()");
    104121    }
     122   
     123    // We also pass data to InjectedBundle::beginTesting() to have it call
     124    // WKBundlePageSetUseTestingViewportConfiguration(false).
    105125}
    106126
Note: See TracChangeset for help on using the changeset viewer.