Changeset 204021 in webkit
- Timestamp:
- Aug 2, 2016 2:43:01 AM (8 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 17 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r204020 r204021 1 2016-08-02 Frederic Wang <fwang.igalia.com> 2 3 Use Optional members to store parsed MathML attributes. 4 https://bugs.webkit.org/show_bug.cgi?id=160400 5 6 Reviewed by Darin Adler. 7 8 Parsed MathML attributes are stored on the element classes using the memoize pattern to 9 minimize the number of parsing updates. Currently, a dirty flag for each member 10 indicate when it must be parsed again. We change this to wrap these members into an 11 Optional<T> container instead, where a null value indicates that the member is dirty. 12 13 No new tests, behavior is unchanged. 14 15 * mathml/MathMLElement.cpp: 16 (WebCore::MathMLElement::cachedMathMLLength): 17 (WebCore::MathMLElement::cachedBooleanAttribute): 18 (WebCore::MathMLElement::parseMathVariantAttribute): 19 (WebCore::MathMLElement::specifiedDisplayStyle): 20 (WebCore::MathMLElement::specifiedMathVariant): 21 * mathml/MathMLElement.h: 22 * mathml/MathMLFractionElement.cpp: 23 (WebCore::MathMLFractionElement::lineThickness): 24 (WebCore::MathMLFractionElement::cachedFractionAlignment): 25 (WebCore::MathMLFractionElement::parseAttribute): 26 * mathml/MathMLFractionElement.h: 27 * mathml/MathMLInlineContainerElement.cpp: 28 (WebCore::MathMLInlineContainerElement::parseAttribute): 29 * mathml/MathMLMathElement.cpp: 30 (WebCore::MathMLMathElement::specifiedDisplayStyle): 31 (WebCore::MathMLMathElement::parseAttribute): 32 * mathml/MathMLOperatorElement.cpp: 33 (WebCore::MathMLOperatorElement::operatorText): 34 * mathml/MathMLPaddedElement.cpp: 35 (WebCore::MathMLPaddedElement::parseAttribute): 36 * mathml/MathMLPaddedElement.h: 37 * mathml/MathMLScriptsElement.cpp: 38 (WebCore::MathMLScriptsElement::parseAttribute): 39 * mathml/MathMLScriptsElement.h: 40 * mathml/MathMLSpaceElement.cpp: 41 (WebCore::MathMLSpaceElement::parseAttribute): 42 * mathml/MathMLSpaceElement.h: 43 * mathml/MathMLTextElement.cpp: 44 (WebCore::MathMLTextElement::parseAttribute): 45 * mathml/MathMLUnderOverElement.cpp: 46 (WebCore::MathMLUnderOverElement::parseAttribute): 47 * mathml/MathMLUnderOverElement.h: 48 * rendering/mathml/MathMLStyle.cpp: 49 (WebCore::MathMLStyle::resolveMathMLStyle): 50 * rendering/mathml/MathMLStyle.h: 51 * rendering/mathml/RenderMathMLToken.cpp: 52 (WebCore::mathVariant): 53 (WebCore::RenderMathMLToken::updateMathVariantGlyph): 54 1 55 2016-08-02 Youenn Fablet <youenn@apple.com> 2 56 -
trunk/Source/WebCore/mathml/MathMLElement.cpp
r203679 r204021 518 518 } 519 519 520 const MathMLElement::Length& MathMLElement::cachedMathMLLength(const QualifiedName& name, Length& length) 521 { 522 if (length.dirty) { 523 length = parseMathMLLength(attributeWithoutSynchronization(name)); 524 length.dirty = false; 525 } 526 return length; 527 } 528 529 const MathMLElement::BooleanValue& MathMLElement::cachedBooleanAttribute(const QualifiedName& name, BooleanAttribute& attribute) 530 { 531 if (!attribute.dirty) 532 return attribute.value; 520 const MathMLElement::Length& MathMLElement::cachedMathMLLength(const QualifiedName& name, Optional<Length>& length) 521 { 522 if (length) 523 return length.value(); 524 length = parseMathMLLength(attributeWithoutSynchronization(name)); 525 return length.value(); 526 } 527 528 const MathMLElement::BooleanValue& MathMLElement::cachedBooleanAttribute(const QualifiedName& name, Optional<BooleanValue>& attribute) 529 { 530 if (attribute) 531 return attribute.value(); 533 532 534 533 // In MathML, attribute values are case-sensitive. 535 534 const AtomicString& value = attributeWithoutSynchronization(name); 536 535 if (value == "true") 537 attribute .value= BooleanValue::True;536 attribute = BooleanValue::True; 538 537 else if (value == "false") 539 attribute .value= BooleanValue::False;538 attribute = BooleanValue::False; 540 539 else 541 attribute.value = BooleanValue::Default; 542 attribute.dirty = false; 543 544 return attribute.value; 540 attribute = BooleanValue::Default; 541 542 return attribute.value(); 545 543 } 546 544 … … 590 588 { 591 589 if (!acceptsDisplayStyleAttribute()) 592 return Optional<bool>();590 return Nullopt; 593 591 const MathMLElement::BooleanValue& specifiedDisplayStyle = cachedBooleanAttribute(displaystyleAttr, m_displayStyle); 594 return specifiedDisplayStyle == BooleanValue::Default ? Optional<bool>() : Optional<bool>(specifiedDisplayStyle == BooleanValue::True);592 return toOptionalBool(specifiedDisplayStyle); 595 593 } 596 594 … … 598 596 { 599 597 if (!acceptsMathVariantAttribute()) 600 return Optional<MathVariant>(); 601 if (m_mathVariant.dirty) { 602 m_mathVariant.value = parseMathVariantAttribute(attributeWithoutSynchronization(mathvariantAttr)); 603 m_mathVariant.dirty = false; 604 } 605 return m_mathVariant.value == MathVariant::None ? Optional<MathVariant>() : Optional<MathVariant>(m_mathVariant.value); 598 return Nullopt; 599 if (!m_mathVariant) 600 m_mathVariant = parseMathVariantAttribute(attributeWithoutSynchronization(mathvariantAttr)); 601 return m_mathVariant.value() == MathVariant::None ? Nullopt : m_mathVariant; 606 602 } 607 603 -
trunk/Source/WebCore/mathml/MathMLElement.h
r203679 r204021 64 64 LengthType type { LengthType::ParsingFailed }; 65 65 float value { 0 }; 66 bool dirty { true };67 66 }; 68 67 static Length parseMathMLLength(const String&); 69 68 70 69 enum class BooleanValue { True, False, Default }; 71 struct BooleanAttribute {72 BooleanValue value { BooleanValue::Default };73 bool dirty { true };74 };75 70 76 71 // These are the mathvariant values from the MathML recommendation. … … 98 93 Stretched = 18 99 94 }; 100 struct MathVariantAttribute {101 MathVariant value { MathVariant::None };102 bool dirty { true };103 };104 95 105 96 virtual Optional<bool> specifiedDisplayStyle(); 106 Optional<Math MLElement::MathVariant> specifiedMathVariant();97 Optional<MathVariant> specifiedMathVariant(); 107 98 108 99 protected: … … 122 113 void defaultEventHandler(Event*) override; 123 114 124 const Length& cachedMathMLLength(const QualifiedName&, Length&);125 const BooleanValue& cachedBooleanAttribute(const QualifiedName&, BooleanAttribute&);115 const Length& cachedMathMLLength(const QualifiedName&, Optional<Length>&); 116 const BooleanValue& cachedBooleanAttribute(const QualifiedName&, Optional<BooleanValue>&); 126 117 127 118 virtual bool acceptsDisplayStyleAttribute() { return false; } 128 119 virtual bool acceptsMathVariantAttribute() { return false; } 129 120 130 BooleanAttribute m_displayStyle; 131 MathVariantAttribute m_mathVariant; 121 static Optional<bool> toOptionalBool(const BooleanValue& value) { return value == BooleanValue::Default ? Nullopt : Optional<bool>(value == BooleanValue::True); } 122 Optional<BooleanValue> m_displayStyle; 123 Optional<MathVariant> m_mathVariant; 132 124 133 125 private: -
trunk/Source/WebCore/mathml/MathMLFractionElement.cpp
r203324 r204021 48 48 const MathMLElement::Length& MathMLFractionElement::lineThickness() 49 49 { 50 if ( !m_lineThickness.dirty)51 return m_lineThickness ;50 if (m_lineThickness) 51 return m_lineThickness.value(); 52 52 53 53 // The MathML3 recommendation states that "medium" is the default thickness. 54 54 // However, it only states that "thin" and "thick" are respectively thiner and thicker. 55 55 // The MathML in HTML5 implementation note suggests 50% and 200% and these values are also used in Gecko. 56 String thickness = attributeWithoutSynchronization(linethicknessAttr); 56 auto& thickness = attributeWithoutSynchronization(linethicknessAttr); 57 m_lineThickness = Length(); 57 58 if (equalLettersIgnoringASCIICase(thickness, "thin")) { 58 m_lineThickness. type = LengthType::UnitLess;59 m_lineThickness.value = .5;59 m_lineThickness.value().type = LengthType::UnitLess; 60 m_lineThickness.value().value = .5; 60 61 } else if (equalLettersIgnoringASCIICase(thickness, "medium")) { 61 m_lineThickness. type = LengthType::UnitLess;62 m_lineThickness.value = 1;62 m_lineThickness.value().type = LengthType::UnitLess; 63 m_lineThickness.value().value = 1; 63 64 } else if (equalLettersIgnoringASCIICase(thickness, "thick")) { 64 m_lineThickness. type = LengthType::UnitLess;65 m_lineThickness.value = 2;65 m_lineThickness.value().type = LengthType::UnitLess; 66 m_lineThickness.value().value = 2; 66 67 } else 67 68 m_lineThickness = parseMathMLLength(thickness); 68 m_lineThickness.dirty = false; 69 return m_lineThickness; 69 return m_lineThickness.value(); 70 70 } 71 71 72 MathMLFractionElement::FractionAlignment MathMLFractionElement::cachedFractionAlignment(const QualifiedName& name, FractionAlignmentAttribute& alignment)72 MathMLFractionElement::FractionAlignment MathMLFractionElement::cachedFractionAlignment(const QualifiedName& name, Optional<FractionAlignment>& alignment) 73 73 { 74 if ( !alignment.dirty)75 return alignment.value ;74 if (alignment) 75 return alignment.value(); 76 76 77 Stringvalue = attributeWithoutSynchronization(name);77 auto& value = attributeWithoutSynchronization(name); 78 78 if (equalLettersIgnoringASCIICase(value, "left")) 79 alignment .value= FractionAlignmentLeft;79 alignment = FractionAlignmentLeft; 80 80 else if (equalLettersIgnoringASCIICase(value, "right")) 81 alignment .value= FractionAlignmentRight;81 alignment = FractionAlignmentRight; 82 82 else 83 alignment.value = FractionAlignmentCenter; 84 alignment.dirty = false; 85 return alignment.value; 83 alignment = FractionAlignmentCenter; 84 return alignment.value(); 86 85 } 87 86 … … 99 98 { 100 99 if (name == linethicknessAttr) 101 m_lineThickness .dirty = true;100 m_lineThickness = Nullopt; 102 101 else if (name == numalignAttr) 103 m_numeratorAlignment .dirty = true;102 m_numeratorAlignment = Nullopt; 104 103 else if (name == denomalignAttr) 105 m_denominatorAlignment .dirty = true;104 m_denominatorAlignment = Nullopt; 106 105 107 106 MathMLElement::parseAttribute(name, value); -
trunk/Source/WebCore/mathml/MathMLFractionElement.h
r203285 r204021 48 48 void parseAttribute(const QualifiedName&, const AtomicString&) final; 49 49 50 struct FractionAlignmentAttribute { 51 FractionAlignment value { FractionAlignmentCenter }; 52 bool dirty { true }; 53 }; 54 FractionAlignment cachedFractionAlignment(const QualifiedName&, FractionAlignmentAttribute&); 50 FractionAlignment cachedFractionAlignment(const QualifiedName&, Optional<FractionAlignment>&); 55 51 56 Lengthm_lineThickness;57 FractionAlignmentAttributem_numeratorAlignment;58 FractionAlignmentAttributem_denominatorAlignment;52 Optional<Length> m_lineThickness; 53 Optional<FractionAlignment> m_numeratorAlignment; 54 Optional<FractionAlignment> m_denominatorAlignment; 59 55 }; 60 56 -
trunk/Source/WebCore/mathml/MathMLInlineContainerElement.cpp
r203679 r204021 91 91 bool mathVariantAttribute = name == mathvariantAttr && acceptsMathVariantAttribute(); 92 92 if (displayStyleAttribute) 93 m_displayStyle .dirty = true;93 m_displayStyle = Nullopt; 94 94 if (mathVariantAttribute) 95 m_mathVariant .dirty = true;95 m_mathVariant = Nullopt; 96 96 if ((displayStyleAttribute || mathVariantAttribute) && renderer()) 97 97 MathMLStyle::resolveMathMLStyleTree(renderer()); -
trunk/Source/WebCore/mathml/MathMLMathElement.cpp
r203679 r204021 59 59 if (cachedBooleanAttribute(displaystyleAttr, m_displayStyle) == BooleanValue::Default) { 60 60 // The default displaystyle value of the <math> depends on the display attribute, so we parse it here. 61 const AtomicString& value = attributeWithoutSynchronization(displayAttr);61 auto& value = attributeWithoutSynchronization(displayAttr); 62 62 if (value == "block") 63 m_displayStyle .value= BooleanValue::True;63 m_displayStyle = BooleanValue::True; 64 64 else if (value == "inline") 65 m_displayStyle .value= BooleanValue::False;65 m_displayStyle = BooleanValue::False; 66 66 } 67 return m_displayStyle.value == BooleanValue::Default ? Optional<bool>() : Optional<bool>(m_displayStyle.value == BooleanValue::True);67 return toOptionalBool(m_displayStyle.value()); 68 68 } 69 69 … … 73 73 bool mathVariantAttribute = name == mathvariantAttr; 74 74 if (displayStyleAttribute) 75 m_displayStyle .dirty = true;75 m_displayStyle = Nullopt; 76 76 if (mathVariantAttribute) 77 m_mathVariant .dirty = true;77 m_mathVariant = Nullopt; 78 78 if ((displayStyleAttribute || mathVariantAttribute) && renderer()) 79 79 MathMLStyle::resolveMathMLStyleTree(renderer()); -
trunk/Source/WebCore/mathml/MathMLOperatorElement.cpp
r203896 r204021 64 64 return m_operatorText.value(); 65 65 66 m_operatorText = Optional<UChar>(parseOperatorText(textContent()));66 m_operatorText = parseOperatorText(textContent()); 67 67 return m_operatorText.value(); 68 68 } … … 70 70 void MathMLOperatorElement::childrenChanged(const ChildChange& change) 71 71 { 72 m_operatorText = Optional<UChar>();72 m_operatorText = Nullopt; 73 73 MathMLTextElement::childrenChanged(change); 74 74 } -
trunk/Source/WebCore/mathml/MathMLPaddedElement.cpp
r203150 r204021 74 74 { 75 75 if (name == widthAttr) 76 m_width .dirty = true;76 m_width = Nullopt; 77 77 else if (name == heightAttr) 78 m_height .dirty = true;78 m_height = Nullopt; 79 79 else if (name == depthAttr) 80 m_depth .dirty = true;80 m_depth = Nullopt; 81 81 else if (name == lspaceAttr) 82 m_lspace .dirty = true;82 m_lspace = Nullopt; 83 83 else if (name == voffsetAttr) 84 m_voffset .dirty = true;84 m_voffset = Nullopt; 85 85 86 86 MathMLElement::parseAttribute(name, value); -
trunk/Source/WebCore/mathml/MathMLPaddedElement.h
r203228 r204021 45 45 void parseAttribute(const QualifiedName&, const AtomicString&) final; 46 46 47 Lengthm_width;48 Lengthm_height;49 Lengthm_depth;50 Lengthm_lspace;51 Lengthm_voffset;47 Optional<Length> m_width; 48 Optional<Length> m_height; 49 Optional<Length> m_depth; 50 Optional<Length> m_lspace; 51 Optional<Length> m_voffset; 52 52 }; 53 53 -
trunk/Source/WebCore/mathml/MathMLScriptsElement.cpp
r203553 r204021 59 59 { 60 60 if (name == subscriptshiftAttr) 61 m_subscriptShift .dirty = true;61 m_subscriptShift = Nullopt; 62 62 else if (name == superscriptshiftAttr) 63 m_superscriptShift .dirty = true;63 m_superscriptShift = Nullopt; 64 64 65 65 MathMLElement::parseAttribute(name, value); -
trunk/Source/WebCore/mathml/MathMLScriptsElement.h
r203553 r204021 44 44 void parseAttribute(const QualifiedName&, const AtomicString&) override; 45 45 46 Lengthm_subscriptShift;47 Lengthm_superscriptShift;46 Optional<Length> m_subscriptShift; 47 Optional<Length> m_superscriptShift; 48 48 }; 49 49 -
trunk/Source/WebCore/mathml/MathMLSpaceElement.cpp
r203108 r204021 64 64 { 65 65 if (name == widthAttr) 66 m_width .dirty = true;66 m_width = Nullopt; 67 67 else if (name == heightAttr) 68 m_height .dirty = true;68 m_height = Nullopt; 69 69 else if (name == depthAttr) 70 m_depth .dirty = true;70 m_depth = Nullopt; 71 71 72 72 MathMLElement::parseAttribute(name, value); -
trunk/Source/WebCore/mathml/MathMLSpaceElement.h
r203228 r204021 43 43 void parseAttribute(const QualifiedName&, const AtomicString&) final; 44 44 45 Lengthm_width;46 Lengthm_height;47 Lengthm_depth;45 Optional<Length> m_width; 46 Optional<Length> m_height; 47 Optional<Length> m_depth; 48 48 }; 49 49 -
trunk/Source/WebCore/mathml/MathMLTextElement.cpp
r203688 r204021 66 66 { 67 67 if (name == mathvariantAttr) { 68 m_mathVariant .dirty = true;68 m_mathVariant = Nullopt; 69 69 if (renderer()) 70 70 MathMLStyle::resolveMathMLStyleTree(renderer()); -
trunk/Source/WebCore/mathml/MathMLUnderOverElement.cpp
r203553 r204021 59 59 { 60 60 if (name == accentAttr) 61 m_accent .dirty = true;61 m_accent = Nullopt; 62 62 else if (name == accentunderAttr) 63 m_accentUnder .dirty = true;63 m_accentUnder = Nullopt; 64 64 65 65 MathMLElement::parseAttribute(name, value); -
trunk/Source/WebCore/mathml/MathMLUnderOverElement.h
r203553 r204021 42 42 void parseAttribute(const QualifiedName&, const AtomicString&) final; 43 43 44 BooleanAttributem_accent;45 BooleanAttributem_accentUnder;44 Optional<BooleanValue> m_accent; 45 Optional<BooleanValue> m_accentUnder; 46 46 }; 47 47
Note: See TracChangeset
for help on using the changeset viewer.