Changeset 145332 in webkit


Ignore:
Timestamp:
Mar 10, 2013 1:40:47 PM (11 years ago)
Author:
timothy_horton@apple.com
Message:

Add a heuristic to determine the “primary” snapshotted plugin
https://bugs.webkit.org/show_bug.cgi?id=111932
<rdar://problem/13270208>

Reviewed by Dean Jackson.

  • WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp:

(WebKit::WebFrameLoaderClient::dispatchDidCommitLoad):
Forward didCommitLoad to WebPage. Move existing code that manipulated WebPage
itself during didCommitLoad into WebPage, where it belongs.
(WebKit::WebFrameLoaderClient::dispatchDidFinishLoad): Forward didFinishLoad to WebPage.

  • WebProcess/WebPage/WebPage.cpp:

(WebKit::WebPage::WebPage): Initialize m_didFindPrimarySnapshottedPlugin to false.
(WebKit::WebPage::didCommitLoad): Move code from WebPageFrameLoaderClient.
Reset the flag that says we've already found a snapshotted plugin.
(WebKit::WebPage::didFinishLoad):
Call determinePrimarySnapshottedPlugIn when any frame finishes loading. We call this for subframes,
not just the main frame, in case the main frame loads with no "primary" plugins, but a subframe later loads with one.
(WebKit::WebPage::determinePrimarySnapshottedPlugIn):
Attempt to find the primary snapshotted plugin on the page, by hit-testing a grid of points spaced 200px apart.
A plugin is considered if it is snapshotted and > 450x300. We scan vertically and left-to-right, only discarding
a previous candidate if another candidate is at least 110% the size of the previous candidate.
This tends to select plugins near the top left of the page, unless there is a significantly larger plugin elsewhere.
(WebKit::WebPage::resetPrimarySnapshottedPlugIn):

  • WebProcess/WebPage/WebPage.h:

(WebPage):

  • WebCore.exp.in: Export a few things.
  • html/HTMLPlugInImageElement.cpp:

(WebCore::HTMLPlugInImageElement::HTMLPlugInImageElement):
(WebCore::classNameForShadowRoot): If we've been informed that we are the primary snapshotted plugin, add the 'primary' class.
(WebCore::HTMLPlugInImageElement::setIsPrimarySnapshottedPlugIn): Added
(WebCore::HTMLPlugInImageElement::updateSnapshotInfo): Hand classNameForShadowRoot our primary-ness.

  • html/HTMLPlugInImageElement.h:

(HTMLPlugInImageElement): Add storage for m_isPrimarySnapshottedPlugIn.

