1 /******************************************************************************
2   File:     $Id: pclgen.h,v 1.25 2001/08/18 17:41:29 Martin Rel $
3   Contents: Header for PCL-generating routines
4   Author:   Martin Lottermoser, Greifswaldstrasse 28, 38124 Braunschweig,
5             Germany. E-mail: Martin.Lottermoser@t-online.de.
6 
7 *******************************************************************************
8 *									      *
9 *	Copyright (C) 1999, 2000, 2001 by Martin Lottermoser		      *
10 *	All rights reserved						      *
11 *									      *
12 *******************************************************************************
13 
14   The functions declared in this header file generate code for
15   Hewlett-Packard's Printer Command Language level 3+ ("PCL 3+", also called
16   "PCL 3 Plus").
17 
18   The routines support only raster graphics data.
19 
20 ******************************************************************************/
21 
22 #ifndef _pclgen_h	/* Inclusion protection */
23 #define _pclgen_h
24 
25 /* Configuration management identification */
26 #pragma ident "@(#)$Id: pclgen.h,v 1.25 2001/08/18 17:41:29 Martin Rel $"
27 
28 /*****************************************************************************/
29 
30 /* Standard headers */
31 #include <stdio.h>
32 
33 /*****************************************************************************/
34 
35 /* PCL dialects */
36 typedef enum {
37   pcl_level_3plus_DJ500,
38    /* End Raster Graphics is still ESC * r B, no Shingling */
39   pcl_level_3plus_ERG_both,
40    /* ESC*rbC, otherwise identical with 'pcl_level_3plus_S5' */
41   pcl_level_3plus_S5,
42    /* DeskJet 500 series except 540: old quality commands, no
43       Configure Raster Data, ESC*rC */
44   pcl_level_3plus_S68,
45    /* DeskJet 540, DeskJet 600 and 800 series */
46   pcl_level_3plus_CRD_only
47    /* printers always and only using Configure Raster Data instead of
48       Set Number of Planes per Row and Set Raster Graphics Resolution */
49 } pcl_Level;
50 
51 
52 /* Test macros */
53 #define pcl_use_oldERG(level)		(level <= pcl_level_3plus_DJ500)
54 #define pcl_use_oldquality(level)	(level <= pcl_level_3plus_S5)
55 #define pcl_has_CRD(level)		(level >= pcl_level_3plus_S68)
56 
57 /*****************************************************************************/
58 
59 /*  Page Size codes (permitted arguments for the PCL command "Page Size")
60 
61     There exists an area of confusion around this command in connection with
62     "orientation" in various senses. Unfortunately, the documentation made
63     externally available by Hewlett-Packard is not only incomplete but also
64     inconsistent in this respect. (Well, not only in this respect, but don't
65     get me started on this topic or I'll run out of screen space.) In
66     particular, HP does not distinguish between "input orientation"
67     (orientation of a sheet with respect to the feeding direction: short edge
68     first or long edge first) and "page orientation" (orientation of a sheet
69     with respect to the "up" direction of the page contents: portrait or
70     landscape). This is further complicated by the fact that PCL permits
71     several relative orientations between text and graphics data.
72 
73     The following information is therefore partially in disagreement with
74     HP documentation but does agree with the actual behaviour of the DJ 850C.
75 
76     (1) The Page Orientation command has no influence on the orientation of
77 	raster graphics data.
78     (2) Therefore it is possible to define, independent of the Page Orientation
79 	setting, a coordinate system on the medium by reference to the printing
80 	of raster lines ("rows"): the order of pixels within a row defines what
81 	is left and right, and the order in which successive rows are printed
82 	distinguishes between up and down. I call this the "raster space"
83 	coordinate system. (Its units are irrelevant, but we need the
84 	directions.)
85     (3) Because of the way DeskJet printers are constructed (limited memory!),
86 	raster space is fixed with respect to the feeding direction: the "up"
87 	edge of a sheet in raster space is the one entering the printer first
88 	(the leading edge).
89     (4) Hence the media orientation in raster space depends only on the
90 	input orientation: short edge first leads to portrait and long edge
91 	first to landscape orientation in raster space.
92     (5) Among other effects, the Page Size command sets in particular the
93 	printable region for the media size requested.
94     (6) For raster graphics data, clipping occurs at the edge of the printable
95 	region. This happens at the right edge in raster space.
96     (7) It is not possible in PCL to specify the input orientation one has
97 	chosen. In particular, the sign of a Page Size code has no influence on
98 	the printable region as seen in raster space.
99     (8) Some Page Size codes do modify the orientation for text printing on
100 	some printers, but this can be overridden with a subsequent Page
101 	Orientation command.
102     (9) The Page Size command usually sets up the printable region under the
103 	assumption of portrait orientation in raster space (i.e., the input
104 	orientation is short edge first). Exceptions occur with envelope sizes
105 	(Env10 and EnvDL) on older DeskJet printers (500 and 500C, possibly
106 	also 400) where envelopes have to be fed long edge first.
107 
108     The key conclusion to be drawn from this is that the layer represented by
109     the functions in this interface does not have any information on the media
110     orientation in raster space nor can this information be formulated in PCL
111     and passed through this layer. It is information shared between the printer
112     and the client code calling this interface, and the caller must therefore
113     obtain it from an external source.
114 
115     In introducing the concept of a "raster space" I have deliberately avoided
116     the term "physical page" used in the PCL documentation. The latter is not
117     made sufficiently precise, and for printing raster data as done here the
118     first concept is the one required.
119 
120 
121     Two Page Size codes are marked "PS3". These are from Adobe's "LanguageLevel
122     3 Specification and Adobe PostScript 3 Version 3010 Product Supplement"
123     (dated 1997-10-10), page 352, where eight PCL-5 page size codes are listed.
124     Six of these agree with PCL-3 page size codes, and the remaining two are
125     those inserted here and marked "PS3". I have not heard of any PCL-3 printer
126     supporting these two sizes as discrete sizes.
127 
128     The identifiers are usually named after the corresponding 'mediaOption'
129     keyword from Adobe's PPD 4.3 specification.
130 */
131 typedef enum {
132   pcl_ps_default = 0,	/* default size for the printer (e.g., BPD03004 or
133     BPD02926; but note that in some versions of these documents the text
134     representation is wrong, you should look at the hex codes) */
135   pcl_ps_Executive = 1,	/* US Executive (7.25 x 10.5 in).
136     According to Adobe's PPD 4.3 specification, media sizes called by this name
137     vary by up to 1/2 in. */
138   pcl_ps_Letter = 2,	/* US Letter (8.5 x 11 in) */
139   pcl_ps_Legal = 3,	/* US Legal (8.5 x 14 in) */
140   pcl_ps_Tabloid = 6,	/* US Tabloid (11 x 17 in) or Ledger (17 x 11 in)
141 			   (DJ1120C). The designation as Tabloid versus Ledger
142 			   is not always consistent. I'm following PPD 4.3. */
143   pcl_ps_Statement = 15, /* US Statement (5.5 x 8.5 in) (DJ1120C) */
144   pcl_ps_HPSuperB = 16,	/* Super B (13 x 19 in (330 x 483 mm) according to
145 			   DJ1120C, while 305 x 487 mm according to PPD 4.3).
146 			   Not supported in PCL 3 according to BPD07645
147 			   (HP 2500C). */
148   pcl_ps_A6 = 24,	/* ISO/JIS A6 (105 x 148 mm) */
149   pcl_ps_A5 = 25,	/* ISO/JIS A5 (148 x 210 mm) */
150   pcl_ps_A4 = 26,	/* ISO/JIS A4 (210 x 297 mm) */
151   pcl_ps_A3 = 27,	/* ISO/JIS A3 (297 x 420 mm) (DJ1120C, BPL02327) */
152   pcl_ps_JISB5 = 45,	/* JIS B5 (182 x 257 mm) */
153   pcl_ps_JISB4 = 46,	/* JIS B4 (257 x 364 mm) (DJ1120C, BPL02327) */
154   pcl_ps_Postcard = 71,	/* Japanese Hagaki postcard (100 x 148 mm) */
155   pcl_ps_DoublePostcard = 72,	/* Japanese Oufuko-Hagaki postcard
156 			   (148 x 200 mm) (DJ6/8) */
157   pcl_ps_A6Card = 73,	/* "ISO and JIS A6 card" (DJ6/8, DJ1120C). This is the
158 			   value given for most DeskJets supporting A6. I do
159 			   not know what the difference between this value and
160 			   pcl_ps_A6 (24) is. */
161   pcl_ps_Index4x6in = 74,  /* US Index card (4 x 6 in) */
162   pcl_ps_Index5x8in = 75,  /* US Index card (5 x 8 in) */
163   pcl_ps_Index3x5in = 78,  /* US Index card (3 x 5 in) */
164   pcl_ps_EnvMonarch = 80,  /* US Monarch (3.875 x 7.5 in) (PS3, BPL02327) */
165   pcl_ps_Env10 = 81,	/* US No. 10 envelope (4.125 x 9.5 in) */
166   pcl_ps_Env10_Negative = -81,  /* also US No. 10 envelope */
167   /* According to Lexmark-PTR, 89 is US No. 9 envelope (3.875 x 8.875 in). */
168   pcl_ps_EnvDL = 90,	/* ISO DL (110 x 220 mm) */
169   pcl_ps_EnvDL_Negative = -90,  /* also ISO DL. This value is hinted at in
170     TRG500 p. 3-2 in the "Range" line at the bottom of the table and it is
171     explicitly listed in DJ3/4 on p. 36. On a DJ 850C, I found no difference in
172     text orientation with respect to the value 90. */
173   pcl_ps_EnvC5 = 91,	/* ISO C5 (162 x 229 mm) in PCL 5 (PS3, BPL02327) */
174   pcl_ps_EnvC6 = 92,	/* ISO C6 (114 x 162 mm) */
175   pcl_ps_ISOB5 = 100,	/* ISO B5 (176 x 250 mm, BPL02327; the dimensions in
176     millimetres in BPL02327 are wrong, those in inches are right) */
177   pcl_ps_CustomPageSize = 101,  /* Custom page size */
178   pcl_ps_EnvUS_A2 = 109,  /* US A2 envelope (4.375 x 5.75 in) */
179   pcl_ps_EnvChou3 = 110, /* Japanese long Envelope #3 (120 mm x 235 mm)
180 			    (DJ1120C) */
181   pcl_ps_EnvChou4 = 111, /* Japanese long envelope #4 (90 mm x 205 mm)
182 			    (DJ1120C) */
183   pcl_ps_EnvKaku2 = 113	/* Kaku envelope (240 x 332 mm) (DJ1120C) */
184 } pcl_PageSize;
185 
186 /*****************************************************************************/
187 
188 /* Raster graphics compression methods */
189 typedef enum {
190   pcl_cm_none = 0,	/* Unencoded, non-compressed method */
191   pcl_cm_rl = 1,	/* Run-Length Encoding */
192   pcl_cm_tiff = 2,	/* Tagged Image File Format (TIFF) revision 4.0
193 			   "packbits" encoding */
194   pcl_cm_delta = 3,	/* Delta Row Compression */
195   pcl_cm_adaptive = 5,	/* Adaptive Compression */
196   pcl_cm_crdr = 9	/* Compressed Replacement Delta Row Encoding */
197 } pcl_Compression;
198 
199 /* Macro to test for differential compression methods */
200 #define pcl_cm_is_differential(cm)		\
201   ((cm) == pcl_cm_delta || (cm) == pcl_cm_adaptive || (cm) == pcl_cm_crdr)
202 
203 /*****************************************************************************/
204 
205 /* Type and constants for boolean variables */
206 typedef int pcl_bool;
207 #ifndef FALSE
208 #define FALSE	0
209 #else
210 #if FALSE != 0
211 #error "FALSE is defined as non-zero."
212 #endif	/* FALSE != 0 */
213 #endif	/* FALSE */
214 #ifndef TRUE
215 #define TRUE	1
216 #else
217 #if TRUE == 0
218 #error "TRUE is defined as zero."
219 #endif	/* TRUE == 0 */
220 #endif	/* TRUE */
221 
222 
223 /* Palette (process colour model) */
224 typedef enum {
225   pcl_no_palette,	/* Don't send Number of Planes per Row */
226   pcl_black,
227   pcl_CMY,
228   pcl_CMYK,
229   pcl_RGB,		/* Using the RGB palette is discouraged by HP. */
230   pcl_any_palette	/* Don't use this value unless you know what you are
231 			   doing. */
232 } pcl_Palette;
233 
234 
235 /* Information per colorant for raster images */
236 typedef struct {
237   unsigned int hres, vres;	/* Resolution in ppi. The orientation refers to
238     raster space. Both values must be non-zero. */
239   unsigned int levels;	/* Number of intensity levels. 2 or larger. */
240 } pcl_ColorantState;
241 
242 /*****************************************************************************/
243 
244 /* 'pcl_Octet' is used to store 8-bit bytes as unsigned numbers. */
245 #ifndef _pcl_Octet_defined
246 #define _pcl_Octet_defined
247 typedef unsigned char pcl_Octet;
248 #endif
249 
250 /* Octet strings */
251 typedef struct {
252   pcl_Octet *str;	/* Data area for storing the octet string. */
253   int length;		/* Length of 'str' in octets (non-negative). */
254 } pcl_OctetString;
255 /*  A "valid" pcl_OctetString is one where either 'length' is zero, or
256     'length' is positive and 'str' is non-NULL and points to a storage
257     area of at least 'length' octets.
258     A "zero" pcl_OctetString is one where 'length' is zero.
259 */
260 
261 /*****************************************************************************/
262 
263 /* File-global data */
264 typedef struct {
265   pcl_Level level;
266 
267   /* Printer initialization */
268   int NULs_to_send;
269   char
270     *PJL_job,		/* PJL job name. Ignored if NULL. */
271     *PJL_language;	/* PJL personality. Ignored if NULL. */
272 
273   /* Additional initialization commands (ignored if zero) */
274   pcl_OctetString
275     init1,		/* send immediately after resetting the printer */
276     init2;		/* send after all other initialization commands */
277 
278   /* Media */
279   pcl_PageSize size;
280   int
281     media_type,
282     media_source,	/* 0: don't request a particular media source */
283     media_destination,	/* 0: don't request a particular media destination.
284 			   Not based on HP documentation. */
285     duplex;		/* -1: don't request anything in this respect,
286       0: simplex, 1: duplex long-edge binding, 2: duplex short-edge binding
287       (BPL02705). I assume the correct interpretation of the duplex values to
288       be:
289 	1: duplex, print back side with the same top edge in raster space
290 	2: duplex, print back side with top and bottom edges exchanged in
291 	   raster space
292       */
293   pcl_bool manual_feed;
294 
295   /* Print quality selection. Which of these variables are used depends on the
296      PCL level chosen. */
297   int
298     print_quality,
299     depletion,		/* 0: no depletion command */
300     shingling,
301     raster_graphics_quality;
302 
303   /* Colour information */
304   pcl_Palette palette;
305   unsigned int number_of_colorants;
306   pcl_ColorantState *colorant;
307    /* This variable must either be NULL or point to an array of at least
308       'number_of_colorants' elements. The order of colorants is (K)(CMY) except
309       for 'pcl_any_palette'. If the pointer is NULL, 'colorant_array' is used
310       instead. */
311   pcl_ColorantState colorant_array[4];
312     /* Used if 'colorant' is NULL and with the same meaning. This is only
313        possible if 'number_of_colorants' is at most 4. */
314   pcl_bool order_CMYK;
315    /* For pcl_CMYK, should the order of bit planes when sent to the printer be
316       reversed to CMYK instead of KCMY? This is not standard PCL but is needed
317       by at least one Olivetti printer (Olivetti JP792). */
318 
319   int dry_time;	/* negative for "don't send this command" */
320   pcl_Compression compression;
321 
322   /* Derived information managed by the routines declared here. These fields
323      have reliable values only after a call to plc3_init_file(). */
324   unsigned short number_of_bitplanes;
325   unsigned short black_planes;
326   unsigned int minvres;	/* minimal vertical resolution */
327 } pcl_FileData;
328 
329 /*****************************************************************************/
330 
331 /* Types for raster data */
332 
333 typedef struct {
334   /* Data to be provided by the caller */
335   unsigned int width;	/* maximal length of raster lines in pixels at the
336     lowest horizontal resolution. This may be zero to indicate "as large as
337     possible", but this could waste printer memory. Always set this when
338     using an RGB palette unless you have reliable data on the clipping
339     boundary. The value should probably always be a multiple of 8. */
340   pcl_FileData *global;		/* must point to the data used in the last call
341 				   to pcl3_init_file() */
342   pcl_OctetString
343     *previous, *next;
344     /*  These variables point to the sequences of bit planes for the old and
345         the new strip group. The total number of bit planes per group can be
346 	obtained in the 'number_of_bitplanes' parameter in '*global'.
347 
348 	The order of bit planes within a strip group is as follows:
349 	- Each strip group consists of a number of "colorant strips", one for
350 	  each colorant. All strips in such a group cover the same region on
351 	  the page. Except for 'pcl_RGB', colorant strips are ordered in the
352 	  sequence (K)(CMY), independent of 'order_CMYK'. For an RGB palette,
353 	  the order is (of course) RGB.
354 	- Each colorant strip contains a number of pixel lines for this
355           colorant. If there is more than one line, the lines are ordered from
356 	  top to bottom as seen from raster space. The number of lines is
357 	  the ratio of that colorant's vertical resolution to the smallest
358 	  vertical resolution.
359 	- Within each pixel line for a colorant, bit planes are ordered from
360 	  least to most significant. The number of bit planes within a line is
361 	  pcl3_levels_to_planes(levels) for this colorant.
362 	  When bit planes are again combined into lines for a particular
363 	  colorant, the resulting value per pixel denotes the intensity for
364 	  that colorant. A value of zero denotes absence of that colorant.
365 	'previous' will be ignored (and may then be NULL) unless a differential
366 	compression method is requested (pcl_cm_is_differential()).
367 
368 	When using an RGB palette you should always send bit planes extending
369 	over the whole 'width' because shorter bit planes are implicitly
370 	extended with null octets and a pixel value of zero denotes black in an
371 	RGB palette which is not usually desired.
372     */
373   pcl_Octet *workspace[2];
374     /* Storage for the use of these routines. workspace[0] must be non-NULL,
375        workspace[1] will be ignored except for Delta Row Compression. */
376   size_t workspace_allocated;
377     /* Length allocated for each non-NULL 'workspace[]'. This should be at
378        least 2 larger than the longest possible bit plane, otherwise raster
379        data might have to be sent in uncompressed form even if that would take
380        more space. */
381 
382   /* Internal data for these routines */
383   pcl_Compression current_compression;	/* last compression method used */
384   pcl_OctetString **seed_plane;	/* seed plane indexed by plane index */
385 } pcl_RasterData;
386 
387 /******************************************************************************
388 
389   The routines assume a simple state machine:
390 
391   - You are either on a page or between pages.
392   - If you are on a page, you are either in raster mode or not.
393 
394   You should call pcl3_init_file() before the first page and between pages
395   whenever you change the file-global data (like the resolution). Otherwise,
396   use the ..._begin() and ..._end() functions to navigate between the states.
397 
398   Look into the implementation file for detailed interface descriptions for
399   these routines.
400 
401   The error conventions are the same for all file, page and raster functions:
402   - A return code of zero indicates success.
403   - A positive return code indicates an argument error. This should be
404     avoidable by careful programming.
405   - A negative return code indicates an environment error (e.g., disk overflow).
406   If a function returns with a non-zero code, an error message will have been
407   issued on standard error.
408 
409 ******************************************************************************/
410 
411 /* Auxiliary functions */
412 extern unsigned int pcl3_levels_to_planes(unsigned int levels);
413 extern int pcl3_set_printquality(pcl_FileData *data, int quality);
414 extern int pcl3_set_mediatype(pcl_FileData *data, int mediatype);
415 extern int pcl3_set_oldquality(pcl_FileData *data);
416 extern int pcl_compress(pcl_Compression method, const pcl_OctetString *in,
417   const pcl_OctetString *prev, pcl_OctetString *out);
418 
419 
420 /* File and page functions */
421 extern int pcl3_init_file(FILE *out, pcl_FileData *global);
422 extern int pcl3_begin_page(FILE *out, pcl_FileData *global);
423 extern int pcl3_end_page(FILE *out, pcl_FileData *global);
424 extern int pcl3_end_file(FILE *out, pcl_FileData *global);
425 
426 /* Raster functions */
427 extern int pcl3_begin_raster(FILE *out, pcl_RasterData *data);
428 extern int pcl3_skip_groups(FILE *out, pcl_RasterData *data,
429   unsigned int count);
430 extern int pcl3_transfer_group(FILE *out, pcl_RasterData *data);
431 extern int pcl3_end_raster(FILE *out, pcl_RasterData *data);
432 
433 /*****************************************************************************/
434 
435 #endif	/* Inclusion protection */
436