| line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
|
1
|
|
|
|
|
|
|
package Font::GlyphNames; |
|
2
|
|
|
|
|
|
|
|
|
3
|
|
|
|
|
|
|
require 5.008; |
|
4
|
2
|
|
|
2
|
|
89783
|
use strict; |
|
|
2
|
|
|
|
|
5
|
|
|
|
2
|
|
|
|
|
70
|
|
|
5
|
2
|
|
|
2
|
|
12
|
use warnings; |
|
|
2
|
|
|
|
|
3
|
|
|
|
2
|
|
|
|
|
78
|
|
|
6
|
|
|
|
|
|
|
|
|
7
|
2
|
|
|
2
|
|
1790
|
use File::Spec::Functions 'catfile'; |
|
|
2
|
|
|
|
|
2184
|
|
|
|
2
|
|
|
|
|
194
|
|
|
8
|
2
|
|
|
2
|
|
4344
|
use Encode 'decode'; |
|
|
2
|
|
|
|
|
49436
|
|
|
|
2
|
|
|
|
|
676
|
|
|
9
|
|
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
require Exporter; |
|
11
|
|
|
|
|
|
|
|
|
12
|
|
|
|
|
|
|
our($VERSION) = '1.00000'; |
|
13
|
|
|
|
|
|
|
our(@ISA) = 'Exporter'; |
|
14
|
|
|
|
|
|
|
our(@EXPORT_OK) = qw[ |
|
15
|
|
|
|
|
|
|
name2str |
|
16
|
|
|
|
|
|
|
name2ord |
|
17
|
|
|
|
|
|
|
str2name |
|
18
|
|
|
|
|
|
|
ord2name |
|
19
|
|
|
|
|
|
|
ord2ligname |
|
20
|
|
|
|
|
|
|
]; |
|
21
|
|
|
|
|
|
|
our %EXPORT_TAGS = (all => \@EXPORT_OK); |
|
22
|
|
|
|
|
|
|
|
|
23
|
|
|
|
|
|
|
our $_obj; # object used by the function-oriented interface |
|
24
|
|
|
|
|
|
|
our @LISTS = qw[ zapfdingbats.txt |
|
25
|
|
|
|
|
|
|
glyphlist.txt ]; |
|
26
|
|
|
|
|
|
|
our @PATH = split /::/, __PACKAGE__; |
|
27
|
|
|
|
|
|
|
|
|
28
|
2
|
|
|
|
|
11
|
use subs qw[ |
|
29
|
|
|
|
|
|
|
_read_glyphlist |
|
30
|
2
|
|
|
2
|
|
2068
|
]; |
|
|
2
|
|
|
|
|
61
|
|
|
31
|
|
|
|
|
|
|
|
|
32
|
|
|
|
|
|
|
|
|
33
|
|
|
|
|
|
|
=encoding utf-8 |
|
34
|
|
|
|
|
|
|
|
|
35
|
|
|
|
|
|
|
=head1 NAME |
|
36
|
|
|
|
|
|
|
|
|
37
|
|
|
|
|
|
|
Font::GlyphNames - Convert between glyph names and characters |
|
38
|
|
|
|
|
|
|
|
|
39
|
|
|
|
|
|
|
=head1 VERSION |
|
40
|
|
|
|
|
|
|
|
|
41
|
|
|
|
|
|
|
Version 1.00000 |
|
42
|
|
|
|
|
|
|
|
|
43
|
|
|
|
|
|
|
=head1 SYNOPSIS |
|
44
|
|
|
|
|
|
|
|
|
45
|
|
|
|
|
|
|
use Font::GlyphNames qw[ |
|
46
|
|
|
|
|
|
|
name2str |
|
47
|
|
|
|
|
|
|
name2ord |
|
48
|
|
|
|
|
|
|
str2name |
|
49
|
|
|
|
|
|
|
ord2name |
|
50
|
|
|
|
|
|
|
ord2ligname |
|
51
|
|
|
|
|
|
|
]; |
|
52
|
|
|
|
|
|
|
# or: |
|
53
|
|
|
|
|
|
|
use Font::GlyphNames ':all'; |
|
54
|
|
|
|
|
|
|
|
|
55
|
|
|
|
|
|
|
name2str qw[one two three s_t Psi uni00D4]; |
|
56
|
|
|
|
|
|
|
name2ord qw[one two three s_t Psi uni00D4]; |
|
57
|
|
|
|
|
|
|
str2name qw[1 2 3 st Ψ Ô]; |
|
58
|
|
|
|
|
|
|
ord2name qw[49 50 51 115 116 936 212]; |
|
59
|
|
|
|
|
|
|
ord2ligname qw[49 50 51 115 116 936 212]; |
|
60
|
|
|
|
|
|
|
|
|
61
|
|
|
|
|
|
|
# Or you can use the OO interface: |
|
62
|
|
|
|
|
|
|
|
|
63
|
|
|
|
|
|
|
use Font::GlyphNames; |
|
64
|
|
|
|
|
|
|
|
|
65
|
|
|
|
|
|
|
$gn = new Font::GlyphNames; # use default glyph list |
|
66
|
|
|
|
|
|
|
$gn = new Font::GlyphNames 'my-glyphs.txt'; # custom list |
|
67
|
|
|
|
|
|
|
|
|
68
|
|
|
|
|
|
|
$gn->name2ord(qw[ a slong_slong_i s_t.alt ]); |
|
69
|
|
|
|
|
|
|
# etc. |
|
70
|
|
|
|
|
|
|
|
|
71
|
|
|
|
|
|
|
=head1 DESCRIPTION |
|
72
|
|
|
|
|
|
|
|
|
73
|
|
|
|
|
|
|
This module uses the Adobe Glyph Naming convention (see L) for converting |
|
74
|
|
|
|
|
|
|
between glyph names and characters (or character codes). |
|
75
|
|
|
|
|
|
|
|
|
76
|
|
|
|
|
|
|
=head1 METHODS/FUNCTIONS |
|
77
|
|
|
|
|
|
|
|
|
78
|
|
|
|
|
|
|
Except for C (which is only a method), each item listed |
|
79
|
|
|
|
|
|
|
here is |
|
80
|
|
|
|
|
|
|
both a function and a method. |
|
81
|
|
|
|
|
|
|
|
|
82
|
|
|
|
|
|
|
=over 4 |
|
83
|
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
=item new ( LIST ) |
|
85
|
|
|
|
|
|
|
|
|
86
|
|
|
|
|
|
|
This class method constructs and returns a new Font::GlyphNames object. |
|
87
|
|
|
|
|
|
|
If an error occurs, it returns undef (check C<$@> for the error; note |
|
88
|
|
|
|
|
|
|
also that C clobbers any existing value of C<$@>, whether there |
|
89
|
|
|
|
|
|
|
is an error or not). LIST is a |
|
90
|
|
|
|
|
|
|
list of files to use as a glyph list. If LIST is |
|
91
|
|
|
|
|
|
|
omitted, the Zapf Dingbats Glyph List and the Adobe |
|
92
|
|
|
|
|
|
|
Glyph List (see L) will be used instead. |
|
93
|
|
|
|
|
|
|
|
|
94
|
|
|
|
|
|
|
=item new \%options |
|
95
|
|
|
|
|
|
|
|
|
96
|
|
|
|
|
|
|
C can also take a hashref of options, which are as follows: |
|
97
|
|
|
|
|
|
|
|
|
98
|
|
|
|
|
|
|
=over 4 |
|
99
|
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
=item lists |
|
101
|
|
|
|
|
|
|
|
|
102
|
|
|
|
|
|
|
=item list |
|
103
|
|
|
|
|
|
|
|
|
104
|
|
|
|
|
|
|
(You can specify it with or without the 's'.) Either the name of the file |
|
105
|
|
|
|
|
|
|
containing the glyph list, or a reference to an array of file names. In |
|
106
|
|
|
|
|
|
|
fact, if you want an object with no glyph list (not that you would), you |
|
107
|
|
|
|
|
|
|
can use S [] >>>. |
|
108
|
|
|
|
|
|
|
|
|
109
|
|
|
|
|
|
|
=item search_inc |
|
110
|
|
|
|
|
|
|
|
|
111
|
|
|
|
|
|
|
If this is set to true, 'Font/GlyphNames/' will be added to the beginning |
|
112
|
|
|
|
|
|
|
of each file name, and the files will then be searched for in the folders |
|
113
|
|
|
|
|
|
|
listed in C<@INC>. |
|
114
|
|
|
|
|
|
|
|
|
115
|
|
|
|
|
|
|
=item substitute |
|
116
|
|
|
|
|
|
|
|
|
117
|
|
|
|
|
|
|
Set this to a string that you want C to output for each invalid |
|
118
|
|
|
|
|
|
|
glyph name. The default is C. (Actually, it doesn't have to be a |
|
119
|
|
|
|
|
|
|
string; it could be anything, but it will be stringified if C is |
|
120
|
|
|
|
|
|
|
called in scalar context with more than one argument.) |
|
121
|
|
|
|
|
|
|
|
|
122
|
|
|
|
|
|
|
=back |
|
123
|
|
|
|
|
|
|
|
|
124
|
|
|
|
|
|
|
=cut |
|
125
|
|
|
|
|
|
|
|
|
126
|
|
|
|
|
|
|
sub new { |
|
127
|
11
|
100
|
|
11
|
1
|
66
|
my($class, $self, $search_inc) = (@_ ? shift : __PACKAGE__, {}); |
|
128
|
11
|
|
|
|
|
21
|
my(@lists,$found_list); |
|
129
|
11
|
100
|
100
|
|
|
87
|
if(@_ and ref $_[0] eq 'HASH') { |
|
|
|
100
|
|
|
|
|
|
|
130
|
4
|
|
|
|
|
8
|
for (qw 'lists list') { |
|
131
|
8
|
100
|
|
|
|
29
|
next unless exists $_[0]{$_}; |
|
132
|
3
|
|
|
|
|
4
|
++$found_list; |
|
133
|
1
|
|
|
|
|
4
|
push @lists, ref $_[0]{$_} eq 'ARRAY' |
|
134
|
3
|
100
|
|
|
|
17
|
? @{$_[0]{$_}} |
|
135
|
|
|
|
|
|
|
: $_[0]{$_}; |
|
136
|
|
|
|
|
|
|
} |
|
137
|
4
|
100
|
|
|
|
16
|
$search_inc = delete $_[0]{search_inc} if $found_list; |
|
138
|
4
|
|
|
|
|
17
|
$$self{subst} = delete $_[0]{substitute}; |
|
139
|
|
|
|
|
|
|
} |
|
140
|
|
|
|
|
|
|
elsif(@_) { |
|
141
|
1
|
|
|
|
|
2
|
$found_list++; |
|
142
|
1
|
|
|
|
|
4
|
@lists = @_; |
|
143
|
|
|
|
|
|
|
} |
|
144
|
11
|
100
|
|
|
|
34
|
unless($found_list) { |
|
145
|
7
|
|
|
|
|
11
|
@lists = @{$search_inc = 1, \@LISTS}; |
|
|
7
|
|
|
|
|
31
|
|
|
146
|
|
|
|
|
|
|
} |
|
147
|
|
|
|
|
|
|
|
|
148
|
|
|
|
|
|
|
# read the glyph list(s) into $self; |
|
149
|
11
|
|
|
|
|
38
|
$$self{name2ord} = {}; |
|
150
|
11
|
|
|
|
|
27
|
$$self{str2name} = {}; |
|
151
|
11
|
|
|
|
|
27
|
for my $file (@lists) { |
|
152
|
17
|
|
|
|
|
113
|
my(@h,$fh); |
|
153
|
|
|
|
|
|
|
|
|
154
|
17
|
100
|
|
|
|
43
|
if($search_inc) { |
|
155
|
16
|
|
|
|
|
18
|
my $f; |
|
156
|
|
|
|
|
|
|
# I pilfered this code from Unicode::Collate (and |
|
157
|
|
|
|
|
|
|
# modified it slightly). |
|
158
|
16
|
|
|
|
|
39
|
for (@INC) { |
|
159
|
53
|
|
|
|
|
321
|
$f = catfile $_, @PATH, $file; |
|
160
|
53
|
100
|
|
|
|
2194
|
last if open $fh, $f; |
|
161
|
38
|
|
|
|
|
78
|
$f = undef; |
|
162
|
|
|
|
|
|
|
} |
|
163
|
16
|
100
|
|
|
|
68
|
defined $f or |
|
164
|
|
|
|
|
|
|
$@ = __PACKAGE__ . ": Can't locate " . |
|
165
|
|
|
|
|
|
|
catfile(@PATH, $file) . |
|
166
|
|
|
|
|
|
|
" in \@INC (\@INC contains @INC).\n", |
|
167
|
|
|
|
|
|
|
return |
|
168
|
|
|
|
|
|
|
} |
|
169
|
|
|
|
|
|
|
else { |
|
170
|
1
|
50
|
|
|
|
19
|
open $fh, $file |
|
171
|
|
|
|
|
|
|
or $@= "$file could not be opened: $!", |
|
172
|
|
|
|
|
|
|
return |
|
173
|
|
|
|
|
|
|
} |
|
174
|
|
|
|
|
|
|
|
|
175
|
16
|
|
|
|
|
41
|
local *_; |
|
176
|
16
|
|
|
|
|
21
|
my $line; for ($line) { |
|
|
16
|
|
|
|
|
38
|
|
|
177
|
16
|
|
|
|
|
387
|
while (<$fh>) { |
|
178
|
31541
|
100
|
|
|
|
99518
|
next if /^\s*(?:#|\z)/; |
|
179
|
31382
|
|
|
|
|
35871
|
s/^\cj//; # for Mac Classic compatibility |
|
180
|
31382
|
50
|
|
|
|
150539
|
/^([^;]+);\s*([0-9a-f][0-9a-f\s]+)\z/i |
|
181
|
|
|
|
|
|
|
or $@ = "Invalid glyph list line in $file: $_", |
|
182
|
|
|
|
|
|
|
return; |
|
183
|
31382
|
|
|
|
|
212407
|
my($name,$codes) = ($1,[map hex, split ' ', $2]); |
|
184
|
31382
|
50
|
|
|
|
177923
|
exists $$self{name2ord}{$name} or |
|
185
|
|
|
|
|
|
|
$$self{name2ord}{$name} = $codes; |
|
186
|
31382
|
100
|
|
|
|
52973
|
if(@$codes == 1) { |
|
187
|
30813
|
|
|
|
|
58610
|
my $key = chr $$codes[0]; |
|
188
|
30813
|
100
|
|
|
|
220630
|
exists $$self{str2name}{$key} or |
|
189
|
|
|
|
|
|
|
$$self{str2name}{$key} = $name; |
|
190
|
|
|
|
|
|
|
} else { |
|
191
|
569
|
|
|
|
|
2042
|
my $key = join '', map chr, @$codes; |
|
192
|
569
|
100
|
|
|
|
3604
|
exists $$self{str2name}{$key} |
|
193
|
|
|
|
|
|
|
or $$self{str2name}{$key} = $name |
|
194
|
|
|
|
|
|
|
} |
|
195
|
|
|
|
|
|
|
}} |
|
196
|
|
|
|
|
|
|
} |
|
197
|
10
|
|
|
|
|
28
|
$ @= ''; |
|
198
|
|
|
|
|
|
|
|
|
199
|
10
|
|
|
|
|
134
|
bless $self, $class; |
|
200
|
|
|
|
|
|
|
} |
|
201
|
|
|
|
|
|
|
|
|
202
|
|
|
|
|
|
|
=item name2str ( LIST ) |
|
203
|
|
|
|
|
|
|
|
|
204
|
|
|
|
|
|
|
LIST is a list of glyph names. This function returns a list of the |
|
205
|
|
|
|
|
|
|
string equivalents of the glyphs in list context. In scalar context the |
|
206
|
|
|
|
|
|
|
individual elements of the list are concatenated. Invalid glyph |
|
207
|
|
|
|
|
|
|
names and names beginning with a dot (chr 0x2E) produce undef. Some |
|
208
|
|
|
|
|
|
|
examples: |
|
209
|
|
|
|
|
|
|
|
|
210
|
|
|
|
|
|
|
name2str 's_t' # returns 'st' |
|
211
|
|
|
|
|
|
|
name2str qw/Psi uni00D4/ # returns ("\x{3a8}", "\xd4") |
|
212
|
|
|
|
|
|
|
name2str '.notdef' # returns undef |
|
213
|
|
|
|
|
|
|
name2str 'uni12345678' # returns "\x{1234}\x{5678}" |
|
214
|
|
|
|
|
|
|
name2str qw/one uni32 three/ # returns ('1', undef, '3') |
|
215
|
|
|
|
|
|
|
|
|
216
|
|
|
|
|
|
|
If, for invalid glyph names, you would like something other than undef |
|
217
|
|
|
|
|
|
|
(the null char, for instance), you can either use the OO interface and the |
|
218
|
|
|
|
|
|
|
C option to L, or replace it afterwards like this: |
|
219
|
|
|
|
|
|
|
|
|
220
|
|
|
|
|
|
|
map +("\0",$_)[defined], name2str ... |
|
221
|
|
|
|
|
|
|
|
|
222
|
|
|
|
|
|
|
=cut |
|
223
|
|
|
|
|
|
|
|
|
224
|
|
|
|
|
|
|
sub name2str { |
|
225
|
72
|
|
|
72
|
1
|
19616
|
my $self = &_get_self; |
|
226
|
72
|
|
|
|
|
202
|
my(@names,@ret,$str) = @_; |
|
227
|
72
|
|
|
|
|
150
|
for(@names) { |
|
228
|
141
|
|
|
|
|
287
|
s/\..*//s; |
|
229
|
141
|
|
|
|
|
169
|
$str = undef; |
|
230
|
141
|
|
|
|
|
680
|
for (split /_/) { |
|
231
|
|
|
|
|
|
|
# Here we check each type of glyph name |
|
232
|
154
|
100
|
|
|
|
6116
|
if (exists $$self{name2ord}{$_}) { |
|
|
|
100
|
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
233
|
32
|
|
|
|
|
193
|
$str .= join '', map chr, |
|
234
|
32
|
|
|
|
|
38
|
@{$$self{name2ord}{$_}}; |
|
235
|
|
|
|
|
|
|
} |
|
236
|
|
|
|
|
|
|
elsif (/^uni( |
|
237
|
|
|
|
|
|
|
(?: #non-surrogate codepoints: |
|
238
|
|
|
|
|
|
|
[0-9A-CEF][0-9A-F]{3} |
|
239
|
|
|
|
|
|
|
| |
|
240
|
|
|
|
|
|
|
D[0-7][0-9A-F]{2} |
|
241
|
|
|
|
|
|
|
)+ |
|
242
|
|
|
|
|
|
|
)\z/x) { |
|
243
|
39
|
|
|
|
|
238
|
$str .= decode 'UTF-16BE', pack 'H*', $1; |
|
244
|
|
|
|
|
|
|
} |
|
245
|
|
|
|
|
|
|
elsif (/^u( |
|
246
|
|
|
|
|
|
|
0{0,2}[0-9A-CEF][0-9A-F]{3} |
|
247
|
|
|
|
|
|
|
| |
|
248
|
|
|
|
|
|
|
0{0,2}D[0-7][0-9A-F]{2} |
|
249
|
|
|
|
|
|
|
| |
|
250
|
|
|
|
|
|
|
(?:0?(?!0)|1(?=0))[0-9A-F]{5} |
|
251
|
|
|
|
|
|
|
)\z/x) { |
|
252
|
39
|
|
|
|
|
214
|
$str .= chr hex $1; |
|
253
|
|
|
|
|
|
|
} |
|
254
|
|
|
|
|
|
|
else { |
|
255
|
2
|
|
|
2
|
|
2244
|
no warnings 'uninitialized'; |
|
|
2
|
|
|
|
|
4
|
|
|
|
2
|
|
|
|
|
213
|
|
|
256
|
44
|
50
|
|
|
|
154
|
defined $str ? $str .= $$self{subst} : |
|
257
|
|
|
|
|
|
|
($str = $$self{subst}); |
|
258
|
|
|
|
|
|
|
} |
|
259
|
|
|
|
|
|
|
} |
|
260
|
141
|
100
|
|
|
|
1054
|
push @ret, defined $str ? $str : $$self{subst}; |
|
261
|
|
|
|
|
|
|
} |
|
262
|
2
|
|
|
2
|
|
16
|
no warnings 'uninitialized'; |
|
|
2
|
|
|
|
|
4
|
|
|
|
2
|
|
|
|
|
2617
|
|
|
263
|
72
|
100
|
|
|
|
569
|
wantarray ? @ret : @ret > 1 ? join '', @ret : $ret[-1]; |
|
|
|
100
|
|
|
|
|
|
|
264
|
|
|
|
|
|
|
} |
|
265
|
|
|
|
|
|
|
|
|
266
|
|
|
|
|
|
|
|
|
267
|
|
|
|
|
|
|
=item name2ord ( LIST ) |
|
268
|
|
|
|
|
|
|
|
|
269
|
|
|
|
|
|
|
LIST is a list of glyph names. This function returns a list of the |
|
270
|
|
|
|
|
|
|
character codes that the glyphs represent. If called in scalar context |
|
271
|
|
|
|
|
|
|
with more than one argument, the behaviour is undefined (and subject to |
|
272
|
|
|
|
|
|
|
change in future releases). Invalid glyph |
|
273
|
|
|
|
|
|
|
names and names beginning with a dot (chr 0x2E) produce -1. Some |
|
274
|
|
|
|
|
|
|
examples: |
|
275
|
|
|
|
|
|
|
|
|
276
|
|
|
|
|
|
|
name2ord 's_t' # returns 115, 116 |
|
277
|
|
|
|
|
|
|
name2ord qw/Psi uni00D4/ # returns 0x3a8, 0xd4 |
|
278
|
|
|
|
|
|
|
name2ord '.notdef' # returns -1 |
|
279
|
|
|
|
|
|
|
name2ord 'uni12345678' # returns 0x1234, 0x5678 |
|
280
|
|
|
|
|
|
|
name2ord qw/one uni32 three/ # returns 49, -1, 51 |
|
281
|
|
|
|
|
|
|
|
|
282
|
|
|
|
|
|
|
=cut |
|
283
|
|
|
|
|
|
|
|
|
284
|
|
|
|
|
|
|
sub name2ord { |
|
285
|
24
|
|
|
24
|
1
|
79
|
my $self = &_get_self; |
|
286
|
24
|
|
|
|
|
59
|
my(@names,@ret) = @_; |
|
287
|
24
|
|
|
|
|
80
|
for(@names) { |
|
288
|
42
|
|
|
|
|
87
|
s/\..*//s; |
|
289
|
42
|
100
|
|
|
|
90
|
$_ = ' ' unless $_; # make sure split returns something |
|
290
|
42
|
|
|
|
|
102
|
for (split /_/) { |
|
291
|
|
|
|
|
|
|
# Here we check each type of glyph name |
|
292
|
|
|
|
|
|
|
# It would be nice to avoid duplicating this logic, |
|
293
|
|
|
|
|
|
|
# but I think it runs faster this way. |
|
294
|
50
|
100
|
|
|
|
281
|
if (exists $$self{name2ord}{$_}) { |
|
|
|
100
|
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
295
|
9
|
|
|
|
|
13
|
push @ret, @{$$self{name2ord}{$_}}; |
|
|
9
|
|
|
|
|
34
|
|
|
296
|
|
|
|
|
|
|
} |
|
297
|
|
|
|
|
|
|
elsif (/^uni( |
|
298
|
|
|
|
|
|
|
(?: #non-surrogate codepoints: |
|
299
|
|
|
|
|
|
|
[0-9A-CEF][0-9A-F]{3} |
|
300
|
|
|
|
|
|
|
| |
|
301
|
|
|
|
|
|
|
D[0-7][0-9A-F]{2} |
|
302
|
|
|
|
|
|
|
)+ |
|
303
|
|
|
|
|
|
|
)\z/x) { |
|
304
|
12
|
|
|
|
|
66
|
push @ret, unpack 'n*', pack 'H*', $1; |
|
305
|
|
|
|
|
|
|
} |
|
306
|
|
|
|
|
|
|
elsif (/^u( |
|
307
|
|
|
|
|
|
|
0{0,2}[0-9A-CEF][0-9A-F]{3} |
|
308
|
|
|
|
|
|
|
| |
|
309
|
|
|
|
|
|
|
0{0,2}D[0-7][0-9A-F]{2} |
|
310
|
|
|
|
|
|
|
| |
|
311
|
|
|
|
|
|
|
(?:0?(?!0)|1(?=0))[0-9A-F]{5} |
|
312
|
|
|
|
|
|
|
)\z/x) { |
|
313
|
12
|
|
|
|
|
46
|
push @ret, hex $1; |
|
314
|
|
|
|
|
|
|
} |
|
315
|
|
|
|
|
|
|
else { |
|
316
|
17
|
|
|
|
|
54
|
push @ret, -1; |
|
317
|
|
|
|
|
|
|
} |
|
318
|
|
|
|
|
|
|
} |
|
319
|
|
|
|
|
|
|
} |
|
320
|
24
|
100
|
|
|
|
202
|
@ret == 1 ? $ret[-1] : @ret ; |
|
321
|
|
|
|
|
|
|
} |
|
322
|
|
|
|
|
|
|
|
|
323
|
|
|
|
|
|
|
|
|
324
|
|
|
|
|
|
|
=item str2name ( LIST ) |
|
325
|
|
|
|
|
|
|
|
|
326
|
|
|
|
|
|
|
LIST is a list of strings. This function returns a list of glyph names that |
|
327
|
|
|
|
|
|
|
correspond to all the arguments passed to it. If a string is more than one |
|
328
|
|
|
|
|
|
|
character long, the resulting glyph name will be a ligature name. An empty |
|
329
|
|
|
|
|
|
|
string will return '.notdef'. If called |
|
330
|
|
|
|
|
|
|
in scalar context |
|
331
|
|
|
|
|
|
|
with more than one argument, the behaviour is undefined (and subject to |
|
332
|
|
|
|
|
|
|
change in future releases). |
|
333
|
|
|
|
|
|
|
|
|
334
|
|
|
|
|
|
|
str2name 'st' # returns 's_t' |
|
335
|
|
|
|
|
|
|
str2name "\x{3a8}", "\xd4" # returns qw/Psi Ocircumflex/ |
|
336
|
|
|
|
|
|
|
str2name "\x{3a8}\xd4" # returns 'Psi_Ocircumflex' |
|
337
|
|
|
|
|
|
|
str2name "\x{1234}\x{5678}" # returns 'uni12345678' |
|
338
|
|
|
|
|
|
|
str2name "\x{05D3}\x{05B9}" # returns 'daletholam' |
|
339
|
|
|
|
|
|
|
|
|
340
|
|
|
|
|
|
|
=cut |
|
341
|
|
|
|
|
|
|
|
|
342
|
|
|
|
|
|
|
sub str2name { |
|
343
|
20
|
|
|
20
|
1
|
3941
|
my $self = &_get_self; |
|
344
|
20
|
|
|
|
|
102
|
my(@strs,@ret) = @_; |
|
345
|
20
|
|
|
|
|
26
|
my $map = $$self{str2name}; |
|
346
|
20
|
|
|
|
|
35
|
for(@strs) { |
|
347
|
36
|
100
|
|
|
|
105
|
if(length > 1) { |
|
|
|
100
|
|
|
|
|
|
|
348
|
20
|
100
|
|
|
|
47
|
if (exists $$map{$_}) { |
|
349
|
4
|
|
|
|
|
13
|
push @ret, $$map{$_}; |
|
350
|
|
|
|
|
|
|
}else{ |
|
351
|
16
|
|
|
|
|
20
|
my @components; |
|
352
|
|
|
|
|
|
|
my $uni_component; # whether the previous |
|
353
|
16
|
|
|
|
|
40
|
for(split //) { # component was a ‘uni-’ |
|
354
|
44
|
100
|
|
|
|
132
|
if (exists $$map{$_}){ |
|
|
|
100
|
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
355
|
12
|
|
|
|
|
21
|
push @components, |
|
356
|
|
|
|
|
|
|
$$map{$_} ; |
|
357
|
12
|
|
|
|
|
23
|
$uni_component =0; |
|
358
|
|
|
|
|
|
|
} elsif((my $ord = ord) > 0xffff) { |
|
359
|
4
|
|
|
|
|
11
|
push @components, |
|
360
|
|
|
|
|
|
|
sprintf "u%X",$ord; |
|
361
|
4
|
|
|
|
|
9
|
$uni_component =0; |
|
362
|
|
|
|
|
|
|
} elsif($uni_component) { |
|
363
|
16
|
|
|
|
|
43
|
$components[-1] .= |
|
364
|
|
|
|
|
|
|
sprintf"%04X",ord; |
|
365
|
|
|
|
|
|
|
} else { |
|
366
|
12
|
|
|
|
|
30
|
push @components, |
|
367
|
|
|
|
|
|
|
sprintf"uni%04X", |
|
368
|
|
|
|
|
|
|
ord; |
|
369
|
12
|
|
|
|
|
19
|
++$uni_component; |
|
370
|
|
|
|
|
|
|
} |
|
371
|
|
|
|
|
|
|
} |
|
372
|
16
|
|
|
|
|
51
|
push @ret, join '_', @components; |
|
373
|
|
|
|
|
|
|
} |
|
374
|
|
|
|
|
|
|
} |
|
375
|
|
|
|
|
|
|
elsif(length) { |
|
376
|
12
|
|
|
|
|
14
|
my $ord = ord; |
|
377
|
12
|
100
|
|
|
|
76
|
push @ret, exists $$map{$_} |
|
|
|
100
|
|
|
|
|
|
|
378
|
|
|
|
|
|
|
? $$map{$_} |
|
379
|
|
|
|
|
|
|
: sprintf $ord > 0xffff ?"u%X":"uni%04X", |
|
380
|
|
|
|
|
|
|
$ord; |
|
381
|
4
|
|
|
|
|
17
|
}else { push @ret, '.notdef' } |
|
382
|
|
|
|
|
|
|
} |
|
383
|
20
|
100
|
|
|
|
152
|
@ret == 1 ? $ret[-1] : @ret ; |
|
384
|
|
|
|
|
|
|
} |
|
385
|
|
|
|
|
|
|
|
|
386
|
|
|
|
|
|
|
|
|
387
|
|
|
|
|
|
|
=item ord2name ( LIST ) |
|
388
|
|
|
|
|
|
|
|
|
389
|
|
|
|
|
|
|
LIST is a list of character codes. This function returns a list of glyph |
|
390
|
|
|
|
|
|
|
names that |
|
391
|
|
|
|
|
|
|
correspond to all the arguments passed to it. If called |
|
392
|
|
|
|
|
|
|
in scalar context |
|
393
|
|
|
|
|
|
|
with more than one argument, the behaviour is undefined (and subject to |
|
394
|
|
|
|
|
|
|
change in future releases). |
|
395
|
|
|
|
|
|
|
|
|
396
|
|
|
|
|
|
|
ord2name 115 # returns 's' |
|
397
|
|
|
|
|
|
|
ord2name 0x3a8, 0xd4 # returns 'Psi', 'Ocircumflex' |
|
398
|
|
|
|
|
|
|
ord2name 0x1234, 0x5678 # returns 'uni1234', 'uni5678' |
|
399
|
|
|
|
|
|
|
|
|
400
|
|
|
|
|
|
|
=cut |
|
401
|
|
|
|
|
|
|
|
|
402
|
|
|
|
|
|
|
sub ord2name { |
|
403
|
8
|
|
|
8
|
1
|
4268
|
my $self = &_get_self; |
|
404
|
8
|
|
|
|
|
22
|
my(@codes,@ret) = @_; |
|
405
|
8
|
|
|
|
|
11
|
my $map = $$self{str2name}; |
|
406
|
8
|
|
|
|
|
21
|
for(@codes) { |
|
407
|
12
|
|
|
|
|
31
|
my $char = chr; |
|
408
|
12
|
100
|
|
|
|
68
|
push @ret, exists $$map{$char} |
|
|
|
100
|
|
|
|
|
|
|
409
|
|
|
|
|
|
|
? $$map{$char} |
|
410
|
|
|
|
|
|
|
: sprintf $_ > 0xffff ?"u%X":"uni%04X", |
|
411
|
|
|
|
|
|
|
$_; |
|
412
|
|
|
|
|
|
|
} |
|
413
|
8
|
100
|
|
|
|
65
|
@ret == 1 ? $ret[-1] : @ret ; |
|
414
|
|
|
|
|
|
|
} |
|
415
|
|
|
|
|
|
|
|
|
416
|
|
|
|
|
|
|
|
|
417
|
|
|
|
|
|
|
=item ord2ligname ( LIST ) |
|
418
|
|
|
|
|
|
|
|
|
419
|
|
|
|
|
|
|
LIST is a list of character codes. This function returns a glyph |
|
420
|
|
|
|
|
|
|
name for a ligature that |
|
421
|
|
|
|
|
|
|
corresponds to the arguments passed to it, or '.notdef' if there are none. |
|
422
|
|
|
|
|
|
|
|
|
423
|
|
|
|
|
|
|
ord2ligname 115, 116 # returns 's_t' |
|
424
|
|
|
|
|
|
|
ord2ligname 0x3a8, 0xd4 # returns 'Psi_Ocircumflex' |
|
425
|
|
|
|
|
|
|
ord2ligname 0x1234, 0x5678 # returns 'uni12345678' |
|
426
|
|
|
|
|
|
|
ord2ligname 0x05D3, 0x05B9 # returns 'daletholam' |
|
427
|
|
|
|
|
|
|
|
|
428
|
|
|
|
|
|
|
=cut |
|
429
|
|
|
|
|
|
|
|
|
430
|
|
|
|
|
|
|
sub ord2ligname { |
|
431
|
20
|
|
|
20
|
1
|
4891
|
my $self = &_get_self; |
|
432
|
20
|
|
|
|
|
101
|
my(@codes) = @_; |
|
433
|
20
|
|
|
|
|
41
|
my $map = $$self{str2name}; |
|
434
|
20
|
|
|
|
|
118
|
my $str = join '', map chr, @codes; |
|
435
|
20
|
100
|
|
|
|
122
|
exists $$map{$str} and return $$map{$str}; |
|
436
|
16
|
|
|
|
|
25
|
my @components; |
|
437
|
|
|
|
|
|
|
my $uni_component; # whether the previous |
|
438
|
16
|
|
|
|
|
32
|
for(@codes) { # component was a ‘uni-’ |
|
439
|
44
|
|
|
|
|
68
|
my $char = chr; |
|
440
|
44
|
100
|
|
|
|
148
|
if (exists $$map{$char}){ |
|
|
|
100
|
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
441
|
16
|
|
|
|
|
37
|
push @components, |
|
442
|
|
|
|
|
|
|
$$map{$char} ; |
|
443
|
16
|
|
|
|
|
28
|
$uni_component =0; |
|
444
|
|
|
|
|
|
|
} elsif( $_ > 0xffff ) { |
|
445
|
6
|
|
|
|
|
17
|
push @components, |
|
446
|
|
|
|
|
|
|
sprintf "u%X",$_; |
|
447
|
6
|
|
|
|
|
15
|
$uni_component =0; |
|
448
|
|
|
|
|
|
|
} elsif($uni_component) { |
|
449
|
12
|
|
|
|
|
36
|
$components[-1] .= |
|
450
|
|
|
|
|
|
|
sprintf"%04X",$_; |
|
451
|
|
|
|
|
|
|
} else { |
|
452
|
10
|
|
|
|
|
38
|
push @components, |
|
453
|
|
|
|
|
|
|
sprintf"uni%04X", |
|
454
|
|
|
|
|
|
|
$_; |
|
455
|
10
|
|
|
|
|
17
|
++$uni_component; |
|
456
|
|
|
|
|
|
|
} |
|
457
|
|
|
|
|
|
|
} |
|
458
|
16
|
100
|
|
|
|
138
|
return @components ? join '_', @components : '.notdef'; |
|
459
|
|
|
|
|
|
|
} |
|
460
|
|
|
|
|
|
|
|
|
461
|
|
|
|
|
|
|
|
|
462
|
|
|
|
|
|
|
=back |
|
463
|
|
|
|
|
|
|
|
|
464
|
|
|
|
|
|
|
=cut |
|
465
|
|
|
|
|
|
|
|
|
466
|
|
|
|
|
|
|
|
|
467
|
|
|
|
|
|
|
|
|
468
|
|
|
|
|
|
|
|
|
469
|
|
|
|
|
|
|
#----------- A PRIVATE SUBROUTINE ---------------# |
|
470
|
|
|
|
|
|
|
|
|
471
|
|
|
|
|
|
|
# _get_self helps the methods act as functions as well. |
|
472
|
|
|
|
|
|
|
# Each function should call it thusly: |
|
473
|
|
|
|
|
|
|
# my $self = &_get_self; |
|
474
|
|
|
|
|
|
|
# The object (if any) will be shifted off @_. |
|
475
|
|
|
|
|
|
|
# If there was no object in @_, $self will refer to $_obj (a |
|
476
|
|
|
|
|
|
|
# package var.) |
|
477
|
|
|
|
|
|
|
|
|
478
|
|
|
|
|
|
|
sub _get_self { |
|
479
|
144
|
100
|
66
|
144
|
|
923
|
UNIVERSAL::isa($_[0], __PACKAGE__) |
|
480
|
|
|
|
|
|
|
? shift |
|
481
|
|
|
|
|
|
|
: ($_obj ||= new); |
|
482
|
|
|
|
|
|
|
} |
|
483
|
|
|
|
|
|
|
|
|
484
|
|
|
|
|
|
|
|
|
485
|
|
|
|
|
|
|
#----------- THE REST OF THE DOCUMENTATION ---------------# |
|
486
|
|
|
|
|
|
|
|
|
487
|
|
|
|
|
|
|
=pod |
|
488
|
|
|
|
|
|
|
|
|
489
|
|
|
|
|
|
|
=head1 THE GLYPH LIST FILE FORMAT |
|
490
|
|
|
|
|
|
|
|
|
491
|
|
|
|
|
|
|
B This section is not intended to be normative. It simply |
|
492
|
|
|
|
|
|
|
describes how this module parses glyph list files--which works with |
|
493
|
|
|
|
|
|
|
those provided by Adobe. |
|
494
|
|
|
|
|
|
|
|
|
495
|
|
|
|
|
|
|
All lines that consist solely of |
|
496
|
|
|
|
|
|
|
whitespace or that have a sharp sign (#) preceded only by whitespace |
|
497
|
|
|
|
|
|
|
(if any) are ignored. All others lines must consist of the glyph name |
|
498
|
|
|
|
|
|
|
followed by a semicolon, and the character numbers in hex, separated |
|
499
|
|
|
|
|
|
|
and optionally |
|
500
|
|
|
|
|
|
|
surrounded by whitespace. If there are multiple character numbers, the |
|
501
|
|
|
|
|
|
|
glyph is understood to represent a sequence of characters. The line |
|
502
|
|
|
|
|
|
|
breaks must be either CRLF sequences |
|
503
|
|
|
|
|
|
|
(as in |
|
504
|
|
|
|
|
|
|
Adobe's |
|
505
|
|
|
|
|
|
|
lists) or native line breaks. |
|
506
|
|
|
|
|
|
|
If a glyph name occurs more than once, the first instance |
|
507
|
|
|
|
|
|
|
will be |
|
508
|
|
|
|
|
|
|
used. |
|
509
|
|
|
|
|
|
|
|
|
510
|
|
|
|
|
|
|
|
|
511
|
|
|
|
|
|
|
=head1 COMPATIBILITY |
|
512
|
|
|
|
|
|
|
|
|
513
|
|
|
|
|
|
|
This module requires perl 5.8.0 or later. |
|
514
|
|
|
|
|
|
|
|
|
515
|
|
|
|
|
|
|
=head1 BUGS |
|
516
|
|
|
|
|
|
|
|
|
517
|
|
|
|
|
|
|
Please e-mail me if you find any. |
|
518
|
|
|
|
|
|
|
|
|
519
|
|
|
|
|
|
|
=head1 AUTHOR & COPYRIGHT |
|
520
|
|
|
|
|
|
|
|
|
521
|
|
|
|
|
|
|
Copyright (C) 2006-8, Father Chrysostomos
|
|
522
|
|
|
|
|
|
|
period o r g]> |
|
523
|
|
|
|
|
|
|
|
|
524
|
|
|
|
|
|
|
=head1 SEE ALSO |
|
525
|
|
|
|
|
|
|
|
|
526
|
|
|
|
|
|
|
=over 4 |
|
527
|
|
|
|
|
|
|
|
|
528
|
|
|
|
|
|
|
=item B |
|
529
|
|
|
|
|
|
|
|
|
530
|
|
|
|
|
|
|
L |
|
531
|
|
|
|
|
|
|
|
|
532
|
|
|
|
|
|
|
=item B |
|
533
|
|
|
|
|
|
|
|
|
534
|
|
|
|
|
|
|
L |
|
535
|
|
|
|
|
|
|
|
|
536
|
|
|
|
|
|
|
=item B |
|
537
|
|
|
|
|
|
|
|
|
538
|
|
|
|
|
|
|
L |
|
539
|
|
|
|
|
|
|
|
|
540
|
|
|
|
|
|
|
=item B |
|
541
|
|
|
|
|
|
|
|
|
542
|
|
|
|
|
|
|
L |
|
543
|
|
|
|
|
|
|
|
|
544
|
|
|
|
|
|
|
=cut |
|
545
|
|
|
|
|
|
|
|
|
546
|
|
|
|
|
|
|
|
|
547
|
|
|
|
|
|
|
|
|
548
|
|
|
|
|
|
|
|