[iOS][WK2] Add device orientation
authorbenjamin@webkit.org <benjamin@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 5 Jun 2014 21:14:52 +0000 (21:14 +0000)
committerbenjamin@webkit.org <benjamin@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 5 Jun 2014 21:14:52 +0000 (21:14 +0000)
https://bugs.webkit.org/show_bug.cgi?id=133530

Source/WebCore:

Patch by Benjamin Poulain <bpoulain@apple.com> on 2014-06-05
Reviewed by Tim Horton.

Previously, WebCore was getting the orientation directly from the WebKit layer.
This had to be done during the frame creation and was very fragile.

Frame is changed to pull the value from the chrome client. That way we avoid races
and we can maintain a single value for all frames.

Sending the values to all the subframes is aslo done here so that we do not have to repeat
it in both WebKit layers.

* WebCore.exp.in:
* loader/EmptyClients.h:
* page/ChromeClient.h:
* page/Frame.cpp:
(WebCore::Frame::Frame):
(WebCore::Frame::orientationChanged):
(WebCore::Frame::orientation):
(WebCore::Frame::sendOrientationChangeEvent): Deleted.
* page/Frame.h:
(WebCore::Frame::orientation): Deleted.

Source/WebKit/ios:

Patch by Benjamin Poulain <bpoulain@apple.com> on 2014-06-05
Reviewed by Tim Horton.

Change WebKit1 to provide the deviceOrientation as pull instead of push.

* DefaultDelegates/WebDefaultUIKitDelegate.m:
(-[WebDefaultUIKitDelegate deviceOrientation]):
* WebCoreSupport/WebChromeClientIOS.h:
* WebCoreSupport/WebChromeClientIOS.mm:
(WebChromeClientIOS::deviceOrientation):
* WebView/WebUIKitDelegate.h:

Source/WebKit/mac:

Patch by Benjamin Poulain <bpoulain@apple.com> on 2014-06-05
Reviewed by Tim Horton.

* WebView/WebFrame.mm:
(-[WebFrame deviceOrientationChanged]):
(-[WebFrame sendOrientationChangeEvent:]):
* WebView/WebFramePrivate.h:

Source/WebKit2:
<rdar://problem/16680041>

Patch by Benjamin Poulain <bpoulain@apple.com> on 2014-06-05
Reviewed by Tim Horton.

Add device orientation for WebKit2.

For the public API, WKWebView get the updates through the notification UIWindowDidRotateNotification.
We do not have any control over how the API is used, but we can expect the size will be updated before
the end of rotation in most cases and the events should be sent in the right order.

For Safari, we use an override to support animated resize (and some tabs corner cases).

On the WebProcess side, we just get the new orientation directly or on DynamicViewportSizeUpdate.

* UIProcess/API/Cocoa/WKWebView.mm:
(deviceOrientationForUIInterfaceOrientation):
(deviceOrientation):
(-[WKWebView initWithFrame:configuration:]):
(-[WKWebView _windowDidRotate:]):
(-[WKWebView _setInterfaceOrientationOverride:]):
(-[WKWebView _interfaceOrientationOverride]):
(-[WKWebView _beginAnimatedResizeWithUpdates:]):
* UIProcess/API/Cocoa/WKWebViewPrivate.h:
* UIProcess/WebPageProxy.cpp:
(WebKit::WebPageProxy::WebPageProxy):
* UIProcess/WebPageProxy.h:
(WebKit::WebPageProxy::deviceOrientation):
* UIProcess/ios/WebPageProxyIOS.mm:
(WebKit::WebPageProxy::dynamicViewportSizeUpdate):
(WebKit::WebPageProxy::setDeviceOrientation):
* WebProcess/WebCoreSupport/WebChromeClient.h:
* WebProcess/WebCoreSupport/ios/WebChromeClientIOS.mm:
(WebKit::WebChromeClient::deviceOrientation):
* WebProcess/WebPage/WebPage.cpp:
(WebKit::WebPage::WebPage):
* WebProcess/WebPage/WebPage.h:
(WebKit::WebPage::deviceOrientation):
* WebProcess/WebPage/WebPage.messages.in:
* WebProcess/WebPage/ios/WebPageIOS.mm:
(WebKit::WebPage::setDeviceOrientation):
(WebKit::WebPage::dynamicViewportSizeUpdate):

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@169625 268f45cc-cd09-0410-ab3c-d52691b4dbfc

