xref: /plan9/sys/src/cmd/gs/src/gschar.c (revision 7dd7cddf99dd7472612f1413b4da293630e6b1bc)
1*7dd7cddfSDavid du Colombier /* Copyright (C) 1999, 2000 Aladdin Enterprises.  All rights reserved.
2*7dd7cddfSDavid du Colombier 
3*7dd7cddfSDavid du Colombier    This file is part of Aladdin Ghostscript.
4*7dd7cddfSDavid du Colombier 
5*7dd7cddfSDavid du Colombier    Aladdin Ghostscript is distributed with NO WARRANTY OF ANY KIND.  No author
6*7dd7cddfSDavid du Colombier    or distributor accepts any responsibility for the consequences of using it,
7*7dd7cddfSDavid du Colombier    or for whether it serves any particular purpose or works at all, unless he
8*7dd7cddfSDavid du Colombier    or she says so in writing.  Refer to the Aladdin Ghostscript Free Public
9*7dd7cddfSDavid du Colombier    License (the "License") for full details.
10*7dd7cddfSDavid du Colombier 
11*7dd7cddfSDavid du Colombier    Every copy of Aladdin Ghostscript must include a copy of the License,
12*7dd7cddfSDavid du Colombier    normally in a plain ASCII text file named PUBLIC.  The License grants you
13*7dd7cddfSDavid du Colombier    the right to copy, modify and redistribute Aladdin Ghostscript, but only
14*7dd7cddfSDavid du Colombier    under certain conditions described in the License.  Among other things, the
15*7dd7cddfSDavid du Colombier    License requires that the copyright notice and this notice be preserved on
16*7dd7cddfSDavid du Colombier    all copies.
17*7dd7cddfSDavid du Colombier  */
18*7dd7cddfSDavid du Colombier 
19*7dd7cddfSDavid du Colombier /*$Id: gschar.c,v 1.2 2000/03/10 04:41:47 lpd Exp $ */
20*7dd7cddfSDavid du Colombier /* Character writing "operators" for Ghostscript library */
21*7dd7cddfSDavid du Colombier #include "gx.h"
22*7dd7cddfSDavid du Colombier #include "gserrors.h"
23*7dd7cddfSDavid du Colombier #include "gsstruct.h"
24*7dd7cddfSDavid du Colombier #include "gsmatrix.h"		/* for gscoord.h */
25*7dd7cddfSDavid du Colombier #include "gscoord.h"		/* for gs_idtransform */
26*7dd7cddfSDavid du Colombier #include "gzstate.h"
27*7dd7cddfSDavid du Colombier #include "gxdevice.h"
28*7dd7cddfSDavid du Colombier #include "gxdevmem.h"
29*7dd7cddfSDavid du Colombier #include "gxchar.h"
30*7dd7cddfSDavid du Colombier #include "gxfont.h"
31*7dd7cddfSDavid du Colombier 
32*7dd7cddfSDavid du Colombier /* Forward declarations */
33*7dd7cddfSDavid du Colombier private int show_n_begin(P4(gs_show_enum *penum, gs_state *pgs, int code,
34*7dd7cddfSDavid du Colombier 			    gs_text_enum_t *pte));
35*7dd7cddfSDavid du Colombier 
36*7dd7cddfSDavid du Colombier /* Structure descriptors */
37*7dd7cddfSDavid du Colombier extern_st(st_gs_show_enum);
38*7dd7cddfSDavid du Colombier 
39*7dd7cddfSDavid du Colombier /* ------ String writing operators ------ */
40*7dd7cddfSDavid du Colombier 
41*7dd7cddfSDavid du Colombier /* Free the contents of a show enumerator. */
42*7dd7cddfSDavid du Colombier void
43*7dd7cddfSDavid du Colombier gs_show_enum_release(gs_show_enum * penum, gs_memory_t * emem)
44*7dd7cddfSDavid du Colombier {
45*7dd7cddfSDavid du Colombier     if (penum->text.operation)	/* otherwise, never initialized */
46*7dd7cddfSDavid du Colombier 	penum->procs->release((gs_text_enum_t *)penum, "gs_show_enum_release");
47*7dd7cddfSDavid du Colombier     if (emem != 0)
48*7dd7cddfSDavid du Colombier 	gs_free_object(emem, penum, "gs_show_enum_release");
49*7dd7cddfSDavid du Colombier }
50*7dd7cddfSDavid du Colombier 
51*7dd7cddfSDavid du Colombier /* show[_n] */
52*7dd7cddfSDavid du Colombier int
53*7dd7cddfSDavid du Colombier gs_show_n_init(gs_show_enum * penum, gs_state * pgs,
54*7dd7cddfSDavid du Colombier 	       const char *str, uint size)
55*7dd7cddfSDavid du Colombier {
56*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
57*7dd7cddfSDavid du Colombier     int code = gs_show_begin(pgs, (const byte *)str, size, pgs->memory, &pte);
58*7dd7cddfSDavid du Colombier 
59*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
60*7dd7cddfSDavid du Colombier }
61*7dd7cddfSDavid du Colombier 
62*7dd7cddfSDavid du Colombier /* ashow[_n] */
63*7dd7cddfSDavid du Colombier int
64*7dd7cddfSDavid du Colombier gs_ashow_n_init(gs_show_enum * penum, gs_state * pgs,
65*7dd7cddfSDavid du Colombier 		floatp ax, floatp ay, const char *str, uint size)
66*7dd7cddfSDavid du Colombier {
67*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
68*7dd7cddfSDavid du Colombier     int code = gs_ashow_begin(pgs, ax, ay, (const byte *)str, size,
69*7dd7cddfSDavid du Colombier 			      pgs->memory, &pte);
70*7dd7cddfSDavid du Colombier 
71*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
72*7dd7cddfSDavid du Colombier }
73*7dd7cddfSDavid du Colombier 
74*7dd7cddfSDavid du Colombier /* widthshow[_n] */
75*7dd7cddfSDavid du Colombier int
76*7dd7cddfSDavid du Colombier gs_widthshow_n_init(gs_show_enum * penum, gs_state * pgs,
77*7dd7cddfSDavid du Colombier 		    floatp cx, floatp cy, gs_char chr,
78*7dd7cddfSDavid du Colombier 		    const char *str, uint size)
79*7dd7cddfSDavid du Colombier {
80*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
81*7dd7cddfSDavid du Colombier     int code = gs_widthshow_begin(pgs, cx, cy, chr, (const byte *)str, size,
82*7dd7cddfSDavid du Colombier 				  pgs->memory, &pte);
83*7dd7cddfSDavid du Colombier 
84*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
85*7dd7cddfSDavid du Colombier }
86*7dd7cddfSDavid du Colombier 
87*7dd7cddfSDavid du Colombier /* awidthshow[_n] */
88*7dd7cddfSDavid du Colombier int
89*7dd7cddfSDavid du Colombier gs_awidthshow_n_init(gs_show_enum * penum, gs_state * pgs,
90*7dd7cddfSDavid du Colombier 		     floatp cx, floatp cy, gs_char chr, floatp ax, floatp ay,
91*7dd7cddfSDavid du Colombier 		     const char *str, uint size)
92*7dd7cddfSDavid du Colombier {
93*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
94*7dd7cddfSDavid du Colombier     int code = gs_awidthshow_begin(pgs, cx, cy, chr, ax, ay,
95*7dd7cddfSDavid du Colombier 				   (const byte *)str, size, pgs->memory, &pte);
96*7dd7cddfSDavid du Colombier 
97*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
98*7dd7cddfSDavid du Colombier }
99*7dd7cddfSDavid du Colombier 
100*7dd7cddfSDavid du Colombier /* kshow[_n] */
101*7dd7cddfSDavid du Colombier int
102*7dd7cddfSDavid du Colombier gs_kshow_n_init(gs_show_enum * penum,
103*7dd7cddfSDavid du Colombier 		gs_state * pgs, const char *str, uint size)
104*7dd7cddfSDavid du Colombier {
105*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
106*7dd7cddfSDavid du Colombier     int code;
107*7dd7cddfSDavid du Colombier 
108*7dd7cddfSDavid du Colombier     switch (pgs->font->FontType) {
109*7dd7cddfSDavid du Colombier     case ft_composite:
110*7dd7cddfSDavid du Colombier     case ft_CID_encrypted:
111*7dd7cddfSDavid du Colombier     case ft_CID_user_defined:
112*7dd7cddfSDavid du Colombier     case ft_CID_TrueType:
113*7dd7cddfSDavid du Colombier     case ft_CID_bitmap:
114*7dd7cddfSDavid du Colombier 	return_error(gs_error_invalidfont);
115*7dd7cddfSDavid du Colombier     default:
116*7dd7cddfSDavid du Colombier 	break;
117*7dd7cddfSDavid du Colombier     }
118*7dd7cddfSDavid du Colombier     code = gs_kshow_begin(pgs, (const byte *)str, size, pgs->memory, &pte);
119*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
120*7dd7cddfSDavid du Colombier }
121*7dd7cddfSDavid du Colombier 
122*7dd7cddfSDavid du Colombier /* xyshow[_n] */
123*7dd7cddfSDavid du Colombier int
124*7dd7cddfSDavid du Colombier gs_xyshow_n_init(gs_show_enum * penum,
125*7dd7cddfSDavid du Colombier 		 gs_state * pgs, const char *str, uint size)
126*7dd7cddfSDavid du Colombier {
127*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
128*7dd7cddfSDavid du Colombier     int code = gs_xyshow_begin(pgs, (const byte *)str, size, NULL, NULL, 0,
129*7dd7cddfSDavid du Colombier 			       pgs->memory, &pte);
130*7dd7cddfSDavid du Colombier 
131*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
132*7dd7cddfSDavid du Colombier }
133*7dd7cddfSDavid du Colombier 
134*7dd7cddfSDavid du Colombier /* glyphshow */
135*7dd7cddfSDavid du Colombier int
136*7dd7cddfSDavid du Colombier gs_glyphshow_init(gs_show_enum * penum, gs_state * pgs, gs_glyph glyph)
137*7dd7cddfSDavid du Colombier {
138*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
139*7dd7cddfSDavid du Colombier     int code = gs_glyphshow_begin(pgs, glyph, pgs->memory, &pte);
140*7dd7cddfSDavid du Colombier 
141*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
142*7dd7cddfSDavid du Colombier }
143*7dd7cddfSDavid du Colombier int
144*7dd7cddfSDavid du Colombier gs_glyphpath_init(gs_show_enum * penum, gs_state * pgs, gs_glyph glyph,
145*7dd7cddfSDavid du Colombier 		  bool stroke_path)
146*7dd7cddfSDavid du Colombier {
147*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
148*7dd7cddfSDavid du Colombier     int code = gs_glyphpath_begin(pgs, glyph, stroke_path, pgs->memory, &pte);
149*7dd7cddfSDavid du Colombier 
150*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
151*7dd7cddfSDavid du Colombier }
152*7dd7cddfSDavid du Colombier int
153*7dd7cddfSDavid du Colombier gs_glyphwidth_init(gs_show_enum * penum, gs_state * pgs, gs_glyph glyph)
154*7dd7cddfSDavid du Colombier {
155*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
156*7dd7cddfSDavid du Colombier     int code = gs_glyphwidth_begin(pgs, glyph, pgs->memory, &pte);
157*7dd7cddfSDavid du Colombier 
158*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
159*7dd7cddfSDavid du Colombier }
160*7dd7cddfSDavid du Colombier 
161*7dd7cddfSDavid du Colombier /* ------ Related operators ------ */
162*7dd7cddfSDavid du Colombier 
163*7dd7cddfSDavid du Colombier /* cshow[_n] */
164*7dd7cddfSDavid du Colombier int
165*7dd7cddfSDavid du Colombier gs_cshow_n_init(gs_show_enum * penum,
166*7dd7cddfSDavid du Colombier 		gs_state * pgs, const char *str, uint size)
167*7dd7cddfSDavid du Colombier {
168*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
169*7dd7cddfSDavid du Colombier     int code = gs_cshow_begin(pgs, (const byte *)str, size, pgs->memory, &pte);
170*7dd7cddfSDavid du Colombier 
171*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
172*7dd7cddfSDavid du Colombier }
173*7dd7cddfSDavid du Colombier 
174*7dd7cddfSDavid du Colombier /* stringwidth[_n] */
175*7dd7cddfSDavid du Colombier int
176*7dd7cddfSDavid du Colombier gs_stringwidth_n_init(gs_show_enum * penum, gs_state * pgs,
177*7dd7cddfSDavid du Colombier 		      const char *str, uint size)
178*7dd7cddfSDavid du Colombier {
179*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
180*7dd7cddfSDavid du Colombier     int code = gs_stringwidth_begin(pgs, (const byte *)str, size,
181*7dd7cddfSDavid du Colombier 				    pgs->memory, &pte);
182*7dd7cddfSDavid du Colombier 
183*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
184*7dd7cddfSDavid du Colombier }
185*7dd7cddfSDavid du Colombier 
186*7dd7cddfSDavid du Colombier /* charpath[_n] */
187*7dd7cddfSDavid du Colombier int
188*7dd7cddfSDavid du Colombier gs_charpath_n_init(gs_show_enum * penum, gs_state * pgs,
189*7dd7cddfSDavid du Colombier 		   const char *str, uint size, bool stroke_path)
190*7dd7cddfSDavid du Colombier {
191*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
192*7dd7cddfSDavid du Colombier     int code = gs_charpath_begin(pgs, (const byte *)str, size, stroke_path,
193*7dd7cddfSDavid du Colombier 				 pgs->memory, &pte);
194*7dd7cddfSDavid du Colombier 
195*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
196*7dd7cddfSDavid du Colombier }
197*7dd7cddfSDavid du Colombier 
198*7dd7cddfSDavid du Colombier /* charboxpath[_n] */
199*7dd7cddfSDavid du Colombier int
200*7dd7cddfSDavid du Colombier gs_charboxpath_n_init(gs_show_enum * penum, gs_state * pgs,
201*7dd7cddfSDavid du Colombier 		      const char *str, uint size, bool use_boxes)
202*7dd7cddfSDavid du Colombier {
203*7dd7cddfSDavid du Colombier     gs_text_enum_t *pte;
204*7dd7cddfSDavid du Colombier     int code = gs_charboxpath_begin(pgs, (const byte *)str, size, use_boxes,
205*7dd7cddfSDavid du Colombier 				    pgs->memory, &pte);
206*7dd7cddfSDavid du Colombier 
207*7dd7cddfSDavid du Colombier     return show_n_begin(penum, pgs, code, pte);
208*7dd7cddfSDavid du Colombier }
209*7dd7cddfSDavid du Colombier 
210*7dd7cddfSDavid du Colombier /* ------ Width/cache operators ------ */
211*7dd7cddfSDavid du Colombier 
212*7dd7cddfSDavid du Colombier /* setcachedevice */
213*7dd7cddfSDavid du Colombier /* The elements of pw are: wx, wy, llx, lly, urx, ury. */
214*7dd7cddfSDavid du Colombier /* Note that this returns 1 if we just set up the cache device. */
215*7dd7cddfSDavid du Colombier int
216*7dd7cddfSDavid du Colombier gs_setcachedevice_double(gs_show_enum *penum, gs_state *pgs, const double *pw)
217*7dd7cddfSDavid du Colombier {
218*7dd7cddfSDavid du Colombier     if (penum->pgs != pgs)
219*7dd7cddfSDavid du Colombier 	return_error(gs_error_rangecheck);
220*7dd7cddfSDavid du Colombier     return gs_text_setcachedevice((gs_text_enum_t *)penum, pw);
221*7dd7cddfSDavid du Colombier }
222*7dd7cddfSDavid du Colombier /* The _float procedure is strictly for backward compatibility. */
223*7dd7cddfSDavid du Colombier int
224*7dd7cddfSDavid du Colombier gs_setcachedevice_float(gs_show_enum * penum, gs_state * pgs, const float *pw)
225*7dd7cddfSDavid du Colombier {
226*7dd7cddfSDavid du Colombier     double w[6];
227*7dd7cddfSDavid du Colombier     int i;
228*7dd7cddfSDavid du Colombier 
229*7dd7cddfSDavid du Colombier     for (i = 0; i < 6; ++i)
230*7dd7cddfSDavid du Colombier 	w[i] = pw[i];
231*7dd7cddfSDavid du Colombier     return gs_setcachedevice_double(penum, pgs, w);
232*7dd7cddfSDavid du Colombier }
233*7dd7cddfSDavid du Colombier 
234*7dd7cddfSDavid du Colombier /* setcachedevice2 */
235*7dd7cddfSDavid du Colombier /* The elements of pw2 are: w0x, w0y, llx, lly, urx, ury, w1x, w1y, vx, vy. */
236*7dd7cddfSDavid du Colombier /* Note that this returns 1 if we just set up the cache device. */
237*7dd7cddfSDavid du Colombier int
238*7dd7cddfSDavid du Colombier gs_setcachedevice2_double(gs_show_enum * penum, gs_state * pgs,
239*7dd7cddfSDavid du Colombier 			  const double *pw2)
240*7dd7cddfSDavid du Colombier {
241*7dd7cddfSDavid du Colombier     if (penum->pgs != pgs)
242*7dd7cddfSDavid du Colombier 	return_error(gs_error_rangecheck);
243*7dd7cddfSDavid du Colombier     return gs_text_setcachedevice2((gs_text_enum_t *)penum, pw2);
244*7dd7cddfSDavid du Colombier }
245*7dd7cddfSDavid du Colombier /* The _float procedure is strictly for backward compatibility. */
246*7dd7cddfSDavid du Colombier int
247*7dd7cddfSDavid du Colombier gs_setcachedevice2_float(gs_show_enum * penum, gs_state * pgs, const float *pw2)
248*7dd7cddfSDavid du Colombier {
249*7dd7cddfSDavid du Colombier     double w2[10];
250*7dd7cddfSDavid du Colombier     int i;
251*7dd7cddfSDavid du Colombier 
252*7dd7cddfSDavid du Colombier     for (i = 0; i < 10; ++i)
253*7dd7cddfSDavid du Colombier 	w2[i] = pw2[i];
254*7dd7cddfSDavid du Colombier     return gs_setcachedevice2_double(penum, pgs, w2);
255*7dd7cddfSDavid du Colombier }
256*7dd7cddfSDavid du Colombier 
257*7dd7cddfSDavid du Colombier /* setcharwidth */
258*7dd7cddfSDavid du Colombier /* Note that this returns 1 if the current show operation is */
259*7dd7cddfSDavid du Colombier /* non-displaying (stringwidth or cshow). */
260*7dd7cddfSDavid du Colombier int
261*7dd7cddfSDavid du Colombier gs_setcharwidth(gs_show_enum * penum, gs_state * pgs,
262*7dd7cddfSDavid du Colombier 		floatp wx, floatp wy)
263*7dd7cddfSDavid du Colombier {
264*7dd7cddfSDavid du Colombier     double w[2];
265*7dd7cddfSDavid du Colombier 
266*7dd7cddfSDavid du Colombier     if (penum->pgs != pgs)
267*7dd7cddfSDavid du Colombier 	return_error(gs_error_rangecheck);
268*7dd7cddfSDavid du Colombier     w[0] = wx, w[1] = wy;
269*7dd7cddfSDavid du Colombier     return gs_text_setcharwidth((gs_text_enum_t *)penum, w);
270*7dd7cddfSDavid du Colombier }
271*7dd7cddfSDavid du Colombier 
272*7dd7cddfSDavid du Colombier /* ------ Enumerator ------ */
273*7dd7cddfSDavid du Colombier 
274*7dd7cddfSDavid du Colombier /* Do the next step of a show (or stringwidth) operation */
275*7dd7cddfSDavid du Colombier int
276*7dd7cddfSDavid du Colombier gs_show_next(gs_show_enum * penum)
277*7dd7cddfSDavid du Colombier {
278*7dd7cddfSDavid du Colombier     return gs_text_process((gs_text_enum_t *)penum);
279*7dd7cddfSDavid du Colombier }
280*7dd7cddfSDavid du Colombier 
281*7dd7cddfSDavid du Colombier /*
282*7dd7cddfSDavid du Colombier  * Return true if we only need the width from the rasterizer
283*7dd7cddfSDavid du Colombier  * and can short-circuit the full rendering of the character,
284*7dd7cddfSDavid du Colombier  * false if we need the actual character bits.
285*7dd7cddfSDavid du Colombier  */
286*7dd7cddfSDavid du Colombier bool
287*7dd7cddfSDavid du Colombier gs_show_width_only(const gs_show_enum * penum)
288*7dd7cddfSDavid du Colombier {
289*7dd7cddfSDavid du Colombier     return gs_text_is_width_only((const gs_text_enum_t *)penum);
290*7dd7cddfSDavid du Colombier }
291*7dd7cddfSDavid du Colombier 
292*7dd7cddfSDavid du Colombier /* ------ Accessors ------ */
293*7dd7cddfSDavid du Colombier 
294*7dd7cddfSDavid du Colombier /* Return the current character for rendering. */
295*7dd7cddfSDavid du Colombier gs_char
296*7dd7cddfSDavid du Colombier gs_show_current_char(const gs_show_enum * penum)
297*7dd7cddfSDavid du Colombier {
298*7dd7cddfSDavid du Colombier     return gs_text_current_char((const gs_text_enum_t *)penum);
299*7dd7cddfSDavid du Colombier }
300*7dd7cddfSDavid du Colombier 
301*7dd7cddfSDavid du Colombier /* Return the current glyph for rendering. */
302*7dd7cddfSDavid du Colombier gs_glyph
303*7dd7cddfSDavid du Colombier gs_show_current_glyph(const gs_show_enum * penum)
304*7dd7cddfSDavid du Colombier {
305*7dd7cddfSDavid du Colombier     return gs_text_current_glyph((const gs_text_enum_t *)penum);
306*7dd7cddfSDavid du Colombier }
307*7dd7cddfSDavid du Colombier 
308*7dd7cddfSDavid du Colombier /* Return the width of the just-enumerated character (for cshow). */
309*7dd7cddfSDavid du Colombier int
310*7dd7cddfSDavid du Colombier gs_show_current_width(const gs_show_enum * penum, gs_point * ppt)
311*7dd7cddfSDavid du Colombier {
312*7dd7cddfSDavid du Colombier     return gs_text_current_width((const gs_text_enum_t *)penum, ppt);
313*7dd7cddfSDavid du Colombier }
314*7dd7cddfSDavid du Colombier 
315*7dd7cddfSDavid du Colombier /* Return the just-displayed character for kerning. */
316*7dd7cddfSDavid du Colombier gs_char
317*7dd7cddfSDavid du Colombier gs_kshow_previous_char(const gs_show_enum * penum)
318*7dd7cddfSDavid du Colombier {
319*7dd7cddfSDavid du Colombier     return gs_text_current_char((const gs_text_enum_t *)penum);
320*7dd7cddfSDavid du Colombier }
321*7dd7cddfSDavid du Colombier 
322*7dd7cddfSDavid du Colombier /* Return the about-to-be-displayed character for kerning. */
323*7dd7cddfSDavid du Colombier gs_char
324*7dd7cddfSDavid du Colombier gs_kshow_next_char(const gs_show_enum * penum)
325*7dd7cddfSDavid du Colombier {
326*7dd7cddfSDavid du Colombier     return penum->text.data.bytes[penum->index];
327*7dd7cddfSDavid du Colombier }
328*7dd7cddfSDavid du Colombier 
329*7dd7cddfSDavid du Colombier /* Return the accumulated width for stringwidth. */
330*7dd7cddfSDavid du Colombier void
331*7dd7cddfSDavid du Colombier gs_show_width(const gs_show_enum * penum, gs_point * ppt)
332*7dd7cddfSDavid du Colombier {
333*7dd7cddfSDavid du Colombier     gs_text_total_width((const gs_text_enum_t *)penum, ppt);
334*7dd7cddfSDavid du Colombier }
335*7dd7cddfSDavid du Colombier 
336*7dd7cddfSDavid du Colombier /* ------ Internal routines ------ */
337*7dd7cddfSDavid du Colombier 
338*7dd7cddfSDavid du Colombier /*
339*7dd7cddfSDavid du Colombier  * Force the enumerator to be a gs_show_enum *, which the current
340*7dd7cddfSDavid du Colombier  * implementation code requires.
341*7dd7cddfSDavid du Colombier  */
342*7dd7cddfSDavid du Colombier private int
343*7dd7cddfSDavid du Colombier show_n_begin(gs_show_enum *penum, gs_state *pgs, int code, gs_text_enum_t *pte)
344*7dd7cddfSDavid du Colombier {
345*7dd7cddfSDavid du Colombier     if (code < 0)
346*7dd7cddfSDavid du Colombier 	return code;
347*7dd7cddfSDavid du Colombier     if (gs_object_type(pgs->memory, pte) != &st_gs_show_enum) {
348*7dd7cddfSDavid du Colombier 	/* Use the default implementation. */
349*7dd7cddfSDavid du Colombier 	gx_device *dev = pgs->device;
350*7dd7cddfSDavid du Colombier 	gs_text_params_t text;
351*7dd7cddfSDavid du Colombier 	gs_memory_t *mem = pte->memory;
352*7dd7cddfSDavid du Colombier 	dev_proc_text_begin((*text_begin)) = dev_proc(dev, text_begin);
353*7dd7cddfSDavid du Colombier 
354*7dd7cddfSDavid du Colombier 	text = pte->text;
355*7dd7cddfSDavid du Colombier 	gs_text_release(pte, "show_n_begin");
356*7dd7cddfSDavid du Colombier 	/* Temporarily reset the text_begin procedure to the default. */
357*7dd7cddfSDavid du Colombier 	set_dev_proc(dev, text_begin, gx_default_text_begin);
358*7dd7cddfSDavid du Colombier 	code = gs_text_begin(pgs, &text, mem, &pte);
359*7dd7cddfSDavid du Colombier 	set_dev_proc(dev, text_begin, text_begin);
360*7dd7cddfSDavid du Colombier 	if (code < 0)
361*7dd7cddfSDavid du Colombier 	    return code;
362*7dd7cddfSDavid du Colombier     }
363*7dd7cddfSDavid du Colombier     /* Now we know pte points to a gs_show_enum. */
364*7dd7cddfSDavid du Colombier     *penum = *(gs_show_enum *)pte;
365*7dd7cddfSDavid du Colombier     gs_free_object(pgs->memory, pte, "show_n_begin");
366*7dd7cddfSDavid du Colombier     return code;
367*7dd7cddfSDavid du Colombier }
368