2 * "$Id: imagetoraster.c 7306 2008-02-15 00:52:38Z mike $"
4 * Image file to raster filter for the Common UNIX Printing System (CUPS).
6 * Copyright 2007-2008 by Apple Inc.
7 * Copyright 1993-2007 by Easy Software Products.
9 * These coded instructions, statements, and computer programs are the
10 * property of Apple Inc. and are protected by Federal copyright
11 * law. Distribution and use rights are outlined in the file "LICENSE.txt"
12 * which should have been included with this file. If this file is
13 * file is missing or damaged, see the license at "http://www.cups.org/".
15 * This file is subject to the Apple OS-Developed Software exception.
19 * main() - Main entry...
20 * blank_line() - Clear a line buffer to the blank value...
21 * format_CMY() - Convert image data to CMY.
22 * format_CMYK() - Convert image data to CMYK.
23 * format_K() - Convert image data to black.
24 * format_KCMY() - Convert image data to KCMY.
25 * format_KCMYcm() - Convert image data to KCMYcm.
26 * format_RGBA() - Convert image data to RGBA/RGBW.
27 * format_W() - Convert image data to luminance.
28 * format_YMC() - Convert image data to YMC.
29 * format_YMCK() - Convert image data to YMCK.
30 * make_lut() - Make a lookup table given gamma and brightness values.
31 * raster_cb() - Validate the page header.
35 * Include necessary headers...
39 #include "image-private.h"
42 #include <cups/i18n.h>
49 int Flip
= 0, /* Flip/mirror pages */
50 XPosition
= 0, /* Horizontal position on page */
51 YPosition
= 0, /* Vertical position on page */
52 Collate
= 0, /* Collate copies? */
53 Copies
= 1; /* Number of copies */
54 int Floyd16x16
[16][16] = /* Traditional Floyd ordered dither */
56 { 0, 128, 32, 160, 8, 136, 40, 168,
57 2, 130, 34, 162, 10, 138, 42, 170 },
58 { 192, 64, 224, 96, 200, 72, 232, 104,
59 194, 66, 226, 98, 202, 74, 234, 106 },
60 { 48, 176, 16, 144, 56, 184, 24, 152,
61 50, 178, 18, 146, 58, 186, 26, 154 },
62 { 240, 112, 208, 80, 248, 120, 216, 88,
63 242, 114, 210, 82, 250, 122, 218, 90 },
64 { 12, 140, 44, 172, 4, 132, 36, 164,
65 14, 142, 46, 174, 6, 134, 38, 166 },
66 { 204, 76, 236, 108, 196, 68, 228, 100,
67 206, 78, 238, 110, 198, 70, 230, 102 },
68 { 60, 188, 28, 156, 52, 180, 20, 148,
69 62, 190, 30, 158, 54, 182, 22, 150 },
70 { 252, 124, 220, 92, 244, 116, 212, 84,
71 254, 126, 222, 94, 246, 118, 214, 86 },
72 { 3, 131, 35, 163, 11, 139, 43, 171,
73 1, 129, 33, 161, 9, 137, 41, 169 },
74 { 195, 67, 227, 99, 203, 75, 235, 107,
75 193, 65, 225, 97, 201, 73, 233, 105 },
76 { 51, 179, 19, 147, 59, 187, 27, 155,
77 49, 177, 17, 145, 57, 185, 25, 153 },
78 { 243, 115, 211, 83, 251, 123, 219, 91,
79 241, 113, 209, 81, 249, 121, 217, 89 },
80 { 15, 143, 47, 175, 7, 135, 39, 167,
81 13, 141, 45, 173, 5, 133, 37, 165 },
82 { 207, 79, 239, 111, 199, 71, 231, 103,
83 205, 77, 237, 109, 197, 69, 229, 101 },
84 { 63, 191, 31, 159, 55, 183, 23, 151,
85 61, 189, 29, 157, 53, 181, 21, 149 },
86 { 254, 127, 223, 95, 247, 119, 215, 87,
87 253, 125, 221, 93, 245, 117, 213, 85 }
91 { 0, 32, 8, 40, 2, 34, 10, 42 },
92 { 48, 16, 56, 24, 50, 18, 58, 26 },
93 { 12, 44, 4, 36, 14, 46, 6, 38 },
94 { 60, 28, 52, 20, 62, 30, 54, 22 },
95 { 3, 35, 11, 43, 1, 33, 9, 41 },
96 { 51, 19, 59, 27, 49, 17, 57, 25 },
97 { 15, 47, 7, 39, 13, 45, 5, 37 },
98 { 63, 31, 55, 23, 61, 29, 53, 21 }
108 cups_ib_t OnPixels
[256], /* On-pixel LUT */
109 OffPixels
[256]; /* Off-pixel LUT */
116 static void blank_line(cups_page_header2_t
*header
, unsigned char *row
);
117 static void format_CMY(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
118 static void format_CMYK(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
119 static void format_K(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
120 static void format_KCMYcm(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
121 static void format_KCMY(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
122 #define format_RGB format_CMY
123 static void format_RGBA(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
124 static void format_W(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
125 static void format_YMC(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
126 static void format_YMCK(cups_page_header2_t
*header
, unsigned char *row
, int y
, int z
, int xsize
, int ysize
, int yerr0
, int yerr1
, cups_ib_t
*r0
, cups_ib_t
*r1
);
127 static void make_lut(cups_ib_t
*, int, float, float);
128 static int raster_cb(cups_page_header2_t
*header
, int preferred_bits
);
132 * 'main()' - Main entry...
135 int /* O - Exit status */
136 main(int argc
, /* I - Number of command-line arguments */
137 char *argv
[]) /* I - Command-line arguments */
139 int i
; /* Looping var */
140 cups_image_t
*img
; /* Image to print */
141 float xprint
, /* Printable area */
143 xinches
, /* Total size in inches */
145 float xsize
, /* Total size in points */
149 float aspect
; /* Aspect ratio */
150 int xpages
, /* # x pages */
151 ypages
, /* # y pages */
152 xpage
, /* Current x page */
153 ypage
, /* Current y page */
154 xtemp
, /* Bitmap width in pixels */
155 ytemp
, /* Bitmap height in pixels */
156 page
; /* Current page number */
157 int xc0
, yc0
, /* Corners of the page in image coords */
159 ppd_file_t
*ppd
; /* PPD file */
160 ppd_choice_t
*choice
; /* PPD option choice */
161 char *resolution
, /* Output resolution */
162 *media_type
; /* Media type */
163 ppd_profile_t
*profile
; /* Color profile */
164 ppd_profile_t userprofile
; /* User-specified profile */
165 cups_raster_t
*ras
; /* Raster stream */
166 cups_page_header2_t header
; /* Page header */
167 int num_options
; /* Number of print options */
168 cups_option_t
*options
; /* Print options */
169 const char *val
; /* Option value */
170 int slowcollate
, /* Collate copies the slow way */
171 slowcopies
; /* Make copies the "slow" way? */
172 float g
; /* Gamma correction value */
173 float b
; /* Brightness factor */
174 float zoom
; /* Zoom facter */
175 int xppi
, yppi
; /* Pixels-per-inch */
176 int hue
, sat
; /* Hue and saturation adjustment */
177 cups_izoom_t
*z
; /* Image zoom buffer */
178 cups_iztype_t zoom_type
; /* Image zoom type */
179 int primary
, /* Primary image colorspace */
180 secondary
; /* Secondary image colorspace */
181 cups_ib_t
*row
, /* Current row */
183 *r1
; /* Bottom row */
184 int y
, /* Current Y coordinate on page */
185 iy
, /* Current Y coordinate in image */
186 last_iy
, /* Previous Y coordinate in image */
187 yerr0
, /* Top Y error value */
188 yerr1
; /* Bottom Y error value */
189 cups_ib_t lut
[256]; /* Gamma/brightness LUT */
190 int plane
, /* Current color plane */
191 num_planes
; /* Number of color planes */
192 char filename
[1024]; /* Name of file to print */
196 * Make sure status messages are not buffered...
199 setbuf(stderr
, NULL
);
202 * Check command-line...
205 if (argc
< 6 || argc
> 7)
207 fprintf(stderr
, _("Usage: %s job-id user title copies options [file]\n"),
213 * See if we need to use the imagetops and pstoraster filters instead...
217 num_options
= cupsParseOptions(argv
[5], 0, &options
);
219 if (getenv("CLASSIFICATION") ||
220 cupsGetOption("page-label", num_options
, options
))
223 * Yes, fork a copy of pstoraster and then transfer control to imagetops...
226 int mypipes
[2]; /* New pipes for imagetops | pstoraster */
227 int pid
; /* PID of pstoraster */
230 cupsFreeOptions(num_options
, options
);
234 perror("ERROR: Unable to create pipes for imagetops | pstoraster");
238 if ((pid
= fork()) == 0)
241 * Child process for pstoraster... Assign new pipe input to pstoraster...
248 execlp("pstoraster", argv
[0], argv
[1], argv
[2], argv
[3], argv
[4], argv
[5],
250 perror("ERROR: Unable to exec pstoraster");
259 perror("ERROR: Unable to fork pstoraster");
264 * Update stdout so it points at the new pstoraster...
272 * Run imagetops to get the classification or page labelling that was
276 execlp("imagetops", argv
[0], argv
[1], argv
[2], argv
[3], argv
[4], argv
[5],
278 perror("ERROR: Unable to exec imagetops");
283 * Copy stdin as needed...
288 int fd
; /* File to write to */
289 char buffer
[8192]; /* Buffer to read into */
290 int bytes
; /* # of bytes to read */
293 if ((fd
= cupsTempFd(filename
, sizeof(filename
))) < 0)
295 perror("ERROR: Unable to copy image file");
299 fprintf(stderr
, "DEBUG: imagetoraster - copying to temp print file \"%s\"\n",
302 while ((bytes
= fread(buffer
, 1, sizeof(buffer
), stdin
)) > 0)
303 write(fd
, buffer
, bytes
);
308 strlcpy(filename
, argv
[6], sizeof(filename
));
311 * Process command-line options and write the prolog...
322 Copies
= atoi(argv
[4]);
324 ppd
= SetCommonOptions(num_options
, options
, 0);
326 if ((val
= cupsGetOption("multiple-document-handling", num_options
, options
)) != NULL
)
329 * This IPP attribute is unnecessarily complicated...
331 * single-document, separate-documents-collated-copies, and
332 * single-document-new-sheet all require collated copies.
334 * separate-documents-collated-copies allows for uncollated copies.
337 Collate
= strcasecmp(val
, "separate-documents-collated-copies") != 0;
340 if ((val
= cupsGetOption("Collate", num_options
, options
)) != NULL
&&
341 strcasecmp(val
, "True") == 0)
344 if ((val
= cupsGetOption("gamma", num_options
, options
)) != NULL
)
347 * Get gamma value from 1 to 10000...
350 g
= atoi(val
) * 0.001f
;
358 if ((val
= cupsGetOption("brightness", num_options
, options
)) != NULL
)
361 * Get brightness value from 10 to 1000.
364 b
= atoi(val
) * 0.01f
;
372 if ((val
= cupsGetOption("scaling", num_options
, options
)) != NULL
)
373 zoom
= atoi(val
) * 0.01;
374 else if ((val
= cupsGetOption("fitplot", num_options
, options
)) != NULL
&&
375 !strcasecmp(val
, "true"))
377 else if ((val
= cupsGetOption("fit-to-page", num_options
, options
)) != NULL
&&
378 !strcasecmp(val
, "true"))
381 if ((val
= cupsGetOption("ppi", num_options
, options
)) != NULL
)
382 if (sscanf(val
, "%dx%d", &xppi
, &yppi
) < 2)
385 if ((val
= cupsGetOption("position", num_options
, options
)) != NULL
)
387 if (strcasecmp(val
, "center") == 0)
392 else if (strcasecmp(val
, "top") == 0)
397 else if (strcasecmp(val
, "left") == 0)
402 else if (strcasecmp(val
, "right") == 0)
407 else if (strcasecmp(val
, "top-left") == 0)
412 else if (strcasecmp(val
, "top-right") == 0)
417 else if (strcasecmp(val
, "bottom") == 0)
422 else if (strcasecmp(val
, "bottom-left") == 0)
427 else if (strcasecmp(val
, "bottom-right") == 0)
434 if ((val
= cupsGetOption("saturation", num_options
, options
)) != NULL
)
437 if ((val
= cupsGetOption("hue", num_options
, options
)) != NULL
)
440 if ((choice
= ppdFindMarkedChoice(ppd
, "MirrorPrint")) != NULL
)
442 val
= choice
->choice
;
446 val
= cupsGetOption("mirror", num_options
, options
);
448 if (val
&& (!strcasecmp(val
, "true") || !strcasecmp(val
, "on") ||
449 !strcasecmp(val
, "yes")))
453 * Set the needed options in the page header...
456 if (cupsRasterInterpretPPD(&header
, ppd
, num_options
, options
, raster_cb
))
458 fputs(_("ERROR: Bad page setup!\n"), stderr
);
459 fprintf(stderr
, "DEBUG: %s\n", cupsRasterErrorString());
464 * Get the media type and resolution that have been chosen...
467 if ((choice
= ppdFindMarkedChoice(ppd
, "MediaType")) != NULL
)
468 media_type
= choice
->choice
;
472 if ((choice
= ppdFindMarkedChoice(ppd
, "Resolution")) != NULL
)
473 resolution
= choice
->choice
;
478 * Choose the appropriate colorspace...
481 switch (header
.cupsColorSpace
)
484 if (header
.cupsBitsPerColor
>= 8)
486 primary
= CUPS_IMAGE_WHITE
;
487 secondary
= CUPS_IMAGE_WHITE
;
491 primary
= CUPS_IMAGE_BLACK
;
492 secondary
= CUPS_IMAGE_BLACK
;
497 case CUPS_CSPACE_RGB
:
498 case CUPS_CSPACE_RGBA
:
499 case CUPS_CSPACE_RGBW
:
500 if (header
.cupsBitsPerColor
>= 8)
502 primary
= CUPS_IMAGE_RGB
;
503 secondary
= CUPS_IMAGE_RGB
;
507 primary
= CUPS_IMAGE_CMY
;
508 secondary
= CUPS_IMAGE_CMY
;
513 case CUPS_CSPACE_WHITE
:
514 case CUPS_CSPACE_GOLD
:
515 case CUPS_CSPACE_SILVER
:
516 primary
= CUPS_IMAGE_BLACK
;
517 secondary
= CUPS_IMAGE_BLACK
;
520 case CUPS_CSPACE_CMYK
:
521 case CUPS_CSPACE_YMCK
:
522 case CUPS_CSPACE_KCMY
:
523 case CUPS_CSPACE_KCMYcm
:
524 case CUPS_CSPACE_GMCK
:
525 case CUPS_CSPACE_GMCS
:
526 if (header
.cupsBitsPerColor
== 1)
528 primary
= CUPS_IMAGE_CMY
;
529 secondary
= CUPS_IMAGE_CMY
;
533 primary
= CUPS_IMAGE_CMYK
;
534 secondary
= CUPS_IMAGE_CMYK
;
538 case CUPS_CSPACE_CMY
:
539 case CUPS_CSPACE_YMC
:
540 primary
= CUPS_IMAGE_CMY
;
541 secondary
= CUPS_IMAGE_CMY
;
547 * Find a color profile matching the current options...
550 if ((val
= cupsGetOption("profile", num_options
, options
)) != NULL
)
552 profile
= &userprofile
;
553 sscanf(val
, "%f,%f,%f,%f,%f,%f,%f,%f,%f,%f,%f",
554 &(userprofile
.density
), &(userprofile
.gamma
),
555 userprofile
.matrix
[0] + 0, userprofile
.matrix
[0] + 1,
556 userprofile
.matrix
[0] + 2,
557 userprofile
.matrix
[1] + 0, userprofile
.matrix
[1] + 1,
558 userprofile
.matrix
[1] + 2,
559 userprofile
.matrix
[2] + 0, userprofile
.matrix
[2] + 1,
560 userprofile
.matrix
[2] + 2);
562 userprofile
.density
*= 0.001f
;
563 userprofile
.gamma
*= 0.001f
;
564 userprofile
.matrix
[0][0] *= 0.001f
;
565 userprofile
.matrix
[0][1] *= 0.001f
;
566 userprofile
.matrix
[0][2] *= 0.001f
;
567 userprofile
.matrix
[1][0] *= 0.001f
;
568 userprofile
.matrix
[1][1] *= 0.001f
;
569 userprofile
.matrix
[1][2] *= 0.001f
;
570 userprofile
.matrix
[2][0] *= 0.001f
;
571 userprofile
.matrix
[2][1] *= 0.001f
;
572 userprofile
.matrix
[2][2] *= 0.001f
;
574 else if (ppd
!= NULL
)
576 fprintf(stderr
, "DEBUG: Searching for profile \"%s/%s\"...\n",
577 resolution
, media_type
);
579 for (i
= 0, profile
= ppd
->profiles
; i
< ppd
->num_profiles
; i
++, profile
++)
581 fprintf(stderr
, "DEBUG: \"%s/%s\" = ", profile
->resolution
,
582 profile
->media_type
);
584 if ((strcmp(profile
->resolution
, resolution
) == 0 ||
585 profile
->resolution
[0] == '-') &&
586 (strcmp(profile
->media_type
, media_type
) == 0 ||
587 profile
->media_type
[0] == '-'))
589 fputs("MATCH!\n", stderr
);
593 fputs("no.\n", stderr
);
597 * If we found a color profile, use it!
600 if (i
>= ppd
->num_profiles
)
607 cupsImageSetProfile(profile
->density
, profile
->gamma
, profile
->matrix
);
609 cupsImageSetRasterColorSpace(header
.cupsColorSpace
);
612 * Create a gamma/brightness LUT...
615 make_lut(lut
, primary
, g
, b
);
618 * Open the input image to print...
621 fputs(_("INFO: Loading image file...\n"), stderr
);
623 if (header
.cupsColorSpace
== CUPS_CSPACE_CIEXYZ
||
624 header
.cupsColorSpace
== CUPS_CSPACE_CIELab
||
625 header
.cupsColorSpace
>= CUPS_CSPACE_ICC1
)
626 img
= cupsImageOpen(filename
, primary
, secondary
, sat
, hue
, NULL
);
628 img
= cupsImageOpen(filename
, primary
, secondary
, sat
, hue
, lut
);
635 fputs(_("ERROR: Unable to open image file for printing!\n"), stderr
);
641 * Scale as necessary...
644 if (zoom
== 0.0 && xppi
== 0)
653 fprintf(stderr
, "DEBUG: Before scaling: xppi=%d, yppi=%d, zoom=%.2f\n",
659 * Scale the image as neccesary to match the desired pixels-per-inch.
664 xprint
= (PageTop
- PageBottom
) / 72.0;
665 yprint
= (PageRight
- PageLeft
) / 72.0;
669 xprint
= (PageRight
- PageLeft
) / 72.0;
670 yprint
= (PageTop
- PageBottom
) / 72.0;
673 fprintf(stderr
, "DEBUG: Before scaling: xprint=%.1f, yprint=%.1f\n",
676 xinches
= (float)img
->xsize
/ (float)xppi
;
677 yinches
= (float)img
->ysize
/ (float)yppi
;
679 fprintf(stderr
, "DEBUG: Image size is %.1f x %.1f inches...\n",
682 if ((val
= cupsGetOption("natural-scaling", num_options
, options
)) != NULL
)
684 xinches
= xinches
* atoi(val
) / 100;
685 yinches
= yinches
* atoi(val
) / 100;
688 if (cupsGetOption("orientation-requested", num_options
, options
) == NULL
&&
689 cupsGetOption("landscape", num_options
, options
) == NULL
)
692 * Rotate the image if it will fit landscape but not portrait...
695 fputs("DEBUG: Auto orientation...\n", stderr
);
697 if ((xinches
> xprint
|| yinches
> yprint
) &&
698 xinches
<= yprint
&& yinches
<= xprint
)
701 * Rotate the image as needed...
704 fputs("DEBUG: Using landscape orientation...\n", stderr
);
706 Orientation
= (Orientation
+ 1) & 3;
716 * Scale percentage of page size...
719 xprint
= (PageRight
- PageLeft
) / 72.0;
720 yprint
= (PageTop
- PageBottom
) / 72.0;
721 aspect
= (float)img
->yppi
/ (float)img
->xppi
;
723 fprintf(stderr
, "DEBUG: Before scaling: xprint=%.1f, yprint=%.1f\n",
726 fprintf(stderr
, "DEBUG: img->xppi = %d, img->yppi = %d, aspect = %f\n",
727 img
->xppi
, img
->yppi
, aspect
);
729 xsize
= xprint
* zoom
;
730 ysize
= xsize
* img
->ysize
/ img
->xsize
/ aspect
;
732 if (ysize
> (yprint
* zoom
))
734 ysize
= yprint
* zoom
;
735 xsize
= ysize
* img
->xsize
* aspect
/ img
->ysize
;
738 xsize2
= yprint
* zoom
;
739 ysize2
= xsize2
* img
->ysize
/ img
->xsize
/ aspect
;
741 if (ysize2
> (xprint
* zoom
))
743 ysize2
= xprint
* zoom
;
744 xsize2
= ysize2
* img
->xsize
* aspect
/ img
->ysize
;
747 fprintf(stderr
, "DEBUG: Portrait size is %.2f x %.2f inches\n", xsize
, ysize
);
748 fprintf(stderr
, "DEBUG: Landscape size is %.2f x %.2f inches\n", xsize2
, ysize2
);
750 if (cupsGetOption("orientation-requested", num_options
, options
) == NULL
&&
751 cupsGetOption("landscape", num_options
, options
) == NULL
)
754 * Choose the rotation with the largest area, but prefer
755 * portrait if they are equal...
758 fputs("DEBUG: Auto orientation...\n", stderr
);
760 if ((xsize
* ysize
) < (xsize2
* xsize2
))
763 * Do landscape orientation...
766 fputs("DEBUG: Using landscape orientation...\n", stderr
);
771 xprint
= (PageTop
- PageBottom
) / 72.0;
772 yprint
= (PageRight
- PageLeft
) / 72.0;
777 * Do portrait orientation...
780 fputs("DEBUG: Using portrait orientation...\n", stderr
);
787 else if (Orientation
& 1)
789 fputs("DEBUG: Using landscape orientation...\n", stderr
);
793 xprint
= (PageTop
- PageBottom
) / 72.0;
794 yprint
= (PageRight
- PageLeft
) / 72.0;
798 fputs("DEBUG: Using portrait orientation...\n", stderr
);
802 xprint
= (PageRight
- PageLeft
) / 72.0;
803 yprint
= (PageTop
- PageBottom
) / 72.0;
808 * Compute the number of pages to print and the size of the image on each
812 xpages
= ceil(xinches
/ xprint
);
813 ypages
= ceil(yinches
/ yprint
);
815 xprint
= xinches
/ xpages
;
816 yprint
= yinches
/ ypages
;
818 fprintf(stderr
, "DEBUG: xpages = %dx%.2fin, ypages = %dx%.2fin\n",
819 xpages
, xprint
, ypages
, yprint
);
822 * Compute the bitmap size...
825 if ((choice
= ppdFindMarkedChoice(ppd
, "PageSize")) != NULL
&&
826 strcasecmp(choice
->choice
, "Custom") == 0)
828 float width
, /* New width in points */
829 length
; /* New length in points */
833 * Use the correct width and length for the current orientation...
838 width
= yprint
* 72.0;
839 length
= xprint
* 72.0;
843 width
= xprint
* 72.0;
844 length
= yprint
* 72.0;
848 * Add margins to page size...
851 width
+= ppd
->custom_margins
[0] + ppd
->custom_margins
[2];
852 length
+= ppd
->custom_margins
[1] + ppd
->custom_margins
[3];
855 * Enforce minimums...
858 if (width
< ppd
->custom_min
[0])
859 width
= ppd
->custom_min
[0];
861 if (length
< ppd
->custom_min
[1])
862 length
= ppd
->custom_min
[1];
864 fprintf(stderr
, "DEBUG: Updated custom page size to %.2f x %.2f inches...\n",
865 width
/ 72.0, length
/ 72.0);
868 * Set the new custom size...
871 strcpy(header
.cupsPageSizeName
, "Custom");
873 header
.cupsPageSize
[0] = width
+ 0.5;
874 header
.cupsPageSize
[1] = length
+ 0.5;
875 header
.PageSize
[0] = width
+ 0.5;
876 header
.PageSize
[1] = length
+ 0.5;
879 * Update page variables...
884 PageLeft
= ppd
->custom_margins
[0];
885 PageRight
= width
- ppd
->custom_margins
[2];
886 PageBottom
= ppd
->custom_margins
[1];
887 PageTop
= length
- ppd
->custom_margins
[3];
890 * Remove margins from page size...
893 width
-= ppd
->custom_margins
[0] + ppd
->custom_margins
[2];
894 length
-= ppd
->custom_margins
[1] + ppd
->custom_margins
[3];
897 * Set the bitmap size...
900 header
.cupsWidth
= width
* header
.HWResolution
[0] / 72.0;
901 header
.cupsHeight
= length
* header
.HWResolution
[1] / 72.0;
903 header
.cupsBytesPerLine
= (header
.cupsBitsPerPixel
*
904 header
.cupsWidth
+ 7) / 8;
906 if (header
.cupsColorOrder
== CUPS_ORDER_BANDED
)
907 header
.cupsBytesPerLine
*= header
.cupsNumColors
;
910 header
.Margins
[0] = PageLeft
;
911 header
.Margins
[1] = PageBottom
;
913 fprintf(stderr
, "DEBUG: PageSize = [%d %d]\n", header
.PageSize
[0],
922 header
.cupsImagingBBox
[0] = PageLeft
;
923 header
.cupsImagingBBox
[2] = PageLeft
+ xprint
* 72;
926 header
.cupsImagingBBox
[0] = (PageRight
+ PageLeft
- xprint
* 72) / 2;
927 header
.cupsImagingBBox
[2] = (PageRight
+ PageLeft
+ xprint
* 72) / 2;
930 header
.cupsImagingBBox
[0] = PageRight
- xprint
* 72;
931 header
.cupsImagingBBox
[2] = PageRight
;
938 header
.cupsImagingBBox
[1] = PageBottom
;
939 header
.cupsImagingBBox
[3] = PageBottom
+ yprint
* 72;
942 header
.cupsImagingBBox
[1] = (PageTop
+ PageBottom
- yprint
* 72) / 2;
943 header
.cupsImagingBBox
[3] = (PageTop
+ PageBottom
+ yprint
* 72) / 2;
946 header
.cupsImagingBBox
[1] = PageTop
- yprint
* 72;
947 header
.cupsImagingBBox
[3] = PageTop
;
956 header
.cupsImagingBBox
[0] = PageBottom
;
957 header
.cupsImagingBBox
[2] = PageBottom
+ yprint
* 72;
960 header
.cupsImagingBBox
[0] = (PageTop
+ PageBottom
- yprint
* 72) / 2;
961 header
.cupsImagingBBox
[2] = (PageTop
+ PageBottom
+ yprint
* 72) / 2;
964 header
.cupsImagingBBox
[0] = PageTop
- yprint
* 72;
965 header
.cupsImagingBBox
[2] = PageTop
;
972 header
.cupsImagingBBox
[1] = PageLeft
;
973 header
.cupsImagingBBox
[3] = PageLeft
+ xprint
* 72;
976 header
.cupsImagingBBox
[1] = (PageRight
+ PageLeft
- xprint
* 72) / 2;
977 header
.cupsImagingBBox
[3] = (PageRight
+ PageLeft
+ xprint
* 72) / 2;
980 header
.cupsImagingBBox
[1] = PageRight
- xprint
* 72;
981 header
.cupsImagingBBox
[3] = PageRight
;
990 header
.cupsImagingBBox
[0] = PageLeft
;
991 header
.cupsImagingBBox
[2] = PageLeft
+ xprint
* 72;
994 header
.cupsImagingBBox
[0] = (PageRight
+ PageLeft
- xprint
* 72) / 2;
995 header
.cupsImagingBBox
[2] = (PageRight
+ PageLeft
+ xprint
* 72) / 2;
998 header
.cupsImagingBBox
[0] = PageRight
- xprint
* 72;
999 header
.cupsImagingBBox
[2] = PageRight
;
1006 header
.cupsImagingBBox
[1] = PageBottom
;
1007 header
.cupsImagingBBox
[3] = PageBottom
+ yprint
* 72;
1010 header
.cupsImagingBBox
[1] = (PageTop
+ PageBottom
- yprint
* 72) / 2;
1011 header
.cupsImagingBBox
[3] = (PageTop
+ PageBottom
+ yprint
* 72) / 2;
1014 header
.cupsImagingBBox
[1] = PageTop
- yprint
* 72;
1015 header
.cupsImagingBBox
[3] = PageTop
;
1024 header
.cupsImagingBBox
[0] = PageBottom
;
1025 header
.cupsImagingBBox
[2] = PageBottom
+ yprint
* 72;
1028 header
.cupsImagingBBox
[0] = (PageTop
+ PageBottom
- yprint
* 72) / 2;
1029 header
.cupsImagingBBox
[2] = (PageTop
+ PageBottom
+ yprint
* 72) / 2;
1032 header
.cupsImagingBBox
[0] = PageTop
- yprint
* 72;
1033 header
.cupsImagingBBox
[2] = PageTop
;
1040 header
.cupsImagingBBox
[1] = PageLeft
;
1041 header
.cupsImagingBBox
[3] = PageLeft
+ xprint
* 72;
1044 header
.cupsImagingBBox
[1] = (PageRight
+ PageLeft
- xprint
* 72) / 2;
1045 header
.cupsImagingBBox
[3] = (PageRight
+ PageLeft
+ xprint
* 72) / 2;
1048 header
.cupsImagingBBox
[1] = PageRight
- xprint
* 72;
1049 header
.cupsImagingBBox
[3] = PageRight
;
1055 header
.ImagingBoundingBox
[0] = header
.cupsImagingBBox
[0];
1056 header
.ImagingBoundingBox
[1] = header
.cupsImagingBBox
[1];
1057 header
.ImagingBoundingBox
[2] = header
.cupsImagingBBox
[2];
1058 header
.ImagingBoundingBox
[3] = header
.cupsImagingBBox
[3];
1060 if (header
.cupsColorOrder
== CUPS_ORDER_PLANAR
)
1061 num_planes
= header
.cupsNumColors
;
1065 if (header
.cupsBitsPerColor
>= 8)
1066 zoom_type
= CUPS_IZOOM_NORMAL
;
1068 zoom_type
= CUPS_IZOOM_FAST
;
1071 * See if we need to collate, and if so how we need to do it...
1074 if (xpages
== 1 && ypages
== 1)
1077 slowcollate
= Collate
&& ppdFindOption(ppd
, "Collate") == NULL
;
1079 slowcopies
= ppd
->manual_copies
;
1083 if (Copies
> 1 && !slowcollate
&& !slowcopies
)
1085 header
.Collate
= (cups_bool_t
)Collate
;
1086 header
.NumCopies
= Copies
;
1091 header
.NumCopies
= 1;
1094 * Create the dithering lookup tables...
1098 OnPixels
[255] = 0xff;
1099 OffPixels
[0] = 0x00;
1100 OffPixels
[255] = 0xff;
1102 switch (header
.cupsBitsPerColor
)
1105 for (i
= 1; i
< 255; i
++)
1107 OnPixels
[i
] = 0x55 * (i
/ 85 + 1);
1108 OffPixels
[i
] = 0x55 * (i
/ 64);
1112 for (i
= 1; i
< 255; i
++)
1114 OnPixels
[i
] = 17 * (i
/ 17 + 1);
1115 OffPixels
[i
] = 17 * (i
/ 16);
1121 * Output the pages...
1124 fprintf(stderr
, "DEBUG: cupsWidth = %d\n", header
.cupsWidth
);
1125 fprintf(stderr
, "DEBUG: cupsHeight = %d\n", header
.cupsHeight
);
1126 fprintf(stderr
, "DEBUG: cupsBitsPerColor = %d\n", header
.cupsBitsPerColor
);
1127 fprintf(stderr
, "DEBUG: cupsBitsPerPixel = %d\n", header
.cupsBitsPerPixel
);
1128 fprintf(stderr
, "DEBUG: cupsBytesPerLine = %d\n", header
.cupsBytesPerLine
);
1129 fprintf(stderr
, "DEBUG: cupsColorOrder = %d\n", header
.cupsColorOrder
);
1130 fprintf(stderr
, "DEBUG: cupsColorSpace = %d\n", header
.cupsColorSpace
);
1131 fprintf(stderr
, "DEBUG: img->colorspace = %d\n", img
->colorspace
);
1133 row
= malloc(2 * header
.cupsBytesPerLine
);
1134 ras
= cupsRasterOpen(1, CUPS_RASTER_WRITE
);
1136 for (i
= 0, page
= 1; i
< Copies
; i
++)
1137 for (xpage
= 0; xpage
< xpages
; xpage
++)
1138 for (ypage
= 0; ypage
< ypages
; ypage
++, page
++)
1140 fprintf(stderr
, _("INFO: Formatting page %d...\n"), page
);
1142 if (Orientation
& 1)
1144 xc0
= img
->xsize
* ypage
/ ypages
;
1145 xc1
= img
->xsize
* (ypage
+ 1) / ypages
- 1;
1146 yc0
= img
->ysize
* xpage
/ xpages
;
1147 yc1
= img
->ysize
* (xpage
+ 1) / xpages
- 1;
1149 xtemp
= header
.HWResolution
[0] * yprint
;
1150 ytemp
= header
.HWResolution
[1] * xprint
;
1154 xc0
= img
->xsize
* xpage
/ xpages
;
1155 xc1
= img
->xsize
* (xpage
+ 1) / xpages
- 1;
1156 yc0
= img
->ysize
* ypage
/ ypages
;
1157 yc1
= img
->ysize
* (ypage
+ 1) / ypages
- 1;
1159 xtemp
= header
.HWResolution
[0] * xprint
;
1160 ytemp
= header
.HWResolution
[1] * yprint
;
1163 cupsRasterWriteHeader2(ras
, &header
);
1165 for (plane
= 0; plane
< num_planes
; plane
++)
1168 * Initialize the image "zoom" engine...
1172 z
= _cupsImageZoomNew(img
, xc0
, yc0
, xc1
, yc1
, -xtemp
, ytemp
,
1173 Orientation
& 1, zoom_type
);
1175 z
= _cupsImageZoomNew(img
, xc0
, yc0
, xc1
, yc1
, xtemp
, ytemp
,
1176 Orientation
& 1, zoom_type
);
1179 * Write leading blank space as needed...
1182 if (header
.cupsHeight
> z
->ysize
&& YPosition
<= 0)
1184 blank_line(&header
, row
);
1186 y
= header
.cupsHeight
- z
->ysize
;
1190 fprintf(stderr
, "DEBUG: Writing %d leading blank lines...\n", y
);
1194 if (cupsRasterWritePixels(ras
, row
, header
.cupsBytesPerLine
) <
1195 header
.cupsBytesPerLine
)
1197 fputs(_("ERROR: Unable to write raster data to driver!\n"),
1199 cupsImageClose(img
);
1206 * Then write image data...
1209 for (y
= z
->ysize
, yerr0
= 0, yerr1
= z
->ysize
, iy
= 0, last_iy
= -2;
1215 if (zoom_type
!= CUPS_IZOOM_FAST
&& (iy
- last_iy
) > 1)
1216 _cupsImageZoomFill(z
, iy
);
1218 _cupsImageZoomFill(z
, iy
+ z
->yincr
);
1224 * Format this line of raster data for the printer...
1227 blank_line(&header
, row
);
1229 r0
= z
->rows
[z
->row
];
1230 r1
= z
->rows
[1 - z
->row
];
1232 switch (header
.cupsColorSpace
)
1234 case CUPS_CSPACE_W
:
1235 format_W(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1236 yerr0
, yerr1
, r0
, r1
);
1239 case CUPS_CSPACE_RGB
:
1240 format_RGB(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1241 yerr0
, yerr1
, r0
, r1
);
1243 case CUPS_CSPACE_RGBA
:
1244 case CUPS_CSPACE_RGBW
:
1245 format_RGBA(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1246 yerr0
, yerr1
, r0
, r1
);
1248 case CUPS_CSPACE_K
:
1249 case CUPS_CSPACE_WHITE
:
1250 case CUPS_CSPACE_GOLD
:
1251 case CUPS_CSPACE_SILVER
:
1252 format_K(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1253 yerr0
, yerr1
, r0
, r1
);
1255 case CUPS_CSPACE_CMY
:
1256 format_CMY(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1257 yerr0
, yerr1
, r0
, r1
);
1259 case CUPS_CSPACE_YMC
:
1260 format_YMC(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1261 yerr0
, yerr1
, r0
, r1
);
1263 case CUPS_CSPACE_CMYK
:
1264 format_CMYK(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1265 yerr0
, yerr1
, r0
, r1
);
1267 case CUPS_CSPACE_YMCK
:
1268 case CUPS_CSPACE_GMCK
:
1269 case CUPS_CSPACE_GMCS
:
1270 format_YMCK(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1271 yerr0
, yerr1
, r0
, r1
);
1273 case CUPS_CSPACE_KCMYcm
:
1274 if (header
.cupsBitsPerColor
== 1)
1276 format_KCMYcm(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1277 yerr0
, yerr1
, r0
, r1
);
1280 case CUPS_CSPACE_KCMY
:
1281 format_KCMY(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1282 yerr0
, yerr1
, r0
, r1
);
1287 * Write the raster data to the driver...
1290 if (cupsRasterWritePixels(ras
, row
, header
.cupsBytesPerLine
) <
1291 header
.cupsBytesPerLine
)
1293 fputs(_("ERROR: Unable to write raster data to driver!\n"),
1295 cupsImageClose(img
);
1300 * Compute the next scanline in the image...
1315 * Write trailing blank space as needed...
1318 if (header
.cupsHeight
> z
->ysize
&& YPosition
>= 0)
1320 blank_line(&header
, row
);
1322 y
= header
.cupsHeight
- z
->ysize
;
1326 fprintf(stderr
, "DEBUG: Writing %d trailing blank lines...\n", y
);
1330 if (cupsRasterWritePixels(ras
, row
, header
.cupsBytesPerLine
) <
1331 header
.cupsBytesPerLine
)
1333 fputs(_("ERROR: Unable to write raster data to driver!\n"),
1335 cupsImageClose(img
);
1342 * Free memory used for the "zoom" engine...
1345 _cupsImageZoomDelete(z
);
1354 cupsRasterClose(ras
);
1355 cupsImageClose(img
);
1363 * 'blank_line()' - Clear a line buffer to the blank value...
1367 blank_line(cups_page_header2_t
*header
, /* I - Page header */
1368 unsigned char *row
) /* I - Row buffer */
1370 int count
; /* Remaining bytes */
1373 count
= header
->cupsBytesPerLine
;
1375 switch (header
->cupsColorSpace
)
1377 case CUPS_CSPACE_CIEXYZ
:
1387 case CUPS_CSPACE_CIELab
:
1388 case CUPS_CSPACE_ICC1
:
1389 case CUPS_CSPACE_ICC2
:
1390 case CUPS_CSPACE_ICC3
:
1391 case CUPS_CSPACE_ICC4
:
1392 case CUPS_CSPACE_ICC5
:
1393 case CUPS_CSPACE_ICC6
:
1394 case CUPS_CSPACE_ICC7
:
1395 case CUPS_CSPACE_ICC8
:
1396 case CUPS_CSPACE_ICC9
:
1397 case CUPS_CSPACE_ICCA
:
1398 case CUPS_CSPACE_ICCB
:
1399 case CUPS_CSPACE_ICCC
:
1400 case CUPS_CSPACE_ICCD
:
1401 case CUPS_CSPACE_ICCE
:
1402 case CUPS_CSPACE_ICCF
:
1412 case CUPS_CSPACE_K
:
1413 case CUPS_CSPACE_CMY
:
1414 case CUPS_CSPACE_CMYK
:
1415 case CUPS_CSPACE_YMC
:
1416 case CUPS_CSPACE_YMCK
:
1417 case CUPS_CSPACE_KCMY
:
1418 case CUPS_CSPACE_KCMYcm
:
1419 case CUPS_CSPACE_GMCK
:
1420 case CUPS_CSPACE_GMCS
:
1421 case CUPS_CSPACE_WHITE
:
1422 case CUPS_CSPACE_GOLD
:
1423 case CUPS_CSPACE_SILVER
:
1424 memset(row
, 0, count
);
1428 memset(row
, 255, count
);
1435 * 'format_CMY()' - Convert image data to CMY.
1439 format_CMY(cups_page_header2_t
*header
, /* I - Page header */
1440 unsigned char *row
, /* IO - Bitmap data for device */
1441 int y
, /* I - Current row */
1442 int z
, /* I - Current plane */
1443 int xsize
, /* I - Width of image data */
1444 int ysize
, /* I - Height of image data */
1445 int yerr0
, /* I - Top Y error */
1446 int yerr1
, /* I - Bottom Y error */
1447 cups_ib_t
*r0
, /* I - Primary image data */
1448 cups_ib_t
*r1
) /* I - Image data for interpolation */
1450 cups_ib_t
*ptr
, /* Pointer into row */
1451 *cptr
, /* Pointer into cyan */
1452 *mptr
, /* Pointer into magenta */
1453 *yptr
, /* Pointer into yellow */
1454 bitmask
; /* Current mask for pixel */
1455 int bitoffset
; /* Current offset in line */
1456 int bandwidth
; /* Width of a color band */
1457 int x
, /* Current X coordinate on page */
1458 *dither
; /* Pointer into dither array */
1467 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
1470 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
1474 ptr
= row
+ bitoffset
/ 8;
1475 bandwidth
= header
->cupsBytesPerLine
/ 3;
1477 switch (header
->cupsColorOrder
)
1479 case CUPS_ORDER_CHUNKED
:
1480 switch (header
->cupsBitsPerColor
)
1483 bitmask
= 64 >> (bitoffset
& 7);
1484 dither
= Floyd16x16
[y
& 15];
1486 for (x
= xsize
; x
> 0; x
--)
1488 if (*r0
++ > dither
[x
& 15])
1492 if (*r0
++ > dither
[x
& 15])
1496 if (*r0
++ > dither
[x
& 15])
1510 dither
= Floyd8x8
[y
& 7];
1512 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1514 if ((r0
[0] & 63) > dither
[x
& 7])
1515 *ptr
^= (0x30 & OnPixels
[r0
[0]]);
1517 *ptr
^= (0x30 & OffPixels
[r0
[0]]);
1519 if ((r0
[1] & 63) > dither
[x
& 7])
1520 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
1522 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
1524 if ((r0
[2] & 63) > dither
[x
& 7])
1525 *ptr
++ ^= (0x03 & OnPixels
[r0
[2]]);
1527 *ptr
++ ^= (0x03 & OffPixels
[r0
[2]]);
1532 dither
= Floyd4x4
[y
& 3];
1534 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1536 if ((r0
[0] & 15) > dither
[x
& 3])
1537 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
1539 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
1541 if ((r0
[1] & 15) > dither
[x
& 3])
1542 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
1544 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
1546 if ((r0
[2] & 15) > dither
[x
& 3])
1547 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
1549 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
1554 for (x
= xsize
* 3; x
> 0; x
--, r0
++, r1
++)
1558 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1563 case CUPS_ORDER_BANDED
:
1565 mptr
= ptr
+ bandwidth
;
1566 yptr
= ptr
+ 2 * bandwidth
;
1568 switch (header
->cupsBitsPerColor
)
1571 bitmask
= 0x80 >> (bitoffset
& 7);
1572 dither
= Floyd16x16
[y
& 15];
1574 for (x
= xsize
; x
> 0; x
--)
1576 if (*r0
++ > dither
[x
& 15])
1578 if (*r0
++ > dither
[x
& 15])
1580 if (*r0
++ > dither
[x
& 15])
1596 bitmask
= 0xc0 >> (bitoffset
& 7);
1597 dither
= Floyd8x8
[y
& 7];
1599 for (x
= xsize
; x
> 0; x
--)
1601 if ((*r0
& 63) > dither
[x
& 7])
1602 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
1604 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
1606 if ((*r0
& 63) > dither
[x
& 7])
1607 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
1609 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
1611 if ((*r0
& 63) > dither
[x
& 7])
1612 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
1614 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
1630 bitmask
= 0xf0 >> (bitoffset
& 7);
1631 dither
= Floyd4x4
[y
& 3];
1633 for (x
= xsize
; x
> 0; x
--)
1635 if ((*r0
& 15) > dither
[x
& 3])
1636 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
1638 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
1640 if ((*r0
& 15) > dither
[x
& 3])
1641 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
1643 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
1645 if ((*r0
& 15) > dither
[x
& 3])
1646 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
1648 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
1650 if (bitmask
== 0xf0)
1664 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
1669 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
1674 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
1679 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
1685 case CUPS_ORDER_PLANAR
:
1686 switch (header
->cupsBitsPerColor
)
1689 bitmask
= 0x80 >> (bitoffset
& 7);
1690 dither
= Floyd16x16
[y
& 15];
1695 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1697 if (r0
[0] > dither
[x
& 15])
1711 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1713 if (r0
[1] > dither
[x
& 15])
1727 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1729 if (r0
[2] > dither
[x
& 15])
1745 bitmask
= 0xc0 >> (bitoffset
& 7);
1746 dither
= Floyd8x8
[y
& 7];
1749 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1751 if ((*r0
& 63) > dither
[x
& 7])
1752 *ptr
^= (bitmask
& OnPixels
[*r0
]);
1754 *ptr
^= (bitmask
& OffPixels
[*r0
]);
1768 bitmask
= 0xf0 >> (bitoffset
& 7);
1769 dither
= Floyd4x4
[y
& 3];
1772 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1774 if ((*r0
& 15) > dither
[x
& 3])
1775 *ptr
^= (bitmask
& OnPixels
[*r0
]);
1777 *ptr
^= (bitmask
& OffPixels
[*r0
]);
1779 if (bitmask
== 0xf0)
1794 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
1799 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1809 * 'format_CMYK()' - Convert image data to CMYK.
1813 format_CMYK(cups_page_header2_t
*header
,/* I - Page header */
1814 unsigned char *row
, /* IO - Bitmap data for device */
1815 int y
, /* I - Current row */
1816 int z
, /* I - Current plane */
1817 int xsize
, /* I - Width of image data */
1818 int ysize
, /* I - Height of image data */
1819 int yerr0
, /* I - Top Y error */
1820 int yerr1
, /* I - Bottom Y error */
1821 cups_ib_t
*r0
, /* I - Primary image data */
1822 cups_ib_t
*r1
) /* I - Image data for interpolation */
1824 cups_ib_t
*ptr
, /* Pointer into row */
1825 *cptr
, /* Pointer into cyan */
1826 *mptr
, /* Pointer into magenta */
1827 *yptr
, /* Pointer into yellow */
1828 *kptr
, /* Pointer into black */
1829 bitmask
; /* Current mask for pixel */
1830 int bitoffset
; /* Current offset in line */
1831 int bandwidth
; /* Width of a color band */
1832 int x
, /* Current X coordinate on page */
1833 *dither
; /* Pointer into dither array */
1834 int pc
, pm
, py
; /* CMY pixels */
1843 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
1846 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
1850 ptr
= row
+ bitoffset
/ 8;
1851 bandwidth
= header
->cupsBytesPerLine
/ 4;
1853 switch (header
->cupsColorOrder
)
1855 case CUPS_ORDER_CHUNKED
:
1856 switch (header
->cupsBitsPerColor
)
1859 bitmask
= 128 >> (bitoffset
& 7);
1860 dither
= Floyd16x16
[y
& 15];
1862 for (x
= xsize
; x
> 0; x
--)
1864 pc
= *r0
++ > dither
[x
& 15];
1865 pm
= *r0
++ > dither
[x
& 15];
1866 py
= *r0
++ > dither
[x
& 15];
1899 dither
= Floyd8x8
[y
& 7];
1901 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
1903 if ((r0
[0] & 63) > dither
[x
& 7])
1904 *ptr
^= (0xc0 & OnPixels
[r0
[0]]);
1906 *ptr
^= (0xc0 & OffPixels
[r0
[0]]);
1908 if ((r0
[1] & 63) > dither
[x
& 7])
1909 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
1911 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
1913 if ((r0
[2] & 63) > dither
[x
& 7])
1914 *ptr
^= (0x0c & OnPixels
[r0
[2]]);
1916 *ptr
^= (0x0c & OffPixels
[r0
[2]]);
1918 if ((r0
[3] & 63) > dither
[x
& 7])
1919 *ptr
++ ^= (0x03 & OnPixels
[r0
[3]]);
1921 *ptr
++ ^= (0x03 & OffPixels
[r0
[3]]);
1926 dither
= Floyd4x4
[y
& 3];
1928 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
1930 if ((r0
[0] & 15) > dither
[x
& 3])
1931 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
1933 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
1935 if ((r0
[1] & 15) > dither
[x
& 3])
1936 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
1938 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
1940 if ((r0
[2] & 15) > dither
[x
& 3])
1941 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
1943 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
1945 if ((r0
[3] & 15) > dither
[x
& 3])
1946 *ptr
++ ^= (0x0f & OnPixels
[r0
[3]]);
1948 *ptr
++ ^= (0x0f & OffPixels
[r0
[3]]);
1953 for (x
= xsize
* 4; x
> 0; x
--, r0
++, r1
++)
1957 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1962 case CUPS_ORDER_BANDED
:
1964 mptr
= ptr
+ bandwidth
;
1965 yptr
= ptr
+ 2 * bandwidth
;
1966 kptr
= ptr
+ 3 * bandwidth
;
1968 switch (header
->cupsBitsPerColor
)
1971 bitmask
= 0x80 >> (bitoffset
& 7);
1972 dither
= Floyd16x16
[y
& 15];
1974 for (x
= xsize
; x
> 0; x
--)
1976 pc
= *r0
++ > dither
[x
& 15];
1977 pm
= *r0
++ > dither
[x
& 15];
1978 py
= *r0
++ > dither
[x
& 15];
2006 bitmask
= 0xc0 >> (bitoffset
& 7);
2007 dither
= Floyd8x8
[y
& 7];
2009 for (x
= xsize
; x
> 0; x
--)
2011 if ((*r0
& 63) > dither
[x
& 7])
2012 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2014 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2016 if ((*r0
& 63) > dither
[x
& 7])
2017 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2019 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2021 if ((*r0
& 63) > dither
[x
& 7])
2022 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2024 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2026 if ((*r0
& 63) > dither
[x
& 7])
2027 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2029 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2046 bitmask
= 0xf0 >> (bitoffset
& 7);
2047 dither
= Floyd4x4
[y
& 3];
2049 for (x
= xsize
; x
> 0; x
--)
2051 if ((*r0
& 15) > dither
[x
& 3])
2052 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2054 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2056 if ((*r0
& 15) > dither
[x
& 3])
2057 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2059 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2061 if ((*r0
& 15) > dither
[x
& 3])
2062 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2064 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2066 if ((*r0
& 15) > dither
[x
& 3])
2067 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2069 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2071 if (bitmask
== 0xf0)
2086 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2091 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2096 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2101 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2106 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2112 case CUPS_ORDER_PLANAR
:
2113 switch (header
->cupsBitsPerColor
)
2116 bitmask
= 0x80 >> (bitoffset
& 7);
2117 dither
= Floyd16x16
[y
& 15];
2119 for (x
= xsize
; x
> 0; x
--)
2121 pc
= *r0
++ > dither
[x
& 15];
2122 pm
= *r0
++ > dither
[x
& 15];
2123 py
= *r0
++ > dither
[x
& 15];
2125 if ((pc
&& pm
&& py
&& z
== 3) ||
2126 (pc
&& z
== 0) || (pm
&& z
== 1) || (py
&& z
== 2))
2140 bitmask
= 0xc0 >> (bitoffset
& 7);
2141 dither
= Floyd8x8
[y
& 7];
2144 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2146 if ((*r0
& 63) > dither
[x
& 7])
2147 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2149 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2163 bitmask
= 0xf0 >> (bitoffset
& 7);
2164 dither
= Floyd4x4
[y
& 3];
2167 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2169 if ((*r0
& 15) > dither
[x
& 3])
2170 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2172 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2174 if (bitmask
== 0xf0)
2189 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2194 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2204 * 'format_K()' - Convert image data to black.
2208 format_K(cups_page_header2_t
*header
, /* I - Page header */
2209 unsigned char *row
, /* IO - Bitmap data for device */
2210 int y
, /* I - Current row */
2211 int z
, /* I - Current plane */
2212 int xsize
, /* I - Width of image data */
2213 int ysize
, /* I - Height of image data */
2214 int yerr0
, /* I - Top Y error */
2215 int yerr1
, /* I - Bottom Y error */
2216 cups_ib_t
*r0
, /* I - Primary image data */
2217 cups_ib_t
*r1
) /* I - Image data for interpolation */
2219 cups_ib_t
*ptr
, /* Pointer into row */
2220 bitmask
; /* Current mask for pixel */
2221 int bitoffset
; /* Current offset in line */
2222 int x
, /* Current X coordinate on page */
2223 *dither
; /* Pointer into dither array */
2234 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2237 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2241 ptr
= row
+ bitoffset
/ 8;
2243 switch (header
->cupsBitsPerColor
)
2246 bitmask
= 0x80 >> (bitoffset
& 7);
2247 dither
= Floyd16x16
[y
& 15];
2249 for (x
= xsize
; x
> 0; x
--)
2251 if (*r0
++ > dither
[x
& 15])
2265 bitmask
= 0xc0 >> (bitoffset
& 7);
2266 dither
= Floyd8x8
[y
& 7];
2268 for (x
= xsize
; x
> 0; x
--)
2270 if ((*r0
& 63) > dither
[x
& 7])
2271 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
2273 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
2287 bitmask
= 0xf0 >> (bitoffset
& 7);
2288 dither
= Floyd4x4
[y
& 3];
2290 for (x
= xsize
; x
> 0; x
--)
2292 if ((*r0
& 15) > dither
[x
& 3])
2293 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
2295 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
2297 if (bitmask
== 0xf0)
2309 for (x
= xsize
; x
> 0; x
--, r0
++, r1
++)
2314 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2322 * 'format_KCMY()' - Convert image data to KCMY.
2326 format_KCMY(cups_page_header2_t
*header
,/* I - Page header */
2327 unsigned char *row
, /* IO - Bitmap data for device */
2328 int y
, /* I - Current row */
2329 int z
, /* I - Current plane */
2330 int xsize
, /* I - Width of image data */
2331 int ysize
, /* I - Height of image data */
2332 int yerr0
, /* I - Top Y error */
2333 int yerr1
, /* I - Bottom Y error */
2334 cups_ib_t
*r0
, /* I - Primary image data */
2335 cups_ib_t
*r1
) /* I - Image data for interpolation */
2337 cups_ib_t
*ptr
, /* Pointer into row */
2338 *cptr
, /* Pointer into cyan */
2339 *mptr
, /* Pointer into magenta */
2340 *yptr
, /* Pointer into yellow */
2341 *kptr
, /* Pointer into black */
2342 bitmask
; /* Current mask for pixel */
2343 int bitoffset
; /* Current offset in line */
2344 int bandwidth
; /* Width of a color band */
2345 int x
, /* Current X coordinate on page */
2346 *dither
; /* Pointer into dither array */
2347 int pc
, pm
, py
; /* CMY pixels */
2356 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2359 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2363 ptr
= row
+ bitoffset
/ 8;
2364 bandwidth
= header
->cupsBytesPerLine
/ 4;
2366 switch (header
->cupsColorOrder
)
2368 case CUPS_ORDER_CHUNKED
:
2369 switch (header
->cupsBitsPerColor
)
2372 bitmask
= 128 >> (bitoffset
& 7);
2373 dither
= Floyd16x16
[y
& 15];
2375 for (x
= xsize
; x
> 0; x
--)
2377 pc
= *r0
++ > dither
[x
& 15];
2378 pm
= *r0
++ > dither
[x
& 15];
2379 py
= *r0
++ > dither
[x
& 15];
2412 dither
= Floyd8x8
[y
& 7];
2414 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2416 if ((r0
[3] & 63) > dither
[x
& 7])
2417 *ptr
^= (0xc0 & OnPixels
[r0
[3]]);
2419 *ptr
^= (0xc0 & OffPixels
[r0
[3]]);
2421 if ((r0
[0] & 63) > dither
[x
& 7])
2422 *ptr
^= (0x30 & OnPixels
[r0
[0]]);
2424 *ptr
^= (0x30 & OffPixels
[r0
[0]]);
2426 if ((r0
[1] & 63) > dither
[x
& 7])
2427 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
2429 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
2431 if ((r0
[2] & 63) > dither
[x
& 7])
2432 *ptr
++ ^= (0x03 & OnPixels
[r0
[2]]);
2434 *ptr
++ ^= (0x03 & OffPixels
[r0
[2]]);
2439 dither
= Floyd4x4
[y
& 3];
2441 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2443 if ((r0
[3] & 15) > dither
[x
& 3])
2444 *ptr
^= (0xf0 & OnPixels
[r0
[3]]);
2446 *ptr
^= (0xf0 & OffPixels
[r0
[3]]);
2448 if ((r0
[0] & 15) > dither
[x
& 3])
2449 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
2451 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
2453 if ((r0
[1] & 15) > dither
[x
& 3])
2454 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
2456 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
2458 if ((r0
[2] & 15) > dither
[x
& 3])
2459 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
2461 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
2466 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2471 *ptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2476 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2481 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2486 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2492 case CUPS_ORDER_BANDED
:
2494 cptr
= ptr
+ bandwidth
;
2495 mptr
= ptr
+ 2 * bandwidth
;
2496 yptr
= ptr
+ 3 * bandwidth
;
2498 switch (header
->cupsBitsPerColor
)
2501 bitmask
= 0x80 >> (bitoffset
& 7);
2502 dither
= Floyd16x16
[y
& 15];
2504 for (x
= xsize
; x
> 0; x
--)
2506 pc
= *r0
++ > dither
[x
& 15];
2507 pm
= *r0
++ > dither
[x
& 15];
2508 py
= *r0
++ > dither
[x
& 15];
2536 bitmask
= 0xc0 >> (bitoffset
& 7);
2537 dither
= Floyd8x8
[y
& 7];
2539 for (x
= xsize
; x
> 0; x
--)
2541 if ((*r0
& 63) > dither
[x
& 7])
2542 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2544 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2546 if ((*r0
& 63) > dither
[x
& 7])
2547 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2549 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2551 if ((*r0
& 63) > dither
[x
& 7])
2552 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2554 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2556 if ((*r0
& 63) > dither
[x
& 7])
2557 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2559 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2576 bitmask
= 0xf0 >> (bitoffset
& 7);
2577 dither
= Floyd4x4
[y
& 3];
2579 for (x
= xsize
; x
> 0; x
--)
2581 if ((*r0
& 15) > dither
[x
& 3])
2582 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2584 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2586 if ((*r0
& 15) > dither
[x
& 3])
2587 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2589 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2591 if ((*r0
& 15) > dither
[x
& 3])
2592 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2594 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2596 if ((*r0
& 15) > dither
[x
& 3])
2597 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2599 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2601 if (bitmask
== 0xf0)
2616 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2621 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2626 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2631 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2636 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2642 case CUPS_ORDER_PLANAR
:
2643 switch (header
->cupsBitsPerColor
)
2646 bitmask
= 0x80 >> (bitoffset
& 7);
2647 dither
= Floyd16x16
[y
& 15];
2649 for (x
= xsize
; x
> 0; x
--)
2651 pc
= *r0
++ > dither
[x
& 15];
2652 pm
= *r0
++ > dither
[x
& 15];
2653 py
= *r0
++ > dither
[x
& 15];
2655 if ((pc
&& pm
&& py
&& z
== 0) ||
2656 (pc
&& z
== 1) || (pm
&& z
== 2) || (py
&& z
== 3))
2670 bitmask
= 0xc0 >> (bitoffset
& 7);
2671 dither
= Floyd8x8
[y
& 7];
2677 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2679 if ((*r0
& 63) > dither
[x
& 7])
2680 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2682 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2696 bitmask
= 0xf0 >> (bitoffset
& 7);
2697 dither
= Floyd4x4
[y
& 3];
2703 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2705 if ((*r0
& 15) > dither
[x
& 3])
2706 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2708 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2710 if (bitmask
== 0xf0)
2733 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2738 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2748 * 'format_KCMYcm()' - Convert image data to KCMYcm.
2753 cups_page_header2_t
*header
, /* I - Page header */
2754 unsigned char *row
, /* IO - Bitmap data for device */
2755 int y
, /* I - Current row */
2756 int z
, /* I - Current plane */
2757 int xsize
, /* I - Width of image data */
2758 int ysize
, /* I - Height of image data */
2759 int yerr0
, /* I - Top Y error */
2760 int yerr1
, /* I - Bottom Y error */
2761 cups_ib_t
*r0
, /* I - Primary image data */
2762 cups_ib_t
*r1
) /* I - Image data for interpolation */
2764 int pc
, pm
, py
, pk
; /* Cyan, magenta, yellow, and black values */
2765 cups_ib_t
*ptr
, /* Pointer into row */
2766 *cptr
, /* Pointer into cyan */
2767 *mptr
, /* Pointer into magenta */
2768 *yptr
, /* Pointer into yellow */
2769 *kptr
, /* Pointer into black */
2770 *lcptr
, /* Pointer into light cyan */
2771 *lmptr
, /* Pointer into light magenta */
2772 bitmask
; /* Current mask for pixel */
2773 int bitoffset
; /* Current offset in line */
2774 int bandwidth
; /* Width of a color band */
2775 int x
, /* Current X coordinate on page */
2776 *dither
; /* Pointer into dither array */
2785 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2788 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2792 ptr
= row
+ bitoffset
/ 8;
2793 bandwidth
= header
->cupsBytesPerLine
/ 6;
2795 switch (header
->cupsColorOrder
)
2797 case CUPS_ORDER_CHUNKED
:
2798 dither
= Floyd16x16
[y
& 15];
2800 for (x
= xsize
; x
> 0; x
--)
2802 pc
= *r0
++ > dither
[x
& 15];
2803 pm
= *r0
++ > dither
[x
& 15];
2804 py
= *r0
++ > dither
[x
& 15];
2805 pk
= pc
&& pm
&& py
;
2808 *ptr
++ ^= 32; /* Black */
2810 *ptr
++ ^= 17; /* Blue (cyan + light magenta) */
2812 *ptr
++ ^= 6; /* Green (light cyan + yellow) */
2814 *ptr
++ ^= 12; /* Red (magenta + yellow) */
2826 case CUPS_ORDER_BANDED
:
2828 cptr
= ptr
+ bandwidth
;
2829 mptr
= ptr
+ 2 * bandwidth
;
2830 yptr
= ptr
+ 3 * bandwidth
;
2831 lcptr
= ptr
+ 4 * bandwidth
;
2832 lmptr
= ptr
+ 5 * bandwidth
;
2834 bitmask
= 0x80 >> (bitoffset
& 7);
2835 dither
= Floyd16x16
[y
& 15];
2837 for (x
= xsize
; x
> 0; x
--)
2839 pc
= *r0
++ > dither
[x
& 15];
2840 pm
= *r0
++ > dither
[x
& 15];
2841 py
= *r0
++ > dither
[x
& 15];
2842 pk
= pc
&& pm
&& py
;
2845 *kptr
^= bitmask
; /* Black */
2848 *cptr
^= bitmask
; /* Blue (cyan + light magenta) */
2853 *lcptr
^= bitmask
; /* Green (light cyan + yellow) */
2858 *mptr
^= bitmask
; /* Red (magenta + yellow) */
2883 case CUPS_ORDER_PLANAR
:
2884 bitmask
= 0x80 >> (bitoffset
& 7);
2885 dither
= Floyd16x16
[y
& 15];
2887 for (x
= xsize
; x
> 0; x
--)
2889 pc
= *r0
++ > dither
[x
& 15];
2890 pm
= *r0
++ > dither
[x
& 15];
2891 py
= *r0
++ > dither
[x
& 15];
2892 pk
= pc
&& pm
&& py
;
2896 else if (pc
&& pm
&& (z
== 1 || z
== 5))
2897 *ptr
^= bitmask
; /* Blue (cyan + light magenta) */
2898 else if (pc
&& py
&& (z
== 3 || z
== 4))
2899 *ptr
^= bitmask
; /* Green (light cyan + yellow) */
2900 else if (pm
&& py
&& (z
== 2 || z
== 3))
2901 *ptr
^= bitmask
; /* Red (magenta + yellow) */
2902 else if (pc
&& z
== 1)
2904 else if (pm
&& z
== 2)
2906 else if (py
&& z
== 3)
2923 * 'format_RGBA()' - Convert image data to RGBA/RGBW.
2927 format_RGBA(cups_page_header2_t
*header
,/* I - Page header */
2928 unsigned char *row
, /* IO - Bitmap data for device */
2929 int y
, /* I - Current row */
2930 int z
, /* I - Current plane */
2931 int xsize
, /* I - Width of image data */
2932 int ysize
, /* I - Height of image data */
2933 int yerr0
, /* I - Top Y error */
2934 int yerr1
, /* I - Bottom Y error */
2935 cups_ib_t
*r0
, /* I - Primary image data */
2936 cups_ib_t
*r1
) /* I - Image data for interpolation */
2938 cups_ib_t
*ptr
, /* Pointer into row */
2939 *cptr
, /* Pointer into cyan */
2940 *mptr
, /* Pointer into magenta */
2941 *yptr
, /* Pointer into yellow */
2942 bitmask
; /* Current mask for pixel */
2943 int bitoffset
; /* Current offset in line */
2944 int bandwidth
; /* Width of a color band */
2945 int x
, /* Current X coordinate on page */
2946 *dither
; /* Pointer into dither array */
2955 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2958 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2962 ptr
= row
+ bitoffset
/ 8;
2963 bandwidth
= header
->cupsBytesPerLine
/ 4;
2965 switch (header
->cupsColorOrder
)
2967 case CUPS_ORDER_CHUNKED
:
2968 switch (header
->cupsBitsPerColor
)
2971 bitmask
= 128 >> (bitoffset
& 7);
2972 dither
= Floyd16x16
[y
& 15];
2974 for (x
= xsize
; x
> 0; x
--)
2976 if (*r0
++ > dither
[x
& 15])
2980 if (*r0
++ > dither
[x
& 15])
2984 if (*r0
++ > dither
[x
& 15])
2998 dither
= Floyd8x8
[y
& 7];
3000 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3002 if ((r0
[0] & 63) > dither
[x
& 7])
3003 *ptr
^= (0xc0 & OnPixels
[r0
[0]]);
3005 *ptr
^= (0xc0 & OffPixels
[r0
[0]]);
3007 if ((r0
[1] & 63) > dither
[x
& 7])
3008 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
3010 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
3012 if ((r0
[2] & 63) > dither
[x
& 7])
3013 *ptr
^= (0x0c & OnPixels
[r0
[2]]);
3015 *ptr
^= (0x0c & OffPixels
[r0
[2]]);
3022 dither
= Floyd4x4
[y
& 3];
3024 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3026 if ((r0
[0] & 15) > dither
[x
& 3])
3027 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
3029 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
3031 if ((r0
[1] & 15) > dither
[x
& 3])
3032 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
3034 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
3036 if ((r0
[2] & 15) > dither
[x
& 3])
3037 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
3039 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
3046 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3051 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3056 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3061 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3069 case CUPS_ORDER_BANDED
:
3071 mptr
= ptr
+ bandwidth
;
3072 yptr
= ptr
+ 2 * bandwidth
;
3074 memset(ptr
+ 3 * bandwidth
, 255, bandwidth
);
3076 switch (header
->cupsBitsPerColor
)
3079 bitmask
= 0x80 >> (bitoffset
& 7);
3080 dither
= Floyd16x16
[y
& 15];
3082 for (x
= xsize
; x
> 0; x
--)
3084 if (*r0
++ > dither
[x
& 15])
3086 if (*r0
++ > dither
[x
& 15])
3088 if (*r0
++ > dither
[x
& 15])
3104 bitmask
= 0xc0 >> (bitoffset
& 7);
3105 dither
= Floyd8x8
[y
& 7];
3107 for (x
= xsize
; x
> 0; x
--)
3109 if ((*r0
& 63) > dither
[x
& 7])
3110 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3112 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3114 if ((*r0
& 63) > dither
[x
& 7])
3115 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3117 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3119 if ((*r0
& 63) > dither
[x
& 7])
3120 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3122 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3138 bitmask
= 0xf0 >> (bitoffset
& 7);
3139 dither
= Floyd4x4
[y
& 3];
3141 for (x
= xsize
; x
> 0; x
--)
3143 if ((*r0
& 15) > dither
[x
& 3])
3144 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3146 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3148 if ((*r0
& 15) > dither
[x
& 3])
3149 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3151 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3153 if ((*r0
& 15) > dither
[x
& 3])
3154 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3156 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3158 if (bitmask
== 0xf0)
3172 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3177 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3182 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3187 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3193 case CUPS_ORDER_PLANAR
:
3196 memset(row
, 255, header
->cupsBytesPerLine
);
3200 switch (header
->cupsBitsPerColor
)
3203 bitmask
= 0x80 >> (bitoffset
& 7);
3204 dither
= Floyd16x16
[y
& 15];
3209 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3211 if (r0
[0] > dither
[x
& 15])
3225 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3227 if (r0
[1] > dither
[x
& 15])
3241 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3243 if (r0
[2] > dither
[x
& 15])
3259 bitmask
= 0xc0 >> (bitoffset
& 7);
3260 dither
= Floyd8x8
[y
& 7];
3263 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3265 if ((*r0
& 63) > dither
[x
& 7])
3266 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3268 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3282 bitmask
= 0xf0 >> (bitoffset
& 7);
3283 dither
= Floyd4x4
[y
& 3];
3286 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3288 if ((*r0
& 15) > dither
[x
& 3])
3289 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3291 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3293 if (bitmask
== 0xf0)
3308 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3313 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3323 * 'format_W()' - Convert image data to luminance.
3327 format_W(cups_page_header2_t
*header
, /* I - Page header */
3328 unsigned char *row
, /* IO - Bitmap data for device */
3329 int y
, /* I - Current row */
3330 int z
, /* I - Current plane */
3331 int xsize
, /* I - Width of image data */
3332 int ysize
, /* I - Height of image data */
3333 int yerr0
, /* I - Top Y error */
3334 int yerr1
, /* I - Bottom Y error */
3335 cups_ib_t
*r0
, /* I - Primary image data */
3336 cups_ib_t
*r1
) /* I - Image data for interpolation */
3338 cups_ib_t
*ptr
, /* Pointer into row */
3339 bitmask
; /* Current mask for pixel */
3340 int bitoffset
; /* Current offset in line */
3341 int x
, /* Current X coordinate on page */
3342 *dither
; /* Pointer into dither array */
3353 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3356 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3360 ptr
= row
+ bitoffset
/ 8;
3362 switch (header
->cupsBitsPerColor
)
3365 bitmask
= 0x80 >> (bitoffset
& 7);
3366 dither
= Floyd16x16
[y
& 15];
3368 for (x
= xsize
; x
> 0; x
--)
3370 if (*r0
++ > dither
[x
& 15])
3384 bitmask
= 0xc0 >> (bitoffset
& 7);
3385 dither
= Floyd8x8
[y
& 7];
3387 for (x
= xsize
; x
> 0; x
--)
3389 if ((*r0
& 63) > dither
[x
& 7])
3390 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
3392 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
3406 bitmask
= 0xf0 >> (bitoffset
& 7);
3407 dither
= Floyd4x4
[y
& 3];
3409 for (x
= xsize
; x
> 0; x
--)
3411 if ((*r0
& 15) > dither
[x
& 3])
3412 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
3414 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
3416 if (bitmask
== 0xf0)
3428 for (x
= xsize
; x
> 0; x
--, r0
++, r1
++)
3433 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3441 * 'format_YMC()' - Convert image data to YMC.
3445 format_YMC(cups_page_header2_t
*header
, /* I - Page header */
3446 unsigned char *row
, /* IO - Bitmap data for device */
3447 int y
, /* I - Current row */
3448 int z
, /* I - Current plane */
3449 int xsize
, /* I - Width of image data */
3450 int ysize
, /* I - Height of image data */
3451 int yerr0
, /* I - Top Y error */
3452 int yerr1
, /* I - Bottom Y error */
3453 cups_ib_t
*r0
, /* I - Primary image data */
3454 cups_ib_t
*r1
) /* I - Image data for interpolation */
3456 cups_ib_t
*ptr
, /* Pointer into row */
3457 *cptr
, /* Pointer into cyan */
3458 *mptr
, /* Pointer into magenta */
3459 *yptr
, /* Pointer into yellow */
3460 bitmask
; /* Current mask for pixel */
3461 int bitoffset
; /* Current offset in line */
3462 int bandwidth
; /* Width of a color band */
3463 int x
, /* Current X coordinate on page */
3464 *dither
; /* Pointer into dither array */
3473 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3476 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3480 ptr
= row
+ bitoffset
/ 8;
3481 bandwidth
= header
->cupsBytesPerLine
/ 3;
3483 switch (header
->cupsColorOrder
)
3485 case CUPS_ORDER_CHUNKED
:
3486 switch (header
->cupsBitsPerColor
)
3489 bitmask
= 64 >> (bitoffset
& 7);
3490 dither
= Floyd16x16
[y
& 15];
3492 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3494 if (r0
[2] > dither
[x
& 15])
3498 if (r0
[1] > dither
[x
& 15])
3502 if (r0
[0] > dither
[x
& 15])
3516 dither
= Floyd8x8
[y
& 7];
3518 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3520 if ((r0
[2] & 63) > dither
[x
& 7])
3521 *ptr
^= (0x30 & OnPixels
[r0
[2]]);
3523 *ptr
^= (0x30 & OffPixels
[r0
[2]]);
3525 if ((r0
[1] & 63) > dither
[x
& 7])
3526 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
3528 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
3530 if ((r0
[0] & 63) > dither
[x
& 7])
3531 *ptr
++ ^= (0x03 & OnPixels
[r0
[0]]);
3533 *ptr
++ ^= (0x03 & OffPixels
[r0
[0]]);
3538 dither
= Floyd4x4
[y
& 3];
3540 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3542 if ((r0
[2] & 15) > dither
[x
& 3])
3543 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
3545 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
3547 if ((r0
[1] & 15) > dither
[x
& 3])
3548 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
3550 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
3552 if ((r0
[0] & 15) > dither
[x
& 3])
3553 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
3555 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
3560 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3565 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3570 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3575 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3581 case CUPS_ORDER_BANDED
:
3583 mptr
= ptr
+ bandwidth
;
3584 cptr
= ptr
+ 2 * bandwidth
;
3586 switch (header
->cupsBitsPerColor
)
3589 bitmask
= 0x80 >> (bitoffset
& 7);
3590 dither
= Floyd16x16
[y
& 15];
3592 for (x
= xsize
; x
> 0; x
--)
3594 if (*r0
++ > dither
[x
& 15])
3596 if (*r0
++ > dither
[x
& 15])
3598 if (*r0
++ > dither
[x
& 15])
3614 bitmask
= 0xc0 >> (bitoffset
& 7);
3615 dither
= Floyd8x8
[y
& 7];
3617 for (x
= xsize
; x
> 0; x
--)
3619 if ((*r0
& 63) > dither
[x
& 7])
3620 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3622 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3624 if ((*r0
& 63) > dither
[x
& 7])
3625 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3627 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3629 if ((*r0
& 63) > dither
[x
& 7])
3630 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3632 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3648 bitmask
= 0xf0 >> (bitoffset
& 7);
3649 dither
= Floyd4x4
[y
& 3];
3651 for (x
= xsize
; x
> 0; x
--)
3653 if ((*r0
& 15) > dither
[x
& 3])
3654 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3656 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3658 if ((*r0
& 15) > dither
[x
& 3])
3659 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3661 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3663 if ((*r0
& 15) > dither
[x
& 3])
3664 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3666 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3668 if (bitmask
== 0xf0)
3682 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3687 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3692 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3697 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3703 case CUPS_ORDER_PLANAR
:
3704 switch (header
->cupsBitsPerColor
)
3707 bitmask
= 0x80 >> (bitoffset
& 7);
3708 dither
= Floyd16x16
[y
& 15];
3713 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3715 if (r0
[0] > dither
[x
& 15])
3729 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3731 if (r0
[1] > dither
[x
& 15])
3745 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3747 if (r0
[2] > dither
[x
& 15])
3763 bitmask
= 0xc0 >> (bitoffset
& 7);
3764 dither
= Floyd8x8
[y
& 7];
3768 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3770 if ((*r0
& 63) > dither
[x
& 7])
3771 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3773 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3787 bitmask
= 0xf0 >> (bitoffset
& 7);
3788 dither
= Floyd4x4
[y
& 3];
3792 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3794 if ((*r0
& 15) > dither
[x
& 3])
3795 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3797 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3799 if (bitmask
== 0xf0)
3815 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3820 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3830 * 'format_YMCK()' - Convert image data to YMCK.
3834 format_YMCK(cups_page_header2_t
*header
,/* I - Page header */
3835 unsigned char *row
, /* IO - Bitmap data for device */
3836 int y
, /* I - Current row */
3837 int z
, /* I - Current plane */
3838 int xsize
, /* I - Width of image data */
3839 int ysize
, /* I - Height of image data */
3840 int yerr0
, /* I - Top Y error */
3841 int yerr1
, /* I - Bottom Y error */
3842 cups_ib_t
*r0
, /* I - Primary image data */
3843 cups_ib_t
*r1
) /* I - Image data for interpolation */
3845 cups_ib_t
*ptr
, /* Pointer into row */
3846 *cptr
, /* Pointer into cyan */
3847 *mptr
, /* Pointer into magenta */
3848 *yptr
, /* Pointer into yellow */
3849 *kptr
, /* Pointer into black */
3850 bitmask
; /* Current mask for pixel */
3851 int bitoffset
; /* Current offset in line */
3852 int bandwidth
; /* Width of a color band */
3853 int x
, /* Current X coordinate on page */
3854 *dither
; /* Pointer into dither array */
3855 int pc
, pm
, py
; /* CMY pixels */
3864 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3867 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3871 ptr
= row
+ bitoffset
/ 8;
3872 bandwidth
= header
->cupsBytesPerLine
/ 4;
3874 switch (header
->cupsColorOrder
)
3876 case CUPS_ORDER_CHUNKED
:
3877 switch (header
->cupsBitsPerColor
)
3880 bitmask
= 128 >> (bitoffset
& 7);
3881 dither
= Floyd16x16
[y
& 15];
3883 for (x
= xsize
; x
> 0; x
--)
3885 pc
= *r0
++ > dither
[x
& 15];
3886 pm
= *r0
++ > dither
[x
& 15];
3887 py
= *r0
++ > dither
[x
& 15];
3921 dither
= Floyd8x8
[y
& 7];
3923 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
3925 if ((r0
[2] & 63) > dither
[x
& 7])
3926 *ptr
^= (0xc0 & OnPixels
[r0
[2]]);
3928 *ptr
^= (0xc0 & OffPixels
[r0
[2]]);
3930 if ((r0
[1] & 63) > dither
[x
& 7])
3931 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
3933 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
3935 if ((r0
[0] & 63) > dither
[x
& 7])
3936 *ptr
^= (0x0c & OnPixels
[r0
[0]]);
3938 *ptr
^= (0x0c & OffPixels
[r0
[0]]);
3940 if ((r0
[3] & 63) > dither
[x
& 7])
3941 *ptr
++ ^= (0x03 & OnPixels
[r0
[3]]);
3943 *ptr
++ ^= (0x03 & OffPixels
[r0
[3]]);
3948 dither
= Floyd4x4
[y
& 3];
3950 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
3952 if ((r0
[2] & 15) > dither
[x
& 3])
3953 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
3955 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
3957 if ((r0
[1] & 15) > dither
[x
& 3])
3958 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
3960 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
3962 if ((r0
[0] & 15) > dither
[x
& 3])
3963 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
3965 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
3967 if ((r0
[3] & 15) > dither
[x
& 3])
3968 *ptr
++ ^= (0x0f & OnPixels
[r0
[3]]);
3970 *ptr
++ ^= (0x0f & OffPixels
[r0
[3]]);
3975 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
3980 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3985 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3990 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3995 *ptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
4001 case CUPS_ORDER_BANDED
:
4003 mptr
= ptr
+ bandwidth
;
4004 cptr
= ptr
+ 2 * bandwidth
;
4005 kptr
= ptr
+ 3 * bandwidth
;
4007 switch (header
->cupsBitsPerColor
)
4010 bitmask
= 0x80 >> (bitoffset
& 7);
4011 dither
= Floyd16x16
[y
& 15];
4013 for (x
= xsize
; x
> 0; x
--)
4015 pc
= *r0
++ > dither
[x
& 15];
4016 pm
= *r0
++ > dither
[x
& 15];
4017 py
= *r0
++ > dither
[x
& 15];
4046 bitmask
= 0xc0 >> (bitoffset
& 7);
4047 dither
= Floyd8x8
[y
& 7];
4049 for (x
= xsize
; x
> 0; x
--)
4051 if ((*r0
& 63) > dither
[x
& 7])
4052 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
4054 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
4056 if ((*r0
& 63) > dither
[x
& 7])
4057 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
4059 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
4061 if ((*r0
& 63) > dither
[x
& 7])
4062 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
4064 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
4066 if ((*r0
& 63) > dither
[x
& 7])
4067 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
4069 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
4086 bitmask
= 0xf0 >> (bitoffset
& 7);
4087 dither
= Floyd4x4
[y
& 3];
4089 for (x
= xsize
; x
> 0; x
--)
4091 if ((*r0
& 15) > dither
[x
& 3])
4092 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
4094 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
4096 if ((*r0
& 15) > dither
[x
& 3])
4097 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
4099 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
4101 if ((*r0
& 15) > dither
[x
& 3])
4102 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
4104 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
4106 if ((*r0
& 15) > dither
[x
& 3])
4107 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
4109 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
4111 if (bitmask
== 0xf0)
4126 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
4131 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
4136 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
4141 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
4146 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
4152 case CUPS_ORDER_PLANAR
:
4153 switch (header
->cupsBitsPerColor
)
4156 bitmask
= 0x80 >> (bitoffset
& 7);
4157 dither
= Floyd16x16
[y
& 15];
4159 for (x
= xsize
; x
> 0; x
--)
4161 pc
= *r0
++ > dither
[x
& 15];
4162 pm
= *r0
++ > dither
[x
& 15];
4163 py
= *r0
++ > dither
[x
& 15];
4165 if ((pc
&& pm
&& py
&& z
== 3) ||
4166 (pc
&& z
== 2) || (pm
&& z
== 1) || (py
&& z
== 0))
4180 bitmask
= 0xc0 >> (bitoffset
& 7);
4181 dither
= Floyd8x8
[y
& 7];
4187 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
4189 if ((*r0
& 63) > dither
[x
& 7])
4190 *ptr
^= (bitmask
& OnPixels
[*r0
]);
4192 *ptr
^= (bitmask
& OffPixels
[*r0
]);
4206 bitmask
= 0xf0 >> (bitoffset
& 7);
4207 dither
= Floyd4x4
[y
& 3];
4213 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
4215 if ((*r0
& 15) > dither
[x
& 3])
4216 *ptr
^= (bitmask
& OnPixels
[*r0
]);
4218 *ptr
^= (bitmask
& OffPixels
[*r0
]);
4220 if (bitmask
== 0xf0)
4243 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
4248 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
4258 * 'make_lut()' - Make a lookup table given gamma and brightness values.
4262 make_lut(cups_ib_t
*lut
, /* I - Lookup table */
4263 int colorspace
, /* I - Colorspace */
4264 float g
, /* I - Image gamma */
4265 float b
) /* I - Image brightness */
4267 int i
; /* Looping var */
4268 int v
; /* Current value */
4274 for (i
= 0; i
< 256; i
++)
4277 v
= 255.0 * b
* (1.0 - pow(1.0 - (float)i
/ 255.0, g
)) + 0.5;
4279 v
= 255.0 * (1.0 - b
* (1.0 - pow((float)i
/ 255.0, g
))) + 0.5;
4292 * 'raster_cb()' - Validate the page header.
4295 static int /* O - 0 if OK, -1 if not */
4297 cups_page_header2_t
*header
, /* IO - Raster header */
4298 int preferred_bits
) /* I - Preferred bits per color */
4301 * Ensure that colorimetric colorspaces use at least 8 bits per
4305 if ((header
->cupsColorSpace
== CUPS_CSPACE_CIEXYZ
||
4306 header
->cupsColorSpace
== CUPS_CSPACE_CIELab
||
4307 header
->cupsColorSpace
>= CUPS_CSPACE_ICC1
) &&
4308 header
->cupsBitsPerColor
< 8)
4309 header
->cupsBitsPerColor
= 8;
4316 * End of "$Id: imagetoraster.c 7306 2008-02-15 00:52:38Z mike $".