This is map_scan.c in view mode; [Download] [Up]
/*
* This software is copyrighted as noted below. It may be freely copied,
* modified, and redistributed, provided that the copyright notices are
* preserved on all copies.
*
* There is no warranty or other guarantee of fitness for this software,
* it is provided solely "as is". Bug reports or fixes may be sent
* to the author, who may or may not act on them as he desires.
*
* You may not include this software in a program or other software product
* without supplying the source, or without informing the end-user that the
* source is available for no extra charge.
*
* If you modify this software, you should include a notice giving the
* name of the person performing the modification, the date of modification,
* and the reason for such modification.
*/
/*
* map_scan.c - Put RLE images on X display.
*
* Author: Spencer W. Thomas (x10)
* Computer Science Dept.
* University of Utah
* Date: Thu Feb 20 1986
* Copyright (c) 1986, University of Utah
*
* Modified: Andrew F. Vesper (x 11)
* High Performance Workstations
* Digital Equipment Corp
* Date: Fri, Aug 7, 1987
* Thu, Jan 14, 1988
* Copyright (c) 1987,1988, Digital Equipment Corporation
*
* Modified: Martin R. Friedmann (better X11, flipbook, MAG, info)
* Dept of Electrical Engineering and Computer Science
* University of Michigan
* Date: Tue, Nov 14, 1989
* Copyright (c) 1989, University of Michigan
*/
#include "getx11.h"
static void map_scanline_generic();
static void map_1_dither_table_1();
static void map_1_dither_table_8();
static void map_1_nodither_table_8();
static void map_2or3_dither_table_8();
static void map_1_nodither_notable_32();
static void map_2or3_nodither_table_8();
static void map_2or3_dither_notable_32();
static void map_2or3_nodither_notable_32();
static void map_1_mono_color_8();
static void map_1_mono_color_32();
static void MAG_scanline_generic();
static void MAG_1_dither_table_1();
static void MAG_1_dither_table_8();
static void MAG_1_nodither_table_8();
static void MAG_1_nodither_notable_32();
static void MAG_2or3_dither_table_8();
static void MAG_2or3_nodither_table_8();
static void MAG_2or3_dither_notable_32();
static void MAG_2or3_nodither_notable_32();
static void MAG_1_mono_color_8();
static void MAG_1_mono_color_32();
static unsigned char LSBMask[9] = { 0x0, 0x1, 0x3, 0x7,
0xf, 0x1f, 0x3f, 0x7f, 0xff };
#if 0 /* Not actually used. */
static unsigned char MSBMask[9] = { 0x00, 0x80, 0xc0, 0xe0,
0xf0, 0xf8, 0xfc, 0xfe, 0xff };
#endif
/*
* Figure out which scan line routine to use.
*/
void choose_scanline_converter( img )
image_information *img;
{
register int i;
register Boolean table_present;
static struct {
Boolean one_color;
Boolean dither;
Boolean table_present;
int bpp;
void (*routine)();
void (*mag_routine)();
} map_scanline_table[] =
{
/* 1 color, dithr, Table, b/p, routine ptr */
{ True, True, True, 1, map_1_dither_table_1, MAG_1_dither_table_1},
{ True, True, True, 8, map_1_dither_table_8, MAG_1_dither_table_8},
{ True, False,True, 8, map_1_nodither_table_8, MAG_1_nodither_table_8},
{ True, False,False,32,map_1_nodither_notable_32, MAG_1_nodither_notable_32},
{ False,True, True, 8, map_2or3_dither_table_8, MAG_2or3_dither_table_8},
{ False,False,True, 8, map_2or3_nodither_table_8, MAG_2or3_nodither_table_8},
{ False,True, False,32,map_2or3_dither_notable_32,MAG_2or3_dither_notable_32},
{ False,False,False,32,map_2or3_nodither_notable_32,MAG_2or3_nodither_notable_32}};
img->map_scanline = map_scanline_generic;
img->MAG_scanline = MAG_scanline_generic;
if (img->pixel_table == NULL)
table_present = False;
else table_present = True;
if (img->mono_color)
switch (img->image->bits_per_pixel) {
case 32:
img->map_scanline = map_1_mono_color_32;
img->MAG_scanline = MAG_1_mono_color_32;
break;
case 8:
img->map_scanline = map_1_mono_color_8;
img->MAG_scanline = MAG_1_mono_color_8;
break;
default:
fprintf(stderr, "%s: Warning: Bits per pixel = %d\n",
progname, img->image->bits_per_pixel);
} else
for (i = 0; i < COUNT_OF (map_scanline_table); i++) {
if (map_scanline_table[i].one_color == img->mono_img &&
map_scanline_table[i].dither == img->dither_img &&
map_scanline_table[i].table_present == table_present &&
map_scanline_table[i].bpp == img->image->bits_per_pixel) {
img->map_scanline = map_scanline_table[i].routine;
img->MAG_scanline = map_scanline_table[i].mag_routine;
if ( verbose_flag ) {
fprintf ( stderr, "Special map_scanline routine used: map_");
if ( img->mono_img )
fputs ( "1_", stderr );
else fputs ( "2or3_", stderr );
if ( !img->dither_img )
fputs ( "no", stderr );
fputs ( "dither_", stderr );
if (! table_present ) fputs ( "no", stderr );
fprintf ( stderr, "table_%d (index %d)\n",
img->image->bits_per_pixel, i );
}
break;
}
}
}
/*
* Map a scanline through the dither matrix.
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
#define DMAP(v,x,y) (divN[v] + (modN[v]>dm16[x][y] ? 1 : 0) )
#define NDMAP(v) (divN[v])
#define DMAP_SETUP( img ) \
register int *divN = img->divN;\
register int *modN = img->modN;\
register array16 *dm16 = img->dm16
#define NDMAP_SETUP( img ) register int *divN = img->divN
#define IN_CMAP_SETUP( img ) register rle_pixel **in_cmap = img->in_cmap
#define LEVELS_SETUP( img ) \
register int levels = img->lvls; \
register int levels_squared = img->lvls_squared
static void
map_scanline_generic (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int x;
register int col;
register int row;
register unsigned char *r;
register long pixel;
register int width = given_width;
row = y % 16;
col = 0;
r = rgb[0];
if (ncolors == 1) {
if ( img->dither_img ) {
for (x = 0;
--width >= 0;
r += stride, col = ((col + 1) & 15), x ++) {
pixel = pixel_table [DMAP(*r, col, row)];
if ( pixel ) pixel = 0xffffffff;
XPutPixel (image, x, y, pixel);
}
}
else {
for (x = 0; --width >= 0;
r += stride, x ++) {
pixel = pixel_table [NDMAP(*r)];
XPutPixel (image, x, y, pixel);
}
}
}
else {
register unsigned char *g;
register unsigned char *b;
g = b = rgb[1];
if (ncolors >= 3) b = rgb[2];
if ( img->dither_img ) {
for (x = 0; --width >= 0;
r += stride, g += stride, b += stride,
col = ((col + 1) & 15), x ++ )
{
if (pixel_table != NULL)
pixel = pixel_table
[DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
else pixel = SHIFT_MASK_PIXEL (DMAP(*r, col, row),
DMAP(*g, col, row),
DMAP(*b, col, row));
XPutPixel (image, x, y, pixel);
}
}
else {
for (x = 0; --width >= 0;
r += stride, g += stride, b += stride, x++ ) {
if ( pixel_table != NULL) {
pixel = pixel_table
[NDMAP(*r) +
NDMAP(*g) * levels +
NDMAP(*b) * levels_squared];
}
else {
pixel = SHIFT_MASK_PIXEL (NDMAP(*r), NDMAP(*g), NDMAP(*b));
}
XPutPixel (image, x, y, pixel);
}
}
}
}
static void
MAG_scanline_generic( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int col;
register unsigned char *r;
int save_x = x;
register int mag_x;
int mag_y = mag_size;
register int w;
register int row = (mag_size * rle_y - 1) % 16;
int x_mod_16 = (mag_size * rle_x) % 16;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
register unsigned long pixel;
while (--height >= 0) {
x = save_x;
w = width;
row = (row + 1) % 16;
col = x_mod_16;
r = rgb_line;
mag_x = mag_size;
if ( img->dpy_channels == 1 ) {
if ( img->dither_img )
while (--w >= 0)
{
pixel = pixel_table [DMAP(*r, col++, row)];
XPutPixel (image, x, y, pixel);
if ( --mag_x == 0 )
{
r++;
mag_x = mag_size;
}
col &=15; x++;
}
else
while (--w >= 0)
{
pixel = pixel_table [NDMAP(*r)];
XPutPixel (image, x, y, pixel);
if ( --mag_x == 0 )
{
r++;
mag_x = mag_size;
}
x++;
}
}
else {
register unsigned char *g;
register unsigned char *b;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
if ( img->dither_img )
while (--w >= 0)
{
if ( pixel_table != NULL)
pixel = pixel_table
[DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
else pixel =
SHIFT_MASK_PIXEL (DMAP(*r, col, row),
DMAP(*g, col, row),
DMAP(*b, col, row));
XPutPixel (image, x++, y, pixel);
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
}
col++;
col &= 15;
}
else
while (--w >= 0)
{
if ( pixel_table != NULL)
pixel = pixel_table
[NDMAP(*r) +
NDMAP(*g) * levels +
NDMAP(*b) * levels_squared];
else pixel = SHIFT_MASK_PIXEL (NDMAP(*r),
NDMAP(*g),
NDMAP(*b));
XPutPixel (image, x++, y, pixel);
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
}
}
}
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
y++;
}
}
/*
* map_1_dither_table_8
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_1_dither_table_8(img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
register int col;
register int row;
register unsigned char *r;
register unsigned char *pixel_ptr;
register int width = given_width;
row = y % 16;
col = 0;
r = rgb[0];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
while (--width >= 0) {
*pixel_ptr++ = pixel_table [ DMAP(*r, col, row) ];
r += stride;
col = ((col + 1) & 15);
}
}
static
void
MAG_1_dither_table_8( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
register int col;
register unsigned char *r;
register unsigned char *pixel_ptr;
register int mag_x;
int mag_y = mag_size;
register int w;
register int row = (mag_size * rle_y - 1) % 16;
int x_mod_16 = (mag_size * rle_x) % 16;
unsigned char *line_ptr;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
line_ptr = ((unsigned char *) image->data)+(y * image->bytes_per_line) + x;
while (--height >= 0) {
pixel_ptr = line_ptr;
w = width;
row = (row + 1) % 16;
col = x_mod_16;
r = rgb_line;
mag_x = mag_size;
while (--w >= 0) {
*pixel_ptr++ = pixel_table [DMAP(*r, col++, row) ];
col &= 15;
if ( --mag_x == 0 )
{
r++;
mag_x = mag_size;
}
}
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_2or3_dither_table_8
*
* Dither three colors into an eight bit table... This is faster than the
* map_scanline_generic routine.
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_2or3_dither_table_8 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int col;
register int row;
register unsigned char *r, *g, *b;
register unsigned char *pixel_ptr;
register int width = given_width;
row = y % 16;
col = 0;
r = rgb[0];
g = b = rgb[1];
if (ncolors >= 3) b = rgb[2];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
while (--width >= 0) {
*pixel_ptr++ = pixel_table [DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
r += stride;
g += stride;
b += stride;
col = ((col + 1) & 15);
}
}
static
void
MAG_2or3_dither_table_8 ( img, rle_x, rle_y, mag_size, x, y, width, height, image)
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int col;
register unsigned char *r, *g, *b;
register unsigned char *pixel_ptr;
register int mag_x;
int mag_y = mag_size;
register int w;
register int row = (mag_size * rle_y - 1) % 16;
int x_mod_16 = (mag_size * rle_x) % 16;
unsigned char *line_ptr;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
line_ptr = ((unsigned char *) image->data)+(y * image->bytes_per_line) + x;
while (--height >= 0) {
pixel_ptr = line_ptr;
w = width;
row = (row + 1) % 16;
col = x_mod_16;
mag_x = mag_size;
r = rgb_line;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
while (--w >= 0) {
*pixel_ptr++ = pixel_table [DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
col++;
col &= 15;
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
}
}
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_1_dither_table_1
*
* Dither three colors into an eight bit table... This is faster than the
* map_scanline_generic routine.
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_1_dither_table_1 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
register int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
register int col;
register int row;
register unsigned char *r;
register unsigned char *pixel_ptr;
register int width = given_width;
int bit;
row = y % 16;
col = bit = 0;
r = rgb[0];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
if( BitmapBitOrder(dpy) == MSBFirst ) {
/* we don't want to trash those good bits */
*pixel_ptr >>= (8 - bit) & 7;
/* do first byte fragment */
while ( col & 7 )
{
*pixel_ptr <<= 1;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x1;
width--;
r += stride;
}
if ( bit )
pixel_ptr++, col &= 15;
while ((width -= 8) >= 0) {
*pixel_ptr = 0;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr = (unsigned char) 0x80;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x40;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x20;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x10;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x8;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x4;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x2;
r += stride;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x1;
r += stride;
col &= 15;
pixel_ptr++;
}
/* if w is non-zero then we have to finish up... */
width = 8 + width;
if ( width )
{
unsigned char savebits;
savebits = *pixel_ptr & LSBMask[8-width];
bit = width;
while (--width >= 0) {
*pixel_ptr <<= 1;
if ( pixel_table [DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x1;
r += stride;
}
*pixel_ptr <<= 8 - bit;
*pixel_ptr |= savebits;
}
}
else
while (--width >= 0) {
*pixel_ptr = (unsigned char)(*pixel_ptr >> 1) | (unsigned char)
((pixel_table[DMAP(*r, col, row)]!= 0) ? 0x80: 0);
r += stride;
col = ((col + 1) & 15);
bit = ((bit + 1) & 7);
if (!bit) pixel_ptr++;
}
}
#define INC_RGB( stmt ) if ( --mag_x == 0 ) {stmt; mag_x = mag_size; }
static
void
MAG_1_dither_table_1 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
register int col, bit;
register unsigned char *r;
register unsigned char *pixel_ptr;
register int mag_x;
register int w;
register int row = (mag_size * rle_y - 1) % 16;
unsigned char *line_ptr;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
int x_mod_16 = (mag_size * rle_x) % 16;
int x_mod_8 = x % 8;
int mag_y = mag_size;
int byte_order = BitmapBitOrder(dpy);
line_ptr = ((unsigned char *) image->data) +
(y * image->bytes_per_line) + x / 8;
while (--height >= 0) {
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
row = (row + 1) % 16;
col = x_mod_16;
bit = x_mod_8;
if( byte_order == MSBFirst ) {
/* we don't want to trash those good bits */
*pixel_ptr >>= (8 - bit) & 7;
/* do first byte fragment */
while ( bit & 7 )
{
*pixel_ptr <<= 1;
*pixel_ptr |= pixel_table[DMAP(*r, col++, row)]!=0;
w--;
INC_RGB( r++ );
bit++;
col &= 15;
}
if ( x_mod_8 )
pixel_ptr++;
/* do the bulk of the line fast in eight bit chunks Gee I hope all
* this fits into your instruction cache... Or else we are
* forked.. You can get rid of 7 (col &= 15)'s if you make dm16
* a 32x16 array with duplicates in the second half of the columns.
* Then we don't have to worry about col overflowing in 8 ++'s
*/
while ((w -= 8) >= 0) {
*pixel_ptr = (unsigned char) 0;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr = (unsigned char) 0x80;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x40;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x20;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x10;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x8;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x4;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x2;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x1;
INC_RGB( r++ ); col &= 15;
pixel_ptr++;
}
/* if w is non-zero then we have to finish up... */
w = 8 + w;
if ( w )
{
unsigned char savebits;
savebits = *pixel_ptr & LSBMask[8-w];
bit = w;
while (--w >= 0) {
*pixel_ptr <<= 1;
*pixel_ptr |= (unsigned char) pixel_table
[DMAP(*r, col++, row)] ? 0x1 : 0;
INC_RGB( r++ ); col &= 15;
}
*pixel_ptr <<= 8 - bit;
*pixel_ptr |= savebits;
}
}
else {
/* we don't want to trash those good bits */
*pixel_ptr <<= (8 - bit) & 7;
/* do first byte fragment */
while ( col & 7 ) {
*pixel_ptr >>= 1;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x80;
w--;
INC_RGB( r++ ); col &= 15;
}
if ( x_mod_8 )
pixel_ptr++;
/* do the bulk of the line fast in eight bit chunks.. */
while ((w -= 8) >= 0) {
*pixel_ptr = (unsigned char) 0x0;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr = (unsigned char) 0x1;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x2;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x4;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x8;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x10;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x20;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x40;
INC_RGB( r++ ); col &= 15;
if ( pixel_table[DMAP(*r, col++, row)] )
*pixel_ptr |= (unsigned char) 0x80;
INC_RGB( r++ ); col &= 15;
pixel_ptr++;
}
/* if w is negative then we have to finish up... */
w = 0 - w;
if ( w )
{
unsigned char savebits = (unsigned char )(*pixel_ptr >> 8 - w);
savebits <<= (unsigned char)8 - w;
bit = w;
while (--w >= 0) {
*pixel_ptr >>= 1;
if (pixel_table[DMAP(*r, col++, row)])
*pixel_ptr |= (unsigned char) 0x80;
INC_RGB( r++ ); col &= 15;
}
*pixel_ptr >>= 8 - bit;
*pixel_ptr |= savebits;
}
}
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_2or3_nodither_table_8
*
* Dither three colors into an eight bit table... This is faster than the
* map_scanline_generic routine.
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_2or3_nodither_table_8 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
NDMAP_SETUP( img );
LEVELS_SETUP( img );
register unsigned char *r, *g, *b;
register unsigned char *pixel_ptr;
register int width = given_width;
r = rgb[0];
g = b = rgb[1];
if (ncolors >= 3) b = rgb[2];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
while (--width >= 0) {
*pixel_ptr++ = pixel_table [ NDMAP(*r)
+ NDMAP(*g) * levels
+ NDMAP(*b) * levels_squared];
r += stride;
g += stride;
b += stride;
}
}
static
void
MAG_2or3_nodither_table_8( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
NDMAP_SETUP( img );
LEVELS_SETUP( img );
register unsigned char *r, *g, *b;
register unsigned char *pixel_ptr;
register unsigned char table_value;
register int mag_x;
int mag_y = mag_size;
register int w;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr =
((unsigned char *) image->data)+(y * image->bytes_per_line) + x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width );
else
{
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
table_value = pixel_table [ NDMAP(*r)
+ NDMAP(*g) * levels
+ NDMAP(*b) * levels_squared];
while ( --w >= 0 ) {
*pixel_ptr++ = table_value;
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
table_value =
pixel_table [ NDMAP(*r)
+ NDMAP(*g) * levels
+ NDMAP(*b) * levels_squared];
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_1_nodither_table_8
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static void
map_1_nodither_table_8 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
NDMAP_SETUP( img );
register unsigned char * r;
register unsigned char * pixel_ptr;
register int width = given_width;
r = rgb[0];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
while (--width >= 0) {
*pixel_ptr++ = pixel_table [ NDMAP(*r) ];
r += stride;
}
}
static void
MAG_1_nodither_table_8(img, rle_x, rle_y, mag_size, x, y, width, height, image)
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
NDMAP_SETUP( img );
register unsigned char * r;
register unsigned char * pixel_ptr;
register unsigned char table_value;
register int mag_x;
int mag_y = mag_size;
register int w;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr =
((unsigned char *) image->data)+(y * image->bytes_per_line) + x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width );
else
{
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
table_value = pixel_table [ NDMAP(*r) ];
while (--w >= 0) {
*pixel_ptr++ = table_value;
if ( --mag_x == 0 ){
r++;
mag_x = mag_size;
table_value = pixel_table [ NDMAP(*r) ];
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_1_mono_color_8
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static void
map_1_mono_color_8 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
register unsigned char * r;
register unsigned char * pixel_ptr;
register int width = given_width;
r = rgb[0];
pixel_ptr = ((unsigned char *) image->data) + y * image->bytes_per_line;
while (--width >= 0) {
*pixel_ptr++ = pixel_table [ *r ];
r += stride;
}
}
static void
MAG_1_mono_color_8 (img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
register unsigned char * r;
register unsigned char * pixel_ptr;
register unsigned char table_value;
register int mag_x;
int mag_y = mag_size;
register int w;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr =
((unsigned char *) image->data)+(y * image->bytes_per_line) + x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width );
else {
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
table_value = pixel_table [ *r ];
while (--w >= 0) {
*pixel_ptr++ = table_value;
if ( --mag_x == 0 ){
r++;
mag_x = mag_size;
table_value = pixel_table [ *r ];
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_2or3_dither_table_32
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
#if 0 /* Never called. */
static
void
map_2or3_dither_table_32 ( img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int col;
register int row;
register unsigned char * r;
register unsigned char *g;
register unsigned char *b;
register unsigned long pixval;
register unsigned char * pixel_ptr;
register int width = given_width;
int byte_order = ImageByteOrder( dpy );
row = y % 16;
col = 0;
r = rgb[0];
g = b = rgb[1];
if (ncolors >= 3) b = rgb[2];
pixel_ptr = (unsigned char *)image->data + y * image->bytes_per_line;
while (--width >= 0) {
pixval = pixel_table [DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
r += stride;
g += stride;
b += stride;
col = ((col + 1) & 15);
}
}
#endif
#if 0 /* Never called. */
static
void
MAG_2or3_dither_table_32 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register Pixel *pixel_table = img->pixel_table;
DMAP_SETUP( img );
LEVELS_SETUP( img );
register int col;
register unsigned long pixval;
register unsigned char * pixel_ptr;
register unsigned char *r;
register unsigned char *g;
register unsigned char *b;
register int w;
register int row = (mag_size * rle_y - 1) % 16;
register int mag_x;
int mag_y = mag_size;
int x_mod_16 = (mag_size * rle_x) % 16;
unsigned char *line_ptr;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
int byte_order = ImageByteOrder( dpy );
line_ptr = (unsigned char *)
((image->data) + (y * image->bytes_per_line)) + 4 * x;
while (--height >= 0) {
pixel_ptr = line_ptr;
w = width;
row = (row + 1) % 16;
col = x_mod_16;
r = rgb_line;
mag_x = mag_size;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
while (--w >= 0) {
pixval = pixel_table [DMAP(*r, col, row) +
DMAP(*g, col, row) * levels +
DMAP(*b, col, row) * levels_squared];
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
}
col++;
col &= 15;
}
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
#endif
/*
* map_2or3_dither_notable_32
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static void
map_2or3_dither_notable_32 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
DMAP_SETUP( img );
register int col;
register int row;
register unsigned char *r;
register unsigned char *g;
register unsigned char *b;
register unsigned long pixval;
register unsigned char *pixel_ptr;
register int width = given_width;
int byte_order = ImageByteOrder( dpy );
row = y % 16;
col = 0;
r = rgb[0];
g = rgb[1];
if (ncolors >= 3) b = rgb[2];
else b = rgb[1];
pixel_ptr = (unsigned char *) ( image->data + y * image->bytes_per_line );
while (--width >= 0) {
pixval = SHIFT_MASK_PIXEL_32 (DMAP(*r, col, row),
DMAP(*g, col, row),
DMAP(*b, col, row));
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
r += stride;
g += stride;
b += stride;
col = ((col + 1) & 15);
}
}
static void
MAG_2or3_dither_notable_32 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
DMAP_SETUP( img );
register unsigned char *r, *g, *b;
register unsigned long pixval;
register unsigned char *pixel_ptr;
register int row = (mag_size * rle_y - 1) % 16;
register int col;
register int mag_x;
int mag_y = mag_size;
register int w;
int x_mod_16 = (mag_size * rle_x) % 16;
unsigned char *line_ptr;
unsigned char *rgb_line = SAVED_RLE_ROW( img, rle_y ) + rle_x;
int rgb_line_stride = img->w * img->dpy_channels;
int byte_order = ImageByteOrder( dpy );
line_ptr = (unsigned char *)
(image->data + (y * image->bytes_per_line)) + 4 * x;
while (--height >= 0) {
pixel_ptr = line_ptr;
w = width;
row = (row + 1) % 16;
col = x_mod_16;
r = rgb_line;
mag_x = mag_size;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
while (--w >= 0) {
pixval = SHIFT_MASK_PIXEL_32(DMAP(*r, col, row),
DMAP(*g, col, row),
DMAP(*b, col, row));
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
}
col++;
col &= 15;
}
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_2or3_nodither_notable_32
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_2or3_nodither_notable_32 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
int stride;
int y;
XImage *image;
{
NDMAP_SETUP( img );
register unsigned char *r;
register unsigned char *g;
register unsigned char *b;
register unsigned long pixval;
register unsigned char *pixel_ptr;
register int width = given_width;
int byte_order = ImageByteOrder( dpy );
r = rgb[0];
g = rgb[1];
if (ncolors >= 3) b = rgb[2];
else b = rgb[1];
pixel_ptr = (unsigned char *) ( image->data + y * image->bytes_per_line );
while (--width >= 0) {
pixval = SHIFT_MASK_PIXEL_32(NDMAP(*r), NDMAP(*g), NDMAP(*b));
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
r += stride;
g += stride;
b += stride;
}
}
static
void
MAG_2or3_nodither_notable_32 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
NDMAP_SETUP( img );
register unsigned char *r, *g, *b;
register unsigned long pixval;
register unsigned char *pixel_ptr;
unsigned long pixel_value;
register int mag_x;
int mag_y = mag_size;
register int w;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
int byte_order = ImageByteOrder( dpy );
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr = (unsigned char *)
(image->data + (y * image->bytes_per_line)) + 4 * x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width * sizeof(long) );
else
{
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
g = b = r + img->w;
if (img->dpy_channels >= 3) b += img->w;
pixel_value = SHIFT_MASK_PIXEL_32(NDMAP(*r), NDMAP(*g), NDMAP(*b));
while (--w >= 0) {
pixval = pixel_value;
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
if ( --mag_x == 0 )
{
r++, g++, b++;
mag_x = mag_size;
pixel_value = SHIFT_MASK_PIXEL_32(NDMAP(*r),
NDMAP(*g), NDMAP(*b));
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_1_nodither_notable_32
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_1_nodither_notable_32 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
register int stride;
int y;
XImage *image;
{
NDMAP_SETUP( img );
register unsigned char *r;
register unsigned long pixval;
register unsigned char *pixel_ptr;
register int width = given_width;
int byte_order = ImageByteOrder( dpy );
r = rgb[0];
pixel_ptr = (unsigned char *) ( image->data + y * image->bytes_per_line );
while (--width >= 0) {
register int bw_value = NDMAP(*r);
pixval = SHIFT_MASK_PIXEL_32( bw_value, bw_value, bw_value );
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
r += stride;
}
}
static
void
MAG_1_nodither_notable_32 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
NDMAP_SETUP( img );
register unsigned char *r;
register unsigned long pixval;
register unsigned char *pixel_ptr;
unsigned long pixel_value;
register int bw_value;
register int mag_x;
register int w;
register int mag_y = mag_size;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
int byte_order = ImageByteOrder( dpy );
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr = (unsigned char *)
(image->data + (y * image->bytes_per_line)) + 4 * x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width * sizeof( long ) );
else
{
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
bw_value = NDMAP(*r);
pixel_value = SHIFT_MASK_PIXEL_32(bw_value, bw_value, bw_value );
while (--w >= 0) {
pixval = pixel_value;
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
if ( --mag_x == 0 )
{
r++;
mag_x = mag_size;
bw_value = NDMAP(*r);
pixel_value =
SHIFT_MASK_PIXEL_32(bw_value, bw_value, bw_value );
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*
* map_1_mono_color_32
*
* Inputs:
* rgb: Pointers to buffers containing the red, green,
* and blue color rows.
* n: Length of row.
* s: Skip between pixels in original image.
* y: Y position of row (necessary for dither)
* line: Pointer to output buffer for dithered color data.
*/
static
void
map_1_mono_color_32 (img, rgb, ncolors, given_width, stride, y, image)
image_information *img;
unsigned char *rgb[3];
int ncolors;
int given_width;
register int stride;
int y;
XImage *image;
{
register unsigned char *r;
register unsigned long pixval;
register unsigned char *pixel_ptr;
register int width = given_width;
int byte_order = ImageByteOrder( dpy );
r = rgb[0];
pixel_ptr = (unsigned char *) ( image->data + y * image->bytes_per_line );
while (--width >= 0) {
pixval = img->pixel_table[ *r ];
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
r += stride;
}
}
static
void
MAG_1_mono_color_32 ( img, rle_x, rle_y, mag_size, x, y, width, height, image )
image_information *img;
int rle_x, rle_y;
int width, height;
int mag_size;
int x, y;
XImage *image;
{
register unsigned char *r;
register unsigned char *pixel_ptr;
register unsigned long pixval;
unsigned long pixel_value;
register int mag_x;
register int w;
register int mag_y = mag_size;
unsigned char *line_ptr, *last_line;
unsigned char *rgb_line, *last_rgb;
int rgb_line_stride = img->w * img->dpy_channels;
int byte_order = ImageByteOrder( dpy );
rgb_line = last_rgb = SAVED_RLE_ROW( img, rle_y ) + rle_x;
last_line = line_ptr = (unsigned char *)
(image->data + (y * image->bytes_per_line)) + 4 * x;
while (--height >= 0) {
if ( rgb_line == last_rgb && last_line != line_ptr )
memcpy( line_ptr, last_line, width * sizeof( long ) );
else
{
pixel_ptr = line_ptr;
w = width;
r = rgb_line;
mag_x = mag_size;
pixel_value = img->pixel_table[ *r ];
while (--w >= 0) {
pixval = pixel_value;
if ( byte_order == MSBFirst )
{
pixel_ptr += 3;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr-- = pixval & 0xff;
pixval >>= 8;
*pixel_ptr = pixval & 0xff;
pixel_ptr += 4;
}
else
{
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
pixval >>= 8;
*pixel_ptr++ = pixval & 0xff;
}
if ( --mag_x == 0 )
{
r++;
mag_x = mag_size;
pixel_value = img->pixel_table[ *r ];
}
}
}
last_line = line_ptr;
last_rgb = rgb_line;
line_ptr += image->bytes_per_line;
if ( --mag_y == 0 )
{
rgb_line += rgb_line_stride;
mag_y = mag_size;
}
}
}
/*****************************************************************
* TAG( map_rgb_to_bw )
*
* Convert RGB to black and white through NTSC transform, but map
* RGB through a color map first.
* Inputs:
* red_row, green_row, blue_row: Given RGB pixel data.
* map: Array[3] of pointers to pixel arrays,
* representing color map.
* rowlen: Number of pixels in the rows.
* Outputs:
* bw_row: Output B&W data. May coincide with one of the
* inputs.
* Algorithm:
* BW = .35*map[0][R] + .55*map[1][G] + .10*map[2][B]
*/
void
map_rgb_to_bw( img, rows, bw_row )
image_information *img;
rle_pixel **rows;
register rle_pixel *bw_row;
{
register rle_pixel *red;
register rle_pixel *green;
register rle_pixel *blue;
rle_pixel **map;
int ncolors;
int rowlen;
map = img->in_cmap;
ncolors = img->img_channels;
rowlen = img->w;
if (ncolors < 1) {
fprintf (stderr, "%s: map_rgb_to_bw given %d colors\n",
progname, ncolors);
exit (1);
}
switch (ncolors) {
case 1:
red = rows[0];
if ( !map || img->mono_color )
duff8( rowlen, *bw_row++ = *red++)
else {
register rle_pixel *cmap = map[0];
duff8( rowlen, *bw_row++ = cmap[*red++])
}
break;
case 2:
red = rows[0];
green = rows[1];
if ( !map )
duff8( rowlen, *bw_row++ = ( 50 * *red++ + 50 * *green++ ) / 100)
else {
register rle_pixel **cmap = map;
duff8( rowlen, *bw_row++ = (50 * cmap[0][*red++] +
50 * cmap[1][*green++]) /100)
}
break;
default:
case 3:
red = rows[0];
green = rows[1];
blue = rows[2];
if ( !map )
duff8( rowlen, *bw_row++ = ( 35 * *red++ + 55 * *green++ +
10 * *blue++ ) / 100)
else {
register rle_pixel **cmap = map;
duff8( rowlen, *bw_row++ = ( 35 * cmap[0][*red++] +
55 * cmap[1][*green++] +
10 * cmap[2][*blue++] ) / 100)
}
break;
}
}
/*****************************************************************
* TAG( map_rgb_to_rgb )
*
* Convert RGB to RGB through a colormap
* Inputs:
* in_rows: Given RGB pixel data.
* map: Array[3] of pointers to pixel arrays,
* representing color map.
* rowlen: Number of pixels in the rows.
* Outputs:
* out_rows: Output data. May coincide with one of the inputs.
*/
void
map_rgb_to_rgb( img, in_rows, out_rows )
image_information *img;
rle_pixel **in_rows, **out_rows;
{
register rle_pixel *in, *out, *cmap;
register int w;
rle_pixel **map;
int ncolors;
int rowlen;
map = img->in_cmap;
ncolors = img->img_channels;
rowlen = img->w;
if ( ncolors < 1 )
{
fprintf (stderr, "%s: map_rgb_to_rgb given %d colors\n",
progname, ncolors);
exit (1);
}
if ( map )
while ( --ncolors >= 0 )
{
in = in_rows[0];
out = out_rows[0];
cmap = map[0];
w = rowlen;
duff8( w, *out++ = cmap[*in++] );
in_rows++;
out_rows++;
map++;
}
else
while ( --ncolors >= 0 )
{
if ( in_rows[0] != out_rows[0] )
memcpy( out_rows[0], in_rows[0], rowlen );
in_rows++;
out_rows++;
}
}
void get_dither_arrays( img )
register image_information *img;
{
if (!img->divN)
img->divN = (int *) malloc ( 256 * sizeof(int) );
if (!img->modN)
img->modN = (int *) malloc ( 256 * sizeof(int) );
if (!img->dm16)
img->dm16 = (array16 *) malloc ( 16 * 16 * sizeof(int) );
if (!img->divN || !img->modN || !img->dm16 )
{
fprintf( stderr, "%s: malloc error getting dither arrays\n");
exit (1);
}
}
int
shift_match_left (mask, high_bit_index)
Pixel mask;
int high_bit_index;
{
register int shift;
register Pixel high_bit;
if (mask == 0) return (0);
high_bit = 0x80000000;
for (shift = (32 - high_bit_index); (high_bit & mask) == 0; shift--) {
high_bit >>= 1;
}
return (shift);
}
int
shift_match_right (mask)
Pixel mask;
{
register int shift;
register Pixel low_bit;
if (mask == 0) return (0);
low_bit = 1;
for (shift = 0; (low_bit & mask) == 0; shift++) {
low_bit <<= 1;
}
return (shift);
}
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.