home *** CD-ROM | disk | FTP | other *** search
/ Compressed Image File Formats / CompressedImageFileFormatsJohnMiano.iso / pc / Examples / c14 / src / pngdecod.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  1999-04-07  |  64.0 KB  |  2,198 lines

  1. //
  2. // Copyright (c) 1997,1998 Colosseum Builders, Inc.
  3. // All rights reserved.
  4. //
  5. // Colosseum Builders, Inc. makes no warranty, expressed or implied
  6. // with regards to this software. It is provided as is.
  7. //
  8. // See the README.TXT file that came with this software for restrictions
  9. // on the use and redistribution of this file or send E-mail to
  10. // info@colosseumbuilders.com
  11. //
  12.  
  13. //
  14. //  Title:  PNG Decoder class implementation
  15. //
  16. //  Author:  John M. Miano  miano@colosseumbuilders.com
  17. //
  18. //  Description:
  19. //
  20. //    This class is a decoder for PNG images
  21. //
  22. #include <iomanip>
  23. #include <limits.h>
  24.  
  25. #include "pngchksm.h"
  26. #include "pngdecod.h"
  27. #include "pngpvt.h"
  28. #include "pnghuffd.h"
  29.  
  30. #define VERYVERBOSE
  31.  
  32. using namespace std ;
  33.  
  34. const unsigned int Max8BitSampleValue = 255 ;
  35.  
  36. // Number of passes in an interlaced image.
  37. const unsigned int InterlacePasses = 7 ;
  38.  
  39. // Deflate Compression Types
  40. enum CompressionType
  41. {
  42.   Uncompressed = 0,
  43.   FixedHuffmanCodes = 1,
  44.   DynamicHuffmanCodes = 2,
  45. } ;
  46.  
  47. // These values define the Adam7 interlace pattern for each pass.
  48. const PngDecoder::InterlaceInfo PngDecoder::interlace_values [InterlacePasses] =
  49.   {
  50.     { 8, 8, 0, 0, },
  51.     { 8, 8, 0, 4, },
  52.     { 8, 4, 4, 0, },
  53.     { 4, 4, 0, 2, },
  54.     { 4, 2, 2, 0, },
  55.     { 2, 2, 0, 1, },
  56.     { 2, 1, 1, 0, },
  57.   } ;
  58.  
  59. //
  60. // Class Constructor
  61. //
  62. // Nothing gets done here except initializing variables to a known state.
  63. //
  64. PngDecoder::PngDecoder ()
  65. {
  66.   Initialize () ;
  67.   return ;
  68. }
  69. //
  70. //  Copy Constructor
  71. //
  72. PngDecoder::PngDecoder (const PngDecoder &source)
  73. {
  74.   Initialize () ;
  75.   DoCopy (source) ;
  76.   return ;
  77. }
  78.  
  79. //
  80. // Class Destructor
  81. //
  82. PngDecoder::~PngDecoder ()
  83. {
  84.   FreeData () ;
  85.   delete distance_table ;
  86.   delete literal_table ;
  87.   return ;
  88. }
  89.  
  90. //
  91. //  Description:
  92. //
  93. //    Assignment Operator
  94. //
  95. PngDecoder &PngDecoder::operator=(PngDecoder &source)
  96. {
  97.   DoCopy (source) ;
  98.   return *this ;
  99. }
  100.  
  101. //
  102. //  Description:
  103. //
  104. //    Object initialization Function for use by constructors.
  105. //
  106. void PngDecoder::Initialize ()
  107. {
  108.   input_stream = NULL ;
  109.   current_image = NULL ;
  110.   row_buffers [0] = NULL ;
  111.   row_buffers [1] = NULL ;
  112.   MakeCrcTable () ;
  113.  
  114.   background_red = 0 ;
  115.   background_green = 0 ;
  116.   background_blue = 0 ;
  117.   background_gray = 0 ;
  118.  
  119.   chunk_data = NULL ;
  120.   chunk_data_size = 0 ;
  121.   lz_window = NULL ;
  122.   verbose_flag = false ;
  123.  
  124.   literal_table = new PngHuffmanDecoder ;
  125.   distance_table = new PngHuffmanDecoder ;
  126.   return ;
  127. }
  128.  
  129. //
  130. //  Description:
  131. //
  132. //    Class copy function. Used by copy constructor and assignment operator
  133. //    to copy data from an object to this one.
  134. //
  135. //  Parameters:
  136. //    source:  The object to copy from.
  137. //
  138. void PngDecoder::DoCopy (const PngDecoder &source)
  139. {
  140.   verbose_flag = source.verbose_flag ;
  141.   background_red = source.background_red ;
  142.   background_green = source.background_green ;
  143.   background_blue = source.background_blue;
  144.   background_gray = source.background_blue;
  145.   BitmapImageDecoder::DoCopy (source) ;
  146.   return ;
  147. }
  148. //
  149. // Description:
  150. //
  151. //   This function frees all of the dynamically allocated data.
  152. //
  153. void PngDecoder::FreeData ()
  154. {
  155.   delete [] chunk_data ; chunk_data = NULL ;
  156.   delete [] lz_window ; lz_window = NULL ;
  157.   delete [] row_buffers [0] ; row_buffers [0] = NULL ;
  158.   delete [] row_buffers [1] ; row_buffers [1] = NULL ;
  159.   return ;
  160. }
  161.  
  162. //
  163. //  Description:
  164. //
  165. //    This function reads a PNG image.
  166. //
  167. //  Parameters:
  168. //    strm:  The input stream
  169. //    image:  The output image
  170. //
  171. void PngDecoder::ReadImage (std::istream &strm, BitmapImage &image)
  172. {
  173.   try
  174.   {
  175.     input_stream = &strm ;
  176.     current_image = &image ;
  177.  
  178.     reading_pixel_data = false ;
  179.     data_read = false ;
  180.     header_read = false ;
  181.     end_read = false ;
  182.     palette_read = false ;
  183.  
  184.     palette_size = 0 ;
  185.  
  186.     lz_window = new UBYTE1 [PngWindowSize] ;
  187.     memset (lz_window, 0, PngWindowSize) ;
  188.     ReadSignature () ;
  189.  
  190.     ReadChunk () ;
  191.     if (chunk_type != ChunkType ("IHDR"))
  192.       throw EPngError ("Missing IHDR block") ;
  193.  
  194.     while (! input_stream->eof () && ! end_read)
  195.     {
  196.       ReadChunk () ;
  197.     }
  198.  
  199.     FreeData () ;
  200.   }
  201.   catch (...)
  202.   {
  203.     FreeData () ;
  204.     throw ;
  205.   }
  206.  
  207.   if (! data_read)
  208.     throw EPngError ("Image Contains no Pixel Data") ;
  209.   return ;
  210. }
  211.  
  212.  
  213. //
  214. // Description:
  215. //
  216. //  This function reads the PNG signature from the input stream. It
  217. //  throws an exception if the stream does not have a valid signature.
  218. //
  219. void PngDecoder::ReadSignature ()
  220. {
  221.   UBYTE1 sigbuf [PngSignatureSize] ;
  222.  
  223.   input_stream->read ((char *) sigbuf, PngSignatureSize) ;
  224.   if (memcmp (sigbuf, PngSignature, PngSignatureSize) != 0)
  225.     throw EPngError ("Not a PNG file") ;
  226.   return ;
  227. }
  228.  
  229. //
  230. //  Description:
  231. //
  232. //    This function reads a complete chunk from the input stream. A chunk
  233. //    consists of:
  234. //
  235. //      Chunk Length:  4 Bytes
  236. //      Chunk Type:    4 Bytes
  237. //      Chunk Data:    "Chunk Length" Bytes
  238. //      Chunk CRC:     4 Bytes
  239. //
  240. //    The chunk CRC value is calculated from the type and data fields.
  241. //
  242. //
  243. void PngDecoder::ReadChunk ()
  244. {
  245.   // Read the chunk length.
  246.   input_stream->read ((char *) &chunk_length, sizeof (chunk_length)) ;
  247.   if (input_stream->eof ())
  248.     return ;
  249.   chunk_length = BigEndianToSystem (chunk_length) ;
  250.   // Enforce the maximum chunk lenth specified in 3.2
  251.   if (chunk_length > (UBYTE4) (1L << 31L) - 1L)
  252.     throw EPngError ("Block length too large") ;
  253.  
  254.   // Read the chunk type.
  255.   input_stream->read ((char *) &chunk_type, sizeof (chunk_type)) ;
  256.  
  257.   // Ensure that the data buffer is large enough to hold the chunk data
  258.   // then read in the data.
  259.   if (chunk_length > chunk_data_size)
  260.   {
  261.     delete [] chunk_data ;
  262.     chunk_data = new UBYTE1 [chunk_length] ;
  263.   }
  264.   input_stream->read ((char *) chunk_data, chunk_length) ;
  265.  
  266.   // Read the CRC value.
  267.   input_stream->read ((char *) &chunk_crc, sizeof (chunk_crc)) ;
  268.   chunk_crc = BigEndianToSystem (chunk_crc) ;
  269.  
  270.   // At this point the entire chunk has been read.
  271.  
  272.   // Calculate the CRC value from the data.
  273.   UBYTE4 crcvalue = 0xFFFFFFFFL ;
  274.   crcvalue = CRC32 (crcvalue, &chunk_type, sizeof (chunk_type)) ;
  275.   crcvalue = CRC32 (crcvalue, chunk_data, chunk_length) ;
  276.   crcvalue ^= 0xFFFFFFFFL ;
  277.   // The CRC is checked below to ensure that the data gets printed
  278.   // if verbose_flag is set.
  279.  
  280.   if (verbose_flag)
  281.   {
  282.     char type [5] = { 0, 0, 0, 0, 0, } ;
  283.     memcpy (type, &chunk_type, sizeof (chunk_type)) ;
  284.     cout << "{" << endl ;
  285.     cout << " Block Type: " << type << endl ;
  286.     cout << " Length: " << chunk_length << endl ;
  287.     cout << " Block CRC: " << hex << chunk_crc << dec << endl ;
  288.     cout << " Calculated CRC: " << hex << crcvalue << dec << endl ;
  289.   }
  290.  
  291.   //  Ensure that the CRC value in the data stream is the same is that CRC
  292.   //  value calculated from the data. We do this after dumping the block.
  293.  
  294.   if (crcvalue != chunk_crc)
  295.     throw EPngError ("Invalid CRC") ;
  296.  
  297.   // Here we process the data within the block. We handle a special case
  298.   // here. Section 4.1.3 specifies that all IDAT chunks must be consecutive
  299.   // with no intervening chunks.
  300.   if (reading_pixel_data)
  301.   {
  302.     // The previous chunk was an IDAT chunk and we have not read all the
  303.     // the pixel data. The only chunk permitted at this point is another
  304.     // IDAT block.
  305.     if (chunk_type != ChunkType ("IDAT"))
  306.       throw EPngError ("IDAT Block Expected") ;
  307.  
  308.     ProcessData () ;
  309.   }
  310.   else
  311.   {
  312.     if (chunk_type == ChunkType ("IHDR")) ProcessHeader () ;
  313.     else if (chunk_type == ChunkType ("IDAT")) ReadPixelData () ;
  314.     else if (chunk_type == ChunkType ("PLTE")) ProcessPalette () ;
  315.     else if (chunk_type == ChunkType ("IEND")) end_read = true ;
  316.     else if (chunk_type == ChunkType ("bKGD")) ProcessBackground () ;
  317.     else if (chunk_type == ChunkType ("gAMA")) ProcessGamma () ;
  318.     else if (chunk_type == ChunkType ("cHRM")) ProcessChromaticities () ;
  319.     else if (chunk_type == ChunkType ("hIST")) ProcessHistogram () ;
  320.     else if (chunk_type == ChunkType ("sBIT")) ProcessSignificantBits () ;
  321.     else if (chunk_type == ChunkType ("tRNS")) ProcessTransparency () ;
  322.     else if (chunk_type == ChunkType ("pHYs")) ProcessPhysicalPixelDimensions () ;
  323.     else if (chunk_type == ChunkType ("tIME")) ProcessImageTime () ;
  324.     else if (chunk_type == ChunkType ("tEXt")) ProcessTextualData () ;
  325.     else if (chunk_type == ChunkType ("zTXt")) ProcessCompressedText () ;
  326.     else if ((chunk_type & (1 << 5)) == 0) 
  327.       throw EPngError ("Unknown critical chunk") ;
  328.   }
  329.  
  330.   if (verbose_flag)
  331.     cout << "}" << endl ;
  332.   return ;
  333. }
  334.  
  335. //
  336. // Description:
  337. //
  338. //   This function processes an IHDR chuck. This chunk contains the image
  339. //   header which defines the dimensions and color type.
  340. //
  341. //   The main functions here are to allocate space in the image object and
  342. //   to create the color table for grayscale images.
  343. //
  344. void PngDecoder::ProcessHeader ()
  345. {
  346.   if (header_read)
  347.     throw EPngError ("Duplicate IHDR Block") ;
  348.   header_read = true ;
  349.  
  350.   if (chunk_length != sizeof (PngImageHeader))
  351.     throw EPngError ("Invalid Header Length") ;
  352.  
  353.   // Save the data from the image header.
  354.   PngImageHeader *header = (PngImageHeader *) chunk_data ;
  355.   image_height = BigEndianToSystem (header->height) ;
  356.   image_width = BigEndianToSystem (header->width) ;
  357.   image_depth = header->bitdepth ;
  358.   image_color_type = (PngColorType) header->colortype ;
  359.   image_compression_method = header->compressionmethod ;
  360.   image_filter_method = header->filtermethod ;
  361.   image_interlace_method = header->interlacemethod ;
  362.  
  363.   if (verbose_flag)
  364.   {
  365.     cout << " Image Dimensions: " << image_height << " x "
  366.          << image_width << endl ;
  367.     cout << " Bit Depth: " << (int) image_depth << endl ;
  368.     cout << " Color Type: (" << (int) image_color_type << ") " ;
  369.     switch (image_color_type)
  370.     {
  371.     case Grayscale: cout << "grayscale" << endl ; break ;
  372.     case RGB: cout << "RGB" << endl ; break ;
  373.     case Palette: cout << "palette" << endl ; break ;
  374.     case GrayscaleAlpha: cout << "grayscale/alpha" << endl ; break ;
  375.     case RGBAlpha: cout << "RGB/alpha" << endl ; break ;
  376.     default: cout << "invalid" << endl ; break ;
  377.     }
  378.     cout << " Compression Method: " << (int) image_compression_method << endl ;
  379.     cout << " Filter Method: " << (int) image_filter_method << endl ;
  380.     cout << " Interlace Method: (" << (int) image_interlace_method << ") " ;
  381.     switch (image_interlace_method)
  382.     {
  383.     case 0: cout << "none" << endl ; break ;
  384.     case 1: cout << "Adam7" << endl ; break ;
  385.     default: cout << "unknown" << endl ; break ;
  386.     }
  387.   }
  388.  
  389.   // Ensure the that the values in the image header are valid.
  390.   if (image_compression_method != 0)
  391.     throw EPngError ("Invalid Compression Method") ;
  392.  
  393.   if (image_filter_method != 0)
  394.     throw EPngError ("Invalid Filter Method") ;
  395.  
  396.   if (image_interlace_method != 0 && image_interlace_method != 1)
  397.     throw EPngError ("Invalid Compression Method") ;
  398.   switch (image_depth)
  399.   {
  400.   case 1: case 2: case 4: case 8: case 16: break ;
  401.   default: throw EPngError ("Invalid Bit Depth") ;
  402.   }
  403.  
  404.   // Ensure that the color type and bit depth values are consistent.
  405.   switch (image_color_type)
  406.   {
  407.   case Grayscale: break ; // All bit depths are legal for grayscale.
  408.   case RGB: case RGBAlpha: case GrayscaleAlpha:
  409.     if (image_depth != 8 && image_depth != 16)
  410.       throw EPngError ("Invalid Bit Depth for Color Type") ;
  411.     break ;
  412.   case Palette:
  413.     if (image_depth == 16)
  414.       throw EPngError ("Invalid Bit Depth for Color Type") ;
  415.     break ;
  416.   default: throw EPngError ("Invalid Color Type") ;
  417.   }
  418.  
  419.   // Allocate space space in the image object.
  420.   if (image_color_type == RGB || image_color_type == RGBAlpha)
  421.   {
  422.     current_image->SetSize (0, 24, image_width, image_height) ;
  423.   }
  424.   else
  425.   {
  426.     // For an interlaced image use a full byte to represent each pixel to
  427.     // simplify decoding. We do the same for 2-bit images since the
  428.     // BitmapImage class does not support 2-bit images.
  429.     if (image_interlace_method != 0 || image_depth == 2)
  430.     {
  431.       if (image_depth <= 8)
  432.       {
  433.         current_image->SetSize (1<<image_depth,
  434.                                 8,
  435.                                 image_width,
  436.                                 image_height) ;
  437.       }
  438.       else
  439.       {
  440.         current_image->SetSize (256,
  441.                                 8,
  442.                                 image_width,
  443.                                 image_height) ;
  444.       }
  445.     }
  446.     else if (image_depth == 16)
  447.     {
  448.       current_image->SetSize (256,
  449.                               8,
  450.                               image_width,
  451.                               image_height) ;
  452.     }
  453.     else
  454.     {
  455.       // Here we handle 1,4, and 8-bit palette and grayscale im
  456.       current_image->SetSize (1<<image_depth,
  457.                               image_depth,
  458.                               image_width,
  459.                               image_height) ;
  460.     }
  461.  
  462.     // For grayscale images we need to create a colormap.
  463.     if (image_color_type == Grayscale || image_color_type == GrayscaleAlpha)
  464.     {
  465.       switch (image_depth)
  466.       {
  467.       case 1: case 2: case 4:
  468.         {
  469.           for (unsigned int ii = 0 ; ii < (1<<image_depth) ; ++ ii)
  470.           {
  471.             UBYTE1 value = (ii * Max8BitSampleValue + (1<<image_depth) - 2)
  472.                            / ((1<<image_depth) - 1) ;
  473.             current_image->ColorMap (0).red = value ;
  474.             current_image->ColorMap (0).green = value ;
  475.             current_image->ColorMap (0).blue = value ;
  476.           }
  477.         }
  478.         break ;
  479.       case 8: case 16:
  480.         {
  481.           for (unsigned int ii = 0 ; ii <= Max8BitSampleValue ; ++ ii)
  482.           {
  483.             current_image->ColorMap (ii).red = ii ;
  484.             current_image->ColorMap (ii).green = ii ;
  485.             current_image->ColorMap (ii).blue = ii ;
  486.           }
  487.         }
  488.         break ;
  489.       default:
  490.         throw EPngError ("Bad Bit Depth") ;
  491.       }
  492.     }
  493.   }
  494.   return ;
  495. }
  496.  
  497. //
  498. //  Description:
  499. //
  500. //    This function processes the data in a PLTE block. A PLTE block
  501. //    defines the color palette for the image.
  502. //
  503. void PngDecoder::ProcessPalette ()
  504. {
  505.   // There can only be one palette for the image.
  506.   if (palette_read)
  507.     throw EPngError ("Duplicate PLTE block") ;
  508.   palette_read = true ;
  509.  
  510.   // Grayscale images are not allowed to have an palette.
  511.   if (image_color_type == Grayscale || image_color_type == GrayscaleAlpha)
  512.     throw EPngError ("Grayscale image contains a PLTE block") ;
  513.  
  514.   // The palette size must be divisable by 3.
  515.   if (chunk_length % 3 != 0)
  516.     throw EPngError ("PLTE chunk length not divisible by 3") ;
  517.   if (chunk_length > 3 * 256)
  518.     throw EPngError ("PLTE chunk length too large") ;
  519.  
  520.   palette_size = chunk_length / 3 ;
  521.  
  522.   // PLTE chunks are permitted with RGB images to suggest colors
  523.   // for quantization.  Our implementation does not do anything
  524.   // with this information.
  525.   if (image_color_type == RGB || image_color_type == RGBAlpha)
  526.     return ;
  527.  
  528.   // Store the palette in the image.
  529.   for (unsigned int ii = 0, jj = 0 ; ii < chunk_length / 3 ; ++ ii, jj += 3)
  530.   {
  531.     current_image->ColorMap (ii).red = chunk_data [jj] ;
  532.     current_image->ColorMap (ii).green = chunk_data [jj+1] ;
  533.     current_image->ColorMap (ii).blue = chunk_data [jj+2] ;
  534.   }
  535.  
  536.   return ;
  537. }
  538.  
  539. //
  540. //  Description:
  541. //
  542. //    This function performs the processing for an IDAT chunk that is not
  543. //    the first chuck in the IDAT block sequence.
  544. //
  545. //    The only processing here is to reset the data pointers.
  546. //
  547. void PngDecoder::ProcessData ()
  548. {
  549.   byte_offset = 0 ;
  550.   bit_offset = CHAR_BIT ;
  551.   return ;
  552. }
  553.  
  554. //
  555. //  Description:
  556. //
  557. //    This function returns the next uncompressed data byte within the IDAT
  558. //    block data stream. The value returned is either the next byte in the
  559. //    current IDAT block or the first byte in the next IDAT block in the
  560. //    input stream.
  561. //
  562. UBYTE1 PngDecoder::GetIDATByte ()
  563. {
  564.   UBYTE1 value ;
  565.   // See if there are any more bytes in this IDAT block.
  566.   if (byte_offset >= chunk_length)
  567.   {
  568.     // We have consumed the current IDAT block. Advance to the next
  569.     // IDAT block with data. It is possible to have a zero length IDAT
  570.     // block.
  571.     do
  572.     {
  573.       ReadChunk () ;
  574.       if (input_stream->eof ())
  575.         throw EPngError ("Premature End-Of-File") ;
  576.     }
  577.     while (byte_offset >= chunk_length) ;
  578.  
  579.   }
  580.   value = chunk_data [byte_offset] ;
  581.   ++ byte_offset ;
  582.   bit_offset = CHAR_BIT ;
  583.   return value ;
  584. }
  585.  
  586. //
  587. //  Description:
  588. //
  589. //    This function returns a number of uncompressed bits from the
  590. //    IDAT block data stream.
  591. //
  592. //  Parameters:
  593. //    count:  The number of bits to return.
  594. //
  595. int PngDecoder::GetBits (unsigned int count)
  596. {
  597.   unsigned int value = 0 ;
  598.   for (unsigned int ii = 0 ; ii < count ; ++ ii)
  599.   {
  600.     // See if we have consumed all the bits in the current byte.
  601.     if (bit_offset >= CHAR_BIT)
  602.     {
  603.       // Move to the next byte and see if we have used up all the data
  604.       // in the current IDAT block.
  605.       bit_buffer = GetIDATByte () ;
  606.       bit_offset = 0 ;
  607.     }
  608.     if ((bit_buffer & (1<<bit_offset)) != 0)
  609.       value |= (1<<ii) ;
  610.     ++ bit_offset ;
  611.   }
  612.   return value ;
  613. }
  614.  
  615. //
  616. //  Description:
  617. //
  618. //    This function reads Huffman-encoded code lengths for another
  619. //    Huffman table. The Huffman encoded values range from 0..18.
  620. //    The values have the following meanings:
  621. //
  622. //      0..15=>A literal length value
  623. //      16=>Repeat the last code N times. N is found by reading
  624. //          the next 2 bits and adding 3.
  625. //      17=>Set the N length codes to zero. N is found by reading the
  626. //          next 3 bits and adding 3.
  627. //      18=>Set the N length codes to zero. N is found by reading the
  628. //          next 7 bits and adding 11.
  629. //
  630. //  Parameters:
  631. //    ht:  The Huffman table used to decode the input stream.
  632. //    lengths: The output length values
  633. //    lengthcount:  The number of length values to read.
  634. //
  635. //
  636. void PngDecoder::ReadLengths (PngHuffmanDecoder &ht,
  637.                               unsigned int lengths [],
  638.                               unsigned int lengthcount)
  639. {
  640.   for (unsigned int index = 0 ; index < lengthcount ;)
  641.   {
  642.     int command = ht.Decode (*this) ;
  643.     if (command < 16)
  644.     {
  645. #if defined (VERYVERBOSE)
  646.       if (verbose_flag)
  647.         cout << index << " Literal: " << command << endl ;
  648. #endif
  649.       // Raw Length
  650.       lengths [index] = command ;
  651.       ++ index ;
  652.     }
  653.     else if (command == 16)
  654.     {
  655.       // Repeat previous
  656.       int count = GetBits (2) + 3 ;
  657. #if defined (VERYVERBOSE)
  658.       if (verbose_flag)
  659.         cout << index << " Repeat: " << count << endl ;
  660. #endif
  661.       for (unsigned int ii = 0 ; ii < count ; ++ ii)
  662.       {
  663.         if (index == lengthcount)
  664.           throw EPngError ("Length Command Out of Range") ;
  665.         lengths [index] = lengths [index - 1] ;
  666.         ++ index ;
  667.       }
  668.     }
  669.     else if (command == 17)
  670.     {
  671.       // Run of zeros
  672.       int count = GetBits (3) + 3 ;
  673. #if defined (VERYVERBOSE)
  674.       if (verbose_flag)
  675.         cout << index << " Zero Run: " << count << endl ;
  676. #endif
  677.       for (unsigned int ii = 0 ; ii < count ; ++ ii)
  678.       {
  679.         if (index == lengthcount)
  680.           throw EPngError ("Length Command Out of Range") ;
  681.         lengths [index] = 0 ;
  682.         ++ index ;
  683.       }
  684.     }
  685.     else if (command == 18)
  686.     {
  687.       // Longer run of zeros
  688.       int count = GetBits (7) + 11 ;
  689. #if defined (VERYVERBOSE)
  690.       if (verbose_flag)
  691.         cout << index << " Zero Run: " << count << endl ;
  692. #endif
  693.       for (unsigned int ii = 0 ; ii < count ; ++ ii)
  694.       {
  695.         if (index == lengthcount)
  696.           throw EPngError ("Length Command Out of Range") ;
  697.         lengths [index] = 0 ;
  698.         ++ index ;
  699.       }
  700.     }
  701.     else
  702.     {
  703.        throw EPngError ("Bad Code") ;
  704.     }
  705.   }
  706.   return ;
  707. }
  708.  
  709. //
  710. //  Description:
  711. //
  712. //    This function returns the next byte in an uncompressed data set.
  713. //
  714. UBYTE1 PngDecoder::DecodeLiteralByte ()
  715. {
  716.   if (literal_count == 0)
  717.   {
  718.     if (final_data_set)
  719.     {
  720.       throw EPngError ("Premature End-Of-File") ;
  721.     }
  722.     else
  723.     {
  724.       StartNewDataSet () ;
  725.       return DecodeByte () ;
  726.     }
  727.   }
  728.   else
  729.   {
  730.      -- literal_count ;
  731.      UBYTE1 value = GetIDATByte () ;
  732.      stream_adler = Adler (stream_adler, value) ;
  733.      return value ;
  734.   }
  735.   DUMMY_RETURN ; // MSVC++ is not smart enough to tell we can't get here.
  736. }
  737.  
  738. //
  739. //  Description:
  740. //
  741. //    This function decodes the next value in the input stream. The stream
  742. //    format is:
  743. //
  744. //      huffman encoded length/literal value.
  745. //           This value can be:  A data byte (0..255)
  746. //           End Marker: 256
  747. //           Length Code: 257..285
  748. //
  749. //      If the code is a length code then it is followed by 0..13 additional
  750. //      literal bytes. This is followed by a huffman encodered distance value
  751. //      with is followed by 0..13 literal bits.
  752. //
  753. //    This function assumes that it is only called when a data value is
  754. //    in the compressed stream.
  755. //
  756.  
  757. UBYTE1 PngDecoder::DecodeCompressedByte ()
  758. {
  759.   // See if we are still processing a copy operation.
  760.   if (copy_count != 0)
  761.   {
  762.     // Copy the value in the LZ window.
  763.     UBYTE1 value = lz_window [copy_position] ;
  764.     lz_window [window_position] = value ;
  765.     -- copy_count ;
  766.  
  767.     // Advance the copy and window positions.
  768.     copy_position = (copy_position + 1) & 0x7FFF ;
  769.     window_position = (window_position + 1) & 0x7FFF ;
  770.  
  771.     // Update the Adler checksum.
  772.     stream_adler = Adler (stream_adler, value) ;
  773.     return value ;
  774.   }
  775.  
  776.   // The number of extra bits for code-257
  777.   static const int length_extra [29] =
  778.                      {
  779.                        0, 0, 0, 0, 0, 0, 0, 0, 1, 1,
  780.                        1, 1, 2, 2, 2, 2, 3, 3, 3, 3,
  781.                        4, 4, 4, 4, 5, 5, 5, 5, 0,
  782.                      } ;
  783.   // The smallest length value for code-257. The actual length value is
  784.   // the sum of this value and the extra bits.
  785.   static const int length_base [29] =
  786.                      {
  787.                        3,   4,   5,   6,   7,   8,   9,  10,  11,  13,
  788.                       15,  17,  19,  23,  27,  31,  35,  43,  51,  59,
  789.                       67,  83,  99, 115, 131, 163, 195, 227, 258
  790.                      } ;
  791.   // The number of extra bits for a distance code.
  792.   static const int distance_extra [30] =
  793.                      {
  794.                       0,  0,  0,  0,  1,  1,  2,  2,  3,  3,
  795.                       4,  4,  5,  5,  6,  6,  7,  7,  8,  8,
  796.                       9,  9, 10, 10, 11, 11, 12, 12, 13, 13,
  797.                      } ;
  798.   // The smallest value for a distance code.
  799.   static const int distance_base [30] =
  800.                  {
  801.                      1,    2,     3,     4,     5,
  802.                      7,    9,    13,    17,    25,
  803.                     33,   49,    65,    97,   129,
  804.                    193,  257,   385,   513,   769,
  805.                   1025, 1537,  2049,  3073,  4097,
  806.                   6145, 8193, 12289, 16385, 24577,
  807.                  } ;
  808.  
  809.  
  810.   unsigned int value = literal_table->Decode (*this) ;
  811.   unsigned int length ;
  812.   unsigned int distance ;
  813.  
  814.   if (value < 256)
  815.   {
  816.     // This is a data value. Add the value to the LZ window and update the
  817.     // Adler checksum.
  818.     lz_window [window_position] = value ;
  819.  
  820.     window_position = (window_position + 1) & 0x7FFF ;
  821.     stream_adler = Adler (stream_adler, value) ;
  822.     return value ;
  823.   }
  824.   else if (value == 256)
  825.   {
  826.     // We just read the end marker. There should be another data set in the
  827.     // input stream that contains the data value.
  828.     if (final_data_set)
  829.     {
  830.       // The current data set end the final bit set. That means there should
  831.       // be no more data sets in the stream.
  832.       throw EPngError ("Premature End-Of-File") ;
  833.     }
  834.     else
  835.     {
  836.       // The data value is in the next data set.
  837.       StartNewDataSet () ;
  838.       return DecodeByte () ;
  839.     }
  840.   }
  841.   else if (value < 286)
  842.   {
  843.     // The code specifies a length value. Read the extra bits
  844.     // to find the actual length value.
  845.     int extra = length_extra [value - 257] ;
  846.     length = length_base [value - 257] ;
  847.     if (extra != 0)
  848.       length += GetBits (length_extra [value - 257]) ;
  849.  
  850.     // The length value is followed by the distance value. Decode the
  851.     // value then add the extra bits to get the distance value.
  852.     value = distance_table->Decode (*this) ;
  853.     if (value > 29)
  854.       throw EPngError ("Invalid Huffman Distance Value") ;
  855.  
  856.     extra = distance_extra [value] ;
  857.     distance = distance_base [value] ;
  858.     if (extra != 0)
  859.       distance += GetBits (distance_extra [value]) ;
  860.  
  861.     // Set of the state variables that are used to find the following copied
  862.     // bytes.
  863.     copy_position = (PngWindowSize + window_position - distance) & 0x7FFF ;
  864.     copy_count = length ;
  865.     // Return the first copy byte.
  866.     value = lz_window [copy_position] ;
  867.     lz_window [window_position] = value ;
  868.  
  869.     copy_position = (copy_position + 1) & 0x7FFF ;
  870.     window_position = (window_position + 1) & 0x7FFF ;
  871.     -- copy_count ;
  872.     stream_adler = Adler (stream_adler, value) ;
  873.     return value ;
  874.   }
  875.   else
  876.   {
  877.     throw EPngError ("Invalid Huffman Literal Value") ;
  878.   }
  879.   DUMMY_RETURN ; // MSVC++ is not smart enough to tell that we can't get here.
  880. }
  881.  
  882. //
  883. //  Description:
  884. //
  885. //    This function returns the next encoded byte in the deflate stream.
  886. //    All we do here is determine if we are in a literal or compressed
  887. //    data set then calls a function to handle the appropriate type.
  888. //
  889. UBYTE1 PngDecoder::DecodeByte ()
  890. {
  891.   // Handle the easy case of a literal mode data stream. Compressed
  892.   // data sets are handled below.
  893.   if (literal_mode)
  894.   {
  895.     return DecodeLiteralByte () ;
  896.   }
  897.   else
  898.   {
  899.     return DecodeCompressedByte () ;
  900.   }
  901.  
  902. }
  903.  
  904. //
  905. //  Description:
  906. //
  907. //    This function processes the start of a new data set within a compressed
  908. //    stream. The start of a data set has the following format:
  909. //
  910. //      final: 1-bit (1 => this is the last data set)
  911. //      compression type:  2-bits
  912. //      The remainder depends upon the compression type.
  913. //
  914. //      Compression Type:  Uncompressed
  915. //
  916. //        Advance to the next byte boundary. The next two bytes is the
  917. //        length of the uncompressed data. The following two bytes
  918. //        are the ones complement of the length.  [length] uncompressed
  919. //        bytes follow.
  920. //
  921. //      Compression Type:  Fixed Huffman Codes
  922. //
  923. //        The huffman encoded data bits immediately follow the type field. The
  924. //        data is encoded using the huffman lengh codes defined in the deflate
  925. //        specification.
  926. //
  927. //      Compression Type: Dynamic Huffman Codes
  928. //
  929. //        The trick here is that the literal and distance Huffman
  930. //        tables are Huffman-encoded. The next values in the input
  931. //        stream are:
  932. //
  933. //          number of literal codes: 5-bits + 257
  934. //          number of distance codes: 5-bits + 1
  935. //          number of code lengths: 4-bits + 4
  936. //
  937. //          Code Lengths: 3-bits * (code-lengths + 4)
  938. //
  939. //        The code lengths are used to create a huffman table that encodes
  940. //        the literal table followed by the length table.
  941. //
  942. void PngDecoder::StartNewDataSet ()
  943. {
  944.   if (GetBits (1) == 0)
  945.     final_data_set = false ;
  946.   else
  947.     final_data_set = true ;
  948.  
  949.   CompressionType compressiontype = (CompressionType) GetBits (2) ;
  950.   if (verbose_flag)
  951.   {
  952.     cout << " Final: " << final_data_set << endl ;
  953.     cout << " Type:  (" << compressiontype << ") " ;
  954.     switch (compressiontype)
  955.     {
  956.     case 0: cout << "none" ; break ;
  957.     case 1: cout << "Fixed Huffman Codes" ; break ;
  958.     case 2: cout << "Dynamic Huffman Codes" ; break ;
  959.     default: cout << "unknown" ; break ;
  960.     }
  961.     cout << endl ;
  962.   }
  963.  
  964.   if (compressiontype == Uncompressed)
  965.   {
  966.     literal_mode = true ;
  967.     literal_count = GetIDATByte () | (GetIDATByte () << CHAR_BIT) ;
  968.     UBYTE2 testcount = GetIDATByte () | (GetIDATByte () << CHAR_BIT) ;
  969.     if ((literal_count & 0xFFFF) != (~testcount & 0xFFFF))
  970.       throw EPngError ("Invalid Literal Count") ;
  971.   }
  972.   else if (compressiontype == FixedHuffmanCodes)
  973.   {
  974.     // These are the length values that define the
  975.     // literal huffman table.
  976.     static const unsigned int literals [288] =
  977.       {
  978.         8, 8, 8, 8, 8, 8, 8, 8,
  979.         8, 8, 8, 8, 8, 8, 8, 8,
  980.         8, 8, 8, 8, 8, 8, 8, 8,
  981.         8, 8, 8, 8, 8, 8, 8, 8,
  982.         8, 8, 8, 8, 8, 8, 8, 8,
  983.         8, 8, 8, 8, 8, 8, 8, 8,
  984.         8, 8, 8, 8, 8, 8, 8, 8,
  985.         8, 8, 8, 8, 8, 8, 8, 8,
  986.         8, 8, 8, 8, 8, 8, 8, 8,
  987.         8, 8, 8, 8, 8, 8, 8, 8,
  988.         8, 8, 8, 8, 8, 8, 8, 8,
  989.         8, 8, 8, 8, 8, 8, 8, 8,
  990.         8, 8, 8, 8, 8, 8, 8, 8,
  991.         8, 8, 8, 8, 8, 8, 8, 8,
  992.         8, 8, 8, 8, 8, 8, 8, 8,
  993.         8, 8, 8, 8, 8, 8, 8, 8,
  994.         8, 8, 8, 8, 8, 8, 8, 8,
  995.         8, 8, 8, 8, 8, 8, 8, 8,
  996.         9, 9, 9, 9, 9, 9, 9, 9,
  997.         9, 9, 9, 9, 9, 9, 9, 9,
  998.         9, 9, 9, 9, 9, 9, 9, 9,
  999.         9, 9, 9, 9, 9, 9, 9, 9,
  1000.         9, 9, 9, 9, 9, 9, 9, 9,
  1001.         9, 9, 9, 9, 9, 9, 9, 9,
  1002.         9, 9, 9, 9, 9, 9, 9, 9,
  1003.         9, 9, 9, 9, 9, 9, 9, 9,
  1004.         9, 9, 9, 9, 9, 9, 9, 9,
  1005.         9, 9, 9, 9, 9, 9, 9, 9,
  1006.         9, 9, 9, 9, 9, 9, 9, 9,
  1007.         9, 9, 9, 9, 9, 9, 9, 9,
  1008.         9, 9, 9, 9, 9, 9, 9, 9,
  1009.         9, 9, 9, 9, 9, 9, 9, 9,
  1010.         7, 7, 7, 7, 7, 7, 7, 7,
  1011.         7, 7, 7, 7, 7, 7, 7, 7,
  1012.         7, 7, 7, 7, 7, 7, 7, 7,
  1013.         8, 8, 8, 8, 8, 8, 8, 8,
  1014.       } ;
  1015.     // These length values define the distance huffman table.
  1016.     static const unsigned int distances [32] =
  1017.       {
  1018.         5, 5, 5, 5, 5, 5, 5, 5,
  1019.         5, 5, 5, 5, 5, 5, 5, 5,
  1020.         5, 5, 5, 5, 5, 5, 5, 5,
  1021.         5, 5, 5, 5, 5, 5, 5, 5,
  1022.       } ;
  1023.     literal_table->MakeTable (288, literals) ;
  1024.     distance_table->MakeTable (32, distances) ;
  1025.     literal_mode = false ;
  1026.   }
  1027.   else if (compressiontype == DynamicHuffmanCodes)
  1028.   {
  1029.  
  1030.     unsigned int HLIT = GetBits (5) ;
  1031.     unsigned int HDIST = GetBits (5) ;
  1032.     unsigned int HCLEN = GetBits (4) ;
  1033.  
  1034.     if (verbose_flag)
  1035.     {
  1036.       cout << " Literal Code Count: " << (HLIT + 257)
  1037.            << " (" <<  HLIT << ")" << endl ;
  1038.       cout << " Distance Codes: " << (HDIST + 1)
  1039.            << " (" << HDIST << ") " << endl ;
  1040.       cout << " Code Length Codes: " << (HCLEN + 4)
  1041.            << " (" << HCLEN << ")" << endl ;
  1042.     }
  1043.  
  1044.     // Read the length codes used to huffman encode the literal and
  1045.     // distance tables. The unusual thing here is the Huffman values
  1046.     // are not in the order 0..18 but rather the order defined by
  1047.     // the lengthindices array.
  1048.     if (HCLEN + 4 > PngLengthSize)
  1049.       throw EPngError ("Invalid Huffman Code Length") ;
  1050.     unsigned int lengths [PngLengthSize] ;
  1051.     memset (lengths, 0, sizeof (lengths)) ;
  1052.     for (unsigned int ii = 0 ; ii < HCLEN + 4 ; ++ ii)
  1053.     {
  1054.       lengths [PngLengthOrder [ii]] = GetBits (3) ;
  1055.     }
  1056.     PngHuffmanDecoder ht ;
  1057.     ht.MakeTable (PngLengthSize, lengths) ;
  1058.  
  1059. #if defined (VERYVERBOSE)
  1060.     if (verbose_flag)
  1061.     {
  1062.       cout << "  Lengths " << endl ;
  1063.       for (unsigned int ii = 0 ; ii < HCLEN + 4 ; ++ ii)
  1064.         cout << (int) PngLengthOrder [ii] << ") " << lengths [PngLengthOrder [ii]] << endl ;
  1065.     }
  1066. #endif
  1067.     // Using the Huffman table we just created read the length/literals
  1068.     // and distances Huffman tables.
  1069.     unsigned int literals [288] ;
  1070.     ReadLengths (ht, literals, HLIT + 257) ;
  1071.     unsigned int distances [32] ;
  1072.     ReadLengths (ht, distances, HDIST + 1) ;
  1073.  
  1074.     literal_table->MakeTable (HLIT + 257, literals) ;
  1075.     distance_table->MakeTable (HDIST + 1, distances) ;
  1076.     literal_mode = false ;
  1077.   }
  1078.   else
  1079.   {
  1080.     throw EPngError ("Invalid Compression Type") ;
  1081.   }
  1082.   return ;
  1083. }
  1084.  
  1085. //
  1086. //  Description:
  1087. //
  1088. //    This function is called after all the image data is read to check the
  1089. //    the Adler checksum.
  1090. //
  1091. void PngDecoder::CheckAdler ()
  1092. {
  1093.   if (! literal_mode)
  1094.   {
  1095.     // When we arrive here we should have read the last data byte. The next
  1096.     // code in the stream should be the end marker.
  1097.     unsigned int value = literal_table->Decode (*this) ;
  1098.     if (value != 256)
  1099.       throw EPngError ("Missing End Marker") ;
  1100.   }
  1101.   else
  1102.   {
  1103.     if (literal_count != 0)
  1104.       throw EPngError ("Extra data") ;
  1105.   }
  1106.  
  1107.   // Read any empty data sets following the image data.
  1108.   while (! final_data_set)
  1109.   {
  1110.     StartNewDataSet () ;
  1111.     if (literal_mode)
  1112.     {
  1113.        if (literal_count != 0) 
  1114.          throw EPngError ("Extra data") ;
  1115.     }
  1116.     else
  1117.     {
  1118.       unsigned int value = literal_table->Decode (*this) ;
  1119.       if (value != 256)
  1120.         throw EPngError ("Missing End Marker") ;
  1121.     }
  1122.   }
  1123.  
  1124.   // After the end marker the next 4 bytes should be the adler checksum
  1125.   UBYTE4 streamvalue = (GetIDATByte () << (3*CHAR_BIT))
  1126.                      | (GetIDATByte () << (2*CHAR_BIT))
  1127.                      | (GetIDATByte () << CHAR_BIT)
  1128.                      | GetIDATByte () ;
  1129.   if (verbose_flag)
  1130.   {
  1131.     cout << "  Stream Adler Checksum: "
  1132.          << hex << BigEndianToSystem (streamvalue) << endl ;
  1133.     cout << "  Calculated Checksum: " << BigEndianToSystem (stream_adler)
  1134.          << endl << dec ;
  1135.   }
  1136.   if (streamvalue != stream_adler)
  1137.     throw EPngError ("Stream Adler 32 Checksum error") ;
  1138.  
  1139.   return ;
  1140. }
  1141.  
  1142. //
  1143. //  Description:
  1144. //
  1145. //    This function processes an IDAT data stream. It decompresses the
  1146. //    pixel data and stores it in the image.
  1147. //
  1148. //    The Deflate compression system supports many options that are not
  1149. //    permitted in PNG. This is the reason for checking for specific
  1150. //    parameter values.
  1151. //
  1152. void PngDecoder::ReadPixelData ()
  1153. {
  1154.   // Ensure that we only have one IDAT stream in an image stream.
  1155.   if (data_read)
  1156.     throw EPngError ("Image Contains Multiple Data Segments") ;
  1157.   data_read = true ;
  1158.  
  1159.   // If the image requires a palette then it must have been read by
  1160.   // the time we get here.
  1161.   if (image_color_type == Palette && ! palette_read)
  1162.     throw EPngError ("PLTE block must occur before IDAT") ;
  1163.  
  1164.   // This flag isused to ensure that the stream of IDAT chucks is not
  1165.   // interrupted by other block types.
  1166.   reading_pixel_data = true ;
  1167.  
  1168.   ProcessData () ;  // Common IDAT block processing.
  1169.  
  1170.   stream_adler = 1 ;  // Initialize the IDAT counter.
  1171.  
  1172.   // Initialize the LZ compression state variables.
  1173.   window_position = 0 ;
  1174.   copy_position = 0 ;
  1175.   copy_count = 0 ;
  1176.  
  1177.   // Read the copressed stream header.
  1178.   UBYTE1 data1 = GetIDATByte () ;
  1179.   int CM = (data1 & 0x0F) ; // Compression Method
  1180.   int CINFO = (data1 & 0xF0) >> 4 ;
  1181.   int windowsize = (1 << (CINFO + 8)) ;
  1182.  
  1183.   UBYTE1 data2 = GetIDATByte () ;
  1184.   bool FDICT = (data2 & (1 << 5)) != 0 ;
  1185.   int FLEVEL = (data2 & 0xC0) >> 6 ;
  1186.   // The header values are checked below after they have been printed out.
  1187.  
  1188.   if (verbose_flag)
  1189.   {
  1190.     cout << " Compression Method: " << (int) CM << endl ;
  1191.     cout << " WindowSize: " << windowsize << endl ;
  1192.     cout << " Preset Dictionary: " ;
  1193.     if (FDICT != 0)
  1194.       cout << "true" << endl ;
  1195.     else
  1196.        cout << "false" << endl ;
  1197.     cout << " Compression Level: " << FLEVEL << endl ;
  1198.   }
  1199.  
  1200.   // Make sure the header values are valid for PNG.
  1201.   if (CM != 8)
  1202.     throw EPngError ("Invalid Compression Method - Not (8) Deflate") ;
  1203.  
  1204.   if ((data2 | (data1 << 8)) % 31 != 0)
  1205.     throw EPngError ("Invalid IDAT flags") ;
  1206.  
  1207.   if (windowsize > (1 << 15))
  1208.     throw EPngError ("Invalid Compression Window") ;
  1209.  
  1210.   if (FDICT)
  1211.     throw EPngError ("Preset dictionary flag set") ;
  1212.  
  1213.   // Read the start of the new Deflate data set.
  1214.   StartNewDataSet () ;
  1215.  
  1216.   // This block determines the number of bytes needed to store each
  1217.   // data row of the image. Then allocate two buffers to hold row
  1218.   // data.  We need to row buffers to support filtering.
  1219.   unsigned int rowbits ; // The number of bits of data per row.
  1220.   switch (image_color_type)
  1221.   {
  1222.   case Grayscale: case Palette:
  1223.     rowbits = image_width * image_depth ;
  1224.     row_buffer_width = (rowbits + CHAR_BIT - 1) / CHAR_BIT ;
  1225.     break ;
  1226.   case GrayscaleAlpha:
  1227.     row_buffer_width = 2 * image_width * image_depth / CHAR_BIT ;
  1228.     break;
  1229.   case RGB:
  1230.     row_buffer_width = image_width * 3 * image_depth / CHAR_BIT ;
  1231.     break ;
  1232.   case RGBAlpha:
  1233.     row_buffer_width = image_width * 4 * image_depth / CHAR_BIT ;
  1234.     break ;
  1235.   default:
  1236.     throw EPngError ("Invalid Color Type") ;
  1237.   }
  1238.   row_buffers [0] = new UBYTE1 [row_buffer_width] ;
  1239.   row_buffers [1] = new UBYTE1 [row_buffer_width] ;
  1240.  
  1241.   // Read the image data.
  1242.   if (image_interlace_method == 0)
  1243.   {
  1244.     ReadNoninterlaced () ;
  1245.   }
  1246.   else
  1247.   {
  1248.     CallProgressFunction (0) ;
  1249.     for (interlace_pass = 0 ;
  1250.          interlace_pass < InterlacePasses ;
  1251.          ++ interlace_pass)
  1252.     {
  1253.       ReadInterlaced () ;
  1254.     }
  1255.     CallProgressFunction (100) ;
  1256.   }
  1257.  
  1258.   // Make sure that Adler checksum for the compressed data is correct.
  1259.   CheckAdler () ;
  1260.  
  1261.   reading_pixel_data = false ;
  1262.   return ;
  1263. }
  1264.  
  1265. //
  1266. //  Description:
  1267. //
  1268. //    This function filters a row of data.
  1269. //
  1270. //  Parameters:
  1271. //    filter:  The type of filter
  1272. //
  1273. void PngDecoder::FilterRow (unsigned int filter)
  1274. {
  1275.   int lastrow = ! current_row_buffer ; // Index of the previous row
  1276.   int col ;                            // Current Column
  1277.   int offset ;                         // Pixel width
  1278.  
  1279.   // Filtering is done on corresponding items within a record. Determine
  1280.   // the number of bytes between corresponding items.
  1281.   switch (image_color_type)
  1282.   {
  1283.   case Grayscale: case Palette:
  1284.     offset = 1 ;
  1285.     break ;
  1286.   case RGB:
  1287.     offset = 3 * image_depth / CHAR_BIT ;
  1288.     break ;
  1289.   case GrayscaleAlpha:
  1290.     offset = 2 * image_depth / CHAR_BIT ;
  1291.     break ;
  1292.   case RGBAlpha:
  1293.     offset = 4 * image_depth / CHAR_BIT ;
  1294.     break ;
  1295.   default:
  1296.     throw EPngError ("Invalid Color Type") ;
  1297.   }
  1298.  
  1299.   // Filter the row based upon the filter type.
  1300.   switch (filter)
  1301.   {
  1302.   case FilterNone:
  1303.     break ;
  1304.  
  1305.   case FilterSub:
  1306.     // The value is the difference from the value to the left.
  1307.     for (col = offset ; col < row_buffer_width ; ++ col)
  1308.     {
  1309.       row_buffers [current_row_buffer][col] =
  1310.            (row_buffers [current_row_buffer][col] +
  1311.             row_buffers [current_row_buffer][col-offset]) & 0xFF ;
  1312.     }
  1313.     break ;
  1314.  
  1315.   case FilterUp:
  1316.     // The value is the difference from the value in the previous row.
  1317.     for (col = 0 ; col < row_buffer_width ; ++ col)
  1318.     {
  1319.       row_buffers [current_row_buffer][col] =
  1320.            (row_buffers [current_row_buffer][col]
  1321.             + row_buffers [lastrow][col]) & 0xFF ;
  1322.     }
  1323.     break ;
  1324.  
  1325.   case FilterAverage:
  1326.     for (col = 0 ; col < row_buffer_width ; ++ col)
  1327.     {
  1328.       int left ;
  1329.       int above = row_buffers [lastrow][col] ;
  1330.       if (col < offset)
  1331.         left = 0 ;
  1332.       else
  1333.         left = row_buffers [current_row_buffer][col-offset] ;
  1334.  
  1335.       row_buffers [current_row_buffer][col] =
  1336.             (row_buffers [current_row_buffer][col]
  1337.              + (left + above) / 2) & 0xFF ;
  1338.     }
  1339.     break ;
  1340.  
  1341.   case FilterPaeth:
  1342.     for (col = 0 ; col < row_buffer_width ; ++ col)
  1343.     {
  1344.       UBYTE1 left, above, aboveleft ;
  1345.       above = row_buffers [lastrow][col] ;
  1346.       if (col < offset)
  1347.       {
  1348.         left = 0 ;
  1349.         aboveleft = 0 ;
  1350.       }
  1351.       else
  1352.       {
  1353.         left = row_buffers [current_row_buffer][col-offset] ;
  1354.         aboveleft = row_buffers [lastrow][col-offset] ;
  1355.       }
  1356.       int vv = (int) row_buffers [current_row_buffer][col] ;
  1357.       int pp = PaethPredictor (left, above, aboveleft) ;
  1358.       row_buffers [current_row_buffer][col] = (pp + vv) & 0xFF ;
  1359.     }
  1360.     break ;
  1361.  
  1362.   default:
  1363.     throw EPngError ("Invalid Filter Method") ;
  1364.   }
  1365.   return ;
  1366. }
  1367.  
  1368. //
  1369. //  Description:
  1370. //
  1371. //    This function copies the data from a non-interlaced row to the image.
  1372. //
  1373. //  Parameters:
  1374. //    row:  The output row number
  1375. //
  1376. void PngDecoder::CopyNoninterlacedRowToImage (unsigned int row)
  1377. {
  1378.   switch (image_color_type)
  1379.   {
  1380.   case Grayscale:
  1381.   case Palette:
  1382.     {
  1383.       switch (image_depth)
  1384.       {
  1385.       case 1: case 4: case 8:
  1386.         {
  1387.           for (unsigned int ii = 0 ; ii < row_buffer_width ; ++ ii)
  1388.             (*current_image)[row][ii] = row_buffers [current_row_buffer][ii] ;
  1389.         }
  1390.         break ;
  1391.       case 2:
  1392.         {
  1393.           for (unsigned int ii = 0 ; ii < image_width ; ++ ii)
  1394.           {
  1395.             int byteoffset = ii / 4 ;
  1396.             int bitoffset = ii % 4 ;
  1397.  
  1398.             int rawvalue = row_buffers [current_row_buffer][byteoffset] ;
  1399.             (*current_image) [row][ii]
  1400.                = (rawvalue >> 2 * (3 - bitoffset)) & 0x3 ;
  1401.           }
  1402.         }
  1403.         break ;
  1404.       case 16:
  1405.         {
  1406.           for (unsigned int ii = 0 ; ii < row_buffer_width ; ii += 2)
  1407.             (*current_image)[row][ii/2] = row_buffers [current_row_buffer][ii] ;
  1408.         }
  1409.         break ;
  1410.       default:
  1411.         throw EPngError ("Invalid Bit Depth") ;
  1412.       }
  1413.     }
  1414.     break ;
  1415.   case RGB:
  1416.     {
  1417.       for (unsigned int ii = 0, col = 0 ; ii < image_width ; ++ ii)
  1418.       {
  1419.         UBYTE1 red = row_buffers [current_row_buffer][col] ;
  1420.         col += image_depth/CHAR_BIT ;
  1421.         UBYTE1 green = row_buffers [current_row_buffer][col] ;
  1422.         col += image_depth/CHAR_BIT ;
  1423.         UBYTE1 blue = row_buffers [current_row_buffer][col] ;
  1424.         col += image_depth/CHAR_BIT ;
  1425.  
  1426.         (*current_image)[row][3*ii + BitmapImage::RedOffset] = red ;
  1427.         (*current_image)[row][3*ii + BitmapImage::GreenOffset] = green ;
  1428.         (*current_image)[row][3*ii + BitmapImage::BlueOffset] = blue ;
  1429.       }
  1430.     }
  1431.     break ;
  1432.   case GrayscaleAlpha:
  1433.     {
  1434.       // For 8-bit samples each sample interval is 2 bytes. For 16-bit
  1435.       // samples it is four bytes.
  1436.       unsigned int interval = 2 * image_depth / CHAR_BIT ;
  1437.       for (unsigned int ii = 0 ; ii < image_width ; ++ ii)
  1438.       {
  1439.         UBYTE1 alpha = row_buffers [current_row_buffer][interval * ii + 1] ;
  1440.         (*current_image)[row][ii]
  1441.           = (alpha * row_buffers [current_row_buffer][interval * ii]
  1442.              + (Max8BitSampleValue - alpha) * background_gray)
  1443.                / Max8BitSampleValue ;
  1444.       }
  1445.     }
  1446.     break ;
  1447.   case RGBAlpha:
  1448.     {
  1449.       for (unsigned int ii = 0, col = 0 ; ii < image_width ; ++ ii)
  1450.       {
  1451.  
  1452.         UBYTE1 inred = row_buffers [current_row_buffer][col] ;
  1453.         col += image_depth / CHAR_BIT ;
  1454.         UBYTE1 ingreen = row_buffers [current_row_buffer][col] ;
  1455.         col += image_depth / CHAR_BIT ;
  1456.         UBYTE1 inblue = row_buffers [current_row_buffer][col] ;
  1457.         col += image_depth / CHAR_BIT ;
  1458.         UBYTE1 alpha = row_buffers [current_row_buffer][col] ;
  1459.         col += image_depth / CHAR_BIT ;
  1460.  
  1461.         UBYTE1 outred = (alpha * inred
  1462.                          + (Max8BitSampleValue - alpha) * background_red)
  1463.                         / Max8BitSampleValue ;
  1464.         UBYTE1 outgreen = (alpha * ingreen
  1465.                            + (Max8BitSampleValue - alpha) * background_green)
  1466.                           / Max8BitSampleValue ;
  1467.         UBYTE1 outblue = (alpha * inblue
  1468.                           + (Max8BitSampleValue - alpha) * background_blue)
  1469.                          / Max8BitSampleValue ;
  1470.         (*current_image)[row][3*ii+BitmapImage::RedOffset] = outred ;
  1471.         (*current_image)[row][3*ii+BitmapImage::GreenOffset] = outgreen ;
  1472.         (*current_image)[row][3*ii+BitmapImage::BlueOffset] = outblue ;
  1473.       }
  1474.     }
  1475.     break ;
  1476.   default:
  1477.     throw EPngError ("Invalid Color Type") ;
  1478.   }
  1479.   return ;
  1480. }
  1481.  
  1482. //
  1483. //  Description:
  1484. //
  1485. //    This function reads the pixel data for a non-interlaced image.
  1486. //
  1487. void PngDecoder::ReadNoninterlaced ()
  1488. {
  1489.   // Initialize the input buffers.
  1490.   current_row_buffer = 0 ;
  1491.   memset (row_buffers [0], 0, row_buffer_width) ;
  1492.   memset (row_buffers [1], 0, row_buffer_width) ;
  1493.  
  1494.   CallProgressFunction (0) ;
  1495.   for (unsigned int row = 0 ; row < image_height ; ++ row)
  1496.   {
  1497.     PngFilterType filter = (PngFilterType) DecodeByte () ;
  1498.     for (unsigned int col = 0 ; col < row_buffer_width ; ++ col)
  1499.     {
  1500.       int value = DecodeByte () ;
  1501.       row_buffers [current_row_buffer][col] = value ;
  1502.     }
  1503.  
  1504.     FilterRow (filter) ;
  1505.     CopyNoninterlacedRowToImage (row) ;
  1506.     current_row_buffer = ! current_row_buffer ; // Switch buffers
  1507.     CallProgressFunction (100 * row / image_height) ;
  1508.   }
  1509.   CallProgressFunction (100) ;
  1510.   return ;
  1511. }
  1512.  
  1513. //
  1514. //  Description:
  1515. //
  1516. //    This function reads all the rows for an interlaced pass.
  1517. //
  1518. void PngDecoder::ReadInterlaced ()
  1519. {
  1520.   const InterlaceInfo *info = &interlace_values [interlace_pass] ;
  1521.  
  1522.   // If the image is too small we may not have to do any work this small.
  1523.   if (info->start_row >= image_height || info->start_col  >= image_width)
  1524.     return ;
  1525.  
  1526.   current_row_buffer = 0 ;
  1527.   memset (row_buffers [0], 0, row_buffer_width) ;
  1528.   memset (row_buffers [1], 0, row_buffer_width) ;
  1529.  
  1530.   unsigned int pixelsthisrow = (image_width - info->start_col
  1531.                                 + info->col_interval - 1)
  1532.                                / info->col_interval ;
  1533.   unsigned int rowbytes ;
  1534.   switch (image_color_type)
  1535.   {
  1536.   case Grayscale: case Palette:
  1537.     rowbytes = (pixelsthisrow * image_depth + CHAR_BIT - 1) / CHAR_BIT ;
  1538.     break ;
  1539.   case RGB:
  1540.     rowbytes = pixelsthisrow * 3 * image_depth / CHAR_BIT ;
  1541.     break ;
  1542.   case RGBAlpha:
  1543.     rowbytes = pixelsthisrow * 4 * image_depth / CHAR_BIT ;
  1544.     break ;
  1545.   case GrayscaleAlpha:
  1546.     rowbytes = pixelsthisrow * 2 * image_depth / CHAR_BIT ;
  1547.     break ;
  1548.   default:
  1549.     throw EPngError ("Invalid Color Type") ;
  1550.   }
  1551.  
  1552.   for (unsigned int destrow = info->start_row ;
  1553.        destrow < image_height ;
  1554.        destrow += info->row_interval)
  1555.   {
  1556.     // The filter type precedes the row data.
  1557.     PngFilterType filter = (PngFilterType) DecodeByte () ;
  1558.     // Read the row data.
  1559.     for (unsigned int col = 0 ; col < rowbytes ; ++ col)
  1560.       row_buffers [current_row_buffer][col] = DecodeByte () ;
  1561.  
  1562.     // Filter the data
  1563.     FilterRow (filter) ;
  1564.  
  1565.     CopyInterlacedRowToImage (destrow, rowbytes) ;
  1566.  
  1567.     CallProgressFunction (100 * interlace_pass * destrow / image_height / 6) ;
  1568.     current_row_buffer = ! current_row_buffer ;  // Switch buffers
  1569.   }
  1570.   return ;
  1571. }
  1572.  
  1573. //
  1574. //  Description:
  1575. //
  1576. //    This function copies an interlaced row to the output image.
  1577. //
  1578. //  Parameters:
  1579. //    row: The output row number
  1580. //    rowwidth: The number of bytes of data in the row
  1581. //
  1582. void PngDecoder::CopyInterlacedRowToImage (unsigned int row,
  1583.                                            unsigned int rowwidth)
  1584. {
  1585.   const InterlaceInfo *info = &interlace_values [interlace_pass] ;
  1586.  
  1587.   switch (image_color_type)
  1588.   {
  1589.   case Grayscale: case Palette:
  1590.     switch (image_depth)
  1591.     {
  1592.     case 1:
  1593.       {
  1594.         for (unsigned int col = 0, destcol = info->start_col ;
  1595.              col < rowwidth ;
  1596.              ++ col)
  1597.         {
  1598.           for (int ii = CHAR_BIT - 1 ;
  1599.                ii >= 0 && destcol < image_width ;
  1600.                -- ii, destcol += info->col_interval)
  1601.           {
  1602.             UBYTE1 value = (row_buffers [current_row_buffer][col] >> ii) & 0x1 ;
  1603.             (*current_image)[row][destcol] = value ;
  1604.           }
  1605.         }
  1606.       }
  1607.       break ;
  1608.     case 2:
  1609.       {
  1610.         for (unsigned int col = 0, destcol = info->start_col ;
  1611.              col < rowwidth ;
  1612.              ++ col)
  1613.         {
  1614.           for (int ii = 3 * CHAR_BIT/4 ;
  1615.                ii >= 0 && destcol < image_width ;
  1616.                ii -= CHAR_BIT/4 , destcol += info->col_interval)
  1617.           {
  1618.             (*current_image)[row][destcol]
  1619.               = (row_buffers [current_row_buffer][col] >> ii) & 0x3 ;
  1620.           }
  1621.         }
  1622.       }
  1623.       break ;
  1624.     case 4:
  1625.       {
  1626.         for (unsigned int col = 0, destcol = info->start_col ;
  1627.              col < rowwidth ;
  1628.              ++ col)
  1629.         {
  1630.           for (int ii = CHAR_BIT/2 ;
  1631.                ii >= 0 && destcol < image_width ;
  1632.                ii -= CHAR_BIT/2, destcol += info->col_interval)
  1633.           {
  1634.             (*current_image)[row][destcol]
  1635.               = (row_buffers [current_row_buffer][col] >> ii) & 0xF ;
  1636.           }
  1637.         }
  1638.       }
  1639.       break ;
  1640.     case 8:
  1641.       {
  1642.         for (unsigned int col = 0, destcol = info->start_col ;
  1643.              col < rowwidth ;
  1644.              ++ col, destcol += info->col_interval)
  1645.         {
  1646.           (*current_image)[row][destcol]
  1647.             = row_buffers [current_row_buffer][col] ;
  1648.         }
  1649.       }
  1650.       break ;
  1651.     case 16:
  1652.       {
  1653.         for (unsigned int col = 0, destcol = info->start_col ;
  1654.              col < rowwidth ;
  1655.              col += 2, destcol += info->col_interval)
  1656.         {
  1657.           (*current_image)[row][destcol]
  1658.             = row_buffers [current_row_buffer][col] ;
  1659.         }
  1660.       }
  1661.       break ;
  1662.     default:
  1663.       throw EPngError ("Invalid Image Depth") ;
  1664.     }
  1665.     break ;
  1666.   case RGB:
  1667.     {
  1668.       for (unsigned int col = 0, destcol = 3 * info->start_col ;
  1669.            col < rowwidth ;
  1670.            destcol += 3 * info->col_interval)
  1671.       {
  1672.         UBYTE1 red = row_buffers [current_row_buffer][col] ;
  1673.         col += image_depth / CHAR_BIT ;
  1674.         UBYTE1 green = row_buffers [current_row_buffer][col] ;
  1675.         col += image_depth / CHAR_BIT ;
  1676.         UBYTE1 blue = row_buffers [current_row_buffer][col] ;
  1677.         col += image_depth / CHAR_BIT ;
  1678.  
  1679.         (*current_image)[row][destcol + BitmapImage::RedOffset] = red ;
  1680.         (*current_image)[row][destcol + BitmapImage::GreenOffset] = green ;
  1681.         (*current_image)[row][destcol + BitmapImage::BlueOffset] = blue ;
  1682.       }
  1683.     }
  1684.     break ;
  1685.   case RGBAlpha:
  1686.     {
  1687.       for (unsigned int col = 0, destcol = 3 * info->start_col ;
  1688.            col < rowwidth ;
  1689.            destcol += 3 * info->col_interval)
  1690.       {
  1691.         UBYTE1 inred = row_buffers [current_row_buffer][col] ;
  1692.         col += image_depth / CHAR_BIT ;
  1693.         UBYTE1 ingreen = row_buffers [current_row_buffer][col] ;
  1694.         col += image_depth / CHAR_BIT ;
  1695.         UBYTE1 inblue = row_buffers [current_row_buffer][col] ;
  1696.         col += image_depth / CHAR_BIT ;
  1697.         UBYTE1 alpha = row_buffers [current_row_buffer][col] ;
  1698.         col += image_depth / CHAR_BIT ;
  1699.  
  1700.         UBYTE1 outred = (alpha * inred
  1701.                          + (Max8BitSampleValue - alpha) * background_red)
  1702.                         / Max8BitSampleValue ;
  1703.         UBYTE1 outgreen = (alpha * ingreen
  1704.                            + (Max8BitSampleValue - alpha) * background_green)
  1705.                           / Max8BitSampleValue ;
  1706.         UBYTE1 outblue = (alpha * inblue
  1707.                           + (Max8BitSampleValue - alpha) * background_blue)
  1708.                          / Max8BitSampleValue ;
  1709.  
  1710.         (*current_image)[row][destcol + BitmapImage::RedOffset] = outred ;
  1711.         (*current_image)[row][destcol + BitmapImage::GreenOffset] = outgreen ;
  1712.         (*current_image)[row][destcol + BitmapImage::BlueOffset] = outblue ;
  1713.       }
  1714.     }
  1715.     break ;
  1716.   case GrayscaleAlpha:
  1717.     {
  1718.       for (unsigned int col = 0, destcol = info->start_col ;
  1719.            col < rowwidth ;
  1720.            destcol += info->col_interval)
  1721.       {
  1722.         UBYTE1 invalue = row_buffers [current_row_buffer][col] ;
  1723.         col += image_depth / CHAR_BIT ;
  1724.         UBYTE1 alpha = row_buffers [current_row_buffer][col] ;
  1725.         col += image_depth / CHAR_BIT ;
  1726.  
  1727.         UBYTE1 outvalue = (alpha * invalue
  1728.                            + (Max8BitSampleValue - alpha) * background_gray)
  1729.                           / Max8BitSampleValue ;
  1730.         (*current_image)[row][destcol] = outvalue ;
  1731.       }
  1732.     }
  1733.     break ;
  1734.   default:
  1735.     throw EPngError ("Invalid Color Type") ;
  1736.   }
  1737.   return ;
  1738. }
  1739.  
  1740. //
  1741. //  Description:
  1742. //
  1743. //    This function processes a bKGD chuck. This chunk defines the background
  1744. //    color for the image. We only use this for Alpha channel processing.
  1745. //
  1746. void PngDecoder::ProcessBackground ()
  1747. {
  1748.   UBYTE1 index ;
  1749.  
  1750.   switch (image_color_type)
  1751.   {
  1752.   case Grayscale: case GrayscaleAlpha:
  1753.     if (chunk_length == 0)
  1754.       throw EPngError ("bKGD Chunk too small") ;
  1755.     index = chunk_data [0] ;
  1756.     if (index >= (1<<image_depth))
  1757.       throw EPngError ("bKGD palette index too large") ;
  1758.     background_gray = index ;
  1759.     if (verbose_flag)
  1760.     {
  1761.       cout << "Background Grayscale: " << background_gray << endl ;
  1762.     }
  1763.     break ;
  1764.  
  1765.   case Palette:
  1766.     if (chunk_length == 0)
  1767.       throw EPngError ("bKGD Chunk too small") ;
  1768.     index = chunk_data [0] ;
  1769.     if (index >= (1<<image_depth))
  1770.       throw EPngError ("bKGD palette index too large") ;
  1771.     background_red = current_image->ColorMap (index).red ;
  1772.     background_green = current_image->ColorMap (index).green ;
  1773.     background_blue = current_image->ColorMap (index).blue ;
  1774.     if (verbose_flag)
  1775.     {
  1776.       cout << "Background RGB: " << background_red << " "
  1777.            << background_green << background_blue << endl ;
  1778.     }
  1779.     break ;
  1780.  
  1781.   case RGB: case RGBAlpha:
  1782.     if (chunk_length < 6)
  1783.       throw EPngError ("bKGD Chunk too small") ;
  1784.     background_red = chunk_data [0] ;
  1785.     background_green = chunk_data [2] ;
  1786.     background_blue = chunk_data [4] ;
  1787.     if (verbose_flag)
  1788.     {
  1789.       cout << "Background RGB: " << background_red << " " << background_green
  1790.            << background_blue << endl ;
  1791.     }
  1792.     break ;
  1793.  
  1794.   default:
  1795.     throw EPngError ("Invalid Color Type") ;
  1796.   }
  1797.   return ;
  1798. }
  1799.  
  1800. //
  1801. //  Description:
  1802. //    This function processes a gAMA chunk. The game value is stored
  1803. //    as a 4-byte integer which is the Gamma value times 100,000.
  1804. //
  1805. void PngDecoder::ProcessGamma ()
  1806. {
  1807.   if (palette_read)
  1808.     throw EPngError ("gAMA chunk may not occur before PLTE") ;
  1809.   if (data_read)
  1810.     throw EPngError ("gAMA chunk may not occur before IDAT") ;
  1811.  
  1812.   UBYTE4 value ;
  1813.   if (chunk_length < 4)
  1814.     throw EPngError ("gAMA chunk too small") ;
  1815.   value = chunk_data [0] | (chunk_data [1] << CHAR_BIT)
  1816.         | (chunk_data [2] << (2*CHAR_BIT))
  1817.         | (chunk_data [3] << (3*CHAR_BIT)) ;
  1818.   value = BigEndianToSystem (value) ;
  1819.   file_gamma = (double) value / 100000.0 ;
  1820.   if (verbose_flag)
  1821.     cout << " Gamma: " << file_gamma << endl ;
  1822.   return ;
  1823. }
  1824.  
  1825. //
  1826. //  Description:
  1827. //
  1828. //    This function processes a cHRM chunk. This chunk defines
  1829. //    precise color values for the image.
  1830. //
  1831. //    We do nothing with this chunk but dump its contents.
  1832. //
  1833. void PngDecoder::ProcessChromaticities ()
  1834. {
  1835.   if (palette_read)
  1836.     throw EPngError ("cHRM chunk may not occur after PLTE") ;
  1837.   if (data_read)
  1838.     throw EPngError ("cHRM chunk may not occur after IDAT") ;
  1839.  
  1840.   if (chunk_length != sizeof (PngChromaticitiesData))
  1841.     throw EPngError ("Invalid cHRM chunk length") ;
  1842.  
  1843.   PngChromaticitiesData *data = (PngChromaticitiesData *) chunk_data ;
  1844.  
  1845.   data->whitepointx = BigEndianToSystem (data->whitepointx) ;
  1846.   data->whitepointy = BigEndianToSystem (data->whitepointy) ;
  1847.   data->redx = BigEndianToSystem (data->redx) ;
  1848.   data->redy = BigEndianToSystem (data->redy) ;
  1849.   data->greenx = BigEndianToSystem (data->greenx) ;
  1850.   data->greeny = BigEndianToSystem (data->greeny) ;
  1851.   data->bluex = BigEndianToSystem (data->bluex) ;
  1852.   data->bluey = BigEndianToSystem (data->bluey) ;
  1853.  
  1854.   if (verbose_flag)
  1855.   {
  1856.     cout << "  White Point X: " << (double) data->whitepointx / 100000.0
  1857.          << endl ;
  1858.     cout << "  White Point y: " << (double) data->whitepointx / 100000.0
  1859.          << endl ;
  1860.     cout << "  Red X:         " << (double) data->redx / 100000.0 << endl ;
  1861.     cout << "  Red Y:         " << (double) data->redy / 100000.0 << endl ;
  1862.     cout << "  Green X:       " << (double) data->greenx / 100000.0 << endl ;
  1863.     cout << "  Green Y:       " << (double) data->greenx / 100000.0 << endl ;
  1864.     cout << "  Blue X:        " << (double) data->bluex / 100000.0 << endl ;
  1865.     cout << "  Blue Y:        " << (double) data->bluex / 100000.0 << endl ;
  1866.   }
  1867.   return ;
  1868. }
  1869.  
  1870. //
  1871. //  Description:
  1872. //
  1873. //    Tais function processes an hIST chunk. This chunk defines the frequency
  1874. //    that each color in the palette is used within the imamge. This
  1875. //    information can be used to assist in quantization.
  1876. //
  1877. //    We do nothing with this chunk but dump its contents.
  1878. //
  1879. void PngDecoder::ProcessHistogram ()
  1880. {
  1881.   if (! palette_read)
  1882.     throw EPngError ("hIST chunk may not appear before PLTE") ;
  1883.   if (data_read)
  1884.     throw EPngError ("hIST chunk must appear before IDAT") ;
  1885.  
  1886.   if (chunk_length  != 2 * palette_size)
  1887.     throw ("Bad size for hIST chunk") ;
  1888.  
  1889.   UBYTE2 *values = (UBYTE2 *) chunk_data ;
  1890.  
  1891.   if (verbose_flag)
  1892.   {
  1893.     for (unsigned int ii = 0 ; ii < palette_size ; ++ ii)
  1894.     {
  1895.       cout << "  " << ii << ") " << values [ii] << endl ;
  1896.     }
  1897.   }
  1898.  
  1899.   return ;
  1900. }
  1901.  
  1902. //
  1903. //  Description:
  1904. //
  1905. //    This function processes the pHYs chunk. This chunk defines the
  1906. //    dimensions for the image pixels.
  1907. //
  1908. //    We do nothing with this chunk except print its contents.
  1909. //
  1910. void PngDecoder::ProcessPhysicalPixelDimensions ()
  1911. {
  1912.   if (data_read)
  1913.     throw EPngError ("pHYS chunk must come before IDAT chunks") ;
  1914.  
  1915.   if (chunk_length != sizeof (PngPixelDimensions))
  1916.     throw EPngError ("pHYs chunk size invalid") ;
  1917.  
  1918.   PngPixelDimensions *pd = (PngPixelDimensions *) chunk_data ;
  1919.   if (pd->unit > 1)
  1920.     throw EPngError ("pHYs contains an invalid unit") ;
  1921.  
  1922.   static const char *unitstrings [2] = { "unknown unit", "meter" } ;
  1923.   if (verbose_flag)
  1924.   {
  1925.     cout << "  " << pd->pixelsx << " per " << unitstrings [pd->unit] << endl ;
  1926.     cout << "  " << pd->pixelsy << " per " << unitstrings [pd->unit] << endl ;
  1927.     cout << "  Unit: " << pd->unit << endl ;
  1928.   }
  1929.   return ;
  1930. }
  1931.  
  1932. //
  1933. //  Description:
  1934. //
  1935. //    This function processes the sBIT chunk. This chunk can be used to
  1936. //    set the number of significant bits used in color values.
  1937. //
  1938. //    We do nothing with this chunk but print its contents.
  1939. //
  1940. void PngDecoder::ProcessSignificantBits ()
  1941. {
  1942.   if (data_read)
  1943.     throw EPngError ("sBIT chunk must occur before IDAT chunks") ;
  1944.   if (palette_read)
  1945.     throw EPngError ("sBIT chunk must occur before PTLE chunk") ;
  1946.  
  1947.   switch (image_color_type)
  1948.   {
  1949.   case Grayscale:
  1950.     {
  1951.       if (chunk_length < 1)
  1952.         throw EPngError ("sBIT chunk length invalid") ;
  1953.  
  1954.       if (verbose_flag)
  1955.         cout << "  Significant Bits: " << chunk_data [0] << endl ;
  1956.     }
  1957.     break ;
  1958.   case Palette: case RGB:
  1959.     {
  1960.       if (chunk_length < 3)
  1961.         throw EPngError ("sBIT chunk length invalid") ;
  1962.  
  1963.       if (verbose_flag)
  1964.       {
  1965.         cout << " Significant Red Bits: " << chunk_data [0] << endl ;
  1966.         cout << " Significant Green Bits: " << chunk_data [1] << endl ;
  1967.         cout << " Significant Blue Bits: " << chunk_data [2] << endl ;
  1968.       }
  1969.     }
  1970.     break ;
  1971.   case GrayscaleAlpha:
  1972.     {
  1973.       if (chunk_length < 2)
  1974.         throw EPngError ("sBIT chunk length invalid") ;
  1975.  
  1976.       if (verbose_flag)
  1977.       {
  1978.         cout << " Significant Bits: " << chunk_data [0] << endl ;
  1979.         cout << " Significant Alpha Bits: " << chunk_data [1] << endl ;
  1980.       }
  1981.     }
  1982.     break ;
  1983.   case RGBAlpha:
  1984.     {
  1985.       if (chunk_length < 4)
  1986.         throw EPngError ("sBIT chunk length invalid") ;
  1987.  
  1988.       if (verbose_flag)
  1989.       {
  1990.         cout << " Significant Red Bits: " << chunk_data [0] << endl ;
  1991.         cout << " Significant Green Bits: " << chunk_data [1] << endl ;
  1992.         cout << " Significant Blue Bits: " << chunk_data [2] << endl ;
  1993.         cout << " Significant Alpha Bits: " << chunk_data [3] << endl ;
  1994.       }
  1995.     }
  1996.     break ;
  1997.   default:
  1998.     throw EPngError ("Invalid Color Type") ;
  1999.   }
  2000.   return ;
  2001. }
  2002.  
  2003. //
  2004. //  Description:
  2005. //
  2006. //    This function processes the tEXt chunk. This chunk stores text
  2007. //    information in the image.
  2008. //
  2009. //    We do nothing with the chunk except print its contents.
  2010. //
  2011. void PngDecoder::ProcessTextualData ()
  2012. {
  2013.   bool end_found = false ;
  2014.   unsigned int offset ;
  2015.   for (offset = 0 ;
  2016.        offset < chunk_length && offset < 80 ;
  2017.        ++ offset)
  2018.   {
  2019.     if (chunk_data [offset] == '\000')
  2020.     {
  2021.       end_found = true ;
  2022.       break ;
  2023.     }
  2024.   }
  2025.   if (! end_found)
  2026.     throw EPngError ("tEXt keyword not found") ;
  2027.  
  2028.   if (verbose_flag)
  2029.   {
  2030.     cout << " Keyword: '" << chunk_data << "'" << endl ;
  2031.     cout << " Value: '" ;
  2032.     for (unsigned int ii = offset + 1 ; ii < chunk_length ; ++ ii)
  2033.       cout << chunk_data [ii] ;
  2034.     cout << "'" << endl ;
  2035.   }
  2036.   return ;
  2037. }
  2038.  
  2039. //
  2040. //  Description:
  2041. //
  2042. //    This function processes the tIME chunk. This chunk stores the last time
  2043. //    the image was modified.
  2044. //
  2045. //    We do nothing with the chunk except print its contents.
  2046. //
  2047. void PngDecoder::ProcessImageTime ()
  2048. {
  2049.   if (chunk_length != sizeof (PngTimeData))
  2050.     throw EPngError ("tIME chunk size invalid") ;
  2051.  
  2052.   if (verbose_flag)
  2053.   {
  2054.     PngTimeData *td = (PngTimeData *) chunk_data ;
  2055.  
  2056.     cout << "  Year: " << td->year << endl ;
  2057.     cout << "  Month: " << td->month << endl ;
  2058.     cout << "  Day: " << td->day << endl ;
  2059.     cout << "  Hour: " << td->hour << endl ;
  2060.     cout << "  Minute: " << td->minute << endl ;
  2061.     cout << "  Second: " << td->second << endl ;
  2062.   }
  2063.   return ;
  2064. }
  2065.  
  2066. //
  2067. //  Description:
  2068. //
  2069. //    This function processes the tRNS chunk. This chunk allows transparency
  2070. //    to be define for color types without an alpha channel.
  2071. //
  2072. //    We do nothing with the chunk except print its contents.
  2073. //
  2074. void PngDecoder::ProcessTransparency ()
  2075. {
  2076.   if (data_read)
  2077.     throw EPngError ("tRNS chunk cannot occur before IDAT chunks") ;
  2078.  
  2079.   if (verbose_flag)
  2080.   {
  2081.     switch (image_color_type)
  2082.     {
  2083.     case Palette:
  2084.       {
  2085.         if (! palette_read)
  2086.           throw EPngError ("tRNS chunk must occur after PLTE chunk") ;
  2087.  
  2088.         if (palette_size != chunk_length)
  2089.           throw EPngError ("tRNS block length invalid") ;
  2090.  
  2091.         for (unsigned int ii = 0 ; ii < chunk_length ; ++ ii)
  2092.           cout << ii << ") " << chunk_data [ii] << endl ;
  2093.       }
  2094.       break ;
  2095.     case Grayscale:
  2096.       {
  2097.         if (chunk_length < 2)
  2098.           throw EPngError ("tRNS chunk length invalid") ;
  2099.         UBYTE2 *value = (UBYTE2 *) chunk_data ;
  2100.         cout << "  Transparency: " << BigEndianToSystem (*value) << endl ;
  2101.       }
  2102.       break ;
  2103.     case RGB:
  2104.       {
  2105.         if (chunk_length < 6)
  2106.           throw EPngError ("tRNS chunk length invalid") ;
  2107.         UBYTE2 *value = (UBYTE2 *) chunk_data ;
  2108.         cout << "  Red Transparency: "
  2109.              << BigEndianToSystem (value [0]) << endl ;
  2110.         cout << "  Green Transparency: "
  2111.              << BigEndianToSystem (value [1]) << endl ;
  2112.         cout << "  Blue Transparency: "
  2113.              << BigEndianToSystem (value [2]) << endl ;
  2114.       }
  2115.       break ;
  2116.     default:
  2117.       throw EPngError ("Invalid Color Type of tRNS chunk") ;
  2118.     }
  2119.   }
  2120.   return ;
  2121. }
  2122.  
  2123. //
  2124. //  Description:
  2125. //
  2126. //    This function processes the zTXt chunk. This chunk stores text
  2127. //     information.  This chunk is similar to a tEXt chunk except that the
  2128. //    data is compressed.
  2129. //
  2130. //    We do nothing with the chunk except print its contents.
  2131. //
  2132. void PngDecoder::ProcessCompressedText ()
  2133. {
  2134.   bool end_found = false ;
  2135.   unsigned int offset ;
  2136.   for (offset = 0 ;
  2137.        offset < chunk_length && offset < 80 ;
  2138.        ++ offset)
  2139.   {
  2140.     if (chunk_data [offset] != '\000')
  2141.     {
  2142.       end_found = true ;
  2143.       break ;
  2144.     }
  2145.   }
  2146.   if (! end_found)
  2147.     throw EPngError ("ZEXt keyword not found") ;
  2148.  
  2149.   if (verbose_flag)
  2150.   {
  2151.     cout << "Keyword: '" << chunk_data << "'" << endl ;
  2152.     cout << "Compression Method: " << chunk_data [offset + 1] << endl ;
  2153.   }
  2154.   return ;
  2155. }
  2156.  
  2157. //
  2158. //  Description:
  2159. //
  2160. //    This function calls the progress function if it has been
  2161. //    defined.
  2162. //
  2163. //  Parameters:
  2164. //    percent:  The completion percentage (0..100)
  2165. //
  2166. void PngDecoder::CallProgressFunction (unsigned int percent)
  2167. {
  2168.   if (progress_function == NULL)
  2169.     return ;
  2170.  
  2171.   if (percent > 100)
  2172.     percent = 100 ;
  2173.  
  2174.   bool cancel = false ;
  2175.   if (image_interlace_method == 0)
  2176.   {
  2177.     progress_function (*this, progress_data, 1, 1,
  2178.                        percent, cancel) ;
  2179.   }
  2180.   else
  2181.   {
  2182.     if (interlace_pass == InterlacePasses)
  2183.     {
  2184.       progress_function (*this, progress_data, interlace_pass,
  2185.                          InterlacePasses,
  2186.                          percent, cancel) ;
  2187.     }
  2188.     else
  2189.     {
  2190.       progress_function (*this, progress_data, interlace_pass + 1,
  2191.                          InterlacePasses,
  2192.                          percent, cancel) ;
  2193.     }
  2194.   }
  2195.   return ;
  2196. }
  2197.  
  2198.