Location:
trunk/Source
Files:
8 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r145331 r145332  
     12013-03-10  Tim Horton  <timothy_horton@apple.com>
     2
     3        Add a heuristic to determine the “primary” snapshotted plugin
     4        https://bugs.webkit.org/show_bug.cgi?id=111932
     5        <rdar://problem/13270208>
     6
     7        Reviewed by Dean Jackson.
     8
     9        * WebCore.exp.in: Export a few things.
     10        * html/HTMLPlugInImageElement.cpp:
     11        (WebCore::HTMLPlugInImageElement::HTMLPlugInImageElement):
     12        (WebCore::classNameForShadowRoot): If we've been informed that we are the primary snapshotted plugin, add the 'primary' class.
     13        (WebCore::HTMLPlugInImageElement::setIsPrimarySnapshottedPlugIn): Added
     14        (WebCore::HTMLPlugInImageElement::updateSnapshotInfo): Hand classNameForShadowRoot our primary-ness.
     15        * html/HTMLPlugInImageElement.h:
     16        (HTMLPlugInImageElement): Add storage for m_isPrimarySnapshottedPlugIn.
     17
    1182013-03-10  Mike West  <mkwst@chromium.org>
    219
  • trunk/Source/WebCore/WebCore.exp.in

    r145303 r145332  
    7777__ZN7WebCore10MouseEventC1ERKN3WTF12AtomicStringEbbNS1_10PassRefPtrINS_9DOMWindowEEEiiiiibbbbtNS5_INS_11EventTargetEEENS5_INS_9ClipboardEEEb
    7878__ZN7WebCore10RenderView10compositorEv
     79__ZN7WebCore10RenderView7hitTestERKNS_14HitTestRequestERNS_13HitTestResultE
    7980__ZN7WebCore10ScrollView17setUseFixedLayoutEb
    8081__ZN7WebCore10ScrollView18setFixedLayoutSizeERKNS_7IntSizeE
     
    249250__ZN7WebCore13HTTPHeaderMapD1Ev
    250251__ZN7WebCore13HitTestResultC1ERKS0_
     252__ZN7WebCore13HitTestResultC1ERKNS_11LayoutPointE
    251253__ZN7WebCore13HitTestResultD1Ev
    252254__ZN7WebCore13IdentifierRep3getEPKc
     
    674676__ZN7WebCore22systemMarketingVersionEv
    675677__ZN7WebCore22userPreferredLanguagesEv
     678__ZN7WebCore22HTMLPlugInImageElement29setIsPrimarySnapshottedPlugInEb
    676679__ZN7WebCore23ApplicationCacheStorage14setMaximumSizeEx
    677680__ZN7WebCore23ApplicationCacheStorage16deleteAllEntriesEv
     
    12551258__ZNK7WebCore13HitTestResult11targetFrameEv
    12561259__ZNK7WebCore13HitTestResult11textContentEv
     1260__ZNK7WebCore13HitTestResult12innerElementEv
    12571261__ZNK7WebCore13HitTestResult14absolutePDFURLEv
    12581262__ZNK7WebCore13HitTestResult14innerNodeFrameEv
     
    14321436__ZNK7WebCore4Page10pluginDataEv
    14331437__ZNK7WebCore4Page14renderTreeSizeEv
     1438__ZNK7WebCore4Page16hasSeenAnyPluginEv
    14341439__ZNK7WebCore4Page15backForwardListEv
    14351440__ZNK7WebCore4Page17viewportArgumentsEv
     
    15481553#endif
    15491554__ZNK7WebCore9PageCache10frameCountEv
     1555__ZNK7WebCore9RenderBox12clientHeightEv
     1556__ZNK7WebCore9RenderBox11clientWidthEv
    15501557__ZTVN7WebCore12ChromeClientE
    15511558__ZTVN7WebCore14LoaderStrategyE
  • trunk/Source/WebCore/html/HTMLPlugInImageElement.cpp

    r144690 r145332  
    7272    , m_shouldPreferPlugInsForImages(preferPlugInsForImagesOption == ShouldPreferPlugInsForImages)
    7373    , m_needsDocumentActivationCallbacks(false)
     74    , m_isPrimarySnapshottedPlugIn(false)
    7475    , m_simulatedMouseClickTimer(this, &HTMLPlugInImageElement::simulatedMouseClickTimerFired, simulatedMouseClickTimerDelay)
    7576    , m_swapRendererTimer(this, &HTMLPlugInImageElement::swapRendererTimerFired)
     
    296297}
    297298
    298 static AtomicString classNameForShadowRoot(const Node* node)
     299static AtomicString classNameForShadowRoot(const Node* node, bool isPrimary)
    299300{
    300301    DEFINE_STATIC_LOCAL(const AtomicString, plugInTinySizeClassName, ("tiny", AtomicString::ConstructFromLiteral));
     
    302303    DEFINE_STATIC_LOCAL(const AtomicString, plugInMediumSizeClassName, ("medium", AtomicString::ConstructFromLiteral));
    303304    DEFINE_STATIC_LOCAL(const AtomicString, plugInLargeSizeClassName, ("large", AtomicString::ConstructFromLiteral));
     305    DEFINE_STATIC_LOCAL(const AtomicString, plugInLargeSizePrimaryClassName, ("large primary", AtomicString::ConstructFromLiteral));
    304306
    305307    RenderBox* renderBox = static_cast<RenderBox*>(node->renderer());
     
    316318        return plugInMediumSizeClassName;
    317319
    318     return plugInLargeSizeClassName;
     320    return isPrimary ? plugInLargeSizePrimaryClassName : plugInLargeSizeClassName;
     321}
     322   
     323void HTMLPlugInImageElement::setIsPrimarySnapshottedPlugIn(bool isPrimarySnapshottedPlugIn)
     324{
     325    m_isPrimarySnapshottedPlugIn = isPrimarySnapshottedPlugIn;
     326   
     327    updateSnapshotInfo();
    319328}
    320329
     
    326335
    327336    Element* shadowContainer = static_cast<Element*>(root->firstChild());
    328     shadowContainer->setAttribute(classAttr, classNameForShadowRoot(this));
     337    shadowContainer->setAttribute(classAttr, classNameForShadowRoot(this, m_isPrimarySnapshottedPlugIn));
    329338}
    330339
  • trunk/Source/WebCore/html/HTMLPlugInImageElement.h

    r145196 r145332  
    7272    void subframeLoaderWillCreatePlugIn(const KURL& plugInURL);
    7373    void subframeLoaderDidCreatePlugIn(const Widget*);
     74   
     75    void setIsPrimarySnapshottedPlugIn(bool);
    7476
    7577protected:
     
    118120    bool m_shouldPreferPlugInsForImages;
    119121    bool m_needsDocumentActivationCallbacks;
     122    bool m_isPrimarySnapshottedPlugIn;
    120123    RefPtr<RenderStyle> m_customStyleForPageCache;
    121124    RefPtr<MouseEvent> m_pendingClickEventFromSnapshot;
  • trunk/Source/WebKit2/ChangeLog

    r145330 r145332  
     12013-03-10  Tim Horton  <timothy_horton@apple.com>
     2
     3        Add a heuristic to determine the “primary” snapshotted plugin
     4        https://bugs.webkit.org/show_bug.cgi?id=111932
     5        <rdar://problem/13270208>
     6
     7        Reviewed by Dean Jackson.
     8
     9        * WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp:
     10        (WebKit::WebFrameLoaderClient::dispatchDidCommitLoad):
     11        Forward didCommitLoad to WebPage. Move existing code that manipulated WebPage
     12        itself during didCommitLoad into WebPage, where it belongs.
     13        (WebKit::WebFrameLoaderClient::dispatchDidFinishLoad): Forward didFinishLoad to WebPage.
     14        * WebProcess/WebPage/WebPage.cpp:
     15        (WebKit::WebPage::WebPage): Initialize m_didFindPrimarySnapshottedPlugin to false.
     16        (WebKit::WebPage::didCommitLoad): Move code from WebPageFrameLoaderClient.
     17        Reset the flag that says we've already found a snapshotted plugin.
     18        (WebKit::WebPage::didFinishLoad):
     19        Call determinePrimarySnapshottedPlugIn when any frame finishes loading. We call this for subframes,
     20        not just the main frame, in case the main frame loads with no "primary" plugins, but a subframe later loads with one.
     21        (WebKit::WebPage::determinePrimarySnapshottedPlugIn):
     22        Attempt to find the primary snapshotted plugin on the page, by hit-testing a grid of points spaced 200px apart.
     23        A plugin is considered if it is snapshotted and > 450x300. We scan vertically and left-to-right, only discarding
     24        a previous candidate if another candidate is at least 110% the size of the previous candidate.
     25        This tends to select plugins near the top left of the page, unless there is a significantly larger plugin elsewhere.
     26        (WebKit::WebPage::resetPrimarySnapshottedPlugIn):
     27        * WebProcess/WebPage/WebPage.h:
     28        (WebPage):
     29
    1302013-03-10  Sheriff Bot  <webkit.review.bot@gmail.com>
    231
  • trunk/Source/WebKit2/WebProcess/WebCoreSupport/WebFrameLoaderClient.cpp

    r144568 r145332  
    445445    webPage->send(Messages::WebPageProxy::DidCommitLoadForFrame(m_frame->frameID(), response.mimeType(), m_frameHasCustomRepresentation, m_frame->coreFrame()->loader()->loadType(), PlatformCertificateInfo(response), InjectedBundleUserMessageEncoder(userData.get())));
    446446
    447     // Only restore the scale factor for standard frame loads (of the main frame).
    448     if (m_frame->isMainFrame() && m_frame->coreFrame()->loader()->loadType() == FrameLoadTypeStandard) {
    449         Page* page = m_frame->coreFrame()->page();
    450         if (page && page->pageScaleFactor() != 1)
    451             webPage->scalePage(1, IntPoint());
    452     }
     447    webPage->didCommitLoad(m_frame);
    453448}
    454449
     
    525520    if (WebFrame::LoadListener* loadListener = m_frame->loadListener())
    526521        loadListener->didFinishLoad(m_frame);
     522
     523    webPage->didFinishLoad(m_frame);
    527524}
    528525
  • trunk/Source/WebKit2/WebProcess/WebPage/WebPage.cpp

    r145300 r145332  
    102102#include <WebCore/HTMLInputElement.h>
    103103#include <WebCore/HTMLPlugInElement.h>
     104#include <WebCore/HTMLPlugInImageElement.h>
    104105#include <WebCore/HistoryItem.h>
    105106#include <WebCore/KeyboardEvent.h>
     
    236237    , m_scrollingPerformanceLoggingEnabled(false)
    237238    , m_mainFrameIsScrollable(true)
     239#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     240    , m_didFindPrimarySnapshottedPlugin(false)
     241#endif
    238242#if PLATFORM(MAC)
    239243    , m_pdfPluginEnabled(false)
     
    38653869}
    38663870
     3871void WebPage::didCommitLoad(WebFrame* frame)
     3872{
     3873    // Only restore the scale factor for standard frame loads (of the main frame).
     3874    if (frame->isMainFrame() && frame->coreFrame()->loader()->loadType() == FrameLoadTypeStandard) {
     3875        Page* page = frame->coreFrame()->page();
     3876        if (page && page->pageScaleFactor() != 1)
     3877            scalePage(1, IntPoint());
     3878    }
     3879
     3880#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     3881    if (frame->isMainFrame())
     3882        resetPrimarySnapshottedPlugIn();
     3883#endif
     3884}
     3885
     3886void WebPage::didFinishLoad(WebFrame* frame)
     3887{
     3888#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     3889    determinePrimarySnapshottedPlugIn();
     3890#endif
     3891}
     3892
     3893#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     3894static int primarySnapshottedPlugInSearchLimit = 3000;
     3895static int primarySnapshottedPlugInSearchGap = 200;
     3896static float primarySnapshottedPlugInSearchBucketSize = 1.1;
     3897static int primarySnapshottedPlugInMinimumWidth = 450;
     3898static int primarySnapshottedPlugInMinimumHeight = 300;
     3899
     3900void WebPage::determinePrimarySnapshottedPlugIn()
     3901{
     3902    if (!corePage()->hasSeenAnyPlugin())
     3903        return;
     3904
     3905    if (m_didFindPrimarySnapshottedPlugin)
     3906        return;
     3907
     3908    RenderView* renderView = corePage()->mainFrame()->view()->renderView();
     3909
     3910    IntRect searchRect = IntRect(IntPoint(), corePage()->mainFrame()->view()->contentsSize());
     3911    searchRect.intersect(IntRect(IntPoint(), IntSize(primarySnapshottedPlugInSearchLimit, primarySnapshottedPlugInSearchLimit)));
     3912
     3913    HitTestRequest request(HitTestRequest::ReadOnly | HitTestRequest::Active | HitTestRequest::AllowChildFrameContent | HitTestRequest::IgnoreClipping);
     3914
     3915    HashSet<RenderObject*> seenRenderers;
     3916    HTMLPlugInImageElement* candidatePlugIn = 0;
     3917    unsigned candidatePlugInArea = 0;
     3918
     3919    for (int x = searchRect.x(); x <= searchRect.width(); x += primarySnapshottedPlugInSearchGap) {
     3920        for (int y = searchRect.y(); y <= searchRect.height(); y += primarySnapshottedPlugInSearchGap) {
     3921            HitTestResult hitTestResult = HitTestResult(LayoutPoint(x, y));
     3922            renderView->hitTest(request, hitTestResult);
     3923
     3924            Element* element = hitTestResult.innerElement();
     3925            if (!element)
     3926                continue;
     3927
     3928            RenderObject* renderer = element->renderer();
     3929            if (!renderer || !renderer->isBox())
     3930                continue;
     3931
     3932            RenderBox* renderBox = toRenderBox(renderer);
     3933
     3934            if (seenRenderers.contains(renderer))
     3935                continue;
     3936            seenRenderers.add(renderer);
     3937
     3938            if (!element->isPluginElement())
     3939                continue;
     3940
     3941            HTMLPlugInElement* plugInElement = toHTMLPlugInElement(element);
     3942            if (!plugInElement->isPlugInImageElement())
     3943                continue;
     3944
     3945            HTMLPlugInImageElement* plugInImageElement = toHTMLPlugInImageElement(plugInElement);
     3946
     3947            if (plugInElement->displayState() == HTMLPlugInElement::Playing)
     3948                continue;
     3949
     3950            if (renderBox->contentWidth() < primarySnapshottedPlugInMinimumWidth || renderBox->contentHeight() < primarySnapshottedPlugInMinimumHeight)
     3951                continue;
     3952
     3953            LayoutUnit contentArea = renderBox->contentWidth() * renderBox->contentHeight();
     3954
     3955            if (contentArea > candidatePlugInArea * primarySnapshottedPlugInSearchBucketSize) {
     3956                candidatePlugIn = plugInImageElement;
     3957                candidatePlugInArea = contentArea;
     3958            }
     3959        }
     3960    }
     3961
     3962    if (!candidatePlugIn)
     3963        return;
     3964
     3965    m_didFindPrimarySnapshottedPlugin = true;
     3966
     3967    candidatePlugIn->setIsPrimarySnapshottedPlugIn(true);
     3968}
     3969
     3970void WebPage::resetPrimarySnapshottedPlugIn()
     3971{
     3972    m_didFindPrimarySnapshottedPlugin = false;
     3973}
     3974#endif // ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     3975
    38673976} // namespace WebKit
  • trunk/Source/WebKit2/WebProcess/WebPage/WebPage.h

    r145255 r145332  
    9999OBJC_CLASS NSObject;
    100100OBJC_CLASS WKAccessibilityWebPageObject;
     101
     102#define WTF_ENABLE_PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC 1
    101103#endif
    102104
     
    218220    void didStartPageTransition();
    219221    void didCompletePageTransition();
     222    void didCommitLoad(WebFrame*);
     223    void didFinishLoad(WebFrame*);
    220224    void show();
    221225    String userAgent() const { return m_userAgent; }
     
    631635    void didCancelCheckingText(uint64_t requestID);
    632636
     637#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     638    void determinePrimarySnapshottedPlugIn();
     639    void resetPrimarySnapshottedPlugIn();
     640#endif
     641
    633642private:
    634643    WebPage(uint64_t pageID, const WebPageCreationParameters&);
     
    845854    bool m_mainFrameIsScrollable;
    846855
     856#if ENABLE(PRIMARY_SNAPSHOTTED_PLUGIN_HEURISTIC)
     857    bool m_didFindPrimarySnapshottedPlugin;
     858#endif
     859
    847860#if PLATFORM(MAC)
    848861    bool m_pdfPluginEnabled;
Note: See TracChangeset for help on using the changeset viewer.