diff --git a/Lib/glyphsLib/builder/builders.py b/Lib/glyphsLib/builder/builders.py index 74ec553af..60c50c54d 100644 --- a/Lib/glyphsLib/builder/builders.py +++ b/Lib/glyphsLib/builder/builders.py @@ -508,6 +508,10 @@ def _copy_bracket_layers_to_ufo_glyphs(self, bracket_layer_map): ) # swap components if base glyph contains matching bracket layers. for comp in ufo_glyph.components: + if comp.baseGlyph == glyph_name: + # Do not create self referencing glyph components. See: + # tests\builder\designspace_roundtrip_test.py::test_roundtrip_self_ref + continue bracket_comp_name = _bracket_glyph_name( comp.baseGlyph, reverse, location ) diff --git a/tests/builder/designspace_roundtrip_test.py b/tests/builder/designspace_roundtrip_test.py index 0c9685b57..86b4b8c81 100644 --- a/tests/builder/designspace_roundtrip_test.py +++ b/tests/builder/designspace_roundtrip_test.py @@ -76,3 +76,52 @@ def test_default_master_roundtrips(ufo_module): assert reg.copyGroups is True assert reg.copyInfo is True assert reg.copyLib is True + + +def test_roundtrip_self_ref(datadir, ufo_module): + """This test is to solve the problem of roundtrips sometimes resulting in + broken ufos when working with bracket layers. + + Starting with UFO: It's okay to have a bracket glyph that references its + base glyph as a component. However, on the glyphs.app side it's not okay + because the base and bracket glyphs are merged into a single glyph with + the bracket glyph now being a layer. Glyphsapp (2.6.1) does not like the + self referencing component, but that's the best we can do to preserve the + information. + + The goal here is to make sure that the valid ufo we start with, is still + valid in ufo after roundtriping. We are not concerned with making + glyphs.app work properly at the intemediary stage. + """ + path = datadir / "BracketSelfReference/BracketSelfReference.designspace" + designspace = designspaceLib.DesignSpaceDocument.fromfile(path) + + for source in designspace.sources: + font = ufo_module.Font(source.path) + assert "zero" in font + assert "zero.BRACKET.500" in font + assert "space" in font + + # Check zero.BRACKET.500 component correct + assert font["zero.BRACKET.500"].components[0].baseGlyph == "zero" + + gs_font = to_glyphs(designspace) + + # Check that the "zero" glyph contains our bracket layers + glyph_obj = gs_font.glyphs["zero"] + layer_names = [layer.name for layer in glyph_obj.layers] + assert "Regular [500]" in layer_names + assert "Bold [500]" in layer_names + + # Check that our bracket layers contain the base glyph as a component + bracket_layers = [layer for layer in glyph_obj.layers if "[500]" in layer.name] + for layer in bracket_layers: + component_names = [component.name for component in layer.components] + assert component_names == ["zero"] + + designspace2 = to_designspace(gs_font, ufo_module=ufo_module) + ufos = [source.font for source in designspace2.sources] + + # Check zero.BRACKET.500 does not reference itself after roundtrip + for ufo in ufos: + assert ufo["zero.BRACKET.500"].components[0].baseGlyph == "zero" diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/fontinfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/fontinfo.plist new file mode 100644 index 000000000..d8777d445 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/fontinfo.plist @@ -0,0 +1,36 @@ + + + + + ascender + 800 + capHeight + 700 + descender + -200 + familyName + BracketSelfReference + italicAngle + 0 + openTypeHeadCreated + 2019/07/25 10:20:06 + openTypeOS2Type + + 3 + + postscriptUnderlinePosition + -100 + postscriptUnderlineThickness + 50 + styleName + Bold + unitsPerEm + 1000 + versionMajor + 1 + versionMinor + 0 + xHeight + 500 + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/contents.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/contents.plist new file mode 100644 index 000000000..d0681736d --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/contents.plist @@ -0,0 +1,12 @@ + + + + + space + space.glif + zero + zero.glif + zero.BRACKET.500 + zero.B_R_A_C_K_E_T_.500.glif + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/layerinfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/layerinfo.plist new file mode 100644 index 000000000..88994ea41 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/layerinfo.plist @@ -0,0 +1,15 @@ + + + + + lib + + com.schriftgestaltung.layerId + 48798C20-C9A0-4BB9-9A3E-BDB30805D9C9 + com.schriftgestaltung.layerOrderInGlyph.space + 1 + com.schriftgestaltung.layerOrderInGlyph.zero + 0 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/space.glif b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/space.glif new file mode 100644 index 000000000..56fe0bf3d --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/space.glif @@ -0,0 +1,13 @@ + + + + + + + + + com.schriftgestaltung.Glyphs.lastChange + 2019/07/25 10:21:14 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif new file mode 100644 index 000000000..ed8933060 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif @@ -0,0 +1,15 @@ + + + + + + + + + com.schriftgestaltung.Glyphs._originalLayerName + Bold [500] + com.schriftgestaltung.Glyphs.lastChange + 2021/03/31 15:27:05 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.glif b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.glif new file mode 100644 index 000000000..ed2efb1d6 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/glyphs/zero.glif @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + + com.schriftgestaltung.Glyphs.lastChange + 2021/03/31 15:27:05 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/layercontents.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/layercontents.plist new file mode 100644 index 000000000..b9c1a4f27 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/layercontents.plist @@ -0,0 +1,10 @@ + + + + + + public.default + glyphs + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/lib.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/lib.plist new file mode 100644 index 000000000..6c2dcff1e --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/lib.plist @@ -0,0 +1,67 @@ + + + + + com.schriftgestaltung.appVersion + 1352 + com.schriftgestaltung.customParameter.GSFont.Axes + + + Name + Weight + Tag + wght + + + Name + Width + Tag + wdth + + + com.schriftgestaltung.customParameter.GSFont.DisplayStrings + + + 0 + + + + com.schriftgestaltung.customParameter.GSFont.disablesAutomaticAlignment + + com.schriftgestaltung.customParameter.GSFont.useNiceNames + 1 + com.schriftgestaltung.customParameter.GSFontMaster.customValue + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue1 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue2 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue3 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.iconName + + com.schriftgestaltung.customParameter.GSFontMaster.weightValue + 700 + com.schriftgestaltung.customParameter.GSFontMaster.widthValue + 100 + com.schriftgestaltung.fontMasterID + 48798C20-C9A0-4BB9-9A3E-BDB30805D9C9 + com.schriftgestaltung.fontMasterOrder + 1 + com.schriftgestaltung.keyboardIncrement + 1 + com.schriftgestaltung.weight + Bold + com.schriftgestaltung.weightValue + 700 + com.schriftgestaltung.width + Regular + com.schriftgestaltung.widthValue + 100 + public.glyphOrder + + zero + space + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/metainfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/metainfo.plist new file mode 100644 index 000000000..7b8b34ac6 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Bold.ufo/metainfo.plist @@ -0,0 +1,10 @@ + + + + + creator + com.github.fonttools.ufoLib + formatVersion + 3 + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/fontinfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/fontinfo.plist new file mode 100644 index 000000000..9bf5a01d5 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/fontinfo.plist @@ -0,0 +1,36 @@ + + + + + ascender + 800 + capHeight + 700 + descender + -200 + familyName + BracketSelfReference + italicAngle + 0 + openTypeHeadCreated + 2019/07/25 10:20:06 + openTypeOS2Type + + 3 + + postscriptUnderlinePosition + -100 + postscriptUnderlineThickness + 50 + styleName + Regular + unitsPerEm + 1000 + versionMajor + 1 + versionMinor + 0 + xHeight + 500 + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/contents.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/contents.plist new file mode 100644 index 000000000..d0681736d --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/contents.plist @@ -0,0 +1,12 @@ + + + + + space + space.glif + zero + zero.glif + zero.BRACKET.500 + zero.B_R_A_C_K_E_T_.500.glif + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/layerinfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/layerinfo.plist new file mode 100644 index 000000000..695afa81d --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/layerinfo.plist @@ -0,0 +1,15 @@ + + + + + lib + + com.schriftgestaltung.layerId + AC80BBED-896D-4DAA-A852-C79F9201ACE8 + com.schriftgestaltung.layerOrderInGlyph.space + 0 + com.schriftgestaltung.layerOrderInGlyph.zero + 1 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/space.glif b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/space.glif new file mode 100644 index 000000000..56fe0bf3d --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/space.glif @@ -0,0 +1,13 @@ + + + + + + + + + com.schriftgestaltung.Glyphs.lastChange + 2019/07/25 10:21:14 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif new file mode 100644 index 000000000..32284cc54 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.B_R_A_C_K_E_T_.500.glif @@ -0,0 +1,15 @@ + + + + + + + + + com.schriftgestaltung.Glyphs._originalLayerName + Regular [500] + com.schriftgestaltung.Glyphs.lastChange + 2021/03/31 15:27:05 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.glif b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.glif new file mode 100644 index 000000000..240669d67 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/glyphs/zero.glif @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + + com.schriftgestaltung.Glyphs.lastChange + 2021/03/31 15:27:05 + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/layercontents.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/layercontents.plist new file mode 100644 index 000000000..b9c1a4f27 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/layercontents.plist @@ -0,0 +1,10 @@ + + + + + + public.default + glyphs + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/lib.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/lib.plist new file mode 100644 index 000000000..a11506a4a --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/lib.plist @@ -0,0 +1,67 @@ + + + + + com.schriftgestaltung.appVersion + 1352 + com.schriftgestaltung.customParameter.GSFont.Axes + + + Name + Weight + Tag + wght + + + Name + Width + Tag + wdth + + + com.schriftgestaltung.customParameter.GSFont.DisplayStrings + + + 0 + + + + com.schriftgestaltung.customParameter.GSFont.disablesAutomaticAlignment + + com.schriftgestaltung.customParameter.GSFont.useNiceNames + 1 + com.schriftgestaltung.customParameter.GSFontMaster.customValue + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue1 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue2 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.customValue3 + 0 + com.schriftgestaltung.customParameter.GSFontMaster.iconName + + com.schriftgestaltung.customParameter.GSFontMaster.weightValue + 400 + com.schriftgestaltung.customParameter.GSFontMaster.widthValue + 100 + com.schriftgestaltung.fontMasterID + AC80BBED-896D-4DAA-A852-C79F9201ACE8 + com.schriftgestaltung.fontMasterOrder + 0 + com.schriftgestaltung.keyboardIncrement + 1 + com.schriftgestaltung.weight + Regular + com.schriftgestaltung.weightValue + 400 + com.schriftgestaltung.width + Regular + com.schriftgestaltung.widthValue + 100 + public.glyphOrder + + zero + space + + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/metainfo.plist b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/metainfo.plist new file mode 100644 index 000000000..7b8b34ac6 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference-Regular.ufo/metainfo.plist @@ -0,0 +1,10 @@ + + + + + creator + com.github.fonttools.ufoLib + formatVersion + 3 + + diff --git a/tests/data/BracketSelfReference/BracketSelfReference.designspace b/tests/data/BracketSelfReference/BracketSelfReference.designspace new file mode 100644 index 000000000..40839dab0 --- /dev/null +++ b/tests/data/BracketSelfReference/BracketSelfReference.designspace @@ -0,0 +1,132 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + com.schriftgestaltung.export + + com.schriftgestaltung.intanceInterpolations + + AC80BBED-896D-4DAA-A852-C79F9201ACE8 + 1 + + com.schriftgestaltung.manualInterpolation + + com.schriftgestaltung.weight + Regular + com.schriftgestaltung.width + Medium (normal) + + + + + + + + + + + + com.schriftgestaltung.export + + com.schriftgestaltung.intanceInterpolations + + 48798C20-C9A0-4BB9-9A3E-BDB30805D9C9 + 0.66667 + AC80BBED-896D-4DAA-A852-C79F9201ACE8 + 0.33333 + + com.schriftgestaltung.manualInterpolation + + com.schriftgestaltung.weight + SemiBold + com.schriftgestaltung.width + Medium (normal) + + + + + + + + + + + + com.schriftgestaltung.export + + com.schriftgestaltung.intanceInterpolations + + 48798C20-C9A0-4BB9-9A3E-BDB30805D9C9 + 1 + + com.schriftgestaltung.manualInterpolation + + com.schriftgestaltung.weight + Bold + com.schriftgestaltung.width + Medium (normal) + + + + + + + + + + + + com.schriftgestaltung.export + + com.schriftgestaltung.intanceInterpolations + + 48798C20-C9A0-4BB9-9A3E-BDB30805D9C9 + 0.33333 + AC80BBED-896D-4DAA-A852-C79F9201ACE8 + 0.66667 + + com.schriftgestaltung.manualInterpolation + + com.schriftgestaltung.weight + Medium + com.schriftgestaltung.width + Medium (normal) + + + + +