firamath / firamath

Sans-serif font with Unicode math support
https://firamath.github.io/
SIL Open Font License 1.1
436 stars 19 forks source link

Font dimensions related to \overline #29

Closed RuixiZhang42 closed 9 months ago

RuixiZhang42 commented 5 years ago

Related TeX.SX posts:


LuaTeX correctly implements \Umathoverbarkern, \Umathoverbarrule and \Umathoverbarvgap to construct an \overline object. However, XeTeX fails to use \fontdimen55, \fontdimen54 and \fontdimen53.

In my experiment, it seems that XeTeX uses \fontdimen54, \fontdimen54 and 3\fontdimen54 for kern, rule and vgap, respectively, according to most other OpenType math fonts. But this conjecture fails for Fira Math:

% !TeX program = LuaLaTeX % <- Everything lines up perfectly
% !TeX program = XeLaTeX %  <- Not good for Fira Math
\documentclass{article}
\usepackage{unicode-math}
\setmathfont[version=L]{Latin Modern Math}
\setmathfont[version=P]{TeX Gyre Pagella Math}
\setmathfont[version=T]{TeX Gyre Termes Math}
\setmathfont[version=F]{[FiraMath-Regular.otf]}% in the v0.4-beta-1 collection
\makeatletter
\def\test@overbarkern@fontdimen{55}% Not used. XeTeX mistake?
\def\test@overbarrule@fontdimen{54}
\def\test@overbarvgap@fontdimen{53}% Not used. XeTeX mistake?
\def\test@@family{2}
\def\test@overbarkern#1{\fontdimen\test@overbarrule@fontdimen
    \ifx#1\displaystyle\textfont
    \else\ifx#1\textstyle\textfont
        \else\ifx#1\scriptstyle\scriptfont
        \else\scriptscriptfont\fi\fi\fi \test@@family}
\def\test@overbarrule#1{\fontdimen\test@overbarrule@fontdimen
    \ifx#1\displaystyle\textfont
    \else\ifx#1\textstyle\textfont
        \else\ifx#1\scriptstyle\scriptfont
        \else\scriptscriptfont\fi\fi\fi \test@@family}
% The following is very likely an XeTeX engine-wise mistake,
% but it works for most other OTF math fonts.
\def\test@overbarvgap#1{\thr@@\fontdimen\test@overbarrule@fontdimen
    \ifx#1\displaystyle\textfont
    \else\ifx#1\textstyle\textfont
        \else\ifx#1\scriptstyle\scriptfont
        \else\scriptscriptfont\fi\fi\fi \test@@family}
\ifx\XeTeXcharclass\@undefined
    % LuaTeX primitives
    \global\let\test@overbarkern\Umathoverbarkern
    \global\let\test@overbarrule\Umathoverbarrule
    \global\let\test@overbarvgap\Umathoverbarvgap
\fi
\newcommand*\test{\mathpalette\test@stuff{xyz}}
\def\test@stuff#1#2{%
    \vbox{\hrule\@height0.1\p@\hbox{$\m@th#1\overline{#2}$}}\,%
    \vbox{%
    \hrule\@height0.1\p@
    \kern\test@overbarkern#1%
    \hrule\@height\test@overbarrule#1%
    \hbox{\vbox{%
        \kern\test@overbarvgap#1%
        \hbox{$\m@th#1#2$}%
    }}%
    },%
}
\newcommand*\dotest[1]{%
    \begingroup
    \mathversion{#1}%
    $\displaystyle\test$ $\textstyle\test$ $\scriptstyle\test$ $\scriptscriptstyle\test$%
    \endgroup
}
\makeatother

\begin{document}
\dotest{L}\par
\dotest{P}\par
\dotest{T}\par
\dotest{F}
\end{document}

XeLaTeX output: output

With LuaLaTeX, everything lines up perfectly no matter which math font is used.


Font issue v.s. engine issue

I think it is rather clear that the XeTeX engine still implements the wrong math font dimensions. However, even with the “wrong” dimensions used, all TeX Gyre Math fonts as well as Latin Modern Math pass the above test (did not test STIX2 or XITS yet).

This suggests maybe there is something wrong with Fira Math, but I honestly do not know.

RuixiZhang42 commented 5 years ago

table

Perhaps the two “rule thickness” entries should be changed to 50 from the current 66.

stone-zeng commented 5 years ago

According to Microsoft's OpenType specification, these constants are defined as:

The default rule thickness of fira math regular is 66. But I'm not sure whether the other constants should be changed. Still, I need to investigate it thoroughly.

RuixiZhang42 commented 5 years ago

There are definitely something not quite right in the math table. I managed to find two three more:

Axis heights do not match?

q1

TeX sees an unusual rule thickness

q3

Many rule thicknesses

FractionRuleThickness and RadicalRuleThickness are set to 76, while OverbarRuleThickness and UnderbarRuleThickness are 66, although all of them are recommended to be set as the default rule thickness.

stone-zeng commented 5 years ago

As FontForge's documentation says,

These values are stored in tfm files (should you generate a tfm file with your font).

So I think these TeX info has nothing to do with the OpenType MATH table, and hence simply leave them as the default values.

RuixiZhang42 commented 4 years ago

I just found out about the excellent papers by Bogusław Jackowski and Ulrik Vieth, where the authors illustrated Appendix G with drawings and discussed how to set various math font dimensions.

The resources include papers and slides, so I will provide a link that already has them gathered. They can be found at http://www.gust.org.pl/projects/e-foundry/math/index_html starting from “In the preparation for providing math typesetting support with the TeX Gyre fonts”

ppw0 commented 2 years ago

@RuixiZhang42 Even after going through that, I'm still at a loss as to how to have a thinner \overline that's a bit closer to the top of a number in Fira Math + XeTeX.

RuixiZhang42 commented 2 years ago

@ppw0 You can try something like this (no recommended unless you know what you are doing):

% only works with XeLaTeX + unicode-math (actually fontspec)
\setmathfont{Fira Math}[
  FontAdjustment = { % <- a secret option (undocumented)
    \fontdimen 53 \font = 0.75 \fontdimen 53 \font % <- reduce OverbarVerticalGap   to 75% of its original
    \fontdimen 54 \font = 0.5  \fontdimen 54 \font % <- reduce OverbarRuleThickness to 50% of its original
    \fontdimen 55 \font = ...
    % you will probably want to change underbar as well:
    \fontdimen 56 \font = ...
    \fontdimen 57 \font = ...
    \fontdimen 58 \font = ...
  }
]