Robofab script to address Multiple Masters

RachelR's picture

Hi all

Is it possible for a Robofab script to affect all the masters in a Multiple master font ?

I have a MM font with a Light and a Bold Master. I'm kerning this fonts and to speed thing up slightly I wrote this little script to transfer the kerning amount to glyph pairs with the same shape. The script works but only on the light master - is it possible to haveit work on both masters.


from robofab.world import CurrentFont
f = CurrentFont()
kerning = f.kerning
#
OA = kerning[('O','A')]
AO = kerning[('A','O')]
OV = kerning[('O','V')]
VO = kerning[('V','O')]
OW = kerning[('O','W')]
WO = kerning[('W','O')]
OY = kerning[('O','Y')]
YO = kerning[('Y','O')]
OX = kerning[('O','X')]
XO = kerning[('X','O')]
OT = kerning[('O','T')]
TO = kerning[('T','O')]
KO = kerning[('K','O')]
#
#
kerning[('A','C')] = kerning[('A','G')] = kerning[('A','Q')] = kerning[('A','OE')] = AO
kerning[('D','A')] = kerning[('Q','A')] = OA
#
kerning[('V','C')] = kerning[('V','G')] = kerning[('V','Q')] = kerning[('V','OE')] = VO
kerning[('D','V')] = kerning[('Q','V')] = OV
#
kerning[('W','C')] = kerning[('W','G')] = kerning[('W','Q')] = kerning[('W','OE')] = WO
kerning[('D','W')] = kerning[('Q','W')] = OW
#
kerning[('Y','C')] = kerning[('Y','G')] = kerning[('Y','Q')] = kerning[('Y','OE')] = YO
kerning[('D','Y')] = kerning[('Q','Y')] = OY
#
kerning[('X','C')] = kerning[('X','G')] = kerning[('X','Q')] = kerning[('X','OE')] = XO
kerning[('D','X')] = kerning[('Q','X')] = OX
#
kerning[('D','T')] = kerning[('Q','T')] = OT
kerning[('T','C')] = kerning[('T','Q')] = TO
#
kerning[('K','C')] = kerning[('K','G')] = kerning[('K','Q')] = kerning[('K','OE')] = KO
#
#
f.update()
print "UpperUpperKern Done"

Miguel Sousa's picture

I could be wrong, but AFAIK when you handle the kerning through Robofab you can only control the values of the first master. The kerning value amounts of the remaining masters will be the same as the first master. Therefore, you might have to use Robofab's naked() method and go from there, or use FontLab's API's all the way.

I've wrote several scripts for FL that handle MM kerning, and I can tell you things can be complicated. The kerning values reside in something that looks like a list, and are associated with the left glyph of the pair.

Imagine a 2-master font with only one kerning pair AV, with a kerning value of -50 for the first master, and -80 for the second. If you do,
print fl.font['A'].kerning[0].values
you'll get [-50,-80].

The difficulties start when you try to modify the values or add new pairs.

The list of kerning pairs is read-only, so this will fail,
fl.font['A'].kerning[0].values = [-10, -30]
but you can change the values one by one, like so,
fl.font['A'].kerning[0].values[0] = -10
fl.font['A'].kerning[0].values[1] = -30

And to copy the values of one pair to another pair, you first need to create that pair (if it doesn't exist already),
defaultKerningValue = -1
rightGlyphID = fl.font.FindGlyph('T')
pair = KerningPair(rightGlyphID, defaultKerningValue)
fl.font['A'].kerning.append(pair)

and then go through the values and modify them accordingly.

Again, handling MM kerning is not trivial. You might be better off saving AFM files, modifying them and reading back in. But that process is not 100% reliable sometimes, so proceed with care.

Jens Kutilek's picture

Rachel, what your script is trying to to can be handled by class kerning much easier. No coding necessary.

Miguel Sousa's picture

Very good point Jens.

aida's picture

You may be better off writing a single script that has a global variable defining the master. So run it once with the value 0 for light master, and then 1 for the next and so on. I've several scripts that I use on fonts with 7+ masters and this works fine, but I also don't do kerning within FontLab so I'm not 100% sure this will work for what you are doing.

Syndicate content Syndicate content