diff options
author | Lorry Tar Creator <lorry-tar-importer@lorry> | 2017-06-27 06:07:23 +0000 |
---|---|---|
committer | Lorry Tar Creator <lorry-tar-importer@lorry> | 2017-06-27 06:07:23 +0000 |
commit | 1bf1084f2b10c3b47fd1a588d85d21ed0eb41d0c (patch) | |
tree | 46dcd36c86e7fbc6e5df36deb463b33e9967a6f7 /Source/WebCore/history/CachedPage.cpp | |
parent | 32761a6cee1d0dee366b885b7b9c777e67885688 (diff) | |
download | WebKitGtk-tarball-master.tar.gz |
webkitgtk-2.16.5HEADwebkitgtk-2.16.5master
Diffstat (limited to 'Source/WebCore/history/CachedPage.cpp')
-rw-r--r-- | Source/WebCore/history/CachedPage.cpp | 103 |
1 files changed, 68 insertions, 35 deletions
diff --git a/Source/WebCore/history/CachedPage.cpp b/Source/WebCore/history/CachedPage.cpp index cad18497e..3ddd9c18d 100644 --- a/Source/WebCore/history/CachedPage.cpp +++ b/Source/WebCore/history/CachedPage.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. + * Copyright (C) 2006, 2007, 2008, 2014 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -10,10 +10,10 @@ * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * - * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY + * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR @@ -30,9 +30,13 @@ #include "Element.h" #include "FocusController.h" #include "FrameView.h" +#include "HistoryController.h" +#include "HistoryItem.h" #include "MainFrame.h" +#include "NoEventDispatchAssertion.h" #include "Node.h" #include "Page.h" +#include "PageTransitionEvent.h" #include "Settings.h" #include "VisitedLinkState.h" #include <wtf/CurrentTime.h> @@ -50,13 +54,9 @@ namespace WebCore { DEFINE_DEBUG_ONLY_GLOBAL(WTF::RefCountedLeakCounter, cachedPageCounter, ("CachedPage")); CachedPage::CachedPage(Page& page) - : m_timeStamp(monotonicallyIncreasingTime()) - , m_expirationTime(m_timeStamp + page.settings().backForwardCacheExpirationInterval()) + : m_page(page) + , m_expirationTime(monotonicallyIncreasingTime() + page.settings().backForwardCacheExpirationInterval()) , m_cachedMainFrame(std::make_unique<CachedFrame>(page.mainFrame())) - , m_needStyleRecalcForVisitedLinks(false) - , m_needsFullStyleRecalc(false) - , m_needsCaptionPreferencesChanged(false) - , m_needsDeviceScaleChanged(false) { #ifndef NDEBUG cachedPageCounter.increment(); @@ -69,8 +69,33 @@ CachedPage::~CachedPage() cachedPageCounter.decrement(); #endif - destroy(); - ASSERT(!m_cachedMainFrame); + if (m_cachedMainFrame) + m_cachedMainFrame->destroy(); +} + +static void firePageShowAndPopStateEvents(Page& page) +{ + // Dispatching JavaScript events can cause frame destruction. + auto& mainFrame = page.mainFrame(); + Vector<Ref<Frame>> childFrames; + for (auto* child = mainFrame.tree().traverseNextInPostOrderWithWrap(true); child; child = child->tree().traverseNextInPostOrderWithWrap(false)) + childFrames.append(*child); + + for (auto& child : childFrames) { + if (!child->tree().isDescendantOf(&mainFrame)) + continue; + auto* document = child->document(); + if (!document) + continue; + + // FIXME: Update Page Visibility state here. + // https://bugs.webkit.org/show_bug.cgi?id=116770 + document->dispatchPageshowEvent(PageshowEventPersisted); + + auto* historyItem = child->loader().history().currentItem(); + if (historyItem && historyItem->stateObject()) + document->dispatchPopstateEvent(historyItem->stateObject()); + } } void CachedPage::restore(Page& page) @@ -79,7 +104,13 @@ void CachedPage::restore(Page& page) ASSERT(m_cachedMainFrame->view()->frame().isMainFrame()); ASSERT(!page.subframeCount()); - m_cachedMainFrame->open(); + { + // Do not dispatch DOM events as their JavaScript listeners could cause the page to be put + // into the page cache before we have finished restoring it from the page cache. + NoEventDispatchAssertion noEventDispatchAssertion; + + m_cachedMainFrame->open(); + } // Restore the focus appearance for the focused element. // FIXME: Right now we don't support pages w/ frames in the b/f cache. This may need to be tweaked when we add support for that. @@ -89,32 +120,39 @@ void CachedPage::restore(Page& page) // We don't want focused nodes changing scroll position when restoring from the cache // as it can cause ugly jumps before we manage to restore the cached position. page.mainFrame().selection().suppressScrolling(); + + bool hadProhibitsScrolling = false; + FrameView* frameView = page.mainFrame().view(); + if (frameView) { + hadProhibitsScrolling = frameView->prohibitsScrolling(); + frameView->setProhibitsScrolling(true); + } #endif - element->updateFocusAppearance(true); + element->updateFocusAppearance(SelectionRestorationMode::Restore); #if PLATFORM(IOS) + if (frameView) + frameView->setProhibitsScrolling(hadProhibitsScrolling); page.mainFrame().selection().restoreScrolling(); #endif } - if (m_needStyleRecalcForVisitedLinks) { - for (Frame* frame = &page.mainFrame(); frame; frame = frame->tree().traverseNext()) - frame->document()->visitedLinkState().invalidateStyleForAllLinks(); - } - -#if USE(ACCELERATED_COMPOSITING) - if (m_needsDeviceScaleChanged) { + if (m_needsDeviceOrPageScaleChanged) page.mainFrame().deviceOrPageScaleFactorChanged(); - } -#endif - if (m_needsFullStyleRecalc) - page.setNeedsRecalcStyleInAllFrames(); + page.setNeedsRecalcStyleInAllFrames(); #if ENABLE(VIDEO_TRACK) if (m_needsCaptionPreferencesChanged) page.captionPreferencesChanged(); #endif + if (m_needsUpdateContentsSize) { + if (FrameView* frameView = page.mainFrame().view()) + frameView->updateContentsSize(); + } + + firePageShowAndPopStateEvents(page); + clear(); } @@ -122,17 +160,12 @@ void CachedPage::clear() { ASSERT(m_cachedMainFrame); m_cachedMainFrame->clear(); - m_cachedMainFrame = 0; - m_needStyleRecalcForVisitedLinks = false; - m_needsFullStyleRecalc = false; -} - -void CachedPage::destroy() -{ - if (m_cachedMainFrame) - m_cachedMainFrame->destroy(); - - m_cachedMainFrame = 0; + m_cachedMainFrame = nullptr; +#if ENABLE(VIDEO_TRACK) + m_needsCaptionPreferencesChanged = false; +#endif + m_needsDeviceOrPageScaleChanged = false; + m_needsUpdateContentsSize = false; } bool CachedPage::hasExpired() const |