fixed: auto_ptr -> unique_ptr
[opensg.git] / Source / System / Image / FileIO / OSGJPGImageFileType.cpp
blob5e9821cf6f841b804afe08066d665a2258e2cbe8
1 /*---------------------------------------------------------------------------*\
2 * OpenSG *
3 * *
4 * *
5 * Copyright (C) 2000-2002 by the OpenSG Forum *
6 * *
7 * www.opensg.org *
8 * *
9 * contact: dirk@opensg.org, gerrit.voss@vossg.org, jbehr@zgdv.de *
10 * *
11 \*---------------------------------------------------------------------------*/
12 /*---------------------------------------------------------------------------*\
13 * License *
14 * *
15 * This library is free software; you can redistribute it and/or modify it *
16 * under the terms of the GNU Library General Public License as published *
17 * by the Free Software Foundation, version 2. *
18 * *
19 * This library is distributed in the hope that it will be useful, but *
20 * WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
22 * Library General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU Library General Public *
25 * License along with this library; if not, write to the Free Software *
26 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *
27 * *
28 \*---------------------------------------------------------------------------*/
29 /*---------------------------------------------------------------------------*\
30 * Changes *
31 * *
32 * *
33 * *
34 * *
35 * *
36 * *
37 \*---------------------------------------------------------------------------*/
39 #include <cstdlib>
40 #include <cstdio>
42 #include "OSGConfig.h"
44 #ifdef OSG_WITH_JPG
45 extern "C"
48 #ifdef WIN32
49 #define __WIN32__
50 #endif
52 #include <setjmp.h>
53 #include <jpeglib.h>
55 #endif
57 #ifdef OSG_SGI_LIB
58 #include <limits>
59 #endif
60 #include "OSGJPGImageFileType.h"
61 #include "OSGLog.h"
63 #ifndef OSG_DO_DOC
64 # ifdef OSG_WITH_JPG
65 # define OSG_JPG_ARG(ARG) ARG
66 # else
67 # define OSG_JPG_ARG(ARG)
68 # endif
69 #else
70 # define OSG_JPG_ARG(ARG) ARG
71 #endif
73 // Static Class Varible implementations:
74 static const OSG::Char8 *suffixArray[] = { "jpg",
75 "jpeg",
76 "jpe",
77 "jfif" };
79 OSG_BEGIN_NAMESPACE
81 /*! \class JPGImageFileType
83 Image File Type to read/write and store/restore Image objects as
84 JPEG data.
86 To be able to load JPEG images you need the IJG JPEG library,
87 version 6 or later (check the Prerequisites page on www.opensg.org).
88 The lib comes with all Linux distributions.
90 You have to --enable-jpg in the configure line to enable
91 the singleton object.
95 #ifdef OSG_WITH_JPG
97 static const unsigned long BUFFERSIZE = 4096;
99 struct SourceManager
101 struct jpeg_source_mgr pub;
102 std::istream *is;
103 char *buffer;
104 SourceManager(j_decompress_ptr cinfo, std::istream &iStream);
107 static void istream_init_source(j_decompress_ptr cinfo)
109 } // no action necessary
111 static boolean istream_fill_input_buffer(j_decompress_ptr cinfo)
113 SourceManager *sourceManager =
114 reinterpret_cast<SourceManager*>(cinfo->src);
116 sourceManager->is->read(sourceManager->buffer, BUFFERSIZE);
118 cinfo->src->next_input_byte =
119 reinterpret_cast<const JOCTET *>(sourceManager->buffer);
121 if (sourceManager->is->gcount() == 0)
123 /* Insert a fake EOI marker */
124 sourceManager->buffer[0] = JOCTET(0xFF);
125 sourceManager->buffer[1] = JOCTET(JPEG_EOI);
126 cinfo->src->bytes_in_buffer = 2;
128 else
130 cinfo->src->bytes_in_buffer = sourceManager->is->gcount();
133 return TRUE;
136 static void istream_skip_input_data(j_decompress_ptr cinfo, long num_bytes)
138 if (static_cast<unsigned long>(num_bytes) <= cinfo->src->bytes_in_buffer)
140 cinfo->src->bytes_in_buffer -= num_bytes;
141 cinfo->src->next_input_byte += num_bytes;
143 else
145 num_bytes -= long(cinfo->src->bytes_in_buffer);
146 SourceManager *sourceManager =
147 reinterpret_cast<SourceManager*>(cinfo->src);
148 sourceManager->is->ignore(num_bytes);
149 cinfo->src->bytes_in_buffer = 0;
150 cinfo->src->next_input_byte = 0;
154 static void istream_term_source(j_decompress_ptr cinfo) {} // no action necessary
156 SourceManager::SourceManager(j_decompress_ptr cinfo, std::istream &iStream):
157 pub ( ),
158 is (NULL),
159 buffer(NULL)
161 pub.init_source = istream_init_source;
162 pub.fill_input_buffer = istream_fill_input_buffer;
163 pub.skip_input_data = istream_skip_input_data;
164 pub.resync_to_restart = jpeg_resync_to_restart; /* use default method */
165 pub.term_source = istream_term_source;
166 pub.bytes_in_buffer = 0; /* forces fill_input_buffer on first read */
167 pub.next_input_byte = 0; /* until buffer loaded */
168 this->is = &iStream;
169 buffer = static_cast<char*>((*cinfo->mem->alloc_small)(j_common_ptr(cinfo),
170 JPOOL_IMAGE,
171 BUFFERSIZE));
174 struct DestinationManager
176 struct jpeg_destination_mgr pub;
177 std::ostream *os;
178 char *buffer;
179 DestinationManager(j_compress_ptr cinfo, std::ostream &oStream);
182 static void ostream_init_destination(j_compress_ptr cinfo)
184 DestinationManager* dest=
185 reinterpret_cast<DestinationManager*>(cinfo->dest);
187 // Allocate the output buffer --- it will be released when done with image
188 dest->buffer = static_cast<char *>(
189 (*cinfo->mem->alloc_small)(j_common_ptr(cinfo), JPOOL_IMAGE,
190 BUFFERSIZE * sizeof(char)));
192 dest->pub.next_output_byte = reinterpret_cast<JOCTET *>(dest->buffer);
193 dest->pub.free_in_buffer = BUFFERSIZE;
196 static boolean ostream_empty_output_buffer(j_compress_ptr cinfo)
198 DestinationManager *destinationManager =
199 reinterpret_cast<DestinationManager*>(cinfo->dest);
201 destinationManager->os->write(
202 static_cast<char *>(destinationManager->buffer),
203 BUFFERSIZE);
205 destinationManager->pub.next_output_byte =
206 reinterpret_cast<JOCTET *>(destinationManager->buffer);
207 destinationManager->pub.free_in_buffer = BUFFERSIZE;
209 return destinationManager->os->good() != false ? TRUE : FALSE;
212 static void ostream_term_destination(j_compress_ptr cinfo)
214 DestinationManager* dest =
215 reinterpret_cast<DestinationManager*>(cinfo->dest);
217 size_t datacount = BUFFERSIZE - dest->pub.free_in_buffer;
218 // Write any data remaining in the buffer
219 if (datacount > 0)
221 dest->os->write(static_cast<char *>(dest->buffer), datacount);
225 DestinationManager::DestinationManager(j_compress_ptr cinfo,
226 std::ostream &oStream):
227 pub ( ),
228 os (NULL),
229 buffer(NULL)
231 pub.init_destination = ostream_init_destination;
232 pub.empty_output_buffer = ostream_empty_output_buffer;
233 pub.term_destination = ostream_term_destination;
234 this->os = &oStream;
235 buffer = static_cast<char *>(
236 (*cinfo->mem->alloc_small)(j_common_ptr(cinfo),
237 JPOOL_IMAGE,
238 BUFFERSIZE));
239 pub.free_in_buffer = BUFFERSIZE;
240 pub.next_output_byte = reinterpret_cast<JOCTET *>(buffer);
243 struct osg_jpeg_error_mgr
245 struct jpeg_error_mgr pub;
246 jmp_buf setjmp_buffer;
249 static void osg_jpeg_error_exit(j_common_ptr cinfo)
251 /* Always display the message */
252 (*cinfo->err->output_message) (cinfo);
254 /* Let the memory manager delete any temp files before we die */
255 jpeg_destroy(cinfo);
257 /* Return control to the setjmp point */
258 struct osg_jpeg_error_mgr *osgerr =
259 reinterpret_cast<struct osg_jpeg_error_mgr *>(cinfo->err);
260 longjmp(osgerr->setjmp_buffer, 1);
263 static void osg_jpeg_output_message(j_common_ptr cinfo)
265 char buffer[JMSG_LENGTH_MAX];
267 /* Create the message */
268 (*cinfo->err->format_message) (cinfo, buffer);
270 /* Send it to the OSG logger, adding a newline */
271 FFATAL (("JPG: %s\n", buffer));
274 struct jpeg_mem
276 struct jpeg_destination_mgr dest;
277 struct jpeg_source_mgr src;
278 UChar8 *buffer;
279 UInt32 memSize;
280 UInt32 dataSize;
281 } jpeg_mem;
283 /* */
284 static void jpeg_mem_init_source(j_decompress_ptr OSG_CHECK_ARG(cinfo))
286 jpeg_mem.src.next_input_byte = static_cast<JOCTET *>(jpeg_mem.buffer);
287 jpeg_mem.src.bytes_in_buffer = size_t(jpeg_mem.dataSize);
290 /* */
292 static boolean jpeg_mem_fill_input_buffer(
293 j_decompress_ptr OSG_CHECK_ARG(cinfo))
295 SFATAL << "Missing data. Given data block to small." << std::endl;
296 return false;
299 /* */
300 static void jpeg_mem_skip_input_data(j_decompress_ptr OSG_CHECK_ARG(cinfo ),
301 long num_bytes)
303 jpeg_mem.src.next_input_byte += num_bytes;
304 jpeg_mem.src.bytes_in_buffer -= num_bytes;
307 /* */
308 static boolean jpeg_mem_resync_to_restart(
309 j_decompress_ptr OSG_CHECK_ARG(cinfo ),
310 int OSG_CHECK_ARG(desired))
312 return false;
315 /* */
316 static void jpeg_mem_term_source(j_decompress_ptr OSG_CHECK_ARG(cinfo))
320 /* */
321 static void jpeg_mem_init_destination(j_compress_ptr OSG_CHECK_ARG(cinfo))
323 jpeg_mem.dest.next_output_byte = static_cast<JOCTET *>(jpeg_mem.buffer);
324 jpeg_mem.dest.free_in_buffer = size_t(jpeg_mem.memSize);
327 /* */
328 static boolean jpeg_mem_empty_output_buffer(
329 j_compress_ptr OSG_CHECK_ARG(cinfo))
331 SFATAL << "Not enough space left in buffer." << std::endl;
332 return false;
335 /* */
336 static void jpeg_mem_term_destination(j_compress_ptr OSG_CHECK_ARG(cinfo))
338 jpeg_mem.dataSize =
339 (static_cast<UChar8 *>(jpeg_mem.dest.next_output_byte)) -
340 (static_cast<UChar8 *>(jpeg_mem.buffer));
343 /* */
344 static void jpeg_memory_dest(struct jpeg_compress_struct *cinfo,
345 UChar8 *buffer,
346 UInt32 memSize)
348 jpeg_mem.buffer=buffer;
349 jpeg_mem.memSize=memSize;
350 jpeg_mem.dest.init_destination = jpeg_mem_init_destination;
351 jpeg_mem.dest.empty_output_buffer = jpeg_mem_empty_output_buffer;
352 jpeg_mem.dest.term_destination = jpeg_mem_term_destination;
354 cinfo->dest=&jpeg_mem.dest;
357 /* */
358 static void jpeg_memory_src( struct jpeg_decompress_struct *cinfo,
359 const UChar8 *buffer,
360 UInt32 dataSize)
362 jpeg_mem.buffer = const_cast < UChar8 * > (buffer);
363 jpeg_mem.dataSize = dataSize;
365 jpeg_mem.src.init_source = jpeg_mem_init_source;
366 jpeg_mem.src.fill_input_buffer = jpeg_mem_fill_input_buffer;
367 jpeg_mem.src.skip_input_data = jpeg_mem_skip_input_data;
368 jpeg_mem.src.resync_to_restart = jpeg_mem_resync_to_restart;
369 jpeg_mem.src.term_source = jpeg_mem_term_source;
370 cinfo->src = &jpeg_mem.src;
372 #endif
374 JPGImageFileType JPGImageFileType:: _the("image/jpeg",
375 suffixArray, sizeof(suffixArray),
376 (OSG_READ_SUPPORTED |
377 OSG_WRITE_SUPPORTED));
379 void JPGImageFileType::setQuality(UInt32 cl)
381 if(cl > 100)
382 cl = 100;
384 _quality = cl;
387 UInt32 JPGImageFileType::getQuality(void)
389 return _quality;
392 #ifdef OSG_DEBUG_OLD_C_CASTS
393 #ifdef jpeg_create_compress
394 #undef jpeg_create_compress
395 #endif
396 #ifdef jpeg_create_decompress
397 #undef jpeg_create_decompress
398 #endif
400 #define jpeg_create_compress(cinfo) \
401 jpeg_CreateCompress((cinfo), JPEG_LIB_VERSION, \
402 size_t(sizeof(struct jpeg_compress_struct)))
403 #define jpeg_create_decompress(cinfo) \
404 jpeg_CreateDecompress((cinfo), JPEG_LIB_VERSION, \
405 size_t(sizeof(struct jpeg_decompress_struct)))
406 #endif
408 //-------------------------------------------------------------------------
410 Tries to fill the image object with the data read from
411 the given stream. Returns true on success.
414 bool JPGImageFileType::read( Image *OSG_JPG_ARG(pImage ),
415 std::istream &OSG_JPG_ARG(is ),
416 const std::string &OSG_JPG_ARG(mimetype))
418 #ifdef OSG_WITH_JPG
420 struct osg_jpeg_error_mgr jerr;
421 struct jpeg_decompress_struct cinfo;
423 cinfo.err = jpeg_std_error(&jerr.pub);
424 if (setjmp(jerr.setjmp_buffer))
425 return false;
426 cinfo.err->error_exit = osg_jpeg_error_exit;
427 cinfo.err->output_message = osg_jpeg_output_message;
429 jpeg_create_decompress(&cinfo);
431 SourceManager *sourceManager =
432 new ((*cinfo.mem->alloc_small)(j_common_ptr(&cinfo),
433 JPOOL_IMAGE,
434 sizeof(SourceManager)))
435 SourceManager(&cinfo, is);
437 cinfo.src = reinterpret_cast<jpeg_source_mgr *>(sourceManager);
439 jpeg_read_header(&cinfo, TRUE);
440 jpeg_start_decompress(&cinfo);
442 Image::PixelFormat pixelFormat;
444 switch (cinfo.output_components)
446 case 1:
447 pixelFormat = Image::OSG_L_PF;
448 break;
449 case 3:
450 pixelFormat = Image::OSG_RGB_PF;
451 break;
452 default:
453 pixelFormat = Image::OSG_INVALID_PF;
454 break;
457 bool retCode;
459 if(pImage->set(pixelFormat,
460 cinfo.output_width,
461 cinfo.output_height) == true)
463 Real32 res_x = Real32(cinfo.X_density);
464 Real32 res_y = Real32(cinfo.Y_density);
465 UInt16 res_unit = UInt16(cinfo.density_unit);
466 if(res_unit == 2) // centimeter
468 // convert dpcm to dpi.
469 res_x *= 2.54f;
470 res_y *= 2.54f;
471 res_unit = Image::OSG_RESUNIT_INCH;
473 pImage->setResX(res_x);
474 pImage->setResY(res_y);
475 pImage->setResUnit(res_unit);
477 unsigned char *destData = pImage->editData() + pImage->getSize();
479 int row_stride = cinfo.output_width * cinfo.output_components;
481 while (cinfo.output_scanline < cinfo.output_height)
483 destData -= row_stride;
484 jpeg_read_scanlines(&cinfo, &destData, 1);
486 retCode = true;
488 else
490 retCode = false;
493 jpeg_finish_decompress (&cinfo);
494 jpeg_destroy_decompress(&cinfo);
496 return retCode;
498 #else
500 SWARNING << getMimeType()
501 << " read is not compiled into the current binary "
502 << std::endl;
504 return false;
506 #endif
509 //-------------------------------------------------------------------------
510 /*! Tries to write the image object to the given stream.
511 Returns true on success.
514 bool JPGImageFileType::write(const Image *OSG_JPG_ARG(pImage ),
515 std::ostream &OSG_JPG_ARG(os ),
516 const std::string &OSG_JPG_ARG(mimetype))
518 #ifdef OSG_WITH_JPG
520 if((pImage->getBpp() != 1 &&
521 pImage->getBpp() != 3) || pImage->getDepth() != 1)
523 SWARNING << getMimeType()
524 << " JPEG write only works for 2D 1 or 3 bpp images "
525 << std::endl;
527 return false;
530 struct osg_jpeg_error_mgr jerr;
531 struct jpeg_compress_struct cinfo;
533 cinfo.err = jpeg_std_error(&jerr.pub);
535 if (setjmp(jerr.setjmp_buffer))
536 return false;
537 cinfo.err->error_exit = osg_jpeg_error_exit;
538 cinfo.err->output_message = osg_jpeg_output_message;
540 jpeg_create_compress(&cinfo);
542 DestinationManager *destinationManager =
543 new ((*cinfo.mem->alloc_small)(j_common_ptr(&cinfo),
544 JPOOL_IMAGE,
545 sizeof(DestinationManager)))
546 DestinationManager(&cinfo, os);
548 cinfo.dest =
549 reinterpret_cast<jpeg_destination_mgr*>(destinationManager);
550 cinfo.image_width = pImage->getWidth();
551 cinfo.image_height = pImage->getHeight();
552 cinfo.input_components = pImage->getBpp();
553 cinfo.in_color_space = (pImage->getBpp() == 1) ? JCS_GRAYSCALE : JCS_RGB;
555 jpeg_set_defaults(&cinfo);
557 cinfo.density_unit = 1; // dpi
558 cinfo.X_density = UInt16(pImage->getResX() < 0.0f ?
559 pImage->getResX() - 0.5f :
560 pImage->getResX() + 0.5f);
561 cinfo.Y_density = UInt16(pImage->getResY() < 0.0f ?
562 pImage->getResY() - 0.5f :
563 pImage->getResY() + 0.5f);
565 jpeg_set_quality (&cinfo, _quality, TRUE);
566 jpeg_start_compress(&cinfo, TRUE);
568 unsigned char *srcData =
569 const_cast<UInt8 *>(pImage->getData()) + pImage->getSize();
570 int row_stride = cinfo.image_width * cinfo.input_components;
572 while (cinfo.next_scanline < cinfo.image_height)
574 srcData -= row_stride;
575 jpeg_write_scanlines(&cinfo, &srcData, 1);
578 jpeg_finish_compress (&cinfo);
579 jpeg_destroy_compress(&cinfo);
581 return true;
582 #else
584 SWARNING << getMimeType()
585 << " write is not compiled into the current binary "
586 << std::endl;
588 return false;
590 #endif
593 //-------------------------------------------------------------------------
595 Tries to determine the mime type of the data provided by an input stream
596 by searching for magic bytes. Returns the mime type or an empty string
597 when the function could not determine the mime type.
600 std::string JPGImageFileType::determineMimetypeFromStream(std::istream &is)
602 char filecode[2];
604 is.read(filecode, 2);
605 is.seekg(-2, std::ios::cur);
607 return strncmp(filecode, "\xff\xd8", 2) == 0 ?
608 std::string(getMimeType()) : std::string();
612 bool JPGImageFileType::validateHeader(const Char8 *fileName,
613 bool &implemented)
615 implemented = true;
617 if(fileName == NULL)
618 return false;
620 FILE *file = fopen(fileName, "rb");
622 if(file == NULL)
623 return false;
625 UInt16 magic = 0;
627 fread(static_cast<void *>(&magic), sizeof(magic), 1, file);
629 fclose(file);
631 #if BYTE_ORDER == LITTLE_ENDIAN
632 if(magic == 0xd8ff) // the magic header is big endian need to swap it.
633 #else
634 if(magic == 0xffd8)
635 #endif
637 return true;
640 return false;
644 UInt64 JPGImageFileType::restoreData( Image *OSG_JPG_ARG(pImage ),
645 const UChar8 *OSG_JPG_ARG(buffer ),
646 Int32 OSG_JPG_ARG(memSize)) const
648 #ifdef OSG_WITH_JPG
649 UInt64 retCode = 0;
651 struct local_error_mgr
653 struct jpeg_error_mgr pub;
654 jmp_buf setjmp_buffer;
657 unsigned char *destData;
658 Image::PixelFormat pixelFormat = Image::OSG_INVALID_PF;
660 unsigned long imageSize;
661 struct local_error_mgr jerr;
662 struct jpeg_decompress_struct cinfo;
663 JSAMPARRAY imagebuffer;
665 int row_stride;
667 cinfo.err = jpeg_std_error(&jerr.pub);
669 if(setjmp(jerr.setjmp_buffer))
671 jpeg_destroy_decompress(&cinfo);
673 return 0;
676 jpeg_create_decompress(&cinfo);
677 jpeg_memory_src(&cinfo, buffer, memSize);
678 jpeg_read_header(&cinfo, TRUE);
679 jpeg_start_decompress(&cinfo);
681 switch(cinfo.output_components)
683 case 1:
684 pixelFormat = Image::OSG_L_PF;
685 break;
686 case 2:
687 pixelFormat = Image::OSG_LA_PF;
688 break;
689 case 3:
690 pixelFormat = Image::OSG_RGB_PF;
691 break;
692 case 4:
693 pixelFormat = Image::OSG_RGBA_PF;
694 break;
697 if(pImage->set(pixelFormat, cinfo.output_width, cinfo.output_height))
699 imageSize = pImage->getSize();
700 destData = pImage->editData() + imageSize;
701 row_stride = cinfo.output_width * cinfo.output_components;
703 imagebuffer = (*cinfo.mem->alloc_sarray) (j_common_ptr(&cinfo),
704 JPOOL_IMAGE,
705 row_stride,
708 while(cinfo.output_scanline < cinfo.output_height)
710 destData -= row_stride;
711 jpeg_read_scanlines(&cinfo, imagebuffer, 1);
712 memcpy(destData, *imagebuffer, row_stride);
715 retCode = imageSize;
717 else
719 retCode = 0;
722 jpeg_finish_decompress(&cinfo);
723 jpeg_destroy_decompress(&cinfo);
725 return retCode;
726 #else
727 SWARNING << getMimeType()
728 << " read is not compiled into the current binary "
729 << std::endl;
731 return 0;
732 #endif
735 //-------------------------------------------------------------------------
737 Tries to restore the image data from the given memblock.
738 Returns the amount of data read.
740 UInt64 JPGImageFileType::storeData(const Image *OSG_JPG_ARG(pImage ),
741 UChar8 *OSG_JPG_ARG(buffer ),
742 Int32 OSG_JPG_ARG(memSize)) const
744 #ifdef OSG_WITH_JPG
745 if((pImage->getBpp () != 1 && pImage->getBpp() != 3) ||
746 (pImage->getDepth() != 1) )
748 SWARNING << getMimeType()
749 << " JPEG storeData only works for 2D 1 or 3 bpp images "
750 << std::endl;
752 return 0;
755 struct local_error_mgr
757 struct jpeg_error_mgr pub;
758 jmp_buf setjmp_buffer;
761 struct local_error_mgr jerr;
762 struct jpeg_compress_struct cinfo;
763 JSAMPARRAY imagebuffer;
764 UChar8 *data;
766 cinfo.err = jpeg_std_error(&jerr.pub);
768 if(setjmp(jerr.setjmp_buffer))
770 jpeg_destroy_compress(&cinfo);
772 return 0;
775 jpeg_create_compress(&cinfo);
776 jpeg_memory_dest (&cinfo, buffer, memSize);
778 cinfo.image_width = pImage->getWidth();
779 cinfo.image_height = pImage->getHeight();
780 cinfo.input_components = pImage->getBpp();
781 cinfo.in_color_space = (pImage->getBpp() == 1) ? JCS_GRAYSCALE : JCS_RGB;
783 jpeg_set_defaults(&cinfo);
784 jpeg_set_quality(&cinfo, _quality, TRUE);
785 jpeg_start_compress(&cinfo, TRUE);
787 imagebuffer = &data;
789 while(cinfo.next_scanline < cinfo.image_height)
791 data =
792 const_cast<UInt8 *>(pImage->getData()) +
793 (pImage->getHeight() - 1 - cinfo.next_scanline) *
794 pImage->getWidth() *
795 pImage->getBpp();
797 jpeg_write_scanlines(&cinfo, imagebuffer, 1);
800 jpeg_finish_compress(&cinfo);
801 jpeg_destroy_compress(&cinfo);
803 return jpeg_mem.dataSize;
804 #else
805 SWARNING << getMimeType()
806 << " write is not compiled into the current binary "
807 << std::endl;
809 return 0;
810 #endif
813 //-------------------------------------------------------------------------
814 /*! Constructor used for the singleton object
817 JPGImageFileType::JPGImageFileType(const Char8 *mimeType,
818 const Char8 *suffixArray[],
819 UInt16 suffixByteCount,
820 UInt32 flags) :
822 Inherited(mimeType,
823 suffixArray,
824 suffixByteCount,
825 flags),
826 _quality(90)
830 //-------------------------------------------------------------------------
831 /*! Dummy Copy Constructor
834 //-------------------------------------------------------------------------
838 JPGImageFileType::~JPGImageFileType(void)
842 OSG_END_NAMESPACE