26 files changed:
Source/WebCore/ChangeLog
Source/WebCore/WebCore.exp.in
Source/WebCore/loader/EmptyClients.h
Source/WebCore/page/ChromeClient.h
Source/WebCore/page/Frame.cpp
Source/WebCore/page/Frame.h
Source/WebKit/ios/ChangeLog
Source/WebKit/ios/DefaultDelegates/WebDefaultUIKitDelegate.m
Source/WebKit/ios/WebCoreSupport/WebChromeClientIOS.h
Source/WebKit/ios/WebCoreSupport/WebChromeClientIOS.mm
Source/WebKit/ios/WebView/WebUIKitDelegate.h
Source/WebKit/mac/ChangeLog
Source/WebKit/mac/WebView/WebFrame.mm
Source/WebKit/mac/WebView/WebFramePrivate.h
Source/WebKit2/ChangeLog
Source/WebKit2/UIProcess/API/Cocoa/WKWebView.mm
Source/WebKit2/UIProcess/API/Cocoa/WKWebViewPrivate.h
Source/WebKit2/UIProcess/WebPageProxy.cpp
Source/WebKit2/UIProcess/WebPageProxy.h
Source/WebKit2/UIProcess/ios/WebPageProxyIOS.mm
Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.h
Source/WebKit2/WebProcess/WebCoreSupport/ios/WebChromeClientIOS.mm
Source/WebKit2/WebProcess/WebPage/WebPage.cpp
Source/WebKit2/WebProcess/WebPage/WebPage.h
Source/WebKit2/WebProcess/WebPage/WebPage.messages.in
Source/WebKit2/WebProcess/WebPage/ios/WebPageIOS.mm

index 770951b..e7dafae 100644 (file)
@@ -1,3 +1,30 @@
+2014-06-05  Benjamin Poulain  <bpoulain@apple.com>
+
+        [iOS][WK2] Add device orientation
+        https://bugs.webkit.org/show_bug.cgi?id=133530
+
+        Reviewed by Tim Horton.
+
+        Previously, WebCore was getting the orientation directly from the WebKit layer.
+        This had to be done during the frame creation and was very fragile.
+
+        Frame is changed to pull the value from the chrome client. That way we avoid races
+        and we can maintain a single value for all frames.
+
+        Sending the values to all the subframes is aslo done here so that we do not have to repeat
+        it in both WebKit layers.
+
+        * WebCore.exp.in:
+        * loader/EmptyClients.h:
+        * page/ChromeClient.h:
+        * page/Frame.cpp:
+        (WebCore::Frame::Frame):
+        (WebCore::Frame::orientationChanged):
+        (WebCore::Frame::orientation):
+        (WebCore::Frame::sendOrientationChangeEvent): Deleted.
+        * page/Frame.h:
+        (WebCore::Frame::orientation): Deleted.
+
 2014-06-05  Timothy Horton  <timothy_horton@apple.com>
 
         Fix the !CACHE_SUBIMAGES build
index 2753874..5fd1e12 100644 (file)
@@ -3218,7 +3218,7 @@ __ZN7WebCore22NotificationController10clientFromEPNS_4PageE
 #endif
 
 #if ENABLE(ORIENTATION_EVENTS)
-__ZN7WebCore5Frame26sendOrientationChangeEventEi
+__ZN7WebCore5Frame18orientationChangedEv
 #endif
 
 #if USE(PLUGIN_HOST_PROCESS)
index 4fc83fe..7829c14 100644 (file)
@@ -214,6 +214,10 @@ public:
     virtual void showPlaybackTargetPicker(bool) override { };
 #endif // PLATFORM(IOS)
 
+#if ENABLE(ORIENTATION_EVENTS)
+    virtual int deviceOrientation() const override { return 0; }
+#endif
+
 #if PLATFORM(IOS)
     virtual bool isStopping() override { return false; }
 #endif
index 7b70212..470b743 100644 (file)
@@ -266,6 +266,10 @@ public:
     virtual void showPlaybackTargetPicker(bool hasVideo) = 0;
 #endif
 
+#if ENABLE(ORIENTATION_EVENTS)
+    virtual int deviceOrientation() const = 0;
+#endif
+
 #if ENABLE(INPUT_TYPE_COLOR)
     virtual PassOwnPtr<ColorChooser> createColorChooser(ColorChooserClient*, const Color&) = 0;
 #endif
