1 /* This Source Code Form is subject to the terms of the Mozilla Public
2  * License, v. 2.0. If a copy of the MPL was not distributed with this
3  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4 
5 #ifndef GFX_MATH_TABLE_H
6 #define GFX_MATH_TABLE_H
7 
8 #include "gfxFont.h"
9 
10 /**
11  * Used by |gfxFont| to represent the MATH table of an OpenType font.
12  * Each |gfxFont| owns at most one |gfxMathTable| instance.
13  */
14 class gfxMathTable {
15  public:
16   /**
17    * @param aFace The HarfBuzz face containing the math table.
18    * @param aSize The font size to pass to HarfBuzz.
19    */
20   gfxMathTable(hb_face_t* aFace, gfxFloat aSize);
21 
22   /**
23    * Releases our reference to the MATH table and cleans up everything else.
24    */
25   ~gfxMathTable();
26 
27   enum MathConstant {
28     // The order of the constants must match the order of the fields
29     // defined in the MATH table.
30     ScriptPercentScaleDown,
31     ScriptScriptPercentScaleDown,
32     DelimitedSubFormulaMinHeight,
33     DisplayOperatorMinHeight,
34     MathLeading,
35     AxisHeight,
36     AccentBaseHeight,
37     FlattenedAccentBaseHeight,
38     SubscriptShiftDown,
39     SubscriptTopMax,
40     SubscriptBaselineDropMin,
41     SuperscriptShiftUp,
42     SuperscriptShiftUpCramped,
43     SuperscriptBottomMin,
44     SuperscriptBaselineDropMax,
45     SubSuperscriptGapMin,
46     SuperscriptBottomMaxWithSubscript,
47     SpaceAfterScript,
48     UpperLimitGapMin,
49     UpperLimitBaselineRiseMin,
50     LowerLimitGapMin,
51     LowerLimitBaselineDropMin,
52     StackTopShiftUp,
53     StackTopDisplayStyleShiftUp,
54     StackBottomShiftDown,
55     StackBottomDisplayStyleShiftDown,
56     StackGapMin,
57     StackDisplayStyleGapMin,
58     StretchStackTopShiftUp,
59     StretchStackBottomShiftDown,
60     StretchStackGapAboveMin,
61     StretchStackGapBelowMin,
62     FractionNumeratorShiftUp,
63     FractionNumeratorDisplayStyleShiftUp,
64     FractionDenominatorShiftDown,
65     FractionDenominatorDisplayStyleShiftDown,
66     FractionNumeratorGapMin,
67     FractionNumDisplayStyleGapMin,
68     FractionRuleThickness,
69     FractionDenominatorGapMin,
70     FractionDenomDisplayStyleGapMin,
71     SkewedFractionHorizontalGap,
72     SkewedFractionVerticalGap,
73     OverbarVerticalGap,
74     OverbarRuleThickness,
75     OverbarExtraAscender,
76     UnderbarVerticalGap,
77     UnderbarRuleThickness,
78     UnderbarExtraDescender,
79     RadicalVerticalGap,
80     RadicalDisplayStyleVerticalGap,
81     RadicalRuleThickness,
82     RadicalExtraAscender,
83     RadicalKernBeforeDegree,
84     RadicalKernAfterDegree,
85     RadicalDegreeBottomRaisePercent
86   };
87 
88   /**
89    * Returns the value of the specified constant from the MATH table.
90    */
91   gfxFloat Constant(MathConstant aConstant) const;
92 
93   /**
94    * Returns the value of the specified constant in app units.
95    */
Constant(MathConstant aConstant,uint32_t aAppUnitsPerDevPixel)96   nscoord Constant(MathConstant aConstant,
97                    uint32_t aAppUnitsPerDevPixel) const {
98     return NSToCoordRound(Constant(aConstant) * aAppUnitsPerDevPixel);
99   }
100 
101   /**
102    *  If the MATH table contains an italic correction for that glyph, this
103    *  function returns the corresponding value. Otherwise it returns 0.
104    */
105   gfxFloat ItalicsCorrection(uint32_t aGlyphID) const;
106 
107   /**
108    * @param aGlyphID  glyph index of the character we want to stretch
109    * @param aVertical direction of the stretching (vertical/horizontal)
110    * @param aSize     the desired size variant
111    *
112    * Returns the glyph index of the desired size variant or 0 if there is not
113    * any such size variant.
114    */
115   uint32_t VariantsSize(uint32_t aGlyphID, bool aVertical,
116                         uint16_t aSize) const;
117 
118   /**
119    * @param aGlyphID  glyph index of the character we want to stretch
120    * @param aVertical direction of the stretching (vertical/horizontal)
121    * @param aGlyphs   pre-allocated buffer of 4 elements where the glyph
122    * indexes (or 0 for absent parts) will be stored. The parts are stored in
123    * the order expected by the nsMathMLChar: Top (or Left), Middle, Bottom
124    * (or Right), Glue.
125    *
126    * Tries to fill-in aGlyphs with the relevant glyph indexes and returns
127    * whether the operation was successful. The function returns false if
128    * there is not any assembly for the character we want to stretch or if
129    * the format is not supported by the nsMathMLChar code.
130    *
131    */
132   bool VariantsParts(uint32_t aGlyphID, bool aVertical,
133                      uint32_t aGlyphs[4]) const;
134 
135  private:
136   // size-specific font object, owned by the gfxMathTable
137   hb_font_t* mHBFont;
138 
139   static const unsigned int kMaxCachedSizeCount = 10;
140   struct MathVariantCacheEntry {
141     uint32_t glyphID;
142     bool vertical;
143     uint32_t sizes[kMaxCachedSizeCount];
144     uint32_t parts[4];
145     bool arePartsValid;
146   };
147   mutable MathVariantCacheEntry mMathVariantCache;
148   void ClearCache() const;
149   void UpdateMathVariantCache(uint32_t aGlyphID, bool aVertical) const;
150 };
151 
152 #endif
153