Expose PDF information in hit test result
[WebKit-https.git] / Source / WebKit2 / WebProcess / WebCoreSupport / WebChromeClient.cpp
1 /*
2  * Copyright (C) 2010, 2011 Apple Inc. All rights reserved.
3  * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
15  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
16  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
18  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
24  * THE POSSIBILITY OF SUCH DAMAGE.
25  */
26
27 #include "config.h"
28 #include "WebChromeClient.h"
29
30 #include "DrawingArea.h"
31 #include "InjectedBundleNavigationAction.h"
32 #include "InjectedBundleUserMessageCoders.h"
33 #include "WebContextMenu.h"
34 #include "WebCoreArgumentCoders.h"
35 #include "WebFrame.h"
36 #include "WebFrameLoaderClient.h"
37 #include "WebFullScreenManager.h"
38 #include "WebOpenPanelParameters.h"
39 #include "WebOpenPanelResultListener.h"
40 #include "WebPage.h"
41 #include "WebPageCreationParameters.h"
42 #include "WebPageProxyMessages.h"
43 #include "WebPopupMenu.h"
44 #include "WebPreferencesStore.h"
45 #include "WebProcess.h"
46 #include "WebSearchPopupMenu.h"
47 #include <WebCore/AXObjectCache.h>
48 #include <WebCore/DatabaseTracker.h>
49 #include <WebCore/FileChooser.h>
50 #include <WebCore/FileIconLoader.h>
51 #include <WebCore/Frame.h>
52 #include <WebCore/FrameLoadRequest.h>
53 #include <WebCore/FrameLoader.h>
54 #include <WebCore/FrameView.h>
55 #include <WebCore/HTMLNames.h>
56 #include <WebCore/HTMLPlugInImageElement.h>
57 #include <WebCore/Icon.h>
58 #include <WebCore/NotImplemented.h>
59 #include <WebCore/Page.h>
60 #include <WebCore/SecurityOrigin.h>
61
62 using namespace WebCore;
63 using namespace HTMLNames;
64
65 namespace WebKit {
66
67 static double area(WebFrame* frame)
68 {
69     IntSize size = frame->visibleContentBoundsExcludingScrollbars().size();
70     return static_cast<double>(size.height()) * size.width();
71 }
72
73
74 static WebFrame* findLargestFrameInFrameSet(WebPage* page)
75 {
76     // Approximate what a user could consider a default target frame for application menu operations.
77
78     WebFrame* mainFrame = page->mainWebFrame();
79     if (!mainFrame->isFrameSet())
80         return 0;
81
82     WebFrame* largestSoFar = 0;
83
84     RefPtr<ImmutableArray> frameChildren = mainFrame->childFrames();
85     size_t count = frameChildren->size();
86     for (size_t i = 0; i < count; ++i) {
87         WebFrame* childFrame = frameChildren->at<WebFrame>(i);
88         if (!largestSoFar || area(childFrame) > area(largestSoFar))
89             largestSoFar = childFrame;
90     }
91
92     return largestSoFar;
93 }
94
95 void WebChromeClient::chromeDestroyed()
96 {
97     delete this;
98 }
99
100 void WebChromeClient::setWindowRect(const FloatRect& windowFrame)
101 {
102     m_page->send(Messages::WebPageProxy::SetWindowFrame(windowFrame));
103 }
104
105 FloatRect WebChromeClient::windowRect()
106 {
107     FloatRect newWindowFrame;
108
109     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::GetWindowFrame(), Messages::WebPageProxy::GetWindowFrame::Reply(newWindowFrame), m_page->pageID()))
110         return FloatRect();
111
112     return newWindowFrame;
113 }
114
115 FloatRect WebChromeClient::pageRect()
116 {
117     return FloatRect(FloatPoint(), m_page->size());
118 }
119
120 void WebChromeClient::focus()
121 {
122     m_page->send(Messages::WebPageProxy::SetFocus(true));
123 }
124
125 void WebChromeClient::unfocus()
126 {
127     m_page->send(Messages::WebPageProxy::SetFocus(false));
128 }
129
130 #if PLATFORM(MAC)
131 void WebChromeClient::makeFirstResponder()
132 {
133     m_page->send(Messages::WebPageProxy::MakeFirstResponder());
134 }    
135 #endif    
136
137 bool WebChromeClient::canTakeFocus(FocusDirection)
138 {
139     notImplemented();
140     return true;
141 }
142
143 void WebChromeClient::takeFocus(FocusDirection direction)
144 {
145     m_page->send(Messages::WebPageProxy::TakeFocus(direction));
146 }
147
148 void WebChromeClient::focusedNodeChanged(Node*)
149 {
150     notImplemented();
151 }
152
153 void WebChromeClient::focusedFrameChanged(Frame* frame)
154 {
155     WebFrame* webFrame = frame ? static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame() : 0;
156
157     WebProcess::shared().connection()->send(Messages::WebPageProxy::FocusedFrameChanged(webFrame ? webFrame->frameID() : 0), m_page->pageID());
158 }
159
160 Page* WebChromeClient::createWindow(Frame*, const FrameLoadRequest& request, const WindowFeatures& windowFeatures, const NavigationAction& navigationAction)
161 {
162     uint32_t modifiers = static_cast<uint32_t>(InjectedBundleNavigationAction::modifiersForNavigationAction(navigationAction));
163     int32_t mouseButton = static_cast<int32_t>(InjectedBundleNavigationAction::mouseButtonForNavigationAction(navigationAction));
164
165     uint64_t newPageID = 0;
166     WebPageCreationParameters parameters;
167     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::CreateNewPage(request.resourceRequest(), windowFeatures, modifiers, mouseButton), Messages::WebPageProxy::CreateNewPage::Reply(newPageID, parameters), m_page->pageID()))
168         return 0;
169
170     if (!newPageID)
171         return 0;
172
173     WebProcess::shared().createWebPage(newPageID, parameters);
174     return WebProcess::shared().webPage(newPageID)->corePage();
175 }
176
177 void WebChromeClient::show()
178 {
179     m_page->show();
180 }
181
182 bool WebChromeClient::canRunModal()
183 {
184     return m_page->canRunModal();
185 }
186
187 void WebChromeClient::runModal()
188 {
189     m_page->runModal();
190 }
191
192 void WebChromeClient::setToolbarsVisible(bool toolbarsAreVisible)
193 {
194     m_page->send(Messages::WebPageProxy::SetToolbarsAreVisible(toolbarsAreVisible));
195 }
196
197 bool WebChromeClient::toolbarsVisible()
198 {
199     WKBundlePageUIElementVisibility toolbarsVisibility = m_page->injectedBundleUIClient().toolbarsAreVisible(m_page);
200     if (toolbarsVisibility != WKBundlePageUIElementVisibilityUnknown)
201         return toolbarsVisibility == WKBundlePageUIElementVisible;
202     
203     bool toolbarsAreVisible = true;
204     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::GetToolbarsAreVisible(), Messages::WebPageProxy::GetToolbarsAreVisible::Reply(toolbarsAreVisible), m_page->pageID()))
205         return true;
206
207     return toolbarsAreVisible;
208 }
209
210 void WebChromeClient::setStatusbarVisible(bool statusBarIsVisible)
211 {
212     m_page->send(Messages::WebPageProxy::SetStatusBarIsVisible(statusBarIsVisible));
213 }
214
215 bool WebChromeClient::statusbarVisible()
216 {
217     WKBundlePageUIElementVisibility statusbarVisibility = m_page->injectedBundleUIClient().statusBarIsVisible(m_page);
218     if (statusbarVisibility != WKBundlePageUIElementVisibilityUnknown)
219         return statusbarVisibility == WKBundlePageUIElementVisible;
220
221     bool statusBarIsVisible = true;
222     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::GetStatusBarIsVisible(), Messages::WebPageProxy::GetStatusBarIsVisible::Reply(statusBarIsVisible), m_page->pageID()))
223         return true;
224
225     return statusBarIsVisible;
226 }
227
228 void WebChromeClient::setScrollbarsVisible(bool)
229 {
230     notImplemented();
231 }
232
233 bool WebChromeClient::scrollbarsVisible()
234 {
235     notImplemented();
236     return true;
237 }
238
239 void WebChromeClient::setMenubarVisible(bool menuBarVisible)
240 {
241     m_page->send(Messages::WebPageProxy::SetMenuBarIsVisible(menuBarVisible));
242 }
243
244 bool WebChromeClient::menubarVisible()
245 {
246     WKBundlePageUIElementVisibility menubarVisibility = m_page->injectedBundleUIClient().menuBarIsVisible(m_page);
247     if (menubarVisibility != WKBundlePageUIElementVisibilityUnknown)
248         return menubarVisibility == WKBundlePageUIElementVisible;
249     
250     bool menuBarIsVisible = true;
251     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::GetMenuBarIsVisible(), Messages::WebPageProxy::GetMenuBarIsVisible::Reply(menuBarIsVisible), m_page->pageID()))
252         return true;
253
254     return menuBarIsVisible;
255 }
256
257 void WebChromeClient::setResizable(bool resizable)
258 {
259     m_page->send(Messages::WebPageProxy::SetIsResizable(resizable));
260 }
261
262 void WebChromeClient::addMessageToConsole(MessageSource, MessageType, MessageLevel, const String& message, unsigned int lineNumber, const String& sourceID)
263 {
264     // Notify the bundle client.
265     m_page->injectedBundleUIClient().willAddMessageToConsole(m_page, message, lineNumber);
266
267     notImplemented();
268 }
269
270 bool WebChromeClient::canRunBeforeUnloadConfirmPanel()
271 {
272     return m_page->canRunBeforeUnloadConfirmPanel();
273 }
274
275 bool WebChromeClient::runBeforeUnloadConfirmPanel(const String& message, Frame* frame)
276 {
277     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
278
279     bool shouldClose = false;
280     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::RunBeforeUnloadConfirmPanel(message, webFrame->frameID()), Messages::WebPageProxy::RunBeforeUnloadConfirmPanel::Reply(shouldClose), m_page->pageID()))
281         return false;
282
283     return shouldClose;
284 }
285
286 void WebChromeClient::closeWindowSoon()
287 {
288     // FIXME: This code assumes that the client will respond to a close page
289     // message by actually closing the page. Safari does this, but there is
290     // no guarantee that other applications will, which will leave this page
291     // half detached. This approach is an inherent limitation making parts of
292     // a close execute synchronously as part of window.close, but other parts
293     // later on.
294
295     m_page->corePage()->setGroupName(String());
296
297     if (WebFrame* frame = m_page->mainWebFrame()) {
298         if (Frame* coreFrame = frame->coreFrame())
299             coreFrame->loader()->stopForUserCancel();
300     }
301
302     m_page->sendClose();
303 }
304
305 void WebChromeClient::runJavaScriptAlert(Frame* frame, const String& alertText)
306 {
307     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
308
309     // Notify the bundle client.
310     m_page->injectedBundleUIClient().willRunJavaScriptAlert(m_page, alertText, webFrame);
311
312     unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? CoreIPC::SpinRunLoopWhileWaitingForReply : 0;
313     WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::RunJavaScriptAlert(webFrame->frameID(), alertText), Messages::WebPageProxy::RunJavaScriptAlert::Reply(), m_page->pageID(), CoreIPC::Connection::DefaultTimeout, syncSendFlags);
314 }
315
316 bool WebChromeClient::runJavaScriptConfirm(Frame* frame, const String& message)
317 {
318     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
319
320     // Notify the bundle client.
321     m_page->injectedBundleUIClient().willRunJavaScriptConfirm(m_page, message, webFrame);
322
323     unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? CoreIPC::SpinRunLoopWhileWaitingForReply : 0;
324     bool result = false;
325     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::RunJavaScriptConfirm(webFrame->frameID(), message), Messages::WebPageProxy::RunJavaScriptConfirm::Reply(result), m_page->pageID(), CoreIPC::Connection::DefaultTimeout, syncSendFlags))
326         return false;
327
328     return result;
329 }
330
331 bool WebChromeClient::runJavaScriptPrompt(Frame* frame, const String& message, const String& defaultValue, String& result)
332 {
333     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
334
335     // Notify the bundle client.
336     m_page->injectedBundleUIClient().willRunJavaScriptPrompt(m_page, message, defaultValue, webFrame);
337
338     unsigned syncSendFlags = (WebCore::AXObjectCache::accessibilityEnabled()) ? CoreIPC::SpinRunLoopWhileWaitingForReply : 0;
339     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::RunJavaScriptPrompt(webFrame->frameID(), message, defaultValue), Messages::WebPageProxy::RunJavaScriptPrompt::Reply(result), m_page->pageID(), CoreIPC::Connection::DefaultTimeout, syncSendFlags))
340         return false;
341
342     return !result.isNull();
343 }
344
345 void WebChromeClient::setStatusbarText(const String& statusbarText)
346 {
347     // Notify the bundle client.
348     m_page->injectedBundleUIClient().willSetStatusbarText(m_page, statusbarText);
349
350     m_page->send(Messages::WebPageProxy::SetStatusText(statusbarText));
351 }
352
353 bool WebChromeClient::shouldInterruptJavaScript()
354 {
355     bool shouldInterrupt = false;
356     if (!WebProcess::shared().connection()->sendSync(Messages::WebPageProxy::ShouldInterruptJavaScript(), Messages::WebPageProxy::ShouldInterruptJavaScript::Reply(shouldInterrupt), m_page->pageID()))
357         return false;
358
359     return shouldInterrupt;
360 }
361
362 KeyboardUIMode WebChromeClient::keyboardUIMode()
363 {
364     return m_page->keyboardUIMode();
365 }
366
367 IntRect WebChromeClient::windowResizerRect() const
368 {
369     return m_page->windowResizerRect();
370 }
371
372 void WebChromeClient::invalidateWindow(const IntRect&, bool)
373 {
374     // Do nothing here, there's no concept of invalidating the window in the web process.
375 }
376
377 void WebChromeClient::invalidateContentsAndWindow(const IntRect& rect, bool)
378 {
379     if (Document* document = m_page->corePage()->mainFrame()->document()) {
380         if (document->printing())
381             return;
382     }
383
384     m_page->drawingArea()->setNeedsDisplay(rect);
385 }
386
387 void WebChromeClient::invalidateContentsForSlowScroll(const IntRect& rect, bool)
388 {
389     if (Document* document = m_page->corePage()->mainFrame()->document()) {
390         if (document->printing())
391             return;
392     }
393
394     m_page->pageDidScroll();
395     m_page->drawingArea()->setNeedsDisplay(rect);
396 }
397
398 void WebChromeClient::scroll(const IntSize& scrollOffset, const IntRect& scrollRect, const IntRect& clipRect)
399 {
400     m_page->pageDidScroll();
401     m_page->drawingArea()->scroll(intersection(scrollRect, clipRect), scrollOffset);
402 }
403
404 #if USE(TILED_BACKING_STORE)
405 void WebChromeClient::delegatedScrollRequested(const IntPoint& scrollOffset)
406 {
407     m_page->pageDidRequestScroll(scrollOffset);
408 }
409 #endif
410
411 IntPoint WebChromeClient::screenToWindow(const IntPoint& point) const
412 {
413     return m_page->screenToWindow(point);
414 }
415
416 IntRect WebChromeClient::windowToScreen(const IntRect& rect) const
417 {
418     return m_page->windowToScreen(rect);
419 }
420
421 PlatformPageClient WebChromeClient::platformPageClient() const
422 {
423     notImplemented();
424     return 0;
425 }
426
427 void WebChromeClient::contentsSizeChanged(Frame* frame, const IntSize& size) const
428 {
429 #if PLATFORM(QT)
430 #if USE(TILED_BACKING_STORE)
431     if (frame->page()->mainFrame() == frame)
432         m_page->resizeToContentsIfNeeded();
433 #endif
434
435     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
436
437     if (!m_page->mainWebFrame() || m_page->mainWebFrame() != webFrame)
438         return;
439
440     m_page->send(Messages::WebPageProxy::DidChangeContentsSize(size));
441 #endif
442
443     WebFrame* largestFrame = findLargestFrameInFrameSet(m_page);
444     if (largestFrame != m_cachedFrameSetLargestFrame.get()) {
445         m_cachedFrameSetLargestFrame = largestFrame;
446         m_page->send(Messages::WebPageProxy::FrameSetLargestFrameChanged(largestFrame ? largestFrame->frameID() : 0));
447     }
448
449     if (frame->page()->mainFrame() != frame)
450         return;
451     FrameView* frameView = frame->view();
452     if (!frameView)
453         return;
454
455     bool hasHorizontalScrollbar = frameView->horizontalScrollbar();
456     bool hasVerticalScrollbar = frameView->verticalScrollbar();
457
458     if (hasHorizontalScrollbar != m_cachedMainFrameHasHorizontalScrollbar || hasVerticalScrollbar != m_cachedMainFrameHasVerticalScrollbar) {
459         m_page->send(Messages::WebPageProxy::DidChangeScrollbarsForMainFrame(hasHorizontalScrollbar, hasVerticalScrollbar));
460         
461         m_cachedMainFrameHasHorizontalScrollbar = hasHorizontalScrollbar;
462         m_cachedMainFrameHasVerticalScrollbar = hasVerticalScrollbar;
463     }
464 }
465
466 void WebChromeClient::scrollRectIntoView(const IntRect&) const
467 {
468     notImplemented();
469 }
470
471 bool WebChromeClient::shouldMissingPluginMessageBeButton() const
472 {
473     // FIXME: <rdar://problem/8794397> We should only return true when there is a 
474     // missingPluginButtonClicked callback defined on the Page UI client.
475     return true;
476 }
477     
478 void WebChromeClient::missingPluginButtonClicked(Element* element) const
479 {
480     ASSERT(element->hasTagName(objectTag) || element->hasTagName(embedTag));
481
482     HTMLPlugInImageElement* pluginElement = static_cast<HTMLPlugInImageElement*>(element);
483
484     m_page->send(Messages::WebPageProxy::MissingPluginButtonClicked(pluginElement->serviceType(), pluginElement->url(), pluginElement->getAttribute(pluginspageAttr)));
485 }
486
487 void WebChromeClient::scrollbarsModeDidChange() const
488 {
489     notImplemented();
490 }
491
492 void WebChromeClient::mouseDidMoveOverElement(const HitTestResult& hitTestResult, unsigned modifierFlags)
493 {
494     RefPtr<APIObject> userData;
495
496     // Notify the bundle client.
497     m_page->injectedBundleUIClient().mouseDidMoveOverElement(m_page, hitTestResult, static_cast<WebEvent::Modifiers>(modifierFlags), userData);
498
499     WebHitTestResult::Data webHitTestResultData;
500     webHitTestResultData.absoluteImageURL = hitTestResult.absoluteImageURL().string();
501     webHitTestResultData.absolutePDFURL = hitTestResult.absolutePDFURL().string();
502     webHitTestResultData.absoluteLinkURL = hitTestResult.absoluteLinkURL().string();
503     webHitTestResultData.absoluteMediaURL = hitTestResult.absoluteMediaURL().string();
504     webHitTestResultData.linkLabel = hitTestResult.textContent();
505     webHitTestResultData.linkTitle = hitTestResult.titleDisplayString();
506
507     // Notify the UIProcess.
508     m_page->send(Messages::WebPageProxy::MouseDidMoveOverElement(webHitTestResultData, modifierFlags, InjectedBundleUserMessageEncoder(userData.get())));
509 }
510
511 void WebChromeClient::setToolTip(const String& toolTip, TextDirection)
512 {
513     // Only send a tool tip to the WebProcess if it has changed since the last time this function was called.
514
515     if (toolTip == m_cachedToolTip)
516         return;
517     m_cachedToolTip = toolTip;
518
519     m_page->send(Messages::WebPageProxy::SetToolTip(m_cachedToolTip));
520 }
521
522 void WebChromeClient::print(Frame* frame)
523 {
524     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
525     m_page->sendSync(Messages::WebPageProxy::PrintFrame(webFrame->frameID()), Messages::WebPageProxy::PrintFrame::Reply());
526 }
527
528 #if ENABLE(SQL_DATABASE)
529 void WebChromeClient::exceededDatabaseQuota(Frame* frame, const String& databaseName)
530 {
531     WebFrame* webFrame = static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame();
532     SecurityOrigin* origin = frame->document()->securityOrigin();
533
534     DatabaseDetails details = DatabaseTracker::tracker().detailsForNameAndOrigin(databaseName, origin);
535     uint64_t currentQuota = DatabaseTracker::tracker().quotaForOrigin(origin);
536     uint64_t currentOriginUsage = DatabaseTracker::tracker().usageForOrigin(origin);
537     uint64_t newQuota = 0;
538     WebProcess::shared().connection()->sendSync(
539         Messages::WebPageProxy::ExceededDatabaseQuota(webFrame->frameID(), origin->databaseIdentifier(), databaseName, details.displayName(), currentQuota, currentOriginUsage, details.currentUsage(), details.expectedUsage()),
540         Messages::WebPageProxy::ExceededDatabaseQuota::Reply(newQuota), m_page->pageID());
541
542     DatabaseTracker::tracker().setQuota(origin, newQuota);
543 }
544 #endif
545
546
547 void WebChromeClient::reachedMaxAppCacheSize(int64_t)
548 {
549     notImplemented();
550 }
551
552 void WebChromeClient::reachedApplicationCacheOriginQuota(SecurityOrigin*, int64_t)
553 {
554     notImplemented();
555 }
556
557 #if ENABLE(DASHBOARD_SUPPORT)
558 void WebChromeClient::dashboardRegionsChanged()
559 {
560     notImplemented();
561 }
562 #endif
563
564 void WebChromeClient::populateVisitedLinks()
565 {
566 }
567
568 FloatRect WebChromeClient::customHighlightRect(Node*, const AtomicString& type, const FloatRect& lineRect)
569 {
570     notImplemented();
571     return FloatRect();
572 }
573
574 void WebChromeClient::paintCustomHighlight(Node*, const AtomicString& type, const FloatRect& boxRect, const FloatRect& lineRect,
575                                   bool behindText, bool entireLine)
576 {
577     notImplemented();
578 }
579
580 bool WebChromeClient::shouldReplaceWithGeneratedFileForUpload(const String& path, String& generatedFilename)
581 {
582     generatedFilename = m_page->injectedBundleUIClient().shouldGenerateFileForUpload(m_page, path);
583     return !generatedFilename.isNull();
584 }
585
586 String WebChromeClient::generateReplacementFile(const String& path)
587 {
588     return m_page->injectedBundleUIClient().generateFileForUpload(m_page, path);
589 }
590
591 bool WebChromeClient::paintCustomOverhangArea(GraphicsContext* context, const IntRect& horizontalOverhangArea, const IntRect& verticalOverhangArea, const IntRect& dirtyRect)
592 {
593     if (!m_page->injectedBundleUIClient().shouldPaintCustomOverhangArea())
594         return false;
595
596     m_page->injectedBundleUIClient().paintCustomOverhangArea(m_page, context, horizontalOverhangArea, verticalOverhangArea, dirtyRect);
597     return true;
598 }
599
600 void WebChromeClient::requestGeolocationPermissionForFrame(Frame*, Geolocation*)
601 {
602     notImplemented();
603 }
604
605 void WebChromeClient::cancelGeolocationPermissionRequestForFrame(Frame*, Geolocation*)
606 {
607     notImplemented();
608 }
609
610 void WebChromeClient::runOpenPanel(Frame* frame, PassRefPtr<FileChooser> prpFileChooser)
611 {
612     if (m_page->activeOpenPanelResultListener())
613         return;
614
615     RefPtr<FileChooser> fileChooser = prpFileChooser;
616
617     m_page->setActiveOpenPanelResultListener(WebOpenPanelResultListener::create(m_page, fileChooser.get()));
618     m_page->send(Messages::WebPageProxy::RunOpenPanel(static_cast<WebFrameLoaderClient*>(frame->loader()->client())->webFrame()->frameID(), fileChooser->settings()));
619 }
620
621 void WebChromeClient::loadIconForFiles(const Vector<String>& filenames, FileIconLoader* loader)
622 {
623     loader->notifyFinished(Icon::createIconForFiles(filenames));
624 }
625
626 void WebChromeClient::setCursor(const WebCore::Cursor& cursor)
627 {
628 #if USE(LAZY_NATIVE_CURSOR)
629     m_page->send(Messages::WebPageProxy::SetCursor(cursor));
630 #endif
631 }
632
633 void WebChromeClient::setCursorHiddenUntilMouseMoves(bool hiddenUntilMouseMoves)
634 {
635     m_page->send(Messages::WebPageProxy::SetCursorHiddenUntilMouseMoves(hiddenUntilMouseMoves));
636 }
637
638 void WebChromeClient::formStateDidChange(const Node*)
639 {
640     notImplemented();
641 }
642
643 bool WebChromeClient::selectItemWritingDirectionIsNatural()
644 {
645 #if PLATFORM(WIN)
646     return true;
647 #else
648     return false;
649 #endif
650 }
651
652 bool WebChromeClient::selectItemAlignmentFollowsMenuWritingDirection()
653 {
654 #if PLATFORM(WIN)
655     return false;
656 #else
657     return true;
658 #endif
659 }
660
661 PassRefPtr<WebCore::PopupMenu> WebChromeClient::createPopupMenu(WebCore::PopupMenuClient* client) const
662 {
663     return WebPopupMenu::create(m_page, client);
664 }
665
666 PassRefPtr<WebCore::SearchPopupMenu> WebChromeClient::createSearchPopupMenu(WebCore::PopupMenuClient* client) const
667 {
668     return WebSearchPopupMenu::create(m_page, client);
669 }
670
671 #if ENABLE(CONTEXT_MENUS)
672 void WebChromeClient::showContextMenu()
673 {
674     m_page->contextMenu()->show();
675 }
676 #endif
677
678 #if USE(ACCELERATED_COMPOSITING)
679 void WebChromeClient::attachRootGraphicsLayer(Frame*, GraphicsLayer* layer)
680 {
681     if (layer)
682         m_page->enterAcceleratedCompositingMode(layer);
683     else
684         m_page->exitAcceleratedCompositingMode();
685 }
686
687 void WebChromeClient::setNeedsOneShotDrawingSynchronization()
688 {
689     notImplemented();
690 }
691
692 void WebChromeClient::scheduleCompositingLayerSync()
693 {
694     if (m_page->drawingArea())
695         m_page->drawingArea()->scheduleCompositingLayerSync();
696 }
697
698 #endif
699
700 #if ENABLE(NOTIFICATIONS)
701 WebCore::NotificationPresenter* WebChromeClient::notificationPresenter() const
702 {
703     return 0;
704 }
705 #endif
706
707 #if ENABLE(TOUCH_EVENTS)
708 void WebChromeClient::needTouchEvents(bool needTouchEvents)
709 {
710     m_page->send(Messages::WebPageProxy::NeedTouchEvents(needTouchEvents));
711 }
712 #endif
713
714 #if PLATFORM(WIN)
715 void WebChromeClient::setLastSetCursorToCurrentCursor()
716 {
717 }
718 #endif
719
720 #if ENABLE(FULLSCREEN_API)
721 bool WebChromeClient::supportsFullScreenForElement(const WebCore::Element* element, bool withKeyboard)
722 {
723     return m_page->fullScreenManager()->supportsFullScreen(withKeyboard);
724 }
725
726 void WebChromeClient::enterFullScreenForElement(WebCore::Element* element)
727 {
728     m_page->fullScreenManager()->enterFullScreenForElement(element);
729 }
730
731 void WebChromeClient::exitFullScreenForElement(WebCore::Element* element)
732 {
733     m_page->fullScreenManager()->exitFullScreenForElement(element);
734 }
735     
736 void WebChromeClient::setRootFullScreenLayer(GraphicsLayer* layer)
737 {
738     m_page->fullScreenManager()->setRootFullScreenLayer(layer);
739 }
740
741 #endif
742
743 void WebChromeClient::dispatchViewportDataDidChange(const ViewportArguments& args) const
744 {
745     m_page->send(Messages::WebPageProxy::DidChangeViewportData(args));
746 }
747
748 void WebChromeClient::didStartRubberBandForFrame(Frame*, const IntSize&) const
749 {
750     m_page->drawingArea()->disableDisplayThrottling();
751 }
752
753 void WebChromeClient::didCompleteRubberBandForFrame(Frame* frame, const IntSize& initialOverhang) const
754 {
755     m_page->drawingArea()->enableDisplayThrottling();
756 }
757
758 void WebChromeClient::didStartAnimatedScroll() const
759 {
760     m_page->drawingArea()->disableDisplayThrottling();
761 }
762
763 void WebChromeClient::didCompleteAnimatedScroll() const
764 {
765     m_page->drawingArea()->enableDisplayThrottling();
766 }
767     
768 void WebChromeClient::notifyScrollerThumbIsVisibleInRect(const IntRect& scrollerThumb)
769 {
770     m_page->send(Messages::WebPageProxy::NotifyScrollerThumbIsVisibleInRect(scrollerThumb));
771 }
772
773 bool WebChromeClient::shouldRubberBandInDirection(WebCore::ScrollDirection direction) const
774 {
775     ASSERT(direction != WebCore::ScrollUp && direction != WebCore::ScrollDown);
776     
777     if (direction == WebCore::ScrollLeft)
778         return m_page->injectedBundleUIClient().shouldRubberBandInDirection(m_page, WKScrollDirectionLeft);
779     if (direction == WebCore::ScrollRight)
780         return m_page->injectedBundleUIClient().shouldRubberBandInDirection(m_page, WKScrollDirectionRight);
781
782     ASSERT_NOT_REACHED();
783     return true;
784 }
785
786 void WebChromeClient::numWheelEventHandlersChanged(unsigned count)
787 {
788     m_page->send(Messages::WebPageProxy::NumWheelEventHandlersChanged(count));
789 }
790
791 } // namespace WebKit