1/* 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Apple Inc. All Rights Reserved. 3 * Copyright (C) 2008 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/) 4 * 5 * This library is free software; you can redistribute it and/or 6 * modify it under the terms of the GNU Library General Public 7 * License as published by the Free Software Foundation; either 8 * version 2 of the License, or (at your option) any later version. 9 * This library is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * Library General Public License for more details. 13 * 14 * You should have received a copy of the GNU Library General Public License 15 * along with this library; see the file COPYING.LIB. If not, write to 16 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 17 * Boston, MA 02110-1301, USA. 18 */ 19 20#include "config.h" 21#include "core/page/Page.h" 22 23#include "core/dom/ClientRectList.h" 24#include "core/dom/DocumentMarkerController.h" 25#include "core/dom/StyleEngine.h" 26#include "core/dom/VisitedLinkState.h" 27#include "core/editing/Caret.h" 28#include "core/editing/UndoStack.h" 29#include "core/events/Event.h" 30#include "core/fetch/ResourceFetcher.h" 31#include "core/frame/DOMTimer.h" 32#include "core/frame/FrameConsole.h" 33#include "core/frame/FrameHost.h" 34#include "core/frame/FrameView.h" 35#include "core/frame/LocalDOMWindow.h" 36#include "core/frame/LocalFrame.h" 37#include "core/frame/RemoteFrame.h" 38#include "core/frame/RemoteFrameView.h" 39#include "core/frame/Settings.h" 40#include "core/inspector/InspectorController.h" 41#include "core/inspector/InspectorInstrumentation.h" 42#include "core/loader/FrameLoader.h" 43#include "core/loader/HistoryItem.h" 44#include "core/page/AutoscrollController.h" 45#include "core/page/Chrome.h" 46#include "core/page/ChromeClient.h" 47#include "core/page/ContextMenuController.h" 48#include "core/page/DragController.h" 49#include "core/page/FocusController.h" 50#include "core/page/FrameTree.h" 51#include "core/page/PageLifecycleNotifier.h" 52#include "core/page/PointerLockController.h" 53#include "core/page/StorageClient.h" 54#include "core/page/ValidationMessageClient.h" 55#include "core/page/scrolling/ScrollingCoordinator.h" 56#include "core/rendering/RenderView.h" 57#include "core/rendering/TextAutosizer.h" 58#include "core/storage/StorageNamespace.h" 59#include "platform/plugins/PluginData.h" 60#include "wtf/HashMap.h" 61#include "wtf/RefCountedLeakCounter.h" 62#include "wtf/StdLibExtras.h" 63#include "wtf/text/Base64.h" 64 65namespace blink { 66 67DEFINE_DEBUG_ONLY_GLOBAL(WTF::RefCountedLeakCounter, pageCounter, ("Page")); 68 69// static 70HashSet<Page*>& Page::allPages() 71{ 72 DEFINE_STATIC_LOCAL(HashSet<Page*>, allPages, ()); 73 return allPages; 74} 75 76// static 77HashSet<Page*>& Page::ordinaryPages() 78{ 79 DEFINE_STATIC_LOCAL(HashSet<Page*>, ordinaryPages, ()); 80 return ordinaryPages; 81} 82 83 84void Page::networkStateChanged(bool online) 85{ 86 WillBeHeapVector<RefPtrWillBeMember<LocalFrame> > frames; 87 88 // Get all the frames of all the pages in all the page groups 89 HashSet<Page*>::iterator end = allPages().end(); 90 for (HashSet<Page*>::iterator it = allPages().begin(); it != end; ++it) { 91 for (Frame* frame = (*it)->mainFrame(); frame; frame = frame->tree().traverseNext()) { 92 // FIXME: There is currently no way to dispatch events to out-of-process frames. 93 if (frame->isLocalFrame()) 94 frames.append(toLocalFrame(frame)); 95 } 96 InspectorInstrumentation::networkStateChanged(*it, online); 97 } 98 99 AtomicString eventName = online ? EventTypeNames::online : EventTypeNames::offline; 100 for (unsigned i = 0; i < frames.size(); i++) 101 frames[i]->domWindow()->dispatchEvent(Event::create(eventName)); 102} 103 104float deviceScaleFactor(LocalFrame* frame) 105{ 106 if (!frame) 107 return 1; 108 Page* page = frame->page(); 109 if (!page) 110 return 1; 111 return page->deviceScaleFactor(); 112} 113 114Page::Page(PageClients& pageClients) 115 : SettingsDelegate(Settings::create()) 116 , m_animator(PageAnimator::create(*this)) 117 , m_autoscrollController(AutoscrollController::create(*this)) 118 , m_chrome(Chrome::create(this, pageClients.chromeClient)) 119 , m_dragCaretController(DragCaretController::create()) 120 , m_dragController(DragController::create(this, pageClients.dragClient)) 121 , m_focusController(FocusController::create(this)) 122 , m_contextMenuController(ContextMenuController::create(this, pageClients.contextMenuClient)) 123 , m_inspectorController(InspectorController::create(this, pageClients.inspectorClient)) 124 , m_pointerLockController(PointerLockController::create(this)) 125 , m_undoStack(UndoStack::create()) 126 , m_mainFrame(nullptr) 127 , m_backForwardClient(pageClients.backForwardClient) 128 , m_editorClient(pageClients.editorClient) 129 , m_spellCheckerClient(pageClients.spellCheckerClient) 130 , m_storageClient(pageClients.storageClient) 131 , m_subframeCount(0) 132 , m_openedByDOM(false) 133 , m_tabKeyCyclesThroughElements(true) 134 , m_defersLoading(false) 135 , m_deviceScaleFactor(1) 136 , m_timerAlignmentInterval(DOMTimer::visiblePageAlignmentInterval()) 137 , m_visibilityState(PageVisibilityStateVisible) 138 , m_isCursorVisible(true) 139#if ENABLE(ASSERT) 140 , m_isPainting(false) 141#endif 142 , m_frameHost(FrameHost::create(*this)) 143{ 144 ASSERT(m_editorClient); 145 146 ASSERT(!allPages().contains(this)); 147 allPages().add(this); 148 149#ifndef NDEBUG 150 pageCounter.increment(); 151#endif 152} 153 154Page::~Page() 155{ 156 // willBeDestroyed() must be called before Page destruction. 157 ASSERT(!m_mainFrame); 158} 159 160void Page::makeOrdinary() 161{ 162 ASSERT(!ordinaryPages().contains(this)); 163 ordinaryPages().add(this); 164} 165 166ViewportDescription Page::viewportDescription() const 167{ 168 return mainFrame() && mainFrame()->isLocalFrame() && deprecatedLocalMainFrame()->document() ? deprecatedLocalMainFrame()->document()->viewportDescription() : ViewportDescription(); 169} 170 171ScrollingCoordinator* Page::scrollingCoordinator() 172{ 173 if (!m_scrollingCoordinator && m_settings->acceleratedCompositingEnabled()) 174 m_scrollingCoordinator = ScrollingCoordinator::create(this); 175 176 return m_scrollingCoordinator.get(); 177} 178 179String Page::mainThreadScrollingReasonsAsText() 180{ 181 if (ScrollingCoordinator* scrollingCoordinator = this->scrollingCoordinator()) 182 return scrollingCoordinator->mainThreadScrollingReasonsAsText(); 183 184 return String(); 185} 186 187PassRefPtrWillBeRawPtr<ClientRectList> Page::nonFastScrollableRects(const LocalFrame* frame) 188{ 189 if (m_mainFrame->isLocalFrame() && deprecatedLocalMainFrame()->document()) 190 deprecatedLocalMainFrame()->document()->updateLayout(); 191 192 Vector<IntRect> rects; 193 if (ScrollingCoordinator* scrollingCoordinator = this->scrollingCoordinator()) 194 rects = scrollingCoordinator->computeShouldHandleScrollGestureOnMainThreadRegion(frame, IntPoint()).rects(); 195 196 Vector<FloatQuad> quads(rects.size()); 197 for (size_t i = 0; i < rects.size(); ++i) 198 quads[i] = FloatRect(rects[i]); 199 return ClientRectList::create(quads); 200} 201 202void Page::setMainFrame(Frame* mainFrame) 203{ 204 // Should only be called during initialization or swaps between local and 205 // remote frames. 206 // FIXME: Unfortunately we can't assert on this at the moment, because this 207 // is called in the base constructor for both LocalFrame and RemoteFrame, 208 // when the vtables for the derived classes have not yet been setup. 209 m_mainFrame = mainFrame; 210} 211 212void Page::documentDetached(Document* document) 213{ 214 m_multisamplingChangedObservers.clear(); 215 m_pointerLockController->documentDetached(document); 216 m_contextMenuController->documentDetached(document); 217 if (m_validationMessageClient) 218 m_validationMessageClient->documentDetached(*document); 219} 220 221bool Page::openedByDOM() const 222{ 223 return m_openedByDOM; 224} 225 226void Page::setOpenedByDOM() 227{ 228 m_openedByDOM = true; 229} 230 231void Page::scheduleForcedStyleRecalcForAllPages() 232{ 233 HashSet<Page*>::iterator end = allPages().end(); 234 for (HashSet<Page*>::iterator it = allPages().begin(); it != end; ++it) 235 for (Frame* frame = (*it)->mainFrame(); frame; frame = frame->tree().traverseNext()) { 236 if (frame->isLocalFrame()) 237 toLocalFrame(frame)->document()->setNeedsStyleRecalc(SubtreeStyleChange); 238 } 239} 240 241void Page::setNeedsRecalcStyleInAllFrames() 242{ 243 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 244 if (frame->isLocalFrame()) 245 toLocalFrame(frame)->document()->styleResolverChanged(); 246 } 247} 248 249void Page::setNeedsLayoutInAllFrames() 250{ 251 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 252 if (!frame->isLocalFrame()) 253 continue; 254 if (FrameView* view = toLocalFrame(frame)->view()) { 255 view->setNeedsLayout(); 256 view->scheduleRelayout(); 257 } 258 } 259} 260 261void Page::refreshPlugins(bool reload) 262{ 263 if (allPages().isEmpty()) 264 return; 265 266 PluginData::refresh(); 267 268 WillBeHeapVector<RefPtrWillBeMember<LocalFrame> > framesNeedingReload; 269 270 HashSet<Page*>::iterator end = allPages().end(); 271 for (HashSet<Page*>::iterator it = allPages().begin(); it != end; ++it) { 272 Page* page = *it; 273 274 // Clear out the page's plug-in data. 275 if (page->m_pluginData) 276 page->m_pluginData = nullptr; 277 278 if (!reload) 279 continue; 280 281 for (Frame* frame = (*it)->mainFrame(); frame; frame = frame->tree().traverseNext()) { 282 if (frame->isLocalFrame() && toLocalFrame(frame)->document()->containsPlugins()) 283 framesNeedingReload.append(toLocalFrame(frame)); 284 } 285 } 286 287 for (size_t i = 0; i < framesNeedingReload.size(); ++i) 288 framesNeedingReload[i]->loader().reload(); 289} 290 291PluginData* Page::pluginData() const 292{ 293 if (!deprecatedLocalMainFrame()->loader().allowPlugins(NotAboutToInstantiatePlugin)) 294 return 0; 295 if (!m_pluginData) 296 m_pluginData = PluginData::create(this); 297 return m_pluginData.get(); 298} 299 300static Frame* incrementFrame(Frame* curr, bool forward, bool wrapFlag) 301{ 302 return forward 303 ? curr->tree().traverseNextWithWrap(wrapFlag) 304 : curr->tree().traversePreviousWithWrap(wrapFlag); 305} 306 307void Page::unmarkAllTextMatches() 308{ 309 if (!mainFrame()) 310 return; 311 312 Frame* frame = mainFrame(); 313 do { 314 if (frame->isLocalFrame()) 315 toLocalFrame(frame)->document()->markers().removeMarkers(DocumentMarker::TextMatch); 316 frame = incrementFrame(frame, true, false); 317 } while (frame); 318} 319 320void Page::setValidationMessageClient(PassOwnPtrWillBeRawPtr<ValidationMessageClient> client) 321{ 322 m_validationMessageClient = client; 323} 324 325void Page::setDefersLoading(bool defers) 326{ 327 if (defers == m_defersLoading) 328 return; 329 330 m_defersLoading = defers; 331 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 332 if (frame->isLocalFrame()) 333 toLocalFrame(frame)->loader().setDefersLoading(defers); 334 } 335} 336 337void Page::setPageScaleFactor(float scale, const IntPoint& origin) 338{ 339 if (!mainFrame()->isLocalFrame()) 340 return; 341 342 FrameView* view = deprecatedLocalMainFrame()->view(); 343 PinchViewport& viewport = frameHost().pinchViewport(); 344 345 if (scale != viewport.scale()) { 346 viewport.setScale(scale); 347 348 if (view && !settings().pinchVirtualViewportEnabled()) 349 view->setVisibleContentScaleFactor(scale); 350 351 deprecatedLocalMainFrame()->deviceOrPageScaleFactorChanged(); 352 m_chrome->client().deviceOrPageScaleFactorChanged(); 353 354 // FIXME: In virtual-viewport pinch mode, scale doesn't change the fixed-pos viewport; 355 // remove once it's the only pinch mode in town. 356 if (view) 357 view->viewportConstrainedVisibleContentSizeChanged(true, true); 358 359 deprecatedLocalMainFrame()->loader().saveScrollState(); 360 } 361 362 if (view && view->scrollPosition() != origin) 363 view->notifyScrollPositionChanged(origin); 364} 365 366float Page::pageScaleFactor() const 367{ 368 return frameHost().pinchViewport().scale(); 369} 370 371void Page::setDeviceScaleFactor(float scaleFactor) 372{ 373 if (m_deviceScaleFactor == scaleFactor) 374 return; 375 376 m_deviceScaleFactor = scaleFactor; 377 setNeedsRecalcStyleInAllFrames(); 378 379 if (mainFrame() && mainFrame()->isLocalFrame()) { 380 deprecatedLocalMainFrame()->deviceOrPageScaleFactorChanged(); 381 m_chrome->client().deviceOrPageScaleFactorChanged(); 382 } 383} 384 385void Page::setDeviceColorProfile(const Vector<char>& profile) 386{ 387 // FIXME: implement. 388} 389 390void Page::resetDeviceColorProfile() 391{ 392 // FIXME: implement. 393} 394 395void Page::allVisitedStateChanged() 396{ 397 HashSet<Page*>::iterator pagesEnd = ordinaryPages().end(); 398 for (HashSet<Page*>::iterator it = ordinaryPages().begin(); it != pagesEnd; ++it) { 399 Page* page = *it; 400 for (Frame* frame = page->m_mainFrame; frame; frame = frame->tree().traverseNext()) { 401 if (frame->isLocalFrame()) 402 toLocalFrame(frame)->document()->visitedLinkState().invalidateStyleForAllLinks(); 403 } 404 } 405} 406 407void Page::visitedStateChanged(LinkHash linkHash) 408{ 409 HashSet<Page*>::iterator pagesEnd = ordinaryPages().end(); 410 for (HashSet<Page*>::iterator it = ordinaryPages().begin(); it != pagesEnd; ++it) { 411 Page* page = *it; 412 for (Frame* frame = page->m_mainFrame; frame; frame = frame->tree().traverseNext()) { 413 if (frame->isLocalFrame()) 414 toLocalFrame(frame)->document()->visitedLinkState().invalidateStyleForLink(linkHash); 415 } 416 } 417} 418 419StorageNamespace* Page::sessionStorage(bool optionalCreate) 420{ 421 if (!m_sessionStorage && optionalCreate) 422 m_sessionStorage = m_storageClient->createSessionStorageNamespace(); 423 return m_sessionStorage.get(); 424} 425 426void Page::setTimerAlignmentInterval(double interval) 427{ 428 if (interval == m_timerAlignmentInterval) 429 return; 430 431 m_timerAlignmentInterval = interval; 432 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNextWithWrap(false)) { 433 if (frame->isLocalFrame() && toLocalFrame(frame)->document()) 434 toLocalFrame(frame)->document()->didChangeTimerAlignmentInterval(); 435 } 436} 437 438double Page::timerAlignmentInterval() const 439{ 440 return m_timerAlignmentInterval; 441} 442 443#if ENABLE(ASSERT) 444void Page::checkSubframeCountConsistency() const 445{ 446 ASSERT(m_subframeCount >= 0); 447 448 int subframeCount = 0; 449 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) 450 ++subframeCount; 451 452 ASSERT(m_subframeCount + 1 == subframeCount); 453} 454#endif 455 456void Page::setVisibilityState(PageVisibilityState visibilityState, bool isInitialState) 457{ 458 if (m_visibilityState == visibilityState) 459 return; 460 m_visibilityState = visibilityState; 461 462 if (visibilityState == blink::PageVisibilityStateVisible) 463 setTimerAlignmentInterval(DOMTimer::visiblePageAlignmentInterval()); 464 else 465 setTimerAlignmentInterval(DOMTimer::hiddenPageAlignmentInterval()); 466 467 if (!isInitialState) 468 lifecycleNotifier().notifyPageVisibilityChanged(); 469 470 if (!isInitialState && m_mainFrame && m_mainFrame->isLocalFrame()) 471 deprecatedLocalMainFrame()->didChangeVisibilityState(); 472} 473 474PageVisibilityState Page::visibilityState() const 475{ 476 return m_visibilityState; 477} 478 479bool Page::isCursorVisible() const 480{ 481 return m_isCursorVisible && settings().deviceSupportsMouse(); 482} 483 484void Page::addMultisamplingChangedObserver(MultisamplingChangedObserver* observer) 485{ 486 m_multisamplingChangedObservers.add(observer); 487} 488 489void Page::removeMultisamplingChangedObserver(MultisamplingChangedObserver* observer) 490{ 491 m_multisamplingChangedObservers.remove(observer); 492} 493 494void Page::settingsChanged(SettingsDelegate::ChangeType changeType) 495{ 496 switch (changeType) { 497 case SettingsDelegate::StyleChange: 498 setNeedsRecalcStyleInAllFrames(); 499 break; 500 case SettingsDelegate::ViewportDescriptionChange: 501 if (mainFrame() && mainFrame()->isLocalFrame()) 502 deprecatedLocalMainFrame()->document()->updateViewportDescription(); 503 break; 504 case SettingsDelegate::MediaTypeChange: 505 if (m_mainFrame->isLocalFrame()) { 506 deprecatedLocalMainFrame()->view()->setMediaType(AtomicString(settings().mediaTypeOverride())); 507 setNeedsRecalcStyleInAllFrames(); 508 } 509 break; 510 case SettingsDelegate::DNSPrefetchingChange: 511 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 512 if (frame->isLocalFrame()) 513 toLocalFrame(frame)->document()->initDNSPrefetch(); 514 } 515 break; 516 case SettingsDelegate::MultisamplingChange: { 517 WillBeHeapHashSet<RawPtrWillBeWeakMember<MultisamplingChangedObserver> >::iterator stop = m_multisamplingChangedObservers.end(); 518 for (WillBeHeapHashSet<RawPtrWillBeWeakMember<MultisamplingChangedObserver> >::iterator it = m_multisamplingChangedObservers.begin(); it != stop; ++it) 519 (*it)->multisamplingChanged(m_settings->openGLMultisamplingEnabled()); 520 break; 521 } 522 case SettingsDelegate::ImageLoadingChange: 523 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 524 if (frame->isLocalFrame()) { 525 toLocalFrame(frame)->document()->fetcher()->setImagesEnabled(settings().imagesEnabled()); 526 toLocalFrame(frame)->document()->fetcher()->setAutoLoadImages(settings().loadsImagesAutomatically()); 527 } 528 } 529 break; 530 case SettingsDelegate::TextAutosizingChange: 531 if (!mainFrame() || !mainFrame()->isLocalFrame()) 532 break; 533 if (TextAutosizer* textAutosizer = deprecatedLocalMainFrame()->document()->textAutosizer()) 534 textAutosizer->updatePageInfoInAllFrames(); 535 break; 536 case SettingsDelegate::ScriptEnableChange: 537 m_inspectorController->scriptsEnabled(settings().scriptEnabled()); 538 break; 539 case SettingsDelegate::FontFamilyChange: 540 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 541 if (frame->isLocalFrame()) 542 toLocalFrame(frame)->document()->styleEngine()->updateGenericFontFamilySettings(); 543 } 544 setNeedsRecalcStyleInAllFrames(); 545 break; 546 case SettingsDelegate::AcceleratedCompositingChange: 547 updateAcceleratedCompositingSettings(); 548 break; 549 case SettingsDelegate::MediaQueryChange: 550 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 551 if (frame->isLocalFrame()) 552 toLocalFrame(frame)->document()->mediaQueryAffectingValueChanged(); 553 } 554 setNeedsRecalcStyleInAllFrames(); 555 break; 556 } 557} 558 559void Page::updateAcceleratedCompositingSettings() 560{ 561 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 562 if (!frame->isLocalFrame()) 563 continue; 564 if (FrameView* view = toLocalFrame(frame)->view()) 565 view->updateAcceleratedCompositingSettings(); 566 } 567} 568 569void Page::didCommitLoad(LocalFrame* frame) 570{ 571 lifecycleNotifier().notifyDidCommitLoad(frame); 572 if (m_mainFrame == frame) { 573 frame->console().clearMessages(); 574 useCounter().didCommitLoad(); 575 m_inspectorController->didCommitLoadForMainFrame(); 576 UserGestureIndicator::clearProcessedUserGestureSinceLoad(); 577 } 578} 579 580void Page::acceptLanguagesChanged() 581{ 582 WillBeHeapVector<RefPtrWillBeMember<LocalFrame> > frames; 583 584 // Even though we don't fire an event from here, the LocalDOMWindow's will fire 585 // an event so we keep the frames alive until we are done. 586 for (Frame* frame = mainFrame(); frame; frame = frame->tree().traverseNext()) { 587 if (frame->isLocalFrame()) 588 frames.append(toLocalFrame(frame)); 589 } 590 591 for (unsigned i = 0; i < frames.size(); ++i) 592 frames[i]->domWindow()->acceptLanguagesChanged(); 593} 594 595PageLifecycleNotifier& Page::lifecycleNotifier() 596{ 597 return static_cast<PageLifecycleNotifier&>(LifecycleContext<Page>::lifecycleNotifier()); 598} 599 600PassOwnPtr<LifecycleNotifier<Page> > Page::createLifecycleNotifier() 601{ 602 return PageLifecycleNotifier::create(this); 603} 604 605void Page::trace(Visitor* visitor) 606{ 607#if ENABLE(OILPAN) 608 visitor->trace(m_animator); 609 visitor->trace(m_dragCaretController); 610 visitor->trace(m_dragController); 611 visitor->trace(m_focusController); 612 visitor->trace(m_contextMenuController); 613 visitor->trace(m_inspectorController); 614 visitor->trace(m_pointerLockController); 615 visitor->trace(m_undoStack); 616 visitor->trace(m_mainFrame); 617 visitor->trace(m_validationMessageClient); 618 visitor->trace(m_multisamplingChangedObservers); 619 visitor->trace(m_frameHost); 620 HeapSupplementable<Page>::trace(visitor); 621#endif 622 LifecycleContext<Page>::trace(visitor); 623} 624 625void Page::willBeDestroyed() 626{ 627 // Destroy inspector first, since it uses frame and view during destruction. 628 m_inspectorController->willBeDestroyed(); 629 630 RefPtrWillBeRawPtr<Frame> mainFrame = m_mainFrame; 631 632 mainFrame->detach(); 633 634 if (mainFrame->isLocalFrame()) { 635 toLocalFrame(mainFrame.get())->setView(nullptr); 636 } else { 637 ASSERT(m_mainFrame->isRemoteFrame()); 638 toRemoteFrame(mainFrame.get())->setView(nullptr); 639 } 640 641 allPages().remove(this); 642 if (ordinaryPages().contains(this)) 643 ordinaryPages().remove(this); 644 645 if (m_scrollingCoordinator) 646 m_scrollingCoordinator->willBeDestroyed(); 647 648#ifndef NDEBUG 649 pageCounter.decrement(); 650#endif 651 652 m_chrome->willBeDestroyed(); 653 if (m_validationMessageClient) 654 m_validationMessageClient->willBeDestroyed(); 655 m_mainFrame = nullptr; 656} 657 658Page::PageClients::PageClients() 659 : chromeClient(0) 660 , contextMenuClient(0) 661 , editorClient(0) 662 , dragClient(0) 663 , inspectorClient(0) 664 , backForwardClient(0) 665 , spellCheckerClient(0) 666 , storageClient(0) 667{ 668} 669 670Page::PageClients::~PageClients() 671{ 672} 673 674} // namespace blink 675