summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--base/gdevdsha.c2
-rw-r--r--base/gdevp14.c14
-rw-r--r--base/gscolor3.c12
-rw-r--r--base/gsdcolor.h5
-rw-r--r--base/gsdevice.c2
-rw-r--r--base/gsht.c3
-rw-r--r--base/gsptype1.c40
-rw-r--r--base/gxblend1.c22
-rw-r--r--base/gxdcolor.h3
-rw-r--r--base/gxgstate.h13
-rw-r--r--base/gxp1fill.c17
-rw-r--r--base/gxpcmap.c1
-rw-r--r--base/gxpcolor.h1
-rw-r--r--base/lib.mak2
14 files changed, 85 insertions, 52 deletions
diff --git a/base/gdevdsha.c b/base/gdevdsha.c
index 5a5c69bd1..054429871 100644
--- a/base/gdevdsha.c
+++ b/base/gdevdsha.c
@@ -266,8 +266,8 @@ gx_default_fill_linear_color_scanline(gx_device *dev, const gs_fill_attributes *
if (ci1 != ci0) {
si = max(bi, fixed2int(fa->clip->p.x)); /* Must be compatible to the clipping logic. */
ei = min(i, fixed2int_ceiling(fa->clip->q.x)); /* Must be compatible to the clipping logic. */
- ci0 |= tag; /* set tag (may be 0 if the device doesn't use tags) */
if (si < ei) {
+ ci0 |= tag; /* set tag (may be 0 if the device doesn't use tags) */
if (fa->swap_axes) {
code = dev_proc(dev, fill_rectangle)(dev, j, si, 1, ei - si, ci0);
} else {
diff --git a/base/gdevp14.c b/base/gdevp14.c
index 0d757e0c0..ff73d3cf9 100644
--- a/base/gdevp14.c
+++ b/base/gdevp14.c
@@ -274,7 +274,7 @@ static const gx_color_map_procs *
pdf14_dev_spec_op, /* dev_spec_op */\
pdf14_copy_planes, /* copy_planes */\
NULL, /* */\
- NULL, /* set_graphics_type_tag */\
+ gx_forward_set_graphics_type_tag, /* set_graphics_type_tag */\
NULL, /* strip_copy_rop2 */\
NULL, /* strip_tile_rect_devn */\
pdf14_copy_alpha_hl_color /* copy_alpha_hl_color */\
@@ -1183,8 +1183,6 @@ pdf14_pop_transparency_group(gs_gstate *pgs, pdf14_ctx *ctx,
} else {
maskbuf = mask_stack->rc_mask->mask_buf;
}
- if (nos == NULL)
- return_error(gs_error_rangecheck);
/* Sanitise the dirty rectangles, in case some of the drawing routines
* have made them overly large. */
rect_intersect(tos->dirty, tos->rect);
@@ -1748,6 +1746,7 @@ pdf14_get_buffer_information(const gx_device * dev,
if (width <= 0 || height <= 0 || buf->data == NULL)
return 0;
transbuff->n_chan = buf->n_chan;
+ transbuff->has_tags = buf->has_tags;
transbuff->has_shape = buf->has_shape;
transbuff->width = buf->rect.q.x - buf->rect.p.x;
transbuff->height = buf->rect.q.y - buf->rect.p.y;
@@ -1766,7 +1765,7 @@ pdf14_get_buffer_information(const gx_device * dev,
transbuff->planestride = planestride;
transbuff->rowstride = rowstride;
- transbuff->transbytes = gs_alloc_bytes(mem, planestride*buf->n_chan,
+ transbuff->transbytes = gs_alloc_bytes(mem, planestride*(buf->n_chan + buf->has_tags ? 1 : 0),
"pdf14_get_buffer_information");
transbuff->mem = mem;
for (j = 0; j < transbuff->n_chan; j++) {
@@ -5950,7 +5949,8 @@ gs_pdf14_device_push(gs_memory_t *mem, gs_gstate * pgs,
p14dev->color_info.comp_shift[p14dev->color_info.num_components] = p14dev->color_info.depth;
p14dev->color_info.depth += 8;
}
- check_device_separable((gx_device *)p14dev);
+ /* by definition pdf14_encode _is_ standard */
+ p14dev->color_info.separable_and_linear = GX_CINFO_SEP_LIN_STANDARD;
gx_device_fill_in_procs((gx_device *)p14dev);
p14dev->save_get_cmap_procs = pgs->get_cmap_procs;
pgs->get_cmap_procs = pdf14_get_cmap_procs;
@@ -6905,7 +6905,7 @@ send_pdf14trans(gs_gstate * pgs, gx_device * dev,
pdf14_dev_spec_op,\
NULL, /* copy planes */\
NULL, /* get_profile */\
- NULL, /* set_graphics_type_tag */\
+ gx_forward_set_graphics_type_tag, /* set_graphics_type_tag */\
NULL, /* strip_copy_rop2 */\
NULL, /* strip_tile_rect_devn */\
gx_forward_copy_alpha_hl_color\
@@ -7188,7 +7188,7 @@ pdf14_create_clist_device(gs_memory_t *mem, gs_gstate * pgs,
pdev->color_info.comp_shift[pdev->color_info.num_components] = pdev->color_info.depth;
pdev->color_info.depth += 8;
}
- check_device_separable((gx_device *)pdev);
+ pdev->color_info.separable_and_linear = GX_CINFO_SEP_LIN_STANDARD; /* this is the standard */
gx_device_fill_in_procs((gx_device *)pdev);
gs_pdf14_device_copy_params((gx_device *)pdev, target);
gx_device_set_target((gx_device_forward *)pdev, target);
diff --git a/base/gscolor3.c b/base/gscolor3.c
index 6f3cf229b..c7993382e 100644
--- a/base/gscolor3.c
+++ b/base/gscolor3.c
@@ -93,6 +93,12 @@ gs_shfill(gs_gstate * pgs, const gs_shading_t * psh)
if (pcs == NULL)
return_error(gs_error_VMerror);
+ /* make sure the tag gets set correctly */
+ if (pgs->show_gstate == NULL)
+ ensure_tag_is_set(pgs, pgs->device, GS_PATH_TAG); /* NB: may unset_dev_color */
+ else
+ ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
+
pcs->params.pattern.has_base_space = false;
code = pcs->type->remap_color(&cc, pcs, &devc, pgs,
pgs->device, gs_color_select_texture);
@@ -101,12 +107,6 @@ gs_shfill(gs_gstate * pgs, const gs_shading_t * psh)
bool need_path = !dev_proc(dev, dev_spec_op)(dev,
gxdso_pattern_shfill_doesnt_need_path, NULL, 0);
- /* make sure the tag gets set correctly */
- if (pgs->show_gstate == NULL)
- ensure_tag_is_set(pgs, pgs->device, GS_PATH_TAG); /* NB: may unset_dev_color */
- else
- ensure_tag_is_set(pgs, pgs->device, GS_TEXT_TAG); /* NB: may unset_dev_color */
-
if (need_path) {
gx_path cpath;
diff --git a/base/gsdcolor.h b/base/gsdcolor.h
index 5ab803ce3..c74277e1b 100644
--- a/base/gsdcolor.h
+++ b/base/gsdcolor.h
@@ -20,6 +20,7 @@
# define gsdcolor_INCLUDED
#include "gsccolor.h"
+#include "gscms.h" /* for gs_graphics_type_tag_t */
#include "gxarith.h" /* for imod */
#include "gxbitmap.h"
#include "gxhttile.h"
@@ -101,7 +102,7 @@ bool gx_device_color_equal(const gx_device_color *pdevc1,
#define color_is_set(pdc)\
((pdc)->type != gx_dc_type_none)
#define color_unset(pdc)\
- ((pdc)->type = gx_dc_type_none)
+ (((pdc)->type = gx_dc_type_none), ((pdc)->tag = 0))
#define gx_dc_is_null(pdc)\
((pdc)->type == gx_dc_type_null)
@@ -266,6 +267,7 @@ struct gx_device_color_s {
* union, we put the type first.
*/
gx_device_color_type type;
+ gs_graphics_type_tag_t tag; /* value used to set dev_color */
/*
* See the comment above for descriptions of the members. We use
* b_, c_, and p_ member names because some old compilers don't
@@ -375,6 +377,7 @@ struct gx_device_color_s {
struct gx_device_color_saved_s {
gx_device_color_type type;
+ gs_graphics_type_tag_t tag; /* value used to set dev_color */
union _svc {
gx_color_index pure;
struct _svbin {
diff --git a/base/gsdevice.c b/base/gsdevice.c
index 5d64c7bd0..610a6dea4 100644
--- a/base/gsdevice.c
+++ b/base/gsdevice.c
@@ -466,7 +466,7 @@ static void
gs_gstate_update_device(gs_gstate *pgs, gx_device *dev)
{
gx_set_cmap_procs(pgs, dev);
- gx_unset_dev_color(pgs);
+ gx_unset_both_dev_colors(pgs);
}
int
diff --git a/base/gsht.c b/base/gsht.c
index fbc2d18f0..a784eee00 100644
--- a/base/gsht.c
+++ b/base/gsht.c
@@ -1209,8 +1209,7 @@ gx_ht_install(gs_gstate * pgs, const gs_halftone * pht,
new_ht->rc = rc;
}
pgs->halftone = new_ht;
- gx_unset_dev_color(pgs);
- gx_unset_alt_dev_color(pgs);
+ gx_unset_both_dev_colors(pgs);
return 0;
}
diff --git a/base/gsptype1.c b/base/gsptype1.c
index 59cdd7ff4..faa7fdd1f 100644
--- a/base/gsptype1.c
+++ b/base/gsptype1.c
@@ -1587,6 +1587,7 @@ typedef struct tile_trans_clist_info_s {
int rowstride;
int planestride;
int n_chan; /* number of pixel planes including alpha */
+ bool has_tags; /* extra plane for tags */
int width;
int height;
} tile_trans_clist_info_t;
@@ -1717,6 +1718,8 @@ gx_dc_pattern_trans_write_raster(gx_color_tile *ptile, int64_t offset, byte *dat
/* Everything that we need to handle the transparent tile */
size = size_h + ptile->ttrans->n_chan * ptile->ttrans->planestride;
+ if (ptile->ttrans->has_tags)
+ size += ptile->ttrans->planestride;
/* data is sent with NULL if the clist writer just wanted the size */
if (data == NULL) {
@@ -1752,6 +1755,7 @@ gx_dc_pattern_trans_write_raster(gx_color_tile *ptile, int64_t offset, byte *dat
/* Do the transparency information now */
trans_info.height = ptile->ttrans->height;
trans_info.n_chan = ptile->ttrans->n_chan;
+ trans_info.has_tags = ptile->ttrans->has_tags;
trans_info.planestride = ptile->ttrans->planestride;
trans_info.rect.p.x = ptile->ttrans->rect.p.x;
trans_info.rect.p.y = ptile->ttrans->rect.p.y;
@@ -1769,11 +1773,11 @@ gx_dc_pattern_trans_write_raster(gx_color_tile *ptile, int64_t offset, byte *dat
offset1 += sizeof(trans_info);
}
- /* Now do the transparency tile data itself. Note that it may
- be split up in the writing stage if it is large */
+ /* Now do the transparency tile data itself. Note that it may be split up
+ * in the writing stage if it is large. The size include n_chan + the tag
+ * plane if this buffer has_tags. */
/* check if we have written it all */
-
if (offset1 <= size) {
/* Get the most that we can write */
int u = min(size, left);
@@ -1817,10 +1821,10 @@ gx_dc_pattern_write(
/* A special case for writing a known pattern :
Just write the tile id. */
gs_id id = ptile->id; /* Ensure sizeof(gs_id). */
- if_debug2m('?', dev->memory,
- "[v*] Writing trans tile ID into clist, uid = %ld id = %ld \n",
- ptile->uid.id, ptile->id);
- memcpy(dp, &ptile->id, sizeof(id));
+ if_debug2m('?', dev->memory,
+ "[v*] Writing trans tile ID into clist, uid = %ld id = %ld \n",
+ ptile->uid.id, ptile->id);
+ memcpy(dp, &ptile->id, sizeof(id));
*psize = sizeof(gs_id);
return 0;
}
@@ -1828,12 +1832,12 @@ gx_dc_pattern_write(
/* Check if pattern has transparency object
If so then that is what we will stuff in
the clist */
- if (ptile->ttrans != NULL) {
- if_debug2m('?', dev->memory,
- "[v*] Writing trans tile into clist, uid = %ld id = %ld \n",
- ptile->uid.id, ptile->id);
- return gx_dc_pattern_trans_write_raster(ptile, offset, data, psize);
- }
+ if (ptile->ttrans != NULL) {
+ if_debug2m('?', dev->memory,
+ "[v*] Writing trans tile into clist, uid = %ld id = %ld \n",
+ ptile->uid.id, ptile->id);
+ return gx_dc_pattern_trans_write_raster(ptile, offset, data, psize);
+ }
if (ptile->cdev == NULL)
return gx_dc_pattern_write_raster(ptile, offset, data, psize, dev);
@@ -1979,6 +1983,9 @@ gx_dc_pattern_read_trans_buff(gx_color_tile *ptile, int64_t offset,
int data_size;
data_size = trans_pat->planestride * trans_pat->n_chan;
+ if (trans_pat->has_tags)
+ data_size += trans_pat->planestride;
+
/* Allocate the bytes */
if (trans_pat->transbytes == NULL){
trans_pat->transbytes = gs_alloc_bytes(mem, data_size, "gx_dc_pattern_read_raster");
@@ -2102,6 +2109,7 @@ gx_dc_pattern_read(
ptile->ttrans->height = trans_info.height;
ptile->ttrans->n_chan = trans_info.n_chan;
+ ptile->ttrans->has_tags = trans_info.has_tags;
ptile->ttrans->pdev14 = NULL;
ptile->ttrans->planestride = trans_info.planestride;
ptile->ttrans->rect.p.x = trans_info.rect.p.x;
@@ -2111,9 +2119,9 @@ gx_dc_pattern_read(
ptile->ttrans->rowstride = trans_info.rowstride;
ptile->ttrans->width = trans_info.width;
pdevc->type = &gx_dc_pattern_trans;
- if_debug2m('?', pgs->memory,
- "[v*] Reading trans tile from clist into cache, uid = %ld id = %ld \n",
- ptile->uid.id, ptile->id);
+ if_debug2m('?', pgs->memory,
+ "[v*] Reading trans tile from clist into cache, uid = %ld id = %ld \n",
+ ptile->uid.id, ptile->id);
code = gx_dc_pattern_read_trans_buff(ptile, offset1, dp, left, mem);
if (code < 0)
diff --git a/base/gxblend1.c b/base/gxblend1.c
index 72c32ee40..146d5f5bc 100644
--- a/base/gxblend1.c
+++ b/base/gxblend1.c
@@ -346,9 +346,14 @@ pdf14_compose_group(pdf14_buf *tos, pdf14_buf *nos, pdf14_buf *maskbuf,
if ((tos->n_chan == 0) || (nos->n_chan == 0))
return;
rect_merge(nos->dirty, tos->dirty);
- if_debug6m('v', memory,
- "pdf14_pop_transparency_group y0 = %d, y1 = %d, w = %d, alpha = %d, shape = %d, tag = bm = %d\n",
- y0, y1, width, alpha, shape, blend_mode);
+ if (nos->has_tags)
+ if_debug7m('v', memory,
+ "pdf14_pop_transparency_group y0 = %d, y1 = %d, w = %d, alpha = %d, shape = %d, tag = %d, bm = %d\n",
+ y0, y1, width, alpha, shape, dev->graphics_type_tag & ~GS_DEVICE_ENCODES_TAGS, blend_mode);
+ else
+ if_debug6m('v', memory,
+ "pdf14_pop_transparency_group y0 = %d, y1 = %d, w = %d, alpha = %d, shape = %d, bm = %d\n",
+ y0, y1, width, alpha, shape, blend_mode);
if (!nos->has_shape)
nos_shape_offset = 0;
if (!nos->has_tags)
@@ -573,13 +578,6 @@ pdf14_compose_group(pdf14_buf *tos, pdf14_buf *nos, pdf14_buf *maskbuf,
pix_alpha, blend_mode, pblend_procs, pdev,
num_spots);
}
- if (tos_has_tag) {
- if (pix_alpha == 255) {
- nos_ptr[nos_tag_offset] = tos_ptr[tos_tag_offset];
- } else if (pix_alpha != 0) {
- nos_ptr[nos_tag_offset] |= tos_ptr[tos_tag_offset];
- }
- }
}
if (nos_shape_offset) {
nos_ptr[nos_shape_offset] =
@@ -620,6 +618,10 @@ pdf14_compose_group(pdf14_buf *tos, pdf14_buf *nos, pdf14_buf *maskbuf,
nos_ptr[i * nos_planestride] = 255 - nos_pixel[i];
}
}
+ /* tags */
+ if (nos_tag_offset && tos_has_tag) {
+ nos_ptr[nos_tag_offset] |= tos_ptr[tos_tag_offset];
+ }
/* alpha */
nos_ptr[n_chan * nos_planestride] = nos_pixel[n_chan];
diff --git a/base/gxdcolor.h b/base/gxdcolor.h
index b75eb69d9..2d9ff6219 100644
--- a/base/gxdcolor.h
+++ b/base/gxdcolor.h
@@ -314,6 +314,9 @@ int gx_remap_color(gs_gstate *);
color_unset(gs_currentdevicecolor_inline(pgs))
#define gx_unset_alt_dev_color(pgs)\
color_unset(gs_altdevicecolor_inline(pgs))
+#define gx_unset_both_dev_colors(pgs)\
+ (color_unset(gs_currentdevicecolor_inline(pgs)),\
+ color_unset(gs_altdevicecolor_inline(pgs)))
/* Load the halftone cache in preparation for drawing. */
#define gx_color_load_select(pdevc, pgs, dev, select)\
diff --git a/base/gxgstate.h b/base/gxgstate.h
index 1f30de4ba..1e7045bc0 100644
--- a/base/gxgstate.h
+++ b/base/gxgstate.h
@@ -504,14 +504,17 @@ int gs_currentscreenphase_pgs(const gs_gstate *, gs_int_point *, gs_color_select
int gs_swapcolors(gs_gstate *);
void gs_swapcolors_quick(gs_gstate *);
-/* Set the graphics_type_tag iff the requested tag bit is not set, and unset */
-/* the dev_color so that gx_set_dev_color will remap (encode) with the new tag */
+/* Set the graphics_type_tag iff the requested tag bit is not set in the dev_color and */
+/* unset the dev_color so that gx_set_dev_color will remap (encode) with the new tag. */
+/* Also make sure the tag is set in the device so the two remain in sync. */
static inline void ensure_tag_is_set(gs_gstate *pgs, gx_device *dev, gs_graphics_type_tag_t tag)
{
- if ((dev->graphics_type_tag & tag) == 0) {
- if (device_encodes_tags(dev)) {
- gx_unset_dev_color(pgs); /* current dev_color needs update to new tag */
+ if (device_encodes_tags(dev)) {
+ if ((dev->graphics_type_tag & tag) == 0)
dev_proc(dev, set_graphics_type_tag)(dev, tag);
+ if ((pgs->color[0].dev_color->tag & tag) == 0) {
+ gx_unset_dev_color(pgs); /* current dev_color needs update to new tag */
+ pgs->color[0].dev_color->tag = tag; /* after unset, now set it */
}
}
}
diff --git a/base/gxp1fill.c b/base/gxp1fill.c
index cfd1a81fc..c9596a060 100644
--- a/base/gxp1fill.c
+++ b/base/gxp1fill.c
@@ -720,6 +720,7 @@ tile_rect_trans_simple(int xmin, int ymin, int xmax, int ymax,
int mid_copy_width, right_copy_width;
int tile_width = ptile->ttrans->width;
int tile_height = ptile->ttrans->height;
+ int src_planes = fill_trans_buffer->n_chan + (fill_trans_buffer->has_tags ? 1 : 0);
/* Update the bbox in the topmost stack entry to reflect the fact that we
* have drawn into it. FIXME: This makes the groups too large! */
@@ -778,10 +779,12 @@ tile_rect_trans_simple(int xmin, int ymin, int xmax, int ymax,
if (right_copy_width < 0)
right_copy_width = 0;
- for (kk = 0; kk < fill_trans_buffer->n_chan; kk++) {
+ for (kk = 0; kk < src_planes; kk++) {
ptr_out = buff_out + kk * fill_trans_buffer->planestride;
ptr_in = buff_in + kk * ptile->ttrans->planestride;
+ if (fill_trans_buffer->has_shape && kk == fill_trans_buffer->n_chan)
+ ptr_out += fill_trans_buffer->planestride; /* tag plane follows shape plane */
for (jj = 0; jj < h; jj++, ptr_out += fill_trans_buffer->rowstride) {
@@ -843,8 +846,12 @@ tile_rect_trans_blend(int xmin, int ymin, int xmax, int ymax,
int tile_width = ptile->ttrans->width;
int tile_height = ptile->ttrans->height;
int num_chan = ptile->ttrans->n_chan; /* Includes alpha */
+ int tag_offset = fill_trans_buffer->n_chan + (fill_trans_buffer->has_shape ? 1 : 0);
pdf14_device *p14dev = (pdf14_device *) fill_trans_buffer->pdev14;
+ if (fill_trans_buffer->has_tags == 0)
+ tag_offset = 0;
+
/* Update the bbox in the topmost stack entry to reflect the fact that we
* have drawn into it. FIXME: This makes the groups too large! */
if (fill_trans_buffer->dirty->p.x > xmin)
@@ -915,6 +922,14 @@ tile_rect_trans_blend(int xmin, int ymin, int xmax, int ymax,
for (kk = 0; kk < num_chan; kk++) {
*(buff_ptr + kk * fill_trans_buffer->planestride) = dst[kk];
}
+ /* Now handle the blending of the tag. NB: dst tag_offset follows shape */
+ if (tag_offset > 0) {
+ int src_tag = *(tile_ptr + num_chan * ptile->ttrans->planestride);
+ int dst_tag = *(buff_ptr + tag_offset * fill_trans_buffer->planestride);
+
+ dst_tag |= src_tag; /* simple blend combines tags */
+ *(buff_ptr + tag_offset * fill_trans_buffer->planestride) = dst_tag;
+ }
}
}
diff --git a/base/gxpcmap.c b/base/gxpcmap.c
index 7e732795a..082f8b02c 100644
--- a/base/gxpcmap.c
+++ b/base/gxpcmap.c
@@ -332,7 +332,6 @@ gx_pattern_accum_alloc(gs_memory_t * mem, gs_memory_t * storage_memory,
fdev->log2_align_mod = tdev->log2_align_mod;
fdev->pad = tdev->pad;
fdev->is_planar = tdev->is_planar;
- check_device_separable((gx_device *)fdev);
gx_device_forward_fill_in_procs(fdev);
return fdev;
}
diff --git a/base/gxpcolor.h b/base/gxpcolor.h
index 8e4b2077f..248e70383 100644
--- a/base/gxpcolor.h
+++ b/base/gxpcolor.h
@@ -168,6 +168,7 @@ struct gx_pattern_trans_s {
int planestride;
int n_chan; /* number of pixel planes including alpha */
bool has_shape; /* extra plane inserted */
+ bool has_tags; /* and yet another plane for the tag */
int width; /* Complete plane width/height; rect may be a subset of this */
int height;
const pdf14_nonseparable_blending_procs_t *blending_procs;
diff --git a/base/lib.mak b/base/lib.mak
index 46b5ee163..7eb134f07 100644
--- a/base/lib.mak
+++ b/base/lib.mak
@@ -492,7 +492,7 @@ gxband_h=$(GLSRC)gxband.h $(gxclio_h)
gxcdevn_h=$(GLSRC)gxcdevn.h $(gsrefct_h) $(gxcindex_h)
gxchar_h=$(GLSRC)gxchar.h $(gschar_h) $(gxtext_h)
gxchrout_h=$(GLSRC)gxchrout.h
-gsdcolor_h=$(GLSRC)gsdcolor.h $(gsccolor_h)\
+gsdcolor_h=$(GLSRC)gsdcolor.h $(gsccolor_h) $(gscms_h)\
$(gxarith_h) $(gxbitmap_h) $(gxcindex_h) $(gxhttile_h)
gxdcolor_h=$(GLSRC)gxdcolor.h\
$(gscsel_h) $(gsdcolor_h) $(gsropt_h) $(gsstruct_h) $(stdint__h)