diff options
Diffstat (limited to 'Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp')
-rw-r--r-- | Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp | 863 |
1 files changed, 564 insertions, 299 deletions
diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp index 6bf25a642..091280899 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/WebChromeClient.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010, 2011, 2012 Apple Inc. All rights reserved. + * Copyright (C) 2010-2017 Apple Inc. All rights reserved. * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). * * Redistribution and use in source and binary forms, with or without @@ -27,31 +27,35 @@ #include "config.h" #include "WebChromeClient.h" +#include "APIArray.h" +#include "APISecurityOrigin.h" #include "DrawingArea.h" +#include "HangDetectionDisabler.h" #include "InjectedBundleNavigationAction.h" -#include "InjectedBundleUserMessageCoders.h" -#include "LayerTreeHost.h" +#include "InjectedBundleNodeHandle.h" +#include "NavigationActionData.h" #include "PageBanner.h" +#include "UserData.h" #include "WebColorChooser.h" #include "WebCoreArgumentCoders.h" #include "WebFrame.h" #include "WebFrameLoaderClient.h" #include "WebFullScreenManager.h" +#include "WebHitTestResultData.h" #include "WebImage.h" -#include "WebOpenPanelParameters.h" #include "WebOpenPanelResultListener.h" #include "WebPage.h" #include "WebPageCreationParameters.h" #include "WebPageProxyMessages.h" #include "WebPopupMenu.h" -#include "WebPreferencesStore.h" #include "WebProcess.h" +#include "WebProcessPoolMessages.h" #include "WebProcessProxyMessages.h" #include "WebSearchPopupMenu.h" -#include "WebSecurityOrigin.h" +#include <WebCore/ApplicationCacheStorage.h> #include <WebCore/AXObjectCache.h> #include <WebCore/ColorChooser.h> -#include <WebCore/DatabaseManager.h> +#include <WebCore/DatabaseTracker.h> #include <WebCore/DocumentLoader.h> #include <WebCore/FileChooser.h> #include <WebCore/FileIconLoader.h> @@ -66,13 +70,24 @@ #include <WebCore/MainFrame.h> #include <WebCore/NotImplemented.h> #include <WebCore/Page.h> +#include <WebCore/ScriptController.h> #include <WebCore/SecurityOrigin.h> +#include <WebCore/SecurityOriginData.h> #include <WebCore/Settings.h> +#if PLATFORM(IOS) || (PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)) +#include "WebPlaybackSessionManager.h" +#include "WebVideoFullscreenManager.h" +#endif + #if ENABLE(ASYNC_SCROLLING) #include "RemoteScrollingCoordinator.h" #endif +#if USE(COORDINATED_GRAPHICS) +#include "LayerTreeHost.h" +#endif + #if PLATFORM(GTK) #include "PrinterListGtk.h" #endif @@ -88,21 +103,20 @@ static double area(WebFrame* frame) return static_cast<double>(size.height()) * size.width(); } - -static WebFrame* findLargestFrameInFrameSet(WebPage* page) +static WebFrame* findLargestFrameInFrameSet(WebPage& page) { // Approximate what a user could consider a default target frame for application menu operations. - WebFrame* mainFrame = page->mainWebFrame(); + WebFrame* mainFrame = page.mainWebFrame(); if (!mainFrame || !mainFrame->isFrameSet()) - return 0; + return nullptr; - WebFrame* largestSoFar = 0; + WebFrame* largestSoFar = nullptr; - RefPtr<API::Array> frameChildren = mainFrame->childFrames(); + Ref<API::Array> frameChildren = mainFrame->childFrames(); size_t count = frameChildren->size(); for (size_t i = 0; i < count; ++i) { - WebFrame* childFrame = frameChildren->at<WebFrame>(i); + auto* childFrame = frameChildren->at<WebFrame>(i); if (!largestSoFar || area(childFrame) > area(largestSoFar)) largestSoFar = childFrame; } @@ -110,6 +124,15 @@ static WebFrame* findLargestFrameInFrameSet(WebPage* page) return largestSoFar; } +WebChromeClient::WebChromeClient(WebPage& page) + : m_page(page) +{ +} + +inline WebChromeClient::~WebChromeClient() +{ +} + void WebChromeClient::chromeDestroyed() { delete this; @@ -117,44 +140,60 @@ void WebChromeClient::chromeDestroyed() void WebChromeClient::setWindowRect(const FloatRect& windowFrame) { - m_page->sendSetWindowFrame(windowFrame); + m_page.sendSetWindowFrame(windowFrame); } FloatRect WebChromeClient::windowRect() { +#if PLATFORM(IOS) + return FloatRect(); +#else #if PLATFORM(MAC) - if (m_page->hasCachedWindowFrame()) - return m_page->windowFrameInUnflippedScreenCoordinates(); + if (m_page.hasCachedWindowFrame()) + return m_page.windowFrameInUnflippedScreenCoordinates(); #endif FloatRect newWindowFrame; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetWindowFrame(), Messages::WebPageProxy::GetWindowFrame::Reply(newWindowFrame), m_page->pageID())) + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetWindowFrame(), Messages::WebPageProxy::GetWindowFrame::Reply(newWindowFrame), m_page.pageID())) return FloatRect(); return newWindowFrame; +#endif } FloatRect WebChromeClient::pageRect() { - return FloatRect(FloatPoint(), m_page->size()); + return FloatRect(FloatPoint(), m_page.size()); } void WebChromeClient::focus() { - m_page->send(Messages::WebPageProxy::SetFocus(true)); + m_page.send(Messages::WebPageProxy::SetFocus(true)); } void WebChromeClient::unfocus() { - m_page->send(Messages::WebPageProxy::SetFocus(false)); + m_page.send(Messages::WebPageProxy::SetFocus(false)); +} + +#if PLATFORM(COCOA) + +void WebChromeClient::elementDidFocus(Element& element) +{ + m_page.elementDidFocus(&element); +} + +void WebChromeClient::elementDidBlur(Element& element) +{ + m_page.elementDidBlur(&element); } -#if PLATFORM(MAC) void WebChromeClient::makeFirstResponder() { - m_page->send(Messages::WebPageProxy::MakeFirstResponder()); -} + m_page.send(Messages::WebPageProxy::MakeFirstResponder()); +} + #endif bool WebChromeClient::canTakeFocus(FocusDirection) @@ -165,86 +204,96 @@ bool WebChromeClient::canTakeFocus(FocusDirection) void WebChromeClient::takeFocus(FocusDirection direction) { - m_page->send(Messages::WebPageProxy::TakeFocus(direction)); + m_page.send(Messages::WebPageProxy::TakeFocus(direction)); } void WebChromeClient::focusedElementChanged(Element* element) { - if (!element) - return; - if (!isHTMLInputElement(element)) + if (!is<HTMLInputElement>(element)) return; - HTMLInputElement* inputElement = toHTMLInputElement(element); - if (!inputElement->isText()) + HTMLInputElement& inputElement = downcast<HTMLInputElement>(*element); + if (!inputElement.isText()) return; - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(element->document().frame()->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + WebFrame* webFrame = WebFrame::fromCoreFrame(*element->document().frame()); ASSERT(webFrame); - m_page->injectedBundleFormClient().didFocusTextField(m_page, inputElement, webFrame); + m_page.injectedBundleFormClient().didFocusTextField(&m_page, &inputElement, webFrame); } void WebChromeClient::focusedFrameChanged(Frame* frame) { - WebFrameLoaderClient* webFrameLoaderClient = frame ? toWebFrameLoaderClient(frame->loader().client()) : 0; - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + WebFrame* webFrame = frame ? WebFrame::fromCoreFrame(*frame) : nullptr; - WebProcess::shared().parentProcessConnection()->send(Messages::WebPageProxy::FocusedFrameChanged(webFrame ? webFrame->frameID() : 0), m_page->pageID()); + WebProcess::singleton().parentProcessConnection()->send(Messages::WebPageProxy::FocusedFrameChanged(webFrame ? webFrame->frameID() : 0), m_page.pageID()); } -Page* WebChromeClient::createWindow(Frame* frame, const FrameLoadRequest& request, const WindowFeatures& windowFeatures, const NavigationAction& navigationAction) +Page* WebChromeClient::createWindow(Frame& frame, const FrameLoadRequest& request, const WindowFeatures& windowFeatures, const NavigationAction& navigationAction) { - uint32_t modifiers = static_cast<uint32_t>(InjectedBundleNavigationAction::modifiersForNavigationAction(navigationAction)); - int32_t mouseButton = static_cast<int32_t>(InjectedBundleNavigationAction::mouseButtonForNavigationAction(navigationAction)); - #if ENABLE(FULLSCREEN_API) - if (frame->document() && frame->document()->webkitCurrentFullScreenElement()) - frame->document()->webkitCancelFullScreen(); -#else - UNUSED_PARAM(frame); + if (frame.document() && frame.document()->webkitCurrentFullScreenElement()) + frame.document()->webkitCancelFullScreen(); #endif + auto& webProcess = WebProcess::singleton(); + + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); + + NavigationActionData navigationActionData; + navigationActionData.navigationType = navigationAction.type(); + navigationActionData.modifiers = InjectedBundleNavigationAction::modifiersForNavigationAction(navigationAction); + navigationActionData.mouseButton = InjectedBundleNavigationAction::mouseButtonForNavigationAction(navigationAction); + navigationActionData.syntheticClickType = InjectedBundleNavigationAction::syntheticClickTypeForNavigationAction(navigationAction); + navigationActionData.userGestureTokenIdentifier = webProcess.userGestureTokenIdentifier(navigationAction.userGestureToken()); + navigationActionData.canHandleRequest = m_page.canHandleRequest(request.resourceRequest()); + navigationActionData.shouldOpenExternalURLsPolicy = navigationAction.shouldOpenExternalURLsPolicy(); + navigationActionData.downloadAttribute = navigationAction.downloadAttribute(); + uint64_t newPageID = 0; WebPageCreationParameters parameters; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::CreateNewPage(request.resourceRequest(), windowFeatures, modifiers, mouseButton), Messages::WebPageProxy::CreateNewPage::Reply(newPageID, parameters), m_page->pageID())) - return 0; + if (!webProcess.parentProcessConnection()->sendSync(Messages::WebPageProxy::CreateNewPage(webFrame->frameID(), SecurityOriginData::fromFrame(&frame), request.resourceRequest(), windowFeatures, navigationActionData), Messages::WebPageProxy::CreateNewPage::Reply(newPageID, parameters), m_page.pageID())) + return nullptr; if (!newPageID) - return 0; + return nullptr; - WebProcess::shared().createWebPage(newPageID, parameters); - return WebProcess::shared().webPage(newPageID)->corePage(); + webProcess.createWebPage(newPageID, WTFMove(parameters)); + return webProcess.webPage(newPageID)->corePage(); } void WebChromeClient::show() { - m_page->show(); + m_page.show(); } bool WebChromeClient::canRunModal() { - return m_page->canRunModal(); + return m_page.canRunModal(); } void WebChromeClient::runModal() { - m_page->runModal(); + m_page.runModal(); +} + +void WebChromeClient::reportProcessCPUTime(int64_t cpuTime, ActivityStateForCPUSampling activityState) +{ + WebProcess::singleton().send(Messages::WebProcessPool::ReportWebContentCPUTime(cpuTime, static_cast<uint64_t>(activityState)), 0); } void WebChromeClient::setToolbarsVisible(bool toolbarsAreVisible) { - m_page->send(Messages::WebPageProxy::SetToolbarsAreVisible(toolbarsAreVisible)); + m_page.send(Messages::WebPageProxy::SetToolbarsAreVisible(toolbarsAreVisible)); } bool WebChromeClient::toolbarsVisible() { - WKBundlePageUIElementVisibility toolbarsVisibility = m_page->injectedBundleUIClient().toolbarsAreVisible(m_page); - if (toolbarsVisibility != WKBundlePageUIElementVisibilityUnknown) - return toolbarsVisibility == WKBundlePageUIElementVisible; + API::InjectedBundle::PageUIClient::UIElementVisibility toolbarsVisibility = m_page.injectedBundleUIClient().toolbarsAreVisible(&m_page); + if (toolbarsVisibility != API::InjectedBundle::PageUIClient::UIElementVisibility::Unknown) + return toolbarsVisibility == API::InjectedBundle::PageUIClient::UIElementVisibility::Visible; bool toolbarsAreVisible = true; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetToolbarsAreVisible(), Messages::WebPageProxy::GetToolbarsAreVisible::Reply(toolbarsAreVisible), m_page->pageID())) + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetToolbarsAreVisible(), Messages::WebPageProxy::GetToolbarsAreVisible::Reply(toolbarsAreVisible), m_page.pageID())) return true; return toolbarsAreVisible; @@ -252,17 +301,17 @@ bool WebChromeClient::toolbarsVisible() void WebChromeClient::setStatusbarVisible(bool statusBarIsVisible) { - m_page->send(Messages::WebPageProxy::SetStatusBarIsVisible(statusBarIsVisible)); + m_page.send(Messages::WebPageProxy::SetStatusBarIsVisible(statusBarIsVisible)); } bool WebChromeClient::statusbarVisible() { - WKBundlePageUIElementVisibility statusbarVisibility = m_page->injectedBundleUIClient().statusBarIsVisible(m_page); - if (statusbarVisibility != WKBundlePageUIElementVisibilityUnknown) - return statusbarVisibility == WKBundlePageUIElementVisible; + API::InjectedBundle::PageUIClient::UIElementVisibility statusbarVisibility = m_page.injectedBundleUIClient().statusBarIsVisible(&m_page); + if (statusbarVisibility != API::InjectedBundle::PageUIClient::UIElementVisibility::Unknown) + return statusbarVisibility == API::InjectedBundle::PageUIClient::UIElementVisibility::Visible; bool statusBarIsVisible = true; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetStatusBarIsVisible(), Messages::WebPageProxy::GetStatusBarIsVisible::Reply(statusBarIsVisible), m_page->pageID())) + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetStatusBarIsVisible(), Messages::WebPageProxy::GetStatusBarIsVisible::Reply(statusBarIsVisible), m_page.pageID())) return true; return statusBarIsVisible; @@ -281,17 +330,17 @@ bool WebChromeClient::scrollbarsVisible() void WebChromeClient::setMenubarVisible(bool menuBarVisible) { - m_page->send(Messages::WebPageProxy::SetMenuBarIsVisible(menuBarVisible)); + m_page.send(Messages::WebPageProxy::SetMenuBarIsVisible(menuBarVisible)); } bool WebChromeClient::menubarVisible() { - WKBundlePageUIElementVisibility menubarVisibility = m_page->injectedBundleUIClient().menuBarIsVisible(m_page); - if (menubarVisibility != WKBundlePageUIElementVisibilityUnknown) - return menubarVisibility == WKBundlePageUIElementVisible; + API::InjectedBundle::PageUIClient::UIElementVisibility menubarVisibility = m_page.injectedBundleUIClient().menuBarIsVisible(&m_page); + if (menubarVisibility != API::InjectedBundle::PageUIClient::UIElementVisibility::Unknown) + return menubarVisibility == API::InjectedBundle::PageUIClient::UIElementVisibility::Visible; bool menuBarIsVisible = true; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetMenuBarIsVisible(), Messages::WebPageProxy::GetMenuBarIsVisible::Reply(menuBarIsVisible), m_page->pageID())) + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::GetMenuBarIsVisible(), Messages::WebPageProxy::GetMenuBarIsVisible::Reply(menuBarIsVisible), m_page.pageID())) return true; return menuBarIsVisible; @@ -299,30 +348,29 @@ bool WebChromeClient::menubarVisible() void WebChromeClient::setResizable(bool resizable) { - m_page->send(Messages::WebPageProxy::SetIsResizable(resizable)); + m_page.send(Messages::WebPageProxy::SetIsResizable(resizable)); } -void WebChromeClient::addMessageToConsole(MessageSource, MessageLevel, const String& message, unsigned lineNumber, unsigned /*columnNumber*/, const String& /*sourceID*/) +void WebChromeClient::addMessageToConsole(MessageSource source, MessageLevel level, const String& message, unsigned lineNumber, unsigned columnNumber, const String& sourceID) { // Notify the bundle client. - m_page->injectedBundleUIClient().willAddMessageToConsole(m_page, message, lineNumber); - - notImplemented(); + m_page.injectedBundleUIClient().willAddMessageToConsole(&m_page, source, level, message, lineNumber, columnNumber, sourceID); } bool WebChromeClient::canRunBeforeUnloadConfirmPanel() { - return m_page->canRunBeforeUnloadConfirmPanel(); + return m_page.canRunBeforeUnloadConfirmPanel(); } -bool WebChromeClient::runBeforeUnloadConfirmPanel(const String& message, Frame* frame) +bool WebChromeClient::runBeforeUnloadConfirmPanel(const String& message, Frame& frame) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; - ASSERT(webFrame); + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); bool shouldClose = false; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunBeforeUnloadConfirmPanel(message, webFrame->frameID()), Messages::WebPageProxy::RunBeforeUnloadConfirmPanel::Reply(shouldClose), m_page->pageID())) + + HangDetectionDisabler hangDetectionDisabler; + + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunBeforeUnloadConfirmPanel(message, webFrame->frameID()), Messages::WebPageProxy::RunBeforeUnloadConfirmPanel::Reply(shouldClose), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend)) return false; return shouldClose; @@ -337,60 +385,74 @@ void WebChromeClient::closeWindowSoon() // a close execute synchronously as part of window.close, but other parts // later on. - m_page->corePage()->setGroupName(String()); + m_page.corePage()->setGroupName(String()); - if (WebFrame* frame = m_page->mainWebFrame()) { + if (WebFrame* frame = m_page.mainWebFrame()) { if (Frame* coreFrame = frame->coreFrame()) coreFrame->loader().stopForUserCancel(); } - m_page->sendClose(); + m_page.sendClose(); } -void WebChromeClient::runJavaScriptAlert(Frame* frame, const String& alertText) +static bool shouldSuppressJavaScriptDialogs(Frame& frame) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + if (frame.loader().opener() && frame.loader().stateMachine().isDisplayingInitialEmptyDocument() && frame.loader().provisionalDocumentLoader()) + return true; + + return false; +} + +void WebChromeClient::runJavaScriptAlert(Frame& frame, const String& alertText) +{ + if (shouldSuppressJavaScriptDialogs(frame)) + return; + + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); // Notify the bundle client. - m_page->injectedBundleUIClient().willRunJavaScriptAlert(m_page, alertText, webFrame); + m_page.injectedBundleUIClient().willRunJavaScriptAlert(&m_page, alertText, webFrame); - // FIXME (126021): It is not good to change IPC behavior conditionally, and SpinRunLoopWhileWaitingForReply was known to cause trouble in other similar cases. - unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? IPC::SpinRunLoopWhileWaitingForReply : 0; - WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptAlert(webFrame->frameID(), alertText), Messages::WebPageProxy::RunJavaScriptAlert::Reply(), m_page->pageID(), std::chrono::milliseconds::max(), syncSendFlags); + HangDetectionDisabler hangDetectionDisabler; + + WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptAlert(webFrame->frameID(), SecurityOriginData::fromFrame(&frame), alertText), Messages::WebPageProxy::RunJavaScriptAlert::Reply(), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend); } -bool WebChromeClient::runJavaScriptConfirm(Frame* frame, const String& message) +bool WebChromeClient::runJavaScriptConfirm(Frame& frame, const String& message) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + if (shouldSuppressJavaScriptDialogs(frame)) + return false; + + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); // Notify the bundle client. - m_page->injectedBundleUIClient().willRunJavaScriptConfirm(m_page, message, webFrame); + m_page.injectedBundleUIClient().willRunJavaScriptConfirm(&m_page, message, webFrame); + + HangDetectionDisabler hangDetectionDisabler; - // FIXME (126021): It is not good to change IPC behavior conditionally, and SpinRunLoopWhileWaitingForReply was known to cause trouble in other similar cases. - unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? IPC::SpinRunLoopWhileWaitingForReply : 0; bool result = false; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptConfirm(webFrame->frameID(), message), Messages::WebPageProxy::RunJavaScriptConfirm::Reply(result), m_page->pageID(), std::chrono::milliseconds::max(), syncSendFlags)) + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptConfirm(webFrame->frameID(), SecurityOriginData::fromFrame(&frame), message), Messages::WebPageProxy::RunJavaScriptConfirm::Reply(result), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend)) return false; return result; } -bool WebChromeClient::runJavaScriptPrompt(Frame* frame, const String& message, const String& defaultValue, String& result) +bool WebChromeClient::runJavaScriptPrompt(Frame& frame, const String& message, const String& defaultValue, String& result) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + if (shouldSuppressJavaScriptDialogs(frame)) + return false; + + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); // Notify the bundle client. - m_page->injectedBundleUIClient().willRunJavaScriptPrompt(m_page, message, defaultValue, webFrame); + m_page.injectedBundleUIClient().willRunJavaScriptPrompt(&m_page, message, defaultValue, webFrame); - // FIXME (126021): It is not good to change IPC behavior conditionally, and SpinRunLoopWhileWaitingForReply was known to cause trouble in other similar cases. - unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? IPC::SpinRunLoopWhileWaitingForReply : 0; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptPrompt(webFrame->frameID(), message, defaultValue), Messages::WebPageProxy::RunJavaScriptPrompt::Reply(result), m_page->pageID(), std::chrono::milliseconds::max(), syncSendFlags)) + HangDetectionDisabler hangDetectionDisabler; + + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::RunJavaScriptPrompt(webFrame->frameID(), SecurityOriginData::fromFrame(&frame), message, defaultValue), Messages::WebPageProxy::RunJavaScriptPrompt::Reply(result), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend)) return false; return !result.isNull(); @@ -399,121 +461,129 @@ bool WebChromeClient::runJavaScriptPrompt(Frame* frame, const String& message, c void WebChromeClient::setStatusbarText(const String& statusbarText) { // Notify the bundle client. - m_page->injectedBundleUIClient().willSetStatusbarText(m_page, statusbarText); + m_page.injectedBundleUIClient().willSetStatusbarText(&m_page, statusbarText); - m_page->send(Messages::WebPageProxy::SetStatusText(statusbarText)); + m_page.send(Messages::WebPageProxy::SetStatusText(statusbarText)); } -bool WebChromeClient::shouldInterruptJavaScript() +KeyboardUIMode WebChromeClient::keyboardUIMode() { - bool shouldInterrupt = false; - if (!WebProcess::shared().parentProcessConnection()->sendSync(Messages::WebPageProxy::ShouldInterruptJavaScript(), Messages::WebPageProxy::ShouldInterruptJavaScript::Reply(shouldInterrupt), m_page->pageID())) - return false; - - return shouldInterrupt; + return m_page.keyboardUIMode(); } -KeyboardUIMode WebChromeClient::keyboardUIMode() +#if ENABLE(POINTER_LOCK) + +bool WebChromeClient::requestPointerLock() { - return m_page->keyboardUIMode(); + m_page.send(Messages::WebPageProxy::RequestPointerLock()); + return true; } -IntRect WebChromeClient::windowResizerRect() const +void WebChromeClient::requestPointerUnlock() { - return m_page->windowResizerRect(); + m_page.send(Messages::WebPageProxy::RequestPointerUnlock()); } -void WebChromeClient::invalidateRootView(const IntRect&, bool) +#endif + +void WebChromeClient::invalidateRootView(const IntRect&) { // Do nothing here, there's no concept of invalidating the window in the web process. } -void WebChromeClient::invalidateContentsAndRootView(const IntRect& rect, bool) +void WebChromeClient::invalidateContentsAndRootView(const IntRect& rect) { - if (Document* document = m_page->corePage()->mainFrame().document()) { + if (Document* document = m_page.corePage()->mainFrame().document()) { if (document->printing()) return; } - m_page->drawingArea()->setNeedsDisplayInRect(rect); + m_page.drawingArea()->setNeedsDisplayInRect(rect); } -void WebChromeClient::invalidateContentsForSlowScroll(const IntRect& rect, bool) +void WebChromeClient::invalidateContentsForSlowScroll(const IntRect& rect) { - if (Document* document = m_page->corePage()->mainFrame().document()) { + if (Document* document = m_page.corePage()->mainFrame().document()) { if (document->printing()) return; } - m_page->pageDidScroll(); + m_page.pageDidScroll(); #if USE(COORDINATED_GRAPHICS) - m_page->drawingArea()->scroll(rect, IntSize()); -#else - m_page->drawingArea()->setNeedsDisplayInRect(rect); + FrameView* frameView = m_page.mainFrame()->view(); + if (frameView && frameView->delegatesScrolling()) { + m_page.drawingArea()->scroll(rect, IntSize()); + return; + } #endif + m_page.drawingArea()->setNeedsDisplayInRect(rect); } void WebChromeClient::scroll(const IntSize& scrollDelta, const IntRect& scrollRect, const IntRect& clipRect) { - m_page->pageDidScroll(); - m_page->drawingArea()->scroll(intersection(scrollRect, clipRect), scrollDelta); + m_page.pageDidScroll(); + m_page.drawingArea()->scroll(intersection(scrollRect, clipRect), scrollDelta); } -#if USE(TILED_BACKING_STORE) +#if USE(COORDINATED_GRAPHICS) void WebChromeClient::delegatedScrollRequested(const IntPoint& scrollOffset) { - m_page->pageDidRequestScroll(scrollOffset); + m_page.pageDidRequestScroll(scrollOffset); } #endif IntPoint WebChromeClient::screenToRootView(const IntPoint& point) const { - return m_page->screenToWindow(point); + return m_page.screenToRootView(point); } IntRect WebChromeClient::rootViewToScreen(const IntRect& rect) const { - return m_page->windowToScreen(rect); + return m_page.rootViewToScreen(rect); +} + +#if PLATFORM(IOS) +IntPoint WebChromeClient::accessibilityScreenToRootView(const IntPoint& point) const +{ + return m_page.accessibilityScreenToRootView(point); } +IntRect WebChromeClient::rootViewToAccessibilityScreen(const IntRect& rect) const +{ + return m_page.rootViewToAccessibilityScreen(rect); +} +#endif + PlatformPageClient WebChromeClient::platformPageClient() const { notImplemented(); return 0; } -void WebChromeClient::contentsSizeChanged(Frame* frame, const IntSize& size) const +void WebChromeClient::contentsSizeChanged(Frame& frame, const IntSize& size) const { - if (!m_page->corePage()->settings().frameFlatteningEnabled()) { + if (!m_page.corePage()->settings().frameFlatteningEnabled()) { WebFrame* largestFrame = findLargestFrameInFrameSet(m_page); if (largestFrame != m_cachedFrameSetLargestFrame.get()) { m_cachedFrameSetLargestFrame = largestFrame; - m_page->send(Messages::WebPageProxy::FrameSetLargestFrameChanged(largestFrame ? largestFrame->frameID() : 0)); + m_page.send(Messages::WebPageProxy::FrameSetLargestFrameChanged(largestFrame ? largestFrame->frameID() : 0)); } } - if (&frame->page()->mainFrame() != frame) + if (&frame.page()->mainFrame() != &frame) return; -#if USE(COORDINATED_GRAPHICS) - if (m_page->useFixedLayout()) - m_page->drawingArea()->layerTreeHost()->sizeDidChange(size); - - m_page->send(Messages::WebPageProxy::DidChangeContentSize(size)); -#endif -#if PLATFORM(IOS) - m_page->send(Messages::WebPageProxy::DidChangeContentSize(size)); -#endif + m_page.send(Messages::WebPageProxy::DidChangeContentSize(size)); - m_page->drawingArea()->mainFrameContentSizeChanged(size); + m_page.drawingArea()->mainFrameContentSizeChanged(size); - FrameView* frameView = frame->view(); + FrameView* frameView = frame.view(); if (frameView && !frameView->delegatesScrolling()) { bool hasHorizontalScrollbar = frameView->horizontalScrollbar(); bool hasVerticalScrollbar = frameView->verticalScrollbar(); if (hasHorizontalScrollbar != m_cachedMainFrameHasHorizontalScrollbar || hasVerticalScrollbar != m_cachedMainFrameHasVerticalScrollbar) { - m_page->send(Messages::WebPageProxy::DidChangeScrollbarsForMainFrame(hasHorizontalScrollbar, hasVerticalScrollbar)); + m_page.send(Messages::WebPageProxy::DidChangeScrollbarsForMainFrame(hasHorizontalScrollbar, hasVerticalScrollbar)); m_cachedMainFrameHasHorizontalScrollbar = hasHorizontalScrollbar; m_cachedMainFrameHasVerticalScrollbar = hasVerticalScrollbar; @@ -545,21 +615,21 @@ bool WebChromeClient::shouldUnavailablePluginMessageBeButton(RenderEmbeddedObjec return false; } -void WebChromeClient::unavailablePluginButtonClicked(Element* element, RenderEmbeddedObject::PluginUnavailabilityReason pluginUnavailabilityReason) const +void WebChromeClient::unavailablePluginButtonClicked(Element& element, RenderEmbeddedObject::PluginUnavailabilityReason pluginUnavailabilityReason) const { #if ENABLE(NETSCAPE_PLUGIN_API) - ASSERT(element->hasTagName(objectTag) || element->hasTagName(embedTag) || element->hasTagName(appletTag)); + ASSERT(element.hasTagName(objectTag) || element.hasTagName(embedTag) || element.hasTagName(appletTag)); ASSERT(pluginUnavailabilityReason == RenderEmbeddedObject::PluginMissing || pluginUnavailabilityReason == RenderEmbeddedObject::InsecurePluginVersion || pluginUnavailabilityReason); - HTMLPlugInImageElement* pluginElement = static_cast<HTMLPlugInImageElement*>(element); + auto& pluginElement = downcast<HTMLPlugInImageElement>(element); - String frameURLString = pluginElement->document().frame()->loader().documentLoader()->responseURL().string(); - String pageURLString = m_page->mainFrame()->loader().documentLoader()->responseURL().string(); - String pluginURLString = pluginElement->document().completeURL(pluginElement->url()).string(); - URL pluginspageAttributeURL = element->document().completeURL(stripLeadingAndTrailingHTMLSpaces(pluginElement->getAttribute(pluginspageAttr))); + String frameURLString = pluginElement.document().frame()->loader().documentLoader()->responseURL().string(); + String pageURLString = m_page.mainFrame()->loader().documentLoader()->responseURL().string(); + String pluginURLString = pluginElement.document().completeURL(pluginElement.url()).string(); + URL pluginspageAttributeURL = pluginElement.document().completeURL(stripLeadingAndTrailingHTMLSpaces(pluginElement.attributeWithoutSynchronization(pluginspageAttr))); if (!pluginspageAttributeURL.protocolIsInHTTPFamily()) pluginspageAttributeURL = URL(); - m_page->send(Messages::WebPageProxy::UnavailablePluginButtonClicked(pluginUnavailabilityReason, pluginElement->serviceType(), pluginURLString, pluginspageAttributeURL.string(), frameURLString, pageURLString)); + m_page.send(Messages::WebPageProxy::UnavailablePluginButtonClicked(pluginUnavailabilityReason, pluginElement.serviceType(), pluginURLString, pluginspageAttributeURL.string(), frameURLString, pageURLString)); #else UNUSED_PARAM(element); UNUSED_PARAM(pluginUnavailabilityReason); @@ -576,11 +646,11 @@ void WebChromeClient::mouseDidMoveOverElement(const HitTestResult& hitTestResult RefPtr<API::Object> userData; // Notify the bundle client. - m_page->injectedBundleUIClient().mouseDidMoveOverElement(m_page, hitTestResult, static_cast<WebEvent::Modifiers>(modifierFlags), userData); + m_page.injectedBundleUIClient().mouseDidMoveOverElement(&m_page, hitTestResult, static_cast<WebEvent::Modifiers>(modifierFlags), userData); // Notify the UIProcess. - WebHitTestResult::Data webHitTestResultData(hitTestResult); - m_page->send(Messages::WebPageProxy::MouseDidMoveOverElement(webHitTestResultData, modifierFlags, InjectedBundleUserMessageEncoder(userData.get()))); + WebHitTestResultData webHitTestResultData(hitTestResult); + m_page.send(Messages::WebPageProxy::MouseDidMoveOverElement(webHitTestResultData, modifierFlags, UserData(WebProcess::singleton().transformObjectsToHandles(userData.get()).get()))); } void WebChromeClient::setToolTip(const String& toolTip, TextDirection) @@ -591,171 +661,168 @@ void WebChromeClient::setToolTip(const String& toolTip, TextDirection) return; m_cachedToolTip = toolTip; - m_page->send(Messages::WebPageProxy::SetToolTip(m_cachedToolTip)); + m_page.send(Messages::WebPageProxy::SetToolTip(m_cachedToolTip)); } -void WebChromeClient::print(Frame* frame) +void WebChromeClient::print(Frame& frame) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); -#if PLATFORM(GTK) && defined(HAVE_GTK_UNIX_PRINTING) +#if PLATFORM(GTK) && HAVE(GTK_UNIX_PRINTING) // When printing synchronously in GTK+ we need to make sure that we have a list of Printers before starting the print operation. // Getting the list of printers is done synchronously by GTK+, but using a nested main loop that might process IPC messages // comming from the UI process like EndPrinting. When the EndPriting message is received while the printer list is being populated, // the print operation is finished unexpectely and the web process crashes, see https://bugs.webkit.org/show_bug.cgi?id=126979. // The PrinterListGtk class gets the list of printers in the constructor so we just need to ensure there's an instance alive // during the synchronous print operation. - RefPtr<PrinterListGtk> printerList = PrinterListGtk::shared(); + RefPtr<PrinterListGtk> printerList = PrinterListGtk::getOrCreate(); + if (!printerList) { + // PrinterListGtk::getOrCreate() returns nullptr when called while a printers enumeration is ongoing. + // This can happen if a synchronous print is started by a JavaScript and another one is inmeditaley started + // from a JavaScript event listener. The second print operation is handled by the nested main loop used by GTK+ + // to enumerate the printers, and we end up here trying to get a reference of an object that is being constructed. + // It's very unlikely that the user wants to print twice in a row, and other browsers don't do two print operations + // in this particular case either. So, the safest solution is to return early here and ignore the second print. + // See https://bugs.webkit.org/show_bug.cgi?id=141035 + return; + } #endif - m_page->sendSync(Messages::WebPageProxy::PrintFrame(webFrame->frameID()), Messages::WebPageProxy::PrintFrame::Reply()); + m_page.sendSync(Messages::WebPageProxy::PrintFrame(webFrame->frameID()), Messages::WebPageProxy::PrintFrame::Reply(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend); } -#if ENABLE(SQL_DATABASE) -void WebChromeClient::exceededDatabaseQuota(Frame* frame, const String& databaseName, DatabaseDetails details) +void WebChromeClient::exceededDatabaseQuota(Frame& frame, const String& databaseName, DatabaseDetails details) { - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + WebFrame* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); - SecurityOrigin* origin = frame->document()->securityOrigin(); - - DatabaseManager& dbManager = DatabaseManager::manager(); - uint64_t currentQuota = dbManager.quotaForOrigin(origin); - uint64_t currentOriginUsage = dbManager.usageForOrigin(origin); + auto& origin = frame.document()->securityOrigin(); + auto originData = SecurityOriginData::fromSecurityOrigin(origin); + auto& tracker = DatabaseTracker::singleton(); + auto currentQuota = tracker.quota(originData); + auto currentOriginUsage = tracker.usage(originData); uint64_t newQuota = 0; - RefPtr<WebSecurityOrigin> webSecurityOrigin = WebSecurityOrigin::createFromDatabaseIdentifier(origin->databaseIdentifier()); - newQuota = m_page->injectedBundleUIClient().didExceedDatabaseQuota(m_page, webSecurityOrigin.get(), databaseName, details.displayName(), currentQuota, currentOriginUsage, details.currentUsage(), details.expectedUsage()); + RefPtr<API::SecurityOrigin> securityOrigin = API::SecurityOrigin::create(SecurityOriginData::fromDatabaseIdentifier(SecurityOriginData::fromSecurityOrigin(origin).databaseIdentifier())->securityOrigin()); + newQuota = m_page.injectedBundleUIClient().didExceedDatabaseQuota(&m_page, securityOrigin.get(), databaseName, details.displayName(), currentQuota, currentOriginUsage, details.currentUsage(), details.expectedUsage()); if (!newQuota) { - WebProcess::shared().parentProcessConnection()->sendSync( - Messages::WebPageProxy::ExceededDatabaseQuota(webFrame->frameID(), origin->databaseIdentifier(), databaseName, details.displayName(), currentQuota, currentOriginUsage, details.currentUsage(), details.expectedUsage()), - Messages::WebPageProxy::ExceededDatabaseQuota::Reply(newQuota), m_page->pageID()); + WebProcess::singleton().parentProcessConnection()->sendSync( + Messages::WebPageProxy::ExceededDatabaseQuota(webFrame->frameID(), SecurityOriginData::fromSecurityOrigin(origin).databaseIdentifier(), databaseName, details.displayName(), currentQuota, currentOriginUsage, details.currentUsage(), details.expectedUsage()), + Messages::WebPageProxy::ExceededDatabaseQuota::Reply(newQuota), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend); } - dbManager.setQuota(origin, newQuota); + tracker.setQuota(originData, newQuota); } -#endif - void WebChromeClient::reachedMaxAppCacheSize(int64_t) { notImplemented(); } -void WebChromeClient::reachedApplicationCacheOriginQuota(SecurityOrigin* origin, int64_t totalBytesNeeded) +void WebChromeClient::reachedApplicationCacheOriginQuota(SecurityOrigin& origin, int64_t totalBytesNeeded) { - RefPtr<WebSecurityOrigin> webSecurityOrigin = WebSecurityOrigin::createFromString(origin->toString()); - m_page->injectedBundleUIClient().didReachApplicationCacheOriginQuota(m_page, webSecurityOrigin.get(), totalBytesNeeded); -} + RefPtr<API::SecurityOrigin> securityOrigin = API::SecurityOrigin::createFromString(origin.toString()); + if (m_page.injectedBundleUIClient().didReachApplicationCacheOriginQuota(&m_page, securityOrigin.get(), totalBytesNeeded)) + return; -#if ENABLE(DASHBOARD_SUPPORT) -void WebChromeClient::annotatedRegionsChanged() -{ - notImplemented(); -} -#endif + auto& cacheStorage = m_page.corePage()->applicationCacheStorage(); + int64_t currentQuota = 0; + if (!cacheStorage.calculateQuotaForOrigin(origin, currentQuota)) + return; -void WebChromeClient::populateVisitedLinks() -{ -} + uint64_t newQuota = 0; + WebProcess::singleton().parentProcessConnection()->sendSync( + Messages::WebPageProxy::ReachedApplicationCacheOriginQuota(SecurityOriginData::fromSecurityOrigin(origin).databaseIdentifier(), currentQuota, totalBytesNeeded), + Messages::WebPageProxy::ReachedApplicationCacheOriginQuota::Reply(newQuota), m_page.pageID(), Seconds::infinity(), IPC::SendSyncOption::InformPlatformProcessWillSuspend); -FloatRect WebChromeClient::customHighlightRect(Node*, const AtomicString& /*type*/, const FloatRect& /*lineRect*/) -{ - notImplemented(); - return FloatRect(); + cacheStorage.storeUpdatedQuotaForOrigin(&origin, newQuota); } -void WebChromeClient::paintCustomHighlight(Node*, const AtomicString& /*type*/, const FloatRect& /*boxRect*/, const FloatRect& /*lineRect*/, - bool /*behindText*/, bool /*entireLine*/) +#if ENABLE(DASHBOARD_SUPPORT) + +void WebChromeClient::annotatedRegionsChanged() { notImplemented(); } +#endif + bool WebChromeClient::shouldReplaceWithGeneratedFileForUpload(const String& path, String& generatedFilename) { - generatedFilename = m_page->injectedBundleUIClient().shouldGenerateFileForUpload(m_page, path); + generatedFilename = m_page.injectedBundleUIClient().shouldGenerateFileForUpload(&m_page, path); return !generatedFilename.isNull(); } String WebChromeClient::generateReplacementFile(const String& path) { - return m_page->injectedBundleUIClient().generateFileForUpload(m_page, path); + return m_page.injectedBundleUIClient().generateFileForUpload(&m_page, path); } #if ENABLE(INPUT_TYPE_COLOR) -PassOwnPtr<ColorChooser> WebChromeClient::createColorChooser(ColorChooserClient* client, const Color& initialColor) + +std::unique_ptr<ColorChooser> WebChromeClient::createColorChooser(ColorChooserClient& client, const Color& initialColor) { - return adoptPtr(new WebColorChooser(m_page, client, initialColor)); + return std::make_unique<WebColorChooser>(&m_page, &client, initialColor); } + #endif -void WebChromeClient::runOpenPanel(Frame* frame, PassRefPtr<FileChooser> prpFileChooser) +void WebChromeClient::runOpenPanel(Frame& frame, FileChooser& fileChooser) { - if (m_page->activeOpenPanelResultListener()) + if (m_page.activeOpenPanelResultListener()) return; - RefPtr<FileChooser> fileChooser = prpFileChooser; + m_page.setActiveOpenPanelResultListener(WebOpenPanelResultListener::create(&m_page, &fileChooser)); - m_page->setActiveOpenPanelResultListener(WebOpenPanelResultListener::create(m_page, fileChooser.get())); - - WebFrameLoaderClient* webFrameLoaderClient = toWebFrameLoaderClient(frame->loader().client()); - WebFrame* webFrame = webFrameLoaderClient ? webFrameLoaderClient->webFrame() : 0; + auto* webFrame = WebFrame::fromCoreFrame(frame); ASSERT(webFrame); - - m_page->send(Messages::WebPageProxy::RunOpenPanel(webFrame->frameID(), fileChooser->settings())); + m_page.send(Messages::WebPageProxy::RunOpenPanel(webFrame->frameID(), SecurityOriginData::fromFrame(&frame), fileChooser.settings())); } -void WebChromeClient::loadIconForFiles(const Vector<String>& filenames, FileIconLoader* loader) +void WebChromeClient::loadIconForFiles(const Vector<String>& filenames, FileIconLoader& loader) { - loader->notifyFinished(Icon::createIconForFiles(filenames)); + loader.iconLoaded(Icon::createIconForFiles(filenames)); } #if !PLATFORM(IOS) -void WebChromeClient::setCursor(const WebCore::Cursor& cursor) + +void WebChromeClient::setCursor(const Cursor& cursor) { - m_page->send(Messages::WebPageProxy::SetCursor(cursor)); + m_page.send(Messages::WebPageProxy::SetCursor(cursor)); } void WebChromeClient::setCursorHiddenUntilMouseMoves(bool hiddenUntilMouseMoves) { - m_page->send(Messages::WebPageProxy::SetCursorHiddenUntilMouseMoves(hiddenUntilMouseMoves)); + m_page.send(Messages::WebPageProxy::SetCursorHiddenUntilMouseMoves(hiddenUntilMouseMoves)); } + #endif -#if ENABLE(REQUEST_ANIMATION_FRAME) && !USE(REQUEST_ANIMATION_FRAME_TIMER) +#if !USE(REQUEST_ANIMATION_FRAME_TIMER) + void WebChromeClient::scheduleAnimation() { #if USE(COORDINATED_GRAPHICS) - m_page->drawingArea()->layerTreeHost()->scheduleAnimation(); + m_page.drawingArea()->layerTreeHost()->scheduleAnimation(); #endif } -#endif -void WebChromeClient::formStateDidChange(const Node*) -{ - notImplemented(); -} +#endif -void WebChromeClient::didAssociateFormControls(const Vector<RefPtr<WebCore::Element>>& elements) +void WebChromeClient::didAssociateFormControls(const Vector<RefPtr<Element>>& elements) { - return m_page->injectedBundleFormClient().didAssociateFormControls(m_page, elements); + return m_page.injectedBundleFormClient().didAssociateFormControls(&m_page, elements); } bool WebChromeClient::shouldNotifyOnFormChanges() { - return m_page->injectedBundleFormClient().shouldNotifyOnFormChanges(m_page); + return m_page.injectedBundleFormClient().shouldNotifyOnFormChanges(&m_page); } bool WebChromeClient::selectItemWritingDirectionIsNatural() { -#if PLATFORM(EFL) - return true; -#else return false; -#endif } bool WebChromeClient::selectItemAlignmentFollowsMenuWritingDirection() @@ -769,28 +836,44 @@ bool WebChromeClient::hasOpenedPopup() const return false; } -PassRefPtr<WebCore::PopupMenu> WebChromeClient::createPopupMenu(WebCore::PopupMenuClient* client) const +RefPtr<PopupMenu> WebChromeClient::createPopupMenu(PopupMenuClient& client) const { - return WebPopupMenu::create(m_page, client); + return WebPopupMenu::create(&m_page, &client); } -PassRefPtr<WebCore::SearchPopupMenu> WebChromeClient::createSearchPopupMenu(WebCore::PopupMenuClient* client) const +RefPtr<SearchPopupMenu> WebChromeClient::createSearchPopupMenu(PopupMenuClient& client) const { - return WebSearchPopupMenu::create(m_page, client); + return WebSearchPopupMenu::create(&m_page, &client); } -#if USE(ACCELERATED_COMPOSITING) GraphicsLayerFactory* WebChromeClient::graphicsLayerFactory() const { - return m_page->drawingArea()->graphicsLayerFactory(); + if (auto drawingArea = m_page.drawingArea()) + return drawingArea->graphicsLayerFactory(); + return nullptr; +} + +#if USE(REQUEST_ANIMATION_FRAME_DISPLAY_MONITOR) + +RefPtr<DisplayRefreshMonitor> WebChromeClient::createDisplayRefreshMonitor(PlatformDisplayID displayID) const +{ + return m_page.drawingArea()->createDisplayRefreshMonitor(displayID); } -void WebChromeClient::attachRootGraphicsLayer(Frame*, GraphicsLayer* layer) +#endif + +void WebChromeClient::attachRootGraphicsLayer(Frame&, GraphicsLayer* layer) { if (layer) - m_page->enterAcceleratedCompositingMode(layer); + m_page.enterAcceleratedCompositingMode(layer); else - m_page->exitAcceleratedCompositingMode(); + m_page.exitAcceleratedCompositingMode(); +} + +void WebChromeClient::attachViewOverlayGraphicsLayer(Frame& frame, GraphicsLayer* graphicsLayer) +{ + if (auto drawingArea = m_page.drawingArea()) + drawingArea->attachViewOverlayGraphicsLayer(&frame, graphicsLayer); } void WebChromeClient::setNeedsOneShotDrawingSynchronization() @@ -800,161 +883,343 @@ void WebChromeClient::setNeedsOneShotDrawingSynchronization() void WebChromeClient::scheduleCompositingLayerFlush() { - if (m_page->drawingArea()) - m_page->drawingArea()->scheduleCompositingLayerFlush(); + if (m_page.drawingArea()) + m_page.drawingArea()->scheduleCompositingLayerFlush(); } +bool WebChromeClient::adjustLayerFlushThrottling(LayerFlushThrottleState::Flags flags) +{ + return m_page.drawingArea() && m_page.drawingArea()->adjustLayerFlushThrottling(flags); +} bool WebChromeClient::layerTreeStateIsFrozen() const { - if (m_page->drawingArea()) - return m_page->drawingArea()->layerTreeStateIsFrozen(); + if (m_page.drawingArea()) + return m_page.drawingArea()->layerTreeStateIsFrozen(); return false; } -#endif #if ENABLE(ASYNC_SCROLLING) -PassRefPtr<ScrollingCoordinator> WebChromeClient::createScrollingCoordinator(Page* page) const + +RefPtr<ScrollingCoordinator> WebChromeClient::createScrollingCoordinator(Page& page) const { - ASSERT(m_page->corePage() == page); - if (m_page->drawingArea()->type() == DrawingAreaTypeRemoteLayerTree) - return RemoteScrollingCoordinator::create(m_page); + ASSERT_UNUSED(page, m_page.corePage() == &page); + if (m_page.drawingArea()->type() != DrawingAreaTypeRemoteLayerTree) + return nullptr; + return RemoteScrollingCoordinator::create(&m_page); +} - return 0; +#endif + +#if (PLATFORM(IOS) && HAVE(AVKIT)) || (PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE)) + +bool WebChromeClient::supportsVideoFullscreen(HTMLMediaElementEnums::VideoFullscreenMode mode) +{ + return m_page.videoFullscreenManager().supportsVideoFullscreen(mode); +} + +void WebChromeClient::setUpPlaybackControlsManager(HTMLMediaElement& mediaElement) +{ + m_page.playbackSessionManager().setUpPlaybackControlsManager(mediaElement); } + +void WebChromeClient::clearPlaybackControlsManager() +{ + m_page.playbackSessionManager().clearPlaybackControlsManager(); +} + +void WebChromeClient::enterVideoFullscreenForVideoElement(HTMLVideoElement& videoElement, HTMLMediaElementEnums::VideoFullscreenMode mode) +{ + ASSERT(mode != HTMLMediaElementEnums::VideoFullscreenModeNone); + m_page.videoFullscreenManager().enterVideoFullscreenForVideoElement(videoElement, mode); +} + +void WebChromeClient::exitVideoFullscreenForVideoElement(HTMLVideoElement& videoElement) +{ + m_page.videoFullscreenManager().exitVideoFullscreenForVideoElement(videoElement); +} + #endif -#if ENABLE(TOUCH_EVENTS) -void WebChromeClient::needTouchEvents(bool needTouchEvents) +#if PLATFORM(MAC) && ENABLE(VIDEO_PRESENTATION_MODE) + +void WebChromeClient::exitVideoFullscreenToModeWithoutAnimation(HTMLVideoElement& videoElement, HTMLMediaElementEnums::VideoFullscreenMode targetMode) { - m_page->send(Messages::WebPageProxy::NeedTouchEvents(needTouchEvents)); + m_page.videoFullscreenManager().exitVideoFullscreenToModeWithoutAnimation(videoElement, targetMode); } + #endif #if ENABLE(FULLSCREEN_API) -bool WebChromeClient::supportsFullScreenForElement(const WebCore::Element*, bool withKeyboard) + +bool WebChromeClient::supportsFullScreenForElement(const Element&, bool withKeyboard) { - return m_page->fullScreenManager()->supportsFullScreen(withKeyboard); + return m_page.fullScreenManager()->supportsFullScreen(withKeyboard); } -void WebChromeClient::enterFullScreenForElement(WebCore::Element* element) +void WebChromeClient::enterFullScreenForElement(Element& element) { - m_page->fullScreenManager()->enterFullScreenForElement(element); + m_page.fullScreenManager()->enterFullScreenForElement(&element); } -void WebChromeClient::exitFullScreenForElement(WebCore::Element* element) +void WebChromeClient::exitFullScreenForElement(Element* element) { - m_page->fullScreenManager()->exitFullScreenForElement(element); + m_page.fullScreenManager()->exitFullScreenForElement(element); } + #endif -void WebChromeClient::dispatchViewportPropertiesDidChange(const ViewportArguments& viewportArguments) const -{ #if PLATFORM(IOS) - m_page->send(Messages::WebPageProxy::DidChangeViewportArguments(viewportArguments)); -#else - UNUSED_PARAM(viewportArguments); -#endif -#if USE(TILED_BACKING_STORE) - if (!m_page->useFixedLayout()) - return; - m_page->sendViewportAttributesChanged(); +FloatSize WebChromeClient::screenSize() const +{ + return m_page.screenSize(); +} + +FloatSize WebChromeClient::availableScreenSize() const +{ + return m_page.availableScreenSize(); +} + #endif + +void WebChromeClient::dispatchViewportPropertiesDidChange(const ViewportArguments& viewportArguments) const +{ + m_page.viewportPropertiesDidChange(viewportArguments); } void WebChromeClient::notifyScrollerThumbIsVisibleInRect(const IntRect& scrollerThumb) { - m_page->send(Messages::WebPageProxy::NotifyScrollerThumbIsVisibleInRect(scrollerThumb)); + m_page.send(Messages::WebPageProxy::NotifyScrollerThumbIsVisibleInRect(scrollerThumb)); } -void WebChromeClient::recommendedScrollbarStyleDidChange(int32_t newStyle) +void WebChromeClient::recommendedScrollbarStyleDidChange(ScrollbarStyle newStyle) { - m_page->send(Messages::WebPageProxy::RecommendedScrollbarStyleDidChange(newStyle)); + m_page.send(Messages::WebPageProxy::RecommendedScrollbarStyleDidChange(static_cast<int32_t>(newStyle))); } -Color WebChromeClient::underlayColor() const +std::optional<ScrollbarOverlayStyle> WebChromeClient::preferredScrollbarOverlayStyle() { - return m_page->underlayColor(); + return m_page.scrollbarOverlayStyle(); } -void WebChromeClient::numWheelEventHandlersChanged(unsigned count) +Color WebChromeClient::underlayColor() const { - m_page->numWheelEventHandlersChanged(count); + return m_page.underlayColor(); } -void WebChromeClient::logDiagnosticMessage(const String& message, const String& description, const String& success) +void WebChromeClient::pageExtendedBackgroundColorDidChange(Color backgroundColor) const { - if (!m_page->corePage()->settings().diagnosticLoggingEnabled()) - return; +#if PLATFORM(MAC) + m_page.send(Messages::WebPageProxy::PageExtendedBackgroundColorDidChange(backgroundColor)); +#else + UNUSED_PARAM(backgroundColor); +#endif +} - m_page->injectedBundleDiagnosticLoggingClient().logDiagnosticMessage(m_page, message, description, success); +void WebChromeClient::wheelEventHandlersChanged(bool hasHandlers) +{ + m_page.wheelEventHandlersChanged(hasHandlers); } String WebChromeClient::plugInStartLabelTitle(const String& mimeType) const { - return m_page->injectedBundleUIClient().plugInStartLabelTitle(mimeType); + return m_page.injectedBundleUIClient().plugInStartLabelTitle(mimeType); } String WebChromeClient::plugInStartLabelSubtitle(const String& mimeType) const { - return m_page->injectedBundleUIClient().plugInStartLabelSubtitle(mimeType); + return m_page.injectedBundleUIClient().plugInStartLabelSubtitle(mimeType); } String WebChromeClient::plugInExtraStyleSheet() const { - return m_page->injectedBundleUIClient().plugInExtraStyleSheet(); + return m_page.injectedBundleUIClient().plugInExtraStyleSheet(); } String WebChromeClient::plugInExtraScript() const { - return m_page->injectedBundleUIClient().plugInExtraScript(); + return m_page.injectedBundleUIClient().plugInExtraScript(); } void WebChromeClient::enableSuddenTermination() { - m_page->send(Messages::WebProcessProxy::EnableSuddenTermination()); + m_page.send(Messages::WebProcessProxy::EnableSuddenTermination()); } void WebChromeClient::disableSuddenTermination() { - m_page->send(Messages::WebProcessProxy::DisableSuddenTermination()); + m_page.send(Messages::WebProcessProxy::DisableSuddenTermination()); } -void WebChromeClient::didAddHeaderLayer(GraphicsLayer* headerParent) +void WebChromeClient::didAddHeaderLayer(GraphicsLayer& headerParent) { #if ENABLE(RUBBER_BANDING) - if (PageBanner* banner = m_page->headerPageBanner()) - banner->didAddParentLayer(headerParent); + if (PageBanner* banner = m_page.headerPageBanner()) + banner->didAddParentLayer(&headerParent); #else UNUSED_PARAM(headerParent); #endif } -void WebChromeClient::didAddFooterLayer(GraphicsLayer* footerParent) +void WebChromeClient::didAddFooterLayer(GraphicsLayer& footerParent) { #if ENABLE(RUBBER_BANDING) - if (PageBanner* banner = m_page->footerPageBanner()) - banner->didAddParentLayer(footerParent); + if (PageBanner* banner = m_page.footerPageBanner()) + banner->didAddParentLayer(&footerParent); #else UNUSED_PARAM(footerParent); #endif } -bool WebChromeClient::shouldUseTiledBackingForFrameView(const FrameView* frameView) const +bool WebChromeClient::shouldUseTiledBackingForFrameView(const FrameView& frameView) const { - return m_page->drawingArea()->shouldUseTiledBackingForFrameView(frameView); + return m_page.drawingArea()->shouldUseTiledBackingForFrameView(&frameView); } -void WebChromeClient::incrementActivePageCount() +void WebChromeClient::isPlayingMediaDidChange(MediaProducer::MediaStateFlags state, uint64_t sourceElementID) { - WebProcess::shared().incrementActiveTaskCount(); + m_page.send(Messages::WebPageProxy::IsPlayingMediaDidChange(state, sourceElementID)); } -void WebChromeClient::decrementActivePageCount() +void WebChromeClient::didPlayMediaPreventedFromPlayingWithoutUserGesture() +{ + m_page.send(Messages::WebPageProxy::DidPlayMediaPreventedFromPlayingWithoutUserGesture()); +} + +#if ENABLE(MEDIA_SESSION) + +void WebChromeClient::hasMediaSessionWithActiveMediaElementsDidChange(bool state) +{ + m_page.send(Messages::WebPageProxy::HasMediaSessionWithActiveMediaElementsDidChange(state)); +} + +void WebChromeClient::mediaSessionMetadataDidChange(const MediaSessionMetadata& metadata) +{ + m_page.send(Messages::WebPageProxy::MediaSessionMetadataDidChange(metadata)); +} + +void WebChromeClient::focusedContentMediaElementDidChange(uint64_t elementID) +{ + m_page.send(Messages::WebPageProxy::FocusedContentMediaElementDidChange(elementID)); +} + +#endif + +#if ENABLE(SUBTLE_CRYPTO) + +bool WebChromeClient::wrapCryptoKey(const Vector<uint8_t>& key, Vector<uint8_t>& wrappedKey) const +{ + bool succeeded; + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::WrapCryptoKey(key), Messages::WebPageProxy::WrapCryptoKey::Reply(succeeded, wrappedKey), m_page.pageID())) + return false; + return succeeded; +} + +bool WebChromeClient::unwrapCryptoKey(const Vector<uint8_t>& wrappedKey, Vector<uint8_t>& key) const +{ + bool succeeded; + if (!WebProcess::singleton().parentProcessConnection()->sendSync(Messages::WebPageProxy::UnwrapCryptoKey(wrappedKey), Messages::WebPageProxy::UnwrapCryptoKey::Reply(succeeded, key), m_page.pageID())) + return false; + return succeeded; +} + +#endif + +#if ENABLE(TELEPHONE_NUMBER_DETECTION) && PLATFORM(MAC) + +void WebChromeClient::handleTelephoneNumberClick(const String& number, const IntPoint& point) +{ + m_page.handleTelephoneNumberClick(number, point); +} + +#endif + +#if ENABLE(SERVICE_CONTROLS) + +void WebChromeClient::handleSelectionServiceClick(FrameSelection& selection, const Vector<String>& telephoneNumbers, const IntPoint& point) +{ + m_page.handleSelectionServiceClick(selection, telephoneNumbers, point); +} + +bool WebChromeClient::hasRelevantSelectionServices(bool isTextOnly) const +{ + return (isTextOnly && WebProcess::singleton().hasSelectionServices()) || WebProcess::singleton().hasRichContentServices(); +} + +#endif + +bool WebChromeClient::shouldDispatchFakeMouseMoveEvents() const +{ + return m_page.shouldDispatchFakeMouseMoveEvents(); +} + +void WebChromeClient::handleAutoFillButtonClick(HTMLInputElement& inputElement) +{ + RefPtr<API::Object> userData; + + // Notify the bundle client. + auto nodeHandle = InjectedBundleNodeHandle::getOrCreate(inputElement); + m_page.injectedBundleUIClient().didClickAutoFillButton(m_page, nodeHandle.get(), userData); + + // Notify the UIProcess. + m_page.send(Messages::WebPageProxy::HandleAutoFillButtonClick(UserData(WebProcess::singleton().transformObjectsToHandles(userData.get()).get()))); +} + +#if ENABLE(WIRELESS_PLAYBACK_TARGET) && !PLATFORM(IOS) + +void WebChromeClient::addPlaybackTargetPickerClient(uint64_t contextId) +{ + m_page.send(Messages::WebPageProxy::AddPlaybackTargetPickerClient(contextId)); +} + +void WebChromeClient::removePlaybackTargetPickerClient(uint64_t contextId) +{ + m_page.send(Messages::WebPageProxy::RemovePlaybackTargetPickerClient(contextId)); +} + +void WebChromeClient::showPlaybackTargetPicker(uint64_t contextId, const IntPoint& position, bool isVideo) +{ + FrameView* frameView = m_page.mainFrame()->view(); + FloatRect rect(frameView->contentsToRootView(frameView->windowToContents(position)), FloatSize()); + m_page.send(Messages::WebPageProxy::ShowPlaybackTargetPicker(contextId, rect, isVideo)); +} + +void WebChromeClient::playbackTargetPickerClientStateDidChange(uint64_t contextId, MediaProducer::MediaStateFlags state) +{ + m_page.send(Messages::WebPageProxy::PlaybackTargetPickerClientStateDidChange(contextId, state)); +} + +void WebChromeClient::setMockMediaPlaybackTargetPickerEnabled(bool enabled) +{ + m_page.send(Messages::WebPageProxy::SetMockMediaPlaybackTargetPickerEnabled(enabled)); +} + +void WebChromeClient::setMockMediaPlaybackTargetPickerState(const String& name, MediaPlaybackTargetContext::State state) +{ + m_page.send(Messages::WebPageProxy::SetMockMediaPlaybackTargetPickerState(name, state)); +} + +#endif + +void WebChromeClient::imageOrMediaDocumentSizeChanged(const IntSize& newSize) +{ + m_page.imageOrMediaDocumentSizeChanged(newSize); +} + +#if ENABLE(VIDEO) && USE(GSTREAMER) + +void WebChromeClient::requestInstallMissingMediaPlugins(const String& details, const String& description, MediaPlayerRequestInstallMissingPluginsCallback& callback) +{ + m_page.requestInstallMissingMediaPlugins(details, description, callback); +} + +#endif + +void WebChromeClient::didInvalidateDocumentMarkerRects() { - WebProcess::shared().decrementActiveTaskCount(); + m_page.findController().didInvalidateDocumentMarkerRects(); } } // namespace WebKit |