Bug 1293210 - add cap height support to nsFontMetrics.
MozReview-Commit-ID: 8EXWUtbuN3s
--- a/gfx/src/nsFontMetrics.cpp
+++ b/gfx/src/nsFontMetrics.cpp
@@ -168,16 +168,22 @@ nsFontMetrics::GetMetrics(gfxFont::Orien
nscoord
nsFontMetrics::XHeight()
{
return ROUND_TO_TWIPS(GetMetrics().xHeight);
}
nscoord
+nsFontMetrics::CapHeight()
+{
+ return ROUND_TO_TWIPS(GetMetrics().capHeight);
+}
+
+nscoord
nsFontMetrics::SuperscriptOffset()
{
return ROUND_TO_TWIPS(GetMetrics().emHeight *
NS_FONT_SUPERSCRIPT_OFFSET_RATIO);
}
nscoord
nsFontMetrics::SubscriptOffset()
--- a/gfx/src/nsFontMetrics.h
+++ b/gfx/src/nsFontMetrics.h
@@ -70,16 +70,21 @@ public:
void Destroy();
/**
* Return the font's x-height.
*/
nscoord XHeight();
/**
+ * Return the font's cap-height.
+ */
+ nscoord CapHeight();
+
+ /**
* Return the font's superscript offset (the distance from the
* baseline to where a superscript's baseline should be placed).
* The value returned will be positive.
*/
nscoord SuperscriptOffset();
/**
* Return the font's subscript offset (the distance from the
--- a/gfx/thebes/gfxFont.cpp
+++ b/gfx/thebes/gfxFont.cpp
@@ -3454,22 +3454,28 @@ gfxFont::InitMetricsFromSfntTables(Metri
SET_UNSIGNED(underlineSize, post->underlineThickness);
// 'OS/2' table is optional, if not found we'll estimate xHeight
// and aveCharWidth by measuring glyphs
gfxFontEntry::AutoTable os2Table(mFontEntry, kOS_2TableTag);
if (os2Table) {
const OS2Table *os2 =
reinterpret_cast<const OS2Table*>(hb_blob_get_data(os2Table, &len));
- // although sxHeight is a signed field, we consider negative values to
- // be erroneous and just ignore them
- if (len >= offsetof(OS2Table, sxHeight) + sizeof(int16_t) &&
- uint16_t(os2->version) >= 2 && int16_t(os2->sxHeight) > 0) {
- // version 2 and later includes the x-height field
- SET_SIGNED(xHeight, os2->sxHeight);
+ // although sxHeight and sCapHeight are signed fields, we consider
+ // negative values to be erroneous and just ignore them
+ if (uint16_t(os2->version) >= 2) {
+ // version 2 and later includes the x-height and cap-height fields
+ if (len >= offsetof(OS2Table, sxHeight) + sizeof(int16_t) &&
+ int16_t(os2->sxHeight) > 0) {
+ SET_SIGNED(xHeight, os2->sxHeight);
+ }
+ if (len >= offsetof(OS2Table, sCapHeight) + sizeof(int16_t) &&
+ int16_t(os2->sCapHeight) > 0) {
+ SET_SIGNED(capHeight, os2->sCapHeight);
+ }
}
// this should always be present in any valid OS/2 of any version
if (len >= offsetof(OS2Table, sTypoLineGap) + sizeof(int16_t)) {
SET_SIGNED(aveCharWidth, os2->xAvgCharWidth);
SET_SIGNED(strikeoutSize, os2->yStrikeoutSize);
SET_SIGNED(strikeoutOffset, os2->yStrikeoutPosition);
// for fonts with USE_TYPO_METRICS set in the fsSelection field,
@@ -3507,16 +3513,22 @@ void gfxFont::CalculateDerivedMetrics(Me
if (aMetrics.xHeight <= 0) {
// only happens if we couldn't find either font metrics
// or a char to measure;
// pick an arbitrary value that's better than zero
aMetrics.xHeight = aMetrics.maxAscent * DEFAULT_XHEIGHT_FACTOR;
}
+ // If we have a font that doesn't provide a capHeight value, use maxAscent
+ // as a reasonable fallback.
+ if (aMetrics.capHeight <= 0) {
+ aMetrics.capHeight = aMetrics.maxAscent;
+ }
+
aMetrics.maxHeight = aMetrics.maxAscent + aMetrics.maxDescent;
if (aMetrics.maxHeight - aMetrics.emHeight > 0.0) {
aMetrics.internalLeading = aMetrics.maxHeight - aMetrics.emHeight;
} else {
aMetrics.internalLeading = 0.0;
}
@@ -3769,16 +3781,17 @@ gfxFont::CreateVerticalMetrics()
metrics->strikeoutSize = std::max(1.0, metrics->strikeoutSize);
metrics->strikeoutOffset = - 0.5 * metrics->strikeoutSize;
// Somewhat arbitrary values for now, subject to future refinement...
metrics->spaceWidth = metrics->aveCharWidth;
metrics->zeroOrAveCharWidth = metrics->aveCharWidth;
metrics->maxHeight = metrics->maxAscent + metrics->maxDescent;
metrics->xHeight = metrics->emHeight / 2;
+ metrics->capHeight = metrics->maxAscent;
return metrics;
}
gfxFloat
gfxFont::SynthesizeSpaceWidth(uint32_t aCh)
{
// return an appropriate width for various Unicode space characters
--- a/gfx/thebes/gfxFont.h
+++ b/gfx/thebes/gfxFont.h
@@ -1507,16 +1507,17 @@ public:
virtual already_AddRefed<mozilla::gfx::GlyphRenderingOptions>
GetGlyphRenderingOptions(const TextRunDrawParams* aRunParams = nullptr)
{ return nullptr; }
gfxFloat SynthesizeSpaceWidth(uint32_t aCh);
// Font metrics
struct Metrics {
+ gfxFloat capHeight;
gfxFloat xHeight;
gfxFloat strikeoutSize;
gfxFloat strikeoutOffset;
gfxFloat underlineSize;
gfxFloat underlineOffset;
gfxFloat internalLeading;
gfxFloat externalLeading;