1 /***************************************************************************/
5 /* OpenType font driver implementation (body). */
7 /* Copyright 1996-2001, 2002 by */
8 /* David Turner, Robert Wilhelm, and Werner Lemberg. */
10 /* This file is part of the FreeType project, and may only be used, */
11 /* modified, and distributed under the terms of the FreeType project */
12 /* license, LICENSE.TXT. By continuing to use, modify, or distribute */
13 /* this file you indicate that you have read the license and */
14 /* understand and accept it fully. */
16 /***************************************************************************/
20 #include FT_FREETYPE_H
21 #include FT_INTERNAL_DEBUG_H
22 #include FT_INTERNAL_STREAM_H
23 #include FT_INTERNAL_SFNT_H
24 #include FT_TRUETYPE_IDS_H
25 #include FT_INTERNAL_POSTSCRIPT_NAMES_H
34 /*************************************************************************/
36 /* The macro FT_COMPONENT is used in trace mode. It is an implicit */
37 /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */
38 /* messages during execution. */
41 #define FT_COMPONENT trace_cffdriver
44 /*************************************************************************/
45 /*************************************************************************/
46 /*************************************************************************/
52 /*************************************************************************/
53 /*************************************************************************/
54 /*************************************************************************/
58 #define PAIR_TAG( left, right ) ( ( (FT_ULong)left << 16 ) | \
62 /*************************************************************************/
68 /* A driver method used to return the kerning vector between two */
69 /* glyphs of the same face. */
72 /* face :: A handle to the source face object. */
74 /* left_glyph :: The index of the left glyph in the kern pair. */
76 /* right_glyph :: The index of the right glyph in the kern pair. */
79 /* kerning :: The kerning vector. This is in font units for */
80 /* scalable formats, and in pixels for fixed-sizes */
84 /* FreeType error code. 0 means success. */
87 /* Only horizontal layouts (left-to-right & right-to-left) are */
88 /* supported by this function. Other layouts, or more sophisticated */
89 /* kernings, are out of scope of this method (the basic driver */
90 /* interface is meant to be simple). */
92 /* They can be implemented by format-specific interfaces. */
95 Get_Kerning( TT_Face face
,
104 return CFF_Err_Invalid_Face_Handle
;
109 if ( face
->kern_pairs
)
111 /* there are some kerning pairs in this font file! */
112 FT_ULong search_tag
= PAIR_TAG( left_glyph
, right_glyph
);
117 right
= face
->num_kern_pairs
- 1;
119 while ( left
<= right
)
121 FT_Int middle
= left
+ ( ( right
- left
) >> 1 );
125 pair
= face
->kern_pairs
+ middle
;
126 cur_pair
= PAIR_TAG( pair
->left
, pair
->right
);
128 if ( cur_pair
== search_tag
)
131 if ( cur_pair
< search_tag
)
142 kerning
->x
= pair
->value
;
150 /*************************************************************************/
156 /* A driver method used to load a glyph within a given glyph slot. */
159 /* slot :: A handle to the target slot object where the glyph */
160 /* will be loaded. */
162 /* size :: A handle to the source face size at which the glyph */
163 /* must be scaled, loaded, etc. */
165 /* glyph_index :: The index of the glyph in the font file. */
167 /* load_flags :: A flag indicating what to load for this glyph. The */
168 /* FTLOAD_??? constants can be used to control the */
169 /* glyph loading process (e.g., whether the outline */
170 /* should be scaled, whether to load bitmaps or not, */
171 /* whether to hint the outline, etc). */
174 /* FreeType error code. 0 means success. */
177 Load_Glyph( CFF_GlyphSlot slot
,
179 FT_UShort glyph_index
,
186 return CFF_Err_Invalid_Slot_Handle
;
188 /* check whether we want a scaled outline or bitmap */
190 load_flags
|= FT_LOAD_NO_SCALE
| FT_LOAD_NO_HINTING
;
192 if ( load_flags
& FT_LOAD_NO_SCALE
)
195 /* reset the size object if necessary */
198 /* these two object must have the same parent */
199 if ( size
->face
!= slot
->root
.face
)
200 return CFF_Err_Invalid_Face_Handle
;
203 /* now load the glyph outline if necessary */
204 error
= CFF_Load_Glyph( slot
, size
, glyph_index
, load_flags
);
206 /* force drop-out mode to 2 - irrelevant now */
207 /* slot->outline.dropout_mode = 2; */
213 /*************************************************************************/
214 /*************************************************************************/
215 /*************************************************************************/
218 /**** C H A R A C T E R M A P P I N G S ****/
221 /*************************************************************************/
222 /*************************************************************************/
223 /*************************************************************************/
226 cff_get_glyph_name( CFF_Face face
,
231 CFF_Font font
= (CFF_Font
)face
->extra
.data
;
232 FT_Memory memory
= FT_FACE_MEMORY( face
);
235 PSNames_Service psnames
;
239 psnames
= (PSNames_Service
)FT_Get_Module_Interface(
240 face
->root
.driver
->root
.library
, "psnames" );
244 FT_ERROR(( "cff_get_glyph_name:" ));
245 FT_ERROR(( " cannot open CFF & CEF fonts\n" ));
247 FT_ERROR(( " without the `PSNames' module\n" ));
248 error
= CFF_Err_Unknown_File_Format
;
252 /* first, locate the sid in the charset table */
253 sid
= font
->charset
.sids
[glyph_index
];
255 /* now, lookup the name itself */
256 gname
= CFF_Get_String( &font
->string_index
, sid
, psnames
);
258 if ( buffer_max
> 0 )
260 FT_UInt len
= ft_strlen( gname
);
263 if ( len
>= buffer_max
)
264 len
= buffer_max
- 1;
266 FT_MEM_COPY( buffer
, gname
, len
);
267 ((FT_Byte
*)buffer
)[len
] = 0;
278 /*************************************************************************/
281 /* cff_get_char_index */
284 /* Uses a charmap to return a given character code's glyph index. */
287 /* charmap :: A handle to the source charmap object. */
288 /* charcode :: The character code. */
291 /* Glyph index. 0 means `undefined character code'. */
294 cff_get_char_index( TT_CharMap charmap
,
302 cmap
= &charmap
->cmap
;
303 face
= (CFF_Face
)charmap
->root
.face
;
305 /* Load table if needed */
308 SFNT_Service sfnt
= (SFNT_Service
)face
->sfnt
;
311 error
= sfnt
->load_charmap( face
, cmap
, face
->root
.stream
);
318 return ( cmap
->get_index
? cmap
->get_index( cmap
, charcode
) : 0 );
322 /*************************************************************************/
325 /* cff_get_next_char */
328 /* Uses a charmap to return the next encoded charcode. */
331 /* charmap :: A handle to the source charmap object. */
332 /* charcode :: The character code. */
335 /* Char code. 0 means `no encoded chars above the given one'. */
338 cff_get_next_char( TT_CharMap charmap
,
346 cmap
= &charmap
->cmap
;
347 face
= (CFF_Face
)charmap
->root
.face
;
349 /* Load table if needed */
352 SFNT_Service sfnt
= (SFNT_Service
)face
->sfnt
;
355 error
= sfnt
->load_charmap( face
, cmap
, face
->root
.stream
);
362 return ( cmap
->get_next_char
? cmap
->get_next_char( cmap
, charcode
)
367 /*************************************************************************/
370 /* cff_get_name_index */
373 /* Uses the psnames module and the CFF font's charset to to return a */
374 /* a given glyph name's glyph index. */
377 /* face :: A handle to the source face object. */
379 /* glyph_name :: The glyph name. */
382 /* Glyph index. 0 means `undefined character code'. */
385 cff_get_name_index( CFF_Face face
,
386 FT_String
* glyph_name
)
390 PSNames_Service psnames
;
391 FT_Memory memory
= FT_FACE_MEMORY( face
);
398 cff
= (CFF_FontRec
*)face
->extra
.data
;
399 charset
= &cff
->charset
;
401 psnames
= (PSNames_Service
)FT_Get_Module_Interface(
402 face
->root
.driver
->root
.library
, "psnames" );
404 for ( i
= 0; i
< cff
->num_glyphs
; i
++ )
406 sid
= charset
->sids
[i
];
409 name
= CFF_Get_Name( &cff
->string_index
, sid
- 391 );
411 name
= (FT_String
*)psnames
->adobe_std_strings( sid
);
413 result
= ft_strcmp( glyph_name
, name
);
426 /*************************************************************************/
427 /*************************************************************************/
428 /*************************************************************************/
431 /**** D R I V E R I N T E R F A C E ****/
434 /*************************************************************************/
435 /*************************************************************************/
436 /*************************************************************************/
438 static FT_Module_Interface
439 cff_get_interface( CFF_Driver driver
,
440 const char* module_interface
)
445 #ifndef FT_CONFIG_OPTION_NO_GLYPH_NAMES
447 if ( ft_strcmp( (const char*)module_interface
, "glyph_name" ) == 0 )
448 return (FT_Module_Interface
)cff_get_glyph_name
;
450 if ( ft_strcmp( (const char*)module_interface
, "name_index" ) == 0 )
451 return (FT_Module_Interface
)cff_get_name_index
;
455 /* we simply pass our request to the `sfnt' module */
456 sfnt
= FT_Get_Module( driver
->root
.root
.library
, "sfnt" );
458 return sfnt
? sfnt
->clazz
->get_interface( sfnt
, module_interface
) : 0;
462 /* The FT_DriverInterface structure is defined in ftdriver.h. */
464 FT_CALLBACK_TABLE_DEF
465 const FT_Driver_ClassRec cff_driver_class
=
467 /* begin with the FT_Module_Class fields */
469 ft_module_font_driver
|
470 ft_module_driver_scalable
|
471 ft_module_driver_has_hinter
,
473 sizeof( CFF_DriverRec
),
478 0, /* module-specific interface */
480 (FT_Module_Constructor
)CFF_Driver_Init
,
481 (FT_Module_Destructor
) CFF_Driver_Done
,
482 (FT_Module_Requester
) cff_get_interface
,
485 /* now the specific driver fields */
486 sizeof( TT_FaceRec
),
487 sizeof( FT_SizeRec
),
488 sizeof( CFF_GlyphSlotRec
),
490 (FT_Face_InitFunc
) CFF_Face_Init
,
491 (FT_Face_DoneFunc
) CFF_Face_Done
,
492 (FT_Size_InitFunc
) CFF_Size_Init
,
493 (FT_Size_DoneFunc
) CFF_Size_Done
,
494 (FT_Slot_InitFunc
) CFF_GlyphSlot_Init
,
495 (FT_Slot_DoneFunc
) CFF_GlyphSlot_Done
,
497 (FT_Size_ResetPointsFunc
) CFF_Size_Reset
,
498 (FT_Size_ResetPixelsFunc
) CFF_Size_Reset
,
500 (FT_Slot_LoadFunc
) Load_Glyph
,
501 (FT_CharMap_CharIndexFunc
)cff_get_char_index
,
503 (FT_Face_GetKerningFunc
) Get_Kerning
,
504 (FT_Face_AttachFunc
) 0,
505 (FT_Face_GetAdvancesFunc
) 0,
507 (FT_CharMap_CharNextFunc
) cff_get_next_char