image_io_jpeg.cpp
上传用户:yhdzpy8989
上传日期:2007-06-13
资源大小:13604k
文件大小:21k
源码类别:

生物技术

开发平台:

C/C++

  1. /*
  2.  * ===========================================================================
  3.  * PRODUCTION $Log: image_io_jpeg.cpp,v $
  4.  * PRODUCTION Revision 1000.3  2004/06/01 19:41:34  gouriano
  5.  * PRODUCTION PRODUCTION: UPGRADED [GCC34_MSVC7] Dev-tree R1.8
  6.  * PRODUCTION
  7.  * ===========================================================================
  8.  */
  9. /*  $Id: image_io_jpeg.cpp,v 1000.3 2004/06/01 19:41:34 gouriano Exp $
  10.  * ===========================================================================
  11.  *
  12.  *                            PUBLIC DOMAIN NOTICE
  13.  *               National Center for Biotechnology Information
  14.  *
  15.  *  This software/database is a "United States Government Work" under the
  16.  *  terms of the United States Copyright Act.  It was written as part of
  17.  *  the author's official duties as a United States Government employee and
  18.  *  thus cannot be copyrighted.  This software/database is freely available
  19.  *  to the public for use. The National Library of Medicine and the U.S.
  20.  *  Government have not placed any restriction on its use or reproduction.
  21.  *
  22.  *  Although all reasonable efforts have been taken to ensure the accuracy
  23.  *  and reliability of the software and data, the NLM and the U.S.
  24.  *  Government do not and cannot warrant the performance or results that
  25.  *  may be obtained by using this software or data. The NLM and the U.S.
  26.  *  Government disclaim all warranties, express or implied, including
  27.  *  warranties of performance, merchantability or fitness for any particular
  28.  *  purpose.
  29.  *
  30.  *  Please cite the author in any work or product based on this material.
  31.  *
  32.  * ===========================================================================
  33.  *
  34.  * Authors:  Mike DiCuccio
  35.  *
  36.  * File Description:
  37.  *    CImageIOJpeg -- interface class for reading/writing JPEG files
  38.  */
  39. #include <ncbi_pch.hpp>
  40. #include "image_io_jpeg.hpp"
  41. #include <util/image/image.hpp>
  42. #include <util/image/image_exception.hpp>
  43. #ifdef HAVE_LIBJPEG
  44. //
  45. //
  46. // JPEG SUPPORT
  47. //
  48. //
  49. #include <stdio.h>
  50. // hack to get around duplicate definition of INT32
  51. #ifdef NCBI_OS_MSWIN
  52. #define XMD_H
  53. #endif
  54. // jpeglib include (not extern'ed already (!))
  55. extern "C" {
  56. #include <jpeglib.h>
  57. }
  58. BEGIN_NCBI_SCOPE
  59. static const int sc_JpegBufLen = 4096;
  60. static void s_JpegErrorHandler(j_common_ptr ptr)
  61. {
  62.     string msg("Error processing JPEG image: ");
  63.     msg += ptr->err->jpeg_message_table[ptr->err->msg_code];
  64.     if (ptr->is_decompressor) {
  65.         NCBI_THROW(CImageException, eReadError, msg);
  66.     } else {
  67.         NCBI_THROW(CImageException, eWriteError, msg);
  68.     }
  69. }
  70. static void s_JpegOutputHandler(j_common_ptr ptr)
  71. {
  72.     string msg("JPEG message: ");
  73.     msg += ptr->err->jpeg_message_table[ptr->err->msg_code];
  74.     LOG_POST(Warning << msg);
  75. }
  76. //
  77. // specialized internal structs used for reading/writing from streams
  78. //
  79. struct SJpegInput {
  80.     // the input data elements
  81.     struct jpeg_source_mgr pub;
  82.     // our buffer and stream
  83.     CNcbiIstream* stream;
  84.     JOCTET* buffer;
  85. };
  86. struct SJpegOutput {
  87.     // the input data elements
  88.     struct jpeg_destination_mgr pub;
  89.     // our buffer and stream
  90.     CNcbiOstream* stream;
  91.     JOCTET* buffer;
  92. };
  93. //
  94. // JPEG stream i/o handlers handlers
  95. //
  96. // initialize reading on the stream
  97. static void s_JpegReadInit(j_decompress_ptr cinfo)
  98. {
  99.     struct SJpegInput* sptr = (SJpegInput*)cinfo->src;
  100.     // set up our buffer for the first read
  101.     sptr->pub.bytes_in_buffer = 0;
  102.     sptr->pub.next_input_byte = sptr->buffer;
  103. }
  104. // grab data from the stream
  105. static boolean s_JpegReadBuffer(j_decompress_ptr cinfo)
  106. {
  107.     struct SJpegInput* sptr = (SJpegInput*)cinfo->src;
  108.     // read data from the stream
  109.     sptr->stream->read(reinterpret_cast<char*>(sptr->buffer), sc_JpegBufLen);
  110.     // reset our counts
  111.     sptr->pub.bytes_in_buffer = sptr->stream->gcount();
  112.     sptr->pub.next_input_byte = sptr->buffer;
  113.     return TRUE;
  114. }
  115. // skip over some data in an input stream (rare operation)
  116. static void s_JpegReadSkipData(j_decompress_ptr cinfo, long bytes)
  117. {
  118.     struct SJpegInput* sptr = (SJpegInput*)cinfo->src;
  119.     if (bytes > 0) {
  120.         while (bytes > sptr->pub.bytes_in_buffer) {
  121.             bytes -= sptr->pub.bytes_in_buffer;
  122.             s_JpegReadBuffer(cinfo);
  123.         }
  124.         sptr->pub.next_input_byte += (size_t) bytes;
  125.         sptr->pub.bytes_in_buffer -= (size_t) bytes;
  126.     }
  127. }
  128. // finalize reading in a stream (no-op)
  129. static void s_JpegReadTerminate(j_decompress_ptr)
  130. {
  131.     // don't need to do anything here
  132. }
  133. // initialize writing to a stream
  134. static void s_JpegWriteInit(j_compress_ptr cinfo)
  135. {
  136.     struct SJpegOutput* sptr = (SJpegOutput*)cinfo->dest;
  137.     // set up our buffer for the first read
  138.     sptr->pub.next_output_byte = sptr->buffer;
  139.     sptr->pub.free_in_buffer   = sc_JpegBufLen;
  140. }
  141. // fill the input buffer
  142. static boolean s_JpegWriteBuffer(j_compress_ptr cinfo)
  143. {
  144.     struct SJpegOutput* sptr = (SJpegOutput*)cinfo->dest;
  145.     // read data from the stream
  146.     sptr->stream->write(reinterpret_cast<const char*>(sptr->buffer),
  147.                         sc_JpegBufLen);
  148.     // reset our counts
  149.     sptr->pub.next_output_byte = sptr->buffer;
  150.     sptr->pub.free_in_buffer  = sc_JpegBufLen;
  151.     return TRUE;
  152. }
  153. // finalize our JPEG output
  154. static void s_JpegWriteTerminate(j_compress_ptr cinfo)
  155. {
  156.     // don't need to do anything here
  157.     struct SJpegOutput* sptr = (SJpegOutput*)cinfo->dest;
  158.     size_t datacount = sc_JpegBufLen - sptr->pub.free_in_buffer;
  159.     // read data from the stream
  160.     if (datacount > 0) {
  161.         sptr->stream->write(reinterpret_cast<const char*>(sptr->buffer),
  162.                             datacount);
  163.     }
  164.     sptr->stream->flush();
  165.     if ( !*(sptr->stream) ) {
  166.         NCBI_THROW(CImageException, eWriteError,
  167.                    "Error writing to JPEG stream");
  168.     }
  169. }
  170. //
  171. // set up our read structure to handle stream sources
  172. // this is provided in place of jpeg_stdio_src()
  173. //
  174. static void s_JpegReadSetup(j_decompress_ptr cinfo,
  175.                             CNcbiIstream& istr, JOCTET* buffer)
  176. {
  177.     struct SJpegInput* sptr = NULL;
  178.     if (cinfo->src == NULL) {
  179.         cinfo->src =
  180.             (struct jpeg_source_mgr*)malloc(sizeof(SJpegInput));
  181.         sptr = (SJpegInput*)cinfo->src;
  182.     }
  183.     // allocate buffer and save our stream
  184.     sptr->stream = &istr;
  185.     sptr->buffer = buffer;
  186.     // set our callbacks
  187.     sptr->pub.init_source       = s_JpegReadInit;
  188.     sptr->pub.fill_input_buffer = s_JpegReadBuffer;
  189.     sptr->pub.skip_input_data   = s_JpegReadSkipData;
  190.     sptr->pub.resync_to_restart = jpeg_resync_to_restart;
  191.     sptr->pub.term_source       = s_JpegReadTerminate;
  192.     // make sure the structure knows we're just starting now
  193.     sptr->pub.bytes_in_buffer = 0;
  194.     sptr->pub.next_input_byte = buffer;
  195. }
  196. //
  197. // set up our read structure to handle stream sources
  198. // this is provided in place of jpeg_stdio_src()
  199. //
  200. static void s_JpegWriteSetup(j_compress_ptr cinfo,
  201.                              CNcbiOstream& ostr, JOCTET* buffer)
  202. {
  203.     struct SJpegOutput* sptr = NULL;
  204.     if (cinfo->dest == NULL) {
  205.         cinfo->dest =
  206.             (struct jpeg_destination_mgr*)malloc(sizeof(SJpegOutput));
  207.         sptr = (SJpegOutput*)cinfo->dest;
  208.     }
  209.     // allocate buffer and save our stream
  210.     sptr->stream = &ostr;
  211.     sptr->buffer = buffer;
  212.     // set our callbacks
  213.     sptr->pub.init_destination    = s_JpegWriteInit;
  214.     sptr->pub.empty_output_buffer = s_JpegWriteBuffer;
  215.     sptr->pub.term_destination    = s_JpegWriteTerminate;
  216.     // make sure the structure knows we're just starting now
  217.     sptr->pub.free_in_buffer = sc_JpegBufLen;
  218.     sptr->pub.next_output_byte = buffer;
  219. }
  220. //
  221. // ReadImage()
  222. // read a JPEG format image into memory, returning the image itself
  223. // This version reads the entire image
  224. //
  225. CImage* CImageIOJpeg::ReadImage(CNcbiIstream& istr)
  226. {
  227.     vector<JOCTET> buffer(sc_JpegBufLen);
  228.     JOCTET* buf_ptr = &buffer[0];
  229.     CRef<CImage> image;
  230.     // standard libjpeg stuff
  231.     struct jpeg_decompress_struct cinfo;
  232.     struct jpeg_error_mgr jerr;
  233.     try {
  234.         // open our file for reading
  235.         // set up the standard error handler
  236.         cinfo.err = jpeg_std_error(&jerr);
  237.         cinfo.err->error_exit = s_JpegErrorHandler;
  238.         cinfo.err->output_message = s_JpegOutputHandler;
  239.         jpeg_create_decompress(&cinfo);
  240.         // set up our standard stream processor
  241.         s_JpegReadSetup(&cinfo, istr, buf_ptr);
  242.         //jpeg_stdio_src(&cinfo, fp);
  243.         jpeg_read_header(&cinfo, TRUE);
  244.         // decompression parameters
  245.         cinfo.dct_method = JDCT_FLOAT;
  246.         jpeg_start_decompress(&cinfo);
  247.         // allocate an image to hold our data
  248.         image.Reset(new CImage(cinfo.output_width, cinfo.output_height, 3));
  249.         // we process the image 1 scanline at a time
  250.         unsigned char *scanline[1];
  251.         const size_t stride = cinfo.output_width * cinfo.out_color_components;
  252.         switch (cinfo.out_color_components) {
  253.         case 1:
  254.             {{
  255.                  unsigned char* data = image->SetData();
  256.                  vector<unsigned char> scan_buf(stride);
  257.                  scanline[0] = &scan_buf[0];
  258.                  for (size_t i = 0;  i < image->GetHeight();  ++i) {
  259.                      jpeg_read_scanlines(&cinfo, scanline, 1);
  260.                      for (size_t j = 0;  j < stride;  ++j) {
  261.                          *data++ = scanline[0][j];
  262.                          *data++ = scanline[0][j];
  263.                          *data++ = scanline[0][j];
  264.                      }
  265.                  }
  266.              }}
  267.             break;
  268.         case 3:
  269.             scanline[0] = image->SetData();
  270.             for (size_t i = 0;  i < image->GetHeight();  ++i) {
  271.                 jpeg_read_scanlines(&cinfo, scanline, 1);
  272.                 scanline[0] += stride;
  273.             }
  274.             break;
  275.         default:
  276.             NCBI_THROW(CImageException, eReadError,
  277.                        "CImageIOJpeg::ReadImage(): Unhandled color components");
  278.         }
  279.         // standard clean-up
  280.         jpeg_finish_decompress(&cinfo);
  281.         jpeg_destroy_decompress(&cinfo);
  282.     }
  283.     catch (...) {
  284.         // clean up our mess
  285.         jpeg_destroy_decompress(&cinfo);
  286.         throw;
  287.     }
  288.     return image.Release();
  289. }
  290. //
  291. // ReadImage()
  292. // read a JPEG format image into memory, returning the image itself
  293. // This version reads only a subset of the image
  294. //
  295. CImage* CImageIOJpeg::ReadImage(CNcbiIstream& istr,
  296.                                 size_t x, size_t y, size_t w, size_t h)
  297. {
  298.     vector<JOCTET> buffer(sc_JpegBufLen);
  299.     JOCTET* buf_ptr = &buffer[0];
  300.     CRef<CImage> image;
  301.     // standard libjpeg stuff
  302.     struct jpeg_decompress_struct cinfo;
  303.     struct jpeg_error_mgr jerr;
  304.     try {
  305.         // open our file for reading
  306.         // set up the standard error handler
  307.         cinfo.err = jpeg_std_error(&jerr);
  308.         cinfo.err->error_exit = s_JpegErrorHandler;
  309.         cinfo.err->output_message = s_JpegOutputHandler;
  310.         jpeg_create_decompress(&cinfo);
  311.         // set up our standard stream processor
  312.         s_JpegReadSetup(&cinfo, istr, buf_ptr);
  313.         //jpeg_stdio_src(&cinfo, fp);
  314.         jpeg_read_header(&cinfo, TRUE);
  315.         // decompression parameters
  316.         cinfo.dct_method = JDCT_FLOAT;
  317.         jpeg_start_decompress(&cinfo);
  318.         // further validation: make sure we're actually on the image
  319.         if (x >= cinfo.output_width  ||  y >= cinfo.output_height) {
  320.             string msg("CImageIOJpeg::ReadImage(): invalid starting position: ");
  321.             msg += NStr::IntToString(x);
  322.             msg += ", ";
  323.             msg += NStr::IntToString(y);
  324.             msg += " (image dimensions: ";
  325.             msg += NStr::IntToString(cinfo.output_width);
  326.             msg += ", ";
  327.             msg += NStr::IntToString(cinfo.output_height);
  328.             msg += ")";
  329.             NCBI_THROW(CImageException, eReadError, msg);
  330.         }
  331.         // clamp our width and height to the image size
  332.         if (x + w >= cinfo.output_width) {
  333.             w = cinfo.output_width - x;
  334.             LOG_POST(Warning
  335.                      << "CImageIOJpeg::ReadImage(): clamped width to " << w);
  336.         }
  337.         if (y + h >= cinfo.output_height) {
  338.             h = cinfo.output_height - y;
  339.             LOG_POST(Warning
  340.                      << "CImageIOJpeg::ReadImage(): clamped height to " << h);
  341.         }
  342.         // allocate an image to store the subimage's data
  343.         image.Reset(new CImage(w, h, 3));
  344.         // we process the image 1 scanline at a time
  345.         unsigned char *scanline[1];
  346.         const size_t stride = cinfo.output_width * cinfo.out_color_components;
  347.         vector<unsigned char> row(stride);
  348.         scanline[0] = &row[0];
  349.         size_t i;
  350.         // start by skipping a number of scan lines
  351.         for (i = 0;  i < y;  ++i) {
  352.             jpeg_read_scanlines(&cinfo, scanline, 1);
  353.         }
  354.         // now read the actual data
  355.         unsigned char* data = image->SetData();
  356.         switch (cinfo.out_color_components) {
  357.         case 1:
  358.             for ( ;  i < y + h;  ++i) {
  359.                 jpeg_read_scanlines(&cinfo, scanline, 1);
  360.                 for (size_t j = x;  j < x + w;  ++j) {
  361.                     *data++ = scanline[0][j];
  362.                     *data++ = scanline[0][j];
  363.                     *data++ = scanline[0][j];
  364.                 }
  365.             }
  366.             break;
  367.         case 3:
  368.             {{
  369.                  const size_t offs      = x * image->GetDepth();
  370.                  const size_t scan_w    = w * image->GetDepth();
  371.                  const size_t to_stride = image->GetWidth() * image->GetDepth();
  372.                  for ( ;  i < y + h;  ++i) {
  373.                      jpeg_read_scanlines(&cinfo, scanline, 1);
  374.                      memcpy(data, scanline[0] + offs, scan_w);
  375.                      data += to_stride;
  376.                      scanline[0] += stride;
  377.                  }
  378.              }}
  379.             break;
  380.         default:
  381.             NCBI_THROW(CImageException, eReadError,
  382.                        "CImageIOJpeg::ReadImage(): Unhandled color components");
  383.         }
  384.         // standard clean-up
  385.         jpeg_destroy_decompress(&cinfo);
  386.     }
  387.     catch (...) {
  388.         // clean up our mess
  389.         jpeg_destroy_decompress(&cinfo);
  390.         throw;
  391.     }
  392.     return image.Release();
  393. }
  394. //
  395. // WriteImage()
  396. // write an image to a file in JPEG format
  397. // This version writes the entire image
  398. //
  399. void CImageIOJpeg::WriteImage(const CImage& image, CNcbiOstream& ostr,
  400.                               CImageIO::ECompress compress)
  401. {
  402.     vector<JOCTET> buffer(sc_JpegBufLen);
  403.     JOCTET* buf_ptr = &buffer[0];
  404.     struct jpeg_compress_struct cinfo;
  405.     struct jpeg_error_mgr jerr;
  406.     try {
  407.         // standard libjpeg setup
  408.         cinfo.err = jpeg_std_error(&jerr);
  409.         cinfo.err->error_exit = s_JpegErrorHandler;
  410.         cinfo.err->output_message = s_JpegOutputHandler;
  411.         jpeg_create_compress(&cinfo);
  412.         //jpeg_stdio_dest(&cinfo, fp);
  413.         s_JpegWriteSetup(&cinfo, ostr, buf_ptr);
  414.         cinfo.image_width      = image.GetWidth();
  415.         cinfo.image_height     = image.GetHeight();
  416.         cinfo.input_components = image.GetDepth();
  417.         cinfo.in_color_space   = JCS_RGB;
  418.         jpeg_set_defaults(&cinfo);
  419.         // set our compression quality
  420.         int quality = 70;
  421.         switch (compress) {
  422.         case CImageIO::eCompress_None:
  423.             quality = 100;
  424.             break;
  425.         case CImageIO::eCompress_Low:
  426.             quality = 90;
  427.             break;
  428.         case CImageIO::eCompress_Medium:
  429.             quality = 70;
  430.             break;
  431.         case CImageIO::eCompress_High:
  432.             quality = 40;
  433.             break;
  434.         default:
  435.             LOG_POST(Error << "unknown compression type: " << (int)compress);
  436.             break;
  437.         }
  438.         jpeg_set_quality(&cinfo, quality, TRUE);
  439.         // begin compression
  440.         jpeg_start_compress(&cinfo, true);
  441.         // process our data on a line-by-line basis
  442.         JSAMPROW data[1];
  443.         data[0] =
  444.             const_cast<JSAMPLE*> (static_cast<const JSAMPLE*> (image.GetData()));
  445.         for (size_t i = 0;  i < image.GetHeight();  ++i) {
  446.             jpeg_write_scanlines(&cinfo, data, 1);
  447.             data[0] += image.GetWidth() * image.GetDepth();
  448.         }
  449.         // standard clean-up
  450.         jpeg_finish_compress(&cinfo);
  451.         jpeg_destroy_compress(&cinfo);
  452.     }
  453.     catch (...) {
  454.         jpeg_destroy_compress(&cinfo);
  455.         throw;
  456.     }
  457. }
  458. //
  459. // WriteImage()
  460. // write an image to a file in JPEG format
  461. // This version writes only a subpart of the image
  462. //
  463. void CImageIOJpeg::WriteImage(const CImage& image, CNcbiOstream& ostr,
  464.                               size_t x, size_t y, size_t w, size_t h,
  465.                               CImageIO::ECompress compress)
  466. {
  467.     // validate our image position as inside the image we've been passed
  468.     if (x >= image.GetWidth()  ||  y >= image.GetHeight()) {
  469.         string msg("CImageIOJpeg::WriteImage(): invalid image position: ");
  470.         msg += NStr::IntToString(x);
  471.         msg += ", ";
  472.         msg += NStr::IntToString(y);
  473.         NCBI_THROW(CImageException, eWriteError, msg);
  474.     }
  475.     // clamp our width and height
  476.     if (x + w >= image.GetWidth()) {
  477.         w = image.GetWidth() - x;
  478.         LOG_POST(Warning
  479.                  << "CImageIOJpeg::WriteImage(): clamped width to " << w);
  480.     }
  481.     if (y + h >= image.GetHeight()) {
  482.         h = image.GetHeight() - y;
  483.         LOG_POST(Warning
  484.                  << "CImageIOJpeg::WriteImage(): clamped height to " << h);
  485.     }
  486.     vector<JOCTET> buffer(sc_JpegBufLen);
  487.     JOCTET* buf_ptr = &buffer[0];
  488.     struct jpeg_compress_struct cinfo;
  489.     struct jpeg_error_mgr jerr;
  490.     try {
  491.         // standard libjpeg setup
  492.         cinfo.err = jpeg_std_error(&jerr);
  493.         cinfo.err->error_exit = s_JpegErrorHandler;
  494.         cinfo.err->output_message = s_JpegOutputHandler;
  495.         jpeg_create_compress(&cinfo);
  496.         //jpeg_stdio_dest(&cinfo, fp);
  497.         s_JpegWriteSetup(&cinfo, ostr, buf_ptr);
  498.         cinfo.image_width      = w;
  499.         cinfo.image_height     = h;
  500.         cinfo.input_components = image.GetDepth();
  501.         cinfo.in_color_space   = JCS_RGB;
  502.         jpeg_set_defaults(&cinfo);
  503.         // set our compression quality
  504.         int quality = 70;
  505.         switch (compress) {
  506.         case CImageIO::eCompress_None:
  507.             quality = 100;
  508.             break;
  509.         case CImageIO::eCompress_Low:
  510.             quality = 90;
  511.             break;
  512.         case CImageIO::eCompress_Medium:
  513.             quality = 70;
  514.             break;
  515.         case CImageIO::eCompress_High:
  516.             quality = 40;
  517.             break;
  518.         default:
  519.             LOG_POST(Error << "unknown compression type: " << (int)compress);
  520.             break;
  521.         }
  522.         jpeg_set_quality(&cinfo, quality, TRUE);
  523.         // begin compression
  524.         jpeg_start_compress(&cinfo, true);
  525.         // process our data on a line-by-line basis
  526.         const unsigned char* data_start =
  527.             image.GetData() + (y * image.GetWidth() + x) * image.GetDepth();
  528.         size_t data_stride = image.GetWidth() * image.GetDepth();
  529.         JSAMPROW data[1];
  530.         data[0] = const_cast<JSAMPLE*> (static_cast<const JSAMPLE*> (data_start));
  531.         for (size_t i = 0;  i < h;  ++i) {
  532.             jpeg_write_scanlines(&cinfo, data, 1);
  533.             data[0] += data_stride;
  534.         }
  535.         // standard clean-up
  536.         jpeg_finish_compress(&cinfo);
  537.         jpeg_destroy_compress(&cinfo);
  538.     }
  539.     catch (...) {
  540.         jpeg_destroy_compress(&cinfo);
  541.         throw;
  542.     }
  543. }
  544. END_NCBI_SCOPE
  545. #else // !HAVE_LIBJPEG
  546. //
  547. // JPEGLIB functionality not included - we stub out the various needed
  548. // functions
  549. //
  550. BEGIN_NCBI_SCOPE
  551. CImage* CImageIOJpeg::ReadImage(CNcbiIstream& file)
  552. {
  553.     NCBI_THROW(CImageException, eUnsupported,
  554.                "CImageIOJpeg::ReadImage(): JPEG format not supported");
  555. }
  556. CImage* CImageIOJpeg::ReadImage(CNcbiIstream& file,
  557.                                 size_t, size_t, size_t, size_t)
  558. {
  559.     NCBI_THROW(CImageException, eUnsupported,
  560.                "CImageIOJpeg::ReadImage(): JPEG format not supported");
  561. }
  562. void CImageIOJpeg::WriteImage(const CImage& image, CNcbiOstream& file,
  563.                               CImageIO::ECompress)
  564. {
  565.     NCBI_THROW(CImageException, eUnsupported,
  566.                "CImageIOJpeg::WriteImage(): JPEG format not supported");
  567. }
  568. void CImageIOJpeg::WriteImage(const CImage& image, CNcbiOstream& file,
  569.                               size_t, size_t, size_t, size_t,
  570.                               CImageIO::ECompress)
  571. {
  572.     NCBI_THROW(CImageException, eUnsupported,
  573.                "CImageIOJpeg::WriteImage(): JPEG format not supported");
  574. }
  575. END_NCBI_SCOPE
  576. #endif  // HAVE_LIBJPEG
  577. /*
  578.  * ===========================================================================
  579.  * $Log: image_io_jpeg.cpp,v $
  580.  * Revision 1000.3  2004/06/01 19:41:34  gouriano
  581.  * PRODUCTION: UPGRADED [GCC34_MSVC7] Dev-tree R1.8
  582.  *
  583.  * Revision 1.8  2004/05/17 21:07:58  gorelenk
  584.  * Added include of PCH ncbi_pch.hpp
  585.  *
  586.  * Revision 1.7  2004/01/31 17:52:10  dicuccio
  587.  * Added support for black & white JPG images (color components = 1).  Fixed
  588.  * reading of sub-images
  589.  *
  590.  * Revision 1.6  2003/12/16 16:12:27  dicuccio
  591.  * Fixed compilation problems on Linux - return value of read function is not
  592.  * always unsigned char
  593.  *
  594.  * Revision 1.5  2003/12/16 15:49:36  dicuccio
  595.  * Large re-write of image handling.  Added improved error-handling and support
  596.  * for streams-based i/o (via hooks into each client library).
  597.  *
  598.  * Revision 1.4  2003/11/03 15:19:57  dicuccio
  599.  * Added optional compression parameter
  600.  *
  601.  * Revision 1.3  2003/10/02 15:37:33  ivanov
  602.  * Get rid of compilation warnings
  603.  *
  604.  * Revision 1.2  2003/06/16 19:20:02  dicuccio
  605.  * Added guard for libjpeg on Win32
  606.  *
  607.  * Revision 1.1  2003/06/03 15:17:13  dicuccio
  608.  * Initial revision of image library
  609.  *
  610.  * ===========================================================================
  611.  */