1 /*---------------------------------------------------------------------------*
2  |              PDFlib - A library for generating PDF on the fly             |
3  +---------------------------------------------------------------------------+
4  | Copyright (c) 1997-2006 Thomas Merz and PDFlib GmbH. All rights reserved. |
5  +---------------------------------------------------------------------------+
6  |                                                                           |
7  |    This software is subject to the PDFlib license. It is NOT in the       |
8  |    public domain. Extended versions and commercial licenses are           |
9  |    available, please check http://www.pdflib.com.                         |
10  |                                                                           |
11  *---------------------------------------------------------------------------*/
12 
13 /* $Id: ft_cid.c,v 1.64.2.18 2009/02/27 13:04:38 kurt Exp $
14  *
15  * FONT CID functions
16  *
17  */
18 
19 #define FT_CID_C
20 
21 #include <errno.h>
22 
23 #include "ft_font.h"
24 #include "pc_file.h"
25 
26 /* ------------------------ Predefined CMaps ------------------------ */
27 
28 /* Predefined CMaps and the corresponding character collection */
29 static const fnt_cmap_info fnt_predefined_cmaps[] =
30 {
31     { "83pv-RKSJ-H",      cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 0},
32     { "90ms-RKSJ-H",      cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 0},
33     { "90ms-RKSJ-V",      cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 1},
34     { "90msp-RKSJ-H",     cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 0},
35     { "90msp-RKSJ-V",     cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 1},
36     { "90pv-RKSJ-H",      cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 0},
37     { "Add-RKSJ-H",       cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 0},
38     { "Add-RKSJ-V",       cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 1},
39     { "EUC-H",            cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 0},
40     { "EUC-V",            cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 1},
41     { "Ext-RKSJ-H",       cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 0},
42     { "Ext-RKSJ-V",       cc_japanese, 0, PDC_1_3, 2, 2, 2, 2, 1},
43     { "H",                cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 0},
44     { "V",                cc_japanese, 0, PDC_1_3, 1, 1, 1, 1, 1},
45     { "UniJIS-UCS2-H",    cc_japanese, 2, PDC_1_3, 2, 4, 4, 6, 0},
46     { "UniJIS-UCS2-V",    cc_japanese, 2, PDC_1_3, 2, 4, 4, 6, 1},
47     { "UniJIS-UCS2-HW-H", cc_japanese,-2, PDC_1_3, 2, 4, 4, 6, 0},
48     { "UniJIS-UCS2-HW-V", cc_japanese -2, PDC_1_3, 2, 4, 4, 6, 1},
49     { "UniJIS-UTF16-H",   cc_japanese, 2, PDC_1_5, 0, 0, 5, 6, 0},
50     { "UniJIS-UTF16-V",   cc_japanese, 2, PDC_1_5, 0, 0, 5, 6, 1},
51 
52     { "GB-EUC-H",         cc_simplified_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
53     { "GB-EUC-V",         cc_simplified_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
54     { "GBpc-EUC-H",       cc_simplified_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
55     { "GBpc-EUC-V",       cc_simplified_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
56     { "GBK-EUC-H",        cc_simplified_chinese, 0, PDC_1_3, 2, 2, 2, 2, 0},
57     { "GBK-EUC-V",        cc_simplified_chinese, 0, PDC_1_3, 2, 2, 2, 2, 1},
58     { "GBKp-EUC-H",       cc_simplified_chinese, 0, PDC_1_4, 0, 2, 2, 2, 0},
59     { "GBKp-EUC-V",       cc_simplified_chinese, 0, PDC_1_4, 0, 2, 2, 2, 1},
60     { "GBK2K-H",          cc_simplified_chinese, 0, PDC_1_4, 0, 4, 4, 5, 0},
61     { "GBK2K-V",          cc_simplified_chinese, 0, PDC_1_4, 0, 4, 4, 5, 1},
62     { "UniGB-UCS2-H",     cc_simplified_chinese, 2, PDC_1_3, 2, 4, 4, 4, 0},
63     { "UniGB-UCS2-V",     cc_simplified_chinese, 2, PDC_1_3, 2, 4, 4, 4, 1},
64     { "UniGB-UTF16-H",    cc_simplified_chinese, 2, PDC_1_5, 0, 0, 4, 5, 0},
65     { "UniGB-UTF16-V",    cc_simplified_chinese, 2, PDC_1_5, 0, 0, 4, 5, 1},
66 
67     { "B5pc-H",           cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
68     { "B5pc-V",           cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
69     { "HKscs-B5-H",       cc_traditional_chinese, 0, PDC_1_4, 0, 3, 3, 5, 0},
70     { "HKscs-B5-V",       cc_traditional_chinese, 0, PDC_1_4, 0, 3, 3, 5, 1},
71     { "ETen-B5-H",        cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
72     { "ETen-B5-V",        cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
73     { "ETenms-B5-H",      cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
74     { "ETenms-B5-V",      cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
75     { "CNS-EUC-H",        cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 0},
76     { "CNS-EUC-V",        cc_traditional_chinese, 0, PDC_1_3, 0, 0, 0, 0, 1},
77     { "UniCNS-UCS2-H",    cc_traditional_chinese, 2, PDC_1_3, 0, 3, 3, 3, 0},
78     { "UniCNS-UCS2-V",    cc_traditional_chinese, 2, PDC_1_3, 0, 3, 3, 3, 1},
79     { "UniCNS-UTF16-H",   cc_traditional_chinese, 2, PDC_1_5, 0, 0, 4, 4, 0},
80     { "UniCNS-UTF16-V",   cc_traditional_chinese, 2, PDC_1_5, 0, 0, 4, 4, 1},
81 
82     { "KSC-EUC-H",        cc_korean, 0, PDC_1_3, 0, 0, 0, 0, 0},
83     { "KSC-EUC-V",        cc_korean, 0, PDC_1_3, 0, 0, 0, 0, 1},
84     { "KSCms-UHC-H",      cc_korean, 0, PDC_1_3, 1, 1, 1, 1, 0},
85     { "KSCms-UHC-V",      cc_korean, 0, PDC_1_3, 1, 1, 1, 1, 1},
86     { "KSCms-UHC-HW-H",   cc_korean, 0, PDC_1_3, 1, 1, 1, 1, 0},
87     { "KSCms-UHC-HW-V",   cc_korean, 0, PDC_1_3, 1, 1, 1, 1, 1},
88     { "KSCpc-EUC-H",      cc_korean, 0, PDC_1_3, 0, 0, 0, 0, 0},
89     { "UniKS-UCS2-H",     cc_korean, 2, PDC_1_3, 1, 1, 1, 1, 0},
90     { "UniKS-UCS2-V",     cc_korean, 2, PDC_1_3, 1, 1, 1, 1, 1},
91     { "UniKS-UTF16-H",    cc_korean, 2, PDC_1_5, 0, 0, 2, 2, 0},
92     { "UniKS-UTF16-V",    cc_korean, 2, PDC_1_5, 0, 0, 2, 2, 1},
93 
94     { "Identity-H",       cc_identity, 0, PDC_1_3, 0, 0, 0, 0, 0},
95     { "Identity-V",       cc_identity, 0, PDC_1_3, 0, 0, 0, 0, 1},
96 
97     { NULL,               cc_none, 0, 0, 0, 0, 0, 0, 0},
98 };
99 
100 static int
fnt_get_predefined_cmap_slot(const char * cmapname)101 fnt_get_predefined_cmap_slot(const char *cmapname)
102 {
103     int slot;
104 
105     for (slot = 0; ; slot++)
106     {
107         if (fnt_predefined_cmaps[slot].name == NULL)
108         {
109             slot = -1;
110             break;
111         }
112         if (!strcmp(fnt_predefined_cmaps[slot].name, cmapname))
113             break;
114     }
115 
116     return slot;
117 }
118 
119 int
fnt_get_predefined_cmap_info(const char * cmapname,fnt_cmap_info * cmapinfo)120 fnt_get_predefined_cmap_info(const char *cmapname, fnt_cmap_info *cmapinfo)
121 {
122     int slot;
123 
124     slot = fnt_get_predefined_cmap_slot(cmapname);
125 
126     if (slot == -1)
127         return cc_none;
128 
129     if (cmapinfo)
130         *cmapinfo = fnt_predefined_cmaps[slot];
131 
132     return fnt_predefined_cmaps[slot].charcoll;
133 }
134 
135 static const pdc_keyconn fnt_charcoll_keylist[] =
136 {
137     { "Japan1",    cc_japanese},
138     { "GB1",       cc_simplified_chinese},
139     { "CNS1",      cc_traditional_chinese},
140     { "Korea1",    cc_korean},
141     { "Identity",  cc_identity},
142     { "Unknown",   cc_unknown},
143     { NULL, 0}
144 };
145 
146 const char *
fnt_get_ordering_cid(int charcoll)147 fnt_get_ordering_cid(int charcoll)
148 {
149     return pdc_get_keyword(charcoll, fnt_charcoll_keylist);
150 }
151 
152 int
fnt_get_charcoll(const char * ordering)153 fnt_get_charcoll(const char *ordering)
154 {
155     int charcoll;
156 
157     charcoll = (int) pdc_get_keycode(ordering, fnt_charcoll_keylist);
158 
159     if (charcoll == PDC_KEY_NOTFOUND)
160         return cc_unknown;
161     else
162         return charcoll;
163 }
164 
165 int
fnt_get_supplement(fnt_cmap_info * cmapinfo,int compatibility)166 fnt_get_supplement(fnt_cmap_info *cmapinfo, int compatibility)
167 {
168     int retval = 0;
169 
170     switch(compatibility)
171     {
172         case PDC_1_3:
173         retval = cmapinfo->supplement13;
174         break;
175 
176         case PDC_1_4:
177         retval = cmapinfo->supplement14;
178         break;
179 
180         case PDC_1_5:
181         retval = cmapinfo->supplement15;
182         break;
183 
184         default:
185         case PDC_1_6:
186         retval = cmapinfo->supplement16;
187         break;
188     }
189 
190     return retval;
191 }
192 
193 /*
194  * See:
195  * Adobe Technical Note #5078 (Japanese1)
196  * Adobe Technical Note #5079 (GB1)
197  * Adobe Technical Note #5080 (CNS1)
198  * Adobe Technical Note #5093 (Korea1)
199  *
200  */
201 
202 int
fnt_get_maxcid(int charcoll,int supplement)203 fnt_get_maxcid(int charcoll, int supplement)
204 {
205     switch(charcoll)
206     {
207         case cc_japanese:
208         switch(supplement)
209         {
210             case 0:
211             return 8283;
212 
213             case 1:
214             return 8358;
215 
216             case 2:
217             return 8719;
218 
219             case 3:
220             return 9353;
221 
222             case 4:
223             return 15443;
224 
225             case 5:
226             return 20316;
227 
228             case 6:
229             default:
230             return 23057;
231         }
232 
233         case cc_simplified_chinese:
234         switch(supplement)
235         {
236             case 0:
237             return 7716;
238 
239             case 1:
240             return 9896;
241 
242             case 2:
243             return 22126;
244 
245             case 3:
246             return 22352;
247 
248             case 4:
249             return 29063;
250 
251             case 5:
252             default:
253             return 30283;
254         }
255 
256         case cc_traditional_chinese:
257         switch(supplement)
258         {
259             case 0:
260             return 14098;
261 
262             case 1:
263             return 17407;
264 
265             case 2:
266             return 17600;
267 
268             case 3:
269             return 18845;
270 
271             case 4:
272             return 18964;
273 
274             case 5:
275             default:
276             return 19087;
277         }
278 
279         case cc_korean:
280         switch(supplement)
281         {
282             case 0:
283             return 9332;
284 
285             case 1:
286             return 18154;
287 
288             case 2:
289             default:
290             return 18351;
291         }
292 
293         case cc_identity:
294         case cc_unknown:
295         return FNT_MAXCID;
296 
297         default:
298         return 0;
299     }
300 }
301 
302