-
-
Save defremov/eda5e00596f2eded8b85 to your computer and use it in GitHub Desktop.
| diff --git a/foo2hbpl1.c b/foo2hbpl1.c | |
| index fb4f448..d0ad6cd 100644 | |
| --- a/foo2hbpl1.c | |
| +++ b/foo2hbpl1.c | |
| @@ -52,11 +52,38 @@ static char Version[] = "$Id: foo2hbpl1.c,v 1.3 2014/03/30 05:08:32 rick Exp $"; | |
| /* | |
| * Command line options | |
| */ | |
| -int MediaCode = 0; | |
| +char *ClutFilePath = NULL; | |
| +int DocType = 0; | |
| +int OutputColor = 0; | |
| +int DraftMode = 0; | |
| +int NumCopies = 1; | |
| +int Trapping = 0; | |
| +int Screen = 0; | |
| +int MediaCode = 1; | |
| char *Username = NULL; | |
| char *Filename = NULL; | |
| int Clip[] = { 8,8,8,8 }; | |
| +char *cb_cmyk = "CMYK"; | |
| +char *cb_lmh = "LMH"; | |
| +char ColorBalance[] = | |
| +/* +--- L = Low | |
| + |+-- M = Medium | |
| + ||+- H = High | |
| + ||| */ | |
| + "333" /* C = Cyan */ | |
| + "333" /* M = Magenta */ | |
| + "333" /* Y = Yellow */ | |
| + "333"; /* K = Black */ | |
| +/* | |
| + 0 = Lighter (-3) | |
| + 1 = Lighter (-2) | |
| + 2 = Lighter (-1) | |
| + * 3 = Normal | |
| + 4 = Darker (+1) | |
| + 5 = Darker (+2) | |
| + 6 = Darker (+3) */ | |
| + | |
| void | |
| usage(void) | |
| { | |
| @@ -73,15 +100,73 @@ usage(void) | |
| " | foo2hbpl1 >testpage.zc\n" | |
| "\n" | |
| "Options:\n" | |
| -"-m media Media code to send to printer [1 or 6]\n" | |
| -" 1=plain, 2=bond, 3=lwcard, 4=lwgcard, 5=labels,\n" | |
| -" 6=envelope, 7=recycled, 8=plain2, 9=bond2,\n" | |
| -" 10=lwcard2, 11=lwgcard2, 12=recycled2\n" | |
| +"-a values Color balance adjustment [default: %s]\n" | |
| +" Argument is a string of 12 adjustment values\n" | |
| +" in range of 0..6 each:\n" | |
| +" 0 = Lighter (-3)\n" | |
| +" 1 = Lighter (-2)\n" | |
| +" 2 = Lighter (-1)\n" | |
| +" 3 = Normal\n" | |
| +" 4 = Darker (+1)\n" | |
| +" 5 = Darker (+2)\n" | |
| +" 6 = Darker (+3)\n" | |
| +" in the following order:\n" | |
| +" |C|C|C|M|M|M|Y|Y|Y|K|K|K|\n" | |
| +" |l|m|h|l|m|h|l|m|h|l|m|h|\n" | |
| +" where C=Cyan, M=Magenta, Y=Yellow, K=Black,\n" | |
| +" l=Low, m=Medium, h=High.\n" | |
| +"-c Print ppmraw in color mode.\n" | |
| +" If not set print in black and white.\n" | |
| +" Has no effect if document type (-i option) is 0\n" | |
| +"-i type Document type code for print quality\n" | |
| +" adjustment of ppmraw input [default: %d]\n" | |
| +" 0=No adjustment, 1=Standard, 2=Photos,\n" | |
| +" 3=Presentation, 4=Web Pages, 5=POP, 6=None\n" | |
| +"-l path Pathname of the file containing color\n" | |
| +" look-up tables. Must be specified for\n" | |
| +" document types 1..5 in color mode.\n" | |
| +"-m media Media code to send to printer [default: %d]\n" | |
| +" 1=Plain\n" | |
| +" 2=Plain, side 2\n" | |
| +" 3=Bond\n" | |
| +" 4=Bond, side 2\n" | |
| +" 5=Recycled\n" | |
| +" 6=Recycled, side 2\n" | |
| +" 7=Labels\n" | |
| +" 8=Lightweight Cardstock\n" | |
| +" 9=Lightweight Cardstock, side 2\n" | |
| +" 10=Lightweight Glossy Cardstock\n" | |
| +" 11=Lightweight Glossy Cardstock, side 2\n" | |
| +" 12=Letterhead\n" | |
| +" 13=Letterhead, side 2\n" | |
| +" 14=Pre-Printed\n" | |
| +" 15=Pre-Printed, side 2\n" | |
| +" 16=Hole Punched\n" | |
| +" 17=Hole Punched, side 2\n" | |
| +" 18=Colored\n" | |
| +" 19=Colored, side 2\n" | |
| +" 20=Custom Type\n" | |
| +" 21=Custom Type, side 2\n" | |
| +" 22=Special\n" | |
| +" 23=Special, side 2\n" | |
| +" 24=Envelope\n" | |
| +"-n copies Number of copies, 1..100 [default: %d]\n" | |
| +"-s type Screen type code [default: %d]\n" | |
| +" 0=Auto, 1=Fineness, 2=Standard, 3=Gradation\n" | |
| +"-t Print ppmraw in draft mode.\n" | |
| +" Has no effect if document type (-i option) is 0\n" | |
| "-u left,top,right,bottom\n" | |
| -" Erase margins of specified width [%d,%d,%d,%d]\n" | |
| +" Erase margins of specified width\n" | |
| +" [default: %d,%d,%d,%d]\n" | |
| "-J filename Filename string to send to printer\n" | |
| +"-T Turn trapping on.\n" | |
| "-U username Username string to send to printer\n" | |
| "-V Version %s\n" | |
| + , ColorBalance | |
| + , DocType | |
| + , MediaCode | |
| + , NumCopies | |
| + , Screen | |
| , Clip[0], Clip[1], Clip[2], Clip[3] | |
| , Version); | |
| } | |
| @@ -98,6 +183,37 @@ error(int fatal, char *fmt, ...) | |
| if (fatal) exit(fatal); | |
| } | |
| +enum doc_type_id { | |
| + DOC_NORMAL, | |
| + DOC_PHOTO, | |
| + DOC_PRESENTATION, | |
| + DOC_WEB, | |
| + DOC_POP, | |
| + DOC_NONE | |
| +}; | |
| + | |
| +struct doc_type_jobattr | |
| +{ | |
| + int color, mono; | |
| +} screen_jobattr_index[] = { | |
| + {61, 64}, // Fineness | |
| + {62, 65}, // Standard | |
| + {63, 66} // Gradation | |
| + }; | |
| + | |
| +static const struct doc_type | |
| +{ | |
| + int clut_id; | |
| + struct doc_type_jobattr jobattr; | |
| +} doc_type_index[] = { | |
| + { 0, {11, 33}}, // Normal | |
| + { 2, {14, 33}}, // Photo | |
| + { 3, {15, 33}}, // Presentation | |
| + { 5, {17, 33}}, // Web | |
| + { 7, {19, 33}}, // POP | |
| + {18, {31, 33}} // Off | |
| + }; | |
| + | |
| struct stream | |
| { | |
| unsigned char *buf; | |
| @@ -262,20 +378,38 @@ start_doc(int color) | |
| struct tm *tmp; | |
| char datestr[16], timestr[16]; | |
| char cname[128] = "My Computer"; | |
| + int i, doc_type_id; | |
| + static const char *doc_type_jobattr_cprucr[] = {"CPR", "UCR"}; | |
| + static const char *doc_type_jobattr_trcscr[] = {"TRC", "SCR"}; | |
| + static const char *doc_type_jobattr_prefix = "TGI"; | |
| + int doc_type_jobattr = 0; | |
| + const struct doc_type_jobattr *s_doc_type_jobattr = NULL; | |
| char *mname[] = | |
| - { "", | |
| - "NORMAL", | |
| - "THICK", | |
| - "HIGHQUALITY", | |
| - "COAT2", | |
| - "LABEL", | |
| - "ENVELOPE", | |
| - "RECYCLED", | |
| - "NORMALREV", | |
| - "THICKSIDE2", | |
| - "HIGHQUALITYREV", | |
| - "COATEDPAPER2REV", | |
| - "RECYCLEREV", | |
| + { | |
| + "NORMAL", | |
| + "NORMALREV", | |
| + "HIGHQUALITY", | |
| + "HIGHQUALITYREV", | |
| + "RECYCLE", | |
| + "RECYCLEREV", | |
| + "LABEL", | |
| + "THICK", | |
| + "THICKSIDE2", | |
| + "COATEDPAPER2", | |
| + "COATEDPAPER2REV", | |
| + "LETTERHEAD", | |
| + "LETTERHEADREV", | |
| + "PREPRINTED", | |
| + "PREPRINTEDREV", | |
| + "PREPUNCHED", | |
| + "PREPUNCHEDREV", | |
| + "COLOR", | |
| + "COLORREV", | |
| + "USER1", | |
| + "USER1REV", | |
| + "SPECIAL", | |
| + "SPECIALREV", | |
| + "ENVELOPE" | |
| }; | |
| t = time(NULL); | |
| @@ -296,54 +430,98 @@ start_doc(int color) | |
| /* Lines end with \n, not \r\n */ | |
| printf( | |
| - "\033%%-12345X@PJL SET STRINGCODESET=UTF8\n" | |
| - "@PJL COMMENT DATE=%s\n" | |
| - "@PJL COMMENT TIME=%s\n" | |
| - "@PJL COMMENT DNAME=%s\n" | |
| - "@PJL JOB MODE=PRINTER\n" | |
| - "@PJL SET JOBATTR=\"@LUNA=%s\"\n" | |
| - "@PJL SET JOBATTR=\"@TRCH=OFF\"\n" | |
| - "@PJL SET DUPLEX=OFF\n" | |
| - "@PJL SET BINDING=LONGEDGE\n" | |
| - "@PJL SET IWAMANUALDUP=OFF\n" | |
| - "@PJL SET JOBATTR=\"@MSIP=%s\"\n" | |
| - "@PJL SET RENDERMODE=%s\n" | |
| - "@PJL SET ECONOMODE=OFF\n" | |
| - "@PJL SET RET=ON\n" | |
| - "@PJL SET JOBATTR=\"@IREC=OFF\"\n" | |
| - "@PJL SET JOBATTR=\"@TRAP=ON\"\n" | |
| - "@PJL SET JOBATTR=\"@JOAU=%s\"\n" | |
| - "@PJL SET JOBATTR=\"@CNAM=%s\"\n" | |
| - "@PJL SET COPIES=1\n" | |
| - "@PJL SET QTY=1\n" | |
| - "@PJL SET PAPERDIRECTION=SEF\n" | |
| - "@PJL SET RESOLUTION=600\n" | |
| - "@PJL SET BITSPERPIXEL=8\n" | |
| - "@PJL SET JOBATTR=\"@DRDM=XRC\"\n" | |
| - "@PJL SET JOBATTR=\"@TSCR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@GSCR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@ISCR=12\"\n" | |
| - "@PJL SET JOBATTR=\"@TTRC=11\"\n" | |
| - "@PJL SET JOBATTR=\"@GTRC=11\"\n" | |
| - "@PJL SET JOBATTR=\"@ITRC=12\"\n" | |
| - "@PJL SET JOBATTR=\"@TCPR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@GCPR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@ICPR=12\"\n" | |
| - "@PJL SET JOBATTR=\"@TUCR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@GUCR=11\"\n" | |
| - "@PJL SET JOBATTR=\"@IUCR=12\"\n" | |
| - "@PJL SET JOBATTR=\"@BSPM=OFF\"\n" | |
| - "@PJL SET JOBATTR=\"@TDFT=0\"\n" | |
| - "@PJL SET JOBATTR=\"@GDFT=0\"\n" | |
| - "@PJL SET JOBATTR=\"@IDFT=0\"\n" | |
| - "@PJL ENTER LANGUAGE=HBPL\n" | |
| - , datestr, timestr | |
| - , Filename ? Filename : "" | |
| - , Username ? Username : "" | |
| - , mname[MediaCode] | |
| - , color ? "COLOR" : "GRAYSCALE" | |
| - , Username ? Username : "" | |
| - , cname); | |
| + "\033%%-12345X@PJL JOB MODE=PRINTER\n" | |
| + "@PJL SET STRINGCODESET=UTF8\n" | |
| + ); | |
| + | |
| + printf("@PJL COMMENT DATE=%s\n", datestr); | |
| + printf("@PJL COMMENT TIME=%s\n", timestr); | |
| + printf("@PJL COMMENT DNAME=%s\n", Filename ? Filename : ""); | |
| + printf("@PJL SET JOBATTR=\"@LUNA=%s\"\n", Username ? Username : ""); | |
| + printf("@PJL SET COPIES=%d\n", NumCopies); | |
| + | |
| + printf( | |
| + "@PJL SET JOBATTR=\"@TRCH=OFF\"\n" | |
| + "@PJL SET DUPLEX=OFF\n" | |
| + ); | |
| + | |
| + for (i = 0; i < 12; i++) { | |
| + printf("@PJL SET JOBATTR=\"@AJ%c%c=%c\"\n", | |
| + cb_cmyk[i / 3], cb_lmh[i % 3], ColorBalance[i]); | |
| + } | |
| + | |
| + printf("@PJL SET JOBATTR=\"@APSP=OFF\"\n"); | |
| + | |
| + printf("@PJL SET JOBATTR=\"@MSIP=%s\"\n", mname[MediaCode - 1]); | |
| + printf("@PJL SET RENDERMODE=%s\n", color ? "COLOR" : "GRAYSCALE"); | |
| + printf("@PJL SET ECONOMODE=%s\n", DraftMode ? "ON" : "OFF"); | |
| + | |
| + printf("@PJL SET JOBATTR=\"@IREC=OFF\"\n"); | |
| + | |
| + printf("@PJL SET JOBATTR=\"@TRAP=%s\"\n", | |
| + color && Trapping ? "ON" : "OFF"); | |
| + | |
| + // "ON" only if 'Image Enhancement' option is enabled in original Xerox's driver. | |
| + printf("@PJL SET RET=%s\n", "OFF"); | |
| + | |
| + printf( | |
| + "@PJL SET JOBATTR=\"@TDFT=0\"\n" | |
| + "@PJL SET JOBATTR=\"@GDFT=0\"\n" | |
| + "@PJL SET JOBATTR=\"@IDFT=0\"\n" | |
| + "@PJL SET JOBATTR=\"@NLPP=1\"\n" | |
| + "@PJL SET JOBATTR=\"@HOAD=IC0A809\"\n" | |
| + ); | |
| + | |
| + printf("@PJL SET JOBATTR=\"@JOAU=%s\"\n", Username ? Username : ""); | |
| + printf("@PJL SET JOBATTR=\"@CNAM=%s\"\n", cname); | |
| + | |
| + printf( | |
| + "@PJL SET OUTBIN=FACEDOWN\n" | |
| + "@PJL SET JOBATTR=\"@PODR=NORMAL\"\n" | |
| + "@PJL SET SLIPSHEET=OFF\n" | |
| + "@PJL SET PAPERDIRECTION=SEF\n" | |
| + "@PJL SET RESOLUTION=600\n" | |
| + "@PJL SET BITSPERPIXEL=8\n" | |
| + "@PJL SET JOBATTR=\"@DRDM=RASTER\"\n" | |
| + ); | |
| + | |
| + doc_type_id = DocType == 0 ? 0 : DocType - 1; | |
| + | |
| + if (color) { | |
| + for (i = 0; i < 6; i++) { | |
| + printf("@PJL SET JOBATTR=\"@%c%s=%d\"\n", | |
| + doc_type_jobattr_prefix[i % 3], | |
| + doc_type_jobattr_cprucr[i / 3], | |
| + doc_type_index[doc_type_id].jobattr.color); | |
| + } | |
| + } | |
| + | |
| + if (Screen == 0) { | |
| + s_doc_type_jobattr = &doc_type_index[doc_type_id].jobattr; | |
| + } else { | |
| + s_doc_type_jobattr = &screen_jobattr_index[Screen - 1]; | |
| + } | |
| + doc_type_jobattr = color ? | |
| + s_doc_type_jobattr->color : s_doc_type_jobattr->mono; | |
| + for (i = 0; i < 6; i++) { | |
| + printf("@PJL SET JOBATTR=\"@%c%s=%d\"\n", | |
| + doc_type_jobattr_prefix[i % 3], | |
| + doc_type_jobattr_trcscr[i / 3], | |
| + doc_type_jobattr); | |
| + } | |
| + | |
| + if (!color) { | |
| + printf("@PJL SET JOBATTR=\"@PBLK=OFF\"\n"); | |
| + } | |
| + | |
| + printf("@PJL SET JOBATTR=\"@BANR=DEVICE\"\n"); | |
| + | |
| + if (doc_type_id == DOC_NONE) { | |
| + printf("@PJL SET JOBATTR=\"@FCMS=ON\"\n"); | |
| + } | |
| + | |
| + printf("@PJL ENTER LANGUAGE=HBPL\n"); | |
| + | |
| fwrite (reca, 1, sizeof reca, stdout); | |
| } | |
| @@ -401,11 +579,14 @@ encode_page(int color, int width, int height, char *image) | |
| int paper = 510, hsel = 0, off = 0, bit = 0, stat = 0; | |
| int margin = width-96; | |
| - for (i = 0; i < sizeof papers / sizeof *papers; i++) | |
| - if (abs(width-papers[i+1]) < 36 && abs(height-papers[i+2]) < 36) | |
| + for (i = 0; i < sizeof papers / sizeof *papers; i+=3) { | |
| + if (abs(width-papers[i+1]) < 36 && abs(height-papers[i+2]) < 36) { | |
| paper = papers[i]; | |
| + break; | |
| + } | |
| + } | |
| if (!MediaCode) | |
| - MediaCode = paper & 1 ? 6 : 1; | |
| + MediaCode = paper & 1 ? 24 : 1; | |
| if (!pagenum) | |
| start_doc(color); | |
| head[12] = paper >> 1; | |
| @@ -532,6 +713,421 @@ encode_page(int color, int width, int height, char *image) | |
| #undef BP | |
| #undef put_token | |
| +#define CLUT_BLK0_OFFSET 0x374 | |
| +#define CLUT_OFFSET 0x308 | |
| +#define CLUT_SIZE (17 * 17 * 17 * 4) | |
| +#define CLUT_BLK_SIZE ((CLUT_OFFSET) + (CLUT_SIZE)) | |
| +#define FILE_CLUT_OFFSET(i) ((CLUT_BLK0_OFFSET) + (CLUT_BLK_SIZE) * (i) + (CLUT_OFFSET)) | |
| + | |
| +#define CLUT_X_FACT (1 * 4) | |
| +#define CLUT_Y_FACT (17 * 4) | |
| +#define CLUT_Z_FACT (17 * 17 * 4) | |
| + | |
| +#define RGB_TO_GRAY(r, g, b) ((1229 * (r) + 2417 * (g) + 451 * (b)) >> 12) | |
| + | |
| +unsigned char* | |
| +load_clut(const int clut_id, const char *clut_fname) | |
| +{ | |
| + unsigned char *clut; | |
| + FILE *clut_fp; | |
| + | |
| + if ((clut = malloc(CLUT_SIZE * sizeof(char))) == NULL) { | |
| + error(1, "Can't allocate memory for CLUT\n"); | |
| + } | |
| + | |
| + if (!(clut_fp = fopen(clut_fname, "r"))) { | |
| + error(1, "Can't open '%s' for reading\n", clut_fname); | |
| + } | |
| + | |
| + if (fseek(clut_fp, FILE_CLUT_OFFSET(clut_id), SEEK_SET) != 0 | |
| + || fread(clut, sizeof(char), CLUT_SIZE, clut_fp) < CLUT_SIZE) { | |
| + fclose(clut_fp); | |
| + error(1, "Can't read CLUT #%d from '%s'\n", clut_id, clut_fname); | |
| + } | |
| + | |
| + fclose(clut_fp); | |
| + | |
| + return clut; | |
| +} | |
| + | |
| +// Borrowed from Little Color Management System, http://www.littlecms.com | |
| +// Copyright (c) 1998-2012 Marti Maria Saguer | |
| +// Licensed under the MIT license | |
| +// http://opensource.org/licenses/mit-license.php | |
| + | |
| +// Tetrahedral interpolation, using Sakamoto algorithm. | |
| +void | |
| +rgb_to_kcmy(const unsigned char clut[], unsigned char kcmy[], const unsigned char rgb[]) | |
| +{ | |
| + int i; | |
| + int rx, ry, rz; | |
| + int x0, y0, z0; | |
| + int x1, y1, z1; | |
| + const unsigned char *plane; | |
| + int c0, c1, c2, c3; | |
| + | |
| + rx = rgb[0] & 0xf; ry = rgb[1] & 0xf; rz = rgb[2] & 0xf; | |
| + | |
| + if (rgb[0] == 255) { | |
| + x0 = CLUT_X_FACT << 4; x1 = 0; | |
| + } else { | |
| + x0 = (rgb[0] >> 4) * (x1 = CLUT_X_FACT); | |
| + } | |
| + | |
| + if (rgb[1] == 255) { | |
| + y0 = CLUT_Y_FACT << 4; y1 = 0; | |
| + } else { | |
| + y0 = (rgb[1] >> 4) * (y1 = CLUT_Y_FACT); | |
| + } | |
| + | |
| + if (rgb[2] == 255) { | |
| + z0 = CLUT_Z_FACT << 4; z1 = 0; | |
| + } else { | |
| + z0 = (rgb[2] >> 4) * (z1 = CLUT_Z_FACT); | |
| + } | |
| + | |
| + clut = &clut[x0 + y0 + z0]; | |
| + | |
| + if (rx >= ry) { | |
| + if (ry >= rz) { | |
| + y1 += x1; | |
| + z1 += y1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; // in KCMY order | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c3 -= c2; | |
| + c2 -= c1; | |
| + c1 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } else if (rz >= rx) { | |
| + x1 += z1; | |
| + y1 += x1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c2 -= c1; | |
| + c1 -= c3; | |
| + c3 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } else { | |
| + z1 += x1; | |
| + y1 += z1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c2 -= c3; | |
| + c3 -= c1; | |
| + c1 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } | |
| + } else { | |
| + if (rx >= rz) { | |
| + x1 += y1; | |
| + z1 += x1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c3 -= c1; | |
| + c1 -= c2; | |
| + c2 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } else if (ry >= rz) { | |
| + z1 += y1; | |
| + x1 += z1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c1 -= c3; | |
| + c3 -= c2; | |
| + c2 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } else { | |
| + y1 += z1; | |
| + x1 += y1; | |
| + for (i = 0; i < 4; i++) { | |
| + plane = &clut[(i - 1) & 3]; | |
| + c1 = plane[x1]; | |
| + c2 = plane[y1]; | |
| + c3 = plane[z1]; | |
| + c0 = plane[0]; | |
| + c1 -= c2; | |
| + c2 -= c3; | |
| + c3 -= c0; | |
| + kcmy[i] = c0 + ((c1 * rx + c2 * ry + c3 * rz) >> 4); | |
| + } | |
| + } | |
| + } | |
| + | |
| + return; | |
| +} | |
| + | |
| +enum proc_mode { | |
| + PROC_BITMAP, | |
| + PROC_GRAY, | |
| + PROC_RGB_NOADJ, | |
| + PROC_RGB_ADJ_COLOR, | |
| + PROC_RGB_ADJ_COLOR_NONE, | |
| + PROC_RGB_ADJ_COLOR_DRAFT, | |
| + PROC_RGB_ADJ_COLOR_NONE_DRAFT, | |
| + PROC_RGB_ADJ_MONO, | |
| + PROC_RGB_ADJ_MONO_DRAFT, | |
| + PROC_CMYK | |
| +}; | |
| + | |
| +enum margin_pos { | |
| + LEFT, | |
| + TOP, | |
| + RIGHT, | |
| + BOTTOM, | |
| +}; | |
| + | |
| +static unsigned char trc_rgb_color_std[] = { | |
| + 0, 0, 0, 0, 0, 0, 1, 1, 2, 2, 2, 3, 3, 4, 5, 6, 7, 8, 9, 10, 12, 13, 14, | |
| + 15, 16, 18, 19, 20, 21, 22, 23, 25, 26, 27, 28, 29, 31, 32, 33, 34, 35, | |
| + 36, 37, 38, 40, 41, 42, 43, 44, 45, 46, 47, 48, 50, 51, 52, 53, 54, 55, | |
| + 56, 57, 58, 59, 60, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 74, 75, | |
| + 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 90, 91, 92, 93, 94, | |
| + 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, | |
| + 110, 111, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, | |
| + 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, | |
| + 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, | |
| + 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164, 165, 166, | |
| + 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, | |
| + 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 193, 194, | |
| + 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207, 208, | |
| + 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, | |
| + 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, | |
| + 237, 238, 239, 240, 240, 241, 242, 243, 244, 245, 246, 247, 248, 249, | |
| + 250, 251, 252, 253, 254, 255 | |
| +}; | |
| + | |
| +// Identity transformation | |
| +static unsigned char trc_rgb_color_none[] = { | |
| + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, | |
| + 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, | |
| + 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, | |
| + 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, | |
| + 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, | |
| + 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, | |
| + 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, | |
| + 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, | |
| + 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, | |
| + 150, 151, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, | |
| + 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, | |
| + 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, | |
| + 192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, | |
| + 206, 207, 208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, | |
| + 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, | |
| + 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, | |
| + 248, 249, 250, 251, 252, 253, 254, 255 | |
| +}; | |
| + | |
| +static unsigned char trc_rgb_gray_std[] = { | |
| + 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 2, 3, 4, 6, 7, 10, 12, 13, 15, 16, 19, 20, | |
| + 23, 23, 26, 27, 28, 31, 32, 34, 35, 36, 38, 40, 41, 43, 44, 45, 46, 48, | |
| + 50, 51, 52, 54, 55, 56, 57, 59, 61, 62, 63, 64, 66, 67, 68, 69, 70, 71, | |
| + 74, 75, 76, 77, 78, 79, 80, 81, 83, 84, 85, 86, 87, 88, 90, 91, 92, 93, | |
| + 94, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, | |
| + 110, 111, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, | |
| + 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, | |
| + 139, 140, 141, 142, 143, 144, 145, 145, 146, 147, 148, 149, 150, 151, | |
| + 152, 153, 154, 155, 156, 157, 158, 159, 159, 160, 161, 162, 163, 164, | |
| + 165, 166, 167, 168, 169, 169, 170, 171, 172, 173, 174, 175, 176, 177, | |
| + 178, 178, 179, 180, 181, 182, 183, 184, 185, 185, 186, 187, 188, 189, | |
| + 190, 191, 192, 192, 193, 194, 195, 196, 197, 198, 198, 199, 200, 201, | |
| + 202, 203, 204, 204, 205, 206, 207, 208, 209, 209, 210, 211, 212, 213, | |
| + 214, 215, 215, 216, 217, 218, 219, 220, 220, 221, 222, 223, 224, 225, | |
| + 225, 226, 227, 228, 229, 229, 230, 231, 232, 233, 234, 234, 235, 236, | |
| + 237, 238, 238, 239, 240, 240, 241, 241, 242, 243, 244, 245, 245, 246, | |
| + 247, 248, 249, 249, 250, 251, 252, 253, 253, 254, 255 | |
| +}; | |
| + | |
| +static unsigned char trc_rgb_gray_none[] = { | |
| + 0, 1, 1, 2, 2, 3, 4, 6, 7, 8, 10, 11, 13, 15, 16, 18, 20, 21, 23, 24, | |
| + 26, 27, 29, 30, 32, 33, 34, 36, 37, 39, 40, 41, 43, 44, 45, 47, 48, 49, | |
| + 50, 52, 53, 54, 55, 57, 58, 59, 60, 62, 63, 64, 65, 66, 68, 69, 70, 71, | |
| + 72, 73, 75, 76, 77, 78, 79, 80, 81, 82, 84, 85, 86, 87, 88, 89, 90, 91, | |
| + 92, 93, 94, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, | |
| + 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, | |
| + 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, | |
| + 137, 138, 139, 140, 141, 142, 143, 144, 144, 145, 146, 147, 148, 149, | |
| + 150, 151, 152, 153, 154, 155, 156, 157, 158, 158, 159, 160, 161, 162, | |
| + 163, 164, 165, 166, 167, 168, 168, 169, 170, 171, 172, 173, 174, 175, | |
| + 176, 177, 177, 178, 179, 180, 181, 182, 183, 184, 184, 185, 186, 187, | |
| + 188, 189, 190, 191, 191, 192, 193, 194, 195, 196, 197, 197, 198, 199, | |
| + 200, 201, 202, 203, 203, 204, 205, 206, 207, 208, 208, 209, 210, 211, | |
| + 212, 213, 214, 214, 215, 216, 217, 218, 219, 219, 220, 221, 222, 223, | |
| + 224, 224, 225, 226, 227, 228, 228, 229, 230, 231, 232, 233, 233, 234, | |
| + 235, 236, 237, 237, 238, 239, 240, 241, 241, 242, 243, 244, 245, 245, | |
| + 246, 247, 248, 249, 249, 250, 251, 252, 253, 253, 254, 255 | |
| +}; | |
| + | |
| +static unsigned char trc_draft[] = { | |
| + 0, 0, 1, 2, 2, 3, 4, 4, 5, 6, 7, 7, 8, 9, 9, 10, 11, 11, 12, 13, 14, 14, | |
| + 15, 16, 16, 17, 18, 18, 19, 20, 21, 21, 22, 23, 23, 24, 25, 25, 26, 27, | |
| + 28, 28, 29, 30, 30, 31, 32, 32, 33, 34, 35, 35, 36, 37, 37, 38, 39, 39, | |
| + 40, 41, 42, 42, 43, 44, 44, 45, 46, 46, 47, 48, 49, 49, 50, 51, 51, 52, | |
| + 53, 53, 54, 55, 56, 56, 57, 58, 58, 59, 60, 60, 61, 62, 62, 63, 64, 65, | |
| + 65, 66, 67, 67, 68, 69, 70, 70, 71, 72, 72, 73, 74, 74, 75, 76, 77, 77, | |
| + 78, 79, 79, 80, 81, 81, 82, 83, 84, 84, 85, 86, 86, 87, 88, 88, 89, 90, | |
| + 91, 91, 92, 93, 93, 94, 95, 95, 96, 97, 98, 98, 99, 100, 100, 101, 102, | |
| + 102, 103, 104, 105, 105, 106, 107, 107, 108, 109, 109, 110, 111, 112, | |
| + 112, 113, 114, 114, 115, 116, 116, 117, 118, 118, 119, 120, 121, 121, | |
| + 122, 123, 123, 124, 125, 125, 126, 127, 128, 128, 129, 130, 130, 131, | |
| + 132, 133, 133, 134, 135, 135, 136, 137, 137, 138, 139, 140, 140, 141, | |
| + 142, 142, 143, 144, 144, 145, 146, 147, 147, 148, 149, 149, 150, 151, | |
| + 151, 152, 153, 154, 154, 155, 156, 156, 157, 158, 158, 159, 160, 161, | |
| + 161, 162, 163, 163, 164, 165, 165, 166, 167, 168, 168, 169, 170, 170, | |
| + 171, 172, 172, 173, 174, 175, 175, 176, 177, 177, 178 | |
| +}; | |
| + | |
| +void | |
| +detect_rgb_content(unsigned char *const image, | |
| + const int wide, const int high, const int margins[4], | |
| + int *is_color, int *is_blank) | |
| +{ | |
| + const int deep = 3; | |
| + const int byte = wide * deep; | |
| + int i, m[4]; | |
| + int start_row, end_row; | |
| + int start_col, end_col; | |
| + int start_col_off, end_col_off; | |
| + unsigned char *rowp, *end_rowp, *startp, *endp, *p; | |
| + int color_detected = 0; | |
| + int gray_detected = 0; | |
| + | |
| + for (i = 0; i < 4; i++) { | |
| + m[i] = margins[i] < 0 ? 0 : margins[i]; | |
| + } | |
| + | |
| + start_row = m[TOP]; | |
| + end_row = high - m[BOTTOM]; | |
| + start_col = m[LEFT]; | |
| + end_col = wide - m[RIGHT]; | |
| + | |
| + if (start_row < end_row && start_col < end_col) { | |
| + end_rowp = image + (end_row - 1) * byte; | |
| + start_col_off = start_col * deep; | |
| + end_col_off = (end_col - 1) * deep; | |
| + | |
| + for (rowp = image + start_row * byte;; rowp += byte) { | |
| + startp = rowp + start_col_off; | |
| + endp = rowp + end_col_off; | |
| + | |
| + for (p = startp;; p += deep) { | |
| + if (p[0] != p[1] || p[1] != p[2]) { | |
| + color_detected = 1; | |
| + goto end_search; | |
| + } else if (p[0] != 255) { | |
| + gray_detected = 1; | |
| + } | |
| + if (p == endp) { | |
| + break; | |
| + } | |
| + } | |
| + if (rowp == end_rowp) { | |
| + break; | |
| + } | |
| + } | |
| + } | |
| + | |
| +end_search: *is_color = color_detected; | |
| + *is_blank = !(color_detected || gray_detected); | |
| + | |
| + return; | |
| +} | |
| + | |
| +void | |
| +apply_trapping(unsigned char *image, int wide, int high, const int margins[4]) | |
| +{ | |
| + int byte; | |
| + int i, j, k, m[4], n[24]; | |
| + int skip_mlr, eff_byte; | |
| + unsigned char *p, *row_endp, *img_endp, *np; | |
| + | |
| + for (i = 0; i < 4; i++) { | |
| + m[i] = margins[i] > 1 ? margins[i] : 2; | |
| + } | |
| + | |
| + if (m[TOP] < high - m[BOTTOM] && m[LEFT] < wide - m[RIGHT]) { | |
| + | |
| + byte = wide * 4; | |
| + | |
| + // Array `n` contains relative offsets | |
| + // of the neighbor pixels in a 5x5 window. | |
| + // | |
| + // +----+----+----+----+----+ | |
| + // | 0 | 1 | 2 | 3 | 4 | | |
| + // +----+----+----+----+----+ | |
| + // | 5 | 6 | 7 | 8 | 9 | | |
| + // +----+----+---------+----+ | |
| + // | 10 | 11 | p | 12 | 13 | | |
| + // +----+----+---------+----+ | |
| + // | 14 | 15 | 16 | 17 | 18 | | |
| + // +----+----+----+----+----+ | |
| + // | 19 | 20 | 21 | 22 | 23 | | |
| + // +----+----+----+----+----+ | |
| + | |
| + for (k = 0, i = -2; i < 3; i++) { | |
| + for (j = -2; j < 3; j++) { | |
| + if (i || j) { | |
| + n[k++] = byte * i + 4 * j; | |
| + } | |
| + } | |
| + } | |
| + | |
| + p = image + m[TOP] * byte + m[LEFT] * 4; | |
| + img_endp = image + (high - m[BOTTOM]) * byte - m[RIGHT] * 4; | |
| + skip_mlr = (m[LEFT] + m[RIGHT]) * 4; | |
| + eff_byte = byte - skip_mlr; | |
| + row_endp = p + eff_byte; | |
| + | |
| + for (; p != img_endp; p += 4) { | |
| + if (p == row_endp) { | |
| + p += skip_mlr; | |
| + row_endp = p + eff_byte; | |
| + } | |
| + | |
| + if (p[0] < 204) { | |
| + continue; | |
| + } | |
| + | |
| + for (i = 0; i < 24; i++) { | |
| + np = p + n[i]; | |
| + if (np[0] < 204) { | |
| + for (j = 1; j < 4; j++) { | |
| + if (p[j] < np[j]) { | |
| + p[j] = np[j]; | |
| + } | |
| + } | |
| + } | |
| + } | |
| + } | |
| + } | |
| + | |
| + return; | |
| +} | |
| + | |
| int | |
| getint(FILE *fp) | |
| { | |
| @@ -557,6 +1153,15 @@ do_file(FILE *fp) | |
| int wide, deep, byte, row, col, i, k; | |
| char tupl[128], line[128]; | |
| unsigned char *image, *sp, *dp; | |
| + int buf_size, ibuf_size; | |
| + unsigned char *sstart, *dstart; | |
| + int doc_type_id = 0; | |
| + const struct doc_type *s_doc_type; | |
| + unsigned char *clut = NULL; | |
| + enum proc_mode proc_mode; | |
| + unsigned char *trc = trc_rgb_color_none; | |
| + int is_color = 0; | |
| + int is_blank = 0; | |
| while ((type = fgetc(fp)) != EOF) | |
| { | |
| @@ -566,12 +1171,37 @@ do_file(FILE *fp) | |
| { | |
| case '4': | |
| deep = 1 + (ideep = 0); | |
| + proc_mode = PROC_BITMAP; | |
| goto six; | |
| case '5': | |
| deep = ideep = 1; | |
| + proc_mode = PROC_GRAY; | |
| goto six; | |
| case '6': | |
| - deep = 1 + (ideep = 3); | |
| + if (DocType != 0) { | |
| + doc_type_id = DocType - 1; | |
| + if (OutputColor) { | |
| + deep = 1 + (ideep = 3); | |
| + if (doc_type_id == DOC_NONE) { | |
| + proc_mode = DraftMode ? | |
| + PROC_RGB_ADJ_COLOR_NONE_DRAFT : PROC_RGB_ADJ_COLOR_NONE; | |
| + } else { | |
| + if (!ClutFilePath) { | |
| + error(1, "CLUT file path (option -l) is not set.\n"); | |
| + } | |
| + proc_mode = DraftMode ? | |
| + PROC_RGB_ADJ_COLOR_DRAFT : PROC_RGB_ADJ_COLOR; | |
| + } | |
| + } else { | |
| + ideep = 3; | |
| + deep = 1; | |
| + proc_mode = DraftMode ? | |
| + PROC_RGB_ADJ_MONO_DRAFT : PROC_RGB_ADJ_MONO; | |
| + } | |
| + } else { | |
| + deep = 1 + (ideep = 3); | |
| + proc_mode = PROC_RGB_NOADJ; | |
| + } | |
| six: iwide = getint(fp); | |
| ihigh = getint(fp); | |
| imax = type == '4' ? 255 : getint(fp); | |
| @@ -592,6 +1222,7 @@ six: iwide = getint(fp); | |
| strcpy (tupl, line + 9); | |
| } while (strcmp(line, "ENDHDR\n")); | |
| if (ideep != 4 || strcmp(tupl, "CMYK\n")) goto fail; | |
| + proc_mode = PROC_CMYK; | |
| break; | |
| default: | |
| goto fail; | |
| @@ -603,37 +1234,118 @@ six: iwide = getint(fp); | |
| else | |
| ibyte = wide >> 3; | |
| byte = wide * deep; | |
| - image = calloc (ihigh+2, byte); | |
| + | |
| + buf_size = (ibyte > byte ? ibyte : byte) * ihigh + byte * 2; | |
| + | |
| + if ((image = malloc(buf_size)) == NULL) { | |
| + error(1, "Can't allocate memory for page buffer\n"); | |
| + } | |
| + | |
| + dstart = image + byte; | |
| + ibuf_size = ibyte * ihigh; | |
| + sstart = image + (buf_size - ibuf_size); | |
| + | |
| + if (fread (sstart, ibuf_size, 1, fp) != 1) { | |
| + error(1, "Error reading image data\n"); | |
| + } | |
| + | |
| + if (ideep == 3 && DocType != 0) { | |
| + detect_rgb_content(sstart, iwide, ihigh, Clip, | |
| + &is_color, &is_blank); | |
| + | |
| + if (doc_type_id == DOC_NONE) { | |
| + trc = is_color ? trc_rgb_color_none : trc_rgb_gray_none; | |
| + } else { | |
| + s_doc_type = &doc_type_index[doc_type_id]; | |
| + clut = load_clut(s_doc_type->clut_id, ClutFilePath); | |
| + trc = is_color ? trc_rgb_color_std : trc_rgb_gray_std; | |
| + } | |
| + } | |
| + | |
| for (row = 1; row <= ihigh; row++) | |
| { | |
| - i = fread (image, ibyte, 1, fp); | |
| - sp = image; | |
| - dp = image + row*byte; | |
| + sp = sstart; | |
| + dp = dstart; | |
| for (col = 0; col < iwide; col++) | |
| { | |
| dp += deep; | |
| - switch (ideep) | |
| + switch (proc_mode) | |
| { | |
| - case 0: | |
| - *dp = ((image[col >> 3] >> (~col & 7)) & 1) * 255; | |
| + case PROC_BITMAP: | |
| + *dp = ((sp[col >> 3] >> (~col & 7)) & 1) * 255; | |
| break; | |
| - case 1: | |
| + case PROC_GRAY: | |
| *dp = ~*sp; | |
| break; | |
| - case 3: | |
| + case PROC_RGB_NOADJ: | |
| for (k = sp[2], i = 0; i < 2; i++) | |
| if (k < sp[i]) k = sp[i]; | |
| *dp = ~k; | |
| for (i = 0; i < 3; i++) | |
| dp[i+1] = k ? (k - sp[i]) * 255 / k : 255; | |
| break; | |
| - case 4: | |
| + case PROC_RGB_ADJ_COLOR: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + rgb_to_kcmy(clut, dp, sp); | |
| + break; | |
| + case PROC_RGB_ADJ_COLOR_NONE: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + for (k = sp[2], i = 0; i < 2; i++) | |
| + if (k < sp[i]) k = sp[i]; | |
| + *dp = ~k; | |
| + for (i = 0; i < 3; i++) | |
| + dp[i+1] = k - sp[i]; | |
| + break; | |
| + case PROC_RGB_ADJ_COLOR_DRAFT: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + rgb_to_kcmy(clut, dp, sp); | |
| + for (i = 0; i < 4; i++) { | |
| + dp[i] = trc_draft[dp[i]]; | |
| + } | |
| + break; | |
| + case PROC_RGB_ADJ_COLOR_NONE_DRAFT: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + for (k = sp[2], i = 0; i < 2; i++) | |
| + if (k < sp[i]) k = sp[i]; | |
| + *dp = ~k; | |
| + for (i = 0; i < 3; i++) | |
| + dp[i+1] = k - sp[i]; | |
| + for (i = 0; i < 4; i++) { | |
| + dp[i] = trc_draft[dp[i]]; | |
| + } | |
| + break; | |
| + case PROC_RGB_ADJ_MONO: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + *dp = ~RGB_TO_GRAY(sp[0], sp[1], sp[2]); | |
| + break; | |
| + case PROC_RGB_ADJ_MONO_DRAFT: | |
| + for (i = 0; i < 3; i++) { | |
| + sp[i] = trc[sp[i]]; | |
| + } | |
| + *dp = ~RGB_TO_GRAY(sp[0], sp[1], sp[2]); | |
| + for (i = 0; i < 4; i++) { | |
| + dp[i] = trc_draft[dp[i]]; | |
| + } | |
| + break; | |
| + case PROC_CMYK: | |
| for (i=0; i < 4; i++) | |
| dp[i] = sp[((i-1) & 3)]; | |
| break; | |
| } | |
| sp += ideep; | |
| } | |
| + sstart += ibyte; | |
| + dstart += byte; | |
| for (i = 0; i < deep*Clip[0]; i++) | |
| image[row*byte + deep+i] = 0; | |
| for (i = deep*(iwide-Clip[2]); i < byte; i++) | |
| @@ -641,8 +1353,14 @@ six: iwide = getint(fp); | |
| } | |
| memset(image+deep, 0, byte*(Clip[1]+1)); | |
| memset(image+deep + byte*(ihigh-Clip[3]+1), 0, byte*Clip[3]); | |
| + if (deep == 4 && Trapping) { | |
| + apply_trapping(image + byte + deep, iwide, ihigh, Clip); | |
| + } | |
| encode_page(deep > 1, iwide, ihigh, (char *) image); | |
| free(image); | |
| + if (ideep == 3 && DocType != 0 && doc_type_id != DOC_NONE) { | |
| + free(clut); | |
| + } | |
| } | |
| return; | |
| fail: | |
| @@ -654,15 +1372,61 @@ main(int argc, char *argv[]) | |
| { | |
| int c, i; | |
| - while ( (c = getopt(argc, argv, "m:u:J:U:V")) != EOF) | |
| + while ( (c = getopt(argc, argv, "a:ci:l:m:s:tu:J:TU:V")) != EOF) | |
| switch (c) | |
| { | |
| - case 'm': MediaCode = atoi(optarg); break; | |
| + case 'a': | |
| + for (i = 0; i < 12 && optarg[i]; i++) { | |
| + if (optarg[i] >= '0' && optarg[i] <= '6') { | |
| + ColorBalance[i] = optarg[i]; | |
| + } else { | |
| + error(1, "Color balance values must be in range 0..6\n"); | |
| + } | |
| + } | |
| + break; | |
| + case 'c': | |
| + OutputColor = 1; | |
| + break; | |
| + case 'i': | |
| + if (sscanf(optarg, "%d", &DocType) != 1 | |
| + || DocType < 0 || DocType > 6 | |
| + ) { | |
| + error(1, "Document type code must be in range 1..6.\n"); | |
| + } | |
| + break; | |
| + case 'l': if (optarg[0]) ClutFilePath = optarg; break; | |
| + case 'm': | |
| + if (sscanf(optarg, "%d", &MediaCode) != 1 | |
| + || MediaCode < 1 || MediaCode > 24 | |
| + ) { | |
| + error(1, "Media code must be in range 1..24.\n"); | |
| + } | |
| + break; | |
| + case 'n': | |
| + if (sscanf(optarg, "%d", &NumCopies) != 1 | |
| + || NumCopies < 1 || NumCopies > 24 | |
| + ) { | |
| + error(1, "Number of copies must be in range 1..100.\n"); | |
| + } | |
| + break; | |
| + case 's': | |
| + if (sscanf(optarg, "%d", &Screen) != 1 | |
| + || Screen < 0 || Screen > 3 | |
| + ) { | |
| + error(1, "Screen type code must be in range 0..3.\n"); | |
| + } | |
| + break; | |
| + case 't': | |
| + DraftMode = 1; | |
| + break; | |
| case 'u': if (sscanf(optarg, "%d,%d,%d,%d", | |
| Clip, Clip+1, Clip+2, Clip+3) != 4) | |
| error(1, "Must specify four clipping margins!\n"); | |
| break; | |
| case 'J': if (optarg[0]) Filename = optarg; break; | |
| + case 'T': | |
| + Trapping = 1; | |
| + break; | |
| case 'U': if (optarg[0]) Username = optarg; break; | |
| case 'V': printf("%s\n", Version); return 0; | |
| default: usage(); return 1; |
yeah, got the xerox driver working.
In the xerox ppd are some good examples how modify the ppd.
Hi @defremov - I was looking at the original HBPLv1 code by Dave Coffin, and it follows a certain sequence of 6 codes, which I'm assuming is probably based on his printer of that time, maybe a Dell 1250c, or one of the other 4 listed.
Looking at the 24 MediaCodes you have listed, do these all work? which printer is it?
@JoesCat, mine was Xerox Phaser 6010N. As to whether those codes worked I can't even remember now but I am pretty sure I didn't test them all at the time by actually printing something using each one of them.
Reading the conversation above, I sort of guessed that, but thanks for the confirmation, plus the additional info. I have the same one. It's a pretty good printer.
I have googled up a bit the situation with Ubuntu, they seem to promise that they will support 32-bit printer drivers.