def test_insert_comment_outside_block(self, testufo): writer = MarkFeatureWriter() testufo.features.text = dedent("""\ # # Automatic Code # """) feaFile = parseLayoutFeatures(testufo) assert writer.write(testufo, feaFile) testufo.features.text = dedent("""\ # # Automatic Code # markClass acutecomb <anchor 100 200> @MC_top; feature mark { lookup mark1 { pos base a <anchor 100 200> mark @MC_top; } mark1; } mark; """) feaFile = parseLayoutFeatures(testufo) assert writer.write(testufo, feaFile) # test append mode writer = MarkFeatureWriter(mode="append") assert writer.write(testufo, feaFile)
def test_insert_comment_middle(self, testufo): writer = MarkFeatureWriter() testufo.features.text = dedent("""\ markClass acutecomb <anchor 100 200> @MC_top; feature mark { lookup mark1 { pos base a <anchor 100 200> mark @MC_top; } mark1; # # Automatic Code # lookup mark2 { pos base a <anchor 150 250> mark @MC_top; } mark2; } mark; """) feaFile = parseLayoutFeatures(testufo) with pytest.raises( InvalidFeaturesData, match="Insert marker has rules before and after, feature mark " "cannot be inserted.", ): writer.write(testufo, feaFile) # test append mode ignores insert marker generated = self.writeFeatures(testufo, mode="append") assert str(generated) == dedent("""\ markClass tildecomb <anchor 100 200> @MC_top; feature mark { lookup mark2base { pos base a <anchor 100 200> mark @MC_top; } mark2base; lookup mark2liga { pos ligature f_i <anchor 100 500> mark @MC_top ligComponent <anchor 600 500> mark @MC_top; } mark2liga; } mark; feature mkmk { lookup mark2mark_top { @MFS_mark2mark_top = [acutecomb tildecomb]; lookupflag UseMarkFilteringSet @MFS_mark2mark_top; pos mark tildecomb <anchor 100 300> mark @MC_top; } mark2mark_top; } mkmk; """)
def test_write_only_one(self, testufo): writer = MarkFeatureWriter(features=["mkmk"]) # only builds "mkmk" feaFile = ast.FeatureFile() assert writer.write(testufo, feaFile) fea = str(feaFile) assert "feature mark" not in fea assert "feature mkmk" in fea writer = MarkFeatureWriter(features=["mark"]) # only builds "mark" feaFile = ast.FeatureFile() assert writer.write(testufo, feaFile) fea = str(feaFile) assert "feature mark" in fea assert "feature mkmk" not in fea
def test_mark_mkmk_features(self, testufo): writer = MarkFeatureWriter() # by default both mark + mkmk are built feaFile = ast.FeatureFile() assert writer.write(testufo, feaFile) assert str(feaFile) == dedent("""\ markClass acutecomb <anchor 100 200> @MC_top; markClass tildecomb <anchor 100 200> @MC_top; feature mark { lookup mark2base { pos base a <anchor 100 200> mark @MC_top; } mark2base; lookup mark2liga { pos ligature f_i <anchor 100 500> mark @MC_top ligComponent <anchor 600 500> mark @MC_top; } mark2liga; } mark; feature mkmk { lookup mark2mark_top { @MFS_mark2mark_top = [acutecomb tildecomb]; lookupflag UseMarkFilteringSet @MFS_mark2mark_top; pos mark tildecomb <anchor 100 300> mark @MC_top; } mark2mark_top; } mkmk; """)
def test_defs_and_lookups_first(self, testufo): testufo.newGlyph("circumflexcomb") writer = MarkFeatureWriter() testufo.features.text = dedent("""\ feature mkmk { # Automatic Code # Move acutecomb down and right if preceded by circumflexcomb lookup move_acutecomb { lookupflag UseMarkFilteringSet [acutecomb circumflexcomb]; pos circumflexcomb acutecomb' <0 20 0 20>; } move_acutecomb; } mkmk; """) feaFile = parseLayoutFeatures(testufo) assert writer.write(testufo, feaFile) assert str(feaFile) == dedent("""\ markClass acutecomb <anchor 100 200> @MC_top; markClass tildecomb <anchor 100 200> @MC_top; feature mark { lookup mark2base { pos base a <anchor 100 200> mark @MC_top; } mark2base; lookup mark2liga { pos ligature f_i <anchor 100 500> mark @MC_top ligComponent <anchor 600 500> mark @MC_top; } mark2liga; } mark; feature mkmk { lookup mark2mark_top { @MFS_mark2mark_top = [acutecomb tildecomb]; lookupflag UseMarkFilteringSet @MFS_mark2mark_top; pos mark tildecomb <anchor 100 300> mark @MC_top; } mark2mark_top; } mkmk; feature mkmk { # Move acutecomb down and right if preceded by circumflexcomb lookup move_acutecomb { lookupflag UseMarkFilteringSet [acutecomb circumflexcomb]; pos circumflexcomb acutecomb' <0 20 0 20>; } move_acutecomb; } mkmk; """)
out_path = sys.argv[2] if len(sys.argv) == 4: stylename = sys.argv[3] else: # e.g. "Bold" in "sources/masters/Rasa-Bold.ufo" stylename = re.search(r"Rasa\-([A-z]+)", out_path).group(1) features = "" # Generate markClass statements and prepend them font = Font(out_path) markClassDefinitions = [] feaFile = FeatureFile() # A holder for the generated mark features markWriter = MarkFeatureWriter() markWriter.write(font, feaFile) markFeatures = feaFile.asFea() # Get the generated mark features reMarkClass = re.compile(r"markClass.*;") markClassDefinitions = reMarkClass.findall( markFeatures) # Save all the markClass definitions # Read the input feature file with open(in_path, "r") as input_fea: # Replace $markClasses with the generated markClassDefinitions if markClassDefinitions != []: features = input_fea.read().replace( "$markClasses", "\n".join(markClassDefinitions)) else: features = input_fea.read().replace("$markClasses", "")
def test_insert_comment_after(self, testufo): writer = MarkFeatureWriter() testufo.features.text = dedent("""\ markClass acutecomb <anchor 100 200> @MC_top; feature mark { lookup mark1 { pos base a <anchor 100 200> mark @MC_top; } mark1; # # Automatic Code # } mark; """) feaFile = parseLayoutFeatures(testufo) assert writer.write(testufo, feaFile) assert str(feaFile) == dedent("""\ markClass acutecomb <anchor 100 200> @MC_top; feature mark { lookup mark1 { pos base a <anchor 100 200> mark @MC_top; } mark1; # # } mark; markClass tildecomb <anchor 100 200> @MC_top; feature mark { lookup mark2base { pos base a <anchor 100 200> mark @MC_top; } mark2base; lookup mark2liga { pos ligature f_i <anchor 100 500> mark @MC_top ligComponent <anchor 600 500> mark @MC_top; } mark2liga; } mark; feature mkmk { lookup mark2mark_top { @MFS_mark2mark_top = [acutecomb tildecomb]; lookupflag UseMarkFilteringSet @MFS_mark2mark_top; pos mark tildecomb <anchor 100 300> mark @MC_top; } mark2mark_top; } mkmk; """) # test append mode ignores insert marker generated = self.writeFeatures(testufo, mode="append") assert str(generated) == dedent("""\ markClass tildecomb <anchor 100 200> @MC_top; feature mark { lookup mark2base { pos base a <anchor 100 200> mark @MC_top; } mark2base; lookup mark2liga { pos ligature f_i <anchor 100 500> mark @MC_top ligComponent <anchor 600 500> mark @MC_top; } mark2liga; } mark; feature mkmk { lookup mark2mark_top { @MFS_mark2mark_top = [acutecomb tildecomb]; lookupflag UseMarkFilteringSet @MFS_mark2mark_top; pos mark tildecomb <anchor 100 300> mark @MC_top; } mark2mark_top; } mkmk; """)