2 |
- |
1 |
/* Copyright (C) 1989, 1992, 1993, 1994, 1996, 1997, 1998, 1999 Aladdin Enterprises. All rights reserved.
|
|
|
2 |
|
|
|
3 |
This software is provided AS-IS with no warranty, either express or
|
|
|
4 |
implied.
|
|
|
5 |
|
|
|
6 |
This software is distributed under license and may not be copied,
|
|
|
7 |
modified or distributed except as expressly authorized under the terms
|
|
|
8 |
of the license contained in the file LICENSE in this distribution.
|
|
|
9 |
|
|
|
10 |
For more information about licensing, please refer to
|
|
|
11 |
http://www.ghostscript.com/licensing/. For information on
|
|
|
12 |
commercial licensing, go to http://www.artifex.com/licensing/ or
|
|
|
13 |
contact Artifex Software, Inc., 101 Lucas Valley Road #110,
|
|
|
14 |
San Rafael, CA 94903, U.S.A., +1(415)492-9861.
|
|
|
15 |
*/
|
|
|
16 |
|
|
|
17 |
/* $Id: gscolor1.c,v 1.11 2004/08/04 19:36:12 stefan Exp $ */
|
|
|
18 |
/* Level 1 extended color operators for Ghostscript library */
|
|
|
19 |
#include "gx.h"
|
|
|
20 |
#include "gserrors.h"
|
|
|
21 |
#include "gsstruct.h"
|
|
|
22 |
#include "gsutil.h" /* for gs_next_ids */
|
|
|
23 |
#include "gsccolor.h"
|
|
|
24 |
#include "gxcspace.h"
|
|
|
25 |
#include "gxdcconv.h"
|
|
|
26 |
#include "gxdevice.h" /* for gx_color_index */
|
|
|
27 |
#include "gxcmap.h"
|
|
|
28 |
#include "gzstate.h"
|
|
|
29 |
#include "gscolor1.h"
|
|
|
30 |
#include "gscolor2.h"
|
|
|
31 |
#include "gxhttype.h"
|
|
|
32 |
#include "gzht.h"
|
|
|
33 |
|
|
|
34 |
/* Imports from gscolor.c */
|
|
|
35 |
void load_transfer_map(gs_state *, gx_transfer_map *, floatp);
|
|
|
36 |
|
|
|
37 |
/* Imported from gsht.c */
|
|
|
38 |
void gx_set_effective_transfer(gs_state *);
|
|
|
39 |
|
|
|
40 |
/* Force a parameter into the range [0.0..1.0]. */
|
|
|
41 |
#define FORCE_UNIT(p) (p < 0.0 ? 0.0 : p > 1.0 ? 1.0 : p)
|
|
|
42 |
|
|
|
43 |
/* setcmykcolor */
|
|
|
44 |
int
|
|
|
45 |
gs_setcmykcolor(gs_state * pgs, floatp c, floatp m, floatp y, floatp k)
|
|
|
46 |
{
|
|
|
47 |
gs_color_space cs;
|
|
|
48 |
int code;
|
|
|
49 |
|
|
|
50 |
gs_cspace_init_DeviceCMYK(pgs->memory, &cs);
|
|
|
51 |
if ((code = gs_setcolorspace(pgs, &cs)) >= 0) {
|
|
|
52 |
gs_client_color * pcc = pgs->ccolor;
|
|
|
53 |
|
|
|
54 |
cs_adjust_color_count(pgs, -1); /* not strictly necessary */
|
|
|
55 |
pcc->paint.values[0] = FORCE_UNIT(c);
|
|
|
56 |
pcc->paint.values[1] = FORCE_UNIT(m);
|
|
|
57 |
pcc->paint.values[2] = FORCE_UNIT(y);
|
|
|
58 |
pcc->paint.values[3] = FORCE_UNIT(k);
|
|
|
59 |
pcc->pattern = 0; /* for GC */
|
|
|
60 |
gx_unset_dev_color(pgs);
|
|
|
61 |
}
|
|
|
62 |
return code;
|
|
|
63 |
}
|
|
|
64 |
|
|
|
65 |
|
|
|
66 |
/* setblackgeneration */
|
|
|
67 |
/* Remap=0 is used by the interpreter. */
|
|
|
68 |
int
|
|
|
69 |
gs_setblackgeneration(gs_state * pgs, gs_mapping_proc proc)
|
|
|
70 |
{
|
|
|
71 |
return gs_setblackgeneration_remap(pgs, proc, true);
|
|
|
72 |
}
|
|
|
73 |
int
|
|
|
74 |
gs_setblackgeneration_remap(gs_state * pgs, gs_mapping_proc proc, bool remap)
|
|
|
75 |
{
|
|
|
76 |
rc_unshare_struct(pgs->black_generation, gx_transfer_map,
|
|
|
77 |
&st_transfer_map, pgs->memory,
|
|
|
78 |
return_error(gs_error_VMerror),
|
|
|
79 |
"gs_setblackgeneration");
|
|
|
80 |
pgs->black_generation->proc = proc;
|
|
|
81 |
pgs->black_generation->id = gs_next_ids(pgs->memory, 1);
|
|
|
82 |
if (remap) {
|
|
|
83 |
load_transfer_map(pgs, pgs->black_generation, 0.0);
|
|
|
84 |
gx_unset_dev_color(pgs);
|
|
|
85 |
}
|
|
|
86 |
return 0;
|
|
|
87 |
}
|
|
|
88 |
|
|
|
89 |
/* currentblackgeneration */
|
|
|
90 |
gs_mapping_proc
|
|
|
91 |
gs_currentblackgeneration(const gs_state * pgs)
|
|
|
92 |
{
|
|
|
93 |
return pgs->black_generation->proc;
|
|
|
94 |
}
|
|
|
95 |
|
|
|
96 |
/* setundercolorremoval */
|
|
|
97 |
/* Remap=0 is used by the interpreter. */
|
|
|
98 |
int
|
|
|
99 |
gs_setundercolorremoval(gs_state * pgs, gs_mapping_proc proc)
|
|
|
100 |
{
|
|
|
101 |
return gs_setundercolorremoval_remap(pgs, proc, true);
|
|
|
102 |
}
|
|
|
103 |
int
|
|
|
104 |
gs_setundercolorremoval_remap(gs_state * pgs, gs_mapping_proc proc, bool remap)
|
|
|
105 |
{
|
|
|
106 |
rc_unshare_struct(pgs->undercolor_removal, gx_transfer_map,
|
|
|
107 |
&st_transfer_map, pgs->memory,
|
|
|
108 |
return_error(gs_error_VMerror),
|
|
|
109 |
"gs_setundercolorremoval");
|
|
|
110 |
pgs->undercolor_removal->proc = proc;
|
|
|
111 |
pgs->undercolor_removal->id = gs_next_ids(pgs->memory, 1);
|
|
|
112 |
if (remap) {
|
|
|
113 |
load_transfer_map(pgs, pgs->undercolor_removal, -1.0);
|
|
|
114 |
gx_unset_dev_color(pgs);
|
|
|
115 |
}
|
|
|
116 |
return 0;
|
|
|
117 |
}
|
|
|
118 |
|
|
|
119 |
/* currentundercolorremoval */
|
|
|
120 |
gs_mapping_proc
|
|
|
121 |
gs_currentundercolorremoval(const gs_state * pgs)
|
|
|
122 |
{
|
|
|
123 |
return pgs->undercolor_removal->proc;
|
|
|
124 |
}
|
|
|
125 |
|
|
|
126 |
/* setcolortransfer */
|
|
|
127 |
/* Remap=0 is used by the interpreter. */
|
|
|
128 |
int
|
|
|
129 |
gs_setcolortransfer_remap(gs_state * pgs, gs_mapping_proc red_proc,
|
|
|
130 |
gs_mapping_proc green_proc,
|
|
|
131 |
gs_mapping_proc blue_proc,
|
|
|
132 |
gs_mapping_proc gray_proc, bool remap)
|
|
|
133 |
{
|
|
|
134 |
gx_transfer *ptran = &pgs->set_transfer;
|
|
|
135 |
gx_transfer old;
|
|
|
136 |
gs_id new_ids = gs_next_ids(pgs->memory, 4);
|
|
|
137 |
gx_device * dev = pgs->device;
|
|
|
138 |
|
|
|
139 |
old = *ptran;
|
|
|
140 |
rc_unshare_struct(ptran->gray, gx_transfer_map, &st_transfer_map,
|
|
|
141 |
pgs->memory, goto fgray, "gs_setcolortransfer");
|
|
|
142 |
rc_unshare_struct(ptran->red, gx_transfer_map, &st_transfer_map,
|
|
|
143 |
pgs->memory, goto fred, "gs_setcolortransfer");
|
|
|
144 |
rc_unshare_struct(ptran->green, gx_transfer_map, &st_transfer_map,
|
|
|
145 |
pgs->memory, goto fgreen, "gs_setcolortransfer");
|
|
|
146 |
rc_unshare_struct(ptran->blue, gx_transfer_map, &st_transfer_map,
|
|
|
147 |
pgs->memory, goto fblue, "gs_setcolortransfer");
|
|
|
148 |
ptran->gray->proc = gray_proc;
|
|
|
149 |
ptran->gray->id = new_ids;
|
|
|
150 |
ptran->red->proc = red_proc;
|
|
|
151 |
ptran->red->id = new_ids + 1;
|
|
|
152 |
ptran->green->proc = green_proc;
|
|
|
153 |
ptran->green->id = new_ids + 2;
|
|
|
154 |
ptran->blue->proc = blue_proc;
|
|
|
155 |
ptran->blue->id = new_ids + 3;
|
|
|
156 |
ptran->red_component_num =
|
|
|
157 |
gs_color_name_component_number(dev, "Red", 3, ht_type_colorscreen);
|
|
|
158 |
ptran->green_component_num =
|
|
|
159 |
gs_color_name_component_number(dev, "Green", 5, ht_type_colorscreen);
|
|
|
160 |
ptran->blue_component_num =
|
|
|
161 |
gs_color_name_component_number(dev, "Blue", 4, ht_type_colorscreen);
|
|
|
162 |
ptran->gray_component_num =
|
|
|
163 |
gs_color_name_component_number(dev, "Gray", 4, ht_type_colorscreen);
|
|
|
164 |
if (remap) {
|
|
|
165 |
load_transfer_map(pgs, ptran->red, 0.0);
|
|
|
166 |
load_transfer_map(pgs, ptran->green, 0.0);
|
|
|
167 |
load_transfer_map(pgs, ptran->blue, 0.0);
|
|
|
168 |
load_transfer_map(pgs, ptran->gray, 0.0);
|
|
|
169 |
gx_set_effective_transfer(pgs);
|
|
|
170 |
gx_unset_dev_color(pgs);
|
|
|
171 |
} else
|
|
|
172 |
gx_set_effective_transfer(pgs);
|
|
|
173 |
return 0;
|
|
|
174 |
fblue:
|
|
|
175 |
rc_assign(ptran->green, old.green, "setcolortransfer");
|
|
|
176 |
fgreen:
|
|
|
177 |
rc_assign(ptran->red, old.red, "setcolortransfer");
|
|
|
178 |
fred:
|
|
|
179 |
rc_assign(ptran->gray, old.gray, "setcolortransfer");
|
|
|
180 |
fgray:
|
|
|
181 |
return_error(gs_error_VMerror);
|
|
|
182 |
}
|
|
|
183 |
int
|
|
|
184 |
gs_setcolortransfer(gs_state * pgs, gs_mapping_proc red_proc,
|
|
|
185 |
gs_mapping_proc green_proc, gs_mapping_proc blue_proc,
|
|
|
186 |
gs_mapping_proc gray_proc)
|
|
|
187 |
{
|
|
|
188 |
return gs_setcolortransfer_remap(pgs, red_proc, green_proc,
|
|
|
189 |
blue_proc, gray_proc, true);
|
|
|
190 |
}
|
|
|
191 |
|
|
|
192 |
/* currentcolortransfer */
|
|
|
193 |
void
|
|
|
194 |
gs_currentcolortransfer(const gs_state * pgs, gs_mapping_proc procs[4])
|
|
|
195 |
{
|
|
|
196 |
const gx_transfer *ptran = &pgs->set_transfer;
|
|
|
197 |
|
|
|
198 |
procs[0] = ptran->red->proc;
|
|
|
199 |
procs[1] = ptran->green->proc;
|
|
|
200 |
procs[2] = ptran->blue->proc;
|
|
|
201 |
procs[3] = ptran->gray->proc;
|
|
|
202 |
}
|