/* Copyright (C) 2012 Johan Mattsson This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. */ using Math; namespace BirdFont { class EotWriter : GLib.Object { string ttf_file_name; string eot_file_name; public EotWriter (string ttf_file, string eot_file) { ttf_file_name = ttf_file; eot_file_name = eot_file; } public void write () throws Error { FontData fd = new FontData (); FontData ttf_data = new FontData (); OpenFontFormatReader input; uint32 ttf_length; File ttf_file; File eot_file; FileInfo file_info; OtfInputStream dis; DataOutputStream os; uint8* data; uint32 l; NameTable names; string tn; ttf_file = File.new_for_path (ttf_file_name); if (!ttf_file.query_exists ()) { warning (@"EotWriter: file does not exist. $((!) ttf_file.get_path ())"); return; } eot_file = File.new_for_path (eot_file_name); if (eot_file.query_exists ()) { warning ("EOT file exists in eot export."); eot_file.delete (); } os = new DataOutputStream(eot_file.create (FileCreateFlags.REPLACE_DESTINATION)); file_info = ttf_file.query_info ("*", FileQueryInfoFlags.NONE); ttf_length = (uint32) file_info.get_size (); if (ttf_length == 0) { warning ("TTF file is of zero length."); return; } dis = new OtfInputStream (ttf_file.read ()); ttf_data.write_table (dis, 0, ttf_length); // parse file to find head checksum input = new OpenFontFormatReader (); input.parse_index (ttf_file_name); names = input.directory_table.name_table; fd.add_littleendian_u32 (0); // table length fd.add_littleendian_u32 (ttf_length); fd.add_littleendian_u32 (0x00020001); // table format version fd.add_littleendian_u32 (0); // flags // panose for (int i = 0; i < 10; i++) { fd.add (0); } // according to specification should charset and italic be added the // other way around, but it does not work fd.add (1); // default charset fd.add (0); // italic set to regular fd.add_littleendian_u32 (400); // weight fd.add_littleendian_u16 (0); // 0 drm, designer must be notified fd.add_littleendian_u16 (0x504C); // magic number // FIXME: // unicode ranges fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); // FIXME: // code page range fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (input.get_head_checksum ()); // head checksum adjustment // reserved fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u32 (0); fd.add_littleendian_u16 (0); // padding tn = names.get_name (NameTable.FONT_NAME); fd.add_littleendian_u16 ((uint16) (2 * tn.char_count ())); // strlen of family name fd.add_str_littleendian_utf16 (tn); fd.add_littleendian_u16 (0); // padding tn = names.get_name (NameTable.SUBFAMILY_NAME); fd.add_littleendian_u16 ((uint16) (2 * tn.char_count ())); // strlen of family name fd.add_str_littleendian_utf16 (tn); fd.add_littleendian_u16 (0); // padding // FIXA version or name + version tn = names.get_name (NameTable.VERSION); fd.add_littleendian_u16 ((uint16) (2 * tn.char_count ())); // strlen of family name fd.add_str_littleendian_utf16 (tn); fd.add_littleendian_u16 (0); // padding tn = names.get_name (NameTable.FULL_FONT_NAME); fd.add_littleendian_u16 ((uint16) (2 * tn.char_count ())); // strlen of family name fd.add_str_littleendian_utf16 (tn); fd.add_littleendian_u16 (0); // padding fd.add_littleendian_u16 (0); // length of root string // the root string goes here. // update length of this table fd.seek (0); fd.add_littleendian_u32 (fd.length () + ttf_length); l = fd.length_with_padding (); data = fd.table_data; for (int i = 0; i < l; i++) { os.put_byte (data[i]); } l = ttf_data.length_with_padding (); data = ttf_data.table_data; for (int i = 0; i < l; i++) { os.put_byte (data[i]); } dis.close (); os.close (); input.close (); } } }