1593dc095SDavid du Colombier /* Copyright (C) 2000, 2001 Aladdin Enterprises. All rights reserved.
23ff48bf5SDavid du Colombier
3593dc095SDavid du Colombier This software is provided AS-IS with no warranty, either express or
4593dc095SDavid du Colombier implied.
53ff48bf5SDavid du Colombier
6593dc095SDavid du Colombier This software is distributed under license and may not be copied,
7593dc095SDavid du Colombier modified or distributed except as expressly authorized under the terms
8593dc095SDavid du Colombier of the license contained in the file LICENSE in this distribution.
93ff48bf5SDavid du Colombier
10593dc095SDavid du Colombier For more information about licensing, please refer to
11593dc095SDavid du Colombier http://www.ghostscript.com/licensing/. For information on
12593dc095SDavid du Colombier commercial licensing, go to http://www.artifex.com/licensing/ or
13593dc095SDavid du Colombier contact Artifex Software, Inc., 101 Lucas Valley Road #110,
14593dc095SDavid du Colombier San Rafael, CA 94903, U.S.A., +1(415)492-9861.
153ff48bf5SDavid du Colombier */
163ff48bf5SDavid du Colombier
17593dc095SDavid du Colombier /* $Id: zfcid1.c,v 1.23 2004/11/19 04:39:11 ray Exp $ */
183ff48bf5SDavid du Colombier /* CIDFontType 1 and 2 operators */
193ff48bf5SDavid du Colombier #include "memory_.h"
203ff48bf5SDavid du Colombier #include "ghost.h"
213ff48bf5SDavid du Colombier #include "oper.h"
223ff48bf5SDavid du Colombier #include "gsmatrix.h"
233ff48bf5SDavid du Colombier #include "gsccode.h"
243ff48bf5SDavid du Colombier #include "gsstruct.h"
25593dc095SDavid du Colombier #include "gsgcache.h"
263ff48bf5SDavid du Colombier #include "gxfcid.h"
273ff48bf5SDavid du Colombier #include "bfont.h"
283ff48bf5SDavid du Colombier #include "icid.h"
293ff48bf5SDavid du Colombier #include "idict.h"
303ff48bf5SDavid du Colombier #include "idparam.h"
313ff48bf5SDavid du Colombier #include "ifcid.h"
32593dc095SDavid du Colombier #include "ichar1.h"
333ff48bf5SDavid du Colombier #include "ifont42.h"
343ff48bf5SDavid du Colombier #include "store.h"
35593dc095SDavid du Colombier #include "stream.h"
36593dc095SDavid du Colombier #include "files.h"
373ff48bf5SDavid du Colombier
383ff48bf5SDavid du Colombier /* ---------------- CIDFontType 1 (FontType 10) ---------------- */
393ff48bf5SDavid du Colombier
403ff48bf5SDavid du Colombier /* <string|name> <font_dict> .buildfont10 <string|name> <font> */
413ff48bf5SDavid du Colombier private int
zbuildfont10(i_ctx_t * i_ctx_p)423ff48bf5SDavid du Colombier zbuildfont10(i_ctx_t *i_ctx_p)
433ff48bf5SDavid du Colombier {
443ff48bf5SDavid du Colombier os_ptr op = osp;
453ff48bf5SDavid du Colombier build_proc_refs build;
463ff48bf5SDavid du Colombier int code = build_gs_font_procs(op, &build);
473ff48bf5SDavid du Colombier gs_cid_system_info_t cidsi;
483ff48bf5SDavid du Colombier gs_font_base *pfont;
493ff48bf5SDavid du Colombier
503ff48bf5SDavid du Colombier if (code < 0)
513ff48bf5SDavid du Colombier return code;
523ff48bf5SDavid du Colombier code = cid_font_system_info_param(&cidsi, op);
533ff48bf5SDavid du Colombier if (code < 0)
543ff48bf5SDavid du Colombier return code;
553ff48bf5SDavid du Colombier make_null(&build.BuildChar); /* only BuildGlyph */
563ff48bf5SDavid du Colombier code = build_gs_simple_font(i_ctx_p, op, &pfont, ft_CID_user_defined,
573ff48bf5SDavid du Colombier &st_gs_font_cid1, &build,
583ff48bf5SDavid du Colombier bf_Encoding_optional |
593ff48bf5SDavid du Colombier bf_UniqueID_ignored);
603ff48bf5SDavid du Colombier if (code < 0)
613ff48bf5SDavid du Colombier return code;
623ff48bf5SDavid du Colombier ((gs_font_cid1 *)pfont)->cidata.CIDSystemInfo = cidsi;
633ff48bf5SDavid du Colombier return define_gs_font((gs_font *)pfont);
643ff48bf5SDavid du Colombier }
653ff48bf5SDavid du Colombier
663ff48bf5SDavid du Colombier /* ---------------- CIDFontType 2 (FontType 11) ---------------- */
673ff48bf5SDavid du Colombier
683ff48bf5SDavid du Colombier /* ------ Accessing ------ */
693ff48bf5SDavid du Colombier
703ff48bf5SDavid du Colombier /* Map a glyph CID to a TrueType glyph number using the CIDMap. */
713ff48bf5SDavid du Colombier private int
z11_CIDMap_proc(gs_font_cid2 * pfont,gs_glyph glyph)723ff48bf5SDavid du Colombier z11_CIDMap_proc(gs_font_cid2 *pfont, gs_glyph glyph)
733ff48bf5SDavid du Colombier {
743ff48bf5SDavid du Colombier const ref *pcidmap = &pfont_data(pfont)->u.type42.CIDMap;
753ff48bf5SDavid du Colombier ulong cid = glyph - gs_min_cid_glyph;
763ff48bf5SDavid du Colombier int gdbytes = pfont->cidata.common.GDBytes;
773ff48bf5SDavid du Colombier int gnum = 0;
783ff48bf5SDavid du Colombier const byte *data;
793ff48bf5SDavid du Colombier int i, code;
803ff48bf5SDavid du Colombier ref rcid;
813ff48bf5SDavid du Colombier ref *prgnum;
823ff48bf5SDavid du Colombier
833ff48bf5SDavid du Colombier switch (r_type(pcidmap)) {
843ff48bf5SDavid du Colombier case t_string:
853ff48bf5SDavid du Colombier if (cid >= r_size(pcidmap) / gdbytes)
863ff48bf5SDavid du Colombier return_error(e_rangecheck);
873ff48bf5SDavid du Colombier data = pcidmap->value.const_bytes + cid * gdbytes;
883ff48bf5SDavid du Colombier break;
893ff48bf5SDavid du Colombier case t_integer:
903ff48bf5SDavid du Colombier return cid + pcidmap->value.intval;
913ff48bf5SDavid du Colombier case t_dictionary:
923ff48bf5SDavid du Colombier make_int(&rcid, cid);
933ff48bf5SDavid du Colombier code = dict_find(pcidmap, &rcid, &prgnum);
943ff48bf5SDavid du Colombier if (code <= 0)
953ff48bf5SDavid du Colombier return (code < 0 ? code : gs_note_error(e_undefined));
963ff48bf5SDavid du Colombier if (!r_has_type(prgnum, t_integer))
973ff48bf5SDavid du Colombier return_error(e_typecheck);
983ff48bf5SDavid du Colombier return prgnum->value.intval;
993ff48bf5SDavid du Colombier default: /* array type */
100593dc095SDavid du Colombier code = string_array_access_proc(pfont->memory, pcidmap, 1, cid * gdbytes,
1013ff48bf5SDavid du Colombier gdbytes, &data);
1023ff48bf5SDavid du Colombier
1033ff48bf5SDavid du Colombier if (code < 0)
1043ff48bf5SDavid du Colombier return code;
105593dc095SDavid du Colombier if ( code > 0 )
106593dc095SDavid du Colombier return_error(e_invalidfont);
1073ff48bf5SDavid du Colombier }
1083ff48bf5SDavid du Colombier for (i = 0; i < gdbytes; ++i)
1093ff48bf5SDavid du Colombier gnum = (gnum << 8) + data[i];
1103ff48bf5SDavid du Colombier return gnum;
1113ff48bf5SDavid du Colombier }
1123ff48bf5SDavid du Colombier
1133ff48bf5SDavid du Colombier /* Handle MetricsCount when accessing outline or metrics information. */
1143ff48bf5SDavid du Colombier private int
z11_get_outline(gs_font_type42 * pfont,uint glyph_index,gs_glyph_data_t * pgd)1153ff48bf5SDavid du Colombier z11_get_outline(gs_font_type42 * pfont, uint glyph_index,
116593dc095SDavid du Colombier gs_glyph_data_t *pgd)
1173ff48bf5SDavid du Colombier {
1183ff48bf5SDavid du Colombier gs_font_cid2 *const pfcid = (gs_font_cid2 *)pfont;
1193ff48bf5SDavid du Colombier int skip = pfcid->cidata.MetricsCount << 1;
120593dc095SDavid du Colombier int code = pfcid->cidata.orig_procs.get_outline(pfont, glyph_index, pgd);
1213ff48bf5SDavid du Colombier
1223ff48bf5SDavid du Colombier if (code >= 0) {
123593dc095SDavid du Colombier uint size = pgd->bits.size;
1243ff48bf5SDavid du Colombier
1253ff48bf5SDavid du Colombier if (size <= skip) {
126593dc095SDavid du Colombier gs_glyph_data_free(pgd, "z11_get_outline");
127593dc095SDavid du Colombier gs_glyph_data_from_null(pgd);
1283ff48bf5SDavid du Colombier } else {
129593dc095SDavid du Colombier gs_glyph_data_substring(pgd, skip, size - skip);
1303ff48bf5SDavid du Colombier }
1313ff48bf5SDavid du Colombier }
1323ff48bf5SDavid du Colombier return code;
1333ff48bf5SDavid du Colombier }
134593dc095SDavid du Colombier
135593dc095SDavid du Colombier #define GET_U16_MSB(p) (((uint)((p)[0]) << 8) + (p)[1])
136593dc095SDavid du Colombier #define GET_S16_MSB(p) (int)((GET_U16_MSB(p) ^ 0x8000) - 0x8000)
137593dc095SDavid du Colombier
138*409b3affSDavid du Colombier double recipunitsperem(gs_font_type42 *pfont);
139*409b3affSDavid du Colombier
1403ff48bf5SDavid du Colombier private int
z11_get_metrics(gs_font_type42 * pfont,uint glyph_index,int wmode,float sbw[4])1413ff48bf5SDavid du Colombier z11_get_metrics(gs_font_type42 * pfont, uint glyph_index, int wmode,
1423ff48bf5SDavid du Colombier float sbw[4])
1433ff48bf5SDavid du Colombier {
1443ff48bf5SDavid du Colombier gs_font_cid2 *const pfcid = (gs_font_cid2 *)pfont;
1453ff48bf5SDavid du Colombier int skip = pfcid->cidata.MetricsCount << 1;
146593dc095SDavid du Colombier gs_glyph_data_t gdata;
1473ff48bf5SDavid du Colombier const byte *pmetrics;
1483ff48bf5SDavid du Colombier int lsb, width;
1493ff48bf5SDavid du Colombier int code = 0;
1503ff48bf5SDavid du Colombier
151593dc095SDavid du Colombier gdata.memory = pfont->memory;
152593dc095SDavid du Colombier if (wmode >= skip >> 2 ||
153593dc095SDavid du Colombier (code = pfcid->cidata.orig_procs.get_outline(pfont, glyph_index, &gdata)) < 0 ||
154593dc095SDavid du Colombier gdata.bits.size < skip
1553ff48bf5SDavid du Colombier )
1563ff48bf5SDavid du Colombier return pfcid->cidata.orig_procs.get_metrics(pfont, glyph_index, wmode,
1573ff48bf5SDavid du Colombier sbw);
158593dc095SDavid du Colombier pmetrics = gdata.bits.data + skip - 4 - (wmode << 2);
159593dc095SDavid du Colombier lsb = GET_S16_MSB(pmetrics + 2);
160593dc095SDavid du Colombier width = GET_U16_MSB(pmetrics + 0);
1613ff48bf5SDavid du Colombier {
162*409b3affSDavid du Colombier double factor = recipunitsperem(pfont);
1633ff48bf5SDavid du Colombier
1643ff48bf5SDavid du Colombier if (wmode) {
1653ff48bf5SDavid du Colombier sbw[0] = 0, sbw[1] = -lsb * factor;
1663ff48bf5SDavid du Colombier sbw[2] = 0, sbw[3] = -width * factor;
1673ff48bf5SDavid du Colombier } else {
1683ff48bf5SDavid du Colombier sbw[0] = lsb * factor, sbw[1] = 0;
1693ff48bf5SDavid du Colombier sbw[2] = width * factor, sbw[3] = 0;
1703ff48bf5SDavid du Colombier }
1713ff48bf5SDavid du Colombier }
172593dc095SDavid du Colombier gs_glyph_data_free(&gdata, "z11_get_metrics");
1733ff48bf5SDavid du Colombier return 0;
1743ff48bf5SDavid du Colombier }
1753ff48bf5SDavid du Colombier
176593dc095SDavid du Colombier private int
z11_glyph_info_aux(gs_font * font,gs_glyph glyph,const gs_matrix * pmat,int members,gs_glyph_info_t * info)177593dc095SDavid du Colombier z11_glyph_info_aux(gs_font *font, gs_glyph glyph, const gs_matrix *pmat,
178593dc095SDavid du Colombier int members, gs_glyph_info_t *info)
179593dc095SDavid du Colombier {
180593dc095SDavid du Colombier gs_font_cid2 *fontCID2 = (gs_font_cid2 *)font;
181593dc095SDavid du Colombier uint glyph_index;
182593dc095SDavid du Colombier int code = (glyph > GS_MIN_GLYPH_INDEX
183593dc095SDavid du Colombier ? glyph - GS_MIN_GLYPH_INDEX
184593dc095SDavid du Colombier : fontCID2->cidata.CIDMap_proc(fontCID2, glyph));
185593dc095SDavid du Colombier
186593dc095SDavid du Colombier if(code < 0)
187593dc095SDavid du Colombier return code;
188593dc095SDavid du Colombier glyph_index = (uint)code;
189593dc095SDavid du Colombier return gs_type42_glyph_info_by_gid(font, glyph, pmat, members, info, glyph_index);
190593dc095SDavid du Colombier }
191593dc095SDavid du Colombier
192593dc095SDavid du Colombier private int
z11_glyph_info(gs_font * font,gs_glyph glyph,const gs_matrix * pmat,int members,gs_glyph_info_t * info)193593dc095SDavid du Colombier z11_glyph_info(gs_font *font, gs_glyph glyph, const gs_matrix *pmat,
194593dc095SDavid du Colombier int members, gs_glyph_info_t *info)
195593dc095SDavid du Colombier {
196593dc095SDavid du Colombier int wmode = (members & GLYPH_INFO_WIDTH0 ? 0 : 1);
197593dc095SDavid du Colombier
198593dc095SDavid du Colombier return z1_glyph_info_generic(font, glyph, pmat, members, info,
199593dc095SDavid du Colombier &z11_glyph_info_aux, wmode);
200593dc095SDavid du Colombier }
201593dc095SDavid du Colombier
202593dc095SDavid du Colombier
203593dc095SDavid du Colombier /* Enumerate glyphs (keys) from GlyphDirectory instead of loca / glyf. */
204593dc095SDavid du Colombier private int
z11_enumerate_glyph(gs_font * font,int * pindex,gs_glyph_space_t glyph_space,gs_glyph * pglyph)205593dc095SDavid du Colombier z11_enumerate_glyph(gs_font *font, int *pindex,
206593dc095SDavid du Colombier gs_glyph_space_t glyph_space, gs_glyph *pglyph)
207593dc095SDavid du Colombier {
208593dc095SDavid du Colombier gs_font_cid2 *pfont = (gs_font_cid2 *)font;
209593dc095SDavid du Colombier int code0 = z11_CIDMap_proc(pfont, GS_MIN_CID_GLYPH);
210593dc095SDavid du Colombier int code;
211593dc095SDavid du Colombier
212593dc095SDavid du Colombier for (;;) {
213593dc095SDavid du Colombier code = z11_CIDMap_proc(pfont, GS_MIN_CID_GLYPH + *pindex);
214593dc095SDavid du Colombier
215593dc095SDavid du Colombier if (code < 0) {
216593dc095SDavid du Colombier *pindex = 0;
217593dc095SDavid du Colombier return 0;
218593dc095SDavid du Colombier }
219593dc095SDavid du Colombier (*pindex)++;
220593dc095SDavid du Colombier if (*pindex == 1 || code != code0)
221593dc095SDavid du Colombier break;
222593dc095SDavid du Colombier /* else skip an underfined glyph */
223593dc095SDavid du Colombier }
224593dc095SDavid du Colombier if (glyph_space == GLYPH_SPACE_INDEX)
225593dc095SDavid du Colombier *pglyph = GS_MIN_GLYPH_INDEX + (uint)code;
226593dc095SDavid du Colombier else
227593dc095SDavid du Colombier *pglyph = GS_MIN_CID_GLYPH + (uint)(*pindex - 1);
228593dc095SDavid du Colombier return 0;
229593dc095SDavid du Colombier }
230593dc095SDavid du Colombier
231593dc095SDavid du Colombier private uint
z11_get_glyph_index(gs_font_type42 * pfont,gs_glyph glyph)232593dc095SDavid du Colombier z11_get_glyph_index(gs_font_type42 *pfont, gs_glyph glyph)
233593dc095SDavid du Colombier {
234593dc095SDavid du Colombier int code = z11_CIDMap_proc((gs_font_cid2 *)pfont, glyph);
235593dc095SDavid du Colombier
236593dc095SDavid du Colombier return (code < 0 ? 0 /* notdef */: (uint)code);
237593dc095SDavid du Colombier }
238593dc095SDavid du Colombier
239593dc095SDavid du Colombier
240593dc095SDavid du Colombier private int
z11_glyph_outline(gs_font * font,int WMode,gs_glyph glyph,const gs_matrix * pmat,gx_path * ppath,double sbw[4])241593dc095SDavid du Colombier z11_glyph_outline(gs_font *font, int WMode, gs_glyph glyph, const gs_matrix *pmat,
242593dc095SDavid du Colombier gx_path *ppath, double sbw[4])
243593dc095SDavid du Colombier {
244593dc095SDavid du Colombier return gs_type42_glyph_outline(font, WMode,
245593dc095SDavid du Colombier z11_get_glyph_index((gs_font_type42 *)font, glyph) + GS_MIN_GLYPH_INDEX,
246593dc095SDavid du Colombier pmat, ppath, sbw);
247593dc095SDavid du Colombier }
248593dc095SDavid du Colombier
2493ff48bf5SDavid du Colombier /* ------ Defining ------ */
2503ff48bf5SDavid du Colombier
2513ff48bf5SDavid du Colombier /* <string|name> <font_dict> .buildfont11 <string|name> <font> */
2523ff48bf5SDavid du Colombier private int
zbuildfont11(i_ctx_t * i_ctx_p)2533ff48bf5SDavid du Colombier zbuildfont11(i_ctx_t *i_ctx_p)
2543ff48bf5SDavid du Colombier {
2553ff48bf5SDavid du Colombier os_ptr op = osp;
2563ff48bf5SDavid du Colombier gs_font_cid_data common;
2573ff48bf5SDavid du Colombier gs_font_type42 *pfont;
2583ff48bf5SDavid du Colombier gs_font_cid2 *pfcid;
2593ff48bf5SDavid du Colombier int MetricsCount;
260593dc095SDavid du Colombier ref rcidmap, ignore_gdir, file, *pfile, cfnstr, *pCIDFontName, CIDFontName;
261593dc095SDavid du Colombier ulong loca_glyph_pos[2][2];
2623ff48bf5SDavid du Colombier int code = cid_font_data_param(op, &common, &ignore_gdir);
2633ff48bf5SDavid du Colombier
2643ff48bf5SDavid du Colombier if (code < 0 ||
265593dc095SDavid du Colombier (code = dict_find_string(op, "CIDFontName", &pCIDFontName)) <= 0 ||
2663ff48bf5SDavid du Colombier (code = dict_int_param(op, "MetricsCount", 0, 4, 0, &MetricsCount)) < 0
2673ff48bf5SDavid du Colombier )
2683ff48bf5SDavid du Colombier return code;
269593dc095SDavid du Colombier /*
270593dc095SDavid du Colombier * Since build_gs_simple_font may resize the dictionary and cause
271593dc095SDavid du Colombier * pointers to become invalid, save CIDFontName
272593dc095SDavid du Colombier */
273593dc095SDavid du Colombier CIDFontName = *pCIDFontName;
2743ff48bf5SDavid du Colombier if (MetricsCount & 1) /* only allowable values are 0, 2, 4 */
2753ff48bf5SDavid du Colombier return_error(e_rangecheck);
276593dc095SDavid du Colombier code = dict_find_string(op, "File", &pfile);
277593dc095SDavid du Colombier if (code < 0 && code != e_dictfull)
278593dc095SDavid du Colombier return code;
279593dc095SDavid du Colombier if (code > 0) {
280593dc095SDavid du Colombier ref *file_table_pos, *a, v;
281593dc095SDavid du Colombier const char *name[2] = {"loca", "glyf"};
282593dc095SDavid du Colombier int i, j;
283593dc095SDavid du Colombier
284593dc095SDavid du Colombier /*
285593dc095SDavid du Colombier * Since build_gs_simple_font may resize the dictionary and cause
286593dc095SDavid du Colombier * pointers to become invalid, save File and CIDFontName
287593dc095SDavid du Colombier */
288593dc095SDavid du Colombier file = *pfile;
289593dc095SDavid du Colombier check_read_type(file, t_file);
290593dc095SDavid du Colombier code = dict_find_string(op, "file_table_pos", &file_table_pos);
291593dc095SDavid du Colombier if (code <= 0 || r_type(file_table_pos) != t_dictionary)
292593dc095SDavid du Colombier return_error(e_invalidfont);
293593dc095SDavid du Colombier for (i = 0; i < 2; i++) {
294593dc095SDavid du Colombier code = dict_find_string(file_table_pos, name[i], &a);
295593dc095SDavid du Colombier if (code <= 0 || r_type(a) != t_array)
296593dc095SDavid du Colombier return_error(e_invalidfont);
297593dc095SDavid du Colombier for (j = 0; j < 2; j++) {
298593dc095SDavid du Colombier code = array_get(imemory, a, j, &v);
299593dc095SDavid du Colombier if (code < 0 || r_type(&v) != t_integer)
300593dc095SDavid du Colombier return_error(e_invalidfont);
301593dc095SDavid du Colombier loca_glyph_pos[i][j] = v.value.intval;
302593dc095SDavid du Colombier }
303593dc095SDavid du Colombier }
304593dc095SDavid du Colombier } else
305593dc095SDavid du Colombier pfile = NULL;
306593dc095SDavid du Colombier code = font_string_array_param(imemory, op, "CIDMap", &rcidmap);
3073ff48bf5SDavid du Colombier switch (code) {
3083ff48bf5SDavid du Colombier case 0: /* in PLRM3 */
3093ff48bf5SDavid du Colombier gdb:
3103ff48bf5SDavid du Colombier /* GDBytes is required for indexing a string or string array. */
3113ff48bf5SDavid du Colombier if (common.GDBytes == 0)
3123ff48bf5SDavid du Colombier return_error(e_rangecheck);
3133ff48bf5SDavid du Colombier break;
3143ff48bf5SDavid du Colombier default:
3153ff48bf5SDavid du Colombier return code;
3163ff48bf5SDavid du Colombier case e_typecheck:
3173ff48bf5SDavid du Colombier switch (r_type(&rcidmap)) {
3183ff48bf5SDavid du Colombier case t_string: /* in PLRM3 */
3193ff48bf5SDavid du Colombier goto gdb;
3203ff48bf5SDavid du Colombier case t_dictionary: /* added in 3011 */
3213ff48bf5SDavid du Colombier case t_integer: /* added in 3011 */
3223ff48bf5SDavid du Colombier break;
3233ff48bf5SDavid du Colombier default:
3243ff48bf5SDavid du Colombier return code;
3253ff48bf5SDavid du Colombier }
3263ff48bf5SDavid du Colombier break;
3273ff48bf5SDavid du Colombier }
3283ff48bf5SDavid du Colombier code = build_gs_TrueType_font(i_ctx_p, op, &pfont, ft_CID_TrueType,
3293ff48bf5SDavid du Colombier &st_gs_font_cid2,
3303ff48bf5SDavid du Colombier (const char *)0, "%Type11BuildGlyph",
3313ff48bf5SDavid du Colombier bf_Encoding_optional |
3323ff48bf5SDavid du Colombier bf_UniqueID_ignored |
3333ff48bf5SDavid du Colombier bf_CharStrings_optional);
3343ff48bf5SDavid du Colombier if (code < 0)
3353ff48bf5SDavid du Colombier return code;
3363ff48bf5SDavid du Colombier pfcid = (gs_font_cid2 *)pfont;
3373ff48bf5SDavid du Colombier pfcid->cidata.common = common;
3383ff48bf5SDavid du Colombier pfcid->cidata.MetricsCount = MetricsCount;
3393ff48bf5SDavid du Colombier ref_assign(&pfont_data(pfont)->u.type42.CIDMap, &rcidmap);
3403ff48bf5SDavid du Colombier pfcid->cidata.CIDMap_proc = z11_CIDMap_proc;
341593dc095SDavid du Colombier pfont->procs.enumerate_glyph = z11_enumerate_glyph;
342593dc095SDavid du Colombier pfont->procs.glyph_info = z11_glyph_info;
343593dc095SDavid du Colombier pfont->procs.glyph_outline = z11_glyph_outline;
344593dc095SDavid du Colombier pfont->data.get_glyph_index = z11_get_glyph_index;
345593dc095SDavid du Colombier get_font_name(imemory, &cfnstr, &CIDFontName);
346593dc095SDavid du Colombier copy_font_name(&pfcid->font_name, &cfnstr);
3473ff48bf5SDavid du Colombier if (MetricsCount) {
3483ff48bf5SDavid du Colombier /* "Wrap" the glyph accessor procedures. */
3493ff48bf5SDavid du Colombier pfcid->cidata.orig_procs.get_outline = pfont->data.get_outline;
3503ff48bf5SDavid du Colombier pfont->data.get_outline = z11_get_outline;
3513ff48bf5SDavid du Colombier pfcid->cidata.orig_procs.get_metrics = pfont->data.get_metrics;
3523ff48bf5SDavid du Colombier pfont->data.get_metrics = z11_get_metrics;
353593dc095SDavid du Colombier } else if(pfile != NULL) {
354593dc095SDavid du Colombier /*
355593dc095SDavid du Colombier * We assume that disk fonts has no MetricsCount.
356593dc095SDavid du Colombier * We could do not, but the number of virtual function wariants increases.
357593dc095SDavid du Colombier */
358593dc095SDavid du Colombier stream *s;
359593dc095SDavid du Colombier
360593dc095SDavid du Colombier check_read_file(s, &file);
361593dc095SDavid du Colombier pfont->data.loca = loca_glyph_pos[0][0];
362593dc095SDavid du Colombier pfont->data.glyf = loca_glyph_pos[1][0];
363593dc095SDavid du Colombier pfont->data.get_outline = gs_get_glyph_data_cached;
364593dc095SDavid du Colombier pfont->data.gdcache = gs_glyph_cache__alloc(pfont, s, gs_type42_get_outline_from_TT_file);
3653ff48bf5SDavid du Colombier }
3663ff48bf5SDavid du Colombier return define_gs_font((gs_font *)pfont);
3673ff48bf5SDavid du Colombier }
3683ff48bf5SDavid du Colombier
3693ff48bf5SDavid du Colombier /* <cid11font> <cid> .type11mapcid <glyph_index> */
3703ff48bf5SDavid du Colombier private int
ztype11mapcid(i_ctx_t * i_ctx_p)3713ff48bf5SDavid du Colombier ztype11mapcid(i_ctx_t *i_ctx_p)
3723ff48bf5SDavid du Colombier {
3733ff48bf5SDavid du Colombier os_ptr op = osp;
3743ff48bf5SDavid du Colombier gs_font *pfont;
3753ff48bf5SDavid du Colombier int code = font_param(op - 1, &pfont);
3763ff48bf5SDavid du Colombier
3773ff48bf5SDavid du Colombier if (code < 0)
3783ff48bf5SDavid du Colombier return code;
379593dc095SDavid du Colombier check_type(*op, t_integer);
380593dc095SDavid du Colombier #if defined(TEST)
381593dc095SDavid du Colombier /* Allow a Type 42 font here, for testing .wrapfont. */
382593dc095SDavid du Colombier if (pfont->FontType == ft_TrueType) {
383593dc095SDavid du Colombier /* Use the CID as the glyph index. */
384593dc095SDavid du Colombier if (op->value.intval < 0 ||
385593dc095SDavid du Colombier op->value.intval >= ((gs_font_type42 *)pfont)->data.numGlyphs
386593dc095SDavid du Colombier )
387593dc095SDavid du Colombier return_error(e_rangecheck);
388593dc095SDavid du Colombier code = (int)op->value.intval;
389593dc095SDavid du Colombier } else
390593dc095SDavid du Colombier #endif
391593dc095SDavid du Colombier {
3923ff48bf5SDavid du Colombier if (pfont->FontType != ft_CID_TrueType)
3933ff48bf5SDavid du Colombier return_error(e_invalidfont);
3943ff48bf5SDavid du Colombier code = z11_CIDMap_proc((gs_font_cid2 *)pfont,
3953ff48bf5SDavid du Colombier (gs_glyph)(gs_min_cid_glyph + op->value.intval));
396593dc095SDavid du Colombier }
3973ff48bf5SDavid du Colombier if (code < 0)
3983ff48bf5SDavid du Colombier return code;
3993ff48bf5SDavid du Colombier make_int(op - 1, code);
4003ff48bf5SDavid du Colombier pop(1);
4013ff48bf5SDavid du Colombier return 0;
4023ff48bf5SDavid du Colombier }
4033ff48bf5SDavid du Colombier
404593dc095SDavid du Colombier /* <Decoding> <TT_cmap> <SubstNWP> <GDBytes> <CIDMap> .fillCIDMap - */
405593dc095SDavid du Colombier private int
zfillCIDMap(i_ctx_t * i_ctx_p)406593dc095SDavid du Colombier zfillCIDMap(i_ctx_t *i_ctx_p)
407593dc095SDavid du Colombier {
408593dc095SDavid du Colombier os_ptr op = osp;
409593dc095SDavid du Colombier ref *Decoding = op - 4, *TT_cmap = op - 3, *SubstNWP = op - 2,
410593dc095SDavid du Colombier *GDBytes = op - 1, *CIDMap = op;
411593dc095SDavid du Colombier int code;
412593dc095SDavid du Colombier
413593dc095SDavid du Colombier check_type(*Decoding, t_dictionary);
414593dc095SDavid du Colombier check_type(*TT_cmap, t_array);
415593dc095SDavid du Colombier check_type(*SubstNWP, t_array);
416593dc095SDavid du Colombier check_type(*GDBytes, t_integer);
417593dc095SDavid du Colombier check_type(*CIDMap, t_array);
418593dc095SDavid du Colombier code = cid_fill_CIDMap(imemory, Decoding, TT_cmap, SubstNWP, GDBytes->value.intval, CIDMap);
419593dc095SDavid du Colombier pop(5);
420593dc095SDavid du Colombier return code;
421593dc095SDavid du Colombier }
422593dc095SDavid du Colombier
4233ff48bf5SDavid du Colombier /* ------ Initialization procedure ------ */
4243ff48bf5SDavid du Colombier
4253ff48bf5SDavid du Colombier const op_def zfcid1_op_defs[] =
4263ff48bf5SDavid du Colombier {
4273ff48bf5SDavid du Colombier {"2.buildfont10", zbuildfont10},
4283ff48bf5SDavid du Colombier {"2.buildfont11", zbuildfont11},
4293ff48bf5SDavid du Colombier {"2.type11mapcid", ztype11mapcid},
430593dc095SDavid du Colombier {"2.fillCIDMap", zfillCIDMap},
4313ff48bf5SDavid du Colombier op_def_end(0)
4323ff48bf5SDavid du Colombier };
433