adobe-type-tools / afdko

Adobe Font Development Kit for OpenType
https://adobe-type-tools.github.io/afdko/
Other
1.05k stars 167 forks source link

Reusing components / subroutinezation is missing? #1319

Closed dy closed 3 years ago

dy commented 3 years ago

Trying to implement composite glyphs in wavefont as reusing smaller glyphs with overlay: image

Running the following commands to build variable OTF:

buildmasterotfs --mkot -r,-S,-omitMacNames -d masters/wavefont.designspace
buildcff2vf -c -k -d masters/wavefont.designspace -o ./font/wavefont.otf

Resulting OTF font file size increases from 35kb for simple glyphs to 48kb for composed glyphs. To compare, TTF font size reduces from 35kb for simple glyphs to 27kb for composed glyphs, due to components reuse.

Inspecting masters shows that OTF doesn't use components, unlike TTF, but instead flattens glyph shapes: image

With TTF the upper/lower halves reuse _50 glyph: image

I expected subroutinization to be on-par with TTF components, but it seems it's missing or not as efficient in terms of reducing font size.

Is there a special option to force subroutinization/ehnance OTF build, or any sort of components-like technique of reusing glyphs, or that file size tax is unavoidable?

benkiel commented 3 years ago

(edit, I missed the command above)

@dy did you try with just -r? That turns on subroutines, the -S isn't needed.

Depending on the design, the subroutinization will be on par with TTF OTF components, smaller, or sometimes larger: it depends on if flattening components and removing overlap makes new shapes or if there are lots of shapes that can be compacted easily. Someone from Adobe will likely have a more detailed answer than that.

dy commented 3 years ago

-r without -S doesn't seem to make much difference. Just curious if that particular case can be expected to be more optimal, or the result is correct.

josh-hadley commented 3 years ago

CFF subroutinization does not work the same way as TTF composite glyphs. They're similar ideas (pattern replacement) but CFF subroutinization works on the sub-path level (curve/line segments that make up a larger contour) whereas TTF is typically complete contours or groups of contours (i.e. if you have glyphsAacute, A, and acute, you could potentially build Aacute with a recipe of something like "A + acute moved up and over a little"). TTF composite glyphs can also make use of a 2x2 transformation matrix to enable stretching/slanting/rotating components.

As @benkiel pointed out, the design will dictate the savings. Sometimes subroutinization yields larger savings, sometimes componentization does.

Additionally, as noted in this thread, the order of glyph analysis for subroutinization can impact the size efficiency. Both makeotf and tx support subroutinization, but they can yield different results because the glyphs get analyzed in a different order. So for fun, you might try subroutinizing with tx and see if it makes any difference.

miguelsousa commented 3 years ago

@dy buildcff2vf doesn't do any subroutinization; it needs to be done as a separate step afterwards. See this example.

cjchapman commented 3 years ago

There's also an example in the AFDKO wiki: How to subroutinize a CFF or CFF2 font

josh-hadley commented 3 years ago

@dy I think your question is answered, so I'm going to close this issue. Please re-open if you have remaining concerns or questions related to this.

dy commented 3 years ago

Sorry for the delay, was hoping to test out with linefont. After performing cp ./font/wavefont.otf ./font/wavefont.min.otf && tx -cff2 +S +b ./font/wavefont.otf > ./font/table.CFF2 && sfntedit -a CFF2=./font/table.CFF2 ./font/wavefont.min.otf from howto example the font loses/doesn't display same glyphs. Should there be some additional config or feature-file? Thanks

before-after-subr.zip

josh-hadley commented 3 years ago

@dy I'm unable to reproduce that problem here. I agree that the wavefont.min.otf that you attached is not correct; it seems that something became corrupted:

$ tx -dump -1 wavefont.min.otf 
tx: --- wavefont.min.otf
tx: (cfr) bad INDEX header

When I run those commands here, I get different output (attached).

wavefont.min.otf.zip