summaryrefslogtreecommitdiff
path: root/devices
diff options
context:
space:
mode:
authorKen Sharp <ken.sharp@artifex.com>2023-03-09 14:05:47 +0000
committerKen Sharp <ken.sharp@artifex.com>2023-03-09 14:07:23 +0000
commitf00a2966ec40cf9d593e1b6e52f5cd656ae32402 (patch)
tree788652badb53bd202a1722f5d81d03b9b11cdbe8 /devices
parent7c8a46b827063bea9318f30479eb7d6e519970c3 (diff)
downloadghostpdl-f00a2966ec40cf9d593e1b6e52f5cd656ae32402.tar.gz
pdfwrite - Fix missing shading case
Bug #706453 "Element missing while converting pdf from rgb to cmyk using Ghostscript" When converting a shading to an image (for ps2write or certain cases of colour converting shadings with pdfwrite) it is possible that the shading functions only call fill_trapezoid() and not fill_path(). This can result in us reaching dump_converted_image with cvd->mask_is_empty and cvd->path_is_empty both true and we would then not write out the rendered image. Because of the convoluted nature of this code (which I am convinced is sub-optimal!) simply setting either mask_is_empty and/or path_is_empty to false results in incorrect rendering. So here we add a new boolean 'filled_trap' and add a case to deal with that after testing all the other conditions. This results in distinct progressions with ps2write and thee files: /tests_private/comparefiles/Bug689189.pdf /tests_private/comparefiles/Clarke-Tate-Manns-Chinese.ai The file /tests_private/comparefiles/Bug691775.pdf shows diffs that are imperceptible by eye.
Diffstat (limited to 'devices')
-rw-r--r--devices/vector/gdevpdfd.c22
-rw-r--r--devices/vector/gdevpdfx.h1
2 files changed, 22 insertions, 1 deletions
diff --git a/devices/vector/gdevpdfd.c b/devices/vector/gdevpdfd.c
index 96d60ea13..fb55655c9 100644
--- a/devices/vector/gdevpdfd.c
+++ b/devices/vector/gdevpdfd.c
@@ -1,4 +1,4 @@
-/* Copyright (C) 2001-2022 Artifex Software, Inc.
+/* Copyright (C) 2001-2023 Artifex Software, Inc.
All Rights Reserved.
This software is provided AS-IS with no warranty, either express or
@@ -1397,7 +1397,12 @@ pdf_dump_converted_image(gx_device_pdf *pdev, pdf_lcvd_t *cvd, int for_pattern)
stream_puts(pdev->strm, "q\n");
code = write_image_with_clip(pdev, cvd, for_pattern);
stream_puts(pdev->strm, "Q\n");
+ } else if (cvd->filled_trap){
+ stream_puts(pdev->strm, "q\n");
+ code = write_image_with_clip(pdev, cvd, for_pattern);
+ stream_puts(pdev->strm, "Q\n");
}
+ cvd->filled_trap = false;
cvd->mdev.width += cvd->mdev.mapped_x;
cvd->mdev.height += cvd->mdev.mapped_y;
if (code > 0)
@@ -1406,6 +1411,19 @@ pdf_dump_converted_image(gx_device_pdf *pdev, pdf_lcvd_t *cvd, int for_pattern)
return code;
}
static int
+lcvd_fill_trapezoid(gx_device * dev, const gs_fixed_edge * left,
+ const gs_fixed_edge * right, fixed ybot, fixed ytop, bool swap_axes,
+ const gx_device_color * pdevc, gs_logical_operation_t lop)
+{
+ int code = 0;
+ pdf_lcvd_t *cvd = (pdf_lcvd_t *)dev;
+
+ if (cvd->mask != NULL)
+ cvd->filled_trap = true;
+ return gx_default_fill_trapezoid(dev, left, right, ybot, ytop, swap_axes, pdevc, lop);
+}
+
+static int
lcvd_handle_fill_path_as_shading_coverage(gx_device *dev,
const gs_gstate *pgs, gx_path *ppath,
const gx_fill_params *params,
@@ -1539,6 +1557,7 @@ pdf_setup_masked_image_converter(gx_device_pdf *pdev, gs_memory_t *mem, const gs
cvd->path_is_empty = true;
cvd->mask_is_empty = true;
cvd->mask_is_clean = false;
+ cvd->filled_trap = false;
cvd->has_background = false;
cvd->mask = 0;
cvd->write_matrix = true;
@@ -1588,6 +1607,7 @@ pdf_setup_masked_image_converter(gx_device_pdf *pdev, gs_memory_t *mem, const gs
dev_proc(&cvd->mdev, dev_spec_op) = lcvd_dev_spec_op;
dev_proc(&cvd->mdev, fill_path) = lcvd_handle_fill_path_as_shading_coverage;
dev_proc(&cvd->mdev, transform_pixel_region) = lcvd_transform_pixel_region;
+ dev_proc(&cvd->mdev, fill_trapezoid) = lcvd_fill_trapezoid;
cvd->m = *m;
if (write_on_close) {
cvd->mdev.is_open = true;
diff --git a/devices/vector/gdevpdfx.h b/devices/vector/gdevpdfx.h
index e2b7c98d5..c7d564f96 100644
--- a/devices/vector/gdevpdfx.h
+++ b/devices/vector/gdevpdfx.h
@@ -1282,6 +1282,7 @@ typedef struct pdf_lcvd_s {
bool mask_is_empty;
bool path_is_empty;
bool mask_is_clean;
+ bool filled_trap;
bool write_matrix;
bool has_background;
gs_matrix m;