home *** CD-ROM | disk | FTP | other *** search
/ Fresh Fish 2 / FFMCD02.bin / new / gfx / edit / tsmorph / jpeg_ls / jrdtarga.c < prev    next >
C/C++ Source or Header  |  1993-12-21  |  14KB  |  489 lines

  1. /*
  2.  * jrdtarga.c
  3.  *
  4.  * Copyright (C) 1991, 1992, Thomas G. Lane.
  5.  * This file is part of the Independent JPEG Group's software.
  6.  * For conditions of distribution and use, see the accompanying README file.
  7.  *
  8.  * This file contains routines to read input images in Targa format.
  9.  *
  10.  * These routines may need modification for non-Unix environments or
  11.  * specialized applications.  As they stand, they assume input from
  12.  * an ordinary stdio stream.  They further assume that reading begins
  13.  * at the start of the file; input_init may need work if the
  14.  * user interface has already read some data (e.g., to determine that
  15.  * the file is indeed Targa format).
  16.  *
  17.  * These routines are invoked via the methods get_input_row
  18.  * and input_init/term.
  19.  *
  20.  * Based on code contributed by Lee Daniel Crocker.
  21.  */
  22.  
  23. #include "jinclude.h"
  24.  
  25. #ifdef TARGA_SUPPORTED
  26.  
  27.  
  28. /* Macros to deal with unsigned chars as efficiently as compiler allows */
  29.  
  30. #ifdef HAVE_UNSIGNED_CHAR
  31. typedef unsigned char U_CHAR;
  32. #define UCH(x)    ((int) (x))
  33. #else /* !HAVE_UNSIGNED_CHAR */
  34. #ifdef CHAR_IS_UNSIGNED
  35. typedef char U_CHAR;
  36. #define UCH(x)    ((int) (x))
  37. #else
  38. typedef char U_CHAR;
  39. #define UCH(x)    ((int) (x) & 0xFF)
  40. #endif
  41. #endif /* HAVE_UNSIGNED_CHAR */
  42.  
  43.  
  44. #define    ReadOK(file,buffer,len)    (JFREAD(file,buffer,len) == ((size_t) (len)))
  45.  
  46.  
  47. static JSAMPARRAY colormap;    /* Targa colormap (converted to my format) */
  48.  
  49. static big_sarray_ptr whole_image; /* Needed if funny input row order */
  50. static long current_row;    /* Current logical row number to read */
  51.  
  52. /* Pointer to routine to extract next Targa pixel from input file */
  53. static void (*read_pixel) PP((decompress_info_ptr cinfo));
  54.  
  55. /* Result of read_pixel is delivered here: */
  56. static U_CHAR tga_pixel[4];
  57.  
  58. static int pixel_size;        /* Bytes per Targa pixel (1 to 4) */
  59.  
  60. /* State info for reading RLE-coded pixels; both counts must be init to 0 */
  61. static int block_count;        /* # of pixels remaining in RLE block */
  62. static int dup_pixel_count;    /* # of times to duplicate previous pixel */
  63.  
  64. /* This saves the correct pixel-row-expansion method for preload_image */
  65. static void (*get_pixel_row) PP((decompress_info_ptr cinfo,
  66.                  JSAMPARRAY pixel_row));
  67.  
  68.  
  69. /* For expanding 5-bit pixel values to 8-bit with best rounding */
  70.  
  71. static const UINT8 c5to8bits[32] = {
  72.     0,   8,  16,  24,  32,  41,  49,  57,
  73.    65,  74,  82,  90,  98, 106, 115, 123,
  74.   131, 139, 148, 156, 164, 172, 180, 189,
  75.   197, 205, 213, 222, 230, 238, 246, 255
  76. };
  77.  
  78.  
  79.  
  80. LOCAL int
  81. read_byte (decompress_info_ptr cinfo)
  82. /* Read next byte from Targa file */
  83. {
  84. #ifdef AMIGA_IO
  85.   BPTR infile = cinfo->input_file;
  86. #else
  87.   register FILE *infile = cinfo->input_file;
  88. #endif
  89.   register int c;
  90.  
  91.   if ((c = getc(infile)) == EOF)
  92.     ERREXIT(cinfo->emethods, "Premature EOF in Targa file");
  93.   return c;
  94. }
  95.  
  96.  
  97. LOCAL void
  98. read_colormap (decompress_info_ptr cinfo, int cmaplen, int mapentrysize)
  99. /* Read the colormap from a Targa file */
  100. {
  101.   int i;
  102.  
  103.   /* Presently only handles 24-bit BGR format */
  104.   if (mapentrysize != 24)
  105.     ERREXIT(cinfo->emethods, "Unsupported Targa colormap format");
  106.  
  107.   for (i = 0; i < cmaplen; i++) {
  108.     colormap[2][i] = (JSAMPLE) read_byte(cinfo);
  109.     colormap[1][i] = (JSAMPLE) read_byte(cinfo);
  110.     colormap[0][i] = (JSAMPLE) read_byte(cinfo);
  111.   }
  112. }
  113.  
  114.  
  115. /*
  116.  * read_pixel methods: get a single pixel from Targa file into tga_pixel[]
  117.  */
  118.  
  119. LOCAL void
  120. read_non_rle_pixel (decompress_info_ptr cinfo)
  121. /* Read one Targa pixel from the input file; no RLE expansion */
  122. {
  123. #ifdef AMIGA_IO
  124.   register BPTR infile = cinfo->input_file;
  125. #else
  126.   register FILE * infile = cinfo->input_file;
  127. #endif
  128.   register int i;
  129.  
  130.   for (i = 0; i < pixel_size; i++) {
  131.     tga_pixel[i] = (U_CHAR) getc(infile);
  132.   }
  133. }
  134.  
  135.  
  136. LOCAL void
  137. read_rle_pixel (decompress_info_ptr cinfo)
  138. /* Read one Targa pixel from the input file, expanding RLE data as needed */
  139. {
  140. #ifdef AMIGA_IO
  141.   register BPTR infile = cinfo->input_file;
  142. #else
  143.   register FILE * infile = cinfo->input_file;
  144. #endif
  145.   register int i;
  146.  
  147.   /* Duplicate previously read pixel? */
  148.   if (dup_pixel_count > 0) {
  149.     dup_pixel_count--;
  150.     return;
  151.   }
  152.  
  153.   /* Time to read RLE block header? */
  154.   if (--block_count < 0) {    /* decrement pixels remaining in block */
  155.     i = read_byte(cinfo);
  156.     if (i & 0x80) {        /* Start of duplicate-pixel block? */
  157.       dup_pixel_count = i & 0x7F; /* number of duplications after this one */
  158.       block_count = 0;        /* then read new block header */
  159.     } else {
  160.       block_count = i & 0x7F;    /* number of pixels after this one */
  161.     }
  162.   }
  163.  
  164.   /* Read next pixel */
  165.   for (i = 0; i < pixel_size; i++) {
  166.     tga_pixel[i] = (U_CHAR) getc(infile);
  167.   }
  168. }
  169.  
  170.  
  171. /*
  172.  * Read one row of pixels.
  173.  *
  174.  * We provide several different versions depending on input file format.
  175.  */
  176.  
  177.  
  178. METHODDEF void
  179. get_8bit_gray_row (decompress_info_ptr cinfo, JSAMPARRAY pixel_row)
  180. /* This version is for reading 8-bit grayscale pixels */
  181. {
  182.   register JSAMPROW ptr0;
  183.   register JSAMPROW ptr1;
  184.   register JSAMPROW ptr2;
  185.   register long col;
  186.   
  187.   ptr0 = pixel_row[0];
  188.   ptr1 = pixel_row[1];
  189.   ptr2 = pixel_row[2];
  190.   for (col = cinfo->image_width; col > 0; col--) {
  191.     (*read_pixel) (cinfo);    /* Load next pixel into tga_pixel */
  192.     *ptr0++ = (JSAMPLE) UCH(tga_pixel[0]);
  193.     *ptr1++ = (JSAMPLE) UCH(tga_pixel[0]);
  194.     *ptr2++ = (JSAMPLE) UCH(tga_pixel[0]);
  195.   }
  196. }
  197.  
  198. METHODDEF void
  199. get_8bit_row (decompress_info_ptr cinfo, JSAMPARRAY pixel_row)
  200. /* This version is for reading 8-bit colormap indexes */
  201. {
  202.   register int t;
  203.   register JSAMPROW ptr0, ptr1, ptr2;
  204.   register long col;
  205.   
  206.   ptr0 = pixel_row[0];
  207.   ptr1 = pixel_row[1];
  208.   ptr2 = pixel_row[2];
  209.   for (col = cinfo->image_width; col > 0; col--) {
  210.     (*read_pixel) (cinfo);    /* Load next pixel into tga_pixel */
  211.     t = UCH(tga_pixel[0]);
  212.     *ptr0++ = colormap[0][t];
  213.     *ptr1++ = colormap[1][t];
  214.     *ptr2++ = colormap[2][t];
  215.   }
  216. }
  217.  
  218. METHODDEF void
  219. get_16bit_row (decompress_info_ptr cinfo, JSAMPARRAY pixel_row)
  220. /* This version is for reading 16-bit pixels */
  221. {
  222.   register int t;
  223.   register JSAMPROW ptr0, ptr1, ptr2;
  224.   register long col;
  225.   
  226.   ptr0 = pixel_row[0];
  227.   ptr1 = pixel_row[1];
  228.   ptr2 = pixel_row[2];
  229.   for (col = cinfo->image_width; col > 0; col--) {
  230.     (*read_pixel) (cinfo);    /* Load next pixel into tga_pixel */
  231.     t = UCH(tga_pixel[0]);
  232.     t += UCH(tga_pixel[1]) << 8;
  233.     /* We expand 5 bit data to 8 bit sample width.
  234.      * The format of the 16-bit (LSB first) input word is
  235.      *     xRRRRRGGGGGBBBBB
  236.      */
  237.     *ptr2++ = (JSAMPLE) c5to8bits[t & 0x1F];
  238.     t >>= 5;
  239.     *ptr1++ = (JSAMPLE) c5to8bits[t & 0x1F];
  240.     t >>= 5;
  241.     *ptr0++ = (JSAMPLE) c5to8bits[t & 0x1F];
  242.   }
  243. }
  244.  
  245. METHODDEF void
  246. get_24bit_row (decompress_info_ptr cinfo, JSAMPARRAY pixel_row)
  247. /* This version is for reading 24-bit pixels */
  248. {
  249.   register JSAMPROW ptr0, ptr1, ptr2;
  250.   register long col;
  251.   
  252.   ptr0 = pixel_row[0];
  253.   ptr1 = pixel_row[1];
  254.   ptr2 = pixel_row[2];
  255.   for (col = cinfo->image_width; col > 0; col--) {
  256.     (*read_pixel) (cinfo);    /* Load next pixel into tga_pixel */
  257.     *ptr0++ = (JSAMPLE) UCH(tga_pixel[2]); /* convert BGR to RGB order */
  258.     *ptr1++ = (JSAMPLE) UCH(tga_pixel[1]);
  259.     *ptr2++ = (JSAMPLE) UCH(tga_pixel[0]);
  260.   }
  261. }
  262.  
  263. /*
  264.  * Targa also defines a 32-bit pixel format with order B,G,R,A.
  265.  * We presently ignore the attribute byte, so the code for reading
  266.  * these pixels is identical to the 24-bit routine above.
  267.  * This works because the actual pixel length is only known to read_pixel.
  268.  */
  269.  
  270. #define get_32bit_row  get_24bit_row
  271.  
  272.  
  273. /*
  274.  * This method is for re-reading the input data in standard top-down
  275.  * row order.  The entire image has already been read into whole_image
  276.  * with proper conversion of pixel format, but it's in a funny row order.
  277.  */
  278.  
  279. METHODDEF void
  280. get_memory_row (decompress_info_ptr cinfo, JSAMPARRAY pixel_row)
  281. {
  282.   JSAMPARRAY image_ptr;
  283.   long source_row;
  284.  
  285.   /* Compute row of source that maps to current_row of normal order */
  286.   /* For now, assume image is bottom-up and not interlaced. */
  287.   /* NEEDS WORK to support interlaced images! */
  288.   source_row = cinfo->image_height - current_row - 1;
  289.  
  290.   /* Fetch that row from virtual array */
  291.   image_ptr = (*cinfo->emethods->access_big_sarray)
  292.         (whole_image, source_row * cinfo->input_components, FALSE);
  293.  
  294.   jcopy_sample_rows(image_ptr, 0, pixel_row, 0,
  295.