| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2006, 2007, 2009 Apple Inc. All rights reserved. | 2 * Copyright (C) 2006, 2007, 2009 Apple Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * This library is free software; you can redistribute it and/or | 4 * This library is free software; you can redistribute it and/or |
| 5 * modify it under the terms of the GNU Library General Public | 5 * modify it under the terms of the GNU Library General Public |
| 6 * License as published by the Free Software Foundation; either | 6 * License as published by the Free Software Foundation; either |
| 7 * version 2 of the License, or (at your option) any later version. | 7 * version 2 of the License, or (at your option) any later version. |
| 8 * | 8 * |
| 9 * This library is distributed in the hope that it will be useful, | 9 * This library is distributed in the hope that it will be useful, |
| 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of | 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| (...skipping 10 matching lines...) Expand all Loading... |
| 21 #include "core/html/HTMLFrameOwnerElement.h" | 21 #include "core/html/HTMLFrameOwnerElement.h" |
| 22 | 22 |
| 23 #include "bindings/core/v8/ExceptionMessages.h" | 23 #include "bindings/core/v8/ExceptionMessages.h" |
| 24 #include "bindings/core/v8/ExceptionState.h" | 24 #include "bindings/core/v8/ExceptionState.h" |
| 25 #include "core/dom/AXObjectCache.h" | 25 #include "core/dom/AXObjectCache.h" |
| 26 #include "core/dom/ExceptionCode.h" | 26 #include "core/dom/ExceptionCode.h" |
| 27 #include "core/events/Event.h" | 27 #include "core/events/Event.h" |
| 28 #include "core/frame/FrameView.h" | 28 #include "core/frame/FrameView.h" |
| 29 #include "core/frame/LocalFrame.h" | 29 #include "core/frame/LocalFrame.h" |
| 30 #include "core/frame/LocalFrameClient.h" | 30 #include "core/frame/LocalFrameClient.h" |
| 31 #include "core/frame/RemoteFrameView.h" |
| 31 #include "core/layout/LayoutPart.h" | 32 #include "core/layout/LayoutPart.h" |
| 32 #include "core/layout/api/LayoutPartItem.h" | 33 #include "core/layout/api/LayoutPartItem.h" |
| 33 #include "core/loader/FrameLoadRequest.h" | 34 #include "core/loader/FrameLoadRequest.h" |
| 34 #include "core/loader/FrameLoader.h" | 35 #include "core/loader/FrameLoader.h" |
| 35 #include "core/page/Page.h" | 36 #include "core/page/Page.h" |
| 36 #include "core/plugins/PluginView.h" | 37 #include "core/plugins/PluginView.h" |
| 37 #include "platform/heap/HeapAllocator.h" | 38 #include "platform/heap/HeapAllocator.h" |
| 38 #include "platform/weborigin/SecurityOrigin.h" | 39 #include "platform/weborigin/SecurityOrigin.h" |
| 39 | 40 |
| 40 namespace blink { | 41 namespace blink { |
| 41 | 42 |
| 42 typedef HeapHashMap<Member<FrameViewBase>, Member<FrameView>> | 43 using FrameOrPluginToParentMap = |
| 43 FrameViewBaseToParentMap; | 44 HeapHashMap<Member<FrameOrPlugin>, Member<FrameView>>; |
| 44 static FrameViewBaseToParentMap& WidgetNewParentMap() { | 45 |
| 45 DEFINE_STATIC_LOCAL(FrameViewBaseToParentMap, map, | 46 static FrameOrPluginToParentMap& FrameOrPluginNewParentMap() { |
| 46 (new FrameViewBaseToParentMap)); | 47 DEFINE_STATIC_LOCAL(FrameOrPluginToParentMap, map, |
| 48 (new FrameOrPluginToParentMap)); |
| 47 return map; | 49 return map; |
| 48 } | 50 } |
| 49 | 51 |
| 50 using FrameViewBaseSet = HeapHashSet<Member<FrameViewBase>>; | 52 using FrameOrPluginSet = HeapHashSet<Member<FrameOrPlugin>>; |
| 51 static FrameViewBaseSet& WidgetsPendingTemporaryRemovalFromParent() { | 53 static FrameOrPluginSet& FrameOrPluginsPendingTemporaryRemovalFromParent() { |
| 52 // FrameViewBases in this set will not leak because it will be cleared in | 54 // FrameOrPlugins in this set will not leak because it will be cleared in |
| 53 // HTMLFrameOwnerElement::UpdateSuspendScope::performDeferredWidgetTreeOperati
ons. | 55 // HTMLFrameOwnerElement::UpdateSuspendScope::performDeferredWidgetTreeOperati
ons. |
| 54 DEFINE_STATIC_LOCAL(FrameViewBaseSet, set, (new FrameViewBaseSet)); | 56 DEFINE_STATIC_LOCAL(FrameOrPluginSet, set, (new FrameOrPluginSet)); |
| 55 return set; | 57 return set; |
| 56 } | 58 } |
| 57 | 59 |
| 58 using FrameOrPluginList = HeapVector<Member<FrameOrPlugin>>; | 60 static FrameOrPluginSet& FrameOrPluginsPendingDispose() { |
| 59 static FrameOrPluginList& FrameOrPluginsPendingDispose() { | 61 DEFINE_STATIC_LOCAL(FrameOrPluginSet, set, (new FrameOrPluginSet)); |
| 60 DEFINE_STATIC_LOCAL(FrameOrPluginList, list, (new FrameOrPluginList)); | 62 return set; |
| 61 return list; | |
| 62 } | 63 } |
| 63 | 64 |
| 64 SubframeLoadingDisabler::SubtreeRootSet& | 65 SubframeLoadingDisabler::SubtreeRootSet& |
| 65 SubframeLoadingDisabler::DisabledSubtreeRoots() { | 66 SubframeLoadingDisabler::DisabledSubtreeRoots() { |
| 66 DEFINE_STATIC_LOCAL(SubtreeRootSet, nodes, ()); | 67 DEFINE_STATIC_LOCAL(SubtreeRootSet, nodes, ()); |
| 67 return nodes; | 68 return nodes; |
| 68 } | 69 } |
| 69 | 70 |
| 70 static unsigned g_update_suspend_count = 0; | 71 static unsigned g_update_suspend_count = 0; |
| 71 | 72 |
| 72 HTMLFrameOwnerElement::UpdateSuspendScope::UpdateSuspendScope() { | 73 HTMLFrameOwnerElement::UpdateSuspendScope::UpdateSuspendScope() { |
| 73 ++g_update_suspend_count; | 74 ++g_update_suspend_count; |
| 74 } | 75 } |
| 75 | 76 |
| 76 void HTMLFrameOwnerElement::UpdateSuspendScope:: | 77 void HTMLFrameOwnerElement::UpdateSuspendScope:: |
| 77 PerformDeferredWidgetTreeOperations() { | 78 PerformDeferredWidgetTreeOperations() { |
| 78 FrameViewBaseToParentMap map; | 79 FrameOrPluginToParentMap map; |
| 79 WidgetNewParentMap().swap(map); | 80 FrameOrPluginNewParentMap().swap(map); |
| 80 for (const auto& frame_view_base : map) { | 81 for (const auto& entry : map) { |
| 81 FrameViewBase* child = frame_view_base.key.Get(); | 82 FrameOrPlugin* child = entry.key; |
| 82 FrameView* current_parent = ToFrameView(child->Parent()); | 83 FrameView* current_parent = child->Parent(); |
| 83 FrameView* new_parent = frame_view_base.value; | 84 FrameView* new_parent = entry.value; |
| 84 if (new_parent != current_parent) { | 85 if (new_parent != current_parent) { |
| 85 if (current_parent) | 86 if (current_parent) |
| 86 current_parent->RemoveChild(child); | 87 current_parent->RemoveChild(child); |
| 87 if (new_parent) | 88 if (new_parent) |
| 88 new_parent->AddChild(child); | 89 new_parent->AddChild(child); |
| 89 if (current_parent && !new_parent) | 90 if (current_parent && !new_parent) |
| 90 child->Dispose(); | 91 child->Dispose(); |
| 91 } | 92 } |
| 92 } | 93 } |
| 93 | 94 |
| 94 { | 95 FrameOrPluginSet remove_set; |
| 95 FrameViewBaseSet set; | 96 FrameOrPluginsPendingTemporaryRemovalFromParent().swap(remove_set); |
| 96 WidgetsPendingTemporaryRemovalFromParent().swap(set); | 97 for (const auto& child : remove_set) { |
| 97 for (const auto& frame_view_base : set) { | 98 if (child->Parent()) |
| 98 FrameView* current_parent = ToFrameView(frame_view_base->Parent()); | 99 child->Parent()->RemoveChild(child); |
| 99 if (current_parent) | |
| 100 current_parent->RemoveChild(frame_view_base.Get()); | |
| 101 } | |
| 102 } | 100 } |
| 103 | 101 |
| 104 { | 102 FrameOrPluginSet dispose_set; |
| 105 FrameOrPluginList list; | 103 FrameOrPluginsPendingDispose().swap(dispose_set); |
| 106 FrameOrPluginsPendingDispose().swap(list); | 104 for (const auto& frame_or_plugin : dispose_set) { |
| 107 for (const auto& frame_or_plugin : list) { | 105 frame_or_plugin->Dispose(); |
| 108 frame_or_plugin->Dispose(); | |
| 109 } | |
| 110 } | 106 } |
| 111 } | 107 } |
| 112 | 108 |
| 113 HTMLFrameOwnerElement::UpdateSuspendScope::~UpdateSuspendScope() { | 109 HTMLFrameOwnerElement::UpdateSuspendScope::~UpdateSuspendScope() { |
| 114 DCHECK_GT(g_update_suspend_count, 0u); | 110 DCHECK_GT(g_update_suspend_count, 0u); |
| 115 if (g_update_suspend_count == 1) | 111 if (g_update_suspend_count == 1) |
| 116 PerformDeferredWidgetTreeOperations(); | 112 PerformDeferredWidgetTreeOperations(); |
| 117 --g_update_suspend_count; | 113 --g_update_suspend_count; |
| 118 } | 114 } |
| 119 | 115 |
| 120 // Unlike moveWidgetToParentSoon, this will not call dispose. | 116 // Unlike MoveFrameOrPluginToParentSoon, this will not call dispose. |
| 121 void TemporarilyRemoveWidgetFromParentSoon(FrameViewBase* frame_view_base) { | 117 void TemporarilyRemoveFrameOrPluginFromParentSoon(FrameOrPlugin* child) { |
| 122 if (g_update_suspend_count) { | 118 if (g_update_suspend_count) { |
| 123 WidgetsPendingTemporaryRemovalFromParent().insert(frame_view_base); | 119 FrameOrPluginsPendingTemporaryRemovalFromParent().insert(child); |
| 124 } else { | 120 } else { |
| 125 if (ToFrameView(frame_view_base->Parent())) | 121 if (child->Parent()) |
| 126 ToFrameView(frame_view_base->Parent())->RemoveChild(frame_view_base); | 122 child->Parent()->RemoveChild(child); |
| 127 } | 123 } |
| 128 } | 124 } |
| 129 | 125 |
| 130 void MoveWidgetToParentSoon(FrameViewBase* child, FrameView* parent) { | 126 void MoveFrameOrPluginToParentSoon(FrameOrPlugin* child, FrameView* parent) { |
| 131 if (!g_update_suspend_count) { | 127 if (!g_update_suspend_count) { |
| 132 if (parent) { | 128 if (parent) { |
| 133 parent->AddChild(child); | 129 parent->AddChild(child); |
| 134 } else if (ToFrameView(child->Parent())) { | 130 } else if (child->Parent()) { |
| 135 ToFrameView(child->Parent())->RemoveChild(child); | 131 child->Parent()->RemoveChild(child); |
| 136 child->Dispose(); | 132 child->Dispose(); |
| 137 } | 133 } |
| 138 return; | 134 return; |
| 139 } | 135 } |
| 140 WidgetNewParentMap().Set(child, parent); | 136 FrameOrPluginNewParentMap().Set(child, parent); |
| 141 } | 137 } |
| 142 | 138 |
| 143 HTMLFrameOwnerElement::HTMLFrameOwnerElement(const QualifiedName& tag_name, | 139 HTMLFrameOwnerElement::HTMLFrameOwnerElement(const QualifiedName& tag_name, |
| 144 Document& document) | 140 Document& document) |
| 145 : HTMLElement(tag_name, document), | 141 : HTMLElement(tag_name, document), |
| 146 content_frame_(nullptr), | 142 content_frame_(nullptr), |
| 147 widget_(nullptr), | 143 widget_(nullptr), |
| 148 sandbox_flags_(kSandboxNone) {} | 144 sandbox_flags_(kSandboxNone) {} |
| 149 | 145 |
| 150 LayoutPart* HTMLFrameOwnerElement::GetLayoutPart() const { | 146 LayoutPart* HTMLFrameOwnerElement::GetLayoutPart() const { |
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 220 } | 216 } |
| 221 } | 217 } |
| 222 | 218 |
| 223 bool HTMLFrameOwnerElement::IsKeyboardFocusable() const { | 219 bool HTMLFrameOwnerElement::IsKeyboardFocusable() const { |
| 224 return content_frame_ && HTMLElement::IsKeyboardFocusable(); | 220 return content_frame_ && HTMLElement::IsKeyboardFocusable(); |
| 225 } | 221 } |
| 226 | 222 |
| 227 void HTMLFrameOwnerElement::DisposeFrameOrPluginSoon( | 223 void HTMLFrameOwnerElement::DisposeFrameOrPluginSoon( |
| 228 FrameOrPlugin* frame_or_plugin) { | 224 FrameOrPlugin* frame_or_plugin) { |
| 229 if (g_update_suspend_count) { | 225 if (g_update_suspend_count) { |
| 230 FrameOrPluginsPendingDispose().push_back(frame_or_plugin); | 226 FrameOrPluginsPendingDispose().insert(frame_or_plugin); |
| 231 return; | 227 } else { |
| 228 frame_or_plugin->Dispose(); |
| 232 } | 229 } |
| 233 frame_or_plugin->Dispose(); | |
| 234 } | 230 } |
| 235 | 231 |
| 236 void HTMLFrameOwnerElement::UpdateContainerPolicy() { | 232 void HTMLFrameOwnerElement::UpdateContainerPolicy() { |
| 237 container_policy_ = GetContainerPolicyFromAllowedFeatures( | 233 container_policy_ = GetContainerPolicyFromAllowedFeatures( |
| 238 AllowedFeatures(), AllowFullscreen(), AllowPaymentRequest(), | 234 AllowedFeatures(), AllowFullscreen(), AllowPaymentRequest(), |
| 239 GetOriginForFeaturePolicy()); | 235 GetOriginForFeaturePolicy()); |
| 240 // Don't notify about updates if ContentFrame() is null, for example when | 236 // Don't notify about updates if ContentFrame() is null, for example when |
| 241 // the subframe hasn't been created yet. | 237 // the subframe hasn't been created yet. |
| 242 if (ContentFrame()) { | 238 if (ContentFrame()) { |
| 243 GetDocument().GetFrame()->Loader().Client()->DidChangeFramePolicy( | 239 GetDocument().GetFrame()->Loader().Client()->DidChangeFramePolicy( |
| (...skipping 25 matching lines...) Expand all Loading... |
| 269 } | 265 } |
| 270 | 266 |
| 271 Document* HTMLFrameOwnerElement::getSVGDocument( | 267 Document* HTMLFrameOwnerElement::getSVGDocument( |
| 272 ExceptionState& exception_state) const { | 268 ExceptionState& exception_state) const { |
| 273 Document* doc = contentDocument(); | 269 Document* doc = contentDocument(); |
| 274 if (doc && doc->IsSVGDocument()) | 270 if (doc && doc->IsSVGDocument()) |
| 275 return doc; | 271 return doc; |
| 276 return nullptr; | 272 return nullptr; |
| 277 } | 273 } |
| 278 | 274 |
| 279 void HTMLFrameOwnerElement::SetWidget(FrameViewBase* frame_view_base) { | 275 void HTMLFrameOwnerElement::SetWidget(FrameOrPlugin* frame_or_plugin) { |
| 280 if (frame_view_base == widget_) | 276 if (frame_or_plugin == widget_) |
| 281 return; | 277 return; |
| 282 | 278 |
| 283 Document* doc = contentDocument(); | 279 Document* doc = contentDocument(); |
| 284 if (doc && doc->GetFrame()) { | 280 if (doc && doc->GetFrame()) { |
| 285 bool will_be_display_none = !frame_view_base; | 281 bool will_be_display_none = !frame_or_plugin; |
| 286 if (IsDisplayNone() != will_be_display_none) { | 282 if (IsDisplayNone() != will_be_display_none) { |
| 287 doc->WillChangeFrameOwnerProperties( | 283 doc->WillChangeFrameOwnerProperties( |
| 288 MarginWidth(), MarginHeight(), ScrollingMode(), will_be_display_none); | 284 MarginWidth(), MarginHeight(), ScrollingMode(), will_be_display_none); |
| 289 } | 285 } |
| 290 } | 286 } |
| 291 | 287 |
| 292 if (widget_) { | 288 if (widget_) { |
| 293 if (widget_->Parent()) | 289 if (widget_->Parent()) |
| 294 MoveWidgetToParentSoon(widget_.Get(), 0); | 290 MoveFrameOrPluginToParentSoon(widget_, nullptr); |
| 295 widget_ = nullptr; | |
| 296 } | 291 } |
| 297 | 292 |
| 298 widget_ = frame_view_base; | 293 widget_ = frame_or_plugin; |
| 299 FrameOwnerPropertiesChanged(); | 294 FrameOwnerPropertiesChanged(); |
| 300 | 295 |
| 301 LayoutPart* layout_part = ToLayoutPart(GetLayoutObject()); | 296 LayoutPart* layout_part = ToLayoutPart(GetLayoutObject()); |
| 302 LayoutPartItem layout_part_item = LayoutPartItem(layout_part); | 297 LayoutPartItem layout_part_item = LayoutPartItem(layout_part); |
| 303 if (layout_part_item.IsNull()) | 298 if (layout_part_item.IsNull()) |
| 304 return; | 299 return; |
| 305 | 300 |
| 306 if (widget_) { | 301 if (widget_) { |
| 307 layout_part_item.UpdateOnWidgetChange(); | 302 layout_part_item.UpdateOnWidgetChange(); |
| 308 | 303 |
| 309 DCHECK_EQ(GetDocument().View(), layout_part_item.GetFrameView()); | 304 DCHECK_EQ(GetDocument().View(), layout_part_item.GetFrameView()); |
| 310 DCHECK(layout_part_item.GetFrameView()); | 305 DCHECK(layout_part_item.GetFrameView()); |
| 311 MoveWidgetToParentSoon(widget_.Get(), layout_part_item.GetFrameView()); | 306 MoveFrameOrPluginToParentSoon(widget_, layout_part_item.GetFrameView()); |
| 312 } | 307 } |
| 313 | 308 |
| 314 if (AXObjectCache* cache = GetDocument().ExistingAXObjectCache()) | 309 if (AXObjectCache* cache = GetDocument().ExistingAXObjectCache()) |
| 315 cache->ChildrenChanged(layout_part); | 310 cache->ChildrenChanged(layout_part); |
| 316 } | 311 } |
| 317 | 312 |
| 318 FrameViewBase* HTMLFrameOwnerElement::ReleaseWidget() { | 313 FrameOrPlugin* HTMLFrameOwnerElement::ReleaseWidget() { |
| 319 if (!widget_) | 314 if (!widget_) |
| 320 return nullptr; | 315 return nullptr; |
| 321 if (widget_->Parent()) | 316 if (widget_->Parent()) |
| 322 TemporarilyRemoveWidgetFromParentSoon(widget_.Get()); | 317 TemporarilyRemoveFrameOrPluginFromParentSoon(widget_); |
| 323 LayoutPart* layout_part = ToLayoutPart(GetLayoutObject()); | 318 LayoutPart* layout_part = ToLayoutPart(GetLayoutObject()); |
| 324 if (layout_part) { | 319 if (layout_part) { |
| 325 if (AXObjectCache* cache = GetDocument().ExistingAXObjectCache()) | 320 if (AXObjectCache* cache = GetDocument().ExistingAXObjectCache()) |
| 326 cache->ChildrenChanged(layout_part); | 321 cache->ChildrenChanged(layout_part); |
| 327 } | 322 } |
| 328 return widget_.Release(); | 323 return widget_.Release(); |
| 329 } | 324 } |
| 330 | 325 |
| 331 FrameViewBase* HTMLFrameOwnerElement::OwnedWidget() const { | |
| 332 return widget_.Get(); | |
| 333 } | |
| 334 | |
| 335 bool HTMLFrameOwnerElement::LoadOrRedirectSubframe( | 326 bool HTMLFrameOwnerElement::LoadOrRedirectSubframe( |
| 336 const KURL& url, | 327 const KURL& url, |
| 337 const AtomicString& frame_name, | 328 const AtomicString& frame_name, |
| 338 bool replace_current_item) { | 329 bool replace_current_item) { |
| 339 UpdateContainerPolicy(); | 330 UpdateContainerPolicy(); |
| 340 | 331 |
| 341 LocalFrame* parent_frame = GetDocument().GetFrame(); | 332 LocalFrame* parent_frame = GetDocument().GetFrame(); |
| 342 if (ContentFrame()) { | 333 if (ContentFrame()) { |
| 343 ContentFrame()->Navigate(GetDocument(), url, replace_current_item, | 334 ContentFrame()->Navigate(GetDocument(), url, replace_current_item, |
| 344 UserGestureStatus::kNone); | 335 UserGestureStatus::kNone); |
| (...skipping 26 matching lines...) Expand all Loading... |
| 371 } | 362 } |
| 372 | 363 |
| 373 DEFINE_TRACE(HTMLFrameOwnerElement) { | 364 DEFINE_TRACE(HTMLFrameOwnerElement) { |
| 374 visitor->Trace(content_frame_); | 365 visitor->Trace(content_frame_); |
| 375 visitor->Trace(widget_); | 366 visitor->Trace(widget_); |
| 376 HTMLElement::Trace(visitor); | 367 HTMLElement::Trace(visitor); |
| 377 FrameOwner::Trace(visitor); | 368 FrameOwner::Trace(visitor); |
| 378 } | 369 } |
| 379 | 370 |
| 380 } // namespace blink | 371 } // namespace blink |
| OLD | NEW |