// Generated by CoffeeScript 1.7.1
(function() {
  var CmapTable, Subset, utils,
    __indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; };

  CmapTable = require('./tables/cmap');

  utils = require('./utils');

  Subset = (function() {
    function Subset(font) {
      this.font = font;
      this.subset = {};
      this.unicodes = {};
      this.next = 33;
    }

    Subset.prototype.use = function(character) {
      var i, _i, _ref;
      if (typeof character === 'string') {
        for (i = _i = 0, _ref = character.length; 0 <= _ref ? _i < _ref : _i > _ref; i = 0 <= _ref ? ++_i : --_i) {
          this.use(character.charCodeAt(i));
        }
        return;
      }
      if (!this.unicodes[character]) {
        this.subset[this.next] = character;
        return this.unicodes[character] = this.next++;
      }
    };

    Subset.prototype.encodeText = function(text) {
      var char, i, string, _i, _ref;
      string = '';
      for (i = _i = 0, _ref = text.length; 0 <= _ref ? _i < _ref : _i > _ref; i = 0 <= _ref ? ++_i : --_i) {
        char = this.unicodes[text.charCodeAt(i)];
        string += String.fromCharCode(char);
      }
      return string;
    };

    Subset.prototype.generateCmap = function() {
      var mapping, roman, unicode, unicodeCmap, _ref;
      unicodeCmap = this.font.cmap.tables[0].codeMap;
      mapping = {};
      _ref = this.subset;
      for (roman in _ref) {
        unicode = _ref[roman];
        mapping[roman] = unicodeCmap[unicode];
      }
      return mapping;
    };

    Subset.prototype.glyphIDs = function() {
      var ret, roman, unicode, unicodeCmap, val, _ref;
      unicodeCmap = this.font.cmap.tables[0].codeMap;
      ret = [0];
      _ref = this.subset;
      for (roman in _ref) {
        unicode = _ref[roman];
        val = unicodeCmap[unicode];
        if ((val != null) && __indexOf.call(ret, val) < 0) {
          ret.push(val);
        }
      }
      return ret.sort();
    };

    Subset.prototype.glyphsFor = function(glyphIDs) {
      var additionalIDs, glyph, glyphs, id, _i, _len, _ref;
      glyphs = {};
      for (_i = 0, _len = glyphIDs.length; _i < _len; _i++) {
        id = glyphIDs[_i];
        glyphs[id] = this.font.glyf.glyphFor(id);
      }
      additionalIDs = [];
      for (id in glyphs) {
        glyph = glyphs[id];
        if (glyph != null ? glyph.compound : void 0) {
          additionalIDs.push.apply(additionalIDs, glyph.glyphIDs);
        }
      }
      if (additionalIDs.length > 0) {
        _ref = this.glyphsFor(additionalIDs);
        for (id in _ref) {
          glyph = _ref[id];
          glyphs[id] = glyph;
        }
      }
      return glyphs;
    };

    Subset.prototype.encode = function() {
      var cmap, code, glyf, glyphs, id, ids, loca, name, new2old, newIDs, nextGlyphID, old2new, oldID, oldIDs, tables, _ref, _ref1;
      cmap = CmapTable.encode(this.generateCmap(), 'unicode');
      glyphs = this.glyphsFor(this.glyphIDs());
      old2new = {
        0: 0
      };
      _ref = cmap.charMap;
      for (code in _ref) {
        ids = _ref[code];
        old2new[ids.old] = ids["new"];
      }
      nextGlyphID = cmap.maxGlyphID;
      for (oldID in glyphs) {
        if (!(oldID in old2new)) {
          old2new[oldID] = nextGlyphID++;
        }
      }
      new2old = utils.invert(old2new);
      newIDs = Object.keys(new2old).sort(function(a, b) {
        return a - b;
      });
      oldIDs = (function() {
        var _i, _len, _results;
        _results = [];
        for (_i = 0, _len = newIDs.length; _i < _len; _i++) {
          id = newIDs[_i];
          _results.push(new2old[id]);
        }
        return _results;
      })();
      glyf = this.font.glyf.encode(glyphs, oldIDs, old2new);
      loca = this.font.loca.encode(glyf.offsets);
      name = this.font.name.encode();
      this.postscriptName = name.postscriptName;
      this.cmap = {};
      _ref1 = cmap.charMap;
      for (code in _ref1) {
        ids = _ref1[code];
        this.cmap[code] = ids.old;
      }
      tables = {
        cmap: cmap.table,
        glyf: glyf.table,
        loca: loca.table,
        hmtx: this.font.hmtx.encode(oldIDs),
        hhea: this.font.hhea.encode(oldIDs),
        maxp: this.font.maxp.encode(oldIDs),
        post: this.font.post.encode(oldIDs),
        name: name.table,
        head: this.font.head.encode(loca)
      };
      if (this.font.os2.exists) {
        tables['OS/2'] = this.font.os2.raw();
      }
      return this.font.directory.encode(tables);
    };

    return Subset;

  })();

  module.exports = Subset;

}).call(this);
