2 * "$Id: imagetoraster.c 7306 2008-02-15 00:52:38Z mike $"
4 * Image file to raster filter for CUPS.
6 * Copyright 2007-2010 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/language-private.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 _cupsLangPuts(stderr
, _("ERROR: Bad page setup\n"));
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 _cupsLangPuts(stderr
, _("INFO: Loading image file...\n"));
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 _cupsLangPuts(stderr
, _("ERROR: Unable to open image file for printing\n"));
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 _cupsLangPuts(stderr
,
1198 _("ERROR: Unable to write raster data to "
1200 cupsImageClose(img
);
1207 * Then write image data...
1210 for (y
= z
->ysize
, yerr0
= 0, yerr1
= z
->ysize
, iy
= 0, last_iy
= -2;
1216 if (zoom_type
!= CUPS_IZOOM_FAST
&& (iy
- last_iy
) > 1)
1217 _cupsImageZoomFill(z
, iy
);
1219 _cupsImageZoomFill(z
, iy
+ z
->yincr
);
1225 * Format this line of raster data for the printer...
1228 blank_line(&header
, row
);
1230 r0
= z
->rows
[z
->row
];
1231 r1
= z
->rows
[1 - z
->row
];
1233 switch (header
.cupsColorSpace
)
1235 case CUPS_CSPACE_W
:
1236 format_W(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1237 yerr0
, yerr1
, r0
, r1
);
1240 case CUPS_CSPACE_RGB
:
1241 format_RGB(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1242 yerr0
, yerr1
, r0
, r1
);
1244 case CUPS_CSPACE_RGBA
:
1245 case CUPS_CSPACE_RGBW
:
1246 format_RGBA(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1247 yerr0
, yerr1
, r0
, r1
);
1249 case CUPS_CSPACE_K
:
1250 case CUPS_CSPACE_WHITE
:
1251 case CUPS_CSPACE_GOLD
:
1252 case CUPS_CSPACE_SILVER
:
1253 format_K(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1254 yerr0
, yerr1
, r0
, r1
);
1256 case CUPS_CSPACE_CMY
:
1257 format_CMY(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1258 yerr0
, yerr1
, r0
, r1
);
1260 case CUPS_CSPACE_YMC
:
1261 format_YMC(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1262 yerr0
, yerr1
, r0
, r1
);
1264 case CUPS_CSPACE_CMYK
:
1265 format_CMYK(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1266 yerr0
, yerr1
, r0
, r1
);
1268 case CUPS_CSPACE_YMCK
:
1269 case CUPS_CSPACE_GMCK
:
1270 case CUPS_CSPACE_GMCS
:
1271 format_YMCK(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1272 yerr0
, yerr1
, r0
, r1
);
1274 case CUPS_CSPACE_KCMYcm
:
1275 if (header
.cupsBitsPerColor
== 1)
1277 format_KCMYcm(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1278 yerr0
, yerr1
, r0
, r1
);
1281 case CUPS_CSPACE_KCMY
:
1282 format_KCMY(&header
, row
, y
, plane
, z
->xsize
, z
->ysize
,
1283 yerr0
, yerr1
, r0
, r1
);
1288 * Write the raster data to the driver...
1291 if (cupsRasterWritePixels(ras
, row
, header
.cupsBytesPerLine
) <
1292 header
.cupsBytesPerLine
)
1294 _cupsLangPuts(stderr
,
1295 _("ERROR: Unable to write raster data to driver\n"));
1296 cupsImageClose(img
);
1301 * Compute the next scanline in the image...
1316 * Write trailing blank space as needed...
1319 if (header
.cupsHeight
> z
->ysize
&& YPosition
>= 0)
1321 blank_line(&header
, row
);
1323 y
= header
.cupsHeight
- z
->ysize
;
1327 fprintf(stderr
, "DEBUG: Writing %d trailing blank lines...\n", y
);
1331 if (cupsRasterWritePixels(ras
, row
, header
.cupsBytesPerLine
) <
1332 header
.cupsBytesPerLine
)
1334 _cupsLangPuts(stderr
,
1335 _("ERROR: Unable to write raster data to "
1337 cupsImageClose(img
);
1344 * Free memory used for the "zoom" engine...
1347 _cupsImageZoomDelete(z
);
1356 cupsRasterClose(ras
);
1357 cupsImageClose(img
);
1365 * 'blank_line()' - Clear a line buffer to the blank value...
1369 blank_line(cups_page_header2_t
*header
, /* I - Page header */
1370 unsigned char *row
) /* I - Row buffer */
1372 int count
; /* Remaining bytes */
1375 count
= header
->cupsBytesPerLine
;
1377 switch (header
->cupsColorSpace
)
1379 case CUPS_CSPACE_CIEXYZ
:
1389 case CUPS_CSPACE_CIELab
:
1390 case CUPS_CSPACE_ICC1
:
1391 case CUPS_CSPACE_ICC2
:
1392 case CUPS_CSPACE_ICC3
:
1393 case CUPS_CSPACE_ICC4
:
1394 case CUPS_CSPACE_ICC5
:
1395 case CUPS_CSPACE_ICC6
:
1396 case CUPS_CSPACE_ICC7
:
1397 case CUPS_CSPACE_ICC8
:
1398 case CUPS_CSPACE_ICC9
:
1399 case CUPS_CSPACE_ICCA
:
1400 case CUPS_CSPACE_ICCB
:
1401 case CUPS_CSPACE_ICCC
:
1402 case CUPS_CSPACE_ICCD
:
1403 case CUPS_CSPACE_ICCE
:
1404 case CUPS_CSPACE_ICCF
:
1414 case CUPS_CSPACE_K
:
1415 case CUPS_CSPACE_CMY
:
1416 case CUPS_CSPACE_CMYK
:
1417 case CUPS_CSPACE_YMC
:
1418 case CUPS_CSPACE_YMCK
:
1419 case CUPS_CSPACE_KCMY
:
1420 case CUPS_CSPACE_KCMYcm
:
1421 case CUPS_CSPACE_GMCK
:
1422 case CUPS_CSPACE_GMCS
:
1423 case CUPS_CSPACE_WHITE
:
1424 case CUPS_CSPACE_GOLD
:
1425 case CUPS_CSPACE_SILVER
:
1426 memset(row
, 0, count
);
1430 memset(row
, 255, count
);
1437 * 'format_CMY()' - Convert image data to CMY.
1441 format_CMY(cups_page_header2_t
*header
, /* I - Page header */
1442 unsigned char *row
, /* IO - Bitmap data for device */
1443 int y
, /* I - Current row */
1444 int z
, /* I - Current plane */
1445 int xsize
, /* I - Width of image data */
1446 int ysize
, /* I - Height of image data */
1447 int yerr0
, /* I - Top Y error */
1448 int yerr1
, /* I - Bottom Y error */
1449 cups_ib_t
*r0
, /* I - Primary image data */
1450 cups_ib_t
*r1
) /* I - Image data for interpolation */
1452 cups_ib_t
*ptr
, /* Pointer into row */
1453 *cptr
, /* Pointer into cyan */
1454 *mptr
, /* Pointer into magenta */
1455 *yptr
, /* Pointer into yellow */
1456 bitmask
; /* Current mask for pixel */
1457 int bitoffset
; /* Current offset in line */
1458 int bandwidth
; /* Width of a color band */
1459 int x
, /* Current X coordinate on page */
1460 *dither
; /* Pointer into dither array */
1469 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
1472 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
1476 ptr
= row
+ bitoffset
/ 8;
1477 bandwidth
= header
->cupsBytesPerLine
/ 3;
1479 switch (header
->cupsColorOrder
)
1481 case CUPS_ORDER_CHUNKED
:
1482 switch (header
->cupsBitsPerColor
)
1485 bitmask
= 64 >> (bitoffset
& 7);
1486 dither
= Floyd16x16
[y
& 15];
1488 for (x
= xsize
; x
> 0; x
--)
1490 if (*r0
++ > dither
[x
& 15])
1494 if (*r0
++ > dither
[x
& 15])
1498 if (*r0
++ > dither
[x
& 15])
1512 dither
= Floyd8x8
[y
& 7];
1514 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1516 if ((r0
[0] & 63) > dither
[x
& 7])
1517 *ptr
^= (0x30 & OnPixels
[r0
[0]]);
1519 *ptr
^= (0x30 & OffPixels
[r0
[0]]);
1521 if ((r0
[1] & 63) > dither
[x
& 7])
1522 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
1524 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
1526 if ((r0
[2] & 63) > dither
[x
& 7])
1527 *ptr
++ ^= (0x03 & OnPixels
[r0
[2]]);
1529 *ptr
++ ^= (0x03 & OffPixels
[r0
[2]]);
1534 dither
= Floyd4x4
[y
& 3];
1536 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1538 if ((r0
[0] & 15) > dither
[x
& 3])
1539 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
1541 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
1543 if ((r0
[1] & 15) > dither
[x
& 3])
1544 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
1546 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
1548 if ((r0
[2] & 15) > dither
[x
& 3])
1549 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
1551 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
1556 for (x
= xsize
* 3; x
> 0; x
--, r0
++, r1
++)
1560 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1565 case CUPS_ORDER_BANDED
:
1567 mptr
= ptr
+ bandwidth
;
1568 yptr
= ptr
+ 2 * bandwidth
;
1570 switch (header
->cupsBitsPerColor
)
1573 bitmask
= 0x80 >> (bitoffset
& 7);
1574 dither
= Floyd16x16
[y
& 15];
1576 for (x
= xsize
; x
> 0; x
--)
1578 if (*r0
++ > dither
[x
& 15])
1580 if (*r0
++ > dither
[x
& 15])
1582 if (*r0
++ > dither
[x
& 15])
1598 bitmask
= 0xc0 >> (bitoffset
& 7);
1599 dither
= Floyd8x8
[y
& 7];
1601 for (x
= xsize
; x
> 0; x
--)
1603 if ((*r0
& 63) > dither
[x
& 7])
1604 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
1606 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
1608 if ((*r0
& 63) > dither
[x
& 7])
1609 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
1611 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
1613 if ((*r0
& 63) > dither
[x
& 7])
1614 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
1616 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
1632 bitmask
= 0xf0 >> (bitoffset
& 7);
1633 dither
= Floyd4x4
[y
& 3];
1635 for (x
= xsize
; x
> 0; x
--)
1637 if ((*r0
& 15) > dither
[x
& 3])
1638 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
1640 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
1642 if ((*r0
& 15) > dither
[x
& 3])
1643 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
1645 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
1647 if ((*r0
& 15) > dither
[x
& 3])
1648 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
1650 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
1652 if (bitmask
== 0xf0)
1666 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
1671 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
1676 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
1681 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
1687 case CUPS_ORDER_PLANAR
:
1688 switch (header
->cupsBitsPerColor
)
1691 bitmask
= 0x80 >> (bitoffset
& 7);
1692 dither
= Floyd16x16
[y
& 15];
1697 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1699 if (r0
[0] > dither
[x
& 15])
1713 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1715 if (r0
[1] > dither
[x
& 15])
1729 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1731 if (r0
[2] > dither
[x
& 15])
1747 bitmask
= 0xc0 >> (bitoffset
& 7);
1748 dither
= Floyd8x8
[y
& 7];
1751 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1753 if ((*r0
& 63) > dither
[x
& 7])
1754 *ptr
^= (bitmask
& OnPixels
[*r0
]);
1756 *ptr
^= (bitmask
& OffPixels
[*r0
]);
1770 bitmask
= 0xf0 >> (bitoffset
& 7);
1771 dither
= Floyd4x4
[y
& 3];
1774 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
1776 if ((*r0
& 15) > dither
[x
& 3])
1777 *ptr
^= (bitmask
& OnPixels
[*r0
]);
1779 *ptr
^= (bitmask
& OffPixels
[*r0
]);
1781 if (bitmask
== 0xf0)
1796 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
1801 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1811 * 'format_CMYK()' - Convert image data to CMYK.
1815 format_CMYK(cups_page_header2_t
*header
,/* I - Page header */
1816 unsigned char *row
, /* IO - Bitmap data for device */
1817 int y
, /* I - Current row */
1818 int z
, /* I - Current plane */
1819 int xsize
, /* I - Width of image data */
1820 int ysize
, /* I - Height of image data */
1821 int yerr0
, /* I - Top Y error */
1822 int yerr1
, /* I - Bottom Y error */
1823 cups_ib_t
*r0
, /* I - Primary image data */
1824 cups_ib_t
*r1
) /* I - Image data for interpolation */
1826 cups_ib_t
*ptr
, /* Pointer into row */
1827 *cptr
, /* Pointer into cyan */
1828 *mptr
, /* Pointer into magenta */
1829 *yptr
, /* Pointer into yellow */
1830 *kptr
, /* Pointer into black */
1831 bitmask
; /* Current mask for pixel */
1832 int bitoffset
; /* Current offset in line */
1833 int bandwidth
; /* Width of a color band */
1834 int x
, /* Current X coordinate on page */
1835 *dither
; /* Pointer into dither array */
1836 int pc
, pm
, py
; /* CMY pixels */
1845 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
1848 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
1852 ptr
= row
+ bitoffset
/ 8;
1853 bandwidth
= header
->cupsBytesPerLine
/ 4;
1855 switch (header
->cupsColorOrder
)
1857 case CUPS_ORDER_CHUNKED
:
1858 switch (header
->cupsBitsPerColor
)
1861 bitmask
= 128 >> (bitoffset
& 7);
1862 dither
= Floyd16x16
[y
& 15];
1864 for (x
= xsize
; x
> 0; x
--)
1866 pc
= *r0
++ > dither
[x
& 15];
1867 pm
= *r0
++ > dither
[x
& 15];
1868 py
= *r0
++ > dither
[x
& 15];
1901 dither
= Floyd8x8
[y
& 7];
1903 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
1905 if ((r0
[0] & 63) > dither
[x
& 7])
1906 *ptr
^= (0xc0 & OnPixels
[r0
[0]]);
1908 *ptr
^= (0xc0 & OffPixels
[r0
[0]]);
1910 if ((r0
[1] & 63) > dither
[x
& 7])
1911 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
1913 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
1915 if ((r0
[2] & 63) > dither
[x
& 7])
1916 *ptr
^= (0x0c & OnPixels
[r0
[2]]);
1918 *ptr
^= (0x0c & OffPixels
[r0
[2]]);
1920 if ((r0
[3] & 63) > dither
[x
& 7])
1921 *ptr
++ ^= (0x03 & OnPixels
[r0
[3]]);
1923 *ptr
++ ^= (0x03 & OffPixels
[r0
[3]]);
1928 dither
= Floyd4x4
[y
& 3];
1930 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
1932 if ((r0
[0] & 15) > dither
[x
& 3])
1933 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
1935 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
1937 if ((r0
[1] & 15) > dither
[x
& 3])
1938 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
1940 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
1942 if ((r0
[2] & 15) > dither
[x
& 3])
1943 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
1945 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
1947 if ((r0
[3] & 15) > dither
[x
& 3])
1948 *ptr
++ ^= (0x0f & OnPixels
[r0
[3]]);
1950 *ptr
++ ^= (0x0f & OffPixels
[r0
[3]]);
1955 for (x
= xsize
* 4; x
> 0; x
--, r0
++, r1
++)
1959 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
1964 case CUPS_ORDER_BANDED
:
1966 mptr
= ptr
+ bandwidth
;
1967 yptr
= ptr
+ 2 * bandwidth
;
1968 kptr
= ptr
+ 3 * bandwidth
;
1970 switch (header
->cupsBitsPerColor
)
1973 bitmask
= 0x80 >> (bitoffset
& 7);
1974 dither
= Floyd16x16
[y
& 15];
1976 for (x
= xsize
; x
> 0; x
--)
1978 pc
= *r0
++ > dither
[x
& 15];
1979 pm
= *r0
++ > dither
[x
& 15];
1980 py
= *r0
++ > dither
[x
& 15];
2008 bitmask
= 0xc0 >> (bitoffset
& 7);
2009 dither
= Floyd8x8
[y
& 7];
2011 for (x
= xsize
; x
> 0; x
--)
2013 if ((*r0
& 63) > dither
[x
& 7])
2014 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2016 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2018 if ((*r0
& 63) > dither
[x
& 7])
2019 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2021 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2023 if ((*r0
& 63) > dither
[x
& 7])
2024 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2026 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2028 if ((*r0
& 63) > dither
[x
& 7])
2029 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2031 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2048 bitmask
= 0xf0 >> (bitoffset
& 7);
2049 dither
= Floyd4x4
[y
& 3];
2051 for (x
= xsize
; x
> 0; x
--)
2053 if ((*r0
& 15) > dither
[x
& 3])
2054 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2056 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2058 if ((*r0
& 15) > dither
[x
& 3])
2059 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2061 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2063 if ((*r0
& 15) > dither
[x
& 3])
2064 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2066 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2068 if ((*r0
& 15) > dither
[x
& 3])
2069 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2071 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2073 if (bitmask
== 0xf0)
2088 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2093 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2098 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2103 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2108 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2114 case CUPS_ORDER_PLANAR
:
2115 switch (header
->cupsBitsPerColor
)
2118 bitmask
= 0x80 >> (bitoffset
& 7);
2119 dither
= Floyd16x16
[y
& 15];
2121 for (x
= xsize
; x
> 0; x
--)
2123 pc
= *r0
++ > dither
[x
& 15];
2124 pm
= *r0
++ > dither
[x
& 15];
2125 py
= *r0
++ > dither
[x
& 15];
2127 if ((pc
&& pm
&& py
&& z
== 3) ||
2128 (pc
&& z
== 0) || (pm
&& z
== 1) || (py
&& z
== 2))
2142 bitmask
= 0xc0 >> (bitoffset
& 7);
2143 dither
= Floyd8x8
[y
& 7];
2146 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2148 if ((*r0
& 63) > dither
[x
& 7])
2149 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2151 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2165 bitmask
= 0xf0 >> (bitoffset
& 7);
2166 dither
= Floyd4x4
[y
& 3];
2169 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2171 if ((*r0
& 15) > dither
[x
& 3])
2172 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2174 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2176 if (bitmask
== 0xf0)
2191 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2196 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2206 * 'format_K()' - Convert image data to black.
2210 format_K(cups_page_header2_t
*header
, /* I - Page header */
2211 unsigned char *row
, /* IO - Bitmap data for device */
2212 int y
, /* I - Current row */
2213 int z
, /* I - Current plane */
2214 int xsize
, /* I - Width of image data */
2215 int ysize
, /* I - Height of image data */
2216 int yerr0
, /* I - Top Y error */
2217 int yerr1
, /* I - Bottom Y error */
2218 cups_ib_t
*r0
, /* I - Primary image data */
2219 cups_ib_t
*r1
) /* I - Image data for interpolation */
2221 cups_ib_t
*ptr
, /* Pointer into row */
2222 bitmask
; /* Current mask for pixel */
2223 int bitoffset
; /* Current offset in line */
2224 int x
, /* Current X coordinate on page */
2225 *dither
; /* Pointer into dither array */
2236 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2239 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2243 ptr
= row
+ bitoffset
/ 8;
2245 switch (header
->cupsBitsPerColor
)
2248 bitmask
= 0x80 >> (bitoffset
& 7);
2249 dither
= Floyd16x16
[y
& 15];
2251 for (x
= xsize
; x
> 0; x
--)
2253 if (*r0
++ > dither
[x
& 15])
2267 bitmask
= 0xc0 >> (bitoffset
& 7);
2268 dither
= Floyd8x8
[y
& 7];
2270 for (x
= xsize
; x
> 0; x
--)
2272 if ((*r0
& 63) > dither
[x
& 7])
2273 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
2275 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
2289 bitmask
= 0xf0 >> (bitoffset
& 7);
2290 dither
= Floyd4x4
[y
& 3];
2292 for (x
= xsize
; x
> 0; x
--)
2294 if ((*r0
& 15) > dither
[x
& 3])
2295 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
2297 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
2299 if (bitmask
== 0xf0)
2311 for (x
= xsize
; x
> 0; x
--, r0
++, r1
++)
2316 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2324 * 'format_KCMY()' - Convert image data to KCMY.
2328 format_KCMY(cups_page_header2_t
*header
,/* I - Page header */
2329 unsigned char *row
, /* IO - Bitmap data for device */
2330 int y
, /* I - Current row */
2331 int z
, /* I - Current plane */
2332 int xsize
, /* I - Width of image data */
2333 int ysize
, /* I - Height of image data */
2334 int yerr0
, /* I - Top Y error */
2335 int yerr1
, /* I - Bottom Y error */
2336 cups_ib_t
*r0
, /* I - Primary image data */
2337 cups_ib_t
*r1
) /* I - Image data for interpolation */
2339 cups_ib_t
*ptr
, /* Pointer into row */
2340 *cptr
, /* Pointer into cyan */
2341 *mptr
, /* Pointer into magenta */
2342 *yptr
, /* Pointer into yellow */
2343 *kptr
, /* Pointer into black */
2344 bitmask
; /* Current mask for pixel */
2345 int bitoffset
; /* Current offset in line */
2346 int bandwidth
; /* Width of a color band */
2347 int x
, /* Current X coordinate on page */
2348 *dither
; /* Pointer into dither array */
2349 int pc
, pm
, py
; /* CMY pixels */
2358 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2361 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2365 ptr
= row
+ bitoffset
/ 8;
2366 bandwidth
= header
->cupsBytesPerLine
/ 4;
2368 switch (header
->cupsColorOrder
)
2370 case CUPS_ORDER_CHUNKED
:
2371 switch (header
->cupsBitsPerColor
)
2374 bitmask
= 128 >> (bitoffset
& 7);
2375 dither
= Floyd16x16
[y
& 15];
2377 for (x
= xsize
; x
> 0; x
--)
2379 pc
= *r0
++ > dither
[x
& 15];
2380 pm
= *r0
++ > dither
[x
& 15];
2381 py
= *r0
++ > dither
[x
& 15];
2414 dither
= Floyd8x8
[y
& 7];
2416 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2418 if ((r0
[3] & 63) > dither
[x
& 7])
2419 *ptr
^= (0xc0 & OnPixels
[r0
[3]]);
2421 *ptr
^= (0xc0 & OffPixels
[r0
[3]]);
2423 if ((r0
[0] & 63) > dither
[x
& 7])
2424 *ptr
^= (0x30 & OnPixels
[r0
[0]]);
2426 *ptr
^= (0x30 & OffPixels
[r0
[0]]);
2428 if ((r0
[1] & 63) > dither
[x
& 7])
2429 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
2431 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
2433 if ((r0
[2] & 63) > dither
[x
& 7])
2434 *ptr
++ ^= (0x03 & OnPixels
[r0
[2]]);
2436 *ptr
++ ^= (0x03 & OffPixels
[r0
[2]]);
2441 dither
= Floyd4x4
[y
& 3];
2443 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2445 if ((r0
[3] & 15) > dither
[x
& 3])
2446 *ptr
^= (0xf0 & OnPixels
[r0
[3]]);
2448 *ptr
^= (0xf0 & OffPixels
[r0
[3]]);
2450 if ((r0
[0] & 15) > dither
[x
& 3])
2451 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
2453 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
2455 if ((r0
[1] & 15) > dither
[x
& 3])
2456 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
2458 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
2460 if ((r0
[2] & 15) > dither
[x
& 3])
2461 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
2463 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
2468 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2473 *ptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2478 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2483 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2488 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2494 case CUPS_ORDER_BANDED
:
2496 cptr
= ptr
+ bandwidth
;
2497 mptr
= ptr
+ 2 * bandwidth
;
2498 yptr
= ptr
+ 3 * bandwidth
;
2500 switch (header
->cupsBitsPerColor
)
2503 bitmask
= 0x80 >> (bitoffset
& 7);
2504 dither
= Floyd16x16
[y
& 15];
2506 for (x
= xsize
; x
> 0; x
--)
2508 pc
= *r0
++ > dither
[x
& 15];
2509 pm
= *r0
++ > dither
[x
& 15];
2510 py
= *r0
++ > dither
[x
& 15];
2538 bitmask
= 0xc0 >> (bitoffset
& 7);
2539 dither
= Floyd8x8
[y
& 7];
2541 for (x
= xsize
; x
> 0; x
--)
2543 if ((*r0
& 63) > dither
[x
& 7])
2544 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2546 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2548 if ((*r0
& 63) > dither
[x
& 7])
2549 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2551 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2553 if ((*r0
& 63) > dither
[x
& 7])
2554 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2556 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2558 if ((*r0
& 63) > dither
[x
& 7])
2559 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2561 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2578 bitmask
= 0xf0 >> (bitoffset
& 7);
2579 dither
= Floyd4x4
[y
& 3];
2581 for (x
= xsize
; x
> 0; x
--)
2583 if ((*r0
& 15) > dither
[x
& 3])
2584 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
2586 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
2588 if ((*r0
& 15) > dither
[x
& 3])
2589 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
2591 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
2593 if ((*r0
& 15) > dither
[x
& 3])
2594 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
2596 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
2598 if ((*r0
& 15) > dither
[x
& 3])
2599 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
2601 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
2603 if (bitmask
== 0xf0)
2618 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2623 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
2628 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
2633 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
2638 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
2644 case CUPS_ORDER_PLANAR
:
2645 switch (header
->cupsBitsPerColor
)
2648 bitmask
= 0x80 >> (bitoffset
& 7);
2649 dither
= Floyd16x16
[y
& 15];
2651 for (x
= xsize
; x
> 0; x
--)
2653 pc
= *r0
++ > dither
[x
& 15];
2654 pm
= *r0
++ > dither
[x
& 15];
2655 py
= *r0
++ > dither
[x
& 15];
2657 if ((pc
&& pm
&& py
&& z
== 0) ||
2658 (pc
&& z
== 1) || (pm
&& z
== 2) || (py
&& z
== 3))
2672 bitmask
= 0xc0 >> (bitoffset
& 7);
2673 dither
= Floyd8x8
[y
& 7];
2679 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2681 if ((*r0
& 63) > dither
[x
& 7])
2682 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2684 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2698 bitmask
= 0xf0 >> (bitoffset
& 7);
2699 dither
= Floyd4x4
[y
& 3];
2705 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
2707 if ((*r0
& 15) > dither
[x
& 3])
2708 *ptr
^= (bitmask
& OnPixels
[*r0
]);
2710 *ptr
^= (bitmask
& OffPixels
[*r0
]);
2712 if (bitmask
== 0xf0)
2735 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
2740 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
2750 * 'format_KCMYcm()' - Convert image data to KCMYcm.
2755 cups_page_header2_t
*header
, /* I - Page header */
2756 unsigned char *row
, /* IO - Bitmap data for device */
2757 int y
, /* I - Current row */
2758 int z
, /* I - Current plane */
2759 int xsize
, /* I - Width of image data */
2760 int ysize
, /* I - Height of image data */
2761 int yerr0
, /* I - Top Y error */
2762 int yerr1
, /* I - Bottom Y error */
2763 cups_ib_t
*r0
, /* I - Primary image data */
2764 cups_ib_t
*r1
) /* I - Image data for interpolation */
2766 int pc
, pm
, py
, pk
; /* Cyan, magenta, yellow, and black values */
2767 cups_ib_t
*ptr
, /* Pointer into row */
2768 *cptr
, /* Pointer into cyan */
2769 *mptr
, /* Pointer into magenta */
2770 *yptr
, /* Pointer into yellow */
2771 *kptr
, /* Pointer into black */
2772 *lcptr
, /* Pointer into light cyan */
2773 *lmptr
, /* Pointer into light magenta */
2774 bitmask
; /* Current mask for pixel */
2775 int bitoffset
; /* Current offset in line */
2776 int bandwidth
; /* Width of a color band */
2777 int x
, /* Current X coordinate on page */
2778 *dither
; /* Pointer into dither array */
2787 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2790 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2794 ptr
= row
+ bitoffset
/ 8;
2795 bandwidth
= header
->cupsBytesPerLine
/ 6;
2797 switch (header
->cupsColorOrder
)
2799 case CUPS_ORDER_CHUNKED
:
2800 dither
= Floyd16x16
[y
& 15];
2802 for (x
= xsize
; x
> 0; x
--)
2804 pc
= *r0
++ > dither
[x
& 15];
2805 pm
= *r0
++ > dither
[x
& 15];
2806 py
= *r0
++ > dither
[x
& 15];
2807 pk
= pc
&& pm
&& py
;
2810 *ptr
++ ^= 32; /* Black */
2812 *ptr
++ ^= 17; /* Blue (cyan + light magenta) */
2814 *ptr
++ ^= 6; /* Green (light cyan + yellow) */
2816 *ptr
++ ^= 12; /* Red (magenta + yellow) */
2828 case CUPS_ORDER_BANDED
:
2830 cptr
= ptr
+ bandwidth
;
2831 mptr
= ptr
+ 2 * bandwidth
;
2832 yptr
= ptr
+ 3 * bandwidth
;
2833 lcptr
= ptr
+ 4 * bandwidth
;
2834 lmptr
= ptr
+ 5 * bandwidth
;
2836 bitmask
= 0x80 >> (bitoffset
& 7);
2837 dither
= Floyd16x16
[y
& 15];
2839 for (x
= xsize
; x
> 0; x
--)
2841 pc
= *r0
++ > dither
[x
& 15];
2842 pm
= *r0
++ > dither
[x
& 15];
2843 py
= *r0
++ > dither
[x
& 15];
2844 pk
= pc
&& pm
&& py
;
2847 *kptr
^= bitmask
; /* Black */
2850 *cptr
^= bitmask
; /* Blue (cyan + light magenta) */
2855 *lcptr
^= bitmask
; /* Green (light cyan + yellow) */
2860 *mptr
^= bitmask
; /* Red (magenta + yellow) */
2885 case CUPS_ORDER_PLANAR
:
2886 bitmask
= 0x80 >> (bitoffset
& 7);
2887 dither
= Floyd16x16
[y
& 15];
2889 for (x
= xsize
; x
> 0; x
--)
2891 pc
= *r0
++ > dither
[x
& 15];
2892 pm
= *r0
++ > dither
[x
& 15];
2893 py
= *r0
++ > dither
[x
& 15];
2894 pk
= pc
&& pm
&& py
;
2898 else if (pc
&& pm
&& (z
== 1 || z
== 5))
2899 *ptr
^= bitmask
; /* Blue (cyan + light magenta) */
2900 else if (pc
&& py
&& (z
== 3 || z
== 4))
2901 *ptr
^= bitmask
; /* Green (light cyan + yellow) */
2902 else if (pm
&& py
&& (z
== 2 || z
== 3))
2903 *ptr
^= bitmask
; /* Red (magenta + yellow) */
2904 else if (pc
&& z
== 1)
2906 else if (pm
&& z
== 2)
2908 else if (py
&& z
== 3)
2925 * 'format_RGBA()' - Convert image data to RGBA/RGBW.
2929 format_RGBA(cups_page_header2_t
*header
,/* I - Page header */
2930 unsigned char *row
, /* IO - Bitmap data for device */
2931 int y
, /* I - Current row */
2932 int z
, /* I - Current plane */
2933 int xsize
, /* I - Width of image data */
2934 int ysize
, /* I - Height of image data */
2935 int yerr0
, /* I - Top Y error */
2936 int yerr1
, /* I - Bottom Y error */
2937 cups_ib_t
*r0
, /* I - Primary image data */
2938 cups_ib_t
*r1
) /* I - Image data for interpolation */
2940 cups_ib_t
*ptr
, /* Pointer into row */
2941 *cptr
, /* Pointer into cyan */
2942 *mptr
, /* Pointer into magenta */
2943 *yptr
, /* Pointer into yellow */
2944 bitmask
; /* Current mask for pixel */
2945 int bitoffset
; /* Current offset in line */
2946 int bandwidth
; /* Width of a color band */
2947 int x
, /* Current X coordinate on page */
2948 *dither
; /* Pointer into dither array */
2957 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
2960 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
2964 ptr
= row
+ bitoffset
/ 8;
2965 bandwidth
= header
->cupsBytesPerLine
/ 4;
2967 switch (header
->cupsColorOrder
)
2969 case CUPS_ORDER_CHUNKED
:
2970 switch (header
->cupsBitsPerColor
)
2973 bitmask
= 128 >> (bitoffset
& 7);
2974 dither
= Floyd16x16
[y
& 15];
2976 for (x
= xsize
; x
> 0; x
--)
2978 if (*r0
++ > dither
[x
& 15])
2982 if (*r0
++ > dither
[x
& 15])
2986 if (*r0
++ > dither
[x
& 15])
3000 dither
= Floyd8x8
[y
& 7];
3002 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3004 if ((r0
[0] & 63) > dither
[x
& 7])
3005 *ptr
^= (0xc0 & OnPixels
[r0
[0]]);
3007 *ptr
^= (0xc0 & OffPixels
[r0
[0]]);
3009 if ((r0
[1] & 63) > dither
[x
& 7])
3010 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
3012 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
3014 if ((r0
[2] & 63) > dither
[x
& 7])
3015 *ptr
^= (0x0c & OnPixels
[r0
[2]]);
3017 *ptr
^= (0x0c & OffPixels
[r0
[2]]);
3024 dither
= Floyd4x4
[y
& 3];
3026 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3028 if ((r0
[0] & 15) > dither
[x
& 3])
3029 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
3031 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
3033 if ((r0
[1] & 15) > dither
[x
& 3])
3034 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
3036 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
3038 if ((r0
[2] & 15) > dither
[x
& 3])
3039 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
3041 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
3048 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3053 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3058 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3063 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3071 case CUPS_ORDER_BANDED
:
3073 mptr
= ptr
+ bandwidth
;
3074 yptr
= ptr
+ 2 * bandwidth
;
3076 memset(ptr
+ 3 * bandwidth
, 255, bandwidth
);
3078 switch (header
->cupsBitsPerColor
)
3081 bitmask
= 0x80 >> (bitoffset
& 7);
3082 dither
= Floyd16x16
[y
& 15];
3084 for (x
= xsize
; x
> 0; x
--)
3086 if (*r0
++ > dither
[x
& 15])
3088 if (*r0
++ > dither
[x
& 15])
3090 if (*r0
++ > dither
[x
& 15])
3106 bitmask
= 0xc0 >> (bitoffset
& 7);
3107 dither
= Floyd8x8
[y
& 7];
3109 for (x
= xsize
; x
> 0; x
--)
3111 if ((*r0
& 63) > dither
[x
& 7])
3112 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3114 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3116 if ((*r0
& 63) > dither
[x
& 7])
3117 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3119 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3121 if ((*r0
& 63) > dither
[x
& 7])
3122 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3124 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3140 bitmask
= 0xf0 >> (bitoffset
& 7);
3141 dither
= Floyd4x4
[y
& 3];
3143 for (x
= xsize
; x
> 0; x
--)
3145 if ((*r0
& 15) > dither
[x
& 3])
3146 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3148 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3150 if ((*r0
& 15) > dither
[x
& 3])
3151 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3153 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3155 if ((*r0
& 15) > dither
[x
& 3])
3156 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3158 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3160 if (bitmask
== 0xf0)
3174 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3179 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3184 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3189 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3195 case CUPS_ORDER_PLANAR
:
3198 memset(row
, 255, header
->cupsBytesPerLine
);
3202 switch (header
->cupsBitsPerColor
)
3205 bitmask
= 0x80 >> (bitoffset
& 7);
3206 dither
= Floyd16x16
[y
& 15];
3211 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3213 if (r0
[0] > dither
[x
& 15])
3227 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3229 if (r0
[1] > dither
[x
& 15])
3243 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3245 if (r0
[2] > dither
[x
& 15])
3261 bitmask
= 0xc0 >> (bitoffset
& 7);
3262 dither
= Floyd8x8
[y
& 7];
3265 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3267 if ((*r0
& 63) > dither
[x
& 7])
3268 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3270 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3284 bitmask
= 0xf0 >> (bitoffset
& 7);
3285 dither
= Floyd4x4
[y
& 3];
3288 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3290 if ((*r0
& 15) > dither
[x
& 3])
3291 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3293 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3295 if (bitmask
== 0xf0)
3310 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3315 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3325 * 'format_W()' - Convert image data to luminance.
3329 format_W(cups_page_header2_t
*header
, /* I - Page header */
3330 unsigned char *row
, /* IO - Bitmap data for device */
3331 int y
, /* I - Current row */
3332 int z
, /* I - Current plane */
3333 int xsize
, /* I - Width of image data */
3334 int ysize
, /* I - Height of image data */
3335 int yerr0
, /* I - Top Y error */
3336 int yerr1
, /* I - Bottom Y error */
3337 cups_ib_t
*r0
, /* I - Primary image data */
3338 cups_ib_t
*r1
) /* I - Image data for interpolation */
3340 cups_ib_t
*ptr
, /* Pointer into row */
3341 bitmask
; /* Current mask for pixel */
3342 int bitoffset
; /* Current offset in line */
3343 int x
, /* Current X coordinate on page */
3344 *dither
; /* Pointer into dither array */
3355 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3358 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3362 ptr
= row
+ bitoffset
/ 8;
3364 switch (header
->cupsBitsPerColor
)
3367 bitmask
= 0x80 >> (bitoffset
& 7);
3368 dither
= Floyd16x16
[y
& 15];
3370 for (x
= xsize
; x
> 0; x
--)
3372 if (*r0
++ > dither
[x
& 15])
3386 bitmask
= 0xc0 >> (bitoffset
& 7);
3387 dither
= Floyd8x8
[y
& 7];
3389 for (x
= xsize
; x
> 0; x
--)
3391 if ((*r0
& 63) > dither
[x
& 7])
3392 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
3394 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
3408 bitmask
= 0xf0 >> (bitoffset
& 7);
3409 dither
= Floyd4x4
[y
& 3];
3411 for (x
= xsize
; x
> 0; x
--)
3413 if ((*r0
& 15) > dither
[x
& 3])
3414 *ptr
^= (bitmask
& OnPixels
[*r0
++]);
3416 *ptr
^= (bitmask
& OffPixels
[*r0
++]);
3418 if (bitmask
== 0xf0)
3430 for (x
= xsize
; x
> 0; x
--, r0
++, r1
++)
3435 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3443 * 'format_YMC()' - Convert image data to YMC.
3447 format_YMC(cups_page_header2_t
*header
, /* I - Page header */
3448 unsigned char *row
, /* IO - Bitmap data for device */
3449 int y
, /* I - Current row */
3450 int z
, /* I - Current plane */
3451 int xsize
, /* I - Width of image data */
3452 int ysize
, /* I - Height of image data */
3453 int yerr0
, /* I - Top Y error */
3454 int yerr1
, /* I - Bottom Y error */
3455 cups_ib_t
*r0
, /* I - Primary image data */
3456 cups_ib_t
*r1
) /* I - Image data for interpolation */
3458 cups_ib_t
*ptr
, /* Pointer into row */
3459 *cptr
, /* Pointer into cyan */
3460 *mptr
, /* Pointer into magenta */
3461 *yptr
, /* Pointer into yellow */
3462 bitmask
; /* Current mask for pixel */
3463 int bitoffset
; /* Current offset in line */
3464 int bandwidth
; /* Width of a color band */
3465 int x
, /* Current X coordinate on page */
3466 *dither
; /* Pointer into dither array */
3475 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3478 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3482 ptr
= row
+ bitoffset
/ 8;
3483 bandwidth
= header
->cupsBytesPerLine
/ 3;
3485 switch (header
->cupsColorOrder
)
3487 case CUPS_ORDER_CHUNKED
:
3488 switch (header
->cupsBitsPerColor
)
3491 bitmask
= 64 >> (bitoffset
& 7);
3492 dither
= Floyd16x16
[y
& 15];
3494 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3496 if (r0
[2] > dither
[x
& 15])
3500 if (r0
[1] > dither
[x
& 15])
3504 if (r0
[0] > dither
[x
& 15])
3518 dither
= Floyd8x8
[y
& 7];
3520 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3522 if ((r0
[2] & 63) > dither
[x
& 7])
3523 *ptr
^= (0x30 & OnPixels
[r0
[2]]);
3525 *ptr
^= (0x30 & OffPixels
[r0
[2]]);
3527 if ((r0
[1] & 63) > dither
[x
& 7])
3528 *ptr
^= (0x0c & OnPixels
[r0
[1]]);
3530 *ptr
^= (0x0c & OffPixels
[r0
[1]]);
3532 if ((r0
[0] & 63) > dither
[x
& 7])
3533 *ptr
++ ^= (0x03 & OnPixels
[r0
[0]]);
3535 *ptr
++ ^= (0x03 & OffPixels
[r0
[0]]);
3540 dither
= Floyd4x4
[y
& 3];
3542 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3544 if ((r0
[2] & 15) > dither
[x
& 3])
3545 *ptr
++ ^= (0x0f & OnPixels
[r0
[2]]);
3547 *ptr
++ ^= (0x0f & OffPixels
[r0
[2]]);
3549 if ((r0
[1] & 15) > dither
[x
& 3])
3550 *ptr
^= (0xf0 & OnPixels
[r0
[1]]);
3552 *ptr
^= (0xf0 & OffPixels
[r0
[1]]);
3554 if ((r0
[0] & 15) > dither
[x
& 3])
3555 *ptr
++ ^= (0x0f & OnPixels
[r0
[0]]);
3557 *ptr
++ ^= (0x0f & OffPixels
[r0
[0]]);
3562 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3567 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3572 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3577 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3583 case CUPS_ORDER_BANDED
:
3585 mptr
= ptr
+ bandwidth
;
3586 cptr
= ptr
+ 2 * bandwidth
;
3588 switch (header
->cupsBitsPerColor
)
3591 bitmask
= 0x80 >> (bitoffset
& 7);
3592 dither
= Floyd16x16
[y
& 15];
3594 for (x
= xsize
; x
> 0; x
--)
3596 if (*r0
++ > dither
[x
& 15])
3598 if (*r0
++ > dither
[x
& 15])
3600 if (*r0
++ > dither
[x
& 15])
3616 bitmask
= 0xc0 >> (bitoffset
& 7);
3617 dither
= Floyd8x8
[y
& 7];
3619 for (x
= xsize
; x
> 0; x
--)
3621 if ((*r0
& 63) > dither
[x
& 7])
3622 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3624 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3626 if ((*r0
& 63) > dither
[x
& 7])
3627 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3629 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3631 if ((*r0
& 63) > dither
[x
& 7])
3632 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3634 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3650 bitmask
= 0xf0 >> (bitoffset
& 7);
3651 dither
= Floyd4x4
[y
& 3];
3653 for (x
= xsize
; x
> 0; x
--)
3655 if ((*r0
& 15) > dither
[x
& 3])
3656 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
3658 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
3660 if ((*r0
& 15) > dither
[x
& 3])
3661 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
3663 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
3665 if ((*r0
& 15) > dither
[x
& 3])
3666 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
3668 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
3670 if (bitmask
== 0xf0)
3684 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3689 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3694 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3699 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3705 case CUPS_ORDER_PLANAR
:
3706 switch (header
->cupsBitsPerColor
)
3709 bitmask
= 0x80 >> (bitoffset
& 7);
3710 dither
= Floyd16x16
[y
& 15];
3715 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3717 if (r0
[0] > dither
[x
& 15])
3731 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3733 if (r0
[1] > dither
[x
& 15])
3747 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3749 if (r0
[2] > dither
[x
& 15])
3765 bitmask
= 0xc0 >> (bitoffset
& 7);
3766 dither
= Floyd8x8
[y
& 7];
3770 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3772 if ((*r0
& 63) > dither
[x
& 7])
3773 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3775 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3789 bitmask
= 0xf0 >> (bitoffset
& 7);
3790 dither
= Floyd4x4
[y
& 3];
3794 for (x
= xsize
; x
> 0; x
--, r0
+= 3)
3796 if ((*r0
& 15) > dither
[x
& 3])
3797 *ptr
^= (bitmask
& OnPixels
[*r0
]);
3799 *ptr
^= (bitmask
& OffPixels
[*r0
]);
3801 if (bitmask
== 0xf0)
3817 for (x
= xsize
; x
> 0; x
--, r0
+= 3, r1
+= 3)
3822 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
3832 * 'format_YMCK()' - Convert image data to YMCK.
3836 format_YMCK(cups_page_header2_t
*header
,/* I - Page header */
3837 unsigned char *row
, /* IO - Bitmap data for device */
3838 int y
, /* I - Current row */
3839 int z
, /* I - Current plane */
3840 int xsize
, /* I - Width of image data */
3841 int ysize
, /* I - Height of image data */
3842 int yerr0
, /* I - Top Y error */
3843 int yerr1
, /* I - Bottom Y error */
3844 cups_ib_t
*r0
, /* I - Primary image data */
3845 cups_ib_t
*r1
) /* I - Image data for interpolation */
3847 cups_ib_t
*ptr
, /* Pointer into row */
3848 *cptr
, /* Pointer into cyan */
3849 *mptr
, /* Pointer into magenta */
3850 *yptr
, /* Pointer into yellow */
3851 *kptr
, /* Pointer into black */
3852 bitmask
; /* Current mask for pixel */
3853 int bitoffset
; /* Current offset in line */
3854 int bandwidth
; /* Width of a color band */
3855 int x
, /* Current X coordinate on page */
3856 *dither
; /* Pointer into dither array */
3857 int pc
, pm
, py
; /* CMY pixels */
3866 bitoffset
= header
->cupsBitsPerPixel
* ((header
->cupsWidth
- xsize
) / 2);
3869 bitoffset
= header
->cupsBitsPerPixel
* (header
->cupsWidth
- xsize
);
3873 ptr
= row
+ bitoffset
/ 8;
3874 bandwidth
= header
->cupsBytesPerLine
/ 4;
3876 switch (header
->cupsColorOrder
)
3878 case CUPS_ORDER_CHUNKED
:
3879 switch (header
->cupsBitsPerColor
)
3882 bitmask
= 128 >> (bitoffset
& 7);
3883 dither
= Floyd16x16
[y
& 15];
3885 for (x
= xsize
; x
> 0; x
--)
3887 pc
= *r0
++ > dither
[x
& 15];
3888 pm
= *r0
++ > dither
[x
& 15];
3889 py
= *r0
++ > dither
[x
& 15];
3923 dither
= Floyd8x8
[y
& 7];
3925 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
3927 if ((r0
[2] & 63) > dither
[x
& 7])
3928 *ptr
^= (0xc0 & OnPixels
[r0
[2]]);
3930 *ptr
^= (0xc0 & OffPixels
[r0
[2]]);
3932 if ((r0
[1] & 63) > dither
[x
& 7])
3933 *ptr
^= (0x30 & OnPixels
[r0
[1]]);
3935 *ptr
^= (0x30 & OffPixels
[r0
[1]]);
3937 if ((r0
[0] & 63) > dither
[x
& 7])
3938 *ptr
^= (0x0c & OnPixels
[r0
[0]]);
3940 *ptr
^= (0x0c & OffPixels
[r0
[0]]);
3942 if ((r0
[3] & 63) > dither
[x
& 7])
3943 *ptr
++ ^= (0x03 & OnPixels
[r0
[3]]);
3945 *ptr
++ ^= (0x03 & OffPixels
[r0
[3]]);
3950 dither
= Floyd4x4
[y
& 3];
3952 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
3954 if ((r0
[2] & 15) > dither
[x
& 3])
3955 *ptr
^= (0xf0 & OnPixels
[r0
[2]]);
3957 *ptr
^= (0xf0 & OffPixels
[r0
[2]]);
3959 if ((r0
[1] & 15) > dither
[x
& 3])
3960 *ptr
++ ^= (0x0f & OnPixels
[r0
[1]]);
3962 *ptr
++ ^= (0x0f & OffPixels
[r0
[1]]);
3964 if ((r0
[0] & 15) > dither
[x
& 3])
3965 *ptr
^= (0xf0 & OnPixels
[r0
[0]]);
3967 *ptr
^= (0xf0 & OffPixels
[r0
[0]]);
3969 if ((r0
[3] & 15) > dither
[x
& 3])
3970 *ptr
++ ^= (0x0f & OnPixels
[r0
[3]]);
3972 *ptr
++ ^= (0x0f & OffPixels
[r0
[3]]);
3977 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
3982 *ptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
3987 *ptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
3992 *ptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
3997 *ptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
4003 case CUPS_ORDER_BANDED
:
4005 mptr
= ptr
+ bandwidth
;
4006 cptr
= ptr
+ 2 * bandwidth
;
4007 kptr
= ptr
+ 3 * bandwidth
;
4009 switch (header
->cupsBitsPerColor
)
4012 bitmask
= 0x80 >> (bitoffset
& 7);
4013 dither
= Floyd16x16
[y
& 15];
4015 for (x
= xsize
; x
> 0; x
--)
4017 pc
= *r0
++ > dither
[x
& 15];
4018 pm
= *r0
++ > dither
[x
& 15];
4019 py
= *r0
++ > dither
[x
& 15];
4048 bitmask
= 0xc0 >> (bitoffset
& 7);
4049 dither
= Floyd8x8
[y
& 7];
4051 for (x
= xsize
; x
> 0; x
--)
4053 if ((*r0
& 63) > dither
[x
& 7])
4054 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
4056 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
4058 if ((*r0
& 63) > dither
[x
& 7])
4059 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
4061 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
4063 if ((*r0
& 63) > dither
[x
& 7])
4064 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
4066 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
4068 if ((*r0
& 63) > dither
[x
& 7])
4069 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
4071 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
4088 bitmask
= 0xf0 >> (bitoffset
& 7);
4089 dither
= Floyd4x4
[y
& 3];
4091 for (x
= xsize
; x
> 0; x
--)
4093 if ((*r0
& 15) > dither
[x
& 3])
4094 *cptr
^= (bitmask
& OnPixels
[*r0
++]);
4096 *cptr
^= (bitmask
& OffPixels
[*r0
++]);
4098 if ((*r0
& 15) > dither
[x
& 3])
4099 *mptr
^= (bitmask
& OnPixels
[*r0
++]);
4101 *mptr
^= (bitmask
& OffPixels
[*r0
++]);
4103 if ((*r0
& 15) > dither
[x
& 3])
4104 *yptr
^= (bitmask
& OnPixels
[*r0
++]);
4106 *yptr
^= (bitmask
& OffPixels
[*r0
++]);
4108 if ((*r0
& 15) > dither
[x
& 3])
4109 *kptr
^= (bitmask
& OnPixels
[*r0
++]);
4111 *kptr
^= (bitmask
& OffPixels
[*r0
++]);
4113 if (bitmask
== 0xf0)
4128 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
4133 *cptr
++ = (r0
[0] * yerr0
+ r1
[0] * yerr1
) / ysize
;
4138 *mptr
++ = (r0
[1] * yerr0
+ r1
[1] * yerr1
) / ysize
;
4143 *yptr
++ = (r0
[2] * yerr0
+ r1
[2] * yerr1
) / ysize
;
4148 *kptr
++ = (r0
[3] * yerr0
+ r1
[3] * yerr1
) / ysize
;
4154 case CUPS_ORDER_PLANAR
:
4155 switch (header
->cupsBitsPerColor
)
4158 bitmask
= 0x80 >> (bitoffset
& 7);
4159 dither
= Floyd16x16
[y
& 15];
4161 for (x
= xsize
; x
> 0; x
--)
4163 pc
= *r0
++ > dither
[x
& 15];
4164 pm
= *r0
++ > dither
[x
& 15];
4165 py
= *r0
++ > dither
[x
& 15];
4167 if ((pc
&& pm
&& py
&& z
== 3) ||
4168 (pc
&& z
== 2) || (pm
&& z
== 1) || (py
&& z
== 0))
4182 bitmask
= 0xc0 >> (bitoffset
& 7);
4183 dither
= Floyd8x8
[y
& 7];
4189 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
4191 if ((*r0
& 63) > dither
[x
& 7])
4192 *ptr
^= (bitmask
& OnPixels
[*r0
]);
4194 *ptr
^= (bitmask
& OffPixels
[*r0
]);
4208 bitmask
= 0xf0 >> (bitoffset
& 7);
4209 dither
= Floyd4x4
[y
& 3];
4215 for (x
= xsize
; x
> 0; x
--, r0
+= 4)
4217 if ((*r0
& 15) > dither
[x
& 3])
4218 *ptr
^= (bitmask
& OnPixels
[*r0
]);
4220 *ptr
^= (bitmask
& OffPixels
[*r0
]);
4222 if (bitmask
== 0xf0)
4245 for (x
= xsize
; x
> 0; x
--, r0
+= 4, r1
+= 4)
4250 *ptr
++ = (*r0
* yerr0
+ *r1
* yerr1
) / ysize
;
4260 * 'make_lut()' - Make a lookup table given gamma and brightness values.
4264 make_lut(cups_ib_t
*lut
, /* I - Lookup table */
4265 int colorspace
, /* I - Colorspace */
4266 float g
, /* I - Image gamma */
4267 float b
) /* I - Image brightness */
4269 int i
; /* Looping var */
4270 int v
; /* Current value */
4276 for (i
= 0; i
< 256; i
++)
4279 v
= 255.0 * b
* (1.0 - pow(1.0 - (float)i
/ 255.0, g
)) + 0.5;
4281 v
= 255.0 * (1.0 - b
* (1.0 - pow((float)i
/ 255.0, g
))) + 0.5;
4294 * 'raster_cb()' - Validate the page header.
4297 static int /* O - 0 if OK, -1 if not */
4299 cups_page_header2_t
*header
, /* IO - Raster header */
4300 int preferred_bits
) /* I - Preferred bits per color */
4303 * Ensure that colorimetric colorspaces use at least 8 bits per
4307 if ((header
->cupsColorSpace
== CUPS_CSPACE_CIEXYZ
||
4308 header
->cupsColorSpace
== CUPS_CSPACE_CIELab
||
4309 header
->cupsColorSpace
>= CUPS_CSPACE_ICC1
) &&
4310 header
->cupsBitsPerColor
< 8)
4311 header
->cupsBitsPerColor
= 8;
4318 * End of "$Id: imagetoraster.c 7306 2008-02-15 00:52:38Z mike $".