mirror of https://github.com/GNOME/gimp.git
2014 lines
53 KiB
C
2014 lines
53 KiB
C
/*
|
|
* "$Id$"
|
|
*
|
|
* Print plug-in HP PCL driver for the GIMP.
|
|
*
|
|
* Copyright 1997-2000 Michael Sweet (mike@easysw.com) and
|
|
* Robert Krawitz (rlk@alum.mit.edu)
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify it
|
|
* under the terms of the GNU General Public License as published by the Free
|
|
* Software Foundation; either version 2 of the License, or (at your option)
|
|
* any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful, but
|
|
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
|
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
* for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
*
|
|
* Contents:
|
|
*
|
|
* pcl_parameters() - Return the parameter values for the given
|
|
* parameter.
|
|
* pcl_imageable_area() - Return the imageable area of the page.
|
|
* pcl_get_model_capabilities()
|
|
* - Return the capabilities of the printer.
|
|
* pcl_convert_media_size()
|
|
* - Convert media size name into PCL code.
|
|
* pcl_print() - Print an image to an HP printer.
|
|
* pcl_mode0() - Send PCL graphics using mode 0 (no) compression.
|
|
* pcl_mode2() - Send PCL graphics using mode 2 (TIFF) compression.
|
|
*
|
|
* Revision History:
|
|
*
|
|
* See ChangeLog
|
|
*/
|
|
|
|
#include "print.h"
|
|
|
|
/* #define DEBUG */
|
|
/* #define PCL_DEBUG_DISABLE_COMPRESSION */
|
|
|
|
/*
|
|
* Local functions...
|
|
*/
|
|
static void pcl_mode0(FILE *, unsigned char *, int, int);
|
|
static void pcl_mode2(FILE *, unsigned char *, int, int);
|
|
|
|
/*
|
|
* Generic define for a name/value set
|
|
*/
|
|
|
|
typedef struct
|
|
{
|
|
char *pcl_name;
|
|
int pcl_code;
|
|
} pcl_t;
|
|
|
|
/*
|
|
* Media size to PCL media size code table
|
|
*
|
|
* Note, you can force the list of papersizes given in the GUI to be only those
|
|
* supported by defining PCL_NO_CUSTOM_PAPERSIZES
|
|
*/
|
|
|
|
/* #define PCL_NO_CUSTOM_PAPERSIZES */
|
|
|
|
#define PCL_PAPERSIZE_EXECUTIVE 1
|
|
#define PCL_PAPERSIZE_LETTER 2
|
|
#define PCL_PAPERSIZE_LEGAL 3
|
|
#define PCL_PAPERSIZE_TABLOID 6 /* "Ledger" */
|
|
#define PCL_PAPERSIZE_STATEMENT 15 /* Called "Manual" in print-util */
|
|
#define PCL_PAPERSIZE_SUPER_B 16 /* Called "13x19" in print-util */
|
|
#define PCL_PAPERSIZE_A5 25
|
|
#define PCL_PAPERSIZE_A4 26
|
|
#define PCL_PAPERSIZE_A3 27
|
|
#define PCL_PAPERSIZE_JIS_B5 45
|
|
#define PCL_PAPERSIZE_JIS_B4 46
|
|
#define PCL_PAPERSIZE_HAGAKI_CARD 71
|
|
#define PCL_PAPERSIZE_OUFUKU_CARD 72
|
|
#define PCL_PAPERSIZE_A6_CARD 73
|
|
#define PCL_PAPERSIZE_4x6 74
|
|
#define PCL_PAPERSIZE_5x8 75
|
|
#define PCL_PAPERSIZE_3x5 78
|
|
#define PCL_PAPERSIZE_MONARCH_ENV 80
|
|
#define PCL_PAPERSIZE_COMMERCIAL10_ENV 81
|
|
#define PCL_PAPERSIZE_DL_ENV 90
|
|
#define PCL_PAPERSIZE_C5_ENV 91
|
|
#define PCL_PAPERSIZE_C6_ENV 92
|
|
#define PCL_PAPERSIZE_CUSTOM 101 /* Custom size */
|
|
#define PCL_PAPERSIZE_INVITATION_ENV 109
|
|
#define PCL_PAPERSIZE_JAPANESE_3_ENV 110
|
|
#define PCL_PAPERSIZE_JAPANESE_4_ENV 111
|
|
#define PCL_PAPERSIZE_KAKU_ENV 113
|
|
#define PCL_PAPERSIZE_HP_CARD 114 /* HP Greeting card!?? */
|
|
|
|
/*
|
|
* This data comes from the HP documentation "Deskjet 1220C and 1120C
|
|
* PCL reference guide 2.0, Nov 1999". NOTE: The names *must* match
|
|
* those in print-util.c for the lookups to work properly!
|
|
*/
|
|
|
|
const static pcl_t pcl_media_sizes[] =
|
|
{
|
|
{"Executive", PCL_PAPERSIZE_EXECUTIVE}, /* US Exec (7.25 x 10.5 in) */
|
|
{"Letter", PCL_PAPERSIZE_LETTER}, /* US Letter (8.5 x 11 in) */
|
|
{"Legal", PCL_PAPERSIZE_LEGAL}, /* US Legal (8.5 x 14 in) */
|
|
{"Tabloid", PCL_PAPERSIZE_TABLOID}, /* US Tabloid (11 x 17 in) */
|
|
{"Manual", PCL_PAPERSIZE_STATEMENT}, /* US Manual/Statement (5.5 x 8.5 in) */
|
|
{"13x19", PCL_PAPERSIZE_SUPER_B}, /* US 13x19/Super B (13 x 19 in) */
|
|
{"A5", PCL_PAPERSIZE_A5}, /* ISO/JIS A5 (148 x 210 mm) */
|
|
{"A4", PCL_PAPERSIZE_A4}, /* ISO/JIS A4 (210 x 297 mm) */
|
|
{"A3", PCL_PAPERSIZE_A3}, /* ISO/JIS A3 (297 x 420 mm) */
|
|
{"B5 JIS", PCL_PAPERSIZE_JIS_B5}, /* JIS B5 (182 x 257 mm). */
|
|
{"B4 JIS", PCL_PAPERSIZE_JIS_B4}, /* JIS B4 (257 x 364 mm). */
|
|
{"Hagaki Card", PCL_PAPERSIZE_HAGAKI_CARD}, /* Japanese Hagaki Card (100 x 148 mm) */
|
|
{"Oufuku Card", PCL_PAPERSIZE_OUFUKU_CARD}, /* Japanese Oufuku Card (148 x 200 mm) */
|
|
{"A6", PCL_PAPERSIZE_A6_CARD}, /* ISO/JIS A6 card */
|
|
{"4x6", PCL_PAPERSIZE_4x6}, /* US Index card (4 x 6 in) */
|
|
{"5x8", PCL_PAPERSIZE_5x8}, /* US Index card (5 x 8 in) */
|
|
{"3x5", PCL_PAPERSIZE_3x5}, /* US Index card (3 x 5 in) */
|
|
{"Monarch", PCL_PAPERSIZE_MONARCH_ENV}, /* Monarch Envelope (3 7/8 x 7 1/2 in) */
|
|
{"Commercial 10", PCL_PAPERSIZE_COMMERCIAL10_ENV}, /* US Commercial 10 Envelope (4.125 x 9.5 in) Portrait */
|
|
{"DL", PCL_PAPERSIZE_DL_ENV}, /* DL envelope (110 x 220 mm) Portrait */
|
|
{"C5", PCL_PAPERSIZE_C5_ENV}, /* C5 envelope (162 x 229 mm) */
|
|
{"C6", PCL_PAPERSIZE_C6_ENV}, /* C6 envelope (114 x 162 mm) */
|
|
{"A2 Invitation", PCL_PAPERSIZE_INVITATION_ENV}, /* US A2 Invitation envelope (4 3/8 x 5 3/4 in) */
|
|
{"Long 3", PCL_PAPERSIZE_JAPANESE_3_ENV}, /* Japanese Long Envelope #3 (120 x 235 mm) */
|
|
{"Long 4", PCL_PAPERSIZE_JAPANESE_4_ENV}, /* Japanese Long Envelope #4 (90 x 205 mm) */
|
|
{"Kaku", PCL_PAPERSIZE_KAKU_ENV}, /* Japanese Kaku Envelope (240 x 332.1 mm) */
|
|
{"HP Greeting Card", PCL_PAPERSIZE_HP_CARD}, /* Hp greeting card (size?? */
|
|
};
|
|
#define NUM_PRINTER_PAPER_SIZES (sizeof(pcl_media_sizes) / sizeof(pcl_t))
|
|
|
|
/*
|
|
* Media type to code table
|
|
*/
|
|
|
|
#define PCL_PAPERTYPE_PLAIN 0
|
|
#define PCL_PAPERTYPE_BOND 1
|
|
#define PCL_PAPERTYPE_PREMIUM 2
|
|
#define PCL_PAPERTYPE_GLOSSY 3 /* or photo */
|
|
#define PCL_PAPERTYPE_TRANS 4
|
|
#define PCL_PAPERTYPE_QPHOTO 5 /* Quick dry photo (2000 only) */
|
|
#define PCL_PAPERTYPE_QTRANS 6 /* Quick dry transparency (2000 only) */
|
|
|
|
const static pcl_t pcl_media_types[] =
|
|
{
|
|
{"Plain", PCL_PAPERTYPE_PLAIN},
|
|
{"Bond", PCL_PAPERTYPE_BOND},
|
|
{"Premium", PCL_PAPERTYPE_PREMIUM},
|
|
{"Glossy/Photo", PCL_PAPERTYPE_GLOSSY},
|
|
{"Transparency", PCL_PAPERTYPE_TRANS},
|
|
{"Quick-dry Photo", PCL_PAPERTYPE_QPHOTO},
|
|
{"Quick-dry Transparency", PCL_PAPERTYPE_QTRANS},
|
|
};
|
|
#define NUM_PRINTER_PAPER_TYPES (sizeof(pcl_media_types) / sizeof(pcl_t))
|
|
|
|
/*
|
|
* Media feed to code table. There are different names for the same code,
|
|
* so we encode them by adding "lumps" of "PAPERSOURCE_MOD".
|
|
* This is removed later to get back to the main codes.
|
|
*/
|
|
|
|
#define PAPERSOURCE_MOD 16
|
|
|
|
#define PCL_PAPERSOURCE_MANUAL 2
|
|
#define PCL_PAPERSOURCE_ENVELOPE 3 /* Not used */
|
|
|
|
/* LaserJet types */
|
|
#define PCL_PAPERSOURCE_LJ_TRAY2 1
|
|
#define PCL_PAPERSOURCE_LJ_TRAY3 4
|
|
#define PCL_PAPERSOURCE_LJ_TRAY4 5
|
|
#define PCL_PAPERSOURCE_LJ_TRAY1 8
|
|
|
|
/* Deskjet 340 types */
|
|
#define PCL_PAPERSOURCE_340_PCSF 1 + PAPERSOURCE_MOD
|
|
/* Portable sheet feeder for 340 */
|
|
#define PCL_PAPERSOURCE_340_DCSF 4 + PAPERSOURCE_MOD
|
|
/* Desktop sheet feeder for 340 */
|
|
|
|
/* Other Deskjet types */
|
|
#define PCL_PAPERSOURCE_DJ_TRAY 1 + PAPERSOURCE_MOD + PAPERSOURCE_MOD
|
|
#define PCL_PAPERSOURCE_DJ_TRAY2 4 + PAPERSOURCE_MOD + PAPERSOURCE_MOD
|
|
/* Tray 2 for 2500 */
|
|
#define PCL_PAPERSOURCE_DJ_OPTIONAL 5 + PAPERSOURCE_MOD + PAPERSOURCE_MOD
|
|
/* Optional source for 2500 */
|
|
#define PCL_PAPERSOURCE_DJ_AUTO 7 + PAPERSOURCE_MOD + PAPERSOURCE_MOD
|
|
/* Autoselect for 2500 */
|
|
|
|
const static pcl_t pcl_media_sources[] =
|
|
{
|
|
{"Manual", PCL_PAPERSOURCE_MANUAL},
|
|
/* {"Envelope", PCL_PAPERSOURCE_ENVELOPE}, */
|
|
{"Tray 1", PCL_PAPERSOURCE_LJ_TRAY1},
|
|
{"Tray 2", PCL_PAPERSOURCE_LJ_TRAY2},
|
|
{"Tray 3", PCL_PAPERSOURCE_LJ_TRAY3},
|
|
{"Tray 4", PCL_PAPERSOURCE_LJ_TRAY4},
|
|
{"Portable Sheet Feeder", PCL_PAPERSOURCE_340_PCSF},
|
|
{"Desktop Sheet Feeder", PCL_PAPERSOURCE_340_DCSF},
|
|
{"Tray", PCL_PAPERSOURCE_DJ_TRAY},
|
|
{"Tray 2", PCL_PAPERSOURCE_DJ_TRAY2},
|
|
{"Optional Source", PCL_PAPERSOURCE_DJ_OPTIONAL},
|
|
{"Autoselect", PCL_PAPERSOURCE_DJ_AUTO},
|
|
};
|
|
#define NUM_PRINTER_PAPER_SOURCES (sizeof(pcl_media_sources) / sizeof(pcl_t))
|
|
|
|
#define PCL_RES_150_150 1
|
|
#define PCL_RES_300_300 2
|
|
#define PCL_RES_600_300 4 /* DJ 600 series */
|
|
#define PCL_RES_600_600_MONO 8 /* DJ 600/800/1100/2000 b/w only */
|
|
#define PCL_RES_600_600 16 /* DJ 9xx ??*/
|
|
#define PCL_RES_1200_1200 32 /* DJ 9xx ??*/
|
|
#define PCL_RES_2400_1200 64 /* DJ 9xx */
|
|
|
|
const static pcl_t pcl_resolutions[] =
|
|
{
|
|
{"150x150 DPI", PCL_RES_150_150},
|
|
{"300x300 DPI", PCL_RES_300_300},
|
|
{"600x300 DPI", PCL_RES_600_300},
|
|
{"600x600 DPI monochrome", PCL_RES_600_600_MONO},
|
|
{"600x600 DPI", PCL_RES_600_600},
|
|
{"1200x1200 DPI", PCL_RES_1200_1200},
|
|
{"2400x1200 DPI", PCL_RES_2400_1200},
|
|
};
|
|
#define NUM_RESOLUTIONS (sizeof(pcl_resolutions) / sizeof (pcl_t))
|
|
|
|
const char *
|
|
pcl_default_resolution(const printer_t *printer)
|
|
{
|
|
return pcl_resolutions[0].pcl_name;
|
|
}
|
|
|
|
/*
|
|
* Printer capability data
|
|
*/
|
|
|
|
typedef struct {
|
|
int model;
|
|
int max_width;
|
|
int max_height;
|
|
int resolutions;
|
|
int top_margin;
|
|
int bottom_margin;
|
|
int left_margin;
|
|
int right_margin;
|
|
int color_type; /* 2 print head or one, 2 level or 4 */
|
|
int printer_type; /* Deskjet/Laserjet and quirks */
|
|
/* The paper size, paper type and paper source codes cannot be combined */
|
|
int paper_sizes[NUM_PRINTER_PAPER_SIZES + 1];
|
|
/* Paper sizes */
|
|
int paper_types[NUM_PRINTER_PAPER_TYPES + 1];
|
|
/* Paper types */
|
|
int paper_sources[NUM_PRINTER_PAPER_SOURCES + 1];
|
|
/* Paper sources */
|
|
} pcl_cap_t;
|
|
|
|
#define PCL_COLOR_NONE 0
|
|
#define PCL_COLOR_CMY 1 /* One print head */
|
|
#define PCL_COLOR_CMYK 2 /* Two print heads */
|
|
#define PCL_COLOR_CMYK4 4 /* CRet printing */
|
|
#define PCL_COLOR_CMYKcm 8 /* CMY + Photo Cart */
|
|
|
|
#define PCL_PRINTER_LJ 1
|
|
#define PCL_PRINTER_DJ 2
|
|
#define PCL_PRINTER_NEW_ERG 4 /* use "\033*rC" to end raster graphics,
|
|
instead of "\033*rB" */
|
|
#define PCL_PRINTER_TIFF 8 /* Use TIFF compression */
|
|
#define PCL_PRINTER_MEDIATYPE 16 /* Use media type & print quality */
|
|
#define PCL_PRINTER_CUSTOM_SIZE 32 /* Custom sizes supported */
|
|
|
|
/*
|
|
* FIXME - the 520 shouldn't be lumped in with the 500 as it supports
|
|
* more paper sizes.
|
|
*
|
|
* The following models use depletion, raster quality and shingling:-
|
|
* 500, 500c, 510, 520, 550c, 560c.
|
|
* The rest use Media Type and Print Quality.
|
|
*
|
|
* This data comes from the HP documentation "Deskjet 1220C and 1120C
|
|
* PCL reference guide 2.0, Nov 1999".
|
|
*/
|
|
|
|
static pcl_cap_t pcl_model_capabilities[] =
|
|
{
|
|
/* Default/unknown printer - assume laserjet */
|
|
{ 0,
|
|
17 * 72 / 2, 14 * 72, /* Max paper size */
|
|
PCL_RES_150_150 | PCL_RES_300_300, /* Resolutions */
|
|
12, 12, 18, 18, /* Margins */
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_LJ,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
0,
|
|
},
|
|
{ -1, /* No selectable paper types */
|
|
},
|
|
{ -1, /* No selectable paper sources */
|
|
},
|
|
},
|
|
/* Deskjet 340 */
|
|
{ 340,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
7, 41, 18, 18,
|
|
PCL_COLOR_CMY,
|
|
PCL_PRINTER_DJ,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_340_PCSF,
|
|
PCL_PAPERSOURCE_340_DCSF,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 400 */
|
|
{ 400,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
7, 41, 18, 18,
|
|
PCL_COLOR_CMY,
|
|
PCL_PRINTER_DJ,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_JIS_B5,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper sources */
|
|
},
|
|
},
|
|
/* Deskjet 500, 520 */
|
|
{ 500,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
7, 41, 18, 18,
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_DJ,
|
|
{
|
|
/* PCL_PAPERSIZE_EXECUTIVE, The 500 doesn't support this, the 520 does */
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
/* PCL_PAPERSIZE_DL_ENV, The 500 doesn't support this, the 520 does */
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 500C */
|
|
{ 501,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
7, 33, 18, 18,
|
|
PCL_COLOR_CMY,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 540C */
|
|
{ 540,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
7, 33, 18, 18,
|
|
PCL_COLOR_CMY,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_JIS_B5,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 550C, 560C */
|
|
{ 550,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
3, 33, 18, 18,
|
|
PCL_COLOR_CMYK,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
/* The 550/560 support COM10 and DL envelope, but the control codes
|
|
are negative, indicating landscape mode. This needs thinking about! */
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 600/600C */
|
|
{ 600,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_300 | PCL_RES_600_600_MONO,
|
|
0, 33, 18, 18,
|
|
PCL_COLOR_CMY,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper sources */
|
|
},
|
|
},
|
|
/* Deskjet 6xx series */
|
|
{ 601,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_300 | PCL_RES_600_600_MONO,
|
|
0, 33, 18, 18,
|
|
PCL_COLOR_CMYK,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 69x series */
|
|
{ 690,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_300 | PCL_RES_600_600,
|
|
0, 33, 18, 18,
|
|
PCL_COLOR_CMYK | PCL_COLOR_CMYKcm,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 800 series */
|
|
{ 800,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_600_MONO | PCL_RES_600_600_MONO,
|
|
3, 33, 18, 18,
|
|
PCL_COLOR_CMYK | PCL_COLOR_CMYK4,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 900 series */
|
|
{ 900,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_600 | PCL_RES_1200_1200 | PCL_RES_2400_1200,
|
|
3, 33, 18, 18,
|
|
PCL_COLOR_CMYK | PCL_COLOR_CMYK4,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper sources */
|
|
},
|
|
},
|
|
/* Deskjet 1100C, 1120C, 1220C */
|
|
{ 1100,
|
|
13 * 72, 19 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_600_MONO,
|
|
3, 33, 18, 18,
|
|
PCL_COLOR_CMYK | PCL_COLOR_CMYK4,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_TABLOID,
|
|
PCL_PAPERSIZE_STATEMENT,
|
|
PCL_PAPERSIZE_SUPER_B,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_A3,
|
|
PCL_PAPERSIZE_JIS_B5,
|
|
PCL_PAPERSIZE_JIS_B4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
/* PCL_PAPERSIZE_OUFUKU_CARD, 1220C supports, rest don't */
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
/* PCL_PAPERSIZE_3x5, 1220C supports, rest don't */
|
|
/* PCL_PAPERSIZE_HP_CARD, 1220C supports, rest don't */
|
|
/* PCL_PAPERSIZE_MONARCH_ENV, 1220C supports, rest don't */
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
/* PCL_PAPERSIZE_C5_ENV, 1220C supports, rest don't */
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
PCL_PAPERSIZE_JAPANESE_3_ENV,
|
|
PCL_PAPERSIZE_JAPANESE_4_ENV,
|
|
PCL_PAPERSIZE_KAKU_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 1200C, 1600C */
|
|
{ 1200,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_CMYK,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
/* This printer is not mentioned in the Comparison tables,
|
|
so I'll just pick some likely sizes... */
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 2000 */
|
|
{ 2000,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_600_MONO,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_CMYK,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_3x5,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
PCL_PAPERSIZE_C6_ENV,
|
|
PCL_PAPERSIZE_INVITATION_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
PCL_PAPERTYPE_QPHOTO,
|
|
PCL_PAPERTYPE_QTRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
-1,
|
|
},
|
|
},
|
|
/* Deskjet 2500 */
|
|
{ 2500,
|
|
13 * 72, 19 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300 | PCL_RES_600_600_MONO,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_CMYK,
|
|
PCL_PRINTER_DJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF | PCL_PRINTER_MEDIATYPE |
|
|
PCL_PRINTER_CUSTOM_SIZE,
|
|
{
|
|
PCL_PAPERSIZE_EXECUTIVE,
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_TABLOID,
|
|
PCL_PAPERSIZE_STATEMENT,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_A3,
|
|
PCL_PAPERSIZE_JIS_B5,
|
|
PCL_PAPERSIZE_JIS_B4,
|
|
PCL_PAPERSIZE_HAGAKI_CARD,
|
|
PCL_PAPERSIZE_A6_CARD,
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
PCL_PAPERSIZE_COMMERCIAL10_ENV,
|
|
PCL_PAPERSIZE_DL_ENV,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERTYPE_PLAIN,
|
|
PCL_PAPERTYPE_BOND,
|
|
PCL_PAPERTYPE_PREMIUM,
|
|
PCL_PAPERTYPE_GLOSSY,
|
|
PCL_PAPERTYPE_TRANS,
|
|
PCL_PAPERTYPE_QPHOTO,
|
|
PCL_PAPERTYPE_QTRANS,
|
|
-1,
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_DJ_AUTO,
|
|
PCL_PAPERSOURCE_DJ_TRAY,
|
|
PCL_PAPERSOURCE_DJ_TRAY2,
|
|
PCL_PAPERSOURCE_DJ_OPTIONAL,
|
|
-1,
|
|
},
|
|
},
|
|
/* LaserJet II series */
|
|
{ 2,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_LJ,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper types */
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_LJ_TRAY1,
|
|
PCL_PAPERSOURCE_LJ_TRAY2,
|
|
PCL_PAPERSOURCE_LJ_TRAY3,
|
|
PCL_PAPERSOURCE_LJ_TRAY4,
|
|
-1,
|
|
},
|
|
},
|
|
/* LaserJet III series */
|
|
{ 3,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_LJ | PCL_PRINTER_TIFF,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper types */
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_LJ_TRAY1,
|
|
PCL_PAPERSOURCE_LJ_TRAY2,
|
|
PCL_PAPERSOURCE_LJ_TRAY3,
|
|
PCL_PAPERSOURCE_LJ_TRAY4,
|
|
-1,
|
|
},
|
|
},
|
|
/* LaserJet 4 series, 5 series, 6 series */
|
|
{ 4,
|
|
17 * 72 / 2, 14 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_LJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_A4,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper types */
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_LJ_TRAY1,
|
|
PCL_PAPERSOURCE_LJ_TRAY2,
|
|
PCL_PAPERSOURCE_LJ_TRAY3,
|
|
PCL_PAPERSOURCE_LJ_TRAY4,
|
|
-1,
|
|
},
|
|
},
|
|
/* LaserJet 4V, 4Si, 5Si */
|
|
{ 5,
|
|
13 * 72, 19 * 72,
|
|
PCL_RES_150_150 | PCL_RES_300_300,
|
|
12, 12, 18, 18,
|
|
PCL_COLOR_NONE,
|
|
PCL_PRINTER_LJ | PCL_PRINTER_NEW_ERG | PCL_PRINTER_TIFF,
|
|
{
|
|
PCL_PAPERSIZE_LETTER,
|
|
PCL_PAPERSIZE_LEGAL,
|
|
PCL_PAPERSIZE_TABLOID,
|
|
PCL_PAPERSIZE_A5,
|
|
PCL_PAPERSIZE_A4,
|
|
PCL_PAPERSIZE_A3,
|
|
PCL_PAPERSIZE_JIS_B5,
|
|
PCL_PAPERSIZE_JIS_B4, /* Guess */
|
|
PCL_PAPERSIZE_4x6,
|
|
PCL_PAPERSIZE_5x8,
|
|
-1,
|
|
},
|
|
{ -1, /* No selectable paper types */
|
|
},
|
|
{
|
|
PCL_PAPERSOURCE_MANUAL,
|
|
PCL_PAPERSOURCE_LJ_TRAY1,
|
|
PCL_PAPERSOURCE_LJ_TRAY2,
|
|
PCL_PAPERSOURCE_LJ_TRAY3,
|
|
PCL_PAPERSOURCE_LJ_TRAY4,
|
|
-1,
|
|
},
|
|
},
|
|
};
|
|
|
|
/*
|
|
* Convert a name into it's option value
|
|
*/
|
|
|
|
static int pcl_string_to_val(const char *string, /* I: String */
|
|
const pcl_t *options, /* I: Options */
|
|
int num_options) /* I: Num options */
|
|
{
|
|
|
|
int i;
|
|
int code = -1;
|
|
|
|
/*
|
|
* Look up the string in the table and convert to the code.
|
|
*/
|
|
|
|
for (i=0; i<num_options; i++) {
|
|
if (!strcmp(string, options[i].pcl_name)) {
|
|
code=options[i].pcl_code;
|
|
break;
|
|
}
|
|
}
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "String: %s, Code: %d\n", string, code);
|
|
#endif
|
|
|
|
return(code);
|
|
}
|
|
|
|
/*
|
|
* Convert a value into it's option name
|
|
*/
|
|
|
|
static char * pcl_val_to_string(int code, /* I: Code */
|
|
const pcl_t *options, /* I: Options */
|
|
int num_options) /* I: Num options */
|
|
{
|
|
|
|
int i;
|
|
char *string = NULL;
|
|
|
|
/*
|
|
* Look up the code in the table and convert to the string.
|
|
*/
|
|
|
|
for (i=0; i<num_options; i++) {
|
|
if (code == options[i].pcl_code) {
|
|
string=options[i].pcl_name;
|
|
break;
|
|
}
|
|
}
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "Code: %d, String: %s\n", code, string);
|
|
#endif
|
|
|
|
return(string);
|
|
}
|
|
|
|
static double dot_sizes[] = { 0.5, 0.832, 1.0 };
|
|
static simple_dither_range_t variable_dither_ranges[] =
|
|
{
|
|
{ 0.152, 0x1, 0 },
|
|
{ 0.255, 0x2, 0 },
|
|
{ 0.38, 0x3, 0 },
|
|
{ 0.5, 0x1, 1 },
|
|
{ 0.67, 0x2, 1 },
|
|
{ 1.0, 0x3, 1 }
|
|
};
|
|
|
|
/*
|
|
* pcl_get_model_capabilities() - Return struct of model capabilities
|
|
*/
|
|
|
|
static pcl_cap_t /* O: Capabilities */
|
|
pcl_get_model_capabilities(int model) /* I: Model */
|
|
{
|
|
int i;
|
|
int models= sizeof(pcl_model_capabilities) / sizeof(pcl_cap_t);
|
|
for (i=0; i<models; i++) {
|
|
if (pcl_model_capabilities[i].model == model) {
|
|
return pcl_model_capabilities[i];
|
|
}
|
|
}
|
|
fprintf(stderr,"pcl: model %d not found in capabilities list.\n",model);
|
|
return pcl_model_capabilities[0];
|
|
}
|
|
|
|
static char *
|
|
c_strdup(const char *s)
|
|
{
|
|
char *ret = malloc(strlen(s) + 1);
|
|
strcpy(ret, s);
|
|
return ret;
|
|
}
|
|
|
|
/*
|
|
* Convert Media size name into PCL media code for printer
|
|
*/
|
|
|
|
static int pcl_convert_media_size(const char *media_size, /* I: Media size string */
|
|
int model) /* I: model number */
|
|
{
|
|
|
|
int i;
|
|
int media_code = 0;
|
|
pcl_cap_t caps;
|
|
|
|
/*
|
|
* First look up the media size in the table and convert to the code.
|
|
*/
|
|
|
|
media_code = pcl_string_to_val(media_size, pcl_media_sizes,
|
|
sizeof(pcl_media_sizes) / sizeof(pcl_t));
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "Media Size: %s, Code: %d\n", media_size, media_code);
|
|
#endif
|
|
|
|
/*
|
|
* Now see if the printer supports the code found.
|
|
*/
|
|
|
|
if (media_code != -1) {
|
|
caps = pcl_get_model_capabilities(model);
|
|
|
|
for (i=0; (i<NUM_PRINTER_PAPER_SIZES) && (caps.paper_sizes[i] != -1); i++) {
|
|
if (media_code == caps.paper_sizes[i])
|
|
return(media_code); /* Is supported */
|
|
}
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "Media Code %d not supported by printer model %d.\n",
|
|
media_code, model);
|
|
#endif
|
|
return(-1); /* Not supported */
|
|
}
|
|
else
|
|
return(-1); /* Not supported */
|
|
}
|
|
|
|
/*
|
|
* 'pcl_parameters()' - Return the parameter values for the given parameter.
|
|
*/
|
|
|
|
char ** /* O - Parameter values */
|
|
pcl_parameters(const printer_t *printer,/* I - Printer model */
|
|
char *ppd_file, /* I - PPD file (not used) */
|
|
char *name, /* I - Name of parameter */
|
|
int *count) /* O - Number of values */
|
|
{
|
|
int i;
|
|
char **valptrs;
|
|
pcl_cap_t caps;
|
|
|
|
static char *ink_types[] =
|
|
{
|
|
"Color + Black Cartridges",
|
|
"Color + Photo Cartridges"
|
|
};
|
|
|
|
if (count == NULL)
|
|
return (NULL);
|
|
|
|
*count = 0;
|
|
|
|
if (name == NULL)
|
|
return (NULL);
|
|
|
|
caps = pcl_get_model_capabilities(printer->model);
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "Printer model = %d\n", printer->model);
|
|
fprintf(stderr, "PageWidth = %d, PageLength = %d\n", caps.max_width, caps.max_height);
|
|
fprintf(stderr, "Margins: top = %d, bottom = %d, left = %d, right = %d\n",
|
|
caps.top_margin, caps.bottom_margin, caps.left_margin, caps.right_margin);
|
|
fprintf(stderr, "Resolutions: %d\n", caps.resolutions);
|
|
fprintf(stderr, "ColorType = %d, PrinterType = %d\n", caps.color_type, caps.printer_type);
|
|
#endif
|
|
|
|
if (strcmp(name, "PageSize") == 0)
|
|
{
|
|
const papersize_t *papersizes = get_papersizes();
|
|
#ifdef PCL_NO_CUSTOM_PAPERSIZES
|
|
int use_custom = 0;
|
|
#else
|
|
int use_custom = ((caps.printer_type & PCL_PRINTER_CUSTOM_SIZE)
|
|
== PCL_PRINTER_CUSTOM_SIZE);
|
|
#endif
|
|
valptrs = malloc(sizeof(char *) * known_papersizes());
|
|
*count = 0;
|
|
for (i = 0; i < known_papersizes(); i++)
|
|
{
|
|
if (strlen(papersizes[i].name) > 0 &&
|
|
papersizes[i].width <= caps.max_width &&
|
|
papersizes[i].length <= caps.max_height &&
|
|
((use_custom == 1) || ((use_custom == 0) &&
|
|
(pcl_convert_media_size(papersizes[i].name, printer->model) != -1)))
|
|
)
|
|
{
|
|
valptrs[*count] = malloc(strlen(papersizes[i].name) + 1);
|
|
strcpy(valptrs[*count], papersizes[i].name);
|
|
(*count)++;
|
|
}
|
|
}
|
|
return (valptrs);
|
|
}
|
|
else if (strcmp(name, "MediaType") == 0)
|
|
{
|
|
if (caps.paper_types[0] == -1)
|
|
{
|
|
*count = 0;
|
|
return (NULL);
|
|
}
|
|
else
|
|
{
|
|
valptrs = malloc(sizeof(char *) * NUM_PRINTER_PAPER_TYPES);
|
|
*count = 0;
|
|
for (i=0; (i < NUM_PRINTER_PAPER_TYPES) && (caps.paper_types[i] != -1); i++) {
|
|
valptrs[i] = c_strdup(pcl_val_to_string(caps.paper_types[i], pcl_media_types,
|
|
NUM_PRINTER_PAPER_TYPES));
|
|
(*count)++;
|
|
}
|
|
return(valptrs);
|
|
}
|
|
}
|
|
else if (strcmp(name, "InputSlot") == 0)
|
|
{
|
|
if (caps.paper_sources[0] == -1)
|
|
{
|
|
*count = 0;
|
|
return (NULL);
|
|
}
|
|
else
|
|
{
|
|
valptrs = malloc(sizeof(char *) * NUM_PRINTER_PAPER_SOURCES);
|
|
*count = 0;
|
|
for (i=0; (i < NUM_PRINTER_PAPER_SOURCES) && (caps.paper_sources[i] != -1); i++) {
|
|
valptrs[i] = c_strdup(pcl_val_to_string(caps.paper_sources[i], pcl_media_sources,
|
|
NUM_PRINTER_PAPER_SOURCES));
|
|
(*count)++;
|
|
}
|
|
return(valptrs);
|
|
}
|
|
}
|
|
else if (strcmp(name, "Resolution") == 0)
|
|
{
|
|
*count = 0;
|
|
valptrs = malloc(sizeof(char *) * NUM_RESOLUTIONS);
|
|
for (i = 0; i < NUM_RESOLUTIONS; i++)
|
|
{
|
|
if (caps.resolutions & pcl_resolutions[i].pcl_code)
|
|
{
|
|
valptrs[*count] = c_strdup(pcl_val_to_string(pcl_resolutions[i].pcl_code,
|
|
pcl_resolutions, NUM_RESOLUTIONS));
|
|
(*count)++;
|
|
}
|
|
}
|
|
return(valptrs);
|
|
}
|
|
else if (strcmp(name, "InkType") == 0)
|
|
{
|
|
if (caps.color_type & PCL_COLOR_CMYKcm)
|
|
{
|
|
valptrs = malloc(sizeof(char *) * 2);
|
|
valptrs[0] = c_strdup(ink_types[0]);
|
|
valptrs[1] = c_strdup(ink_types[1]);
|
|
*count = 2;
|
|
return(valptrs);
|
|
}
|
|
else
|
|
return(NULL);
|
|
}
|
|
else
|
|
return (NULL);
|
|
}
|
|
|
|
|
|
/*
|
|
* 'pcl_imageable_area()' - Return the imageable area of the page.
|
|
*/
|
|
|
|
void
|
|
pcl_imageable_area(const printer_t *printer, /* I - Printer model */
|
|
const vars_t *v, /* I */
|
|
int *left, /* O - Left position in points */
|
|
int *right, /* O - Right position in points */
|
|
int *bottom, /* O - Bottom position in points */
|
|
int *top) /* O - Top position in points */
|
|
{
|
|
int width, length; /* Size of page */
|
|
pcl_cap_t caps; /* Printer caps */
|
|
|
|
caps = pcl_get_model_capabilities(printer->model);
|
|
|
|
default_media_size(printer, v, &width, &length);
|
|
|
|
/*
|
|
* Note: The margins actually vary with paper size, but since you can
|
|
* move the image around on the page anyway, it hardly matters.
|
|
*/
|
|
|
|
*left = caps.left_margin;
|
|
*right = width - caps.right_margin;
|
|
*top = length - caps.top_margin;
|
|
*bottom = caps.bottom_margin;
|
|
}
|
|
|
|
void
|
|
pcl_limit(const printer_t *printer, /* I - Printer model */
|
|
const vars_t *v, /* I */
|
|
int *width, /* O - Left position in points */
|
|
int *length) /* O - Top position in points */
|
|
{
|
|
pcl_cap_t caps= pcl_get_model_capabilities(printer->model);
|
|
*width = caps.max_width;
|
|
*length = caps.max_height;
|
|
}
|
|
|
|
/*
|
|
* 'pcl_print()' - Print an image to an HP printer.
|
|
*/
|
|
|
|
void
|
|
pcl_print(const printer_t *printer, /* I - Model */
|
|
int copies, /* I - Number of copies */
|
|
FILE *prn, /* I - File to print to */
|
|
Image image, /* I - Image to print */
|
|
const vars_t *v)
|
|
{
|
|
unsigned char *cmap = v->cmap;
|
|
int model = printer->model;
|
|
char *resolution = v->resolution;
|
|
const char *media_size;
|
|
char *media_type = v->media_type;
|
|
char *media_source = v->media_source;
|
|
char *ink_type = v->ink_type;
|
|
int output_type = v->output_type;
|
|
int orientation = v->orientation;
|
|
float scaling = v->scaling;
|
|
int top = v->top;
|
|
int left = v->left;
|
|
int y; /* Looping vars */
|
|
int xdpi, ydpi; /* Resolution */
|
|
unsigned short *out;
|
|
unsigned char *in, /* Input pixels */
|
|
*black, /* Black bitmap data */
|
|
*cyan, /* Cyan bitmap data */
|
|
*magenta, /* Magenta bitmap data */
|
|
*yellow, /* Yellow bitmap data */
|
|
*lcyan, /* Light Cyan bitmap data */
|
|
*lmagenta; /* Light Magenta bitmap data */
|
|
int page_left, /* Left margin of page */
|
|
page_right, /* Right margin of page */
|
|
page_top, /* Top of page */
|
|
page_bottom, /* Bottom of page */
|
|
page_width, /* Width of page */
|
|
page_height, /* Height of page */
|
|
out_width, /* Width of image on page */
|
|
out_height, /* Height of image on page */
|
|
out_bpp, /* Output bytes per pixel */
|
|
length, /* Length of raster data */
|
|
errdiv, /* Error dividend */
|
|
errmod, /* Error modulus */
|
|
errval, /* Current error value */
|
|
errline, /* Current raster line */
|
|
errlast; /* Last raster line loaded */
|
|
convert_t colorfunc; /* Color conversion function... */
|
|
void (*writefunc)(FILE *, unsigned char *, int, int);
|
|
/* PCL output function */
|
|
int image_height,
|
|
image_width,
|
|
image_bpp;
|
|
void * dither;
|
|
pcl_cap_t caps; /* Printer capabilities */
|
|
int do_cret, /* 300 DPI CRet printing */
|
|
do_6color, /* CMY + cmK printing */
|
|
planes; /* # of output planes */
|
|
int pcl_media_size, /* PCL media size code */
|
|
pcl_media_type, /* PCL media type code */
|
|
pcl_media_source; /* PCL media source code */
|
|
vars_t nv;
|
|
const papersize_t *pp;
|
|
|
|
memcpy(&nv, v, sizeof(vars_t));
|
|
caps = pcl_get_model_capabilities(model);
|
|
|
|
/*
|
|
* Setup a read-only pixel region for the entire image...
|
|
*/
|
|
|
|
Image_init(image);
|
|
image_height = Image_height(image);
|
|
image_width = Image_width(image);
|
|
image_bpp = Image_bpp(image);
|
|
|
|
/*
|
|
* Choose the correct color conversion function...
|
|
*/
|
|
if (nv.image_type == IMAGE_MONOCHROME)
|
|
{
|
|
output_type = OUTPUT_GRAY;
|
|
}
|
|
|
|
if (caps.color_type == PCL_COLOR_NONE)
|
|
output_type = OUTPUT_GRAY;
|
|
else if (image_bpp < 3 && cmap == NULL && output_type == OUTPUT_COLOR)
|
|
output_type = OUTPUT_GRAY_COLOR; /* Force grayscale output */
|
|
|
|
colorfunc = choose_colorfunc(output_type, image_bpp, cmap, &out_bpp, &nv);
|
|
|
|
/*
|
|
* Figure out the output resolution...
|
|
*/
|
|
|
|
sscanf(resolution,"%dx%d",&xdpi,&ydpi);
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr,"pcl: resolution=%dx%d\n",xdpi,ydpi);
|
|
#endif
|
|
|
|
if (((caps.resolutions & PCL_RES_600_600_MONO) == PCL_RES_600_600_MONO) &&
|
|
output_type != OUTPUT_GRAY && xdpi == 600 && ydpi == 600) {
|
|
fprintf(stderr, "600x600 resolution only available in MONO, changed to 300x300\n");
|
|
xdpi = 300;
|
|
ydpi = 300;
|
|
}
|
|
|
|
do_cret = (xdpi >= 300 && ((caps.color_type & PCL_COLOR_CMYK4) == PCL_COLOR_CMYK4) &&
|
|
nv.image_type != IMAGE_MONOCHROME);
|
|
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "do_cret = %d\n", do_cret);
|
|
#endif
|
|
|
|
do_6color = (strcmp(ink_type, "Color + Photo Cartridges") == 0);
|
|
#ifdef DEBUG
|
|
fprintf(stderr, "do_6color = %d\n", do_6color);
|
|
#endif
|
|
|
|
/*
|
|
* Compute the output size...
|
|
*/
|
|
|
|
pcl_imageable_area(printer, &nv, &page_left, &page_right,
|
|
&page_bottom, &page_top);
|
|
#ifdef DEBUG
|
|
printf("Before compute_page_parameters()\n");
|
|
printf("page_left = %d, page_right = %d, page_top = %d, page_bottom = %d\n",
|
|
page_left, page_right, page_top, page_bottom);
|
|
printf("top = %d, left = %d\n", top, left);
|
|
printf("scaling = %f, image_width = %d, image_height = %d\n", scaling,
|
|
image_width, image_height);
|
|
#endif
|
|
|
|
compute_page_parameters(page_right, page_left, page_top, page_bottom,
|
|
scaling, image_width, image_height, image,
|
|
&orientation, &page_width, &page_height,
|
|
&out_width, &out_height, &left, &top);
|
|
|
|
/*
|
|
* Recompute the image height and width. If the image has been
|
|
* rotated, these will change from previously.
|
|
*/
|
|
image_height = Image_height(image);
|
|
image_width = Image_width(image);
|
|
|
|
#ifdef DEBUG
|
|
printf("After compute_page_parameters()\n");
|
|
printf("page_width = %d, page_height = %d\n", page_width, page_height);
|
|
printf("out_width = %d, out_height = %d\n", out_width, out_height);
|
|
printf("top = %d, left = %d\n", top, left);
|
|
#endif /* DEBUG */
|
|
|
|
/*
|
|
* Let the user know what we're doing...
|
|
*/
|
|
|
|
Image_progress_init(image);
|
|
|
|
/*
|
|
* Send PCL initialization commands...
|
|
*/
|
|
|
|
fputs("\033E", prn); /* PCL reset */
|
|
|
|
/*
|
|
* Set media size
|
|
*/
|
|
|
|
if (strlen(v->media_size) > 0)
|
|
media_size = v->media_size;
|
|
else if ((pp = get_papersize_by_size(v->page_height, v->page_width)) != NULL)
|
|
media_size = pp->name;
|
|
else
|
|
media_size = "";
|
|
|
|
pcl_media_size = pcl_convert_media_size(media_size, model);
|
|
|
|
#ifdef DEBUG
|
|
printf("pcl_media_size = %d, media_size = %s\n", pcl_media_size, media_size);
|
|
#endif
|
|
|
|
/*
|
|
* If the media size requested is unknown, try it as a custom size.
|
|
*
|
|
* Warning: The margins may need to be fixed for this!
|
|
*/
|
|
|
|
if (pcl_media_size == -1) {
|
|
fprintf(stderr, "Paper size %s is not directly supported by printer.\n",
|
|
media_size);
|
|
fprintf(stderr, "Trying as custom pagesize (watch the margins!)\n");
|
|
pcl_media_size = PCL_PAPERSIZE_CUSTOM; /* Custom */
|
|
}
|
|
|
|
fprintf(prn, "\033&l%dA", pcl_media_size);
|
|
|
|
fputs("\033&l0L", prn); /* Turn off perforation skip */
|
|
fputs("\033&l0E", prn); /* Reset top margin to 0 */
|
|
|
|
/*
|
|
* Convert media type string to the code, if specified.
|
|
*/
|
|
|
|
if (strlen(media_source) != 0) {
|
|
pcl_media_source = pcl_string_to_val(media_source, pcl_media_sources,
|
|
sizeof(pcl_media_sources) / sizeof(pcl_t));
|
|
|
|
#ifdef DEBUG
|
|
printf("pcl_media_source = %d, media_source = %s\n", pcl_media_source,
|
|
media_source);
|
|
#endif
|
|
|
|
if (pcl_media_source == -1)
|
|
fprintf(stderr, "Unknown media source %s, ignored.\n", media_source);
|
|
else {
|
|
|
|
/* Correct the value by taking the modulus */
|
|
|
|
pcl_media_source = pcl_media_source % PAPERSOURCE_MOD;
|
|
fprintf(prn, "\033&l%dH", pcl_media_source);
|
|
}
|
|
}
|
|
|
|
/*
|
|
* Convert media type string to the code, if specified.
|
|
*/
|
|
|
|
if (strlen(media_type) != 0) {
|
|
pcl_media_type = pcl_string_to_val(media_type, pcl_media_types,
|
|
sizeof(pcl_media_types) / sizeof(pcl_t));
|
|
|
|
#ifdef DEBUG
|
|
printf("pcl_media_type = %d, media_type = %s\n", pcl_media_type,
|
|
media_type);
|
|
#endif
|
|
|
|
if (pcl_media_type == -1) {
|
|
fprintf(stderr, "Unknown media type %s, set to PLAIN.\n", media_type);
|
|
pcl_media_type = PCL_PAPERTYPE_PLAIN;
|
|
}
|
|
}
|
|
else
|
|
pcl_media_type = PCL_PAPERTYPE_PLAIN;
|
|
|
|
/*
|
|
* Set DJ print quality to "best" if resolution >= 300
|
|
*/
|
|
|
|
if ((xdpi >= 300) && ((caps.printer_type & PCL_PRINTER_DJ) == PCL_PRINTER_DJ))
|
|
{
|
|
if ((caps.printer_type & PCL_PRINTER_MEDIATYPE) == PCL_PRINTER_MEDIATYPE)
|
|
{
|
|
fputs("\033*o1M", prn); /* Quality = presentation */
|
|
fprintf(prn, "\033&l%dM", pcl_media_type);
|
|
}
|
|
else
|
|
{
|
|
fputs("\033*r2Q", prn); /* Quality (high) */
|
|
fputs("\033*o2Q", prn); /* Shingling (4 passes) */
|
|
|
|
/* Depletion depends on media type and cart type. */
|
|
|
|
if ((pcl_media_type == PCL_PAPERTYPE_PLAIN)
|
|
|| (pcl_media_type == PCL_PAPERTYPE_BOND)) {
|
|
if ((caps.color_type & PCL_COLOR_CMY) == PCL_COLOR_CMY)
|
|
fputs("\033*o2D", prn); /* Depletion 25% */
|
|
else
|
|
fputs("\033*o5D", prn); /* Depletion 50% with gamma correction */
|
|
}
|
|
|
|
else if ((pcl_media_type == PCL_PAPERTYPE_PREMIUM)
|
|
|| (pcl_media_type == PCL_PAPERTYPE_GLOSSY)
|
|
|| (pcl_media_type == PCL_PAPERTYPE_TRANS))
|
|
fputs("\033*o1D", prn); /* Depletion none */
|
|
}
|
|
}
|
|
|
|
if ((xdpi != ydpi) || (do_cret) || (do_6color))
|
|
/* Set resolution using CRD */
|
|
{
|
|
|
|
/*
|
|
* Send configure image data command with horizontal and
|
|
* vertical resolutions as well as a color count...
|
|
*/
|
|
|
|
if (output_type != OUTPUT_GRAY)
|
|
if ((caps.color_type & PCL_COLOR_CMY) == PCL_COLOR_CMY)
|
|
planes = 3;
|
|
else
|
|
if (do_6color)
|
|
planes = 6;
|
|
else
|
|
planes = 4;
|
|
else
|
|
planes = 1;
|
|
|
|
fprintf(prn, "\033*g%dW", 2 + (planes * 6));
|
|
putc(2, prn); /* Format 2 (Complex Direct Planar) */
|
|
putc(planes, prn); /* # output planes */
|
|
|
|
if (planes != 3) {
|
|
putc(xdpi >> 8, prn); /* Black resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
}
|
|
|
|
if (planes != 1) {
|
|
putc(xdpi >> 8, prn); /* Cyan resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
|
|
putc(xdpi >> 8, prn); /* Magenta resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
|
|
putc(xdpi >> 8, prn); /* Yellow resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
}
|
|
if (planes == 6)
|
|
{
|
|
putc(xdpi >> 8, prn); /* Light Cyan resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
|
|
putc(xdpi >> 8, prn); /* Light Magenta resolution */
|
|
putc(xdpi, prn);
|
|
putc(ydpi >> 8, prn);
|
|
putc(ydpi, prn);
|
|
putc(0, prn);
|
|
putc(do_cret ? 4 : 2, prn);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
fprintf(prn, "\033*t%dR", xdpi); /* Simple resolution */
|
|
if (output_type != OUTPUT_GRAY)
|
|
{
|
|
if ((caps.color_type & PCL_COLOR_CMY) == PCL_COLOR_CMY)
|
|
fputs("\033*r-3U", prn); /* Simple CMY color */
|
|
else
|
|
fputs("\033*r-4U", prn); /* Simple KCMY color */
|
|
}
|
|
}
|
|
|
|
#ifndef PCL_DEBUG_DISABLE_COMPRESSION
|
|
if ((caps.printer_type & PCL_PRINTER_TIFF) == PCL_PRINTER_TIFF)
|
|
{
|
|
fputs("\033*b2M", prn); /* Mode 2 (TIFF) */
|
|
writefunc = pcl_mode2;
|
|
}
|
|
else
|
|
#endif
|
|
{
|
|
fputs("\033*b0M", prn); /* Mode 0 (no compression) */
|
|
writefunc = pcl_mode0;
|
|
}
|
|
|
|
/*
|
|
* Convert image size to printer resolution and setup the page for printing...
|
|
*/
|
|
|
|
out_width = xdpi * out_width / 72;
|
|
out_height = ydpi * out_height / 72;
|
|
|
|
fprintf(prn, "\033&a%dH", 10 * left); /* Set left raster position */
|
|
fprintf(prn, "\033&a%dV", 10 * top); /* Set top raster position */
|
|
fprintf(prn, "\033*r%dS", out_width); /* Set raster width */
|
|
fprintf(prn, "\033*r%dT", out_height); /* Set raster height */
|
|
|
|
fputs("\033*r1A", prn); /* Start GFX */
|
|
|
|
/*
|
|
* Allocate memory for the raster data...
|
|
*/
|
|
|
|
length = (out_width + 7) / 8;
|
|
if (do_cret)
|
|
length *= 2;
|
|
|
|
if (output_type == OUTPUT_GRAY)
|
|
{
|
|
black = malloc(length);
|
|
cyan = NULL;
|
|
magenta = NULL;
|
|
yellow = NULL;
|
|
lcyan = NULL;
|
|
lmagenta = NULL;
|
|
}
|
|
else
|
|
{
|
|
cyan = malloc(length);
|
|
magenta = malloc(length);
|
|
yellow = malloc(length);
|
|
|
|
if ((caps.color_type & PCL_COLOR_CMY) == PCL_COLOR_CMY)
|
|
black = NULL;
|
|
else
|
|
black = malloc(length);
|
|
if (do_6color)
|
|
{
|
|
lcyan = malloc(length);
|
|
lmagenta = malloc(length);
|
|
}
|
|
else
|
|
{
|
|
lcyan = NULL;
|
|
lmagenta = NULL;
|
|
}
|
|
}
|
|
|
|
/*
|
|
* Output the page, rotating as necessary...
|
|
*/
|
|
|
|
compute_lut(256, &nv);
|
|
|
|
if (xdpi > ydpi)
|
|
dither = init_dither(image_width, out_width, 1, xdpi / ydpi, &nv);
|
|
else
|
|
dither = init_dither(image_width, out_width, ydpi / xdpi, 1, &nv);
|
|
|
|
/* Set up dithering for special printers. */
|
|
|
|
#if 0 /* Leave alone for now */
|
|
dither_set_black_levels(dither, 1.5, 1.5, 1.5);
|
|
dither_set_black_lower(dither, .4);
|
|
dither_set_black_upper(dither, .999);
|
|
#endif
|
|
|
|
if (do_cret) /* 4-level printing for 800/1120 */
|
|
{
|
|
dither_set_y_ranges_simple(dither, 3, dot_sizes, nv.density);
|
|
dither_set_k_ranges_simple(dither, 3, dot_sizes, nv.density);
|
|
|
|
/* Note: no printer I know of does both CRet (4-level) and 6 colour, but
|
|
what the heck. variable_dither_ranges copied from print-escp2.c */
|
|
|
|
if (do_6color) /* Photo for 69x */
|
|
{
|
|
dither_set_c_ranges(dither, 6, variable_dither_ranges, nv.density);
|
|
dither_set_m_ranges(dither, 6, variable_dither_ranges, nv.density);
|
|
}
|
|
else
|
|
{
|
|
dither_set_c_ranges_simple(dither, 3, dot_sizes, nv.density);
|
|
dither_set_m_ranges_simple(dither, 3, dot_sizes, nv.density);
|
|
}
|
|
}
|
|
else
|
|
|
|
/* Set light inks for 6 colour printers. Numbers copied from print-escp2.c */
|
|
|
|
if (do_6color)
|
|
dither_set_light_inks(dither, .25, .25, 0.0, nv.density);
|
|
|
|
switch (nv.image_type)
|
|
{
|
|
case IMAGE_LINE_ART:
|
|
dither_set_ink_spread(dither, 19);
|
|
break;
|
|
case IMAGE_SOLID_TONE:
|
|
dither_set_ink_spread(dither, 15);
|
|
break;
|
|
case IMAGE_CONTINUOUS:
|
|
dither_set_ink_spread(dither, 14);
|
|
break;
|
|
}
|
|
dither_set_density(dither, nv.density);
|
|
|
|
in = malloc(image_width * image_bpp);
|
|
out = malloc(image_width * out_bpp * 2);
|
|
|
|
errdiv = image_height / out_height;
|
|
errmod = image_height % out_height;
|
|
errval = 0;
|
|
errlast = -1;
|
|
errline = 0;
|
|
|
|
for (y = 0; y < out_height; y ++)
|
|
{
|
|
#ifdef DEBUG
|
|
printf("pcl_print: y = %d, line = %d, val = %d, mod = %d, height = %d\n",
|
|
y, errline, errval, errmod, out_height);
|
|
#endif /* DEBUG */
|
|
|
|
if ((y & 255) == 0)
|
|
Image_note_progress(image, y, out_height);
|
|
|
|
if (errline != errlast)
|
|
{
|
|
errlast = errline;
|
|
Image_get_row(image, in, errline);
|
|
}
|
|
|
|
(*colorfunc)(in, out, image_width, image_bpp, cmap, &nv);
|
|
|
|
if (do_cret)
|
|
{
|
|
/*
|
|
* 4-level (CRet) dithers...
|
|
*/
|
|
|
|
if (output_type == OUTPUT_GRAY)
|
|
{
|
|
dither_black(out, y, dither, black);
|
|
(*writefunc)(prn, black + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, black, length / 2, 1);
|
|
}
|
|
else
|
|
{
|
|
dither_cmyk(out, y, dither, cyan, lcyan, magenta, lmagenta,
|
|
yellow, NULL, black);
|
|
|
|
(*writefunc)(prn, black + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, black, length / 2, 0);
|
|
(*writefunc)(prn, cyan + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, cyan, length / 2, 0);
|
|
(*writefunc)(prn, magenta + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, magenta, length / 2, 0);
|
|
(*writefunc)(prn, yellow + length / 2, length / 2, 0);
|
|
if (do_6color)
|
|
{
|
|
(*writefunc)(prn, yellow, length / 2, 0);
|
|
(*writefunc)(prn, lcyan + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, lcyan, length / 2, 0);
|
|
(*writefunc)(prn, lmagenta + length / 2, length / 2, 0);
|
|
(*writefunc)(prn, lmagenta, length / 2, 1); /* Last plane set on light magenta */
|
|
}
|
|
else
|
|
(*writefunc)(prn, yellow, length / 2, 1); /* Last plane set on yellow */
|
|
}
|
|
}
|
|
else
|
|
{
|
|
/*
|
|
* Standard 2-level dithers...
|
|
*/
|
|
|
|
if (output_type == OUTPUT_GRAY)
|
|
{
|
|
if (nv.image_type == IMAGE_MONOCHROME)
|
|
dither_fastblack(out, y, dither, black);
|
|
else
|
|
dither_black(out, y, dither, black);
|
|
(*writefunc)(prn, black, length, 1);
|
|
}
|
|
else
|
|
{
|
|
dither_cmyk(out, y, dither, cyan, lcyan, magenta, lmagenta,
|
|
yellow, NULL, black);
|
|
|
|
if (black != NULL)
|
|
(*writefunc)(prn, black, length, 0);
|
|
(*writefunc)(prn, cyan, length, 0);
|
|
(*writefunc)(prn, magenta, length, 0);
|
|
if (do_6color)
|
|
{
|
|
(*writefunc)(prn, yellow, length, 0);
|
|
(*writefunc)(prn, lcyan, length, 0);
|
|
(*writefunc)(prn, lmagenta, length, 1); /* Last plane set on light magenta */
|
|
}
|
|
else
|
|
(*writefunc)(prn, yellow, length, 1); /* Last plane set on yellow */
|
|
}
|
|
}
|
|
|
|
errval += errmod;
|
|
errline += errdiv;
|
|
if (errval >= out_height)
|
|
{
|
|
errval -= out_height;
|
|
errline ++;
|
|
}
|
|
}
|
|
Image_progress_conclude(image);
|
|
|
|
free_dither(dither);
|
|
|
|
|
|
/*
|
|
* Cleanup...
|
|
*/
|
|
|
|
free_lut(&nv);
|
|
free(in);
|
|
free(out);
|
|
|
|
if (black != NULL)
|
|
free(black);
|
|
if (cyan != NULL)
|
|
{
|
|
free(cyan);
|
|
free(magenta);
|
|
free(yellow);
|
|
}
|
|
if (lcyan != NULL)
|
|
{
|
|
free(lcyan);
|
|
free(lmagenta);
|
|
}
|
|
|
|
if ((caps.printer_type & PCL_PRINTER_NEW_ERG) == PCL_PRINTER_NEW_ERG)
|
|
fputs("\033*rC", prn);
|
|
else
|
|
fputs("\033*rB", prn);
|
|
|
|
fputs("\033&l0H", prn); /* Eject page */
|
|
fputs("\033E", prn); /* PCL reset */
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
* 'pcl_mode0()' - Send PCL graphics using mode 0 (no) compression.
|
|
*/
|
|
|
|
static void
|
|
pcl_mode0(FILE *prn, /* I - Print file or command */
|
|
unsigned char *line, /* I - Output bitmap data */
|
|
int length, /* I - Length of bitmap data */
|
|
int last_plane) /* I - True if this is the last plane */
|
|
{
|
|
fprintf(prn, "\033*b%d%c", length, last_plane ? 'W' : 'V');
|
|
fwrite(line, length, 1, prn);
|
|
}
|
|
|
|
|
|
/*
|
|
* 'pcl_mode2()' - Send PCL graphics using mode 2 (TIFF) compression.
|
|
*/
|
|
|
|
static void
|
|
pcl_mode2(FILE *prn, /* I - Print file or command */
|
|
unsigned char *line, /* I - Output bitmap data */
|
|
int length, /* I - Length of bitmap data */
|
|
int last_plane) /* I - True if this is the last plane */
|
|
{
|
|
unsigned char comp_buf[1536], /* Compression buffer */
|
|
*comp_ptr, /* Current slot in buffer */
|
|
*start, /* Start of compressed data */
|
|
repeat; /* Repeating char */
|
|
int count, /* Count of compressed bytes */
|
|
tcount; /* Temporary count < 128 */
|
|
|
|
|
|
/*
|
|
* Compress using TIFF "packbits" run-length encoding...
|
|
*/
|
|
|
|
comp_ptr = comp_buf;
|
|
|
|
while (length > 0)
|
|
{
|
|
/*
|
|
* Get a run of non-repeated chars...
|
|
*/
|
|
|
|
start = line;
|
|
line += 2;
|
|
length -= 2;
|
|
|
|
while (length > 0 && (line[-2] != line[-1] || line[-1] != line[0]))
|
|
{
|
|
line ++;
|
|
length --;
|
|
}
|
|
|
|
line -= 2;
|
|
length += 2;
|
|
|
|
/*
|
|
* Output the non-repeated sequences (max 128 at a time).
|
|
*/
|
|
|
|
count = line - start;
|
|
while (count > 0)
|
|
{
|
|
tcount = count > 128 ? 128 : count;
|
|
|
|
comp_ptr[0] = tcount - 1;
|
|
memcpy(comp_ptr + 1, start, tcount);
|
|
|
|
comp_ptr += tcount + 1;
|
|
start += tcount;
|
|
count -= tcount;
|
|
}
|
|
|
|
if (length <= 0)
|
|
break;
|
|
|
|
/*
|
|
* Find the repeated sequences...
|
|
*/
|
|
|
|
start = line;
|
|
repeat = line[0];
|
|
|
|
line ++;
|
|
length --;
|
|
|
|
while (length > 0 && *line == repeat)
|
|
{
|
|
line ++;
|
|
length --;
|
|
}
|
|
|
|
/*
|
|
* Output the repeated sequences (max 128 at a time).
|
|
*/
|
|
|
|
count = line - start;
|
|
while (count > 0)
|
|
{
|
|
tcount = count > 128 ? 128 : count;
|
|
|
|
comp_ptr[0] = 1 - tcount;
|
|
comp_ptr[1] = repeat;
|
|
|
|
comp_ptr += 2;
|
|
count -= tcount;
|
|
}
|
|
}
|
|
|
|
/*
|
|
* Send a line of raster graphics...
|
|
*/
|
|
|
|
fprintf(prn, "\033*b%d%c", (int)(comp_ptr - comp_buf), last_plane ? 'W' : 'V');
|
|
fwrite(comp_buf, comp_ptr - comp_buf, 1, prn);
|
|
}
|