ttfunk 1.4.0 → 1.5.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +0 -0
- data/CHANGELOG.md +114 -0
- data/{README.rdoc → README.md} +12 -8
- data/lib/ttfunk.rb +27 -21
- data/lib/ttfunk/collection.rb +41 -0
- data/lib/ttfunk/directory.rb +10 -4
- data/lib/ttfunk/encoding/mac_roman.rb +50 -40
- data/lib/ttfunk/encoding/windows_1252.rb +28 -22
- data/lib/ttfunk/reader.rb +11 -10
- data/lib/ttfunk/resource_file.rb +28 -21
- data/lib/ttfunk/subset.rb +5 -5
- data/lib/ttfunk/subset/base.rb +66 -38
- data/lib/ttfunk/subset/mac_roman.rb +11 -10
- data/lib/ttfunk/subset/unicode.rb +10 -8
- data/lib/ttfunk/subset/unicode_8bit.rb +16 -16
- data/lib/ttfunk/subset/windows_1252.rb +16 -15
- data/lib/ttfunk/subset_collection.rb +7 -8
- data/lib/ttfunk/table.rb +3 -5
- data/lib/ttfunk/table/cmap.rb +13 -13
- data/lib/ttfunk/table/cmap/format00.rb +8 -10
- data/lib/ttfunk/table/cmap/format04.rb +37 -32
- data/lib/ttfunk/table/cmap/format06.rb +16 -16
- data/lib/ttfunk/table/cmap/format10.rb +22 -17
- data/lib/ttfunk/table/cmap/format12.rb +28 -22
- data/lib/ttfunk/table/cmap/subtable.rb +30 -23
- data/lib/ttfunk/table/glyf.rb +13 -11
- data/lib/ttfunk/table/glyf/compound.rb +13 -10
- data/lib/ttfunk/table/glyf/simple.rb +5 -4
- data/lib/ttfunk/table/head.rb +13 -13
- data/lib/ttfunk/table/hhea.rb +13 -13
- data/lib/ttfunk/table/hmtx.rb +23 -18
- data/lib/ttfunk/table/kern.rb +57 -48
- data/lib/ttfunk/table/kern/format0.rb +18 -10
- data/lib/ttfunk/table/loca.rb +9 -9
- data/lib/ttfunk/table/maxp.rb +9 -9
- data/lib/ttfunk/table/name.rb +65 -56
- data/lib/ttfunk/table/os2.rb +21 -21
- data/lib/ttfunk/table/post.rb +32 -32
- data/lib/ttfunk/table/post/format10.rb +33 -27
- data/lib/ttfunk/table/post/format20.rb +10 -10
- data/lib/ttfunk/table/post/format30.rb +5 -5
- data/lib/ttfunk/table/post/format40.rb +3 -3
- data/lib/ttfunk/table/sbix.rb +19 -10
- metadata +55 -32
- metadata.gz.sig +0 -0
- data/CHANGELOG +0 -5
- data/data/fonts/DejaVuSans.ttf +0 -0
- data/examples/metrics.rb +0 -45
@@ -1,24 +1,28 @@
|
|
1
1
|
module TTFunk
|
2
2
|
module Encoding
|
3
3
|
class Windows1252
|
4
|
-
#
|
5
|
-
TO_UNICODE = Hash[*(0..255).zip((0..255).to_a).flatten]
|
6
|
-
TO_UNICODE.update(
|
7
|
-
0x80 => 0x20AC, 0x82 => 0x201A, 0x83 => 0x0192, 0x84 => 0x201E, 0x85 => 0x2026,
|
8
|
-
0x86 => 0x2020, 0x87 => 0x2021, 0x88 => 0x02C6, 0x89 => 0x2030, 0x8A => 0x0160,
|
9
|
-
0x8B => 0x2039, 0x8C => 0x0152, 0x8E => 0x017D, 0x91 => 0x2018, 0x92 => 0x2019,
|
10
|
-
0x93 => 0x201C, 0x94 => 0x201D, 0x95 => 0x2022, 0x96 => 0x2013, 0x97 => 0x2014,
|
11
|
-
0x98 => 0x02DC, 0x99 => 0x2122, 0x9A => 0x0161, 0x9B => 0x203A, 0x9C => 0x0152,
|
12
|
-
0x9E => 0x017E, 0x9F => 0x0178
|
13
|
-
)
|
4
|
+
# rubocop: disable Style/ExtraSpacing
|
14
5
|
|
15
|
-
|
16
|
-
|
6
|
+
TO_UNICODE =
|
7
|
+
Hash[*(0..255).zip((0..255)).flatten]
|
8
|
+
.update(
|
9
|
+
0x80 => 0x20AC, 0x82 => 0x201A, 0x83 => 0x0192, 0x84 => 0x201E,
|
10
|
+
0x85 => 0x2026, 0x86 => 0x2020, 0x87 => 0x2021, 0x88 => 0x02C6,
|
11
|
+
0x89 => 0x2030, 0x8A => 0x0160, 0x8B => 0x2039, 0x8C => 0x0152,
|
12
|
+
0x8E => 0x017D, 0x91 => 0x2018, 0x92 => 0x2019, 0x93 => 0x201C,
|
13
|
+
0x94 => 0x201D, 0x95 => 0x2022, 0x96 => 0x2013, 0x97 => 0x2014,
|
14
|
+
0x98 => 0x02DC, 0x99 => 0x2122, 0x9A => 0x0161, 0x9B => 0x203A,
|
15
|
+
0x9C => 0x0152, 0x9E => 0x017E, 0x9F => 0x0178
|
16
|
+
).freeze
|
17
17
|
|
18
|
-
|
19
|
-
|
20
|
-
#
|
21
|
-
#
|
18
|
+
FROM_UNICODE = TO_UNICODE.invert.freeze
|
19
|
+
|
20
|
+
# Maps Windows-1252 codes to their corresponding index in the Postscript
|
21
|
+
# glyph table (see TTFunk::Table::Post::Format10). If any entry in this
|
22
|
+
# array is a string, it is a postscript glyph that is not in the standard
|
23
|
+
# list, and which should be emitted specially in the TTF postscript table
|
24
|
+
# ('post', see format 2).
|
25
|
+
# rubocop: disable Metrics/LineLength,Style/AlignArray,Style/IndentArray
|
22
26
|
POSTSCRIPT_GLYPH_MAPPING = [
|
23
27
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
24
28
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
@@ -28,7 +32,7 @@ module TTFunk
|
|
28
32
|
51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66,
|
29
33
|
67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82,
|
30
34
|
83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 0,
|
31
|
-
|
35
|
+
'Euro', 0, 196, 166, 197, 171, 130, 194, 216, 198, 228, 190, 176, 0, 230, 0,
|
32
36
|
0, 182, 183, 180, 181, 135, 178, 179, 217, 140, 229, 191, 177, 0, 231, 186,
|
33
37
|
3, 163, 132, 133, 189, 150, 232, 134, 142, 139, 157, 169, 164, 16, 138, 218,
|
34
38
|
131, 147, 242, 243, 141, 151, 136, 195, 222, 241, 158, 170, 245, 244, 246, 162,
|
@@ -36,26 +40,28 @@ module TTFunk
|
|
36
40
|
233, 102, 211, 208, 209, 175, 103, 240, 145, 214, 212, 213, 104, 235, 237, 137,
|
37
41
|
106, 105, 107, 109, 108, 110, 160, 111, 113, 112, 114, 115, 117, 116, 118, 119,
|
38
42
|
234, 120, 122, 121, 123, 125, 124, 184, 161, 127, 126, 128, 129, 236, 238, 186
|
39
|
-
]
|
43
|
+
].freeze
|
44
|
+
|
45
|
+
# rubocop: enable Style/AlignArray,Metrics/LineLength,Style/ExtraSpacing,Style/IndentArray
|
40
46
|
|
41
47
|
def self.covers?(character)
|
42
48
|
!FROM_UNICODE[character].nil?
|
43
49
|
end
|
44
50
|
|
45
51
|
def self.to_utf8(string)
|
46
|
-
to_unicode_codepoints(string.unpack(
|
52
|
+
to_unicode_codepoints(string.unpack('C*')).pack('U*')
|
47
53
|
end
|
48
54
|
|
49
55
|
def self.to_unicode(string)
|
50
|
-
to_unicode_codepoints(string.unpack(
|
56
|
+
to_unicode_codepoints(string.unpack('C*')).pack('n*')
|
51
57
|
end
|
52
58
|
|
53
59
|
def self.from_utf8(string)
|
54
|
-
from_unicode_codepoints(string.unpack(
|
60
|
+
from_unicode_codepoints(string.unpack('U*')).pack('C*')
|
55
61
|
end
|
56
62
|
|
57
63
|
def self.from_unicode(string)
|
58
|
-
from_unicode_codepoints(string.unpack(
|
64
|
+
from_unicode_codepoints(string.unpack('n*')).pack('C*')
|
59
65
|
end
|
60
66
|
|
61
67
|
def self.to_unicode_codepoints(array)
|
data/lib/ttfunk/reader.rb
CHANGED
@@ -11,31 +11,32 @@ module TTFunk
|
|
11
11
|
end
|
12
12
|
|
13
13
|
def read_signed(count)
|
14
|
-
read(count*2,
|
14
|
+
read(count * 2, 'n*').map { |i| to_signed(i) }
|
15
15
|
end
|
16
16
|
|
17
17
|
def to_signed(n)
|
18
|
-
|
18
|
+
n >= 0x8000 ? -((n ^ 0xFFFF) + 1) : n
|
19
19
|
end
|
20
20
|
|
21
21
|
def parse_from(position)
|
22
|
-
saved
|
22
|
+
saved = io.pos
|
23
|
+
io.pos = position
|
23
24
|
result = yield position
|
24
25
|
io.pos = saved
|
25
|
-
|
26
|
+
result
|
26
27
|
end
|
27
28
|
|
28
29
|
# For debugging purposes
|
29
30
|
def hexdump(string)
|
30
|
-
bytes = string.unpack(
|
31
|
+
bytes = string.unpack('C*')
|
31
32
|
bytes.each_with_index do |c, i|
|
32
|
-
|
33
|
-
if (i+1) % 16 == 0
|
33
|
+
printf('%02X', c)
|
34
|
+
if (i + 1) % 16 == 0
|
34
35
|
puts
|
35
|
-
elsif (i+1) % 8 == 0
|
36
|
-
print
|
36
|
+
elsif (i + 1) % 8 == 0
|
37
|
+
print ' '
|
37
38
|
else
|
38
|
-
print
|
39
|
+
print ' '
|
39
40
|
end
|
40
41
|
end
|
41
42
|
puts unless bytes.length % 16 == 0
|
data/lib/ttfunk/resource_file.rb
CHANGED
@@ -3,7 +3,7 @@ module TTFunk
|
|
3
3
|
attr_reader :map
|
4
4
|
|
5
5
|
def self.open(path)
|
6
|
-
::File.open(path,
|
6
|
+
::File.open(path, 'rb') do |io|
|
7
7
|
file = new(io)
|
8
8
|
yield file
|
9
9
|
end
|
@@ -12,33 +12,39 @@ module TTFunk
|
|
12
12
|
def initialize(io)
|
13
13
|
@io = io
|
14
14
|
|
15
|
-
data_offset, map_offset, map_length = @io.read(16).unpack(
|
15
|
+
data_offset, map_offset, map_length = @io.read(16).unpack('NNx4N')
|
16
16
|
|
17
17
|
@map = {}
|
18
|
-
|
19
|
-
|
18
|
+
# skip header copy, next map handle, file reference, and attrs
|
19
|
+
@io.pos = map_offset + 24
|
20
|
+
type_list_offset, name_list_offset = @io.read(4).unpack('n*')
|
20
21
|
|
21
22
|
type_list_offset += map_offset
|
22
23
|
name_list_offset += map_offset
|
23
24
|
|
24
25
|
@io.pos = type_list_offset
|
25
|
-
max_index = @io.read(2).unpack(
|
26
|
+
max_index = @io.read(2).unpack('n').first
|
26
27
|
0.upto(max_index) do
|
27
|
-
type, max_type_index, ref_list_offset = @io.read(8).unpack(
|
28
|
-
@map[type] = { :
|
28
|
+
type, max_type_index, ref_list_offset = @io.read(8).unpack('A4nn')
|
29
|
+
@map[type] = { list: [], named: {} }
|
29
30
|
|
30
31
|
parse_from(type_list_offset + ref_list_offset) do
|
31
32
|
0.upto(max_type_index) do
|
32
|
-
id, name_ofs, attr = @io.read(5).unpack(
|
33
|
+
id, name_ofs, attr = @io.read(5).unpack('nnC')
|
33
34
|
data_ofs = @io.read(3)
|
34
|
-
data_ofs = data_offset + [0, data_ofs].pack(
|
35
|
-
handle = @io.read(4).unpack(
|
35
|
+
data_ofs = data_offset + [0, data_ofs].pack('CA*').unpack('N').first
|
36
|
+
handle = @io.read(4).unpack('N').first
|
36
37
|
|
37
|
-
entry = {
|
38
|
+
entry = {
|
39
|
+
id: id,
|
40
|
+
attributes: attr,
|
41
|
+
offset: data_ofs,
|
42
|
+
handle: handle
|
43
|
+
}
|
38
44
|
|
39
45
|
if name_list_offset + name_ofs < map_offset + map_length
|
40
46
|
parse_from(name_ofs + name_list_offset) do
|
41
|
-
len = @io.read(1).unpack(
|
47
|
+
len = @io.read(1).unpack('C').first
|
42
48
|
entry[:name] = @io.read(len)
|
43
49
|
end
|
44
50
|
end
|
@@ -50,12 +56,12 @@ module TTFunk
|
|
50
56
|
end
|
51
57
|
end
|
52
58
|
|
53
|
-
def [](type, index=0)
|
59
|
+
def [](type, index = 0)
|
54
60
|
if @map[type]
|
55
|
-
collection = index.is_a?(
|
61
|
+
collection = index.is_a?(Integer) ? :list : :named
|
56
62
|
if @map[type][collection][index]
|
57
63
|
parse_from(@map[type][collection][index][:offset]) do
|
58
|
-
length = @io.read(4).unpack(
|
64
|
+
length = @io.read(4).unpack('N').first
|
59
65
|
return @io.read(length)
|
60
66
|
end
|
61
67
|
end
|
@@ -68,11 +74,12 @@ module TTFunk
|
|
68
74
|
|
69
75
|
private
|
70
76
|
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
+
def parse_from(offset)
|
78
|
+
saved = @io.pos
|
79
|
+
@io.pos = offset
|
80
|
+
yield
|
81
|
+
ensure
|
82
|
+
@io.pos = saved
|
83
|
+
end
|
77
84
|
end
|
78
85
|
end
|
data/lib/ttfunk/subset.rb
CHANGED
@@ -7,11 +7,11 @@ module TTFunk
|
|
7
7
|
module Subset
|
8
8
|
def self.for(original, encoding)
|
9
9
|
case encoding.to_sym
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
10
|
+
when :unicode then Unicode.new(original)
|
11
|
+
when :unicode_8bit then Unicode8Bit.new(original)
|
12
|
+
when :mac_roman then MacRoman.new(original)
|
13
|
+
when :windows_1252 then Windows1252.new(original)
|
14
|
+
else raise NotImplementedError, "encoding #{encoding} is not supported"
|
15
15
|
end
|
16
16
|
end
|
17
17
|
end
|
data/lib/ttfunk/subset/base.rb
CHANGED
@@ -27,11 +27,14 @@ module TTFunk
|
|
27
27
|
{}
|
28
28
|
end
|
29
29
|
|
30
|
-
def encode(options={})
|
30
|
+
def encode(options = {})
|
31
31
|
cmap_table = new_cmap_table(options)
|
32
32
|
glyphs = collect_glyphs(original_glyph_ids)
|
33
33
|
|
34
|
-
old2new_glyph = cmap_table[:charmap]
|
34
|
+
old2new_glyph = cmap_table[:charmap]
|
35
|
+
.each_with_object(0 => 0) do |(_, ids), map|
|
36
|
+
map[ids[:old]] = ids[:new]
|
37
|
+
end
|
35
38
|
next_glyph_id = cmap_table[:max_glyph_id]
|
36
39
|
|
37
40
|
glyphs.keys.each do |old_id|
|
@@ -45,29 +48,45 @@ module TTFunk
|
|
45
48
|
|
46
49
|
# "mandatory" tables. Every font should ("should") have these, including
|
47
50
|
# the cmap table (encoded above).
|
48
|
-
glyf_table = TTFunk::Table::Glyf.encode(
|
51
|
+
glyf_table = TTFunk::Table::Glyf.encode(
|
52
|
+
glyphs, new2old_glyph, old2new_glyph
|
53
|
+
)
|
49
54
|
loca_table = TTFunk::Table::Loca.encode(glyf_table[:offsets])
|
50
|
-
hmtx_table = TTFunk::Table::Hmtx.encode(
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
55
|
+
hmtx_table = TTFunk::Table::Hmtx.encode(
|
56
|
+
original.horizontal_metrics, new2old_glyph
|
57
|
+
)
|
58
|
+
hhea_table = TTFunk::Table::Hhea.encode(
|
59
|
+
original.horizontal_header, hmtx_table
|
60
|
+
)
|
61
|
+
maxp_table = TTFunk::Table::Maxp.encode(
|
62
|
+
original.maximum_profile, old2new_glyph
|
63
|
+
)
|
64
|
+
post_table = TTFunk::Table::Post.encode(
|
65
|
+
original.postscript, new2old_glyph
|
66
|
+
)
|
67
|
+
name_table = TTFunk::Table::Name.encode(
|
68
|
+
original.name, glyf_table[:table]
|
69
|
+
)
|
70
|
+
head_table = TTFunk::Table::Head.encode(
|
71
|
+
original.header, loca_table
|
72
|
+
)
|
73
|
+
|
74
|
+
# "optional" tables. Fonts may omit these if they do not need them.
|
75
|
+
# Because they apply globally, we can simply copy them over, without
|
76
|
+
# modification, if they exist.
|
60
77
|
os2_table = original.os2.raw
|
61
|
-
cvt_table = TTFunk::Table::Simple.new(original,
|
62
|
-
fpgm_table = TTFunk::Table::Simple.new(original,
|
63
|
-
prep_table = TTFunk::Table::Simple.new(original,
|
78
|
+
cvt_table = TTFunk::Table::Simple.new(original, 'cvt ').raw
|
79
|
+
fpgm_table = TTFunk::Table::Simple.new(original, 'fpgm').raw
|
80
|
+
prep_table = TTFunk::Table::Simple.new(original, 'prep').raw
|
64
81
|
|
65
82
|
# for PDF's, the kerning info is all included in the PDF as the text is
|
66
83
|
# drawn. Thus, the PDF readers do not actually use the kerning info in
|
67
|
-
# embedded fonts. If the library is used for something else, the
|
68
|
-
# subfont may need a kerning table... in that case, you need
|
84
|
+
# embedded fonts. If the library is used for something else, the
|
85
|
+
# generated subfont may need a kerning table... in that case, you need
|
86
|
+
# to opt into it.
|
69
87
|
if options[:kerning]
|
70
|
-
kern_table =
|
88
|
+
kern_table =
|
89
|
+
TTFunk::Table::Kern.encode(original.kerning, old2new_glyph)
|
71
90
|
end
|
72
91
|
|
73
92
|
tables = { 'cmap' => cmap_table[:table],
|
@@ -85,21 +104,27 @@ module TTFunk
|
|
85
104
|
'fpgm' => fpgm_table,
|
86
105
|
'cvt ' => cvt_table }
|
87
106
|
|
88
|
-
tables.delete_if { |
|
107
|
+
tables.delete_if { |_tag, table| table.nil? }
|
89
108
|
|
90
109
|
search_range = (Math.log(tables.length) / Math.log(2)).to_i * 16
|
91
110
|
entry_selector = (Math.log(search_range) / Math.log(2)).to_i
|
92
111
|
range_shift = tables.length * 16 - search_range
|
93
112
|
|
94
|
-
newfont = [
|
113
|
+
newfont = [
|
114
|
+
original.directory.scaler_type,
|
115
|
+
tables.length,
|
116
|
+
search_range,
|
117
|
+
entry_selector,
|
118
|
+
range_shift
|
119
|
+
].pack('Nn*')
|
95
120
|
|
96
121
|
directory_size = tables.length * 16
|
97
122
|
offset = newfont.length + directory_size
|
98
123
|
|
99
|
-
table_data =
|
124
|
+
table_data = ''
|
100
125
|
head_offset = nil
|
101
126
|
tables.each do |tag, data|
|
102
|
-
newfont << [tag, checksum(data), offset, data.length].pack(
|
127
|
+
newfont << [tag, checksum(data), offset, data.length].pack('A4N*')
|
103
128
|
table_data << data
|
104
129
|
head_offset = offset if tag == 'head'
|
105
130
|
offset += data.length
|
@@ -112,30 +137,33 @@ module TTFunk
|
|
112
137
|
newfont << table_data
|
113
138
|
sum = checksum(newfont)
|
114
139
|
adjustment = 0xB1B0AFBA - sum
|
115
|
-
newfont[head_offset+8,4] = [adjustment].pack(
|
140
|
+
newfont[head_offset + 8, 4] = [adjustment].pack('N')
|
116
141
|
|
117
|
-
|
142
|
+
newfont
|
118
143
|
end
|
119
144
|
|
120
145
|
private
|
121
146
|
|
122
|
-
|
123
|
-
|
124
|
-
|
147
|
+
def unicode_cmap
|
148
|
+
@unicode_cmap ||= @original.cmap.unicode.first
|
149
|
+
end
|
125
150
|
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
151
|
+
def checksum(data)
|
152
|
+
data += "\0" * (4 - data.length % 4) unless data.length % 4 == 0
|
153
|
+
data.unpack('N*').reduce(:+) & 0xFFFF_FFFF
|
154
|
+
end
|
130
155
|
|
131
|
-
|
132
|
-
|
133
|
-
|
156
|
+
def collect_glyphs(glyph_ids)
|
157
|
+
glyphs = glyph_ids.each_with_object({}) do |id, h|
|
158
|
+
h[id] = original.glyph_outlines.for(id)
|
159
|
+
end
|
160
|
+
additional_ids = glyphs.values.select { |g| g && g.compound? }
|
161
|
+
.map(&:glyph_ids).flatten
|
134
162
|
|
135
|
-
|
163
|
+
glyphs.update(collect_glyphs(additional_ids)) if additional_ids.any?
|
136
164
|
|
137
|
-
|
138
|
-
|
165
|
+
glyphs
|
166
|
+
end
|
139
167
|
end
|
140
168
|
end
|
141
169
|
end
|
@@ -34,18 +34,19 @@ module TTFunk
|
|
34
34
|
|
35
35
|
protected
|
36
36
|
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
end
|
42
|
-
|
43
|
-
TTFunk::Table::Cmap.encode(mapping, :mac_roman)
|
37
|
+
def new_cmap_table(_options)
|
38
|
+
mapping = {}
|
39
|
+
@subset.each_with_index do |unicode, roman|
|
40
|
+
mapping[roman] = unicode_cmap[unicode] if roman
|
44
41
|
end
|
45
42
|
|
46
|
-
|
47
|
-
|
48
|
-
|
43
|
+
TTFunk::Table::Cmap.encode(mapping, :mac_roman)
|
44
|
+
end
|
45
|
+
|
46
|
+
def original_glyph_ids
|
47
|
+
([0] + @subset.map { |unicode| unicode && unicode_cmap[unicode] })
|
48
|
+
.compact.uniq.sort
|
49
|
+
end
|
49
50
|
end
|
50
51
|
end
|
51
52
|
end
|
@@ -14,14 +14,14 @@ module TTFunk
|
|
14
14
|
end
|
15
15
|
|
16
16
|
def to_unicode_map
|
17
|
-
@subset.
|
17
|
+
@subset.each_with_object({}) { |code, map| map[code] = code }
|
18
18
|
end
|
19
19
|
|
20
20
|
def use(character)
|
21
21
|
@subset << character
|
22
22
|
end
|
23
23
|
|
24
|
-
def covers?(
|
24
|
+
def covers?(_character)
|
25
25
|
true
|
26
26
|
end
|
27
27
|
|
@@ -35,14 +35,16 @@ module TTFunk
|
|
35
35
|
|
36
36
|
protected
|
37
37
|
|
38
|
-
|
39
|
-
|
40
|
-
|
38
|
+
def new_cmap_table(_options)
|
39
|
+
mapping = @subset.each_with_object({}) do |code, map|
|
40
|
+
map[code] = unicode_cmap[code]
|
41
41
|
end
|
42
|
+
TTFunk::Table::Cmap.encode(mapping, :unicode)
|
43
|
+
end
|
42
44
|
|
43
|
-
|
44
|
-
|
45
|
-
|
45
|
+
def original_glyph_ids
|
46
|
+
([0] + @subset.map { |code| unicode_cmap[code] }).uniq.sort
|
47
|
+
end
|
46
48
|
end
|
47
49
|
end
|
48
50
|
end
|