1 /***************************************************************************/ 2 /* */ 3 /* ttdriver.c */ 4 /* */ 5 /* TrueType font driver implementation (body). */ 6 /* */ 7 /* Copyright 1996-2001, 2002 by */ 8 /* David Turner, Robert Wilhelm, and Werner Lemberg. */ 9 /* */ 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. */ 15 /* */ 16 /***************************************************************************/ 17 18 19 #include <ft2build.h> 20 #include FT_INTERNAL_DEBUG_H 21 #include FT_INTERNAL_STREAM_H 22 #include FT_INTERNAL_SFNT_H 23 #include FT_TRUETYPE_IDS_H 24 25 #include "ttdriver.h" 26 #include "ttgload.h" 27 28 #include "tterrors.h" 29 30 31 /*************************************************************************/ 32 /* */ 33 /* The macro FT_COMPONENT is used in trace mode. It is an implicit */ 34 /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */ 35 /* messages during execution. */ 36 /* */ 37 #undef FT_COMPONENT 38 #define FT_COMPONENT trace_ttdriver 39 40 41 /*************************************************************************/ 42 /*************************************************************************/ 43 /*************************************************************************/ 44 /**** ****/ 45 /**** ****/ 46 /**** F A C E S ****/ 47 /**** ****/ 48 /**** ****/ 49 /*************************************************************************/ 50 /*************************************************************************/ 51 /*************************************************************************/ 52 53 54 #undef PAIR_TAG 55 #define PAIR_TAG( left, right ) ( ( (FT_ULong)left << 16 ) | \ 56 (FT_ULong)right ) 57 58 59 /*************************************************************************/ 60 /* */ 61 /* <Function> */ 62 /* Get_Kerning */ 63 /* */ 64 /* <Description> */ 65 /* A driver method used to return the kerning vector between two */ 66 /* glyphs of the same face. */ 67 /* */ 68 /* <Input> */ 69 /* face :: A handle to the source face object. */ 70 /* */ 71 /* left_glyph :: The index of the left glyph in the kern pair. */ 72 /* */ 73 /* right_glyph :: The index of the right glyph in the kern pair. */ 74 /* */ 75 /* <Output> */ 76 /* kerning :: The kerning vector. This is in font units for */ 77 /* scalable formats, and in pixels for fixed-sizes */ 78 /* formats. */ 79 /* */ 80 /* <Return> */ 81 /* FreeType error code. 0 means success. */ 82 /* */ 83 /* <Note> */ 84 /* Only horizontal layouts (left-to-right & right-to-left) are */ 85 /* supported by this function. Other layouts, or more sophisticated */ 86 /* kernings, are out of scope of this method (the basic driver */ 87 /* interface is meant to be simple). */ 88 /* */ 89 /* They can be implemented by format-specific interfaces. */ 90 /* */ 91 static FT_Error Get_Kerning(TT_Face face,FT_UInt left_glyph,FT_UInt right_glyph,FT_Vector * kerning)92 Get_Kerning( TT_Face face, 93 FT_UInt left_glyph, 94 FT_UInt right_glyph, 95 FT_Vector* kerning ) 96 { 97 TT_Kern0_Pair pair; 98 99 100 if ( !face ) 101 return TT_Err_Invalid_Face_Handle; 102 103 kerning->x = 0; 104 kerning->y = 0; 105 106 if ( face->kern_pairs ) 107 { 108 /* there are some kerning pairs in this font file! */ 109 FT_ULong search_tag = PAIR_TAG( left_glyph, right_glyph ); 110 FT_Long left, right; 111 112 113 left = 0; 114 right = face->num_kern_pairs - 1; 115 116 while ( left <= right ) 117 { 118 FT_Int middle = left + ( ( right - left ) >> 1 ); 119 FT_ULong cur_pair; 120 121 122 pair = face->kern_pairs + middle; 123 cur_pair = PAIR_TAG( pair->left, pair->right ); 124 125 if ( cur_pair == search_tag ) 126 goto Found; 127 128 if ( cur_pair < search_tag ) 129 left = middle + 1; 130 else 131 right = middle - 1; 132 } 133 } 134 135 Exit: 136 return TT_Err_Ok; 137 138 Found: 139 kerning->x = pair->value; 140 goto Exit; 141 } 142 143 144 #undef PAIR_TAG 145 146 147 /*************************************************************************/ 148 /*************************************************************************/ 149 /*************************************************************************/ 150 /**** ****/ 151 /**** ****/ 152 /**** S I Z E S ****/ 153 /**** ****/ 154 /**** ****/ 155 /*************************************************************************/ 156 /*************************************************************************/ 157 /*************************************************************************/ 158 159 160 /*************************************************************************/ 161 /* */ 162 /* <Function> */ 163 /* Set_Char_Sizes */ 164 /* */ 165 /* <Description> */ 166 /* A driver method used to reset a size's character sizes (horizontal */ 167 /* and vertical) expressed in fractional points. */ 168 /* */ 169 /* <Input> */ 170 /* char_width :: The character width expressed in 26.6 */ 171 /* fractional points. */ 172 /* */ 173 /* char_height :: The character height expressed in 26.6 */ 174 /* fractional points. */ 175 /* */ 176 /* horz_resolution :: The horizontal resolution of the output device. */ 177 /* */ 178 /* vert_resolution :: The vertical resolution of the output device. */ 179 /* */ 180 /* <InOut> */ 181 /* size :: A handle to the target size object. */ 182 /* */ 183 /* <Return> */ 184 /* FreeType error code. 0 means success. */ 185 /* */ 186 static FT_Error Set_Char_Sizes(TT_Size size,FT_F26Dot6 char_width,FT_F26Dot6 char_height,FT_UInt horz_resolution,FT_UInt vert_resolution)187 Set_Char_Sizes( TT_Size size, 188 FT_F26Dot6 char_width, 189 FT_F26Dot6 char_height, 190 FT_UInt horz_resolution, 191 FT_UInt vert_resolution ) 192 { 193 FT_Size_Metrics* metrics = &size->root.metrics; 194 TT_Face face = (TT_Face)size->root.face; 195 FT_Long dim_x, dim_y; 196 197 198 /* This bit flag, when set, indicates that the pixel size must be */ 199 /* truncated to an integer. Nearly all TrueType fonts have this */ 200 /* bit set, as hinting won't work really well otherwise. */ 201 /* */ 202 /* However, for those rare fonts who do not set it, we override */ 203 /* the default computations performed by the base layer. I */ 204 /* really don't know whether this is useful, but hey, that's the */ 205 /* spec :-) */ 206 /* */ 207 if ( ( face->header.Flags & 8 ) == 0 ) 208 { 209 /* Compute pixel sizes in 26.6 units */ 210 dim_x = ( char_width * horz_resolution + 36 ) / 72; 211 dim_y = ( char_height * vert_resolution + 36 ) / 72; 212 213 metrics->x_scale = FT_DivFix( dim_x, face->root.units_per_EM ); 214 metrics->y_scale = FT_DivFix( dim_y, face->root.units_per_EM ); 215 216 metrics->x_ppem = (FT_UShort)( dim_x >> 6 ); 217 metrics->y_ppem = (FT_UShort)( dim_y >> 6 ); 218 } 219 220 size->ttmetrics.valid = FALSE; 221 #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS 222 size->strike_index = 0xFFFF; 223 #endif 224 225 return tt_size_reset( size ); 226 } 227 228 229 /*************************************************************************/ 230 /* */ 231 /* <Function> */ 232 /* Set_Pixel_Sizes */ 233 /* */ 234 /* <Description> */ 235 /* A driver method used to reset a size's character sizes (horizontal */ 236 /* and vertical) expressed in integer pixels. */ 237 /* */ 238 /* <Input> */ 239 /* pixel_width :: The character width expressed in integer pixels. */ 240 /* */ 241 /* pixel_height :: The character height expressed in integer pixels. */ 242 /* */ 243 /* <InOut> */ 244 /* size :: A handle to the target size object. */ 245 /* */ 246 /* <Return> */ 247 /* FreeType error code. 0 means success. */ 248 /* */ 249 static FT_Error Set_Pixel_Sizes(TT_Size size,FT_UInt pixel_width,FT_UInt pixel_height)250 Set_Pixel_Sizes( TT_Size size, 251 FT_UInt pixel_width, 252 FT_UInt pixel_height ) 253 { 254 FT_UNUSED( pixel_width ); 255 FT_UNUSED( pixel_height ); 256 257 /* many things have been pre-computed by the base layer */ 258 259 size->ttmetrics.valid = FALSE; 260 #ifdef TT_CONFIG_OPTION_EMBEDDED_BITMAPS 261 size->strike_index = 0xFFFF; 262 #endif 263 264 return tt_size_reset( size ); 265 } 266 267 268 /*************************************************************************/ 269 /* */ 270 /* <Function> */ 271 /* Load_Glyph */ 272 /* */ 273 /* <Description> */ 274 /* A driver method used to load a glyph within a given glyph slot. */ 275 /* */ 276 /* <Input> */ 277 /* slot :: A handle to the target slot object where the glyph */ 278 /* will be loaded. */ 279 /* */ 280 /* size :: A handle to the source face size at which the glyph */ 281 /* must be scaled, loaded, etc. */ 282 /* */ 283 /* glyph_index :: The index of the glyph in the font file. */ 284 /* */ 285 /* load_flags :: A flag indicating what to load for this glyph. The */ 286 /* FTLOAD_??? constants can be used to control the */ 287 /* glyph loading process (e.g., whether the outline */ 288 /* should be scaled, whether to load bitmaps or not, */ 289 /* whether to hint the outline, etc). */ 290 /* */ 291 /* <Return> */ 292 /* FreeType error code. 0 means success. */ 293 /* */ 294 static FT_Error Load_Glyph(TT_GlyphSlot slot,TT_Size size,FT_UShort glyph_index,FT_Int32 load_flags)295 Load_Glyph( TT_GlyphSlot slot, 296 TT_Size size, 297 FT_UShort glyph_index, 298 FT_Int32 load_flags ) 299 { 300 FT_Error error; 301 302 303 if ( !slot ) 304 return TT_Err_Invalid_Slot_Handle; 305 306 /* check whether we want a scaled outline or bitmap */ 307 if ( !size ) 308 load_flags |= FT_LOAD_NO_SCALE | FT_LOAD_NO_HINTING; 309 310 if ( load_flags & FT_LOAD_NO_SCALE ) 311 size = NULL; 312 313 /* reset the size object if necessary */ 314 if ( size ) 315 { 316 /* these two object must have the same parent */ 317 if ( size->root.face != slot->face ) 318 return TT_Err_Invalid_Face_Handle; 319 320 if ( !size->ttmetrics.valid ) 321 { 322 if ( FT_SET_ERROR( tt_size_reset( size ) ) ) 323 return error; 324 } 325 } 326 327 /* now load the glyph outline if necessary */ 328 error = TT_Load_Glyph( size, slot, glyph_index, load_flags ); 329 330 /* force drop-out mode to 2 - irrelevant now */ 331 /* slot->outline.dropout_mode = 2; */ 332 333 return error; 334 } 335 336 337 /*************************************************************************/ 338 /*************************************************************************/ 339 /*************************************************************************/ 340 /**** ****/ 341 /**** ****/ 342 /**** D R I V E R I N T E R F A C E ****/ 343 /**** ****/ 344 /**** ****/ 345 /*************************************************************************/ 346 /*************************************************************************/ 347 /*************************************************************************/ 348 349 350 static FT_Module_Interface tt_get_interface(TT_Driver driver,const char * tt_interface)351 tt_get_interface( TT_Driver driver, 352 const char* tt_interface ) 353 { 354 FT_Module sfntd = FT_Get_Module( driver->root.root.library, 355 "sfnt" ); 356 SFNT_Service sfnt; 357 358 359 /* only return the default interface from the SFNT module */ 360 if ( sfntd ) 361 { 362 sfnt = (SFNT_Service)( sfntd->clazz->module_interface ); 363 if ( sfnt ) 364 return sfnt->get_interface( FT_MODULE( driver ), tt_interface ); 365 } 366 367 return 0; 368 } 369 370 371 /* The FT_DriverInterface structure is defined in ftdriver.h. */ 372 373 FT_CALLBACK_TABLE_DEF 374 const FT_Driver_ClassRec tt_driver_class = 375 { 376 { 377 ft_module_font_driver | 378 ft_module_driver_scalable | 379 #ifdef TT_CONFIG_OPTION_BYTECODE_INTERPRETER 380 ft_module_driver_has_hinter, 381 #else 382 0, 383 #endif 384 385 sizeof ( TT_DriverRec ), 386 387 "truetype", /* driver name */ 388 0x10000L, /* driver version == 1.0 */ 389 0x20000L, /* driver requires FreeType 2.0 or above */ 390 391 (void*)0, /* driver specific interface */ 392 393 (FT_Module_Constructor)tt_driver_init, 394 (FT_Module_Destructor) tt_driver_done, 395 (FT_Module_Requester) tt_get_interface, 396 }, 397 398 sizeof ( TT_FaceRec ), 399 sizeof ( TT_SizeRec ), 400 sizeof ( FT_GlyphSlotRec ), 401 402 403 (FT_Face_InitFunc) tt_face_init, 404 (FT_Face_DoneFunc) tt_face_done, 405 (FT_Size_InitFunc) tt_size_init, 406 (FT_Size_DoneFunc) tt_size_done, 407 (FT_Slot_InitFunc) 0, 408 (FT_Slot_DoneFunc) 0, 409 410 (FT_Size_ResetPointsFunc) Set_Char_Sizes, 411 (FT_Size_ResetPixelsFunc) Set_Pixel_Sizes, 412 (FT_Slot_LoadFunc) Load_Glyph, 413 414 (FT_Face_GetKerningFunc) Get_Kerning, 415 (FT_Face_AttachFunc) 0, 416 (FT_Face_GetAdvancesFunc) 0 417 }; 418 419 420 /* END */ 421