Rely on Qt to handle small caps text

This has the advantage of simplifying our code and to produce the
correct output: the small capitals should have the exact same width as
the lower case letters.

The slanted fonts are also translated to oblique on Qt side, but this
does not seems to have an effect in my testing. It may be that proper
oblique fonts need to be installed.
This commit is contained in:
Jean-Marc Lasgouttes 2014-05-07 12:06:56 +02:00
parent 5368645e70
commit 015333d987
5 changed files with 12 additions and 99 deletions

View File

@ -304,8 +304,13 @@ GuiFontInfo::GuiFontInfo(FontInfo const & f)
switch (f.realShape()) {
case ITALIC_SHAPE:
font.setStyle(QFont::StyleItalic);
break;
case SLANTED_SHAPE:
font.setItalic(true);
font.setStyle(QFont::StyleOblique);
break;
case SMALLCAPS_SHAPE:
font.setCapitalization(QFont::SmallCaps);
break;
default:
break;
@ -327,19 +332,7 @@ GuiFontInfo::GuiFontInfo(FontInfo const & f)
LYXERR(Debug::FONT, "The font has size: " << font.pointSizeF());
if (f.realShape() != SMALLCAPS_SHAPE) {
metrics = GuiFontMetrics(font);
} else {
// handle small caps ourselves ...
FontInfo smallfont = f;
smallfont.decSize().decSize().setShape(UP_SHAPE);
QFont font2(font);
font2.setKerning(false);
font2.setPointSizeF(convert<double>(lyxrc.font_sizes[smallfont.size()])
* lyxrc.zoom / 100.0);
metrics = GuiFontMetrics(font, font2);
}
metrics = GuiFontMetrics(font);
}

View File

@ -40,7 +40,7 @@ namespace {
* these are not real ucs4 characters. These are codepoints in the
* computer modern fonts used, nothing unicode related.
* See comment in QLPainter::text() for more explanation.
**/
**/
inline QChar const ucs4_to_qchar(char_type const ucs4)
{
LATTEST(is_utf16(ucs4));
@ -49,14 +49,7 @@ inline QChar const ucs4_to_qchar(char_type const ucs4)
} // anon namespace
GuiFontMetrics::GuiFontMetrics(QFont const & font)
: metrics_(font, 0), smallcaps_metrics_(font), smallcaps_shape_(false)
{
}
GuiFontMetrics::GuiFontMetrics(QFont const & font, QFont const & smallcaps_font)
: metrics_(font, 0), smallcaps_metrics_(smallcaps_font), smallcaps_shape_(true)
GuiFontMetrics::GuiFontMetrics(QFont const & font) : metrics_(font, 0)
{
}
@ -115,27 +108,6 @@ int GuiFontMetrics::rbearing(char_type c) const
}
int GuiFontMetrics::smallcapsWidth(char_type c) const
{
// FIXME: Optimisation probably needed: we don't use the width cache.
if (is_utf16(c)) {
QChar const qc = ucs4_to_qchar(c);
QChar const uc = qc.toUpper();
if (qc != uc)
return smallcaps_metrics_.width(uc);
else
return metrics_.width(qc);
} else {
QString const s = toqstr(docstring(1, c));
QString const us = s.toUpper();
if (s != us)
return smallcaps_metrics_.width(us);
else
return metrics_.width(s);
}
}
int GuiFontMetrics::width(docstring const & s) const
{
size_t ls = s.size();
@ -145,10 +117,7 @@ int GuiFontMetrics::width(docstring const & s) const
/**
if isSurrogateBase(s[i]) {
docstring c = s[i];
if (smallcaps_shape_)
w += metrics_.width(toqstr(c + s[i + 1]));
else
w += smallcaps_metrics_.width(toqstr(c + s[i + 1]));
w += metrics_.width(toqstr(c + s[i + 1]));
++i;
}
else
@ -230,9 +199,6 @@ GuiFontMetrics::AscendDescend const GuiFontMetrics::fillMetricsCache(
int GuiFontMetrics::width(char_type c) const
{
if (smallcaps_shape_)
return smallcapsWidth(c);
int value = width_cache_.value(c, outOfLimitMetric);
if (value != outOfLimitMetric)
return value;
@ -250,7 +216,7 @@ int GuiFontMetrics::width(char_type c) const
int GuiFontMetrics::ascent(char_type c) const
{
static AscendDescend const outOfLimitAD =
static AscendDescend const outOfLimitAD =
{outOfLimitMetric, outOfLimitMetric};
AscendDescend value = metrics_cache_.value(c, outOfLimitAD);
if (value.ascent != outOfLimitMetric)
@ -263,7 +229,7 @@ int GuiFontMetrics::ascent(char_type c) const
int GuiFontMetrics::descent(char_type c) const
{
static AscendDescend const outOfLimitAD =
static AscendDescend const outOfLimitAD =
{outOfLimitMetric, outOfLimitMetric};
AscendDescend value = metrics_cache_.value(c, outOfLimitAD);
if (value.descent != outOfLimitMetric)

View File

@ -26,7 +26,6 @@ class GuiFontMetrics : public FontMetrics
{
public:
GuiFontMetrics(QFont const & font);
GuiFontMetrics(QFont const & font, QFont const & smallcaps_font);
virtual ~GuiFontMetrics() {}
@ -54,13 +53,8 @@ public:
int width(QString const & str) const;
private:
int smallcapsWidth(char_type c) const;
/// Metrics on the font
QFontMetrics metrics_;
QFontMetrics smallcaps_metrics_;
bool smallcaps_shape_;
/// Cache of char widths
mutable QHash<char_type, int> width_cache_;

View File

@ -276,33 +276,6 @@ int GuiPainter::text(int x, int y, char_type c, FontInfo const & f)
}
int GuiPainter::smallCapsText(int x, int y,
QString const & s, FontInfo const & f)
{
FontInfo smallfont(f);
smallfont.decSize().decSize().setShape(UP_SHAPE);
QFont const & qfont = getFont(f);
QFont const & qsmallfont = getFont(smallfont);
setQPainterPen(computeColor(f.realColor()));
int textwidth = 0;
size_t const ls = s.length();
for (unsigned int i = 0; i < ls; ++i) {
QChar const c = s[i].toUpper();
if (c != s.at(i)) {
setFont(qsmallfont);
} else {
setFont(qfont);
}
if (isDrawingEnabled())
drawText(x + textwidth, y, c);
textwidth += fontMetrics().width(c);
}
return textwidth;
}
int GuiPainter::text(int x, int y, docstring const & s,
FontInfo const & f)
{
@ -334,12 +307,6 @@ int GuiPainter::text(int x, int y, docstring const & s,
int textwidth;
if (f.realShape() == SMALLCAPS_SHAPE) {
textwidth = smallCapsText(x, y, str, f);
textDecoration(f, x, y, textwidth);
return textwidth;
}
// Here we use the font width cache instead of
// textwidth = fontMetrics().width(str);
// because the above is awfully expensive on MacOSX

View File

@ -144,13 +144,6 @@ private:
/// draw a bevelled button border
void buttonFrame(int x, int y, int w, int h);
/// draw small caps text
/**
\return width of the drawn text.
*/
int smallCapsText(int x, int y,
QString const & str, FontInfo const & f);
/// set pen parameters
void setQPainterPen(QColor const & col,
line_style ls = line_solid, float lw = thin_line);