Ejemplo n.º 1
0
/* Write the BMP file header. */
int
write_bmp_header(gx_device_printer *pdev, FILE *file)
{
    int depth = pdev->color_info.depth;
    bmp_quad palette[256];

    if (depth <= 8) {
	int i;
	gx_color_value rgb[3];
	bmp_quad q;

	q.reserved = 0;
	for (i = 0; i != 1 << depth; i++) {
	    /* Note that the use of map_color_rgb is deprecated in
	       favor of decode_color. This should work, though, because
	       backwards compatibility is preserved. */
	    (*dev_proc(pdev, map_color_rgb))((gx_device *)pdev,
					     (gx_color_index)i, rgb);
	    q.red = gx_color_value_to_byte(rgb[0]);
	    q.green = gx_color_value_to_byte(rgb[1]);
	    q.blue = gx_color_value_to_byte(rgb[2]);
	    palette[i] = q;
	}
    }
    return write_bmp_depth_header(pdev, file, depth, (const byte *)palette,
				  gdev_prn_raster(pdev));
}
Ejemplo n.º 2
0
/* Map a r-g-b color to a color index. */
gx_color_index
bmp_map_16m_rgb_color(gx_device * dev, const gx_color_value cv[])
{

    gx_color_value r, g, b;
    r = cv[0]; g = cv[1]; b = cv[2];
    return gx_color_value_to_byte(r) +
	((uint) gx_color_value_to_byte(g) << 8) +
	((ulong) gx_color_value_to_byte(b) << 16);
}
Ejemplo n.º 3
0
/* Encode a r-g-b color to a color index. */
static gx_color_index
os2prn_map_rgb_color(gx_device * dev, const gx_color_value cv[])
{
    gx_color_value r = cv[0];
    gx_color_value g = cv[1];
    gx_color_value b = cv[2];
    return gx_color_value_to_byte(r) +
		((uint) gx_color_value_to_byte(g) << 8) +
		((ulong) gx_color_value_to_byte(b) << 16);
}
Ejemplo n.º 4
0
/* Map a r-g-b color to a color index. */
static gx_color_index
cp50_rgb_color(gx_device *dev, const gx_color_value cv[])
{   
    gx_color_value red, green, blue;

    red = cv[0]; green = cv[1]; blue = cv[2];
    return ((ulong)gx_color_value_to_byte(red) << 16)+
           ((uint)gx_color_value_to_byte(green) << 8) +
           gx_color_value_to_byte(blue);
}
Ejemplo n.º 5
0
static gx_color_index
pngalpha_encode_color(gx_device * dev, const gx_color_value cv[])
{
    /* bits 0-7 are alpha, stored inverted to avoid white/opaque 
     * being 0xffffffff which is also gx_no_color_index.
     * So 0xff is transparent and 0x00 is opaque.
     * We always return opaque colors (bits 0-7 = 0).
     * Return value is 0xRRGGBB00.
     */
    return
	((uint) gx_color_value_to_byte(cv[2]) << 8) +
	((ulong) gx_color_value_to_byte(cv[1]) << 16) +
	((ulong) gx_color_value_to_byte(cv[0]) << 24);
}
Ejemplo n.º 6
0
static gx_color_index
dca_map_rgb_alpha_color(gx_device * dev,
	      gx_color_value red, gx_color_value green, gx_color_value blue,
			gx_color_value alpha)
{				/*
				 * We work exclusively with premultiplied color values, so we
				 * have to premultiply the color components by alpha here.
				 */
    byte a = gx_color_value_to_byte(alpha);

#define premult_(c)\
  (((c) * a + gx_max_color_value / 2) / gx_max_color_value)
#ifdef PREMULTIPLY_TOWARDS_WHITE
    byte bias = ~a;

#  define premult(c) (premult_(c) + bias)
#else
#  define premult(c) premult_(c)
#endif
    gx_color_index color;

    if (dev->color_info.num_components == 1) {
	uint lum =
	(red * lum_red_weight + green * lum_green_weight +
	 blue * lum_blue_weight + lum_all_weights / 2) /
	lum_all_weights;

	if (a == 0xff)
	    color = gx_color_value_to_byte(lum);
	else			/* Premultiplication is necessary. */
	    color = premult(lum);
    } else {
	if (a == 0xff)
	    color =
		((uint) gx_color_value_to_byte(red) << 16) +
		((uint) gx_color_value_to_byte(green) << 8) +
		gx_color_value_to_byte(blue);
	else			/* Premultiplication is necessary. */
	    color =
		(premult(red) << 16) + (premult(green) << 8) + premult(blue);
    }
#undef premult
    return (color << 8) + a;
}
Ejemplo n.º 7
0
/* Map a r-g-b color to a color index. */
static gx_color_index
win_pr2_map_rgb_color(gx_device * dev, const gx_color_value cv[])
{
    gx_color_value r = cv[0];
    gx_color_value g = cv[1];
    gx_color_value b = cv[2];
    switch (dev->color_info.depth) {
	case 1:
	    return gdev_prn_map_rgb_color(dev, cv);
	case 4:
	    /* use only 8 colors */
	    return (r > (gx_max_color_value / 2 + 1) ? 4 : 0) +
		(g > (gx_max_color_value / 2 + 1) ? 2 : 0) +
		(b > (gx_max_color_value / 2 + 1) ? 1 : 0);
	case 8:
	    return pc_8bit_map_rgb_color(dev, cv);
	case 24:
	    return gx_color_value_to_byte(r) +
		((uint) gx_color_value_to_byte(g) << 8) +
		((ulong) gx_color_value_to_byte(b) << 16);
    }
    return 0;			/* error */
}
Ejemplo n.º 8
0
/* Get the color map for a device.  Return true if there is one. */
static bool
param_HWColorMap(gx_device * dev, byte * palette /* 3 << 8 */ )
{
    int depth = dev->color_info.depth;
    int colors = dev->color_info.num_components;

    if (depth <= 8 && colors <= 3) {
        byte *p = palette;
        gx_color_value rgb[3];
        gx_color_index i;

        fill_dev_proc(dev, map_color_rgb, gx_default_map_color_rgb);
        for (i = 0; (i >> depth) == 0; i++) {
            int j;

            if ((*dev_proc(dev, map_color_rgb)) (dev, i, rgb) < 0)
                return false;
            for (j = 0; j < colors; j++)
                *p++ = gx_color_value_to_byte(rgb[j]);
        }
        return true;
    }
Ejemplo n.º 9
0
/* This routine is used for all formats. */
static int
png_print_page(gx_device_printer * pdev, FILE * file)
{
    gs_memory_t *mem = pdev->memory;
    int raster = gdev_prn_raster(pdev);

    /* PNG structures */
    byte *row = gs_alloc_bytes(mem, raster, "png raster buffer");
    png_struct *png_ptr =
    png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);
    png_info *info_ptr =
    png_create_info_struct(png_ptr);
    int height = pdev->height;
    int depth = pdev->color_info.depth;
    int y;
    int code;			/* return code */
    char software_key[80];
    char software_text[256];
    png_text text_png;

    if (row == 0 || png_ptr == 0 || info_ptr == 0) {
	code = gs_note_error(gs_error_VMerror);
	goto done;
    }
    /* set error handling */
    if (setjmp(png_ptr->jmpbuf)) {
	/* If we get here, we had a problem reading the file */
	code = gs_note_error(gs_error_VMerror);
	goto done;
    }
    code = 0;			/* for normal path */
    /* set up the output control */
    png_init_io(png_ptr, file);

    /* set the file information here */
    info_ptr->width = pdev->width;
    info_ptr->height = pdev->height;
    /* resolution is in pixels per meter vs. dpi */
    info_ptr->x_pixels_per_unit =
	(png_uint_32) (pdev->HWResolution[0] * (100.0 / 2.54));
    info_ptr->y_pixels_per_unit =
	(png_uint_32) (pdev->HWResolution[1] * (100.0 / 2.54));
    info_ptr->phys_unit_type = PNG_RESOLUTION_METER;
    info_ptr->valid |= PNG_INFO_pHYs;
    switch (depth) {
	case 32:
	    info_ptr->bit_depth = 8;
	    info_ptr->color_type = PNG_COLOR_TYPE_RGB_ALPHA;
	    png_set_invert_alpha(png_ptr);
	    {   gx_device_pngalpha *ppdev = (gx_device_pngalpha *)pdev;
		png_color_16 background;
		background.index = 0;
		background.red =   (ppdev->background >> 16) & 0xff;
		background.green = (ppdev->background >> 8)  & 0xff;
		background.blue =  (ppdev->background)       & 0xff;
		background.gray = 0;
		png_set_bKGD(png_ptr, info_ptr, &background);
	    }
	    break;
	case 48:
	    info_ptr->bit_depth = 16;
	    info_ptr->color_type = PNG_COLOR_TYPE_RGB;
#if defined(ARCH_IS_BIG_ENDIAN) && (!ARCH_IS_BIG_ENDIAN) 
	    png_set_swap(png_ptr);
#endif
	    break;
	case 24:
	    info_ptr->bit_depth = 8;
	    info_ptr->color_type = PNG_COLOR_TYPE_RGB;
	    break;
	case 8:
	    info_ptr->bit_depth = 8;
	    if (gx_device_has_color(pdev))
		info_ptr->color_type = PNG_COLOR_TYPE_PALETTE;
	    else
		info_ptr->color_type = PNG_COLOR_TYPE_GRAY;
	    break;
	case 4:
	    info_ptr->bit_depth = 4;
	    info_ptr->color_type = PNG_COLOR_TYPE_PALETTE;
	    break;
	case 1:
	    info_ptr->bit_depth = 1;
	    info_ptr->color_type = PNG_COLOR_TYPE_GRAY;
	    /* invert monocrome pixels */
	    png_set_invert_mono(png_ptr);
	    break;
    }

    /* set the palette if there is one */
    if (info_ptr->color_type == PNG_COLOR_TYPE_PALETTE) {
	int i;
	int num_colors = 1 << depth;
	gx_color_value rgb[3];

	info_ptr->palette =
	    (void *)gs_alloc_bytes(mem, 256 * sizeof(png_color),
				   "png palette");
	if (info_ptr->palette == 0) {
	    code = gs_note_error(gs_error_VMerror);
	    goto done;
	}
	info_ptr->num_palette = num_colors;
	info_ptr->valid |= PNG_INFO_PLTE;
	for (i = 0; i < num_colors; i++) {
	    (*dev_proc(pdev, map_color_rgb)) ((gx_device *) pdev,
					      (gx_color_index) i, rgb);
	    info_ptr->palette[i].red = gx_color_value_to_byte(rgb[0]);
	    info_ptr->palette[i].green = gx_color_value_to_byte(rgb[1]);
	    info_ptr->palette[i].blue = gx_color_value_to_byte(rgb[2]);
	}
    }
    /* add comment */
    strncpy(software_key, "Software", sizeof(software_key));
    sprintf(software_text, "%s %d.%02d", gs_product,
	    (int)(gs_revision / 100), (int)(gs_revision % 100));
    text_png.compression = -1;	/* uncompressed */
    text_png.key = software_key;
    text_png.text = software_text;
    text_png.text_length = strlen(software_text);
    info_ptr->text = &text_png;
    info_ptr->num_text = 1;

    /* write the file information */
    png_write_info(png_ptr, info_ptr);

    /* don't write the comments twice */
    info_ptr->num_text = 0;
    info_ptr->text = NULL;

    /* Write the contents of the image. */
    for (y = 0; y < height; y++) {
	gdev_prn_copy_scan_lines(pdev, y, row, raster);
	png_write_rows(png_ptr, &row, 1);
    }

    /* write the rest of the file */
    png_write_end(png_ptr, info_ptr);

    /* if you alloced the palette, free it here */
    gs_free_object(mem, info_ptr->palette, "png palette");

  done:
    /* free the structures */
    png_destroy_write_struct(&png_ptr, &info_ptr);
    gs_free_object(mem, row, "png raster buffer");

    return code;
}
Ejemplo n.º 10
0
/* one scan line at a time */
static int
win_pr2_print_page(gx_device_printer * pdev, FILE * file)
{
    int raster = gdev_prn_raster(pdev);

    /* BMP scan lines are padded to 32 bits. */
    ulong bmp_raster = raster + (-raster & 3);
    ulong bmp_raster_multi;
    int scan_lines, yslice, lines, i;
    int width;
    int depth = pdev->color_info.depth;
    byte *row;
    int y;
    int code = 0;		/* return code */
    MSG msg;
    char dlgtext[32];
    HGLOBAL hrow;
    int ratio = ((gx_device_win_pr2 *)pdev)->ratio;

    struct bmi_s {
	BITMAPINFOHEADER h;
	RGBQUAD pal[256];
    } bmi;

    scan_lines = dev_print_scan_lines(pdev);
    width = (int)(pdev->width - ((dev_l_margin(pdev) + dev_r_margin(pdev) -
				  dev_x_offset(pdev)) * pdev->x_pixels_per_inch));

    yslice = 65535 / bmp_raster;	/* max lines in 64k */
    bmp_raster_multi = bmp_raster * yslice;
    hrow = GlobalAlloc(0, bmp_raster_multi);
    row = GlobalLock(hrow);
    if (row == 0)		/* can't allocate row buffer */
	return_error(gs_error_VMerror);

    /* Write the info header. */

    bmi.h.biSize = sizeof(bmi.h);
    bmi.h.biWidth = pdev->width;	/* wdev->mdev.width; */
    bmi.h.biHeight = yslice;
    bmi.h.biPlanes = 1;
    bmi.h.biBitCount = pdev->color_info.depth;
    bmi.h.biCompression = 0;
    bmi.h.biSizeImage = 0;	/* default */
    bmi.h.biXPelsPerMeter = 0;	/* default */
    bmi.h.biYPelsPerMeter = 0;	/* default */

    StartPage(wdev->hdcprn);
    
    /* Write the palette. */

    if (depth <= 8) {
	int i;
	gx_color_value rgb[3];
	LPRGBQUAD pq;

	bmi.h.biClrUsed = 1 << depth;
	bmi.h.biClrImportant = 1 << depth;
	for (i = 0; i != 1 << depth; i++) {
	    (*dev_proc(pdev, map_color_rgb)) ((gx_device *) pdev,
					      (gx_color_index) i, rgb);
	    pq = &bmi.pal[i];
	    pq->rgbRed = gx_color_value_to_byte(rgb[0]);
	    pq->rgbGreen = gx_color_value_to_byte(rgb[1]);
	    pq->rgbBlue = gx_color_value_to_byte(rgb[2]);
	    pq->rgbReserved = 0;
	}
    } else {
	bmi.h.biClrUsed = 0;
	bmi.h.biClrImportant = 0;
    }

    if (!wdev->nocancel) {
	sprintf(dlgtext, "Printing page %d", (int)(pdev->PageCount) + 1);
	SetWindowText(GetDlgItem(wdev->hDlgModeless, CANCEL_PRINTING), dlgtext);
	ShowWindow(wdev->hDlgModeless, SW_SHOW);
    }
    for (y = 0; y < scan_lines;) {
	/* copy slice to row buffer */
	if (y > scan_lines - yslice)
	    lines = scan_lines - y;
	else
	    lines = yslice;
	for (i = 0; i < lines; i++)
	    gdev_prn_copy_scan_lines(pdev, y + i,
			      row + (bmp_raster * (lines - 1 - i)), raster);
	
	if (ratio > 1) {
	    StretchDIBits(wdev->hdcprn, 0, y*ratio, pdev->width*ratio, lines*ratio,
			  0, 0, pdev->width, lines,
			  row,
			  (BITMAPINFO FAR *) & bmi, DIB_RGB_COLORS, SRCCOPY);
	} else {
	    SetDIBitsToDevice(wdev->hdcprn, 0, y, pdev->width, lines,
			      0, 0, 0, lines,
			      row,
			      (BITMAPINFO FAR *) & bmi, DIB_RGB_COLORS);
	}
	y += lines;

	if (!wdev->nocancel) {
	    /* inform user of progress */
	    sprintf(dlgtext, "%d%% done", (int)(y * 100L / scan_lines));
	    SetWindowText(GetDlgItem(wdev->hDlgModeless, CANCEL_PCDONE), dlgtext);
	}
	/* process message loop */
	while (PeekMessage(&msg, wdev->hDlgModeless, 0, 0, PM_REMOVE)) {
	    if ((wdev->hDlgModeless == 0) || !IsDialogMessage(wdev->hDlgModeless, &msg)) {
		TranslateMessage(&msg);
		DispatchMessage(&msg);
	    }
	}
	if ((!wdev->nocancel) && (wdev->hDlgModeless == 0)) {
	    /* user pressed cancel button */
	    break;
	}
    }

    if ((!wdev->nocancel) && (wdev->hDlgModeless == 0))
	code = gs_error_Fatal;	/* exit Ghostscript cleanly */
    else {
	/* push out the page */
	if (!wdev->nocancel)
	    SetWindowText(GetDlgItem(wdev->hDlgModeless, CANCEL_PCDONE),
			  "Ejecting page...");
	EndPage(wdev->hdcprn);
	if (!wdev->nocancel)
	    ShowWindow(wdev->hDlgModeless, SW_HIDE);
    }

    GlobalUnlock(hrow);
    GlobalFree(hrow);

    return code;
}
Ejemplo n.º 11
0
/* one scan line at a time */
static int
os2prn_print_page(gx_device_printer * pdev, FILE * file)
{
    int raster = gdev_prn_raster(pdev);

    /* BMP scan lines are padded to 32 bits. */
    ulong bmp_raster = (raster + 3) & (~3);
    ulong bmp_raster_multi;
    int height = pdev->height;
    int depth = pdev->color_info.depth;
    byte *row;
    int y;
    int code = 0;		/* return code */
    POINTL apts[4];
    APIRET rc;
    POINTL aptsb[4];
    HBITMAP hbmp, hbmr;
    int i, lines;
    int ystart, yend;
    int yslice;

    struct bmi_s {
	BITMAPINFOHEADER2 h;
	RGB2 pal[256];
    } bmi;

    yslice = 65535 / bmp_raster;
    bmp_raster_multi = bmp_raster * yslice;
    row = (byte *) gs_malloc(pdev->memory, bmp_raster_multi, 1, "bmp file buffer");
    if (row == 0)		/* can't allocate row buffer */
	return_error(gs_error_VMerror);

    if (opdev->newframe)
	DevEscape(opdev->hdc, DEVESC_NEWFRAME, 0L, NULL, NULL, NULL);
    opdev->newframe = 1;

    /* Write the info header. */

    memset(&bmi.h, 0, sizeof(bmi.h));
    bmi.h.cbFix = sizeof(bmi.h);
    bmi.h.cx = pdev->width;	/* opdev->mdev.width; */
    /* bmi.h.cy = height; */
    bmi.h.cy = yslice;		/* size for memory PS */
    bmi.h.cPlanes = 1;
    bmi.h.cBitCount = pdev->color_info.depth;

    /* Write the palette. */

    if (depth <= 8) {
	int i;
	gx_color_value rgb[3];
	PRGB2 pq;

	bmi.h.cclrUsed = 1 << depth;
	bmi.h.cclrImportant = 1 << depth;
	for (i = 0; i != 1 << depth; i++) {
	    (*dev_proc(pdev, map_color_rgb)) ((gx_device *) pdev,
					      (gx_color_index) i, rgb);
	    pq = &bmi.pal[i];
	    pq->bRed = gx_color_value_to_byte(rgb[0]);
	    pq->bGreen = gx_color_value_to_byte(rgb[1]);
	    pq->bBlue = gx_color_value_to_byte(rgb[2]);
	    pq->fcOptions = 0;
	}
    } else {
	bmi.h.cclrUsed = 0;
	bmi.h.cclrImportant = 0;
    }

    /* for GpiDrawBits */
    /* target is inclusive */
    apts[0].x = 0;
    apts[0].y = 0;		/* filled in later */
    apts[1].x = pdev->width - 1;
    apts[1].y = 0;		/* filled in later */
    /* source is not inclusive of top & right borders */
    apts[2].x = 0;
    apts[2].y = 0;
    apts[3].x = pdev->width;
    apts[3].y = 0;		/* filled in later */

    /* for GpiBitBlt */
    /* target is not inclusive */
    aptsb[0].x = opdev->clipbox[0];
    aptsb[0].y = 0;		/* filled in later */
    aptsb[1].x = opdev->clipbox[2];
    aptsb[1].y = 0;		/* filled in later */
    /* source is not inclusive */
    aptsb[2].x = opdev->clipbox[0];
    aptsb[2].y = 0;
    aptsb[3].x = opdev->clipbox[2];
    aptsb[3].y = 0;		/* filled in later */

    /* write the bits */
    ystart = opdev->clipbox[3];
    yend = opdev->clipbox[1];
    y = ystart;
    while (y > yend) {
	/* create a bitmap for the memory DC */
	hbmp = GpiCreateBitmap(opdev->hpsMem, &bmi.h, 0L, NULL, NULL);
	if (hbmp == GPI_ERROR)
	    goto bmp_done;
	hbmr = GpiSetBitmap(opdev->hpsMem, hbmp);

	/* copy slice to memory bitmap */
	if (y > yend + yslice)
	    lines = yslice;
	else
	    lines = y - yend;
	y -= lines;
	for (i = lines - 1; i >= 0; i--)
	    gdev_prn_copy_scan_lines(pdev, ystart - 1 - (y + i), row + (bmp_raster * i), raster);
	apts[0].y = 0;		/* target */
	apts[1].y = lines;
	apts[3].y = lines - 1;	/* source */
	/* copy DIB bitmap to memory bitmap */
	rc = GpiDrawBits(opdev->hpsMem, row, (BITMAPINFO2 *) & bmi, 4, apts,
			 (depth != 1) ? ROP_SRCCOPY : ROP_NOTSRCCOPY, 0);

	/* copy slice to printer */
	aptsb[0].y = y;
	aptsb[1].y = y + lines;
	aptsb[3].y = lines;
	rc = GpiBitBlt(opdev->hps, opdev->hpsMem, 4, aptsb, ROP_SRCCOPY, BBO_IGNORE);

	/* delete bitmap */
	if (hbmr != HBM_ERROR)
	    GpiSetBitmap(opdev->hpsMem, (ULONG) 0);
	hbmr = HBM_ERROR;
	if (hbmp != GPI_ERROR)
	    GpiDeleteBitmap(hbmp);
	hbmp = GPI_ERROR;
    }

  bmp_done:
    if (row)
	gs_free(pdev->memory, (char *)row, bmp_raster_multi, 1, "bmp file buffer");

    return code;
}