diff options
author | Simon Hausmann <simon.hausmann@nokia.com> | 2012-05-11 09:43:24 +0200 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@nokia.com> | 2012-05-11 09:43:24 +0200 |
commit | 1b914638db989aaa98631a1c1e02c7b2d44805d8 (patch) | |
tree | 87f4fd2c7b38db320079a5de8877890d2ca3c485 /Source/WebKit2/UIProcess | |
parent | 2cf6c8816a73e0132bd8fa3b509d62d7c51b6e47 (diff) | |
download | qtwebkit-1b914638db989aaa98631a1c1e02c7b2d44805d8.tar.gz |
Imported WebKit commit 9a52e27980f47e8b0d8f8b7cc0fd7b5741bceb92 (http://svn.webkit.org/repository/webkit/trunk@116736)
New snapshot to include QDeclarative* -> QQml* build fixes
Diffstat (limited to 'Source/WebKit2/UIProcess')
40 files changed, 799 insertions, 336 deletions
diff --git a/Source/WebKit2/UIProcess/API/C/WKPage.h b/Source/WebKit2/UIProcess/API/C/WKPage.h index a6d8a661a..aeefee796 100644 --- a/Source/WebKit2/UIProcess/API/C/WKPage.h +++ b/Source/WebKit2/UIProcess/API/C/WKPage.h @@ -27,6 +27,7 @@ #define WKPage_h #include <WebKit2/WKBase.h> +#include <WebKit2/WKError.h> #include <WebKit2/WKEvent.h> #include <WebKit2/WKFindOptions.h> #include <WebKit2/WKGeometry.h> @@ -69,9 +70,12 @@ typedef bool (*WKPageCanAuthenticateAgainstProtectionSpaceInFrameCallback)(WKPag typedef void (*WKPageDidReceiveAuthenticationChallengeInFrameCallback)(WKPageRef page, WKFrameRef frame, WKAuthenticationChallengeRef authenticationChallenge, const void *clientInfo); typedef void (*WKPageDidChangeBackForwardListCallback)(WKPageRef page, WKBackForwardListItemRef addedItem, WKArrayRef removedItems, const void *clientInfo); typedef bool (*WKPageShouldGoToBackForwardListItemCallback)(WKPageRef page, WKBackForwardListItemRef item, const void *clientInfo); -typedef void (*WKPageDidFailToInitializePluginCallback)(WKPageRef page, WKStringRef mimeType, const void* clientInfo); typedef void (*WKPageDidNewFirstVisuallyNonEmptyLayoutCallback)(WKPageRef page, WKTypeRef userData, const void *clientInfo); typedef void (*WKPageWillGoToBackForwardListItemCallback)(WKPageRef page, WKBackForwardListItemRef item, WKTypeRef userData, const void *clientInfo); +typedef void (*WKPagePluginDidFailCallback)(WKPageRef page, WKErrorCode errorCode, WKStringRef mimeType, const void* clientInfo); + +// Deprecated +typedef void (*WKPageDidFailToInitializePluginCallback_deprecatedForUseWithV0)(WKPageRef page, WKStringRef mimeType, const void* clientInfo); struct WKPageLoaderClient { int version; @@ -104,7 +108,7 @@ struct WKPageLoaderClient { WKPageCallback processDidCrash; WKPageDidChangeBackForwardListCallback didChangeBackForwardList; WKPageShouldGoToBackForwardListItemCallback shouldGoToBackForwardListItem; - WKPageDidFailToInitializePluginCallback didFailToInitializePlugin; + WKPageDidFailToInitializePluginCallback_deprecatedForUseWithV0 didFailToInitializePlugin_deprecatedForUseWithV0; // Version 1 WKPageDidDetectXSSForFrameCallback didDetectXSSForFrame; @@ -115,6 +119,7 @@ struct WKPageLoaderClient { WKPageWillGoToBackForwardListItemCallback willGoToBackForwardListItem; WKPageCallback interactionOccurredWhileProcessUnresponsive; + WKPagePluginDidFailCallback pluginDidFail; }; typedef struct WKPageLoaderClient WKPageLoaderClient; @@ -172,6 +177,13 @@ typedef struct WKPageResourceLoadClient WKPageResourceLoadClient; enum { kWKPageResourceLoadClientCurrentVersion = 0 }; +enum { + kWKPluginUnavailabilityReasonPluginMissing, + kWKPluginUnavailabilityReasonPluginCrashed, + kWKPluginUnavailabilityReasonInsecurePluginVersion +}; +typedef uint32_t WKPluginUnavailabilityReason; + // UI Client typedef WKPageRef (*WKPageCreateNewPageCallback)(WKPageRef page, WKURLRequestRef urlRequest, WKDictionaryRef features, WKEventModifiers modifiers, WKEventMouseButton mouseButton, const void *clientInfo); typedef void (*WKPageRunJavaScriptAlertCallback)(WKPageRef page, WKStringRef alertText, WKFrameRef frame, const void *clientInfo); @@ -182,7 +194,6 @@ typedef void (*WKPageFocusCallback)(WKPageRef page, const void *clientInfo); typedef void (*WKPageUnfocusCallback)(WKPageRef page, const void *clientInfo); typedef void (*WKPageSetStatusTextCallback)(WKPageRef page, WKStringRef text, const void *clientInfo); typedef void (*WKPageMouseDidMoveOverElementCallback)(WKPageRef page, WKHitTestResultRef hitTestResult, WKEventModifiers modifiers, WKTypeRef userData, const void *clientInfo); -typedef void (*WKPageMissingPluginButtonClickedCallback)(WKPageRef page, WKStringRef mimeType, WKStringRef url, WKStringRef pluginsPageURL, const void* clientInfo); typedef void (*WKPageDidNotHandleKeyEventCallback)(WKPageRef page, WKNativeEventPtr event, const void *clientInfo); typedef void (*WKPageDidNotHandleWheelEventCallback)(WKPageRef page, WKNativeEventPtr event, const void *clientInfo); typedef bool (*WKPageGetToolbarsAreVisibleCallback)(WKPageRef page, const void *clientInfo); @@ -207,10 +218,12 @@ typedef void (*WKPagePrintFrameCallback)(WKPageRef page, WKFrameRef frame, const typedef void (*WKPageSaveDataToFileInDownloadsFolderCallback)(WKPageRef page, WKStringRef suggestedFilename, WKStringRef mimeType, WKURLRef originatingURL, WKDataRef data, const void* clientInfo); typedef bool (*WKPageShouldInterruptJavaScriptCallback)(WKPageRef page, const void *clientInfo); typedef void (*WKPageDecidePolicyForNotificationPermissionRequestCallback)(WKPageRef page, WKSecurityOriginRef origin, WKNotificationPermissionRequestRef permissionRequest, const void *clientInfo); +typedef void (*WKPageUnavailablePluginButtonClickedCallback)(WKPageRef page, WKPluginUnavailabilityReason pluginUnavailabilityReason, WKStringRef mimeType, WKStringRef url, WKStringRef pluginsPageURL, const void* clientInfo); // Deprecated typedef WKPageRef (*WKPageCreateNewPageCallback_deprecatedForUseWithV0)(WKPageRef page, WKDictionaryRef features, WKEventModifiers modifiers, WKEventMouseButton mouseButton, const void *clientInfo); typedef void (*WKPageMouseDidMoveOverElementCallback_deprecatedForUseWithV0)(WKPageRef page, WKEventModifiers modifiers, WKTypeRef userData, const void *clientInfo); +typedef void (*WKPageMissingPluginButtonClickedCallback_deprecatedForUseWithV0)(WKPageRef page, WKStringRef mimeType, WKStringRef url, WKStringRef pluginsPageURL, const void* clientInfo); struct WKPageUIClient { int version; @@ -228,7 +241,7 @@ struct WKPageUIClient { WKPageRunJavaScriptPromptCallback runJavaScriptPrompt; WKPageSetStatusTextCallback setStatusText; WKPageMouseDidMoveOverElementCallback_deprecatedForUseWithV0 mouseDidMoveOverElement_deprecatedForUseWithV0; - WKPageMissingPluginButtonClickedCallback missingPluginButtonClicked; + WKPageMissingPluginButtonClickedCallback_deprecatedForUseWithV0 missingPluginButtonClicked_deprecatedForUseWithV0; WKPageDidNotHandleKeyEventCallback didNotHandleKeyEvent; WKPageDidNotHandleWheelEventCallback didNotHandleWheelEvent; WKPageGetToolbarsAreVisibleCallback toolbarsAreVisible; @@ -261,6 +274,7 @@ struct WKPageUIClient { WKPageCreateNewPageCallback createNewPage; WKPageMouseDidMoveOverElementCallback mouseDidMoveOverElement; WKPageDecidePolicyForNotificationPermissionRequestCallback decidePolicyForNotificationPermissionRequest; + WKPageUnavailablePluginButtonClickedCallback unavailablePluginButtonClicked; }; typedef struct WKPageUIClient WKPageUIClient; diff --git a/Source/WebKit2/UIProcess/API/gtk/WebKitLoaderClient.cpp b/Source/WebKit2/UIProcess/API/gtk/WebKitLoaderClient.cpp index c26d8ebe9..9476255c8 100644 --- a/Source/WebKit2/UIProcess/API/gtk/WebKitLoaderClient.cpp +++ b/Source/WebKit2/UIProcess/API/gtk/WebKitLoaderClient.cpp @@ -145,7 +145,9 @@ void attachLoaderClientToView(WebKitWebView* webView) 0, // shouldGoToBackForwardListItem 0, // didFailToInitializePlugin 0, // didDetectXSSForFrame - 0 // didFirstVisuallyNonEmptyLayoutForFrame + 0, // didFirstVisuallyNonEmptyLayoutForFrame + 0, // willGoToBackForwardListItem + 0 // interactionOccurredWhileProcessUnresponsive }; WKPageRef wkPage = toAPI(webkitWebViewBaseGetPage(WEBKIT_WEB_VIEW_BASE(webView))); WKPageSetPageLoaderClient(wkPage, &wkLoaderClient); diff --git a/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.cpp b/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.cpp index 8bec722b3..5c027044b 100644 --- a/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.cpp +++ b/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.cpp @@ -106,7 +106,9 @@ enum { PROP_ENABLE_WEBAUDIO, PROP_ENABLE_WEBGL, PROP_ZOOM_TEXT_ONLY, - PROP_JAVASCRIPT_CAN_ACCESS_CLIPBOARD + PROP_JAVASCRIPT_CAN_ACCESS_CLIPBOARD, + PROP_MEDIA_PLAYBACK_REQUIRES_USER_GESTURE, + PROP_MEDIA_PLAYBACK_ALLOWS_INLINE }; static void webKitSettingsSetProperty(GObject* object, guint propId, const GValue* value, GParamSpec* paramSpec) @@ -219,6 +221,12 @@ static void webKitSettingsSetProperty(GObject* object, guint propId, const GValu case PROP_JAVASCRIPT_CAN_ACCESS_CLIPBOARD: webkit_settings_set_javascript_can_access_clipboard(settings, g_value_get_boolean(value)); break; + case PROP_MEDIA_PLAYBACK_REQUIRES_USER_GESTURE: + webkit_settings_set_media_playback_requires_user_gesture(settings, g_value_get_boolean(value)); + break; + case PROP_MEDIA_PLAYBACK_ALLOWS_INLINE: + webkit_settings_set_media_playback_allows_inline(settings, g_value_get_boolean(value)); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, propId, paramSpec); break; @@ -335,6 +343,12 @@ static void webKitSettingsGetProperty(GObject* object, guint propId, GValue* val case PROP_JAVASCRIPT_CAN_ACCESS_CLIPBOARD: g_value_set_boolean(value, webkit_settings_get_javascript_can_access_clipboard(settings)); break; + case PROP_MEDIA_PLAYBACK_REQUIRES_USER_GESTURE: + g_value_set_boolean(value, webkit_settings_get_media_playback_requires_user_gesture(settings)); + break; + case PROP_MEDIA_PLAYBACK_ALLOWS_INLINE: + g_value_set_boolean(value, webkit_settings_get_media_playback_allows_inline(settings)); + break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, propId, paramSpec); break; @@ -862,6 +876,38 @@ static void webkit_settings_class_init(WebKitSettingsClass* klass) FALSE, readWriteConstructParamFlags)); + /** + * WebKitSettings:media-playback-requires-user-gesture: + * + * Whether a user gesture (such as clicking the play button) + * would be required to start media playback or load media. This is off + * by default, so media playback could start automatically. + * Setting it on requires a gesture by the user to start playback, or to + * load the media. + */ + g_object_class_install_property(gObjectClass, + PROP_MEDIA_PLAYBACK_REQUIRES_USER_GESTURE, + g_param_spec_boolean("media-playback-requires-user-gesture", + _("Media playback requires user gesture"), + _("Whether media playback requires user gesture"), + FALSE, + readWriteConstructParamFlags)); + + /** + * WebKitSettings:media-playback-allows-inline + * + * Whether media playback is full-screen only or inline playback is allowed. + * This is %TRUE by default, so media playback can be inline. Setting it to + * %FALSE allows specifying that media playback should be always fullscreen. + */ + g_object_class_install_property(gObjectClass, + PROP_MEDIA_PLAYBACK_ALLOWS_INLINE, + g_param_spec_boolean("media-playback-allows-inline", + _("Media playback allows inline"), + _("Whether media playback allows inline"), + TRUE, + readWriteConstructParamFlags)); + g_type_class_add_private(klass, sizeof(WebKitSettingsPrivate)); } @@ -2193,3 +2239,77 @@ void webkit_settings_set_javascript_can_access_clipboard(WebKitSettings* setting g_object_notify(G_OBJECT(settings), "javascript-can-access-clipboard"); } + +/** + * webkit_settings_set_media_playback_requires_user_gesture: + * @settings: a #WebKitSettings + * @enabled: Value to be set + * + * Set the #WebKitSettings:media-playback-requires-user-gesture property. + */ +void webkit_settings_set_media_playback_requires_user_gesture(WebKitSettings* settings, gboolean enabled) +{ + g_return_if_fail(WEBKIT_IS_SETTINGS(settings)); + + WebKitSettingsPrivate* priv = settings->priv; + bool currentValue = WKPreferencesGetMediaPlaybackRequiresUserGesture(priv->preferences.get()); + if (currentValue == enabled) + return; + + WKPreferencesSetMediaPlaybackRequiresUserGesture(priv->preferences.get(), enabled); + + g_object_notify(G_OBJECT(settings), "media-playback-requires-user-gesture"); +} + +/** + * webkit_settings_get_media_playback_requires_user_gesture: + * @settings: a #WebKitSettings + * + * Get the #WebKitSettings:media-playback-requires-user-gesture property. + * + * Returns: %TRUE If an user gesture is needed to play or load media + * or %FALSE if no user gesture is needed. + */ +gboolean webkit_settings_get_media_playback_requires_user_gesture(WebKitSettings* settings) +{ + g_return_val_if_fail(WEBKIT_IS_SETTINGS(settings), FALSE); + + return WKPreferencesGetMediaPlaybackRequiresUserGesture(settings->priv->preferences.get()); +} + +/** + * webkit_settings_set_media_playback_allows_inline: + * @settings: a #WebKitSettings + * @enabled: Value to be set + * + * Set the #WebKitSettings:media-playback-allows-inline property. + */ +void webkit_settings_set_media_playback_allows_inline(WebKitSettings* settings, gboolean enabled) +{ + g_return_if_fail(WEBKIT_IS_SETTINGS(settings)); + + WebKitSettingsPrivate* priv = settings->priv; + bool currentValue = WKPreferencesGetMediaPlaybackAllowsInline(priv->preferences.get()); + if (currentValue == enabled) + return; + + WKPreferencesSetMediaPlaybackAllowsInline(priv->preferences.get(), enabled); + + g_object_notify(G_OBJECT(settings), "media-playback-allows-inline"); +} + +/** + * webkit_settings_get_media_playback_allows_inline: + * @settings: a #WebKitSettings + * + * Get the #WebKitSettings:media-playback-allows-inline property. + * + * Returns: %TRUE If inline playback is allowed for media + * or %FALSE if only fullscreen playback is allowed. + */ +gboolean webkit_settings_get_media_playback_allows_inline(WebKitSettings* settings) +{ + g_return_val_if_fail(WEBKIT_IS_SETTINGS(settings), TRUE); + + return WKPreferencesGetMediaPlaybackAllowsInline(settings->priv->preferences.get()); +} diff --git a/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.h b/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.h index 57bf3f17d..fda7089d0 100644 --- a/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.h +++ b/Source/WebKit2/UIProcess/API/gtk/WebKitSettings.h @@ -321,6 +321,19 @@ WEBKIT_API void webkit_settings_set_javascript_can_access_clipboard (WebKitSettings *settings, gboolean enabled); +WEBKIT_API gboolean +webkit_settings_get_media_playback_requires_user_gesture (WebKitSettings *settings); + +WEBKIT_API void +webkit_settings_set_media_playback_requires_user_gesture (WebKitSettings *settings, + gboolean enabled); + +WEBKIT_API gboolean +webkit_settings_get_media_playback_allows_inline (WebKitSettings *settings); + +WEBKIT_API void +webkit_settings_set_media_playback_allows_inline (WebKitSettings *settings, + gboolean enabled); G_END_DECLS #endif /* WebKitSettings_h */ diff --git a/Source/WebKit2/UIProcess/API/gtk/docs/webkit2gtk-sections.txt b/Source/WebKit2/UIProcess/API/gtk/docs/webkit2gtk-sections.txt index dc5e65ac6..f5e15d9b2 100644 --- a/Source/WebKit2/UIProcess/API/gtk/docs/webkit2gtk-sections.txt +++ b/Source/WebKit2/UIProcess/API/gtk/docs/webkit2gtk-sections.txt @@ -251,6 +251,10 @@ webkit_settings_get_zoom_text_only webkit_settings_set_zoom_text_only webkit_settings_get_javascript_can_access_clipboard webkit_settings_set_javascript_can_access_clipboard +webkit_settings_get_media_playback_requires_user_gesture +webkit_settings_set_media_playback_requires_user_gesture +webkit_settings_get_media_playback_allows_inline +webkit_settings_set_media_playback_allows_inline <SUBSECTION Standard> WebKitSettingsClass diff --git a/Source/WebKit2/UIProcess/API/gtk/tests/TestResources.cpp b/Source/WebKit2/UIProcess/API/gtk/tests/TestResources.cpp index cc272c9e8..e08cfb9c9 100644 --- a/Source/WebKit2/UIProcess/API/gtk/tests/TestResources.cpp +++ b/Source/WebKit2/UIProcess/API/gtk/tests/TestResources.cpp @@ -207,7 +207,7 @@ static void testWebViewResources(ResourcesTest* test, gconstpointer) #endif // Reload. - webkit_web_view_reload(test->m_webView); + webkit_web_view_reload_bypass_cache(test->m_webView); test->waitUntilResourcesLoaded(4); } diff --git a/Source/WebKit2/UIProcess/API/gtk/tests/TestWebKitSettings.cpp b/Source/WebKit2/UIProcess/API/gtk/tests/TestWebKitSettings.cpp index 19491c201..ad03444ae 100644 --- a/Source/WebKit2/UIProcess/API/gtk/tests/TestWebKitSettings.cpp +++ b/Source/WebKit2/UIProcess/API/gtk/tests/TestWebKitSettings.cpp @@ -209,6 +209,16 @@ static void testWebKitSettings(Test*, gconstpointer) webkit_settings_set_javascript_can_access_clipboard(settings, TRUE); g_assert(webkit_settings_get_javascript_can_access_clipboard(settings)); + // By default, media playback doesn't require user gestures. + g_assert(!webkit_settings_get_media_playback_requires_user_gesture(settings)); + webkit_settings_set_media_playback_requires_user_gesture(settings, TRUE); + g_assert(webkit_settings_get_media_playback_requires_user_gesture(settings)); + + // By default, inline media playback is allowed + g_assert(webkit_settings_get_media_playback_allows_inline(settings)); + webkit_settings_set_media_playback_allows_inline(settings, FALSE); + g_assert(!webkit_settings_get_media_playback_allows_inline(settings)); + g_object_unref(G_OBJECT(settings)); } diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp b/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp index b1b465526..167c50f6a 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp @@ -27,6 +27,7 @@ #include "QtDownloadManager.h" #include "QtViewportInteractionEngine.h" #include "QtWebContext.h" +#include "QtWebError.h" #include "QtWebIconDatabaseClient.h" #include "QtWebPageEventHandler.h" #include "QtWebPageLoadClient.h" @@ -52,10 +53,14 @@ #include "qwebviewportinfo_p.h" #include <JavaScriptCore/InitializeThreading.h> +#include <JavaScriptCore/JSBase.h> +#include <JavaScriptCore/JSRetainPtr.h> #include <QDateTime> +#include <QtQml/QJSValue> +#include <WKOpenPanelResultListener.h> +#include <WKSerializedScriptValue.h> #include <WebCore/IntPoint.h> #include <WebCore/IntRect.h> -#include <WKOpenPanelResultListener.h> #include <wtf/Assertions.h> #include <wtf/MainThread.h> #include <wtf/text/WTFString.h> @@ -68,6 +73,105 @@ static const int kAxisLockSampleCount = 5; static const qreal kAxisLockVelocityThreshold = 300; static const qreal kAxisLockVelocityDirectionThreshold = 50; +struct JSCallbackClosure { + QPointer<QObject> receiver; + QByteArray method; + QJSValue value; +}; + +static inline QString toQString(JSStringRef string) +{ + return QString(reinterpret_cast<const QChar*>(JSStringGetCharactersPtr(string)), JSStringGetLength(string)); +} + +static inline QJSValue toQJSValue(JSStringRef string) +{ + return QJSValue(toQString(string)); +} + +static QJSValue buildQJSValue(QJSEngine* engine, JSGlobalContextRef context, JSValueRef value, int depth) +{ + QJSValue var; + JSValueRef exception = 0; + + if (depth > 10) + return var; + + switch (JSValueGetType(context, value)) { + case kJSTypeBoolean: + var = QJSValue(JSValueToBoolean(context, value)); + break; + case kJSTypeNumber: + { + double number = JSValueToNumber(context, value, &exception); + if (!exception) + var = QJSValue(number); + } + break; + case kJSTypeString: + { + JSRetainPtr<JSStringRef> string = JSValueToStringCopy(context, value, &exception); + if (!exception) + var = toQJSValue(string.get()); + } + break; + case kJSTypeObject: + { + JSObjectRef obj = JSValueToObject(context, value, &exception); + + JSPropertyNameArrayRef names = JSObjectCopyPropertyNames(context, obj); + size_t length = JSPropertyNameArrayGetCount(names); + + var = engine->newObject(); + + for (size_t i = 0; i < length; ++i) { + JSRetainPtr<JSStringRef> name = JSPropertyNameArrayGetNameAtIndex(names, i); + JSValueRef property = JSObjectGetProperty(context, obj, name.get(), &exception); + + if (!exception) { + QJSValue value = buildQJSValue(engine, context, property, depth + 1); + var.setProperty(toQString(name.get()), value); + } + } + } + break; + } + return var; +} + +static void javaScriptCallback(WKSerializedScriptValueRef valueRef, WKErrorRef, void* data) +{ + JSCallbackClosure* closure = reinterpret_cast<JSCallbackClosure*>(data); + + if (closure->method.size()) + QMetaObject::invokeMethod(closure->receiver, closure->method); + else { + QJSValue function = closure->value; + + // If a callable function is supplied, we build a JavaScript value accessible + // in the QML engine, and calls the function with that. + if (function.isCallable()) { + QJSValue var; + if (valueRef) { + // FIXME: Slow but OK for now. + JSGlobalContextRef context = JSGlobalContextCreate(0); + + JSValueRef exception = 0; + JSValueRef value = WKSerializedScriptValueDeserialize(valueRef, context, &exception); + var = buildQJSValue(function.engine(), context, value, /* depth */ 0); + + JSGlobalContextRelease(context); + } + + QList<QJSValue> args; + args.append(var); + function.call(args); + } + } + + delete closure; +} + static QQuickWebViewPrivate* createPrivateObject(QQuickWebView* publicObject) { if (s_flickableViewportEnabled) @@ -162,6 +266,7 @@ QQuickWebViewPrivate::QQuickWebViewPrivate(QQuickWebView* viewport) , m_navigatorQtObjectEnabled(false) , m_renderToOffscreenBuffer(false) , m_dialogActive(false) + , m_loadProgress(0) { viewport->setClip(true); viewport->setPixelAligned(true); @@ -230,20 +335,72 @@ QPointF QQuickWebViewPrivate::pageItemPos() \qmlsignal WebView::loadingChanged(WebLoadRequest request) */ +void QQuickWebViewPrivate::provisionalLoadDidStart(const QUrl& url) +{ + Q_Q(QQuickWebView); + + QWebLoadRequest loadRequest(url, QQuickWebView::LoadStartedStatus); + emit q->loadingChanged(&loadRequest); +} + +void QQuickWebViewPrivate::loadDidCommit() +{ + Q_Q(QQuickWebView); + ASSERT(q->loading()); + + emit q->navigationHistoryChanged(); + emit q->urlChanged(); + emit q->titleChanged(); +} + +void QQuickWebViewPrivate::didSameDocumentNavigation() +{ + Q_Q(QQuickWebView); + + emit q->navigationHistoryChanged(); + emit q->urlChanged(); +} + +void QQuickWebViewPrivate::titleDidChange() +{ + Q_Q(QQuickWebView); + + emit q->titleChanged(); +} + +void QQuickWebViewPrivate::loadProgressDidChange(int loadProgress) +{ + Q_Q(QQuickWebView); + + if (!loadProgress) + setIcon(QUrl()); + + m_loadProgress = loadProgress; + + emit q->loadProgressChanged(); +} + +void QQuickWebViewPrivate::backForwardListDidChange() +{ + navigationHistory->d->reset(); +} + void QQuickWebViewPrivate::loadDidSucceed() { Q_Q(QQuickWebView); ASSERT(!q->loading()); + QWebLoadRequest loadRequest(q->url(), QQuickWebView::LoadSucceededStatus); emit q->loadingChanged(&loadRequest); } -void QQuickWebViewPrivate::onComponentComplete() +void QQuickWebViewPrivate::loadDidFail(const QtWebError& error) { - if (m_deferedUrlToLoad.isEmpty()) - return; + Q_Q(QQuickWebView); + ASSERT(!q->loading()); - q_ptr->setUrl(m_deferedUrlToLoad); + QWebLoadRequest loadRequest(error.url(), QQuickWebView::LoadFailedStatus, error.description(), static_cast<QQuickWebView::ErrorDomain>(error.type()), error.errorCode()); + emit q->loadingChanged(&loadRequest); } void QQuickWebViewPrivate::setNeedsDisplay() @@ -269,18 +426,22 @@ void QQuickWebViewPrivate::_q_onIconChangedForPageURL(const QUrl& pageURL, const setIcon(iconURL); } -void QQuickWebViewPrivate::didChangeBackForwardList() -{ - navigationHistory->d->reset(); -} - void QQuickWebViewPrivate::processDidCrash() { - pageView->eventHandler()->resetGestureRecognizers(); - pageLoadClient->completeLoadWhenProcessDidCrashIfNeeded(); + Q_Q(QQuickWebView); QUrl url(KURL(WebCore::ParsedURLString, webPageProxy->urlAtProcessExit())); qWarning("WARNING: The web process experienced a crash on '%s'.", qPrintable(url.toString(QUrl::RemoveUserInfo))); + + pageView->eventHandler()->resetGestureRecognizers(); + + // Check if loading was ongoing, when process crashed. + if (m_loadProgress > 0 && m_loadProgress < 100) { + QWebLoadRequest loadRequest(url, QQuickWebView::LoadFailedStatus, QLatin1String("The web process crashed."), QQuickWebView::InternalErrorDomain, 0); + + loadProgressDidChange(100); + emit q->loadingChanged(&loadRequest); + } } void QQuickWebViewPrivate::didRelaunchProcess() @@ -328,7 +489,7 @@ void QQuickWebViewPrivate::_q_onReceivedResponseFromDownload(QWebDownloadItem* d return; Q_Q(QQuickWebView); - QDeclarativeEngine::setObjectOwnership(downloadItem, QDeclarativeEngine::JavaScriptOwnership); + QQmlEngine::setObjectOwnership(downloadItem, QQmlEngine::JavaScriptOwnership); emit q->experimental()->downloadRequested(downloadItem); } @@ -626,7 +787,6 @@ void QQuickWebViewLegacyPrivate::setZoomFactor(qreal factor) QQuickWebViewFlickablePrivate::QQuickWebViewFlickablePrivate(QQuickWebView* viewport) : QQuickWebViewPrivate(viewport) , pageIsSuspended(true) - , loadSuccessDispatchIsPending(false) { // Disable mouse events on the flickable web view so we do not // select text during pan gestures on platforms which send both @@ -689,44 +849,16 @@ void QQuickWebViewFlickablePrivate::onComponentComplete() _q_resume(); - if (loadSuccessDispatchIsPending) { - QQuickWebViewPrivate::loadDidSucceed(); - loadSuccessDispatchIsPending = false; - } - // Trigger setting of correct visibility flags after everything was allocated and initialized. _q_onVisibleChanged(); - - QQuickWebViewPrivate::onComponentComplete(); -} - -void QQuickWebViewFlickablePrivate::loadDidSucceed() -{ - if (interactionEngine) - QQuickWebViewPrivate::loadDidSucceed(); - else - loadSuccessDispatchIsPending = true; -} - -void QQuickWebViewFlickablePrivate::loadDidCommit() -{ - // Due to entering provisional load before committing, we - // might actually be suspended here. -} - -void QQuickWebViewFlickablePrivate::didFinishFirstNonEmptyLayout() -{ } void QQuickWebViewFlickablePrivate::didChangeViewportProperties(const WebCore::ViewportAttributes& newAttributes) { Q_Q(QQuickWebView); - QSize viewportSize = q->boundingRect().size().toSize(); - // FIXME: Revise these when implementing fit-to-width. WebCore::ViewportAttributes attr = newAttributes; - WebCore::restrictMinimumScaleFactorToViewportSize(attr, viewportSize); WebCore::restrictScaleFactorToInitialScaleIfNotUserScalable(attr); // FIXME: Resetting here can reset more than needed. For instance it will end deferrers. @@ -814,8 +946,20 @@ void QQuickWebViewFlickablePrivate::pageDidRequestScroll(const QPoint& pos) void QQuickWebViewFlickablePrivate::didChangeContentsSize(const QSize& newSize) { Q_Q(QQuickWebView); + QSize viewportSize = q->boundingRect().size().toSize(); + pageView->setContentsSize(newSize); q->experimental()->viewportInfo()->didUpdateContentsSize(); + + float minimumScale = WebCore::computeMinimumScaleFactorForContentContained(attributes, viewportSize, newSize); + + if (!qFuzzyCompare(minimumScale, attributes.minimumScale)) { + interactionEngine->setCSSScaleBounds(minimumScale, attributes.maximumScale); + q->experimental()->viewportInfo()->didUpdateViewportConstraints(); + + if (!interactionEngine->hadUserInteraction() && !pageIsSuspended) + interactionEngine->setCSSScale(minimumScale); + } } /*! @@ -955,13 +1099,13 @@ void QQuickWebViewExperimental::postMessage(const QString& message) d->context->postMessageToNavigatorQtObject(d->webPageProxy.get(), message); } -QDeclarativeComponent* QQuickWebViewExperimental::alertDialog() const +QQmlComponent* QQuickWebViewExperimental::alertDialog() const { Q_D(const QQuickWebView); return d->alertDialog; } -void QQuickWebViewExperimental::setAlertDialog(QDeclarativeComponent* alertDialog) +void QQuickWebViewExperimental::setAlertDialog(QQmlComponent* alertDialog) { Q_D(QQuickWebView); if (d->alertDialog == alertDialog) @@ -970,13 +1114,13 @@ void QQuickWebViewExperimental::setAlertDialog(QDeclarativeComponent* alertDialo emit alertDialogChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::confirmDialog() const +QQmlComponent* QQuickWebViewExperimental::confirmDialog() const { Q_D(const QQuickWebView); return d->confirmDialog; } -void QQuickWebViewExperimental::setConfirmDialog(QDeclarativeComponent* confirmDialog) +void QQuickWebViewExperimental::setConfirmDialog(QQmlComponent* confirmDialog) { Q_D(QQuickWebView); if (d->confirmDialog == confirmDialog) @@ -990,7 +1134,7 @@ QWebNavigationHistory* QQuickWebViewExperimental::navigationHistory() const return d_ptr->navigationHistory.get(); } -QDeclarativeComponent* QQuickWebViewExperimental::promptDialog() const +QQmlComponent* QQuickWebViewExperimental::promptDialog() const { Q_D(const QQuickWebView); return d->promptDialog; @@ -1004,7 +1148,7 @@ QWebPreferences* QQuickWebViewExperimental::preferences() const return d->preferences.get(); } -void QQuickWebViewExperimental::setPromptDialog(QDeclarativeComponent* promptDialog) +void QQuickWebViewExperimental::setPromptDialog(QQmlComponent* promptDialog) { Q_D(QQuickWebView); if (d->promptDialog == promptDialog) @@ -1013,13 +1157,13 @@ void QQuickWebViewExperimental::setPromptDialog(QDeclarativeComponent* promptDia emit promptDialogChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::authenticationDialog() const +QQmlComponent* QQuickWebViewExperimental::authenticationDialog() const { Q_D(const QQuickWebView); return d->authenticationDialog; } -void QQuickWebViewExperimental::setAuthenticationDialog(QDeclarativeComponent* authenticationDialog) +void QQuickWebViewExperimental::setAuthenticationDialog(QQmlComponent* authenticationDialog) { Q_D(QQuickWebView); if (d->authenticationDialog == authenticationDialog) @@ -1028,13 +1172,13 @@ void QQuickWebViewExperimental::setAuthenticationDialog(QDeclarativeComponent* a emit authenticationDialogChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::proxyAuthenticationDialog() const +QQmlComponent* QQuickWebViewExperimental::proxyAuthenticationDialog() const { Q_D(const QQuickWebView); return d->proxyAuthenticationDialog; } -void QQuickWebViewExperimental::setProxyAuthenticationDialog(QDeclarativeComponent* proxyAuthenticationDialog) +void QQuickWebViewExperimental::setProxyAuthenticationDialog(QQmlComponent* proxyAuthenticationDialog) { Q_D(QQuickWebView); if (d->proxyAuthenticationDialog == proxyAuthenticationDialog) @@ -1042,13 +1186,13 @@ void QQuickWebViewExperimental::setProxyAuthenticationDialog(QDeclarativeCompone d->proxyAuthenticationDialog = proxyAuthenticationDialog; emit proxyAuthenticationDialogChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::certificateVerificationDialog() const +QQmlComponent* QQuickWebViewExperimental::certificateVerificationDialog() const { Q_D(const QQuickWebView); return d->certificateVerificationDialog; } -void QQuickWebViewExperimental::setCertificateVerificationDialog(QDeclarativeComponent* certificateVerificationDialog) +void QQuickWebViewExperimental::setCertificateVerificationDialog(QQmlComponent* certificateVerificationDialog) { Q_D(QQuickWebView); if (d->certificateVerificationDialog == certificateVerificationDialog) @@ -1057,13 +1201,13 @@ void QQuickWebViewExperimental::setCertificateVerificationDialog(QDeclarativeCom emit certificateVerificationDialogChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::itemSelector() const +QQmlComponent* QQuickWebViewExperimental::itemSelector() const { Q_D(const QQuickWebView); return d->itemSelector; } -void QQuickWebViewExperimental::setItemSelector(QDeclarativeComponent* itemSelector) +void QQuickWebViewExperimental::setItemSelector(QQmlComponent* itemSelector) { Q_D(QQuickWebView); if (d->itemSelector == itemSelector) @@ -1072,13 +1216,13 @@ void QQuickWebViewExperimental::setItemSelector(QDeclarativeComponent* itemSelec emit itemSelectorChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::filePicker() const +QQmlComponent* QQuickWebViewExperimental::filePicker() const { Q_D(const QQuickWebView); return d->filePicker; } -void QQuickWebViewExperimental::setFilePicker(QDeclarativeComponent* filePicker) +void QQuickWebViewExperimental::setFilePicker(QQmlComponent* filePicker) { Q_D(QQuickWebView); if (d->filePicker == filePicker) @@ -1087,13 +1231,13 @@ void QQuickWebViewExperimental::setFilePicker(QDeclarativeComponent* filePicker) emit filePickerChanged(); } -QDeclarativeComponent* QQuickWebViewExperimental::databaseQuotaDialog() const +QQmlComponent* QQuickWebViewExperimental::databaseQuotaDialog() const { Q_D(const QQuickWebView); return d->databaseQuotaDialog; } -void QQuickWebViewExperimental::setDatabaseQuotaDialog(QDeclarativeComponent* databaseQuotaDialog) +void QQuickWebViewExperimental::setDatabaseQuotaDialog(QQmlComponent* databaseQuotaDialog) { Q_D(QQuickWebView); if (d->databaseQuotaDialog == databaseQuotaDialog) @@ -1171,7 +1315,25 @@ void QQuickWebViewExperimental::setDevicePixelRatio(double devicePixelRatio) emit devicePixelRatioChanged(); } -QQuickUrlSchemeDelegate* QQuickWebViewExperimental::schemeDelegates_At(QDeclarativeListProperty<QQuickUrlSchemeDelegate>* property, int index) +/*! + \internal + + \qmlmethod void WebViewExperimental::evaluateJavaScript(string script [, function(result)]) + + \brief Evaluates the specified JavaScript and, if supplied, calls a function with the result. +*/ + +void QQuickWebViewExperimental::evaluateJavaScript(const QString& script, const QJSValue& value) +{ + JSCallbackClosure* closure = new JSCallbackClosure; + + closure->receiver = this; + closure->value = value; + + d_ptr->webPageProxy.get()->runJavaScriptInMainFrame(script, ScriptValueCallback::create(closure, javaScriptCallback)); +} + +QQuickUrlSchemeDelegate* QQuickWebViewExperimental::schemeDelegates_At(QQmlListProperty<QQuickUrlSchemeDelegate>* property, int index) { const QObjectList children = property->object->children(); if (index < children.count()) @@ -1179,7 +1341,7 @@ QQuickUrlSchemeDelegate* QQuickWebViewExperimental::schemeDelegates_At(QDeclarat return 0; } -void QQuickWebViewExperimental::schemeDelegates_Append(QDeclarativeListProperty<QQuickUrlSchemeDelegate>* property, QQuickUrlSchemeDelegate *scheme) +void QQuickWebViewExperimental::schemeDelegates_Append(QQmlListProperty<QQuickUrlSchemeDelegate>* property, QQuickUrlSchemeDelegate *scheme) { QObject* schemeParent = property->object; scheme->setParent(schemeParent); @@ -1191,12 +1353,12 @@ void QQuickWebViewExperimental::schemeDelegates_Append(QDeclarativeListProperty< d->webPageProxy->registerApplicationScheme(scheme->scheme()); } -int QQuickWebViewExperimental::schemeDelegates_Count(QDeclarativeListProperty<QQuickUrlSchemeDelegate>* property) +int QQuickWebViewExperimental::schemeDelegates_Count(QQmlListProperty<QQuickUrlSchemeDelegate>* property) { return property->object->children().count(); } -void QQuickWebViewExperimental::schemeDelegates_Clear(QDeclarativeListProperty<QQuickUrlSchemeDelegate>* property) +void QQuickWebViewExperimental::schemeDelegates_Clear(QQmlListProperty<QQuickUrlSchemeDelegate>* property) { const QObjectList children = property->object->children(); for (int index = 0; index < children.count(); index++) { @@ -1206,9 +1368,9 @@ void QQuickWebViewExperimental::schemeDelegates_Clear(QDeclarativeListProperty<Q } } -QDeclarativeListProperty<QQuickUrlSchemeDelegate> QQuickWebViewExperimental::schemeDelegates() +QQmlListProperty<QQuickUrlSchemeDelegate> QQuickWebViewExperimental::schemeDelegates() { - return QDeclarativeListProperty<QQuickUrlSchemeDelegate>(schemeParent, 0, + return QQmlListProperty<QQuickUrlSchemeDelegate>(schemeParent, 0, QQuickWebViewExperimental::schemeDelegates_Append, QQuickWebViewExperimental::schemeDelegates_Count, QQuickWebViewExperimental::schemeDelegates_At, @@ -1336,11 +1498,6 @@ void QQuickWebView::setUrl(const QUrl& url) if (url.isEmpty()) return; - if (!isComponentComplete()) { - d->m_deferedUrlToLoad = url; - return; - } - d->webPageProxy->loadURL(url.toString()); } @@ -1360,7 +1517,7 @@ QUrl QQuickWebView::icon() const int QQuickWebView::loadProgress() const { Q_D(const QQuickWebView); - return d->pageLoadClient->loadProgress(); + return d->loadProgress(); } bool QQuickWebView::canGoBack() const @@ -1725,24 +1882,14 @@ void QQuickWebView::setZoomFactor(qreal factor) d->setZoomFactor(factor); } -struct JSCallbackClosure { - QPointer<QObject> receiver; - QByteArray method; -}; - -static void javaScriptCallback(WKSerializedScriptValueRef, WKErrorRef, void* context) -{ - JSCallbackClosure* closure = reinterpret_cast<JSCallbackClosure*>(context); - QMetaObject::invokeMethod(closure->receiver, closure->method); - delete closure; -} - void QQuickWebView::runJavaScriptInMainFrame(const QString &script, QObject *receiver, const char *method) { Q_D(QQuickWebView); + JSCallbackClosure* closure = new JSCallbackClosure; closure->receiver = receiver; closure->method = method; + d->webPageProxy.get()->runJavaScriptInMainFrame(script, ScriptValueCallback::create(closure, javaScriptCallback)); } diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p.h b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p.h index 916f2282d..4bdd0fbbd 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p.h @@ -28,7 +28,7 @@ #include <private/qquickflickable_p.h> class QWebNavigationRequest; -class QDeclarativeComponent; +class QQmlComponent; class QQuickWebPage; class QQuickWebViewAttached; class QWebLoadRequest; @@ -65,11 +65,12 @@ QT_BEGIN_NAMESPACE class QPainter; class QUrl; class QQuickFlickable; +class QJSValue; QT_END_NAMESPACE // Instantiating the WebView in C++ is only possible by creating -// a QDeclarativeComponent as the initialization depends on the +// a QQmlComponent as the initialization depends on the // componentComplete method being called. class QWEBKIT_EXPORT QQuickWebView : public QQuickFlickable { Q_OBJECT @@ -252,18 +253,18 @@ class QWEBKIT_EXPORT QQuickWebViewExperimental : public QObject { Q_PROPERTY(int preferredMinimumContentsWidth WRITE setPreferredMinimumContentsWidth READ preferredMinimumContentsWidth) Q_PROPERTY(QWebNavigationHistory* navigationHistory READ navigationHistory CONSTANT FINAL) - Q_PROPERTY(QDeclarativeComponent* alertDialog READ alertDialog WRITE setAlertDialog NOTIFY alertDialogChanged) - Q_PROPERTY(QDeclarativeComponent* confirmDialog READ confirmDialog WRITE setConfirmDialog NOTIFY confirmDialogChanged) - Q_PROPERTY(QDeclarativeComponent* promptDialog READ promptDialog WRITE setPromptDialog NOTIFY promptDialogChanged) - Q_PROPERTY(QDeclarativeComponent* authenticationDialog READ authenticationDialog WRITE setAuthenticationDialog NOTIFY authenticationDialogChanged) - Q_PROPERTY(QDeclarativeComponent* proxyAuthenticationDialog READ proxyAuthenticationDialog WRITE setProxyAuthenticationDialog NOTIFY proxyAuthenticationDialogChanged) - Q_PROPERTY(QDeclarativeComponent* certificateVerificationDialog READ certificateVerificationDialog WRITE setCertificateVerificationDialog NOTIFY certificateVerificationDialogChanged) - Q_PROPERTY(QDeclarativeComponent* itemSelector READ itemSelector WRITE setItemSelector NOTIFY itemSelectorChanged) - Q_PROPERTY(QDeclarativeComponent* filePicker READ filePicker WRITE setFilePicker NOTIFY filePickerChanged) - Q_PROPERTY(QDeclarativeComponent* databaseQuotaDialog READ databaseQuotaDialog WRITE setDatabaseQuotaDialog NOTIFY databaseQuotaDialogChanged) + Q_PROPERTY(QQmlComponent* alertDialog READ alertDialog WRITE setAlertDialog NOTIFY alertDialogChanged) + Q_PROPERTY(QQmlComponent* confirmDialog READ confirmDialog WRITE setConfirmDialog NOTIFY confirmDialogChanged) + Q_PROPERTY(QQmlComponent* promptDialog READ promptDialog WRITE setPromptDialog NOTIFY promptDialogChanged) + Q_PROPERTY(QQmlComponent* authenticationDialog READ authenticationDialog WRITE setAuthenticationDialog NOTIFY authenticationDialogChanged) + Q_PROPERTY(QQmlComponent* proxyAuthenticationDialog READ proxyAuthenticationDialog WRITE setProxyAuthenticationDialog NOTIFY proxyAuthenticationDialogChanged) + Q_PROPERTY(QQmlComponent* certificateVerificationDialog READ certificateVerificationDialog WRITE setCertificateVerificationDialog NOTIFY certificateVerificationDialogChanged) + Q_PROPERTY(QQmlComponent* itemSelector READ itemSelector WRITE setItemSelector NOTIFY itemSelectorChanged) + Q_PROPERTY(QQmlComponent* filePicker READ filePicker WRITE setFilePicker NOTIFY filePickerChanged) + Q_PROPERTY(QQmlComponent* databaseQuotaDialog READ databaseQuotaDialog WRITE setDatabaseQuotaDialog NOTIFY databaseQuotaDialogChanged) Q_PROPERTY(QWebPreferences* preferences READ preferences CONSTANT FINAL) Q_PROPERTY(QWebViewportInfo* viewportInfo READ viewportInfo CONSTANT FINAL) - Q_PROPERTY(QDeclarativeListProperty<QQuickUrlSchemeDelegate> urlSchemeDelegates READ schemeDelegates) + Q_PROPERTY(QQmlListProperty<QQuickUrlSchemeDelegate> urlSchemeDelegates READ schemeDelegates) Q_PROPERTY(QString userAgent READ userAgent WRITE setUserAgent NOTIFY userAgentChanged) Q_PROPERTY(double devicePixelRatio READ devicePixelRatio WRITE setDevicePixelRatio NOTIFY devicePixelRatioChanged) Q_ENUMS(NavigationRequestActionExperimental) @@ -276,24 +277,24 @@ public: QQuickWebViewExperimental(QQuickWebView* webView); virtual ~QQuickWebViewExperimental(); - QDeclarativeComponent* alertDialog() const; - void setAlertDialog(QDeclarativeComponent*); - QDeclarativeComponent* confirmDialog() const; - void setConfirmDialog(QDeclarativeComponent*); - QDeclarativeComponent* promptDialog() const; - void setPromptDialog(QDeclarativeComponent*); - QDeclarativeComponent* authenticationDialog() const; - void setAuthenticationDialog(QDeclarativeComponent*); - QDeclarativeComponent* certificateVerificationDialog() const; - void setCertificateVerificationDialog(QDeclarativeComponent*); - QDeclarativeComponent* itemSelector() const; - void setItemSelector(QDeclarativeComponent*); - QDeclarativeComponent* proxyAuthenticationDialog() const; - void setProxyAuthenticationDialog(QDeclarativeComponent*); - QDeclarativeComponent* filePicker() const; - void setFilePicker(QDeclarativeComponent*); - QDeclarativeComponent* databaseQuotaDialog() const; - void setDatabaseQuotaDialog(QDeclarativeComponent*); + QQmlComponent* alertDialog() const; + void setAlertDialog(QQmlComponent*); + QQmlComponent* confirmDialog() const; + void setConfirmDialog(QQmlComponent*); + QQmlComponent* promptDialog() const; + void setPromptDialog(QQmlComponent*); + QQmlComponent* authenticationDialog() const; + void setAuthenticationDialog(QQmlComponent*); + QQmlComponent* certificateVerificationDialog() const; + void setCertificateVerificationDialog(QQmlComponent*); + QQmlComponent* itemSelector() const; + void setItemSelector(QQmlComponent*); + QQmlComponent* proxyAuthenticationDialog() const; + void setProxyAuthenticationDialog(QQmlComponent*); + QQmlComponent* filePicker() const; + void setFilePicker(QQmlComponent*); + QQmlComponent* databaseQuotaDialog() const; + void setDatabaseQuotaDialog(QQmlComponent*); QString userAgent() const; void setUserAgent(const QString& userAgent); double devicePixelRatio() const; @@ -305,11 +306,11 @@ public: QWebNavigationHistory* navigationHistory() const; QQuickWebPage* page(); - static QQuickUrlSchemeDelegate* schemeDelegates_At(QDeclarativeListProperty<QQuickUrlSchemeDelegate>*, int index); - static void schemeDelegates_Append(QDeclarativeListProperty<QQuickUrlSchemeDelegate>*, QQuickUrlSchemeDelegate*); - static int schemeDelegates_Count(QDeclarativeListProperty<QQuickUrlSchemeDelegate>*); - static void schemeDelegates_Clear(QDeclarativeListProperty<QQuickUrlSchemeDelegate>*); - QDeclarativeListProperty<QQuickUrlSchemeDelegate> schemeDelegates(); + static QQuickUrlSchemeDelegate* schemeDelegates_At(QQmlListProperty<QQuickUrlSchemeDelegate>*, int index); + static void schemeDelegates_Append(QQmlListProperty<QQuickUrlSchemeDelegate>*, QQuickUrlSchemeDelegate*); + static int schemeDelegates_Count(QQmlListProperty<QQuickUrlSchemeDelegate>*); + static void schemeDelegates_Clear(QQmlListProperty<QQuickUrlSchemeDelegate>*); + QQmlListProperty<QQuickUrlSchemeDelegate> schemeDelegates(); void invokeApplicationSchemeHandler(WTF::PassRefPtr<WebKit::QtRefCountedNetworkRequestData>); void sendApplicationSchemeReply(QQuickNetworkReply*); @@ -332,6 +333,7 @@ public Q_SLOTS: void goBackTo(int index); void goForwardTo(int index); void postMessage(const QString&); + void evaluateJavaScript(const QString& script, const QJSValue& value = QJSValue()); Q_SIGNALS: void alertDialogChanged(); diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h index 417618d0a..de62d39bb 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h @@ -41,6 +41,7 @@ class DrawingAreaProxy; class QtDialogRunner; class QtViewportInteractionEngine; class QtWebContext; +class QtWebError; class QtWebPageLoadClient; class QtWebPagePolicyClient; class WebPageProxy; @@ -50,7 +51,7 @@ class QWebNavigationHistory; class QWebViewportInfo; QT_BEGIN_NAMESPACE -class QDeclarativeComponent; +class QQmlComponent; QT_END_NAMESPACE class QQuickWebViewPrivate { @@ -67,19 +68,26 @@ public: virtual void initialize(WKContextRef contextRef = 0, WKPageGroupRef pageGroupRef = 0); + virtual void onComponentComplete() { } + virtual void enableMouseEvents() { } virtual void disableMouseEvents() { } virtual QPointF pageItemPos(); virtual void updateContentsSize(const QSizeF&) { } + virtual void provisionalLoadDidStart(const QUrl& url); + virtual void loadDidCommit(); + virtual void didSameDocumentNavigation(); + virtual void titleDidChange(); + virtual void loadProgressDidChange(int loadProgress); + virtual void backForwardListDidChange(); virtual void loadDidSucceed(); - virtual void onComponentComplete(); - virtual void loadDidCommit() { } - virtual void didFinishFirstNonEmptyLayout() { } + virtual void loadDidFail(const WebKit::QtWebError& error); + virtual void didChangeViewportProperties(const WebCore::ViewportAttributes& attr) { } - void didChangeBackForwardList(); + int loadProgress() const { return m_loadProgress; } void setNeedsDisplay(); virtual WebKit::QtViewportInteractionEngine* viewportInteractionEngine() { return 0; } @@ -175,15 +183,15 @@ protected: FlickableAxisLocker axisLocker; - QDeclarativeComponent* alertDialog; - QDeclarativeComponent* confirmDialog; - QDeclarativeComponent* promptDialog; - QDeclarativeComponent* authenticationDialog; - QDeclarativeComponent* certificateVerificationDialog; - QDeclarativeComponent* itemSelector; - QDeclarativeComponent* proxyAuthenticationDialog; - QDeclarativeComponent* filePicker; - QDeclarativeComponent* databaseQuotaDialog; + QQmlComponent* alertDialog; + QQmlComponent* confirmDialog; + QQmlComponent* promptDialog; + QQmlComponent* authenticationDialog; + QQmlComponent* certificateVerificationDialog; + QQmlComponent* itemSelector; + QQmlComponent* proxyAuthenticationDialog; + QQmlComponent* filePicker; + QQmlComponent* databaseQuotaDialog; WebCore::ViewportAttributes attributes; @@ -192,7 +200,7 @@ protected: bool m_renderToOffscreenBuffer; bool m_dialogActive; QUrl m_iconURL; - QUrl m_deferedUrlToLoad; + int m_loadProgress; }; class QQuickWebViewLegacyPrivate : public QQuickWebViewPrivate { @@ -216,13 +224,11 @@ public: virtual ~QQuickWebViewFlickablePrivate(); virtual void initialize(WKContextRef contextRef = 0, WKPageGroupRef pageGroupRef = 0); + virtual void onComponentComplete(); + virtual QPointF pageItemPos(); virtual void updateContentsSize(const QSizeF&); - virtual void loadDidSucceed(); - virtual void onComponentComplete(); - virtual void loadDidCommit(); - virtual void didFinishFirstNonEmptyLayout(); virtual void didChangeViewportProperties(const WebCore::ViewportAttributes&); virtual WebKit::QtViewportInteractionEngine* viewportInteractionEngine() { return interactionEngine.data(); } virtual void updateViewportSize(); @@ -237,7 +243,6 @@ public: private: QScopedPointer<WebKit::QtViewportInteractionEngine> interactionEngine; bool pageIsSuspended; - bool loadSuccessDispatchIsPending; }; #endif // qquickwebview_p_p_h diff --git a/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider.cpp b/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider.cpp index dce6ee9df..71342a1e3 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider.cpp @@ -29,7 +29,7 @@ using namespace WebKit; QWebIconImageProvider::QWebIconImageProvider() - : QDeclarativeImageProvider(QDeclarativeImageProvider::Image) + : QQuickImageProvider(QQuickImageProvider::Image) { } diff --git a/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider_p.h b/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider_p.h index 74f55995f..a54008a2c 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qwebiconimageprovider_p.h @@ -23,7 +23,7 @@ #include "qwebkitglobal.h" #include <QtQuick/QQuickImageProvider> -class QWEBKIT_EXPORT QWebIconImageProvider : public QDeclarativeImageProvider { +class QWEBKIT_EXPORT QWebIconImageProvider : public QQuickImageProvider { public: QWebIconImageProvider(); ~QWebIconImageProvider(); diff --git a/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo.cpp b/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo.cpp index 170604d1d..ea16732f5 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo.cpp @@ -62,11 +62,17 @@ QVariant QWebViewportInfo::initialScale() const QVariant QWebViewportInfo::minimumScale() const { + if (QtViewportInteractionEngine* interactionEngine = m_webViewPrivate->viewportInteractionEngine()) + return interactionEngine->m_minimumScale; + return m_webViewPrivate->attributes.minimumScale; } QVariant QWebViewportInfo::maximumScale() const { + if (QtViewportInteractionEngine* interactionEngine = m_webViewPrivate->viewportInteractionEngine()) + return interactionEngine->m_maximumScale; + return m_webViewPrivate->attributes.maximumScale; } diff --git a/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo_p.h b/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo_p.h index ab422e4e7..d3060bbe6 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qwebviewportinfo_p.h @@ -27,7 +27,7 @@ #include <QtCore/QPointer> #include <QtCore/QSize> #include <QtCore/QVariant> -#include <QtDeclarative/QtDeclarative> +#include <QtQml/QtQml> class QQuickWebViewPrivate; diff --git a/Source/WebKit2/UIProcess/API/qt/tests/qmltests/WebView/tst_evaluateJavaScript.qml b/Source/WebKit2/UIProcess/API/qt/tests/qmltests/WebView/tst_evaluateJavaScript.qml new file mode 100644 index 000000000..a3083144d --- /dev/null +++ b/Source/WebKit2/UIProcess/API/qt/tests/qmltests/WebView/tst_evaluateJavaScript.qml @@ -0,0 +1,87 @@ +import QtQuick 2.0 +import QtTest 1.0 +import QtWebKit 3.0 +import QtWebKit.experimental 1.0 +import "../common" + +Item { + TestWebView { + id: webView + property variant lastMessage + property variant lastResult + + signal resultReceived + + experimental.preferences.navigatorQtObjectEnabled: true + experimental.onMessageReceived: { + lastMessage = message + } + } + + SignalSpy { + id: messageSpy + target: webView.experimental + signalName: "messageReceived" + } + + SignalSpy { + id: resultSpy + target: webView + signalName: "resultReceived" + } + + TestCase { + name: "JavaScriptEvaluation" + + function init() { + messageSpy.clear() + webView.lastMessage = null + + resultSpy.clear() + webView.lastResult = null + } + + function test_basic() { + messageSpy.clear() + webView.url = "about:blank" + verify(webView.waitForLoadSucceeded()) + + webView.experimental.evaluateJavaScript( + "navigator.qt.onmessage = function(message) {" + + " var result = message.data.split('');" + + " result = result.reverse().join('');" + + " navigator.qt.postMessage(result);" + + "}"); + + webView.experimental.postMessage("DLROW OLLEH"); + messageSpy.wait() + compare(webView.lastMessage.data, "HELLO WORLD") + } + + function test_propertyObjectWithChild() { + messageSpy.clear() + webView.url = "about:blank" + verify(webView.waitForLoadSucceeded()) + + webView.experimental.evaluateJavaScript( + "(function() {" + + " var parent = new Object;" + + " var child = new Object;" + + " parent['level'] = '1';" + + " child['level'] = 2;" + + " parent['child'] = child;" + + " return parent;" + + "})()", + + function(result) { + webView.lastResult = result + webView.resultReceived() + }); + + resultSpy.wait() + + compare(JSON.stringify(webView.lastResult), + '{"child":{"level":2},"level":"1"}') + } + } +} diff --git a/Source/WebKit2/UIProcess/API/qt/tests/tests.pri b/Source/WebKit2/UIProcess/API/qt/tests/tests.pri index ded493f88..358a2328c 100644 --- a/Source/WebKit2/UIProcess/API/qt/tests/tests.pri +++ b/Source/WebKit2/UIProcess/API/qt/tests/tests.pri @@ -10,7 +10,7 @@ SOURCES += ../util.cpp \ ../bytearraytestdata.cpp INCLUDEPATH += $$PWD -QT += testlib declarative quick quick-private webkit +QT += testlib qml quick quick-private webkit DEFINES += TESTS_SOURCE_DIR=\\\"$$PWD\\\" \ QWP_PATH=\\\"$${ROOT_BUILD_DIR}/bin\\\" diff --git a/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.cpp b/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.cpp index 6519441b0..0fd295dcc 100644 --- a/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.cpp +++ b/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.cpp @@ -245,6 +245,17 @@ void DrawingAreaProxyImpl::exitAcceleratedCompositingMode(uint64_t backingStoreS incorporateUpdate(updateInfo); } +void DrawingAreaProxyImpl::updateAcceleratedCompositingMode(uint64_t backingStoreStateID, const LayerTreeContext& layerTreeContext) +{ + ASSERT_ARG(backingStoreStateID, backingStoreStateID <= m_currentBackingStoreStateID); + if (backingStoreStateID < m_currentBackingStoreStateID) + return; + +#if USE(ACCELERATED_COMPOSITING) + updateAcceleratedCompositingMode(layerTreeContext); +#endif +} + void DrawingAreaProxyImpl::incorporateUpdate(const UpdateInfo& updateInfo) { ASSERT(!isInAcceleratedCompositingMode()); @@ -368,6 +379,14 @@ void DrawingAreaProxyImpl::exitAcceleratedCompositingMode() m_layerTreeContext = LayerTreeContext(); m_webPageProxy->exitAcceleratedCompositingMode(); } + +void DrawingAreaProxyImpl::updateAcceleratedCompositingMode(const LayerTreeContext& layerTreeContext) +{ + ASSERT(isInAcceleratedCompositingMode()); + + m_layerTreeContext = layerTreeContext; + m_webPageProxy->updateAcceleratedCompositingMode(layerTreeContext); +} #endif void DrawingAreaProxyImpl::pageCustomRepresentationChanged() diff --git a/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.h b/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.h index c67cd93da..346f3546d 100644 --- a/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.h +++ b/Source/WebKit2/UIProcess/DrawingAreaProxyImpl.h @@ -65,6 +65,7 @@ private: virtual void didUpdateBackingStoreState(uint64_t backingStoreStateID, const UpdateInfo&, const LayerTreeContext&); virtual void enterAcceleratedCompositingMode(uint64_t backingStoreStateID, const LayerTreeContext&); virtual void exitAcceleratedCompositingMode(uint64_t backingStoreStateID, const UpdateInfo&); + virtual void updateAcceleratedCompositingMode(uint64_t backingStoreStateID, const LayerTreeContext&); void incorporateUpdate(const UpdateInfo&); @@ -76,6 +77,7 @@ private: #if USE(ACCELERATED_COMPOSITING) void enterAcceleratedCompositingMode(const LayerTreeContext&); void exitAcceleratedCompositingMode(); + void updateAcceleratedCompositingMode(const LayerTreeContext&); bool isInAcceleratedCompositingMode() const { return !m_layerTreeContext.isEmpty(); } diff --git a/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.cpp b/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.cpp index cef14dcf0..97775c626 100644 --- a/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.cpp +++ b/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.cpp @@ -174,6 +174,11 @@ static inline String pathExtension(const KURL& url) } #if !PLATFORM(MAC) +bool PluginInfoStore::shouldBlockPlugin(const PluginModuleInfo&) const +{ + return false; +} + String PluginInfoStore::getMIMETypeForExtension(const String& extension) { return MIMETypeRegistry::getMIMETypeForExtension(extension); diff --git a/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.h b/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.h index 4bfecb424..f30303c83 100644 --- a/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.h +++ b/Source/WebKit2/UIProcess/Plugins/PluginInfoStore.h @@ -53,8 +53,11 @@ public: // Returns the info for the plug-in with the given path. PluginModuleInfo infoForPluginWithPath(const String& pluginPath) const; -private: + // Return whether this plug-in should be blocked from being instantiated. + // Note that the plug-in will still be seen by e.g. navigator.plugins + bool shouldBlockPlugin(const PluginModuleInfo&) const; +private: PluginModuleInfo findPluginForMIMEType(const String& mimeType) const; PluginModuleInfo findPluginForExtension(const String& extension, String& mimeType) const; diff --git a/Source/WebKit2/UIProcess/Plugins/mac/PluginInfoStoreMac.mm b/Source/WebKit2/UIProcess/Plugins/mac/PluginInfoStoreMac.mm index 6c6040781..7a04b5355 100644 --- a/Source/WebKit2/UIProcess/Plugins/mac/PluginInfoStoreMac.mm +++ b/Source/WebKit2/UIProcess/Plugins/mac/PluginInfoStoreMac.mm @@ -89,6 +89,11 @@ bool PluginInfoStore::shouldUsePlugin(Vector<PluginModuleInfo>& alreadyLoadedPlu return true; } +bool PluginInfoStore::shouldBlockPlugin(const PluginModuleInfo& plugin) const +{ + return WKShouldBlockPlugin(plugin.bundleIdentifier, plugin.versionString); +} + String PluginInfoStore::getMIMETypeForExtension(const String& extension) { // FIXME: This should just call MIMETypeRegistry::getMIMETypeForExtension and be diff --git a/Source/WebKit2/UIProcess/WebContext.cpp b/Source/WebKit2/UIProcess/WebContext.cpp index f1a0f0fb7..b6258ece1 100644 --- a/Source/WebKit2/UIProcess/WebContext.cpp +++ b/Source/WebKit2/UIProcess/WebContext.cpp @@ -620,7 +620,7 @@ void WebContext::getPlugins(bool refresh, Vector<PluginInfo>& pluginInfos) #endif } -void WebContext::getPluginPath(const String& mimeType, const String& urlString, String& pluginPath) +void WebContext::getPluginPath(const String& mimeType, const String& urlString, String& pluginPath, bool& blocked) { MESSAGE_CHECK_URL(urlString); @@ -630,6 +630,12 @@ void WebContext::getPluginPath(const String& mimeType, const String& urlString, if (!plugin.path) return; + blocked = false; + if (pluginInfoStore().shouldBlockPlugin(plugin)) { + blocked = true; + return; + } + pluginPath = plugin.path; } diff --git a/Source/WebKit2/UIProcess/WebContext.h b/Source/WebKit2/UIProcess/WebContext.h index ddf3d7932..f94dc4a28 100644 --- a/Source/WebKit2/UIProcess/WebContext.h +++ b/Source/WebKit2/UIProcess/WebContext.h @@ -217,7 +217,7 @@ private: // Plugins void getPlugins(bool refresh, Vector<WebCore::PluginInfo>&); - void getPluginPath(const String& mimeType, const String& urlString, String& pluginPath); + void getPluginPath(const String& mimeType, const String& urlString, String& pluginPath, bool& blocked); #if !ENABLE(PLUGIN_PROCESS) void didGetSitesWithPluginData(const Vector<String>& sites, uint64_t callbackID); void didClearPluginSiteData(uint64_t callbackID); diff --git a/Source/WebKit2/UIProcess/WebContext.messages.in b/Source/WebKit2/UIProcess/WebContext.messages.in index 85ea7a2b7..a1397f055 100644 --- a/Source/WebKit2/UIProcess/WebContext.messages.in +++ b/Source/WebKit2/UIProcess/WebContext.messages.in @@ -33,7 +33,7 @@ messages -> WebContext { # Plugin messages. GetPlugins(bool refresh) -> (Vector<WebCore::PluginInfo> plugins) - GetPluginPath(WTF::String mimeType, WTF::String urlString) -> (WTF::String pluginPath) + GetPluginPath(WTF::String mimeType, WTF::String urlString) -> (WTF::String pluginPath, bool blocked) #if !ENABLE(PLUGIN_PROCESS) void DidGetSitesWithPluginData(Vector<WTF::String> sites, uint64_t callbackID) diff --git a/Source/WebKit2/UIProcess/WebLoaderClient.cpp b/Source/WebKit2/UIProcess/WebLoaderClient.cpp index ca9d7f6f1..5a7f71766 100644 --- a/Source/WebKit2/UIProcess/WebLoaderClient.cpp +++ b/Source/WebKit2/UIProcess/WebLoaderClient.cpp @@ -266,10 +266,21 @@ void WebLoaderClient::willGoToBackForwardListItem(WebPageProxy* page, WebBackFor void WebLoaderClient::didFailToInitializePlugin(WebPageProxy* page, const String& mimeType) { - if (!m_client.didFailToInitializePlugin) + if (m_client.didFailToInitializePlugin_deprecatedForUseWithV0) + m_client.didFailToInitializePlugin_deprecatedForUseWithV0(toAPI(page), toAPI(mimeType.impl()), m_client.clientInfo); + + if (!m_client.pluginDidFail) + return; + + m_client.pluginDidFail(toAPI(page), kWKErrorCodeCannotLoadPlugIn, toAPI(mimeType.impl()), m_client.clientInfo); +} + +void WebLoaderClient::didBlockInsecurePluginVersion(WebPageProxy* page, const String& mimeType) +{ + if (!m_client.pluginDidFail) return; - m_client.didFailToInitializePlugin(toAPI(page), toAPI(mimeType.impl()), m_client.clientInfo); + m_client.pluginDidFail(toAPI(page), kWKErrorCodeInsecurePlugInVersion, toAPI(mimeType.impl()), m_client.clientInfo); } } // namespace WebKit diff --git a/Source/WebKit2/UIProcess/WebLoaderClient.h b/Source/WebKit2/UIProcess/WebLoaderClient.h index 3981e2f0d..a78788d76 100644 --- a/Source/WebKit2/UIProcess/WebLoaderClient.h +++ b/Source/WebKit2/UIProcess/WebLoaderClient.h @@ -87,6 +87,7 @@ public: void willGoToBackForwardListItem(WebPageProxy*, WebBackForwardListItem*, APIObject*); void didFailToInitializePlugin(WebPageProxy*, const String& mimeType); + void didBlockInsecurePluginVersion(WebPageProxy*, const String& mimeType); }; } // namespace WebKit diff --git a/Source/WebKit2/UIProcess/WebPageProxy.cpp b/Source/WebKit2/UIProcess/WebPageProxy.cpp index 043cdb690..ca11b64ca 100644 --- a/Source/WebKit2/UIProcess/WebPageProxy.cpp +++ b/Source/WebKit2/UIProcess/WebPageProxy.cpp @@ -109,6 +109,9 @@ using namespace WebCore; +// Represents the number of wheel events we can hold in the queue before we start pushing them preemptively. +static const unsigned wheelEventQueueSizeThreshold = 10; + namespace WebKit { WKPageDebugPaintFlags WebPageProxy::s_debugPaintFlags = 0; @@ -657,13 +660,15 @@ void WebPageProxy::willGoToBackForwardListItem(uint64_t itemID, CoreIPC::Argumen String WebPageProxy::activeURL() const { - if (!m_mainFrame) - return String(); - - // If there is a currently pending url, it is the active URL. + // If there is a currently pending url, it is the active URL, + // even when there's no main frame yet, as it might be the + // first API request. if (!m_pendingAPIRequestURL.isNull()) return m_pendingAPIRequestURL; + if (!m_mainFrame) + return String(); + if (!m_mainFrame->unreachableURL().isEmpty()) return m_mainFrame->unreachableURL(); @@ -985,6 +990,68 @@ void WebPageProxy::handleMouseEvent(const NativeWebMouseEvent& event) process()->send(Messages::WebPage::MouseEvent(event), m_pageID); } +#if MERGE_WHEEL_EVENTS +static bool canCoalesce(const WebWheelEvent& a, const WebWheelEvent& b) +{ + if (a.position() != b.position()) + return false; + if (a.globalPosition() != b.globalPosition()) + return false; + if (a.modifiers() != b.modifiers()) + return false; + if (a.granularity() != b.granularity()) + return false; +#if PLATFORM(MAC) + if (a.phase() != b.phase()) + return false; + if (a.momentumPhase() != b.momentumPhase()) + return false; + if (a.hasPreciseScrollingDeltas() != b.hasPreciseScrollingDeltas()) + return false; +#endif + + return true; +} + +static WebWheelEvent coalesce(const WebWheelEvent& a, const WebWheelEvent& b) +{ + ASSERT(canCoalesce(a, b)); + + FloatSize mergedDelta = a.delta() + b.delta(); + FloatSize mergedWheelTicks = a.wheelTicks() + b.wheelTicks(); + +#if PLATFORM(MAC) + return WebWheelEvent(WebEvent::Wheel, b.position(), b.globalPosition(), mergedDelta, mergedWheelTicks, b.granularity(), b.phase(), b.momentumPhase(), b.hasPreciseScrollingDeltas(), b.modifiers(), b.timestamp(), b.directionInvertedFromDevice()); +#else + return WebWheelEvent(WebEvent::Wheel, b.position(), b.globalPosition(), mergedDelta, mergedWheelTicks, b.granularity(), b.modifiers(), b.timestamp()); +#endif +} +#endif // MERGE_WHEEL_EVENTS + +static WebWheelEvent coalescedWheelEvent(Deque<NativeWebWheelEvent>& queue, Vector<NativeWebWheelEvent>& coalescedEvents) +{ + ASSERT(!queue.isEmpty()); + ASSERT(coalescedEvents.isEmpty()); + +#if MERGE_WHEEL_EVENTS + NativeWebWheelEvent firstEvent = queue.takeFirst(); + coalescedEvents.append(firstEvent); + + WebWheelEvent event = firstEvent; + while (!queue.isEmpty() && canCoalesce(event, queue.first())) { + NativeWebWheelEvent firstEvent = queue.takeFirst(); + coalescedEvents.append(firstEvent); + event = coalesce(event, firstEvent); + } + + return event; +#else + while (!queue.isEmpty()) + coalescedEvents.append(queue.takeFirst()); + return coalescedEvents.last(); +#endif +} + void WebPageProxy::handleWheelEvent(const NativeWebWheelEvent& event) { if (!isValid()) @@ -992,19 +1059,42 @@ void WebPageProxy::handleWheelEvent(const NativeWebWheelEvent& event) if (!m_currentlyProcessedWheelEvents.isEmpty()) { m_wheelEventQueue.append(event); + if (m_wheelEventQueue.size() < wheelEventQueueSizeThreshold) + return; + // The queue has too many wheel events, so push a new event. + } + + if (!m_wheelEventQueue.isEmpty()) { + processNextQueuedWheelEvent(); return; } - m_currentlyProcessedWheelEvents.append(event); + OwnPtr<Vector<NativeWebWheelEvent> > coalescedWheelEvent = adoptPtr(new Vector<NativeWebWheelEvent>); + coalescedWheelEvent->append(event); + m_currentlyProcessedWheelEvents.append(coalescedWheelEvent.release()); + sendWheelEvent(event); +} + +void WebPageProxy::processNextQueuedWheelEvent() +{ + OwnPtr<Vector<NativeWebWheelEvent> > nextCoalescedEvent = adoptPtr(new Vector<NativeWebWheelEvent>); + WebWheelEvent nextWheelEvent = coalescedWheelEvent(m_wheelEventQueue, *nextCoalescedEvent.get()); + m_currentlyProcessedWheelEvents.append(nextCoalescedEvent.release()); + sendWheelEvent(nextWheelEvent); +} +void WebPageProxy::sendWheelEvent(const WebWheelEvent& event) +{ process()->responsivenessTimer()->start(); if (m_shouldSendEventsSynchronously) { bool handled = false; process()->sendSync(Messages::WebPage::WheelEventSyncForTesting(event), Messages::WebPage::WheelEventSyncForTesting::Reply(handled), m_pageID); didReceiveEvent(event.type(), handled); - } else - process()->send(Messages::EventDispatcher::WheelEvent(m_pageID, event, canGoBack(), canGoForward()), 0); + return; + } + + process()->send(Messages::EventDispatcher::WheelEvent(m_pageID, event, canGoBack(), canGoForward()), 0); } void WebPageProxy::handleKeyboardEvent(const NativeWebKeyboardEvent& event) @@ -2309,12 +2399,13 @@ void WebPageProxy::mouseDidMoveOverElement(const WebHitTestResult::Data& hitTest m_uiClient.mouseDidMoveOverElement(this, hitTestResultData, modifiers, userData.get()); } -void WebPageProxy::missingPluginButtonClicked(const String& mimeType, const String& url, const String& pluginsPageURL) +void WebPageProxy::unavailablePluginButtonClicked(uint32_t opaquePluginUnavailabilityReason, const String& mimeType, const String& url, const String& pluginsPageURL) { MESSAGE_CHECK_URL(url); MESSAGE_CHECK_URL(pluginsPageURL); - m_uiClient.missingPluginButtonClicked(this, mimeType, url, pluginsPageURL); + WKPluginUnavailabilityReason pluginUnavailabilityReason = static_cast<WKPluginUnavailabilityReason>(opaquePluginUnavailabilityReason); + m_uiClient.unavailablePluginButtonClicked(this, pluginUnavailabilityReason, mimeType, url, pluginsPageURL); } void WebPageProxy::setToolbarsAreVisible(bool toolbarsAreVisible) @@ -2967,68 +3058,6 @@ void WebPageProxy::setCursorHiddenUntilMouseMoves(bool hiddenUntilMouseMoves) m_pageClient->setCursorHiddenUntilMouseMoves(hiddenUntilMouseMoves); } -#if MERGE_WHEEL_EVENTS -static bool canCoalesce(const WebWheelEvent& a, const WebWheelEvent& b) -{ - if (a.position() != b.position()) - return false; - if (a.globalPosition() != b.globalPosition()) - return false; - if (a.modifiers() != b.modifiers()) - return false; - if (a.granularity() != b.granularity()) - return false; -#if PLATFORM(MAC) - if (a.phase() != b.phase()) - return false; - if (a.momentumPhase() != b.momentumPhase()) - return false; - if (a.hasPreciseScrollingDeltas() != b.hasPreciseScrollingDeltas()) - return false; -#endif - - return true; -} - -static WebWheelEvent coalesce(const WebWheelEvent& a, const WebWheelEvent& b) -{ - ASSERT(canCoalesce(a, b)); - - FloatSize mergedDelta = a.delta() + b.delta(); - FloatSize mergedWheelTicks = a.wheelTicks() + b.wheelTicks(); - -#if PLATFORM(MAC) - return WebWheelEvent(WebEvent::Wheel, b.position(), b.globalPosition(), mergedDelta, mergedWheelTicks, b.granularity(), b.phase(), b.momentumPhase(), b.hasPreciseScrollingDeltas(), b.modifiers(), b.timestamp(), b.directionInvertedFromDevice()); -#else - return WebWheelEvent(WebEvent::Wheel, b.position(), b.globalPosition(), mergedDelta, mergedWheelTicks, b.granularity(), b.modifiers(), b.timestamp()); -#endif -} -#endif - -static WebWheelEvent coalescedWheelEvent(Deque<NativeWebWheelEvent>& queue, Vector<NativeWebWheelEvent>& coalescedEvents) -{ - ASSERT(!queue.isEmpty()); - ASSERT(coalescedEvents.isEmpty()); - -#if MERGE_WHEEL_EVENTS - NativeWebWheelEvent firstEvent = queue.takeFirst(); - coalescedEvents.append(firstEvent); - - WebWheelEvent event = firstEvent; - while (!queue.isEmpty() && canCoalesce(event, queue.first())) { - NativeWebWheelEvent firstEvent = queue.takeFirst(); - coalescedEvents.append(firstEvent); - event = coalesce(event, firstEvent); - } - - return event; -#else - while (!queue.isEmpty()) - coalescedEvents.append(queue.takeFirst()); - return coalescedEvents.last(); -#endif -} - void WebPageProxy::didReceiveEvent(uint32_t opaqueType, bool handled) { WebEvent::Type type = static_cast<WebEvent::Type>(opaqueType); @@ -3091,19 +3120,14 @@ void WebPageProxy::didReceiveEvent(uint32_t opaqueType, bool handled) case WebEvent::Wheel: { ASSERT(!m_currentlyProcessedWheelEvents.isEmpty()); + OwnPtr<Vector<NativeWebWheelEvent> > oldestCoalescedEvent = m_currentlyProcessedWheelEvents.takeFirst(); + // FIXME: Dispatch additional events to the didNotHandleWheelEvent client function. if (!handled && m_uiClient.implementsDidNotHandleWheelEvent()) - m_uiClient.didNotHandleWheelEvent(this, m_currentlyProcessedWheelEvents.last()); - - m_currentlyProcessedWheelEvents.clear(); - - if (!m_wheelEventQueue.isEmpty()) { - WebWheelEvent newWheelEvent = coalescedWheelEvent(m_wheelEventQueue, m_currentlyProcessedWheelEvents); - - process()->responsivenessTimer()->start(); - process()->send(Messages::EventDispatcher::WheelEvent(m_pageID, newWheelEvent, canGoBack(), canGoForward()), 0); - } + m_uiClient.didNotHandleWheelEvent(this, oldestCoalescedEvent->last()); + if (!m_wheelEventQueue.isEmpty()) + processNextQueuedWheelEvent(); break; } @@ -3597,6 +3621,11 @@ void WebPageProxy::didFailToInitializePlugin(const String& mimeType) m_loaderClient.didFailToInitializePlugin(this, mimeType); } +void WebPageProxy::didBlockInsecurePluginVersion(const String& mimeType) +{ + m_loaderClient.didBlockInsecurePluginVersion(this, mimeType); +} + bool WebPageProxy::willHandleHorizontalScrollEvents() const { return !m_canShortCircuitHorizontalWheelEvents; diff --git a/Source/WebKit2/UIProcess/WebPageProxy.h b/Source/WebKit2/UIProcess/WebPageProxy.h index a3e9bb8f7..ef331fc7d 100644 --- a/Source/WebKit2/UIProcess/WebPageProxy.h +++ b/Source/WebKit2/UIProcess/WebPageProxy.h @@ -718,7 +718,7 @@ private: void shouldInterruptJavaScript(bool& result); void setStatusText(const String&); void mouseDidMoveOverElement(const WebHitTestResult::Data& hitTestResultData, uint32_t modifiers, CoreIPC::ArgumentDecoder*); - void missingPluginButtonClicked(const String& mimeType, const String& url, const String& pluginsPageURL); + void unavailablePluginButtonClicked(uint32_t opaquePluginUnavailabilityReason, const String& mimeType, const String& url, const String& pluginsPageURL); void setToolbarsAreVisible(bool toolbarsAreVisible); void getToolbarsAreVisible(bool& toolbarsAreVisible); void setMenuBarIsVisible(bool menuBarIsVisible); @@ -745,6 +745,7 @@ private: void didChangeScrollOffsetPinningForMainFrame(bool pinnedToLeftSide, bool pinnedToRightSide); void didChangePageCount(unsigned); void didFailToInitializePlugin(const String& mimeType); + void didBlockInsecurePluginVersion(const String& mimeType); void setCanShortCircuitHorizontalWheelEvents(bool canShortCircuitHorizontalWheelEvents) { m_canShortCircuitHorizontalWheelEvents = canShortCircuitHorizontalWheelEvents; } void reattachToWebProcess(); @@ -903,6 +904,9 @@ private: void windowedPluginGeometryDidChange(const WebCore::IntRect& frameRect, const WebCore::IntRect& clipRect, uint64_t windowID); #endif + void processNextQueuedWheelEvent(); + void sendWheelEvent(const WebWheelEvent&); + PageClient* m_pageClient; WebLoaderClient m_loaderClient; WebPolicyClient m_policyClient; @@ -1024,7 +1028,7 @@ private: #endif Deque<NativeWebKeyboardEvent> m_keyEventQueue; Deque<NativeWebWheelEvent> m_wheelEventQueue; - Vector<NativeWebWheelEvent> m_currentlyProcessedWheelEvents; + Deque<OwnPtr<Vector<NativeWebWheelEvent> > > m_currentlyProcessedWheelEvents; bool m_processingMouseMoveEvent; OwnPtr<NativeWebMouseEvent> m_nextMouseMoveEvent; diff --git a/Source/WebKit2/UIProcess/WebPageProxy.messages.in b/Source/WebKit2/UIProcess/WebPageProxy.messages.in index 400aced5d..4c48a3cd8 100644 --- a/Source/WebKit2/UIProcess/WebPageProxy.messages.in +++ b/Source/WebKit2/UIProcess/WebPageProxy.messages.in @@ -30,7 +30,7 @@ messages -> WebPageProxy { RunJavaScriptPrompt(uint64_t frameID, WTF::String message, WTF::String defaultValue) -> (WTF::String result) ShouldInterruptJavaScript() -> (bool shouldInterupt) MouseDidMoveOverElement(WebKit::WebHitTestResult::Data hitTestResultData, uint32_t modifiers, WebKit::InjectedBundleUserMessageEncoder userData); - MissingPluginButtonClicked(WTF::String mimeType, WTF::String url, WTF::String pluginsPageURL) + UnavailablePluginButtonClicked(uint32_t pluginUnavailabilityReason, WTF::String mimeType, WTF::String url, WTF::String pluginsPageURL) DidChangeViewportProperties(WebCore::ViewportAttributes attributes) DidReceiveEvent(uint32_t type, bool handled) StopResponsivenessTimer() @@ -66,6 +66,7 @@ messages -> WebPageProxy { DidChangeScrollOffsetPinningForMainFrame(bool hasHorizontalScrollbar, bool hasVerticalScrollbar) DidChangePageCount(unsigned pageCount); DidFailToInitializePlugin(WTF::String mimeType) + DidBlockInsecurePluginVersion(WTF::String mimeType) SetCanShortCircuitHorizontalWheelEvents(bool canShortCircuitHorizontalWheelEvents) #if USE(TILED_BACKING_STORE) diff --git a/Source/WebKit2/UIProcess/WebUIClient.cpp b/Source/WebKit2/UIProcess/WebUIClient.cpp index d01312208..ed1fb930b 100644 --- a/Source/WebKit2/UIProcess/WebUIClient.cpp +++ b/Source/WebKit2/UIProcess/WebUIClient.cpp @@ -174,12 +174,18 @@ void WebUIClient::mouseDidMoveOverElement(WebPageProxy* page, const WebHitTestRe m_client.mouseDidMoveOverElement(toAPI(page), toAPI(webHitTestResult.get()), toAPI(modifiers), toAPI(userData), m_client.clientInfo); } -void WebUIClient::missingPluginButtonClicked(WebPageProxy* page, const String& mimeType, const String& url, const String& pluginsPageURL) +void WebUIClient::unavailablePluginButtonClicked(WebPageProxy* page, WKPluginUnavailabilityReason pluginUnavailabilityReason, const String& mimeType, const String& url, const String& pluginsPageURL) { - if (!m_client.missingPluginButtonClicked) + if (pluginUnavailabilityReason == kWKPluginUnavailabilityReasonPluginMissing) { + if (m_client.missingPluginButtonClicked_deprecatedForUseWithV0) + m_client.missingPluginButtonClicked_deprecatedForUseWithV0(toAPI(page), toAPI(mimeType.impl()), toAPI(url.impl()), toAPI(pluginsPageURL.impl()), m_client.clientInfo); + } + + if (!m_client.unavailablePluginButtonClicked) return; - m_client.missingPluginButtonClicked(toAPI(page), toAPI(mimeType.impl()), toAPI(url.impl()), toAPI(pluginsPageURL.impl()), m_client.clientInfo); + m_client.unavailablePluginButtonClicked(toAPI(page), pluginUnavailabilityReason, toAPI(mimeType.impl()), toAPI(url.impl()), toAPI(pluginsPageURL.impl()), m_client.clientInfo); + } bool WebUIClient::implementsDidNotHandleKeyEvent() const diff --git a/Source/WebKit2/UIProcess/WebUIClient.h b/Source/WebKit2/UIProcess/WebUIClient.h index 835e6ceb7..28cfb686a 100644 --- a/Source/WebKit2/UIProcess/WebUIClient.h +++ b/Source/WebKit2/UIProcess/WebUIClient.h @@ -70,7 +70,7 @@ public: void setStatusText(WebPageProxy*, const String&); void mouseDidMoveOverElement(WebPageProxy*, const WebHitTestResult::Data&, WebEvent::Modifiers, APIObject*); - void missingPluginButtonClicked(WebPageProxy*, const String& mimeType, const String& url, const String& pluginsPageURL); + void unavailablePluginButtonClicked(WebPageProxy*, WKPluginUnavailabilityReason, const String& mimeType, const String& url, const String& pluginsPageURL); bool implementsDidNotHandleKeyEvent() const; void didNotHandleKeyEvent(WebPageProxy*, const NativeWebKeyboardEvent&); diff --git a/Source/WebKit2/UIProcess/mac/WebInspectorProxyMac.mm b/Source/WebKit2/UIProcess/mac/WebInspectorProxyMac.mm index cfb756cdb..bcdfbc272 100644 --- a/Source/WebKit2/UIProcess/mac/WebInspectorProxyMac.mm +++ b/Source/WebKit2/UIProcess/mac/WebInspectorProxyMac.mm @@ -42,7 +42,7 @@ #import <WebCore/SoftLinking.h> #import <wtf/text/WTFString.h> -SOFT_LINK_STAGED_FRAMEWORK_OPTIONAL(WebInspector, PrivateFrameworks) +SOFT_LINK_STAGED_FRAMEWORK_OPTIONAL(WebInspector, PrivateFrameworks, A) using namespace WebCore; using namespace WebKit; diff --git a/Source/WebKit2/UIProcess/qt/QtDialogRunner.h b/Source/WebKit2/UIProcess/qt/QtDialogRunner.h index f53fc92f4..eb229ec84 100644 --- a/Source/WebKit2/UIProcess/qt/QtDialogRunner.h +++ b/Source/WebKit2/UIProcess/qt/QtDialogRunner.h @@ -27,8 +27,8 @@ #include <wtf/OwnPtr.h> QT_BEGIN_NAMESPACE -class QDeclarativeComponent; -class QDeclarativeContext; +class QQmlComponent; +class QQmlContext; class QQuickItem; QT_END_NAMESPACE @@ -41,14 +41,14 @@ public: QtDialogRunner(); virtual ~QtDialogRunner(); - bool initForAlert(QDeclarativeComponent*, QQuickItem* dialogParent, const QString& message); - bool initForConfirm(QDeclarativeComponent*, QQuickItem* dialogParent, const QString& message); - bool initForPrompt(QDeclarativeComponent*, QQuickItem* dialogParent, const QString& message, const QString& defaultValue); - bool initForAuthentication(QDeclarativeComponent*, QQuickItem* dialogParent, const QString& hostname, const QString& realm, const QString& prefilledUsername); - bool initForCertificateVerification(QDeclarativeComponent*, QQuickItem*, const QString& hostname); - bool initForProxyAuthentication(QDeclarativeComponent*, QQuickItem*, const QString& hostname, uint16_t port, const QString& prefilledUsername); - bool initForFilePicker(QDeclarativeComponent*, QQuickItem*, const QStringList& selectedFiles, bool allowMultiple); - bool initForDatabaseQuotaDialog(QDeclarativeComponent*, QQuickItem*, const QString& databaseName, const QString& displayName, WKSecurityOriginRef, quint64 currentQuota, quint64 currentOriginUsage, quint64 currentDatabaseUsage, quint64 expectedUsage); + bool initForAlert(QQmlComponent*, QQuickItem* dialogParent, const QString& message); + bool initForConfirm(QQmlComponent*, QQuickItem* dialogParent, const QString& message); + bool initForPrompt(QQmlComponent*, QQuickItem* dialogParent, const QString& message, const QString& defaultValue); + bool initForAuthentication(QQmlComponent*, QQuickItem* dialogParent, const QString& hostname, const QString& realm, const QString& prefilledUsername); + bool initForCertificateVerification(QQmlComponent*, QQuickItem*, const QString& hostname); + bool initForProxyAuthentication(QQmlComponent*, QQuickItem*, const QString& hostname, uint16_t port, const QString& prefilledUsername); + bool initForFilePicker(QQmlComponent*, QQuickItem*, const QStringList& selectedFiles, bool allowMultiple); + bool initForDatabaseQuotaDialog(QQmlComponent*, QQuickItem*, const QString& databaseName, const QString& displayName, WKSecurityOriginRef, quint64 currentQuota, quint64 currentOriginUsage, quint64 currentDatabaseUsage, quint64 expectedUsage); QQuickItem* dialog() const { return m_dialog.get(); } @@ -88,9 +88,9 @@ public slots: } private: - bool createDialog(QDeclarativeComponent*, QQuickItem* dialogParent, QObject* contextObject); + bool createDialog(QQmlComponent*, QQuickItem* dialogParent, QObject* contextObject); - OwnPtr<QDeclarativeContext> m_dialogContext; + OwnPtr<QQmlContext> m_dialogContext; OwnPtr<QQuickItem> m_dialog; QString m_result; bool m_wasAccepted; diff --git a/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.cpp b/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.cpp index 09f632456..949a5918c 100644 --- a/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.cpp +++ b/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.cpp @@ -365,22 +365,25 @@ void QtViewportInteractionEngine::zoomToAreaGestureEnded(const QPointF& touchPoi if (scrollAnimationActive() || scaleAnimationActive()) return; + m_hadUserInteraction = true; + const int margin = 10; // We want at least a little bit of margin. QRectF endArea = itemRectFromCSS(targetArea.adjusted(-margin, -margin, margin, margin)); const QRectF viewportRect = m_viewport->boundingRect(); - qreal targetCSSScale = cssScaleFromItem(viewportRect.size().width() / endArea.size().width()); - qreal endItemScale = itemScaleFromCSS(innerBoundedCSSScale(qMin(targetCSSScale, qreal(2.5)))); + qreal targetCSSScale = viewportRect.size().width() / endArea.size().width(); + qreal endCSSScale = innerBoundedCSSScale(qMin(targetCSSScale, qreal(2.5))); + qreal endItemScale = itemScaleFromCSS(endCSSScale); qreal currentScale = m_content->contentsScale(); // We want to end up with the target area filling the whole width of the viewport (if possible), // and centralized vertically where the user requested zoom. Thus our hotspot is the center of // the targetArea x-wise and the requested zoom position, y-wise. - const QPointF hotspot = QPointF(endArea.center().x(), touchPoint.y() * m_devicePixelRatio); + const QPointF hotspot = QPointF(endArea.center().x(), itemCoordFromCSS(touchPoint.y())); const QPointF viewportHotspot = viewportRect.center(); - QPointF endPosition = hotspot * endItemScale - viewportHotspot; + QPointF endPosition = hotspot * endCSSScale - viewportHotspot; QRectF endPosRange = computePosRangeForItemAtScale(endItemScale); endPosition = boundPosition(endPosRange.topLeft(), endPosition, endPosRange.bottomRight()); @@ -415,8 +418,9 @@ void QtViewportInteractionEngine::zoomToAreaGestureEnded(const QPointF& touchPoi case ZoomBack: { ScaleStackItem lastScale = m_scaleStack.takeLast(); endItemScale = lastScale.scale; + endCSSScale = cssScaleFromItem(lastScale.scale); // Recalculate endPosition and bound it according to new scale. - endPosition.setY(hotspot.y() * endItemScale - viewportHotspot.y()); + endPosition.setY(hotspot.y() * endCSSScale - viewportHotspot.y()); endPosition.setX(lastScale.xPosition); endPosRange = computePosRangeForItemAtScale(endItemScale); endPosition = boundPosition(endPosRange.topLeft(), endPosition, endPosRange.bottomRight()); diff --git a/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.h b/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.h index 486d8417c..8a720f34b 100644 --- a/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.h +++ b/Source/WebKit2/UIProcess/qt/QtViewportInteractionEngine.h @@ -35,6 +35,8 @@ class QQuickWebView; class QWheelEvent; QT_END_NAMESPACE +class QWebViewportInfo; + namespace WebKit { class ViewportUpdateDeferrer; @@ -114,7 +116,7 @@ private Q_SLOTS: private: friend class ViewportUpdateDeferrer; - friend class QWebViewportInfo; + friend class ::QWebViewportInfo; QQuickWebView* const m_viewport; QQuickWebPage* const m_content; diff --git a/Source/WebKit2/UIProcess/qt/QtWebError.cpp b/Source/WebKit2/UIProcess/qt/QtWebError.cpp index 87ac17edf..9ea2925a9 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebError.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebError.cpp @@ -66,4 +66,9 @@ QString QtWebError::description() const return WKStringCopyQString(WKErrorCopyLocalizedDescription(error.get())); } +bool QtWebError::isCancellation() const +{ + return toImpl(error.get())->platformError().isCancellation(); +} + } // namespace WebKit diff --git a/Source/WebKit2/UIProcess/qt/QtWebError.h b/Source/WebKit2/UIProcess/qt/QtWebError.h index 3c36f701d..8f954054e 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebError.h +++ b/Source/WebKit2/UIProcess/qt/QtWebError.h @@ -46,6 +46,7 @@ public: QUrl url() const; int errorCode() const; QString description() const; + bool isCancellation() const; int errorCodeAsHttpStatusCode() const { return errorCode(); } QNetworkReply::NetworkError errorCodeAsNetworkError() const { return static_cast<QNetworkReply::NetworkError>(errorCode()); } diff --git a/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.cpp b/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.cpp index f510016de..c7a69cd28 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.cpp @@ -22,13 +22,7 @@ #include "QtWebPageLoadClient.h" #include "QtWebError.h" -#include "WKStringQt.h" -#include "qquickwebview_p.h" #include "qquickwebview_p_p.h" -#include "qwebloadrequest_p.h" -#include <KURL.h> -#include <WKFrame.h> -#include <WebPageProxy.h> using namespace WebCore; @@ -36,8 +30,6 @@ namespace WebKit { QtWebPageLoadClient::QtWebPageLoadClient(WKPageRef pageRef, QQuickWebView* webView) : m_webView(webView) - , m_webPageProxy(toImpl(pageRef)) - , m_loadProgress(0) { WKPageLoaderClient loadClient; memset(&loadClient, 0, sizeof(WKPageLoaderClient)); @@ -53,57 +45,38 @@ QtWebPageLoadClient::QtWebPageLoadClient(WKPageRef pageRef, QQuickWebView* webVi loadClient.didStartProgress = didStartProgress; loadClient.didChangeProgress = didChangeProgress; loadClient.didFinishProgress = didFinishProgress; - loadClient.didFirstVisuallyNonEmptyLayoutForFrame = didFirstVisuallyNonEmptyLayoutForFrame; loadClient.didChangeBackForwardList = didChangeBackForwardList; WKPageSetPageLoaderClient(pageRef, &loadClient); } -void QtWebPageLoadClient::completeLoadWhenProcessDidCrashIfNeeded() -{ - // Check if loading was ongoing, when process crashed. - if (!m_loadProgress || m_loadProgress == 100) - return; - - QUrl url(KURL(WebCore::ParsedURLString, m_webPageProxy->urlAtProcessExit())); - QWebLoadRequest loadRequest(url, QQuickWebView::LoadFailedStatus, QLatin1String("The web process crashed."), QQuickWebView::InternalErrorDomain, 0); - - emit m_webView->loadingChanged(&loadRequest); - setLoadProgress(100); -} - void QtWebPageLoadClient::didStartProvisionalLoad(const QUrl& url) { - QWebLoadRequest loadRequest(url, QQuickWebView::LoadStartedStatus); - emit m_webView->loadingChanged(&loadRequest); + m_webView->d_func()->provisionalLoadDidStart(url); } void QtWebPageLoadClient::didCommitLoad() { - emit m_webView->navigationHistoryChanged(); - emit m_webView->urlChanged(); - emit m_webView->titleChanged(); m_webView->d_func()->loadDidCommit(); } void QtWebPageLoadClient::didSameDocumentNavigation() { - emit m_webView->navigationHistoryChanged(); - emit m_webView->urlChanged(); + m_webView->d_func()->didSameDocumentNavigation(); } void QtWebPageLoadClient::didReceiveTitle() { - emit m_webView->titleChanged(); + m_webView->d_func()->titleDidChange(); } -void QtWebPageLoadClient::didFirstVisuallyNonEmptyLayout() +void QtWebPageLoadClient::didChangeProgress(int loadProgress) { - m_webView->d_func()->didFinishFirstNonEmptyLayout(); + m_webView->d_func()->loadProgressDidChange(loadProgress); } void QtWebPageLoadClient::didChangeBackForwardList() { - m_webView->d_func()->didChangeBackForwardList(); + m_webView->d_func()->backForwardListDidChange(); } void QtWebPageLoadClient::dispatchLoadSucceeded() @@ -111,24 +84,17 @@ void QtWebPageLoadClient::dispatchLoadSucceeded() m_webView->d_func()->loadDidSucceed(); } -void QtWebPageLoadClient::dispatchLoadFailed(WKErrorRef error) +void QtWebPageLoadClient::dispatchLoadFailed(const QtWebError& error) { - int errorCode = WKErrorGetErrorCode(error); - if (toImpl(error)->platformError().isCancellation() || errorCode == kWKErrorCodeFrameLoadInterruptedByPolicyChange || errorCode == kWKErrorCodePlugInWillHandleLoad) { + int errorCode = error.errorCode(); + + if (error.isCancellation() || errorCode == kWKErrorCodeFrameLoadInterruptedByPolicyChange || errorCode == kWKErrorCodePlugInWillHandleLoad) { // Make sure that LoadStartedStatus has a counterpart when e.g. requesting a download. dispatchLoadSucceeded(); return; } - QtWebError qtError(error); - QWebLoadRequest loadRequest(qtError.url(), QQuickWebView::LoadFailedStatus, qtError.description(), static_cast<QQuickWebView::ErrorDomain>(qtError.type()), qtError.errorCode()); - emit m_webView->loadingChanged(&loadRequest); -} - -void QtWebPageLoadClient::setLoadProgress(int loadProgress) -{ - m_loadProgress = loadProgress; - emit m_webView->loadProgressChanged(); + m_webView->d_func()->loadDidFail(error); } static QtWebPageLoadClient* toQtWebPageLoadClient(const void* clientInfo) @@ -141,8 +107,7 @@ void QtWebPageLoadClient::didStartProvisionalLoadForFrame(WKPageRef, WKFrameRef { if (!WKFrameIsMainFrame(frame)) return; - WebFrameProxy* wkframe = toImpl(frame); - QString urlStr(wkframe->provisionalURL()); + QString urlStr(toImpl(frame)->provisionalURL()); QUrl qUrl = urlStr; toQtWebPageLoadClient(clientInfo)->didStartProvisionalLoad(qUrl); } @@ -191,26 +156,17 @@ void QtWebPageLoadClient::didReceiveTitleForFrame(WKPageRef, WKStringRef title, void QtWebPageLoadClient::didStartProgress(WKPageRef, const void* clientInfo) { - QtWebPageLoadClient* client = toQtWebPageLoadClient(clientInfo); - client->setLoadProgress(0); - client->m_webView->d_func()->setIcon(QUrl()); + toQtWebPageLoadClient(clientInfo)->didChangeProgress(0); } void QtWebPageLoadClient::didChangeProgress(WKPageRef page, const void* clientInfo) { - toQtWebPageLoadClient(clientInfo)->setLoadProgress(WKPageGetEstimatedProgress(page) * 100); + toQtWebPageLoadClient(clientInfo)->didChangeProgress(WKPageGetEstimatedProgress(page) * 100); } void QtWebPageLoadClient::didFinishProgress(WKPageRef, const void* clientInfo) { - toQtWebPageLoadClient(clientInfo)->setLoadProgress(100); -} - -void QtWebPageLoadClient::didFirstVisuallyNonEmptyLayoutForFrame(WKPageRef, WKFrameRef frame, WKTypeRef, const void *clientInfo) -{ - if (!WKFrameIsMainFrame(frame)) - return; - toQtWebPageLoadClient(clientInfo)->didFirstVisuallyNonEmptyLayout(); + toQtWebPageLoadClient(clientInfo)->didChangeProgress(100); } void QtWebPageLoadClient::didChangeBackForwardList(WKPageRef, WKBackForwardListItemRef, WKArrayRef, const void *clientInfo) diff --git a/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.h b/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.h index a4afd25f8..179eb8ed2 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.h +++ b/Source/WebKit2/UIProcess/qt/QtWebPageLoadClient.h @@ -32,27 +32,23 @@ class QQuickWebView; namespace WebKit { -class WebPageProxy; +class QtWebError; class QtWebPageLoadClient { public: QtWebPageLoadClient(WKPageRef, QQuickWebView*); - int loadProgress() const { return m_loadProgress; } - void completeLoadWhenProcessDidCrashIfNeeded(); - private: void didStartProvisionalLoad(const QUrl&); void didCommitLoad(); void didSameDocumentNavigation(); void didReceiveTitle(); - void didFirstVisuallyNonEmptyLayout(); + void didChangeProgress(int); void didChangeBackForwardList(); void dispatchLoadSucceeded(); - void dispatchLoadFailed(WKErrorRef); + void dispatchLoadFailed(const QtWebError&); - void setLoadProgress(int); // WKPageLoadClient callbacks. static void didStartProvisionalLoadForFrame(WKPageRef, WKFrameRef, WKTypeRef userData, const void* clientInfo); @@ -65,12 +61,9 @@ private: static void didStartProgress(WKPageRef, const void* clientInfo); static void didChangeProgress(WKPageRef, const void* clientInfo); static void didFinishProgress(WKPageRef, const void* clientInfo); - static void didFirstVisuallyNonEmptyLayoutForFrame(WKPageRef, WKFrameRef, WKTypeRef userData, const void* clientInfo); static void didChangeBackForwardList(WKPageRef, WKBackForwardListItemRef, WKArrayRef, const void *clientInfo); QQuickWebView* m_webView; - WebPageProxy* m_webPageProxy; - int m_loadProgress; }; } // namespace Webkit diff --git a/Source/WebKit2/UIProcess/qt/WebPopupMenuProxyQt.h b/Source/WebKit2/UIProcess/qt/WebPopupMenuProxyQt.h index d23134078..21eec5d1d 100644 --- a/Source/WebKit2/UIProcess/qt/WebPopupMenuProxyQt.h +++ b/Source/WebKit2/UIProcess/qt/WebPopupMenuProxyQt.h @@ -31,8 +31,8 @@ #include <QtCore/QObject> #include <wtf/OwnPtr.h> -class QDeclarativeComponent; -class QDeclarativeContext; +class QQmlComponent; +class QQmlContext; class QQuickWebView; class QQuickItem; @@ -59,11 +59,11 @@ private Q_SLOTS: private: WebPopupMenuProxyQt(WebPopupMenuProxy::Client*, QQuickWebView*); void createItem(QObject*); - void createContext(QDeclarativeComponent*, QObject*); + void createContext(QQmlComponent*, QObject*); void notifyValueChanged(); - OwnPtr<QDeclarativeContext> m_context; + OwnPtr<QQmlContext> m_context; OwnPtr<QQuickItem> m_itemSelector; QQuickWebView* m_webView; |