diff options
author | Chris Liddell <chris.liddell@artifex.com> | 2022-06-23 15:36:36 +0100 |
---|---|---|
committer | Chris Liddell <chris.liddell@artifex.com> | 2022-07-04 09:18:56 +0100 |
commit | e16b36bd659f426c41a1ab29bf00c7d4ebfaad7a (patch) | |
tree | cf9dd12674541f9cd52d2acaac0fc32ed6ab3111 | |
parent | 4422012f6b40f0627d3527dba92f3a1ba30017d3 (diff) |
Change how pdfi interacts with FAPI for Truetype fontsghostpdl-9.57.0-test-base-2
In PDF, only symbolic Truetype fonts draw marks from the glyph at GID zero
(the TTF notdef). But the default TTF notdef is an empty rectangle, rather than
the Postscript style non-marking glyph.
The FAPI/Freetype incremental interface integration includes code to spot that
case, and return an empty glyph.
Since PDFs don't do incremental font definitions, the pdfi code simply passed
the TTF into FAPI, and onto Freetype as a complete font, so all the glyph
lookups were handled inside Freetype, not using the incremental interface.
Thus we lost the ability to do that "filtering".
Equally, we don't want to take the time to break down the font and "reassemble"
it as the Postscript interpreter is forced to do.
This implements a hybrid approach where we still pass the font data unchanged
into Freetype, but we still use the incremental interface, allowing that
notdef filtering to happen.
This commit affects a heuristic in freetype which autmatically enables
autohinting, meaning we'll no longer get autohinting in cases where we
previously did. That gives a perceived drop in quality at low resolutions.
Since autohinting can be enabled at the command line, it's not a serious
concern.
-rw-r--r-- | base/fapi_ft.c | 51 | ||||
-rw-r--r-- | base/gxfapi.h | 2 | ||||
-rw-r--r-- | pcl/pl/plfapi.c | 1 | ||||
-rw-r--r-- | pdf/pdf_fapi.c | 43 | ||||
-rw-r--r-- | psi/zfapi.c | 1 | ||||
-rw-r--r-- | xps/xpsfapi.c | 1 |
6 files changed, 71 insertions, 28 deletions
diff --git a/base/fapi_ft.c b/base/fapi_ft.c index 406378bdd..1d04bb309 100644 --- a/base/fapi_ft.c +++ b/base/fapi_ft.c @@ -1277,26 +1277,39 @@ gs_fapi_ft_get_scaled_font(gs_fapi_server * a_server, gs_fapi_font * a_font, /* Get the length of the TrueType data. */ unsigned long ms; - code = a_font->get_long(a_font, gs_fapi_font_feature_TT_size, 0, &ms); - if (code < 0) - return code; - if (ms == 0) - return_error(gs_error_invalidfont); - - open_args.memory_size = (FT_Long)ms; - - /* Load the TrueType data into a single buffer. */ - open_args.memory_base = own_font_data = - FF_alloc(s->ftmemory, open_args.memory_size); - if (!own_font_data) - return_error(gs_error_VMerror); - - own_font_data_len = open_args.memory_size; + if (a_font->retrieve_tt_font != NULL) { + code = a_font->retrieve_tt_font(a_font, &own_font_data, &ms); + if (code == 0) { + data_owned = false; + open_args.memory_base = own_font_data; + open_args.memory_size = own_font_data_len = ms; + } + } + else + code = gs_error_unregistered; - code = a_font->serialize_tt_font(a_font, own_font_data, - open_args.memory_size); - if (code < 0) - return code; + if (code < 0) { + code = a_font->get_long(a_font, gs_fapi_font_feature_TT_size, 0, &ms); + if (code < 0) + return code; + if (ms == 0) + return_error(gs_error_invalidfont); + + open_args.memory_size = (FT_Long)ms; + + /* Load the TrueType data into a single buffer. */ + open_args.memory_base = own_font_data = + FF_alloc(s->ftmemory, open_args.memory_size); + if (!own_font_data) + return_error(gs_error_VMerror); + + own_font_data_len = open_args.memory_size; + + code = a_font->serialize_tt_font(a_font, own_font_data, + open_args.memory_size); + if (code < 0) + return code; + } /* We always load incrementally. */ ft_inc_int = new_inc_int(a_server, a_font); diff --git a/base/gxfapi.h b/base/gxfapi.h index 1ff8018f0..13e21d716 100644 --- a/base/gxfapi.h +++ b/base/gxfapi.h @@ -200,6 +200,8 @@ struct gs_fapi_font_s int (*serialize_tt_font) (gs_fapi_font *ff, void *buf, int buf_size); + int (*retrieve_tt_font) (gs_fapi_font *ff, void **buf, int *buf_size); + int (*get_charstring) (gs_fapi_font *ff, int index, byte *buf, ushort buf_length); int (*get_charstring_name) (gs_fapi_font *ff, int index, byte *buf, ushort buf_length); diff --git a/pcl/pl/plfapi.c b/pcl/pl/plfapi.c index 51f7cb1dd..a905bf6d0 100644 --- a/pcl/pl/plfapi.c +++ b/pcl/pl/plfapi.c @@ -121,6 +121,7 @@ static const gs_fapi_font pl_ff_stub = { NULL, /* get_raw_subr */ pl_fapi_get_glyph, /* get_glyph */ pl_fapi_serialize_tt_font, /* serialize_tt_font */ + NULL, /* retrieve_tt_font */ NULL, /* get_charstring */ NULL, /* get_charstring_name */ pl_get_glyphdirectory_data, /* get_GlyphDirectory_data_ptr */ diff --git a/pdf/pdf_fapi.c b/pdf/pdf_fapi.c index 328c3017d..503064e13 100644 --- a/pdf/pdf_fapi.c +++ b/pdf/pdf_fapi.c @@ -72,6 +72,9 @@ static int pdfi_fapi_serialize_tt_font(gs_fapi_font * ff, void *buf, int buf_size); static int +pdfi_fapi_retrieve_tt_font(gs_fapi_font * ff, void **buf, int *buf_size); + +static int pdfi_fapi_get_charstring(gs_fapi_font *ff, int index, byte *buf, ushort buf_length); static int @@ -132,6 +135,7 @@ static const gs_fapi_font pdfi_ff_stub = { pdfi_fapi_get_raw_subr, /* get_raw_subr */ pdfi_fapi_get_glyph, /* get_glyph */ pdfi_fapi_serialize_tt_font, /* serialize_tt_font */ + pdfi_fapi_retrieve_tt_font, /* retrieve_tt_font */ pdfi_fapi_get_charstring, /* get_charstring */ pdfi_fapi_get_charstring_name, /* get_charstring_name */ pdfi_get_glyphdirectory_data, /* get_GlyphDirectory_data_ptr */ @@ -1110,7 +1114,6 @@ pdfi_fapi_get_glyph(gs_fapi_font * ff, gs_glyph char_code, byte * buf, int buf_l pdf_name *encn; int cstrlen = 0; - /* This should only get called for Postscript-type fonts */ if (ff->is_type1) { if (pbfont->FontType == ft_encrypted) { @@ -1254,7 +1257,16 @@ pdfi_fapi_get_glyph(gs_fapi_font * ff, gs_glyph char_code, byte * buf, int buf_l } } else { - code = gs_error_invalidaccess; + gs_font_type42 *pfont42 = (gs_font_type42 *)pbfont; + gs_glyph_data_t pgd; + + code = pfont42->data.get_outline(pfont42, char_code, &pgd); + cstrlen = pgd.bits.size; + if (code >= 0) { + if (buf && buf_length >= cstrlen) { + memcpy(buf, pgd.bits.data, cstrlen); + } + } } done: if (code < 0) @@ -1270,6 +1282,19 @@ pdfi_fapi_serialize_tt_font(gs_fapi_font * ff, void *buf, int buf_size) } static int +pdfi_fapi_retrieve_tt_font(gs_fapi_font * ff, void **buf, int *buf_size) +{ + gs_font_type42 *pfonttt = (gs_font_type42 *) ff->client_font_data; + pdf_font_truetype *pdfttf = (pdf_font_truetype *)pfonttt->client_data; + + *buf = pdfttf->sfnt.data; + *buf_size = pdfttf->sfnt.size; + + return 0; +} + + +static int pdfi_get_glyphdirectory_data(gs_fapi_font * ff, int char_code, const byte ** ptr) { @@ -1432,6 +1457,7 @@ pdfi_fapi_passfont(pdf_font *font, int subfont, char *fapi_request, char *fapi_id = NULL; int code = 0; gs_string fdata; + gs_string *fdatap = &fdata; gs_font_base *pbfont = (gs_font_base *)font->pfont; gs_fapi_font local_pdf_ff_stub = pdfi_ff_stub; gs_fapi_ttf_cmap_request symbolic_req[GS_FAPI_NUM_TTF_CMAP_REQ] = {{3, 0}, {1, 0}, {3, 1}, {3, 10}, {-1, -1}}; @@ -1443,16 +1469,15 @@ pdfi_fapi_passfont(pdf_font *font, int subfont, char *fapi_request, } if (font->pdfi_font_type == e_pdf_font_truetype) { - fdata.data = ((pdf_font_truetype *)font)->sfnt.data; - fdata.size = ((pdf_font_truetype *)font)->sfnt.size; + fdatap = NULL; } else if (font->pdfi_font_type == e_pdf_cidfont_type2) { - fdata.data = ((pdf_cidfont_type2 *)font)->sfnt.data; - fdata.size = ((pdf_cidfont_type2 *)font)->sfnt.size; + fdatap->data = ((pdf_cidfont_type2 *)font)->sfnt.data; + fdatap->size = ((pdf_cidfont_type2 *)font)->sfnt.size; } else { - fdata.data = font_data; - fdata.size = font_data_len; + fdatap->data = font_data; + fdatap->size = font_data_len; } if (font->pdfi_font_type == e_pdf_font_truetype) { @@ -1469,7 +1494,7 @@ pdfi_fapi_passfont(pdf_font *font, int subfont, char *fapi_request, (gs_font *)pbfont); code = - gs_fapi_passfont((gs_font *)pbfont, subfont, (char *)file_name, &fdata, + gs_fapi_passfont((gs_font *)pbfont, subfont, (char *)file_name, fdatap, (char *)fapi_request, NULL, (char **)&fapi_id, (gs_fapi_get_server_param_callback) pdfi_get_server_param); diff --git a/psi/zfapi.c b/psi/zfapi.c index c1d966645..aa7369a1e 100644 --- a/psi/zfapi.c +++ b/psi/zfapi.c @@ -2269,6 +2269,7 @@ static const gs_fapi_font ps_ff_stub = { FAPI_FF_get_raw_subr, FAPI_FF_get_glyph, FAPI_FF_serialize_tt_font, + NULL, /* retrieve_tt_font */ FAPI_FF_get_charstring, FAPI_FF_get_charstring_name, ps_get_GlyphDirectory_data_ptr, diff --git a/xps/xpsfapi.c b/xps/xpsfapi.c index 5d8ae533a..41083dc2c 100644 --- a/xps/xpsfapi.c +++ b/xps/xpsfapi.c @@ -84,6 +84,7 @@ static const gs_fapi_font pl_ff_stub = { NULL, /* get_raw_subr */ xps_fapi_get_glyph, /* get_glyph */ xps_fapi_serialize_tt_font, /* serialize_tt_font */ + NULL, /* retrieve_tt_font */ NULL, /* get_charstring */ NULL, /* get_charstring_name */ xps_get_glyphdirectory_data, /* get_GlyphDirectory_data_ptr */ |