COLRv1 gradient points values are losing precision while rounding
FreeType is losing the precision of the COLRv1 gradient points values while rounding them. This can cause jittering during the animation of variable colour fonts. We have been facing this issue in Chromium, see crbug.com/1473020.
The reason behind it is that when FreeType tries to get the item delta values from the COLR table in tt_var_get_item_delta
, it calls FT_MulAddFix
to compute the delta values and returns the result of FT_MulAddFix
in tt_var_get_item_delta
. In FT_MulAddFix
delta values are rounded and cast to FT_Int32
which causes losing precision of the fractional part of the delta value. Later on, when the gradient points are defined in read_paint
, they are converted back to fixed using INT_TO_FIXED
, where the previous precision loss in the fractional part cannot be recovered and therefore causing jittering during the animation.
It might be worth removing the rounding part in FT_MulAddFix
and store the item delta values in FT_Fixed
rather than in FT_Int32
for colour fonts, i.e. change the return type of tt_var_get_item_delta
to FT_Fixed
, so that we won't need to convert them back to FT_Fixed
, therefore we won't lose the precision.