Commit 56974e50 authored by tasak@google.com's avatar tasak@google.com

Added addXSLStyleSheet and removeXSLStyleSheet to StyleEngine.

To apply XSLStyleSheet, we only need the first one. We don't need
to have all XSL stylesheets if the XML document has more than two
XSL stylesheets. So modified not to add XSLStyleSheet to
StyleSheetCandidateNodes. Instead, modified to make StyleEngine have
the first XSLStyleSheet.

BUG=367689
TEST=No new test, because this patch is just for refactoring.

Review URL: https://codereview.chromium.org/257363002

git-svn-id: svn://svn.chromium.org/blink/trunk@175775 bbb929c8-8fbe-4397-9dbb-9b2b20218538
parent 62f6c5db
...@@ -51,21 +51,7 @@ void DocumentStyleSheetCollection::collectStyleSheetsFromCandidates(StyleEngine* ...@@ -51,21 +51,7 @@ void DocumentStyleSheetCollection::collectStyleSheetsFromCandidates(StyleEngine*
Node* n = *it; Node* n = *it;
StyleSheetCandidate candidate(*n); StyleSheetCandidate candidate(*n);
if (candidate.isXSL()) { ASSERT(!candidate.isXSL());
// Processing instruction (XML documents only).
// We don't support linking to embedded CSS stylesheets, see <https://bugs.webkit.org/show_bug.cgi?id=49281> for discussion.
// Don't apply XSL transforms to already transformed documents -- <rdar://problem/4132806>
if (RuntimeEnabledFeatures::xsltEnabled() && !document().transformSourceDocument()) {
ProcessingInstruction* pi = toProcessingInstruction(n);
// Don't apply XSL transforms until loading is finished.
if (!document().parsing() && !pi->isLoading())
document().applyXSLTransform(pi);
return;
}
continue;
}
if (candidate.isImport()) { if (candidate.isImport()) {
Document* document = candidate.importedDocument(); Document* document = candidate.importedDocument();
if (!document) if (!document)
......
...@@ -59,8 +59,15 @@ ProcessingInstruction::~ProcessingInstruction() ...@@ -59,8 +59,15 @@ ProcessingInstruction::~ProcessingInstruction()
if (m_sheet) if (m_sheet)
m_sheet->clearOwnerNode(); m_sheet->clearOwnerNode();
if (inDocument()) // FIXME: ProcessingInstruction should not be in document here.
document().styleEngine()->removeStyleSheetCandidateNode(this); // However, if we add ASSERT(!inDocument()), fast/xsl/xslt-entity.xml
// crashes. We need to investigate ProcessingInstruction lifetime.
if (inDocument()) {
if (m_isCSS)
document().styleEngine()->removeStyleSheetCandidateNode(this);
else if (m_isXSL)
document().styleEngine()->removeXSLStyleSheet(this);
}
#endif #endif
} }
...@@ -242,11 +249,11 @@ Node::InsertionNotificationRequest ProcessingInstruction::insertedInto(Container ...@@ -242,11 +249,11 @@ Node::InsertionNotificationRequest ProcessingInstruction::insertedInto(Container
String href; String href;
String charset; String charset;
// To make it possible for us to see isXSL in
// StyleEngine::addStyleSheetCandidateNode, split checkStyleSheet
// into two methods, checkStyleSheet and process.
bool isValid = checkStyleSheet(href, charset); bool isValid = checkStyleSheet(href, charset);
document().styleEngine()->addStyleSheetCandidateNode(this, m_createdByParser); if (m_isCSS)
document().styleEngine()->addStyleSheetCandidateNode(this, m_createdByParser);
else if (m_isXSL)
document().styleEngine()->addXSLStyleSheet(this, m_createdByParser);
if (isValid) if (isValid)
process(href, charset); process(href, charset);
return InsertionDone; return InsertionDone;
...@@ -258,7 +265,10 @@ void ProcessingInstruction::removedFrom(ContainerNode* insertionPoint) ...@@ -258,7 +265,10 @@ void ProcessingInstruction::removedFrom(ContainerNode* insertionPoint)
if (!insertionPoint->inDocument()) if (!insertionPoint->inDocument())
return; return;
document().styleEngine()->removeStyleSheetCandidateNode(this); if (m_isCSS)
document().styleEngine()->removeStyleSheetCandidateNode(this);
else if (m_isXSL)
document().styleEngine()->removeXSLStyleSheet(this);
RefPtrWillBeRawPtr<StyleSheet> removedSheet = m_sheet; RefPtrWillBeRawPtr<StyleSheet> removedSheet = m_sheet;
......
...@@ -86,6 +86,11 @@ private: ...@@ -86,6 +86,11 @@ private:
DEFINE_NODE_TYPE_CASTS(ProcessingInstruction, nodeType() == Node::PROCESSING_INSTRUCTION_NODE); DEFINE_NODE_TYPE_CASTS(ProcessingInstruction, nodeType() == Node::PROCESSING_INSTRUCTION_NODE);
inline bool isXSLStyleSheet(const Node& node)
{
return node.nodeType() == Node::PROCESSING_INSTRUCTION_NODE && toProcessingInstruction(node).isXSL();
}
} // namespace WebCore } // namespace WebCore
#endif #endif
...@@ -75,6 +75,7 @@ StyleEngine::StyleEngine(Document& document) ...@@ -75,6 +75,7 @@ StyleEngine::StyleEngine(Document& document)
// We don't need to create CSSFontSelector for imported document or // We don't need to create CSSFontSelector for imported document or
// HTMLTemplateElement's document, because those documents have no frame. // HTMLTemplateElement's document, because those documents have no frame.
, m_fontSelector(document.frame() ? CSSFontSelector::create(&document) : nullptr) , m_fontSelector(document.frame() ? CSSFontSelector::create(&document) : nullptr)
, m_xslStyleSheet(nullptr)
{ {
if (m_fontSelector) if (m_fontSelector)
m_fontSelector->registerForInvalidationCallbacks(this); m_fontSelector->registerForInvalidationCallbacks(this);
...@@ -286,7 +287,7 @@ void StyleEngine::addStyleSheetCandidateNode(Node* node, bool createdByParser) ...@@ -286,7 +287,7 @@ void StyleEngine::addStyleSheetCandidateNode(Node* node, bool createdByParser)
TreeScope& treeScope = isHTMLStyleElement(*node) ? node->treeScope() : *m_document; TreeScope& treeScope = isHTMLStyleElement(*node) ? node->treeScope() : *m_document;
ASSERT(isHTMLStyleElement(node) || treeScope == m_document); ASSERT(isHTMLStyleElement(node) || treeScope == m_document);
ASSERT(!isXSLStyleSheet(*node));
TreeScopeStyleSheetCollection* collection = ensureStyleSheetCollectionFor(treeScope); TreeScopeStyleSheetCollection* collection = ensureStyleSheetCollectionFor(treeScope);
ASSERT(collection); ASSERT(collection);
collection->addStyleSheetCandidateNode(node, createdByParser); collection->addStyleSheetCandidateNode(node, createdByParser);
...@@ -304,6 +305,7 @@ void StyleEngine::removeStyleSheetCandidateNode(Node* node) ...@@ -304,6 +305,7 @@ void StyleEngine::removeStyleSheetCandidateNode(Node* node)
void StyleEngine::removeStyleSheetCandidateNode(Node* node, ContainerNode* scopingNode, TreeScope& treeScope) void StyleEngine::removeStyleSheetCandidateNode(Node* node, ContainerNode* scopingNode, TreeScope& treeScope)
{ {
ASSERT(isHTMLStyleElement(node) || treeScope == m_document); ASSERT(isHTMLStyleElement(node) || treeScope == m_document);
ASSERT(!isXSLStyleSheet(*node));
TreeScopeStyleSheetCollection* collection = styleSheetCollectionFor(treeScope); TreeScopeStyleSheetCollection* collection = styleSheetCollectionFor(treeScope);
ASSERT(collection); ASSERT(collection);
...@@ -313,6 +315,37 @@ void StyleEngine::removeStyleSheetCandidateNode(Node* node, ContainerNode* scopi ...@@ -313,6 +315,37 @@ void StyleEngine::removeStyleSheetCandidateNode(Node* node, ContainerNode* scopi
m_activeTreeScopes.remove(&treeScope); m_activeTreeScopes.remove(&treeScope);
} }
void StyleEngine::addXSLStyleSheet(ProcessingInstruction* node, bool createdByParser)
{
if (!node->inDocument())
return;
ASSERT(isXSLStyleSheet(*node));
bool needToUpdate = false;
if (createdByParser || !m_xslStyleSheet) {
needToUpdate = !m_xslStyleSheet;
} else {
unsigned position = m_xslStyleSheet->compareDocumentPositionInternal(node, Node::TreatShadowTreesAsDisconnected);
needToUpdate = position & Node::DOCUMENT_POSITION_FOLLOWING;
}
if (!needToUpdate)
return;
markTreeScopeDirty(*m_document);
m_xslStyleSheet = node;
}
void StyleEngine::removeXSLStyleSheet(ProcessingInstruction* node)
{
ASSERT(isXSLStyleSheet(*node));
if (m_xslStyleSheet != node)
return;
markTreeScopeDirty(*m_document);
m_xslStyleSheet = nullptr;
}
void StyleEngine::modifiedStyleSheetCandidateNode(Node* node) void StyleEngine::modifiedStyleSheetCandidateNode(Node* node)
{ {
if (!node->inDocument()) if (!node->inDocument())
...@@ -487,6 +520,13 @@ bool StyleEngine::shouldClearResolver() const ...@@ -487,6 +520,13 @@ bool StyleEngine::shouldClearResolver() const
return !m_didCalculateResolver && !haveStylesheetsLoaded(); return !m_didCalculateResolver && !haveStylesheetsLoaded();
} }
bool StyleEngine::shouldApplyXSLTransform() const
{
if (!RuntimeEnabledFeatures::xsltEnabled())
return false;
return m_xslStyleSheet && !m_document->transformSourceDocument();
}
StyleResolverChange StyleEngine::resolverChanged(StyleResolverUpdateMode mode) StyleResolverChange StyleEngine::resolverChanged(StyleResolverUpdateMode mode)
{ {
StyleResolverChange change; StyleResolverChange change;
...@@ -504,6 +544,15 @@ StyleResolverChange StyleEngine::resolverChanged(StyleResolverUpdateMode mode) ...@@ -504,6 +544,15 @@ StyleResolverChange StyleEngine::resolverChanged(StyleResolverUpdateMode mode)
return change; return change;
} }
if (shouldApplyXSLTransform()) {
// Processing instruction (XML documents only).
// We don't support linking to embedded CSS stylesheets, see <https://bugs.webkit.org/show_bug.cgi?id=49281> for discussion.
// Don't apply XSL transforms to already transformed documents -- <rdar://problem/4132806>
if (!m_document->parsing() && !m_xslStyleSheet->isLoading())
m_document->applyXSLTransform(m_xslStyleSheet.get());
return change;
}
m_didCalculateResolver = true; m_didCalculateResolver = true;
if (document().didLayoutWithPendingStylesheets() && !hasPendingSheets()) if (document().didLayoutWithPendingStylesheets() && !hasPendingSheets())
change.setNeedsRepaint(); change.setNeedsRepaint();
......
...@@ -109,6 +109,8 @@ public: ...@@ -109,6 +109,8 @@ public:
void removeStyleSheetCandidateNode(Node*, ContainerNode* scopingNode, TreeScope&); void removeStyleSheetCandidateNode(Node*, ContainerNode* scopingNode, TreeScope&);
void modifiedStyleSheetCandidateNode(Node*); void modifiedStyleSheetCandidateNode(Node*);
void enableExitTransitionStylesheets(); void enableExitTransitionStylesheets();
void addXSLStyleSheet(ProcessingInstruction*, bool createdByParser);
void removeXSLStyleSheet(ProcessingInstruction*);
void invalidateInjectedStyleSheetCache(); void invalidateInjectedStyleSheetCache();
void updateInjectedStyleSheetCache() const; void updateInjectedStyleSheetCache() const;
...@@ -200,6 +202,7 @@ private: ...@@ -200,6 +202,7 @@ private:
TreeScopeStyleSheetCollection* ensureStyleSheetCollectionFor(TreeScope&); TreeScopeStyleSheetCollection* ensureStyleSheetCollectionFor(TreeScope&);
TreeScopeStyleSheetCollection* styleSheetCollectionFor(TreeScope&); TreeScopeStyleSheetCollection* styleSheetCollectionFor(TreeScope&);
bool shouldUpdateShadowTreeStyleSheetCollection(StyleResolverUpdateMode); bool shouldUpdateShadowTreeStyleSheetCollection(StyleResolverUpdateMode);
bool shouldApplyXSLTransform() const;
void markTreeScopeDirty(TreeScope&); void markTreeScopeDirty(TreeScope&);
...@@ -278,6 +281,8 @@ private: ...@@ -278,6 +281,8 @@ private:
WillBeHeapHashMap<AtomicString, RawPtrWillBeMember<StyleSheetContents> > m_textToSheetCache; WillBeHeapHashMap<AtomicString, RawPtrWillBeMember<StyleSheetContents> > m_textToSheetCache;
WillBeHeapHashMap<RawPtrWillBeMember<StyleSheetContents>, AtomicString> m_sheetToTextCache; WillBeHeapHashMap<RawPtrWillBeMember<StyleSheetContents>, AtomicString> m_sheetToTextCache;
RefPtr<ProcessingInstruction> m_xslStyleSheet;
}; };
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment