1 /***************************************************************************/
2 /* */
3 /* t1driver.c */
4 /* */
5 /* Type 1 driver interface (body). */
6 /* */
7 /* Copyright 1996-2018 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 "t1driver.h"
21 #include "t1gload.h"
22 #include "t1load.h"
23
24 #include "t1errors.h"
25
26 #ifndef T1_CONFIG_OPTION_NO_AFM
27 #include "t1afm.h"
28 #endif
29
30 #include FT_INTERNAL_DEBUG_H
31 #include FT_INTERNAL_STREAM_H
32 #include FT_INTERNAL_HASH_H
33 #include FT_INTERNAL_POSTSCRIPT_PROPS_H
34 #include FT_DRIVER_H
35
36 #include FT_SERVICE_MULTIPLE_MASTERS_H
37 #include FT_SERVICE_GLYPH_DICT_H
38 #include FT_SERVICE_FONT_FORMAT_H
39 #include FT_SERVICE_POSTSCRIPT_NAME_H
40 #include FT_SERVICE_POSTSCRIPT_CMAPS_H
41 #include FT_SERVICE_POSTSCRIPT_INFO_H
42 #include FT_SERVICE_PROPERTIES_H
43 #include FT_SERVICE_KERNING_H
44
45
46 /*************************************************************************/
47 /* */
48 /* The macro FT_COMPONENT is used in trace mode. It is an implicit */
49 /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */
50 /* messages during execution. */
51 /* */
52 #undef FT_COMPONENT
53 #define FT_COMPONENT trace_t1driver
54
55 /*
56 * GLYPH DICT SERVICE
57 *
58 */
59
60 static FT_Error
61 t1_get_glyph_name( T1_Face face,
62 FT_UInt glyph_index,
63 FT_Pointer buffer,
64 FT_UInt buffer_max )
65 {
66 FT_STRCPYN( buffer, face->type1.glyph_names[glyph_index], buffer_max );
67
68 return FT_Err_Ok;
69 }
70
71
72 static FT_UInt
73 t1_get_name_index( T1_Face face,
110
111 static const FT_Service_PsFontNameRec t1_service_ps_name =
112 {
113 (FT_PsName_GetFunc)t1_get_ps_name /* get_ps_font_name */
114 };
115
116
117 /*
118 * MULTIPLE MASTERS SERVICE
119 *
120 */
121
122 #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT
123 static const FT_Service_MultiMastersRec t1_service_multi_masters =
124 {
125 (FT_Get_MM_Func) T1_Get_Multi_Master, /* get_mm */
126 (FT_Set_MM_Design_Func) T1_Set_MM_Design, /* set_mm_design */
127 (FT_Set_MM_Blend_Func) T1_Set_MM_Blend, /* set_mm_blend */
128 (FT_Get_MM_Blend_Func) T1_Get_MM_Blend, /* get_mm_blend */
129 (FT_Get_MM_Var_Func) T1_Get_MM_Var, /* get_mm_var */
130 (FT_Set_Var_Design_Func)T1_Set_Var_Design, /* set_var_design */
131 (FT_Get_Var_Design_Func)T1_Get_Var_Design, /* get_var_design */
132 (FT_Set_Instance_Func) T1_Reset_MM_Blend, /* set_instance */
133
134 (FT_Get_Var_Blend_Func) NULL, /* get_var_blend */
135 (FT_Done_Blend_Func) T1_Done_Blend /* done_blend */
136 };
137 #endif
138
139
140 /*
141 * POSTSCRIPT INFO SERVICE
142 *
143 */
144
145 static FT_Error
146 t1_ps_get_font_info( FT_Face face,
147 PS_FontInfoRec* afont_info )
148 {
149 *afont_info = ((T1_Face)face)->type1.font_info;
150
151 return FT_Err_Ok;
152 }
253 break;
254 case 2:
255 val = type1->font_bbox.xMax;
256 break;
257 case 3:
258 val = type1->font_bbox.yMax;
259 break;
260 }
261 *((FT_Fixed *)value) = val;
262 }
263 }
264 break;
265
266 case PS_DICT_PAINT_TYPE:
267 retval = sizeof ( type1->paint_type );
268 if ( value && value_len >= retval )
269 *((FT_Byte *)value) = type1->paint_type;
270 break;
271
272 case PS_DICT_FONT_NAME:
273 retval = ft_strlen( type1->font_name ) + 1;
274 if ( value && value_len >= retval )
275 ft_memcpy( value, (void *)( type1->font_name ), retval );
276 break;
277
278 case PS_DICT_UNIQUE_ID:
279 retval = sizeof ( type1->private_dict.unique_id );
280 if ( value && value_len >= retval )
281 *((FT_Int *)value) = type1->private_dict.unique_id;
282 break;
283
284 case PS_DICT_NUM_CHAR_STRINGS:
285 retval = sizeof ( type1->num_glyphs );
286 if ( value && value_len >= retval )
287 *((FT_Int *)value) = type1->num_glyphs;
288 break;
289
290 case PS_DICT_CHAR_STRING_KEY:
291 if ( idx < (FT_UInt)type1->num_glyphs )
292 {
293 retval = ft_strlen( type1->glyph_names[idx] ) + 1;
294 if ( value && value_len >= retval )
295 {
345
346 if ( type1->subrs_hash )
347 {
348 /* convert subr index to array index */
349 size_t* val = ft_hash_num_lookup( (FT_Int)idx,
350 type1->subrs_hash );
351
352
353 if ( val )
354 {
355 idx = *val;
356 ok = 1;
357 }
358 }
359 else
360 {
361 if ( idx < (FT_UInt)type1->num_subrs )
362 ok = 1;
363 }
364
365 if ( ok )
366 {
367 retval = type1->subrs_len[idx] + 1;
368 if ( value && value_len >= retval )
369 {
370 ft_memcpy( value, (void *)( type1->subrs[idx] ), retval - 1 );
371 ((FT_Char *)value)[retval - 1] = (FT_Char)'\0';
372 }
373 }
374 }
375 break;
376
377 case PS_DICT_STD_HW:
378 retval = sizeof ( type1->private_dict.standard_width[0] );
379 if ( value && value_len >= retval )
380 *((FT_UShort *)value) = type1->private_dict.standard_width[0];
381 break;
382
383 case PS_DICT_STD_VW:
384 retval = sizeof ( type1->private_dict.standard_height[0] );
385 if ( value && value_len >= retval )
542
543 case PS_DICT_UNDERLINE_POSITION:
544 retval = sizeof ( type1->font_info.underline_position );
545 if ( value && value_len >= retval )
546 *((FT_Short *)value) = type1->font_info.underline_position;
547 break;
548
549 case PS_DICT_UNDERLINE_THICKNESS:
550 retval = sizeof ( type1->font_info.underline_thickness );
551 if ( value && value_len >= retval )
552 *((FT_UShort *)value) = type1->font_info.underline_thickness;
553 break;
554
555 case PS_DICT_FS_TYPE:
556 retval = sizeof ( type1->font_extra.fs_type );
557 if ( value && value_len >= retval )
558 *((FT_UShort *)value) = type1->font_extra.fs_type;
559 break;
560
561 case PS_DICT_VERSION:
562 retval = ft_strlen( type1->font_info.version ) + 1;
563 if ( value && value_len >= retval )
564 ft_memcpy( value, (void *)( type1->font_info.version ), retval );
565 break;
566
567 case PS_DICT_NOTICE:
568 retval = ft_strlen( type1->font_info.notice ) + 1;
569 if ( value && value_len >= retval )
570 ft_memcpy( value, (void *)( type1->font_info.notice ), retval );
571 break;
572
573 case PS_DICT_FULL_NAME:
574 retval = ft_strlen( type1->font_info.full_name ) + 1;
575 if ( value && value_len >= retval )
576 ft_memcpy( value, (void *)( type1->font_info.full_name ), retval );
577 break;
578
579 case PS_DICT_FAMILY_NAME:
580 retval = ft_strlen( type1->font_info.family_name ) + 1;
581 if ( value && value_len >= retval )
582 ft_memcpy( value, (void *)( type1->font_info.family_name ), retval );
583 break;
584
585 case PS_DICT_WEIGHT:
586 retval = ft_strlen( type1->font_info.weight ) + 1;
587 if ( value && value_len >= retval )
588 ft_memcpy( value, (void *)( type1->font_info.weight ), retval );
589 break;
590
591 case PS_DICT_ITALIC_ANGLE:
592 retval = sizeof ( type1->font_info.italic_angle );
593 if ( value && value_len >= retval )
594 *((FT_Long *)value) = type1->font_info.italic_angle;
595 break;
596 }
597
598 return retval == 0 ? -1 : (FT_Long)retval;
599 }
600
601
602 static const FT_Service_PsInfoRec t1_service_ps_info =
603 {
604 (PS_GetFontInfoFunc) t1_ps_get_font_info, /* ps_get_font_info */
605 (PS_GetFontExtraFunc) t1_ps_get_font_extra, /* ps_get_font_extra */
606 (PS_HasGlyphNamesFunc) t1_ps_has_glyph_names, /* ps_has_glyph_names */
607 (PS_GetFontPrivateFunc)t1_ps_get_font_private, /* ps_get_font_private */
608 (PS_GetFontValueFunc) t1_ps_get_font_value, /* ps_get_font_value */
648
649 #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT
650 { FT_SERVICE_ID_MULTI_MASTERS, &t1_service_multi_masters },
651 #endif
652 { NULL, NULL }
653 };
654
655
656 FT_CALLBACK_DEF( FT_Module_Interface )
657 Get_Interface( FT_Module module,
658 const FT_String* t1_interface )
659 {
660 FT_UNUSED( module );
661
662 return ft_service_list_lookup( t1_services, t1_interface );
663 }
664
665
666 #ifndef T1_CONFIG_OPTION_NO_AFM
667
668 /*************************************************************************/
669 /* */
670 /* <Function> */
671 /* Get_Kerning */
672 /* */
673 /* <Description> */
674 /* A driver method used to return the kerning vector between two */
675 /* glyphs of the same face. */
676 /* */
677 /* <Input> */
678 /* face :: A handle to the source face object. */
679 /* */
680 /* left_glyph :: The index of the left glyph in the kern pair. */
681 /* */
682 /* right_glyph :: The index of the right glyph in the kern pair. */
683 /* */
684 /* <Output> */
685 /* kerning :: The kerning vector. This is in font units for */
686 /* scalable formats, and in pixels for fixed-sizes */
687 /* formats. */
688 /* */
689 /* <Return> */
690 /* FreeType error code. 0 means success. */
691 /* */
692 /* <Note> */
693 /* Only horizontal layouts (left-to-right & right-to-left) are */
694 /* supported by this function. Other layouts, or more sophisticated */
695 /* kernings are out of scope of this method (the basic driver */
696 /* interface is meant to be simple). */
697 /* */
698 /* They can be implemented by format-specific interfaces. */
699 /* */
700 static FT_Error
701 Get_Kerning( FT_Face t1face, /* T1_Face */
702 FT_UInt left_glyph,
703 FT_UInt right_glyph,
704 FT_Vector* kerning )
705 {
706 T1_Face face = (T1_Face)t1face;
707
708
709 kerning->x = 0;
710 kerning->y = 0;
711
712 if ( face->afm_data )
713 T1_Get_Kerning( (AFM_FontInfo)face->afm_data,
714 left_glyph,
715 right_glyph,
716 kerning );
717
718 return FT_Err_Ok;
719 }
|
1 /****************************************************************************
2 *
3 * t1driver.c
4 *
5 * Type 1 driver interface (body).
6 *
7 * Copyright (C) 1996-2019 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 "t1driver.h"
21 #include "t1gload.h"
22 #include "t1load.h"
23
24 #include "t1errors.h"
25
26 #ifndef T1_CONFIG_OPTION_NO_AFM
27 #include "t1afm.h"
28 #endif
29
30 #include FT_INTERNAL_DEBUG_H
31 #include FT_INTERNAL_STREAM_H
32 #include FT_INTERNAL_HASH_H
33 #include FT_INTERNAL_POSTSCRIPT_PROPS_H
34 #include FT_DRIVER_H
35
36 #include FT_SERVICE_MULTIPLE_MASTERS_H
37 #include FT_SERVICE_GLYPH_DICT_H
38 #include FT_SERVICE_FONT_FORMAT_H
39 #include FT_SERVICE_POSTSCRIPT_NAME_H
40 #include FT_SERVICE_POSTSCRIPT_CMAPS_H
41 #include FT_SERVICE_POSTSCRIPT_INFO_H
42 #include FT_SERVICE_PROPERTIES_H
43 #include FT_SERVICE_KERNING_H
44
45
46 /**************************************************************************
47 *
48 * The macro FT_COMPONENT is used in trace mode. It is an implicit
49 * parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log
50 * messages during execution.
51 */
52 #undef FT_COMPONENT
53 #define FT_COMPONENT t1driver
54
55 /*
56 * GLYPH DICT SERVICE
57 *
58 */
59
60 static FT_Error
61 t1_get_glyph_name( T1_Face face,
62 FT_UInt glyph_index,
63 FT_Pointer buffer,
64 FT_UInt buffer_max )
65 {
66 FT_STRCPYN( buffer, face->type1.glyph_names[glyph_index], buffer_max );
67
68 return FT_Err_Ok;
69 }
70
71
72 static FT_UInt
73 t1_get_name_index( T1_Face face,
110
111 static const FT_Service_PsFontNameRec t1_service_ps_name =
112 {
113 (FT_PsName_GetFunc)t1_get_ps_name /* get_ps_font_name */
114 };
115
116
117 /*
118 * MULTIPLE MASTERS SERVICE
119 *
120 */
121
122 #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT
123 static const FT_Service_MultiMastersRec t1_service_multi_masters =
124 {
125 (FT_Get_MM_Func) T1_Get_Multi_Master, /* get_mm */
126 (FT_Set_MM_Design_Func) T1_Set_MM_Design, /* set_mm_design */
127 (FT_Set_MM_Blend_Func) T1_Set_MM_Blend, /* set_mm_blend */
128 (FT_Get_MM_Blend_Func) T1_Get_MM_Blend, /* get_mm_blend */
129 (FT_Get_MM_Var_Func) T1_Get_MM_Var, /* get_mm_var */
130 (FT_Set_Var_Design_Func) T1_Set_Var_Design, /* set_var_design */
131 (FT_Get_Var_Design_Func) T1_Get_Var_Design, /* get_var_design */
132 (FT_Set_Instance_Func) T1_Reset_MM_Blend, /* set_instance */
133 (FT_Set_MM_WeightVector_Func)T1_Set_MM_WeightVector, /* set_mm_weightvector */
134 (FT_Get_MM_WeightVector_Func)T1_Get_MM_WeightVector, /* get_mm_weightvector */
135
136 (FT_Get_Var_Blend_Func) NULL, /* get_var_blend */
137 (FT_Done_Blend_Func) T1_Done_Blend /* done_blend */
138 };
139 #endif
140
141
142 /*
143 * POSTSCRIPT INFO SERVICE
144 *
145 */
146
147 static FT_Error
148 t1_ps_get_font_info( FT_Face face,
149 PS_FontInfoRec* afont_info )
150 {
151 *afont_info = ((T1_Face)face)->type1.font_info;
152
153 return FT_Err_Ok;
154 }
255 break;
256 case 2:
257 val = type1->font_bbox.xMax;
258 break;
259 case 3:
260 val = type1->font_bbox.yMax;
261 break;
262 }
263 *((FT_Fixed *)value) = val;
264 }
265 }
266 break;
267
268 case PS_DICT_PAINT_TYPE:
269 retval = sizeof ( type1->paint_type );
270 if ( value && value_len >= retval )
271 *((FT_Byte *)value) = type1->paint_type;
272 break;
273
274 case PS_DICT_FONT_NAME:
275 if ( type1->font_name )
276 {
277 retval = ft_strlen( type1->font_name ) + 1;
278 if ( value && value_len >= retval )
279 ft_memcpy( value, (void *)( type1->font_name ), retval );
280 }
281 break;
282
283 case PS_DICT_UNIQUE_ID:
284 retval = sizeof ( type1->private_dict.unique_id );
285 if ( value && value_len >= retval )
286 *((FT_Int *)value) = type1->private_dict.unique_id;
287 break;
288
289 case PS_DICT_NUM_CHAR_STRINGS:
290 retval = sizeof ( type1->num_glyphs );
291 if ( value && value_len >= retval )
292 *((FT_Int *)value) = type1->num_glyphs;
293 break;
294
295 case PS_DICT_CHAR_STRING_KEY:
296 if ( idx < (FT_UInt)type1->num_glyphs )
297 {
298 retval = ft_strlen( type1->glyph_names[idx] ) + 1;
299 if ( value && value_len >= retval )
300 {
350
351 if ( type1->subrs_hash )
352 {
353 /* convert subr index to array index */
354 size_t* val = ft_hash_num_lookup( (FT_Int)idx,
355 type1->subrs_hash );
356
357
358 if ( val )
359 {
360 idx = *val;
361 ok = 1;
362 }
363 }
364 else
365 {
366 if ( idx < (FT_UInt)type1->num_subrs )
367 ok = 1;
368 }
369
370 if ( ok && type1->subrs )
371 {
372 retval = type1->subrs_len[idx] + 1;
373 if ( value && value_len >= retval )
374 {
375 ft_memcpy( value, (void *)( type1->subrs[idx] ), retval - 1 );
376 ((FT_Char *)value)[retval - 1] = (FT_Char)'\0';
377 }
378 }
379 }
380 break;
381
382 case PS_DICT_STD_HW:
383 retval = sizeof ( type1->private_dict.standard_width[0] );
384 if ( value && value_len >= retval )
385 *((FT_UShort *)value) = type1->private_dict.standard_width[0];
386 break;
387
388 case PS_DICT_STD_VW:
389 retval = sizeof ( type1->private_dict.standard_height[0] );
390 if ( value && value_len >= retval )
547
548 case PS_DICT_UNDERLINE_POSITION:
549 retval = sizeof ( type1->font_info.underline_position );
550 if ( value && value_len >= retval )
551 *((FT_Short *)value) = type1->font_info.underline_position;
552 break;
553
554 case PS_DICT_UNDERLINE_THICKNESS:
555 retval = sizeof ( type1->font_info.underline_thickness );
556 if ( value && value_len >= retval )
557 *((FT_UShort *)value) = type1->font_info.underline_thickness;
558 break;
559
560 case PS_DICT_FS_TYPE:
561 retval = sizeof ( type1->font_extra.fs_type );
562 if ( value && value_len >= retval )
563 *((FT_UShort *)value) = type1->font_extra.fs_type;
564 break;
565
566 case PS_DICT_VERSION:
567 if ( type1->font_info.version )
568 {
569 retval = ft_strlen( type1->font_info.version ) + 1;
570 if ( value && value_len >= retval )
571 ft_memcpy( value, (void *)( type1->font_info.version ), retval );
572 }
573 break;
574
575 case PS_DICT_NOTICE:
576 if ( type1->font_info.notice )
577 {
578 retval = ft_strlen( type1->font_info.notice ) + 1;
579 if ( value && value_len >= retval )
580 ft_memcpy( value, (void *)( type1->font_info.notice ), retval );
581 }
582 break;
583
584 case PS_DICT_FULL_NAME:
585 if ( type1->font_info.full_name )
586 {
587 retval = ft_strlen( type1->font_info.full_name ) + 1;
588 if ( value && value_len >= retval )
589 ft_memcpy( value, (void *)( type1->font_info.full_name ), retval );
590 }
591 break;
592
593 case PS_DICT_FAMILY_NAME:
594 if ( type1->font_info.family_name )
595 {
596 retval = ft_strlen( type1->font_info.family_name ) + 1;
597 if ( value && value_len >= retval )
598 ft_memcpy( value, (void *)( type1->font_info.family_name ),
599 retval );
600 }
601 break;
602
603 case PS_DICT_WEIGHT:
604 if ( type1->font_info.weight )
605 {
606 retval = ft_strlen( type1->font_info.weight ) + 1;
607 if ( value && value_len >= retval )
608 ft_memcpy( value, (void *)( type1->font_info.weight ), retval );
609 }
610 break;
611
612 case PS_DICT_ITALIC_ANGLE:
613 retval = sizeof ( type1->font_info.italic_angle );
614 if ( value && value_len >= retval )
615 *((FT_Long *)value) = type1->font_info.italic_angle;
616 break;
617 }
618
619 return retval == 0 ? -1 : (FT_Long)retval;
620 }
621
622
623 static const FT_Service_PsInfoRec t1_service_ps_info =
624 {
625 (PS_GetFontInfoFunc) t1_ps_get_font_info, /* ps_get_font_info */
626 (PS_GetFontExtraFunc) t1_ps_get_font_extra, /* ps_get_font_extra */
627 (PS_HasGlyphNamesFunc) t1_ps_has_glyph_names, /* ps_has_glyph_names */
628 (PS_GetFontPrivateFunc)t1_ps_get_font_private, /* ps_get_font_private */
629 (PS_GetFontValueFunc) t1_ps_get_font_value, /* ps_get_font_value */
669
670 #ifndef T1_CONFIG_OPTION_NO_MM_SUPPORT
671 { FT_SERVICE_ID_MULTI_MASTERS, &t1_service_multi_masters },
672 #endif
673 { NULL, NULL }
674 };
675
676
677 FT_CALLBACK_DEF( FT_Module_Interface )
678 Get_Interface( FT_Module module,
679 const FT_String* t1_interface )
680 {
681 FT_UNUSED( module );
682
683 return ft_service_list_lookup( t1_services, t1_interface );
684 }
685
686
687 #ifndef T1_CONFIG_OPTION_NO_AFM
688
689 /**************************************************************************
690 *
691 * @Function:
692 * Get_Kerning
693 *
694 * @Description:
695 * A driver method used to return the kerning vector between two
696 * glyphs of the same face.
697 *
698 * @Input:
699 * face ::
700 * A handle to the source face object.
701 *
702 * left_glyph ::
703 * The index of the left glyph in the kern pair.
704 *
705 * right_glyph ::
706 * The index of the right glyph in the kern pair.
707 *
708 * @Output:
709 * kerning ::
710 * The kerning vector. This is in font units for
711 * scalable formats, and in pixels for fixed-sizes
712 * formats.
713 *
714 * @Return:
715 * FreeType error code. 0 means success.
716 *
717 * @Note:
718 * Only horizontal layouts (left-to-right & right-to-left) are
719 * supported by this function. Other layouts, or more sophisticated
720 * kernings are out of scope of this method (the basic driver
721 * interface is meant to be simple).
722 *
723 * They can be implemented by format-specific interfaces.
724 */
725 static FT_Error
726 Get_Kerning( FT_Face t1face, /* T1_Face */
727 FT_UInt left_glyph,
728 FT_UInt right_glyph,
729 FT_Vector* kerning )
730 {
731 T1_Face face = (T1_Face)t1face;
732
733
734 kerning->x = 0;
735 kerning->y = 0;
736
737 if ( face->afm_data )
738 T1_Get_Kerning( (AFM_FontInfo)face->afm_data,
739 left_glyph,
740 right_glyph,
741 kerning );
742
743 return FT_Err_Ok;
744 }
|