index 61303d1..e09244d 100644 (file)
@@ -167,9 +167,6 @@ Frame::Frame(Page& page, HTMLFrameOwnerElement* ownerElement, FrameLoaderClient&
 #endif
     , m_pageZoomFactor(parentPageZoomFactor(this))
     , m_textZoomFactor(parentTextZoomFactor(this))
-#if ENABLE(ORIENTATION_EVENTS)
-    , m_orientation(0)
-#endif
     , m_activeDOMObjectsAndAnimationsSuspendedCount(0)
 {
     AtomicString::init();
@@ -288,11 +285,23 @@ void Frame::setDocument(PassRefPtr<Document> newDocument)
 }
 
 #if ENABLE(ORIENTATION_EVENTS)
-void Frame::sendOrientationChangeEvent(int orientation)
+void Frame::orientationChanged()
+{
+    Vector<Ref<Frame>> frames;
+    for (Frame* frame = this; frame; frame = frame->tree().traverseNext())
+        frames.append(*frame);
+
+    for (unsigned i = 0; i < frames.size(); i++) {
+        if (Document* doc = frames[i]->document())
+            doc->dispatchWindowEvent(Event::create(eventNames().orientationchangeEvent, false, false));
+    }
+}
+
+int Frame::orientation() const
 {
-    m_orientation = orientation;
-    if (Document* doc = document())
-        doc->dispatchWindowEvent(Event::create(eventNames().orientationchangeEvent, false, false));
+    if (m_page)
+        return m_page->chrome().client().deviceOrientation();
+    return 0;
 }
 #endif // ENABLE(ORIENTATION_EVENTS)
 
index 5b4501f..7685679 100644 (file)
@@ -214,8 +214,8 @@ namespace WebCore {
         // Orientation is the interface orientation in degrees. Some examples are:
         //  0 is straight up; -90 is when the device is rotated 90 clockwise;
         //  90 is when rotated counter clockwise.
-        void sendOrientationChangeEvent(int orientation);
-        int orientation() const { return m_orientation; }
+        void orientationChanged();
+        int orientation() const;
 #endif
 
         void clearTimers();
@@ -314,10 +314,6 @@ namespace WebCore {
         float m_pageZoomFactor;
         float m_textZoomFactor;
 
-#if ENABLE(ORIENTATION_EVENTS)
-        int m_orientation;
-#endif
-
         int m_activeDOMObjectsAndAnimationsSuspendedCount;
     };
 
index 96adb7b..aabadd8 100644 (file)
@@ -1,3 +1,19 @@
+2014-06-05  Benjamin Poulain  <bpoulain@apple.com>
+
+        [iOS][WK2] Add device orientation
+        https://bugs.webkit.org/show_bug.cgi?id=133530
+
+        Reviewed by Tim Horton.
+
+        Change WebKit1 to provide the deviceOrientation as pull instead of push.
+
+        * DefaultDelegates/WebDefaultUIKitDelegate.m:
+        (-[WebDefaultUIKitDelegate deviceOrientation]):
+        * WebCoreSupport/WebChromeClientIOS.h:
+        * WebCoreSupport/WebChromeClientIOS.mm:
+        (WebChromeClientIOS::deviceOrientation):
+        * WebView/WebUIKitDelegate.h:
+
 2014-05-09  Benjamin Poulain  <benjamin@webkit.org>
 
         [iOS] Switch geolocation to an explicit authorization query model
index f173dba..714f1f9 100644 (file)
@@ -245,6 +245,13 @@ static WebDefaultUIKitDelegate *sharedDelegate = nil;
 {
 }
 
+#if ENABLE(ORIENTATION_EVENTS)
+- (int)deviceOrientation
+{
+    return 0;
+}
+#endif
+
 - (BOOL)hasRichlyEditableSelection
 {
     return NO;
index e0e4dbb..1b5935d 100644 (file)
@@ -86,6 +86,10 @@ public:
     virtual void focusedElementChanged(WebCore::Element*) override;
     virtual void showPlaybackTargetPicker(bool hasVideo) override;
 
+#if ENABLE(ORIENTATION_EVENTS)
+    virtual int deviceOrientation() const override;
+#endif
+
 private:
     int m_formNotificationSuppressions;
 };
index b5a3484..f664f95 100644 (file)
@@ -328,4 +328,11 @@ void WebChromeClientIOS::showPlaybackTargetPicker(bool hasVideo)
     [[webView() _UIKitDelegateForwarder] showPlaybackTargetPicker:hasVideo fromRect:elementRect];
 }
 
+#if ENABLE(ORIENTATION_EVENTS)
+int WebChromeClientIOS::deviceOrientation() const
+{
+    return [[webView() _UIKitDelegateForwarder] deviceOrientation];
+}
+#endif
+
 #endif // PLATFORM(IOS)
index b24fbaf..84f18f0 100644 (file)
 - (CGPoint)interactionLocation;
 - (void)showPlaybackTargetPicker:(BOOL)hasVideo fromRect:(CGRect)elementRect;
 
+#if ENABLE(ORIENTATION_EVENTS)
+- (int)deviceOrientation;
+#endif
+
 - (BOOL)isUnperturbedDictationResultMarker:(id)metadataForMarker;
 - (void)webView:(WebView *)webView addMessageToConsole:(NSDictionary *)message withSource:(NSString *)source;
 @end
index 3c4a6df..a990520 100644 (file)
@@ -1,3 +1,15 @@
+2014-06-05  Benjamin Poulain  <bpoulain@apple.com>
+
+        [iOS][WK2] Add device orientation
+        https://bugs.webkit.org/show_bug.cgi?id=133530
+
+        Reviewed by Tim Horton.
+
+        * WebView/WebFrame.mm:
+        (-[WebFrame deviceOrientationChanged]):
+        (-[WebFrame sendOrientationChangeEvent:]):
+        * WebView/WebFramePrivate.h:
+
 2014-05-31  Anders Carlsson  <andersca@apple.com>
 
         Change DeferrableOneShotTimer to use std::function instead of being a class template
index afa4978..58bfb98 100644 (file)
@@ -1267,15 +1267,19 @@ static inline WebDataSource *dataSource(DocumentLoader* loader)
     frameLoader.client().saveViewStateToItem(frameLoader.history().currentItem());
 }
 
