| Index: third_party/WebKit/Source/core/svg/SVGUseElement.cpp
|
| diff --git a/third_party/WebKit/Source/core/svg/SVGUseElement.cpp b/third_party/WebKit/Source/core/svg/SVGUseElement.cpp
|
| index 0a352692dfa8e51c24a208ec13e2578e97d540f7..a4ff25cbc0567b10db06207487fd6fc5455be92c 100644
|
| --- a/third_party/WebKit/Source/core/svg/SVGUseElement.cpp
|
| +++ b/third_party/WebKit/Source/core/svg/SVGUseElement.cpp
|
| @@ -25,14 +25,13 @@
|
|
|
| #include "core/svg/SVGUseElement.h"
|
|
|
| -#include "bindings/core/v8/ExceptionState.h"
|
| #include "core/SVGNames.h"
|
| #include "core/XLinkNames.h"
|
| #include "core/dom/Document.h"
|
| #include "core/dom/ElementTraversal.h"
|
| +#include "core/dom/IdTargetObserver.h"
|
| #include "core/dom/StyleChangeReason.h"
|
| #include "core/dom/TaskRunnerHelper.h"
|
| -#include "core/dom/shadow/ElementShadow.h"
|
| #include "core/dom/shadow/ShadowRoot.h"
|
| #include "core/events/Event.h"
|
| #include "core/layout/svg/LayoutSVGTransformableContainer.h"
|
| @@ -41,7 +40,6 @@
|
| #include "core/svg/SVGSVGElement.h"
|
| #include "core/svg/SVGSymbolElement.h"
|
| #include "core/svg/SVGTitleElement.h"
|
| -#include "core/svg/SVGTreeScopeResources.h"
|
| #include "core/xml/parser/XMLDocumentParser.h"
|
| #include "platform/loader/fetch/FetchRequest.h"
|
| #include "platform/loader/fetch/ResourceFetcher.h"
|
| @@ -98,6 +96,7 @@ DEFINE_TRACE(SVGUseElement) {
|
| visitor->trace(m_width);
|
| visitor->trace(m_height);
|
| visitor->trace(m_targetElementInstance);
|
| + visitor->trace(m_targetIdObserver);
|
| visitor->trace(m_resource);
|
| SVGGraphicsElement::trace(visitor);
|
| SVGURIReference::trace(visitor);
|
| @@ -128,8 +127,7 @@ Node::InsertionNotificationRequest SVGUseElement::insertedInto(
|
| void SVGUseElement::removedFrom(ContainerNode* rootParent) {
|
| SVGGraphicsElement::removedFrom(rootParent);
|
| if (rootParent->isConnected()) {
|
| - clearInstanceRoot();
|
| - removeAllOutgoingReferences();
|
| + clearResourceReference();
|
| cancelShadowTreeRecreation();
|
| }
|
| }
|
| @@ -287,52 +285,40 @@ void SVGUseElement::cancelShadowTreeRecreation() {
|
| }
|
|
|
| void SVGUseElement::clearInstanceRoot() {
|
| - if (m_targetElementInstance)
|
| - m_targetElementInstance = nullptr;
|
| + m_targetElementInstance = nullptr;
|
| }
|
|
|
| -void SVGUseElement::clearShadowTree() {
|
| +void SVGUseElement::clearResourceReference() {
|
| + unobserveTarget(m_targetIdObserver);
|
| clearInstanceRoot();
|
| -
|
| - // FIXME: We should try to optimize this, to at least allow partial reclones.
|
| - if (ShadowRoot* shadowTreeRootElement = userAgentShadowRoot())
|
| - shadowTreeRootElement->removeChildren(OmitSubtreeModifiedEvent);
|
| -
|
| removeAllOutgoingReferences();
|
| }
|
|
|
| Element* SVGUseElement::resolveTargetElement() {
|
| if (m_elementIdentifier.isEmpty())
|
| return nullptr;
|
| - const TreeScope* lookupScope = nullptr;
|
| - if (m_elementIdentifierIsLocal)
|
| - lookupScope = &treeScope();
|
| - else if (resourceIsValid())
|
| - lookupScope = m_resource->document();
|
| - else
|
| - return nullptr;
|
| - Element* target = lookupScope->getElementById(m_elementIdentifier);
|
| - // TODO(fs): Why would the Element not be "connected" at this point?
|
| - if (target && target->isConnected())
|
| - return target;
|
| - // Don't record any pending references for external resources.
|
| - if (!m_resource) {
|
| - treeScope().ensureSVGTreeScopedResources().addPendingResource(
|
| - m_elementIdentifier, *this);
|
| - DCHECK(hasPendingResources());
|
| + if (m_elementIdentifierIsLocal) {
|
| + return observeTarget(m_targetIdObserver, treeScope(), m_elementIdentifier,
|
| + WTF::bind(&SVGUseElement::invalidateShadowTree,
|
| + wrapWeakPersistent(this)));
|
| }
|
| - return nullptr;
|
| + if (!resourceIsValid())
|
| + return nullptr;
|
| + return m_resource->document()->getElementById(m_elementIdentifier);
|
| }
|
|
|
| void SVGUseElement::buildPendingResource() {
|
| if (inUseShadowTree())
|
| return;
|
| - clearShadowTree();
|
| + // FIXME: We should try to optimize this, to at least allow partial reclones.
|
| + userAgentShadowRoot()->removeChildren(OmitSubtreeModifiedEvent);
|
| + clearResourceReference();
|
| cancelShadowTreeRecreation();
|
| if (!isConnected())
|
| return;
|
| Element* target = resolveTargetElement();
|
| - if (target && target->isSVGElement()) {
|
| + // TODO(fs): Why would the Element not be "connected" at this point?
|
| + if (target && target->isConnected() && target->isSVGElement()) {
|
| buildShadowAndInstanceTree(toSVGElement(*target));
|
| invalidateDependentShadowTrees();
|
| }
|
| @@ -463,7 +449,8 @@ void SVGUseElement::buildShadowAndInstanceTree(SVGElement& target) {
|
| // Expand all <use> elements in the shadow tree.
|
| // Expand means: replace the actual <use> element by what it references.
|
| if (!expandUseElementsInShadowTree()) {
|
| - clearShadowTree();
|
| + shadowTreeRootElement->removeChildren(OmitSubtreeModifiedEvent);
|
| + clearResourceReference();
|
| return;
|
| }
|
|
|
|
|