The Birdfont Source Code


All Repositories / birdfont.git / blob – RSS feed

SvgFontFormatWriter.vala in /libbirdfont

This file is a part of the Birdfont project.

Contributing

Send patches or pull requests to johan.mattsson.m@gmail.com.
Clone this repository: git clone https://github.com/johanmattssonm/birdfont.git
Circle boundaries heads/master
1 /* 2 Copyright (C) 2012, 2014 Johan Mattsson 3 4 This library is free software; you can redistribute it and/or modify 5 it under the terms of the GNU Lesser General Public License as 6 published by the Free Software Foundation; either version 3 of the 7 License, or (at your option) any later version. 8 9 This library is distributed in the hope that it will be useful, but 10 WITHOUT ANY WARRANTY; without even the implied warranty of 11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 Lesser General Public License for more details. 13 */ 14 15 namespace BirdFont { 16 17 class SvgFontFormatWriter : GLib.Object { 18 19 DataOutputStream os; 20 21 public SvgFontFormatWriter () { 22 } 23 24 public void open (File file) throws Error { 25 if (file.query_exists ()) { 26 throw new FileError.EXIST ("SvgFontFormatWriter: file exists."); 27 } 28 29 os = new DataOutputStream (file.create(FileCreateFlags.REPLACE_DESTINATION)); 30 } 31 32 public void close () throws Error { 33 os.close (); 34 } 35 36 public void write_font_file (Font font) throws Error { 37 string font_name = font.get_full_name (); 38 39 int units_per_em = 100; 40 41 int ascent = 80; 42 int descent = -20; 43 44 StringBuilder b; 45 46 Glyph? g; 47 Glyph glyph; 48 unichar index = 0; 49 50 string uni; 51 52 KerningClasses classes; 53 54 put ("""<?xml version="1.0" standalone="no"?>"""); 55 put ("""<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" >"""); 56 put ("""<svg>"""); 57 58 // (metadata goes here) 59 60 put ("<defs>"); 61 62 string font_id = font_name.replace (" ", "-"); 63 font_id = B.XmlParser.encode (font_id); 64 65 Glyph space = font.get_space ().get_current (); 66 double space_width = space.get_width (); 67 68 put (@"<font id=\"$font_id\" horiz-adv-x=\"$(to_float (space_width))\" >"); 69 put (@"<font-face units-per-em=\"$(to_float (units_per_em))\" ascent=\"$(to_float (ascent))\" descent=\"$(to_float (descent))\" />"); 70 71 put (@"<font-src>"); 72 put (@"\t<font-face-name=\"XmlParser.encode ($font_name)\">"); 73 put (@"</font-src>"); 74 75 // (missing-glyph goes here) 76 77 // regular glyphs 78 while (true) { 79 g = font.get_glyph_index (index++); 80 81 if (g == null) { 82 break; 83 } 84 85 glyph = (!) g; 86 87 b = new StringBuilder (); 88 b.append_unichar (glyph.get_unichar ()); 89 90 if (glyph.get_unichar () >= ' ' && b.str.validate ()) { 91 if (b.str == "\"" || b.str == "&" || b.str == "<" || b.str == ">") { 92 uni = Font.to_hex_code (glyph.get_unichar ()); 93 put (@"<glyph unicode=\"&#x$(uni);\" horiz-adv-x=\"$(to_float (glyph.get_width ()))\" d=\"$(glyph.get_svg_data ())\" />"); 94 } else { 95 put (@"<glyph unicode=\"$(b.str)\" horiz-adv-x=\"$(to_float (glyph.get_width ()))\" d=\"$(glyph.get_svg_data ())\" />"); 96 } 97 } 98 } 99 100 // FIXME: ligatures 101 classes = BirdFont.get_current_font ().get_kerning_classes (); 102 classes.all_pairs ((kerning) => { 103 string l, r; 104 105 foreach (Kerning k in kerning.kerning) { 106 try { 107 if (k.glyph != null) { 108 l = Font.to_hex_code (kerning.character.unichar_code); 109 r = Font.to_hex_code (((!)k.glyph).unichar_code); 110 os.put_string (@"<hkern u1=\"&#x$l;\" u2=\"&#x$r;\" k=\"$(to_float (-k.val))\"/>\n"); 111 } else { 112 warning ("No glyph."); 113 } 114 } catch (GLib.Error e) { 115 warning (e.message); 116 } 117 } 118 }); 119 120 put ("</font>"); 121 put ("</defs>"); 122 put ("</svg>"); 123 } 124 125 string to_float (double d) { 126 string s = @"$d"; 127 if (s.index_of ("e") != -1) { 128 return "0".dup (); 129 } 130 return s.replace (",", "."); 131 } 132 133 /** Write a new line */ 134 private void put (string line) throws Error { 135 os.put_string (line); 136 os.put_string ("\n"); 137 } 138 139 } 140 141 142 } 143