-- (void)sendOrientationChangeEvent:(int)newOrientation
+- (void)deviceOrientationChanged
 {
     WebThreadRun(^{
-        WebCore::Frame *frame = core(self);
-        if (frame)
-            frame->sendOrientationChangeEvent(newOrientation);
+        if (WebCore::Frame* frame = core(self))
+            frame->orientationChanged();
     });
 }
 
+- (void)sendOrientationChangeEvent:(int)newOrientation
+{
+    [self deviceOrientationChanged];
+}
+
 - (void)setNeedsLayout
 {
     WebCore::Frame *frame = core(self);
index da32133..c8f8279 100644 (file)
@@ -118,7 +118,11 @@ typedef enum {
 - (void)_setSelectionFromNone;
 - (void)_saveViewState;
 - (void)_restoreViewState;
+
+- (void)deviceOrientationChanged;
+// FIXME: deprecated, to be removed after the call sites are updated.
 - (void)sendOrientationChangeEvent:(int)newOrientation;
+
 - (void)setNeedsLayout;
 - (CGSize)renderedSizeOfNode:(DOMNode *)node constrainedToWidth:(float)width;
 - (DOMNode *)deepestNodeAtViewportLocation:(CGPoint)aViewportLocation;
index 1d33360..fdcb800 100644 (file)
@@ -1,3 +1,49 @@
+2014-06-05  Benjamin Poulain  <bpoulain@apple.com>
+
+        [iOS][WK2] Add device orientation
+        https://bugs.webkit.org/show_bug.cgi?id=133530
+        <rdar://problem/16680041>
+
+        Reviewed by Tim Horton.
+
+        Add device orientation for WebKit2.
+
+        For the public API, WKWebView get the updates through the notification UIWindowDidRotateNotification.
+        We do not have any control over how the API is used, but we can expect the size will be updated before
+        the end of rotation in most cases and the events should be sent in the right order.
+
+        For Safari, we use an override to support animated resize (and some tabs corner cases).
+
+        On the WebProcess side, we just get the new orientation directly or on DynamicViewportSizeUpdate.
+
+        * UIProcess/API/Cocoa/WKWebView.mm:
+        (deviceOrientationForUIInterfaceOrientation):
+        (deviceOrientation):
+        (-[WKWebView initWithFrame:configuration:]):
+        (-[WKWebView _windowDidRotate:]):
+        (-[WKWebView _setInterfaceOrientationOverride:]):
+        (-[WKWebView _interfaceOrientationOverride]):
+        (-[WKWebView _beginAnimatedResizeWithUpdates:]):
+        * UIProcess/API/Cocoa/WKWebViewPrivate.h:
+        * UIProcess/WebPageProxy.cpp:
+        (WebKit::WebPageProxy::WebPageProxy):
+        * UIProcess/WebPageProxy.h:
+        (WebKit::WebPageProxy::deviceOrientation):
+        * UIProcess/ios/WebPageProxyIOS.mm:
+        (WebKit::WebPageProxy::dynamicViewportSizeUpdate):
+        (WebKit::WebPageProxy::setDeviceOrientation):
+        * WebProcess/WebCoreSupport/WebChromeClient.h:
+        * WebProcess/WebCoreSupport/ios/WebChromeClientIOS.mm:
+        (WebKit::WebChromeClient::deviceOrientation):
+        * WebProcess/WebPage/WebPage.cpp:
+        (WebKit::WebPage::WebPage):
+        * WebProcess/WebPage/WebPage.h:
+        (WebKit::WebPage::deviceOrientation):
+        * WebProcess/WebPage/WebPage.messages.in:
+        * WebProcess/WebPage/ios/WebPageIOS.mm:
+        (WebKit::WebPage::setDeviceOrientation):
+        (WebKit::WebPage::dynamicViewportSizeUpdate):
+
 2014-06-05  Oliver Hunt  <oliver@apple.com>
 
         Enable SANDBOX_EXTENSIONS build flag universally on cocoa
index 7f42ec6..a4f0ed1 100644 (file)
@@ -81,6 +81,7 @@
 #import <CoreGraphics/CGPDFDocumentPrivate.h>
 #import <UIKit/UIApplication.h>
 #import <UIKit/UIPeripheralHost_Private.h>
+#import <UIKit/UIWindow_Private.h>
 #import <QuartzCore/CARenderServer.h>
 #import <QuartzCore/QuartzCorePrivate.h>
 
@@ -150,6 +151,9 @@ WKWebView* fromWebPageProxy(WebKit::WebPageProxy& page)
     UIEdgeInsets _obscuredInsets;
     bool _isChangingObscuredInsetsInteractively;
 
+    UIInterfaceOrientation _interfaceOrientationOverride;
+    BOOL _overridesInterfaceOrientation;
+
     BOOL _needsResetViewStateAfterCommitLoadForMainFrame;
     BOOL _isAnimatingResize;
     CATransform3D _resizeAnimationTransformAdjustments;
@@ -180,6 +184,28 @@ WKWebView* fromWebPageProxy(WebKit::WebPageProxy& page)
     return [self initWithFrame:frame configuration:adoptNS([[WKWebViewConfiguration alloc] init]).get()];
 }
 
+#if PLATFORM(IOS)
+static int32_t deviceOrientationForUIInterfaceOrientation(UIInterfaceOrientation orientation)
+{
+    switch (orientation) {
+    case UIInterfaceOrientationUnknown:
+    case UIInterfaceOrientationPortrait:
+        return 0;
+    case UIInterfaceOrientationPortraitUpsideDown:
+        return 180;
+    case UIInterfaceOrientationLandscapeLeft:
+        return -90;
+    case UIInterfaceOrientationLandscapeRight:
+        return 90;
+    }
+}
+
+static int32_t deviceOrientation()
+{
+    return deviceOrientationForUIInterfaceOrientation([[UIApplication sharedApplication] statusBarOrientation]);
+}
+#endif
+
 - (instancetype)initWithFrame:(CGRect)frame configuration:(WKWebViewConfiguration *)configuration
 {
     if (!(self = [super initWithFrame:frame]))
@@ -228,6 +254,9 @@ WKWebView* fromWebPageProxy(WebKit::WebPageProxy& page)
 
     _contentView = adoptNS([[WKContentView alloc] initWithFrame:bounds context:context configuration:std::move(webPageConfiguration) webView:self]);
     _page = [_contentView page];
+
+    _page->setDeviceOrientation(deviceOrientation());
+
     [_contentView layer].anchorPoint = CGPointZero;
     [_contentView setFrame:bounds];
     [_scrollView addSubview:_contentView.get()];
@@ -240,6 +269,7 @@ WKWebView* fromWebPageProxy(WebKit::WebPageProxy& page)
     [center addObserver:self selector:@selector(_keyboardDidChangeFrame:) name:UIKeyboardDidChangeFrameNotification object:nil];
     [center addObserver:self selector:@selector(_keyboardWillShow:) name:UIKeyboardWillShowNotification object:nil];
     [center addObserver:self selector:@selector(_keyboardWillHide:) name:UIKeyboardWillHideNotification object:nil];
+    [center addObserver:self selector:@selector(_windowDidRotate:) name:UIWindowDidRotateNotification object:nil];
     [center addObserver:self selector:@selector(_contentSizeCategoryDidChange:) name:UIContentSizeCategoryDidChangeNotification object:nil];
     _page->contentSizeCategoryDidChange([self _contentSizeCategory]);
 
@@ -1136,6 +1166,12 @@ static WebCore::FloatPoint constrainContentOffset(WebCore::FloatPoint contentOff
     [self _keyboardChangedWithInfo:notification.userInfo adjustScrollView:YES];
 }
 
+- (void)_windowDidRotate:(NSNotification *)notification
+{
+    if (!_overridesInterfaceOrientation)
+        _page->setDeviceOrientation(deviceOrientation());
+}
+
 - (void)_contentSizeCategoryDidChange:(NSNotification *)notification
 {
     _page->contentSizeCategoryDidChange([self _contentSizeCategory]);
@@ -1686,6 +1722,28 @@ static inline WebKit::FindOptions toFindOptions(_WKFindOptions wkFindOptions)
     [_customContentView web_setObscuredInsets:obscuredInsets];
 }
 
+- (void)_setInterfaceOrientationOverride:(UIInterfaceOrientation)interfaceOrientation
+{
+    if (!_overridesInterfaceOrientation)
+        [[NSNotificationCenter defaultCenter] removeObserver:self name:UIWindowDidRotateNotification object:nil];
+
+    _overridesInterfaceOrientation = YES;
+
+    if (interfaceOrientation == _interfaceOrientationOverride)
+        return;
+
+    _interfaceOrientationOverride = interfaceOrientation;
+
+    if (!_isAnimatingResize)
+        _page->setDeviceOrientation(deviceOrientationForUIInterfaceOrientation(_interfaceOrientationOverride));
+}
+
+- (UIInterfaceOrientation)_interfaceOrientationOverride
+{
+    ASSERT(_overridesInterfaceOrientation);
+    return _interfaceOrientationOverride;
+}
+
 - (CGSize)_maximumUnobscuredSizeOverride
 {
     ASSERT(_overridesMaximumUnobscuredSize);
@@ -1806,7 +1864,13 @@ static inline WebKit::FindOptions toFindOptions(_WKFindOptions wkFindOptions)
     if (_overridesMaximumUnobscuredSize)
         maximumUnobscuredSize = _maximumUnobscuredSizeOverride;
 
-    _page->dynamicViewportSizeUpdate(WebCore::FloatSize(minimumLayoutSize), WebCore::FloatSize(minimumLayoutSizeForMinimalUI), WebCore::FloatSize(maximumUnobscuredSize), visibleRectInContentCoordinates, unobscuredRectInContentCoordinates, futureUnobscuredRectInSelfCoordinates, targetScale);
+    int32_t orientation;
+    if (_overridesInterfaceOrientation)
+        orientation = deviceOrientationForUIInterfaceOrientation(_interfaceOrientationOverride);
+    else
+        orientation = _page->deviceOrientation();
+
+    _page->dynamicViewportSizeUpdate(WebCore::FloatSize(minimumLayoutSize), WebCore::FloatSize(minimumLayoutSizeForMinimalUI), WebCore::FloatSize(maximumUnobscuredSize), visibleRectInContentCoordinates, unobscuredRectInContentCoordinates, futureUnobscuredRectInSelfCoordinates, targetScale, orientation);
 }
 
 - (void)_endAnimatedResize
index 06456c2..051034e 100644 (file)
@@ -108,6 +108,10 @@ typedef NS_OPTIONS(NSUInteger, _WKFindOptions) {
 // Define the inset of the scrollview unusable by the web page.
 @property (nonatomic, setter=_setObscuredInsets:) UIEdgeInsets _obscuredInsets;
 
+// Override the interface orientation. Clients using _beginAnimatedResizeWithUpdates: must update the interface orientation
+// in the update block.
+@property (nonatomic, setter=_setInterfaceOrientationOverride:) UIInterfaceOrientation _interfaceOrientationOverride;
+
 @property (nonatomic, setter=_setBackgroundExtendsBeyondPage:) BOOL _backgroundExtendsBeyondPage;
 
 // FIXME: Remove these three properties once we expose WKWebViewContentProvider as API.
index c55599a..ebc7315 100644 (file)
@@ -273,6 +273,7 @@ WebPageProxy::WebPageProxy(PageClient& pageClient, WebProcessProxy& process, uin
     , m_mainFrame(nullptr)
     , m_userAgent(standardUserAgent())
 #if PLATFORM(IOS)
+    , m_deviceOrientation(0)
     , m_dynamicViewportSizeUpdateInProgress(false)
 #endif
     , m_geolocationPermissionRequestManager(*this)
index c755b11..b1451bb 100644 (file)
@@ -595,12 +595,14 @@ public:
     enum class UnobscuredRectConstraint { ConstrainedToDocumentRect, Unconstrained };
     WebCore::FloatRect computeCustomFixedPositionRect(const WebCore::FloatRect& unobscuredContentRect, double displayedContentScale, UnobscuredRectConstraint = UnobscuredRectConstraint::Unconstrained) const;
 
-    void dynamicViewportSizeUpdate(const WebCore::FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const WebCore::FloatRect& targetExposedContentRect, const WebCore::FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double targetScale);
+    void dynamicViewportSizeUpdate(const WebCore::FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const WebCore::FloatRect& targetExposedContentRect, const WebCore::FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double targetScale, int32_t deviceOrientation);
     void synchronizeDynamicViewportUpdate();
 
     void setViewportConfigurationMinimumLayoutSize(const WebCore::FloatSize&);
     void setViewportConfigurationMinimumLayoutSizeForMinimalUI(const WebCore::FloatSize&);
     void setMaximumUnobscuredSize(const WebCore::FloatSize&);
+    void setDeviceOrientation(int32_t);
+    int32_t deviceOrientation() const { return m_deviceOrientation; }
     void didCommitLayerTree(const WebKit::RemoteLayerTreeTransaction&);
 
     void selectWithGesture(const WebCore::IntPoint, WebCore::TextGranularity, uint32_t gestureType, uint32_t gestureState, PassRefPtr<GestureCallback>);
@@ -1490,6 +1492,7 @@ private:
 #if PLATFORM(IOS)
     RefPtr<WebVideoFullscreenManagerProxy> m_videoFullscreenManager;
     VisibleContentRectUpdateInfo m_lastVisibleContentRectUpdate;
+    int32_t m_deviceOrientation;
     bool m_dynamicViewportSizeUpdateInProgress;
 #endif
 
index 396c4c1..5c6fe45 100644 (file)
@@ -236,10 +236,10 @@ WebCore::FloatRect WebPageProxy::computeCustomFixedPositionRect(const FloatRect&
     return FrameView::rectForViewportConstrainedObjects(enclosingLayoutRect(constrainedUnobscuredRect), roundedLayoutSize(contentsSize), displayedContentScale, false, StickToViewportBounds);
 }
 
-void WebPageProxy::dynamicViewportSizeUpdate(const FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const FloatRect& targetExposedContentRect, const FloatRect& targetUnobscuredRect, const FloatRect& targetUnobscuredRectInScrollViewCoordinates,  double targetScale)
+void WebPageProxy::dynamicViewportSizeUpdate(const FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const FloatRect& targetExposedContentRect, const FloatRect& targetUnobscuredRect, const FloatRect& targetUnobscuredRectInScrollViewCoordinates,  double targetScale, int32_t deviceOrientation)
 {
     m_dynamicViewportSizeUpdateInProgress = true;
-    m_process->send(Messages::WebPage::DynamicViewportSizeUpdate(minimumLayoutSize, minimumLayoutSizeForMinimalUI, maximumUnobscuredSize, targetExposedContentRect, targetUnobscuredRect, targetUnobscuredRectInScrollViewCoordinates, targetScale), m_pageID);
+    m_process->send(Messages::WebPage::DynamicViewportSizeUpdate(minimumLayoutSize, minimumLayoutSizeForMinimalUI, maximumUnobscuredSize, targetExposedContentRect, targetUnobscuredRect, targetUnobscuredRectInScrollViewCoordinates, targetScale, deviceOrientation), m_pageID);
 }
 
 void WebPageProxy::synchronizeDynamicViewportUpdate()
@@ -282,6 +282,15 @@ void WebPageProxy::setMaximumUnobscuredSize(const WebCore::FloatSize& size)
     m_process->send(Messages::WebPage::SetMaximumUnobscuredSize(size), m_pageID);
 }
 
+void WebPageProxy::setDeviceOrientation(int32_t deviceOrientation)
+{
+    if (deviceOrientation != m_deviceOrientation) {
+        m_deviceOrientation = deviceOrientation;
+        if (isValid())
+            m_process->send(Messages::WebPage::SetDeviceOrientation(deviceOrientation), m_pageID);
+    }
+}
+
 void WebPageProxy::didCommitLayerTree(const WebKit::RemoteLayerTreeTransaction& layerTreeTransaction)
 {
     m_pageExtendedBackgroundColor = layerTreeTransaction.pageExtendedBackgroundColor();
index 8f82349..cc85389 100644 (file)
@@ -182,6 +182,10 @@ private:
     virtual void showPlaybackTargetPicker(bool hasVideo) override;
 #endif
 
+#if ENABLE(ORIENTATION_EVENTS)
+    virtual int deviceOrientation() const override;
+#endif
+
     virtual void runOpenPanel(WebCore::Frame*, PassRefPtr<WebCore::FileChooser>) override;
     virtual void loadIconForFiles(const Vector<String>&, WebCore::FileIconLoader*) override;
 
index 6de835e..e95eb52 100644 (file)
@@ -129,6 +129,11 @@ void WebChromeClient::showPlaybackTargetPicker(bool hasVideo)
     m_page->send(Messages::WebPageProxy::ShowPlaybackTargetPicker(hasVideo, m_page->rectForElementAtInteractionLocation()));
 }
 
+int WebChromeClient::deviceOrientation() const
+{
+    return m_page->deviceOrientation();
+}
+
 } // namespace WebKit
 
 #endif // PLATFORM(IOS)
index bf43091..39eca28 100644 (file)
@@ -301,6 +301,7 @@ WebPage::WebPage(uint64_t pageID, const WebPageCreationParameters& parameters)
     , m_hasPendingBlurNotification(false)
     , m_screenSize(parameters.screenSize)
     , m_availableScreenSize(parameters.availableScreenSize)
+    , m_deviceOrientation(0)
     , m_inDynamicSizeUpdate(false)
 #endif
     , m_inspectorClient(0)
index 76fb361..d5a9f06 100644 (file)
@@ -451,6 +451,7 @@ public:
 #if PLATFORM(IOS)
     WebCore::FloatSize screenSize() const;
     WebCore::FloatSize availableScreenSize() const;
+    int32_t deviceOrientation() const { return m_deviceOrientation; }
     void viewportPropertiesDidChange(const WebCore::ViewportArguments&);
     void didReceiveMobileDocType(bool);
     void restorePageState(double scale, bool userHasChangedPageScaleFactor, const WebCore::IntPoint& exposedOrigin);
@@ -724,7 +725,8 @@ public:
     void setViewportConfigurationMinimumLayoutSize(const WebCore::FloatSize&);
     void setViewportConfigurationMinimumLayoutSizeForMinimalUI(const WebCore::FloatSize&);
     void setMaximumUnobscuredSize(const WebCore::FloatSize&);
-    void dynamicViewportSizeUpdate(const WebCore::FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const WebCore::FloatRect& targetExposedContentRect, const WebCore::FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double scale);
+    void setDeviceOrientation(int32_t);
+    void dynamicViewportSizeUpdate(const WebCore::FloatSize& minimumLayoutSize, const WebCore::FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const WebCore::FloatRect& targetExposedContentRect, const WebCore::FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double scale, int32_t deviceOrientation);
     void synchronizeDynamicViewportUpdate(double& newTargetScale, WebCore::FloatPoint& newScrollPosition);
     void updateVisibleContentRects(const VisibleContentRectUpdateInfo&);
     bool scaleWasSetByUIProcess() const { return m_scaleWasSetByUIProcess; }
@@ -1218,6 +1220,7 @@ private:
     RefPtr<WebCore::Range> m_currentBlockSelection;
     WebCore::IntSize m_blockSelectionDesiredSize;
     WebCore::FloatSize m_maximumUnobscuredSize;
+    int32_t m_deviceOrientation;
     bool m_inDynamicSizeUpdate;
     HashMap<std::pair<WebCore::IntSize, double>, WebCore::IntPoint> m_dynamicSizeUpdateHistory;
     RefPtr<WebCore::Node> m_pendingSyntheticClickNode;
index 636de7d..cf034f3 100644 (file)
@@ -46,7 +46,8 @@ messages -> WebPage LegacyReceiver {
     SetViewportConfigurationMinimumLayoutSize(WebCore::FloatSize size)
     SetViewportConfigurationMinimumLayoutSizeForMinimalUI(WebCore::FloatSize size)
     SetMaximumUnobscuredSize(WebCore::FloatSize size)
-    DynamicViewportSizeUpdate(WebCore::FloatSize minimumLayoutSize, WebCore::FloatSize minimumLayoutSizeForMinimalUI,  WebCore::FloatSize maximumUnobscuredSize, WebCore::FloatRect targetExposedContentRect, WebCore::FloatRect targetUnobscuredRect, WebCore::FloatRect targetUnobscuredRectInScrollViewCoordinates, double scale)
+    SetDeviceOrientation(int32_t deviceOrientation)
+    DynamicViewportSizeUpdate(WebCore::FloatSize minimumLayoutSize, WebCore::FloatSize minimumLayoutSizeForMinimalUI,  WebCore::FloatSize maximumUnobscuredSize, WebCore::FloatRect targetExposedContentRect, WebCore::FloatRect targetUnobscuredRect, WebCore::FloatRect targetUnobscuredRectInScrollViewCoordinates, double scale, int32_t deviceOrientation)
     SynchronizeDynamicViewportUpdate() -> (double newTargetScale, WebCore::FloatPoint newScrollPosition)
 
     HandleTap(WebCore::IntPoint point)
index 8e37571..e29a70f 100644 (file)
@@ -1957,6 +1957,14 @@ void WebPage::setMaximumUnobscuredSize(const FloatSize& maximumUnobscuredSize)
     updateViewportSizeForCSSViewportUnits();
 }
 
+void WebPage::setDeviceOrientation(int32_t deviceOrientation)
+{
+    if (deviceOrientation == m_deviceOrientation)
+        return;
+    m_deviceOrientation = deviceOrientation;
+    m_page->mainFrame().orientationChanged();
+}
+
 static inline bool withinEpsilon(float a, float b)
 {
     return fabs(a - b) < std::numeric_limits<float>::epsilon();
@@ -1975,7 +1983,7 @@ void WebPage::resetTextAutosizingBeforeLayoutIfNeeded(const FloatSize& oldSize,
     }
 }
 
-void WebPage::dynamicViewportSizeUpdate(const FloatSize& minimumLayoutSize, const FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const FloatRect& targetExposedContentRect, const FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double targetScale)
+void WebPage::dynamicViewportSizeUpdate(const FloatSize& minimumLayoutSize, const FloatSize& minimumLayoutSizeForMinimalUI, const WebCore::FloatSize& maximumUnobscuredSize, const FloatRect& targetExposedContentRect, const FloatRect& targetUnobscuredRect, const WebCore::FloatRect& targetUnobscuredRectInScrollViewCoordinates, double targetScale, int32_t deviceOrientation)
 {
     TemporaryChange<bool> dynamicSizeUpdateGuard(m_inDynamicSizeUpdate, true);
     // FIXME: this does not handle the cases where the content would change the content size or scroll position from JavaScript.
@@ -2157,6 +2165,7 @@ void WebPage::dynamicViewportSizeUpdate(const FloatSize& minimumLayoutSize, cons
     FloatSize unobscuredContentRectSizeInContentCoordinates = newUnobscuredContentRect.size();
     unobscuredContentRectSizeInContentCoordinates.scale(scale);
     frameView.setCustomSizeForResizeEvent(expandedIntSize(unobscuredContentRectSizeInContentCoordinates));
+    setDeviceOrientation(deviceOrientation);
     frameView.setScrollOffset(roundedUnobscuredContentRect.location());
 
     send(Messages::WebPageProxy::DynamicViewportUpdateChangedTarget(pageScaleFactor(), frameView.scrollPosition()));