diff options
-rw-r--r-- | include/mupdf/fitz/colorspace.h | 1 | ||||
-rw-r--r-- | include/mupdf/fitz/glyph-cache.h | 4 | ||||
-rw-r--r-- | include/mupdf/pdf/font.h | 6 | ||||
-rw-r--r-- | include/mupdf/pdf/interpret.h | 2 | ||||
-rw-r--r-- | include/mupdf/pdf/page.h | 5 | ||||
-rw-r--r-- | source/fitz/colorspace.c | 12 | ||||
-rw-r--r-- | source/fitz/font-imp.h | 2 | ||||
-rw-r--r-- | source/fitz/font.c | 6 | ||||
-rw-r--r-- | source/pdf/pdf-op-run.c | 38 | ||||
-rw-r--r-- | source/pdf/pdf-page.c | 114 | ||||
-rw-r--r-- | source/pdf/pdf-run.c | 16 | ||||
-rw-r--r-- | source/pdf/pdf-type3.c | 4 |
12 files changed, 148 insertions, 62 deletions
diff --git a/include/mupdf/fitz/colorspace.h b/include/mupdf/fitz/colorspace.h index 068ec896..7bd87adf 100644 --- a/include/mupdf/fitz/colorspace.h +++ b/include/mupdf/fitz/colorspace.h @@ -204,6 +204,7 @@ fz_buffer *fz_icc_data_from_icc_colorspace(fz_context *ctx, const fz_colorspace fz_default_colorspaces *fz_new_default_colorspaces(fz_context *ctx); fz_default_colorspaces* fz_keep_default_colorspaces(fz_context *ctx, fz_default_colorspaces *default_cs); void fz_drop_default_colorspaces(fz_context *ctx, fz_default_colorspaces *default_cs); +fz_default_colorspaces *fz_clone_default_colorspaces(fz_context *ctx, fz_default_colorspaces *base); /* Do we want to make fz_default_colorspaces public and get rid of these? */ void fz_set_default_gray(fz_context *ctx, fz_default_colorspaces *default_cs, fz_colorspace *cs); diff --git a/include/mupdf/fitz/glyph-cache.h b/include/mupdf/fitz/glyph-cache.h index 100986a8..2a86213b 100644 --- a/include/mupdf/fitz/glyph-cache.h +++ b/include/mupdf/fitz/glyph-cache.h @@ -8,8 +8,8 @@ void fz_purge_glyph_cache(fz_context *ctx); fz_pixmap *fz_render_glyph_pixmap(fz_context *ctx, fz_font*, int, fz_matrix *, const fz_irect *scissor, int aa); -void fz_render_t3_glyph_direct(fz_context *ctx, fz_device *dev, fz_font *font, int gid, const fz_matrix *trm, void *gstate, int nestedDepth); -void fz_prepare_t3_glyph(fz_context *ctx, fz_font *font, int gid, int nestedDepth); +void fz_render_t3_glyph_direct(fz_context *ctx, fz_device *dev, fz_font *font, int gid, const fz_matrix *trm, void *gstate, int nested_depth, fz_default_colorspaces *def_cs); +void fz_prepare_t3_glyph(fz_context *ctx, fz_font *font, int gid, int nested_depth); void fz_dump_glyph_cache_stats(fz_context *ctx); float fz_subpixel_adjust(fz_context *ctx, fz_matrix *ctm, fz_matrix *subpix_ctm, unsigned char *qe, unsigned char *qf); diff --git a/include/mupdf/pdf/font.h b/include/mupdf/pdf/font.h index 51e9cd43..23bc77bf 100644 --- a/include/mupdf/pdf/font.h +++ b/include/mupdf/pdf/font.h @@ -106,8 +106,8 @@ int pdf_font_cid_to_gid(fz_context *ctx, pdf_font_desc *fontdesc, int cid); const unsigned char *pdf_lookup_substitute_font(fz_context *ctx, int mono, int serif, int bold, int italic, int *len); pdf_font_desc *pdf_load_type3_font(fz_context *ctx, pdf_document *doc, pdf_obj *rdb, pdf_obj *obj); -void pdf_load_type3_glyphs(fz_context *ctx, pdf_document *doc, pdf_font_desc *fontdesc, int nestedDepth); -pdf_font_desc *pdf_load_font(fz_context *ctx, pdf_document *doc, pdf_obj *rdb, pdf_obj *obj, int nestedDepth); +void pdf_load_type3_glyphs(fz_context *ctx, pdf_document *doc, pdf_font_desc *fontdesc, int nested_depth); +pdf_font_desc *pdf_load_font(fz_context *ctx, pdf_document *doc, pdf_obj *rdb, pdf_obj *obj, int nested_depth); pdf_font_desc *pdf_load_hail_mary_font(fz_context *ctx, pdf_document *doc); pdf_font_desc *pdf_new_font_desc(fz_context *ctx); @@ -119,7 +119,7 @@ void pdf_print_font(fz_context *ctx, fz_output *out, pdf_font_desc *fontdesc); fz_rect *pdf_measure_text(fz_context *ctx, pdf_font_desc *fontdesc, unsigned char *buf, size_t len, fz_rect *rect); float pdf_text_stride(fz_context *ctx, pdf_font_desc *fontdesc, float fontsize, unsigned char *buf, size_t len, float room, size_t *count); -void pdf_run_glyph(fz_context *ctx, pdf_document *doc, pdf_obj *resources, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nestedDepth); +void pdf_run_glyph(fz_context *ctx, pdf_document *doc, pdf_obj *resources, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nested_depth, fz_default_colorspaces *default_cs); pdf_obj *pdf_add_simple_font(fz_context *ctx, pdf_document *doc, fz_font *font); pdf_obj *pdf_add_cid_font(fz_context *ctx, pdf_document *doc, fz_font *font); diff --git a/include/mupdf/pdf/interpret.h b/include/mupdf/pdf/interpret.h index b069da0a..812b0b92 100644 --- a/include/mupdf/pdf/interpret.h +++ b/include/mupdf/pdf/interpret.h @@ -181,7 +181,7 @@ struct pdf_csi_s 0 for an initial call, and will be incremented in nested calls due to Type 3 fonts. */ -pdf_processor *pdf_new_run_processor(fz_context *ctx, fz_device *dev, const fz_matrix *ctm, const char *usage, pdf_gstate *gstate, int nested); +pdf_processor *pdf_new_run_processor(fz_context *ctx, fz_device *dev, const fz_matrix *ctm, const char *usage, pdf_gstate *gstate, int nested, fz_default_colorspaces *default_cs); /* pdf_new_buffer_processor: Create a buffer processor. This diff --git a/include/mupdf/pdf/page.h b/include/mupdf/pdf/page.h index 02d6dd4e..13f61bfa 100644 --- a/include/mupdf/pdf/page.h +++ b/include/mupdf/pdf/page.h @@ -179,6 +179,11 @@ fz_transition *pdf_page_presentation(fz_context *ctx, pdf_page *page, fz_transit fz_default_colorspaces *pdf_load_default_colorspaces(fz_context *ctx, pdf_document *doc, pdf_page *page); /* + Update default colorspaces for an xobject. +*/ +fz_default_colorspaces *pdf_update_default_colorspaces(fz_context *ctx, fz_default_colorspaces *old_cs, pdf_obj *res); + +/* * Page tree, pages and related objects */ diff --git a/source/fitz/colorspace.c b/source/fitz/colorspace.c index 9d5c93ab..da4a4f29 100644 --- a/source/fitz/colorspace.c +++ b/source/fitz/colorspace.c @@ -3872,6 +3872,18 @@ fz_new_default_colorspaces(fz_context *ctx) } fz_default_colorspaces * +fz_clone_default_colorspaces(fz_context *ctx, fz_default_colorspaces *base) +{ + fz_default_colorspaces *default_cs = fz_malloc_struct(ctx, fz_default_colorspaces); + default_cs->refs = 1; + default_cs->gray = fz_keep_colorspace(ctx, base->gray); + default_cs->rgb = fz_keep_colorspace(ctx, base->rgb); + default_cs->cmyk = fz_keep_colorspace(ctx, base->cmyk); + default_cs->oi = fz_keep_colorspace(ctx, base->oi); + return default_cs; +} + +fz_default_colorspaces * fz_keep_default_colorspaces(fz_context *ctx, fz_default_colorspaces *default_cs) { return fz_keep_imp(ctx, default_cs, &default_cs->refs); diff --git a/source/fitz/font-imp.h b/source/fitz/font-imp.h index 59ae628e..74a25ccf 100644 --- a/source/fitz/font-imp.h +++ b/source/fitz/font-imp.h @@ -19,7 +19,7 @@ struct fz_font_s float *t3widths; /* has 256 entries if used */ unsigned short *t3flags; /* has 256 entries if used */ void *t3doc; /* a pdf_document for the callback */ - void (*t3run)(fz_context *ctx, void *doc, void *resources, fz_buffer *contents, struct fz_device_s *dev, const fz_matrix *ctm, void *gstate, int nestedDepth); + void (*t3run)(fz_context *ctx, void *doc, void *resources, fz_buffer *contents, struct fz_device_s *dev, const fz_matrix *ctm, void *gstate, int nested_depth, fz_default_colorspaces *default_cs); void (*t3freeres)(fz_context *ctx, void *doc, void *resources); fz_rect bbox; /* font bbox is used only for t3 fonts */ diff --git a/source/fitz/font.c b/source/fitz/font.c index 780d6c83..58a42314 100644 --- a/source/fitz/font.c +++ b/source/fitz/font.c @@ -1276,7 +1276,7 @@ fz_prepare_t3_glyph(fz_context *ctx, fz_font *font, int gid, int nested_depth) FZ_DEVFLAG_LINEWIDTH_UNDEFINED; fz_try(ctx) { - font->t3run(ctx, font->t3doc, font->t3resources, contents, dev, &fz_identity, NULL, 0); + font->t3run(ctx, font->t3doc, font->t3resources, contents, dev, &fz_identity, NULL, 0, NULL); fz_close_device(ctx, dev); font->t3flags[gid] = dev->flags; d1_rect = dev->d1_rect; @@ -1418,7 +1418,7 @@ fz_render_t3_glyph(fz_context *ctx, fz_font *font, int gid, const fz_matrix *trm } void -fz_render_t3_glyph_direct(fz_context *ctx, fz_device *dev, fz_font *font, int gid, const fz_matrix *trm, void *gstate, int nested_depth) +fz_render_t3_glyph_direct(fz_context *ctx, fz_device *dev, fz_font *font, int gid, const fz_matrix *trm, void *gstate, int nested_depth, fz_default_colorspaces *def_cs) { fz_matrix ctm; void *contents; @@ -1444,7 +1444,7 @@ fz_render_t3_glyph_direct(fz_context *ctx, fz_device *dev, fz_font *font, int gi } fz_concat(&ctm, &font->t3matrix, trm); - font->t3run(ctx, font->t3doc, font->t3resources, contents, dev, &ctm, gstate, nested_depth); + font->t3run(ctx, font->t3doc, font->t3resources, contents, dev, &ctm, gstate, nested_depth, def_cs); } fz_rect * diff --git a/source/pdf/pdf-op-run.c b/source/pdf/pdf-op-run.c index 324ee32d..2b9b134c 100644 --- a/source/pdf/pdf-op-run.c +++ b/source/pdf/pdf-op-run.c @@ -77,6 +77,8 @@ struct pdf_run_processor_s pdf_processor super; fz_device *dev; + fz_default_colorspaces *default_cs; + int nested_depth; /* path object state */ @@ -948,7 +950,7 @@ pdf_show_char(fz_context *ctx, pdf_run_processor *pr, int cid) * attributes, or type 3 glyphs within type3 glyphs). */ fz_matrix composed; fz_concat(&composed, &trm, &gstate->ctm); - fz_render_t3_glyph_direct(ctx, pr->dev, fontdesc->font, gid, &composed, gstate, pr->nested_depth); + fz_render_t3_glyph_direct(ctx, pr->dev, fontdesc->font, gid, &composed, gstate, pr->nested_depth, pr->default_cs); /* Render text invisibly so that it can still be extracted. */ pr->text_mode = 3; } @@ -1221,6 +1223,7 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf int transparency = 0; pdf_document *doc; fz_colorspace *cs = NULL; + fz_default_colorspaces *saved_def_cs = NULL; /* Avoid infinite recursion */ if (xobj == NULL || pdf_mark_obj(ctx, xobj->obj)) @@ -1231,6 +1234,7 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf fz_var(oldtop); fz_var(oldbot); fz_var(cs); + fz_var(saved_def_cs); gparent_save = pr->gparent; pr->gparent = pr->gtop; @@ -1304,6 +1308,13 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf if (!resources) resources = page_resources; + saved_def_cs = pr->default_cs; + pr->default_cs = NULL; + pr->default_cs = pdf_update_default_colorspaces(ctx, saved_def_cs, resources); + + if (pr->default_cs != saved_def_cs) + fz_set_default_colorspaces(ctx, pr->dev, pr->default_cs); + doc = pdf_get_bound_document(ctx, xobj->obj); oldbot = pr->gbot; @@ -1315,6 +1326,21 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf { fz_drop_colorspace(ctx, cs); + if (saved_def_cs) + { + fz_drop_default_colorspaces(ctx, pr->default_cs); + pr->default_cs = saved_def_cs; + fz_try(ctx) + { + fz_set_default_colorspaces(ctx, pr->dev, pr->default_cs); + } + fz_catch(ctx) + { + /* Postpone the problem */ + strcpy(errmess, fz_caught_message(ctx)); + } + } + /* Undo any gstate mismatches due to the pdf_process_contents call */ if (oldbot != -1) { @@ -1340,6 +1366,8 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf fz_catch(ctx) { /* Postpone the problem */ + if (errmess[0]) + fz_warn(ctx, errmess); strcpy(errmess, fz_caught_message(ctx)); } } @@ -1352,6 +1380,8 @@ pdf_run_xobject(fz_context *ctx, pdf_run_processor *proc, pdf_xobject *xobj, pdf fz_catch(ctx) { /* Postpone the problem */ + if (errmess[0]) + fz_warn(ctx, errmess); strcpy(errmess, fz_caught_message(ctx)); } } @@ -2059,11 +2089,13 @@ pdf_drop_run_processor(fz_context *ctx, pdf_processor *proc) fz_drop_path(ctx, pr->path); fz_drop_text(ctx, pr->text); + fz_drop_default_colorspaces(ctx, pr->default_cs); + fz_free(ctx, pr->gstate); } pdf_processor * -pdf_new_run_processor(fz_context *ctx, fz_device *dev, const fz_matrix *ctm, const char *usage, pdf_gstate *gstate, int nested) +pdf_new_run_processor(fz_context *ctx, fz_device *dev, const fz_matrix *ctm, const char *usage, pdf_gstate *gstate, int nested, fz_default_colorspaces *default_cs) { pdf_run_processor *proc = pdf_new_processor(ctx, sizeof *proc); { @@ -2195,6 +2227,8 @@ pdf_new_run_processor(fz_context *ctx, fz_device *dev, const fz_matrix *ctm, con proc->dev = dev; + proc->default_cs = fz_keep_default_colorspaces(ctx, default_cs); + proc->nested_depth = nested; proc->path = NULL; diff --git a/source/pdf/pdf-page.c b/source/pdf/pdf-page.c index 90f77f1e..5d426455 100644 --- a/source/pdf/pdf-page.c +++ b/source/pdf/pdf-page.c @@ -867,12 +867,66 @@ pdf_new_page(fz_context *ctx, pdf_document *doc) return page; } +static void +pdf_load_default_colorspaces_imp(fz_context *ctx, fz_default_colorspaces *default_cs, pdf_obj *obj) +{ + pdf_obj *cs_obj; + + /* The spec says to ignore any colors we can't understand */ + fz_try(ctx) + { + cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultGray); + if (cs_obj) + { + fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); + fz_set_default_gray(ctx, default_cs, cs); + fz_drop_colorspace(ctx, cs); + } + } + fz_catch(ctx) + { + if (fz_caught(ctx) != FZ_ERROR_TRYLATER) + fz_warn(ctx, "Error while reading DefaultGray: %s", fz_caught_message(ctx)); + } + + fz_try(ctx) + { + cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultRGB); + if (cs_obj) + { + fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); + fz_set_default_rgb(ctx, default_cs, cs); + fz_drop_colorspace(ctx, cs); + } + } + fz_catch(ctx) + { + if (fz_caught(ctx) != FZ_ERROR_TRYLATER) + fz_warn(ctx, "Error while reading DefaultRGB: %s", fz_caught_message(ctx)); + } + + fz_try(ctx) + { + cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultCMYK); + if (cs_obj) + { + fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); + fz_set_default_cmyk(ctx, default_cs, cs); + fz_drop_colorspace(ctx, cs); + } + } + fz_catch(ctx) + { + if (fz_caught(ctx) != FZ_ERROR_TRYLATER) + fz_warn(ctx, "Error while reading DefaultCMYK: %s", fz_caught_message(ctx)); + } +} + fz_default_colorspaces * pdf_load_default_colorspaces(fz_context *ctx, pdf_document *doc, pdf_page *page) { pdf_obj *res; pdf_obj *obj; - pdf_obj *cs_obj; fz_default_colorspaces *default_cs; fz_colorspace *oi; @@ -885,47 +939,7 @@ pdf_load_default_colorspaces(fz_context *ctx, pdf_document *doc, pdf_page *page) res = pdf_page_resources(ctx, page); obj = pdf_dict_get(ctx, res, PDF_NAME_ColorSpace); if (obj) - { - /* The spec says to ignore any colors we can't understand */ - fz_try(ctx) - { - cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultGray); - if (cs_obj) - { - fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); - fz_set_default_gray(ctx, default_cs, cs); - fz_drop_colorspace(ctx, cs); - } - } - fz_catch(ctx) - {} - - fz_try(ctx) - { - cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultRGB); - if (cs_obj) - { - fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); - fz_set_default_rgb(ctx, default_cs, cs); - fz_drop_colorspace(ctx, cs); - } - } - fz_catch(ctx) - {} - - fz_try(ctx) - { - cs_obj = pdf_dict_get(ctx, obj, PDF_NAME_DefaultCMYK); - if (cs_obj) - { - fz_colorspace *cs = pdf_load_colorspace(ctx, cs_obj); - fz_set_default_cmyk(ctx, default_cs, cs); - fz_drop_colorspace(ctx, cs); - } - } - fz_catch(ctx) - {} - } + pdf_load_default_colorspaces_imp(ctx, default_cs, obj); oi = pdf_document_output_intent(ctx, doc); if (oi) @@ -934,6 +948,22 @@ pdf_load_default_colorspaces(fz_context *ctx, pdf_document *doc, pdf_page *page) return default_cs; } +fz_default_colorspaces * +pdf_update_default_colorspaces(fz_context *ctx, fz_default_colorspaces *old_cs, pdf_obj *res) +{ + pdf_obj *obj; + fz_default_colorspaces *new_cs; + + obj = pdf_dict_get(ctx, res, PDF_NAME_ColorSpace); + if (!obj) + return fz_keep_default_colorspaces(ctx, old_cs); + + new_cs = fz_clone_default_colorspaces(ctx, old_cs); + pdf_load_default_colorspaces_imp(ctx, new_cs, obj); + + return new_cs; +} + pdf_page * pdf_load_page(fz_context *ctx, pdf_document *doc, int number) { diff --git a/source/pdf/pdf-run.c b/source/pdf/pdf-run.c index b1de0342..1436e93a 100644 --- a/source/pdf/pdf-run.c +++ b/source/pdf/pdf-run.c @@ -6,25 +6,29 @@ pdf_run_annot_with_usage(fz_context *ctx, pdf_document *doc, pdf_page *page, pdf { fz_matrix local_ctm, page_ctm; fz_rect mediabox; - pdf_processor *proc; + pdf_processor *proc = NULL; fz_default_colorspaces *default_cs; + fz_var(proc); + default_cs = pdf_load_default_colorspaces(ctx, doc, page); if (default_cs) fz_set_default_colorspaces(ctx, dev, default_cs); - fz_drop_default_colorspaces(ctx, default_cs); pdf_page_transform(ctx, page, &mediabox, &page_ctm); fz_concat(&local_ctm, &page_ctm, ctm); - proc = pdf_new_run_processor(ctx, dev, &local_ctm, usage, NULL, 0); fz_try(ctx) { + proc = pdf_new_run_processor(ctx, dev, &local_ctm, usage, NULL, 0, default_cs); pdf_process_annot(ctx, proc, doc, page, annot, cookie); pdf_close_processor(ctx, proc); } fz_always(ctx) + { pdf_drop_processor(ctx, proc); + fz_drop_default_colorspaces(ctx, default_cs); + } fz_catch(ctx) fz_rethrow(ctx); } @@ -76,7 +80,7 @@ pdf_run_page_contents_with_usage(fz_context *ctx, pdf_document *doc, pdf_page *p fz_drop_colorspace(ctx, colorspace); } - proc = pdf_new_run_processor(ctx, dev, &local_ctm, usage, NULL, 0); + proc = pdf_new_run_processor(ctx, dev, &local_ctm, usage, NULL, 0, default_cs); pdf_process_contents(ctx, proc, doc, resources, contents, cookie); pdf_close_processor(ctx, proc); } @@ -204,14 +208,14 @@ pdf_run_page(fz_context *ctx, pdf_page *page, fz_device *dev, const fz_matrix *c } void -pdf_run_glyph(fz_context *ctx, pdf_document *doc, pdf_obj *resources, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nested_depth) +pdf_run_glyph(fz_context *ctx, pdf_document *doc, pdf_obj *resources, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nested_depth, fz_default_colorspaces *default_cs) { pdf_processor *proc; if (nested_depth > 10) fz_throw(ctx, FZ_ERROR_GENERIC, "Too many nestings of Type3 glyphs"); - proc = pdf_new_run_processor(ctx, dev, ctm, "View", gstate, nested_depth+1); + proc = pdf_new_run_processor(ctx, dev, ctm, "View", gstate, nested_depth+1, default_cs); fz_try(ctx) { pdf_process_glyph(ctx, proc, doc, resources, contents); diff --git a/source/pdf/pdf-type3.c b/source/pdf/pdf-type3.c index 074e3c36..f82bb2f0 100644 --- a/source/pdf/pdf-type3.c +++ b/source/pdf/pdf-type3.c @@ -4,9 +4,9 @@ #include "../fitz/font-imp.h" static void -pdf_run_glyph_func(fz_context *ctx, void *doc, void *rdb, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nested_depth) +pdf_run_glyph_func(fz_context *ctx, void *doc, void *rdb, fz_buffer *contents, fz_device *dev, const fz_matrix *ctm, void *gstate, int nested_depth, fz_default_colorspaces *default_cs) { - pdf_run_glyph(ctx, doc, (pdf_obj *)rdb, contents, dev, ctm, gstate, nested_depth); + pdf_run_glyph(ctx, doc, (pdf_obj *)rdb, contents, dev, ctm, gstate, nested_depth, default_cs); } static void |