2 * The copyright in this software is being made available under the 2-clauses
3 * BSD License, included below. This software may be subject to other third
4 * party and contributor rights, including patent rights, and no such rights
5 * are granted under this license.
7 * Copyright (c) 2002-2014, Universite catholique de Louvain (UCL), Belgium
8 * Copyright (c) 2002-2014, Professor Benoit Macq
9 * Copyright (c) 2001-2003, David Janssens
10 * Copyright (c) 2002-2003, Yannick Verschueren
11 * Copyright (c) 2003-2007, Francois-Olivier Devaux
12 * Copyright (c) 2003-2014, Antonin Descampe
13 * Copyright (c) 2005, Herve Drolon, FreeImage Team
14 * Copyright (c) 2006-2007, Parvatha Elangovan
15 * All rights reserved.
17 * Redistribution and use in source and binary forms, with or without
18 * modification, are permitted provided that the following conditions
20 * 1. Redistributions of source code must retain the above copyright
21 * notice, this list of conditions and the following disclaimer.
22 * 2. Redistributions in binary form must reproduce the above copyright
23 * notice, this list of conditions and the following disclaimer in the
24 * documentation and/or other materials provided with the distribution.
26 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
27 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
30 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
31 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
32 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
33 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
34 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
35 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
36 * POSSIBILITY OF SUCH DAMAGE.
38 #include "opj_apps_config.h"
46 #ifdef OPJ_HAVE_LIBTIFF
48 #endif /* OPJ_HAVE_LIBTIFF */
50 #ifdef OPJ_HAVE_LIBPNG
53 #endif /* OPJ_HAVE_LIBPNG */
59 * Get logarithm of an integer and round downwards.
63 static int int_floorlog2(int a)
66 for (l = 0; a > 1; l++) {
72 /* -->> -->> -->> -->>
76 <<-- <<-- <<-- <<-- */
78 #ifdef INFORMATION_ONLY
79 /* TGA header definition. */
81 unsigned char id_length; /* Image id field length */
82 unsigned char colour_map_type; /* Colour map type */
83 unsigned char image_type; /* Image type */
85 ** Colour map specification
87 unsigned short colour_map_index; /* First entry index */
88 unsigned short colour_map_length; /* Colour map length */
89 unsigned char colour_map_entry_size; /* Colour map entry size */
91 ** Image specification
93 unsigned short x_origin; /* x origin of image */
94 unsigned short y_origin; /* u origin of image */
95 unsigned short image_width; /* Image width */
96 unsigned short image_height; /* Image height */
97 unsigned char pixel_depth; /* Pixel depth */
98 unsigned char image_desc; /* Image descriptor */
100 #endif /* INFORMATION_ONLY */
102 /* Returns a ushort from a little-endian serialized value */
103 static unsigned short get_tga_ushort(const unsigned char *data)
105 return data[0] | (data[1] << 8);
108 #define TGA_HEADER_SIZE 18
110 static int tga_readheader(FILE *fp, unsigned int *bits_per_pixel,
111 unsigned int *width, unsigned int *height, int *flip_image)
115 unsigned char id_len, cmap_type, image_type;
116 unsigned char pixel_depth, image_desc;
117 unsigned short cmap_index, cmap_len, cmap_entry_size;
118 unsigned short x_origin, y_origin, image_w, image_h;
120 if (!bits_per_pixel || !width || !height || !flip_image) {
123 tga = (unsigned char*)malloc(18);
125 if (fread(tga, TGA_HEADER_SIZE, 1, fp) != 1) {
127 "\nError: fread return a number of element different from the expected.\n");
131 id_len = (unsigned char)tga[0];
132 cmap_type = (unsigned char)tga[1];
133 image_type = (unsigned char)tga[2];
134 cmap_index = get_tga_ushort(*(unsigned short*)(&tga[3]));
135 cmap_len = get_tga_ushort(*(unsigned short*)(&tga[5]));
136 cmap_entry_size = (unsigned char)tga[7];
139 x_origin = get_tga_ushort(*(unsigned short*)(&tga[8]));
140 y_origin = get_tga_ushort(*(unsigned short*)(&tga[10]));
141 image_w = get_tga_ushort(*(unsigned short*)(&tga[12]));
142 image_h = get_tga_ushort(*(unsigned short*)(&tga[14]));
143 pixel_depth = (unsigned char)tga[16];
144 image_desc = (unsigned char)tga[17];
148 *bits_per_pixel = (unsigned int)pixel_depth;
149 *width = (unsigned int)image_w;
150 *height = (unsigned int)image_h;
152 /* Ignore tga identifier, if present ... */
154 unsigned char *id = (unsigned char *) malloc(id_len);
155 if (!fread(id, id_len, 1, fp)) {
157 "\nError: fread return a number of element different from the expected.\n");
164 /* Test for compressed formats ... not yet supported ...
165 // Note :- 9 - RLE encoded palettized.
166 // 10 - RLE encoded RGB. */
167 if (image_type > 8) {
168 fprintf(stderr, "Sorry, compressed tga files are not currently supported.\n");
172 *flip_image = !(image_desc & 32);
174 /* Palettized formats are not yet supported, skip over the palette, if present ... */
175 palette_size = cmap_len * (cmap_entry_size / 8);
177 if (palette_size > 0) {
178 fprintf(stderr, "File contains a palette - not yet supported.");
179 fseek(fp, palette_size, SEEK_CUR);
184 #ifdef OPJ_BIG_ENDIAN
186 static inline uint16_t swap16(uint16_t x)
188 return (((x & 0x00ffU) << 8) | ((x & 0xff00U) >> 8));
193 static int tga_writeheader(FILE *fp, int bits_per_pixel, int width, int height,
196 unsigned short image_w, image_h, us0;
197 unsigned char uc0, image_type;
198 unsigned char pixel_depth, image_desc;
200 if (!bits_per_pixel || !width || !height) {
206 if (bits_per_pixel < 256) {
207 pixel_depth = (unsigned char)bits_per_pixel;
209 fprintf(stderr, "ERROR: Wrong bits per pixel inside tga_header");
214 if (fwrite(&uc0, 1, 1, fp) != 1) {
215 goto fails; /* id_length */
217 if (fwrite(&uc0, 1, 1, fp) != 1) {
218 goto fails; /* colour_map_type */
221 image_type = 2; /* Uncompressed. */
222 if (fwrite(&image_type, 1, 1, fp) != 1) {
227 if (fwrite(&us0, 2, 1, fp) != 1) {
228 goto fails; /* colour_map_index */
230 if (fwrite(&us0, 2, 1, fp) != 1) {
231 goto fails; /* colour_map_length */
233 if (fwrite(&uc0, 1, 1, fp) != 1) {
234 goto fails; /* colour_map_entry_size */
237 if (fwrite(&us0, 2, 1, fp) != 1) {
238 goto fails; /* x_origin */
240 if (fwrite(&us0, 2, 1, fp) != 1) {
241 goto fails; /* y_origin */
244 image_w = (unsigned short)width;
245 image_h = (unsigned short) height;
247 #ifndef OPJ_BIG_ENDIAN
248 if (fwrite(&image_w, 2, 1, fp) != 1) {
251 if (fwrite(&image_h, 2, 1, fp) != 1) {
255 image_w = swap16(image_w);
256 image_h = swap16(image_h);
257 if (fwrite(&image_w, 2, 1, fp) != 1) {
260 if (fwrite(&image_h, 2, 1, fp) != 1) {
265 if (fwrite(&pixel_depth, 1, 1, fp) != 1) {
269 image_desc = 8; /* 8 bits per component. */
274 if (fwrite(&image_desc, 1, 1, fp) != 1) {
281 fputs("\nwrite_tgaheader: write ERROR\n", stderr);
285 opj_image_t* tgatoimage(const char *filename, opj_cparameters_t *parameters)
289 unsigned int image_width, image_height, pixel_bit_depth;
292 opj_image_cmptparm_t cmptparm[4]; /* maximum 4 components */
294 OPJ_COLOR_SPACE color_space;
297 int subsampling_dx, subsampling_dy;
300 f = fopen(filename, "rb");
302 fprintf(stderr, "Failed to open %s for reading !!\n", filename);
306 if (!tga_readheader(f, &pixel_bit_depth, &image_width, &image_height,
311 /* We currently only support 24 & 32 bit tga's ... */
312 if (!((pixel_bit_depth == 24) || (pixel_bit_depth == 32))) {
316 /* initialize image components */
317 memset(&cmptparm[0], 0, 4 * sizeof(opj_image_cmptparm_t));
319 mono = (pixel_bit_depth == 8) ||
320 (pixel_bit_depth == 16); /* Mono with & without alpha. */
321 save_alpha = (pixel_bit_depth == 16) ||
322 (pixel_bit_depth == 32); /* Mono with alpha, or RGB with alpha */
325 color_space = CLRSPC_GRAY;
326 numcomps = save_alpha ? 2 : 1;
328 numcomps = save_alpha ? 4 : 3;
329 color_space = CLRSPC_SRGB;
332 /* If the declared file size is > 10 MB, check that the file is big */
333 /* enough to avoid excessive memory allocations */
334 if (image_height != 0 && image_width > 10000000 / image_height / numcomps) {
336 OPJ_UINT64 expected_file_size =
337 (OPJ_UINT64)image_width * image_height * numcomps;
338 long curpos = ftell(f);
339 if (expected_file_size > (OPJ_UINT64)INT_MAX) {
340 expected_file_size = (OPJ_UINT64)INT_MAX;
342 fseek(f, (long)expected_file_size - 1, SEEK_SET);
343 if (fread(&ch, 1, 1, f) != 1) {
347 fseek(f, curpos, SEEK_SET);
350 subsampling_dx = parameters->subsampling_dx;
351 subsampling_dy = parameters->subsampling_dy;
353 for (i = 0; i < numcomps; i++) {
354 cmptparm[i].prec = 8;
356 cmptparm[i].sgnd = 0;
357 cmptparm[i].dx = subsampling_dx;
358 cmptparm[i].dy = subsampling_dy;
359 cmptparm[i].w = image_width;
360 cmptparm[i].h = image_height;
363 /* create the image */
364 image = opj_image_create(numcomps, &cmptparm[0], color_space);
370 /* set image offset and reference grid */
371 image->x0 = parameters->image_offset_x0;
372 image->y0 = parameters->image_offset_y0;
373 image->x1 = !image->x0 ? (image_width - 1) * subsampling_dx + 1 : image->x0 +
374 (image_width - 1) * subsampling_dx + 1;
375 image->y1 = !image->y0 ? (image_height - 1) * subsampling_dy + 1 : image->y0 +
376 (image_height - 1) * subsampling_dy + 1;
379 for (y = 0; y < image_height; y++) {
383 index = (image_height - y - 1) * image_width;
385 index = y * image_width;
389 for (x = 0; x < image_width; x++) {
390 unsigned char r, g, b;
392 if (!fread(&b, 1, 1, f)) {
394 "\nError: fread return a number of element different from the expected.\n");
395 opj_image_destroy(image);
398 if (!fread(&g, 1, 1, f)) {
400 "\nError: fread return a number of element different from the expected.\n");
401 opj_image_destroy(image);
404 if (!fread(&r, 1, 1, f)) {
406 "\nError: fread return a number of element different from the expected.\n");
407 opj_image_destroy(image);
411 image->comps[0].data[index] = r;
412 image->comps[1].data[index] = g;
413 image->comps[2].data[index] = b;
416 } else if (numcomps == 4) {
417 for (x = 0; x < image_width; x++) {
418 unsigned char r, g, b, a;
419 if (!fread(&b, 1, 1, f)) {
421 "\nError: fread return a number of element different from the expected.\n");
422 opj_image_destroy(image);
425 if (!fread(&g, 1, 1, f)) {
427 "\nError: fread return a number of element different from the expected.\n");
428 opj_image_destroy(image);
431 if (!fread(&r, 1, 1, f)) {
433 "\nError: fread return a number of element different from the expected.\n");
434 opj_image_destroy(image);
437 if (!fread(&a, 1, 1, f)) {
439 "\nError: fread return a number of element different from the expected.\n");
440 opj_image_destroy(image);
444 image->comps[0].data[index] = r;
445 image->comps[1].data[index] = g;
446 image->comps[2].data[index] = b;
447 image->comps[3].data[index] = a;
451 fprintf(stderr, "Currently unsupported bit depth : %s\n", filename);
457 int imagetotga(opj_image_t * image, const char *outfile)
459 int width, height, bpp, x, y;
460 opj_bool write_alpha;
461 int i, adjustR, adjustG = 0, adjustB = 0;
462 unsigned int alpha_channel;
469 fdest = fopen(outfile, "wb");
471 fprintf(stderr, "ERROR -> failed to open %s for writing\n", outfile);
475 for (i = 0; i < image->numcomps - 1; i++) {
476 if ((image->comps[0].dx != image->comps[i + 1].dx)
477 || (image->comps[0].dy != image->comps[i + 1].dy)
478 || (image->comps[0].prec != image->comps[i + 1].prec)) {
480 "Unable to create a tga file with such J2K image charateristics.");
485 width = image->comps[0].w;
486 height = image->comps[0].h;
488 /* Mono with alpha, or RGB with alpha. */
489 write_alpha = (image->numcomps == 2) || (image->numcomps == 4);
491 /* Write TGA header */
492 bpp = write_alpha ? 32 : 24;
493 if (!tga_writeheader(fdest, bpp, width, height, OPJ_TRUE)) {
497 alpha_channel = image->numcomps - 1;
499 scale = 255.0f / (float)((1 << image->comps[0].prec) - 1);
501 adjustR = (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
502 if (image->numcomps >= 3) {
503 adjustG = (image->comps[1].sgnd ? 1 << (image->comps[1].prec - 1) : 0);
504 adjustB = (image->comps[2].sgnd ? 1 << (image->comps[2].prec - 1) : 0);
507 for (y = 0; y < height; y++) {
508 unsigned int index = y * width;
510 for (x = 0; x < width; x++, index++) {
511 r = (float)(image->comps[0].data[index] + adjustR);
513 if (image->numcomps > 2) {
514 g = (float)(image->comps[1].data[index] + adjustG);
515 b = (float)(image->comps[2].data[index] + adjustB);
516 } else { /* Greyscale ... */
521 /* TGA format writes BGR ... */
522 value = (unsigned char)(b * scale);
523 res = fwrite(&value, 1, 1, fdest);
525 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
529 value = (unsigned char)(g * scale);
530 res = fwrite(&value, 1, 1, fdest);
532 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
536 value = (unsigned char)(r * scale);
537 res = fwrite(&value, 1, 1, fdest);
539 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
544 a = (float)(image->comps[alpha_channel].data[index]);
545 value = (unsigned char)(a * scale);
546 res = fwrite(&value, 1, 1, fdest);
548 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
558 /* -->> -->> -->> -->>
562 <<-- <<-- <<-- <<-- */
564 /* WORD defines a two byte word */
565 typedef unsigned short int WORD;
567 /* DWORD defines a four byte word */
568 typedef unsigned int DWORD;
571 WORD bfType; /* 'BM' for Bitmap (19776) */
572 DWORD bfSize; /* Size of the file */
573 WORD bfReserved1; /* Reserved : 0 */
574 WORD bfReserved2; /* Reserved : 0 */
575 DWORD bfOffBits; /* Offset */
576 } BITMAPFILEHEADER_t;
579 DWORD biSize; /* Size of the structure in bytes */
580 DWORD biWidth; /* Width of the image in pixels */
581 DWORD biHeight; /* Height of the image in pixels */
582 WORD biPlanes; /* 1 */
583 WORD biBitCount; /* Number of color bits by pixels */
584 DWORD biCompression; /* Type of encoding 0: none 1: RLE8 2: RLE4 */
585 DWORD biSizeImage; /* Size of the image in bytes */
586 DWORD biXpelsPerMeter; /* Horizontal (X) resolution in pixels/meter */
587 DWORD biYpelsPerMeter; /* Vertical (Y) resolution in pixels/meter */
588 DWORD biClrUsed; /* Number of color used in the image (0: ALL) */
589 DWORD biClrImportant; /* Number of important color (0: ALL) */
590 } BITMAPINFOHEADER_t;
592 opj_image_t* bmptoimage(const char *filename, opj_cparameters_t *parameters)
594 int subsampling_dx = parameters->subsampling_dx;
595 int subsampling_dy = parameters->subsampling_dy;
597 int i, numcomps, w, h;
598 OPJ_COLOR_SPACE color_space;
599 opj_image_cmptparm_t cmptparm[3]; /* maximum of 3 components */
600 opj_image_t * image = NULL;
603 BITMAPFILEHEADER_t File_h;
604 BITMAPINFOHEADER_t Info_h;
606 unsigned char *table_R, *table_G, *table_B;
607 unsigned int j, PAD = 0;
614 IN = fopen(filename, "rb");
616 fprintf(stderr, "Failed to open %s for reading !!\n", filename);
620 File_h.bfType = getc(IN);
621 File_h.bfType = (getc(IN) << 8) + File_h.bfType;
623 if (File_h.bfType != 19778) {
624 fprintf(stderr, "Error, not a BMP file!\n");
630 File_h.bfSize = getc(IN);
631 File_h.bfSize = (getc(IN) << 8) + File_h.bfSize;
632 File_h.bfSize = (getc(IN) << 16) + File_h.bfSize;
633 File_h.bfSize = (getc(IN) << 24) + File_h.bfSize;
635 File_h.bfReserved1 = getc(IN);
636 File_h.bfReserved1 = (getc(IN) << 8) + File_h.bfReserved1;
638 File_h.bfReserved2 = getc(IN);
639 File_h.bfReserved2 = (getc(IN) << 8) + File_h.bfReserved2;
641 File_h.bfOffBits = getc(IN);
642 File_h.bfOffBits = (getc(IN) << 8) + File_h.bfOffBits;
643 File_h.bfOffBits = (getc(IN) << 16) + File_h.bfOffBits;
644 File_h.bfOffBits = (getc(IN) << 24) + File_h.bfOffBits;
649 Info_h.biSize = getc(IN);
650 Info_h.biSize = (getc(IN) << 8) + Info_h.biSize;
651 Info_h.biSize = (getc(IN) << 16) + Info_h.biSize;
652 Info_h.biSize = (getc(IN) << 24) + Info_h.biSize;
654 if (Info_h.biSize != 40) {
655 fprintf(stderr, "Error, unknown BMP header size %d\n", Info_h.biSize);
659 Info_h.biWidth = getc(IN);
660 Info_h.biWidth = (getc(IN) << 8) + Info_h.biWidth;
661 Info_h.biWidth = (getc(IN) << 16) + Info_h.biWidth;
662 Info_h.biWidth = (getc(IN) << 24) + Info_h.biWidth;
665 Info_h.biHeight = getc(IN);
666 Info_h.biHeight = (getc(IN) << 8) + Info_h.biHeight;
667 Info_h.biHeight = (getc(IN) << 16) + Info_h.biHeight;
668 Info_h.biHeight = (getc(IN) << 24) + Info_h.biHeight;
671 Info_h.biPlanes = getc(IN);
672 Info_h.biPlanes = (getc(IN) << 8) + Info_h.biPlanes;
674 Info_h.biBitCount = getc(IN);
675 Info_h.biBitCount = (getc(IN) << 8) + Info_h.biBitCount;
677 Info_h.biCompression = getc(IN);
678 Info_h.biCompression = (getc(IN) << 8) + Info_h.biCompression;
679 Info_h.biCompression = (getc(IN) << 16) + Info_h.biCompression;
680 Info_h.biCompression = (getc(IN) << 24) + Info_h.biCompression;
682 Info_h.biSizeImage = getc(IN);
683 Info_h.biSizeImage = (getc(IN) << 8) + Info_h.biSizeImage;
684 Info_h.biSizeImage = (getc(IN) << 16) + Info_h.biSizeImage;
685 Info_h.biSizeImage = (getc(IN) << 24) + Info_h.biSizeImage;
687 Info_h.biXpelsPerMeter = getc(IN);
688 Info_h.biXpelsPerMeter = (getc(IN) << 8) + Info_h.biXpelsPerMeter;
689 Info_h.biXpelsPerMeter = (getc(IN) << 16) + Info_h.biXpelsPerMeter;
690 Info_h.biXpelsPerMeter = (getc(IN) << 24) + Info_h.biXpelsPerMeter;
692 Info_h.biYpelsPerMeter = getc(IN);
693 Info_h.biYpelsPerMeter = (getc(IN) << 8) + Info_h.biYpelsPerMeter;
694 Info_h.biYpelsPerMeter = (getc(IN) << 16) + Info_h.biYpelsPerMeter;
695 Info_h.biYpelsPerMeter = (getc(IN) << 24) + Info_h.biYpelsPerMeter;
697 Info_h.biClrUsed = getc(IN);
698 Info_h.biClrUsed = (getc(IN) << 8) + Info_h.biClrUsed;
699 Info_h.biClrUsed = (getc(IN) << 16) + Info_h.biClrUsed;
700 Info_h.biClrUsed = (getc(IN) << 24) + Info_h.biClrUsed;
702 Info_h.biClrImportant = getc(IN);
703 Info_h.biClrImportant = (getc(IN) << 8) + Info_h.biClrImportant;
704 Info_h.biClrImportant = (getc(IN) << 16) + Info_h.biClrImportant;
705 Info_h.biClrImportant = (getc(IN) << 24) + Info_h.biClrImportant;
707 /* Read the data and store them in the OUT file */
709 if (Info_h.biBitCount == 24) {
711 color_space = CLRSPC_SRGB;
712 /* initialize image components */
713 memset(&cmptparm[0], 0, 3 * sizeof(opj_image_cmptparm_t));
714 for (i = 0; i < numcomps; i++) {
715 cmptparm[i].prec = 8;
717 cmptparm[i].sgnd = 0;
718 cmptparm[i].dx = subsampling_dx;
719 cmptparm[i].dy = subsampling_dy;
723 /* create the image */
724 image = opj_image_create(numcomps, &cmptparm[0], color_space);
730 /* set image offset and reference grid */
731 image->x0 = parameters->image_offset_x0;
732 image->y0 = parameters->image_offset_y0;
733 image->x1 = !image->x0 ? (w - 1) * subsampling_dx + 1 : image->x0 +
734 (w - 1) * subsampling_dx + 1;
735 image->y1 = !image->y0 ? (h - 1) * subsampling_dy + 1 : image->y0 +
736 (h - 1) * subsampling_dy + 1;
740 /* Place the cursor at the beginning of the image information */
741 fseek(IN, 0, SEEK_SET);
742 fseek(IN, File_h.bfOffBits, SEEK_SET);
747 /* PAD = 4 - (3 * W) % 4; */
748 /* PAD = (PAD == 4) ? 0 : PAD; */
749 PAD = (3 * W) % 4 ? 4 - (3 * W) % 4 : 0;
751 RGB = (unsigned char *)
752 malloc((3 * W + PAD) * H * sizeof(unsigned char));
754 if (fread(RGB, sizeof(unsigned char), (3 * W + PAD) * H,
755 IN) != (3 * W + PAD) * H) {
758 opj_image_destroy(image);
760 "\nError: fread return a number of element different from the expected.\n");
766 for (y = 0; y < (int)H; y++) {
767 unsigned char *scanline = RGB + (3 * W + PAD) * (H - 1 - y);
768 for (x = 0; x < (int)W; x++) {
769 unsigned char *pixel = &scanline[3 * x];
770 image->comps[0].data[index] = pixel[2]; /* R */
771 image->comps[1].data[index] = pixel[1]; /* G */
772 image->comps[2].data[index] = pixel[0]; /* B */
777 }/* if (Info_h.biBitCount == 24) */
778 else if (Info_h.biBitCount == 8 && Info_h.biCompression == 0) { /*RGB */
779 if (Info_h.biClrUsed == 0) {
780 Info_h.biClrUsed = 256;
781 } else if (Info_h.biClrUsed > 256) {
782 Info_h.biClrUsed = 256;
785 table_R = (unsigned char *) malloc(256 * sizeof(unsigned char));
786 table_G = (unsigned char *) malloc(256 * sizeof(unsigned char));
787 table_B = (unsigned char *) malloc(256 * sizeof(unsigned char));
790 for (j = 0; j < Info_h.biClrUsed; j++) {
791 table_B[j] = (unsigned char)getc(IN);
792 table_G[j] = (unsigned char)getc(IN);
793 table_R[j] = (unsigned char)getc(IN);
796 !(table_R[j] == table_G[j] && table_R[j] == table_B[j]);
802 /* Place the cursor at the beginning of the image information */
803 fseek(IN, 0, SEEK_SET);
804 fseek(IN, File_h.bfOffBits, SEEK_SET);
808 if (Info_h.biWidth % 2) {
812 numcomps = gray_scale ? 1 : 3;
813 color_space = gray_scale ? CLRSPC_GRAY : CLRSPC_SRGB;
814 /* initialize image components */
815 memset(&cmptparm[0], 0, 3 * sizeof(opj_image_cmptparm_t));
816 for (i = 0; i < numcomps; i++) {
817 cmptparm[i].prec = 8;
819 cmptparm[i].sgnd = 0;
820 cmptparm[i].dx = subsampling_dx;
821 cmptparm[i].dy = subsampling_dy;
825 /* create the image */
826 image = opj_image_create(numcomps, &cmptparm[0], color_space);
835 /* set image offset and reference grid */
836 image->x0 = parameters->image_offset_x0;
837 image->y0 = parameters->image_offset_y0;
838 image->x1 = !image->x0 ? (w - 1) * subsampling_dx + 1 : image->x0 +
839 (w - 1) * subsampling_dx + 1;
840 image->y1 = !image->y0 ? (h - 1) * subsampling_dy + 1 : image->y0 +
841 (h - 1) * subsampling_dy + 1;
845 RGB = (unsigned char *) malloc(W * H * sizeof(unsigned char));
847 if (fread(RGB, sizeof(unsigned char), W * H, IN) != W * H) {
852 opj_image_destroy(image);
854 "\nError: fread return a number of element different from the expected.\n");
859 for (j = 0; j < W * H; j++) {
860 if ((j % W < W - 1 && Info_h.biWidth % 2) || !(Info_h.biWidth % 2)) {
861 image->comps[0].data[index] =
862 table_R[RGB[W * H - ((j) / (W) + 1) * W + (j) % (W)]];
869 for (j = 0; j < W * H; j++) {
870 if ((j % W < W - 1 && Info_h.biWidth % 2)
871 || !(Info_h.biWidth % 2)) {
872 unsigned char pixel_index =
873 RGB[W * H - ((j) / (W) + 1) * W + (j) % (W)];
874 image->comps[0].data[index] = table_R[pixel_index];
875 image->comps[1].data[index] = table_G[pixel_index];
876 image->comps[2].data[index] = table_B[pixel_index];
886 else if (Info_h.biBitCount == 8 && Info_h.biCompression == 1) { /*RLE8*/
887 unsigned char *pix, *beyond;
888 int *gray, *red, *green, *blue;
889 unsigned int x, y, max;
893 if (Info_h.biClrUsed == 0) {
894 Info_h.biClrUsed = 256;
895 } else if (Info_h.biClrUsed > 256) {
896 Info_h.biClrUsed = 256;
899 table_R = (unsigned char *) malloc(256 * sizeof(unsigned char));
900 table_G = (unsigned char *) malloc(256 * sizeof(unsigned char));
901 table_B = (unsigned char *) malloc(256 * sizeof(unsigned char));
904 for (j = 0; j < Info_h.biClrUsed; j++) {
905 table_B[j] = (unsigned char)getc(IN);
906 table_G[j] = (unsigned char)getc(IN);
907 table_R[j] = (unsigned char)getc(IN);
909 has_color += !(table_R[j] == table_G[j] && table_R[j] == table_B[j]);
916 numcomps = gray_scale ? 1 : 3;
917 color_space = gray_scale ? CLRSPC_GRAY : CLRSPC_SRGB;
918 /* initialize image components */
919 memset(&cmptparm[0], 0, 3 * sizeof(opj_image_cmptparm_t));
920 for (i = 0; i < numcomps; i++) {
921 cmptparm[i].prec = 8;
923 cmptparm[i].sgnd = 0;
924 cmptparm[i].dx = subsampling_dx;
925 cmptparm[i].dy = subsampling_dy;
929 /* create the image */
930 image = opj_image_create(numcomps, &cmptparm[0], color_space);
939 /* set image offset and reference grid */
940 image->x0 = parameters->image_offset_x0;
941 image->y0 = parameters->image_offset_y0;
942 image->x1 = !image->x0 ? (w - 1) * subsampling_dx + 1 : image->x0 + (w
943 - 1) * subsampling_dx + 1;
944 image->y1 = !image->y0 ? (h - 1) * subsampling_dy + 1 : image->y0 + (h
945 - 1) * subsampling_dy + 1;
949 /* Place the cursor at the beginning of the image information */
950 fseek(IN, 0, SEEK_SET);
951 fseek(IN, File_h.bfOffBits, SEEK_SET);
955 RGB = (unsigned char *) calloc(1, W * H * sizeof(unsigned char));
956 beyond = RGB + W * H;
966 for (i = 0; i < c && x < W && pix < beyond; i++, x++, pix++) {
967 *pix = (unsigned char)c1;
972 if (c == 0x00) { /* EOL */
975 pix = RGB + x + (H - y - 1) * W;
976 } else if (c == 0x01) { /* EOP */
978 } else if (c == 0x02) { /* MOVE by dxdy */
983 pix = RGB + (H - y - 1) * W + x;
984 } else { /* 03 .. 255 */
986 for (; i < c && x < W && pix < beyond; i++, x++, pix++) {
988 *pix = (unsigned char)c1;
990 if (c & 1) { /* skip padding byte */
998 gray = image->comps[0].data;
1005 *gray++ = table_R[uc];
1008 /*int *red, *green, *blue;*/
1010 red = image->comps[0].data;
1011 green = image->comps[1].data;
1012 blue = image->comps[2].data;
1019 *red++ = table_R[uc];
1020 *green++ = table_G[uc];
1021 *blue++ = table_B[uc];
1031 "Other system than 24 bits/pixels or 8 bits (no RLE coding) "
1032 "is not yet implemented [%d]\n", Info_h.biBitCount);
1038 int imagetobmp(opj_image_t * image, const char *outfile)
1043 int adjustR, adjustG, adjustB;
1045 if (image->comps[0].prec < 8) {
1046 fprintf(stderr, "Unsupported precision: %d\n", image->comps[0].prec);
1049 if (image->numcomps >= 3 && image->comps[0].dx == image->comps[1].dx
1050 && image->comps[1].dx == image->comps[2].dx
1051 && image->comps[0].dy == image->comps[1].dy
1052 && image->comps[1].dy == image->comps[2].dy
1053 && image->comps[0].prec == image->comps[1].prec
1054 && image->comps[1].prec == image->comps[2].prec) {
1056 /* -->> -->> -->> -->>
1058 <<-- <<-- <<-- <<-- */
1060 fdest = fopen(outfile, "wb");
1062 fprintf(stderr, "ERROR -> failed to open %s for writing\n", outfile);
1066 w = image->comps[0].w;
1067 h = image->comps[0].h;
1069 fprintf(fdest, "BM");
1073 fprintf(fdest, "%c%c%c%c",
1074 (unsigned char)(h * w * 3 + 3 * h * (w % 2) + 54) & 0xff,
1075 (unsigned char)((h * w * 3 + 3 * h * (w % 2) + 54) >> 8) & 0xff,
1076 (unsigned char)((h * w * 3 + 3 * h * (w % 2) + 54) >> 16) & 0xff,
1077 (unsigned char)((h * w * 3 + 3 * h * (w % 2) + 54) >> 24) & 0xff);
1078 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1079 ((0) >> 24) & 0xff);
1080 fprintf(fdest, "%c%c%c%c", (54) & 0xff, ((54) >> 8) & 0xff, ((54) >> 16) & 0xff,
1081 ((54) >> 24) & 0xff);
1085 fprintf(fdest, "%c%c%c%c", (40) & 0xff, ((40) >> 8) & 0xff, ((40) >> 16) & 0xff,
1086 ((40) >> 24) & 0xff);
1087 fprintf(fdest, "%c%c%c%c", (unsigned char)((w) & 0xff),
1088 (unsigned char)((w) >> 8) & 0xff,
1089 (unsigned char)((w) >> 16) & 0xff,
1090 (unsigned char)((w) >> 24) & 0xff);
1091 fprintf(fdest, "%c%c%c%c", (unsigned char)((h) & 0xff),
1092 (unsigned char)((h) >> 8) & 0xff,
1093 (unsigned char)((h) >> 16) & 0xff,
1094 (unsigned char)((h) >> 24) & 0xff);
1095 fprintf(fdest, "%c%c", (1) & 0xff, ((1) >> 8) & 0xff);
1096 fprintf(fdest, "%c%c", (24) & 0xff, ((24) >> 8) & 0xff);
1097 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1098 ((0) >> 24) & 0xff);
1099 fprintf(fdest, "%c%c%c%c", (unsigned char)(3 * h * w + 3 * h * (w % 2)) & 0xff,
1100 (unsigned char)((h * w * 3 + 3 * h * (w % 2)) >> 8) & 0xff,
1101 (unsigned char)((h * w * 3 + 3 * h * (w % 2)) >> 16) & 0xff,
1102 (unsigned char)((h * w * 3 + 3 * h * (w % 2)) >> 24) & 0xff);
1103 fprintf(fdest, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
1104 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
1105 fprintf(fdest, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
1106 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
1107 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1108 ((0) >> 24) & 0xff);
1109 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1110 ((0) >> 24) & 0xff);
1112 if (image->comps[0].prec > 8) {
1113 adjustR = image->comps[0].prec - 8;
1114 printf("BMP CONVERSION: Truncating component 0 from %d bits to 8 bits\n",
1115 image->comps[0].prec);
1119 if (image->comps[1].prec > 8) {
1120 adjustG = image->comps[1].prec - 8;
1121 printf("BMP CONVERSION: Truncating component 1 from %d bits to 8 bits\n",
1122 image->comps[1].prec);
1126 if (image->comps[2].prec > 8) {
1127 adjustB = image->comps[2].prec - 8;
1128 printf("BMP CONVERSION: Truncating component 2 from %d bits to 8 bits\n",
1129 image->comps[2].prec);
1134 for (i = 0; i < w * h; i++) {
1135 unsigned char rc, gc, bc;
1138 r = image->comps[0].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];
1139 r += (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
1140 r = ((r >> adjustR) + ((r >> (adjustR - 1)) % 2));
1146 rc = (unsigned char)r;
1148 g = image->comps[1].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];
1149 g += (image->comps[1].sgnd ? 1 << (image->comps[1].prec - 1) : 0);
1150 g = ((g >> adjustG) + ((g >> (adjustG - 1)) % 2));
1156 gc = (unsigned char)g;
1158 b = image->comps[2].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];
1159 b += (image->comps[2].sgnd ? 1 << (image->comps[2].prec - 1) : 0);
1160 b = ((b >> adjustB) + ((b >> (adjustB - 1)) % 2));
1166 bc = (unsigned char)b;
1168 fprintf(fdest, "%c%c%c", bc, gc, rc);
1170 if ((i + 1) % w == 0) {
1171 for (pad = (3 * w) % 4 ? 4 - (3 * w) % 4 : 0; pad > 0; pad--) { /* ADD */
1172 fprintf(fdest, "%c", 0);
1177 } else { /* Gray-scale */
1179 /* -->> -->> -->> -->>
1180 8 bits non code (Gray scale)
1181 <<-- <<-- <<-- <<-- */
1183 fdest = fopen(outfile, "wb");
1184 w = image->comps[0].w;
1185 h = image->comps[0].h;
1187 fprintf(fdest, "BM");
1191 fprintf(fdest, "%c%c%c%c",
1192 (unsigned char)(h * w + 54 + 1024 + h * (w % 2)) & 0xff,
1193 (unsigned char)((h * w + 54 + 1024 + h * (w % 2)) >> 8) & 0xff,
1194 (unsigned char)((h * w + 54 + 1024 + h * (w % 2)) >> 16) & 0xff,
1195 (unsigned char)((h * w + 54 + 1024 + w * (w % 2)) >> 24) & 0xff);
1196 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1197 ((0) >> 24) & 0xff);
1198 fprintf(fdest, "%c%c%c%c", (54 + 1024) & 0xff, ((54 + 1024) >> 8) & 0xff,
1199 ((54 + 1024) >> 16) & 0xff,
1200 ((54 + 1024) >> 24) & 0xff);
1204 fprintf(fdest, "%c%c%c%c", (40) & 0xff, ((40) >> 8) & 0xff, ((40) >> 16) & 0xff,
1205 ((40) >> 24) & 0xff);
1206 fprintf(fdest, "%c%c%c%c", (unsigned char)((w) & 0xff),
1207 (unsigned char)((w) >> 8) & 0xff,
1208 (unsigned char)((w) >> 16) & 0xff,
1209 (unsigned char)((w) >> 24) & 0xff);
1210 fprintf(fdest, "%c%c%c%c", (unsigned char)((h) & 0xff),
1211 (unsigned char)((h) >> 8) & 0xff,
1212 (unsigned char)((h) >> 16) & 0xff,
1213 (unsigned char)((h) >> 24) & 0xff);
1214 fprintf(fdest, "%c%c", (1) & 0xff, ((1) >> 8) & 0xff);
1215 fprintf(fdest, "%c%c", (8) & 0xff, ((8) >> 8) & 0xff);
1216 fprintf(fdest, "%c%c%c%c", (0) & 0xff, ((0) >> 8) & 0xff, ((0) >> 16) & 0xff,
1217 ((0) >> 24) & 0xff);
1218 fprintf(fdest, "%c%c%c%c", (unsigned char)(h * w + h * (w % 2)) & 0xff,
1219 (unsigned char)((h * w + h * (w % 2)) >> 8) & 0xff,
1220 (unsigned char)((h * w + h * (w % 2)) >> 16) & 0xff,
1221 (unsigned char)((h * w + h * (w % 2)) >> 24) & 0xff);
1222 fprintf(fdest, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
1223 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
1224 fprintf(fdest, "%c%c%c%c", (7834) & 0xff, ((7834) >> 8) & 0xff,
1225 ((7834) >> 16) & 0xff, ((7834) >> 24) & 0xff);
1226 fprintf(fdest, "%c%c%c%c", (256) & 0xff, ((256) >> 8) & 0xff,
1227 ((256) >> 16) & 0xff, ((256) >> 24) & 0xff);
1228 fprintf(fdest, "%c%c%c%c", (256) & 0xff, ((256) >> 8) & 0xff,
1229 ((256) >> 16) & 0xff, ((256) >> 24) & 0xff);
1231 if (image->comps[0].prec > 8) {
1232 adjustR = image->comps[0].prec - 8;
1233 printf("BMP CONVERSION: Truncating component 0 from %d bits to 8 bits\n",
1234 image->comps[0].prec);
1239 for (i = 0; i < 256; i++) {
1240 fprintf(fdest, "%c%c%c%c", i, i, i, 0);
1243 for (i = 0; i < w * h; i++) {
1246 r = image->comps[0].data[w * h - ((i) / (w) + 1) * w + (i) % (w)];
1247 r += (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
1248 r = ((r >> adjustR) + ((r >> (adjustR - 1)) % 2));
1255 fprintf(fdest, "%c", (unsigned char)r);
1257 if ((i + 1) % w == 0) {
1258 for (pad = w % 4 ? 4 - w % 4 : 0; pad > 0; pad--) { /* ADD */
1259 fprintf(fdest, "%c", 0);
1269 /* -->> -->> -->> -->>
1273 <<-- <<-- <<-- <<-- */
1276 static unsigned char readuchar(FILE * f)
1279 if (!fread(&c1, 1, 1, f)) {
1281 "\nError: fread return a number of element different from the expected.\n");
1287 static unsigned short readushort(FILE * f, int bigendian)
1289 unsigned char c1, c2;
1290 if (!fread(&c1, 1, 1, f)) {
1292 "\nError: fread return a number of element different from the expected.\n");
1295 if (!fread(&c2, 1, 1, f)) {
1297 "\nError: fread return a number of element different from the expected.\n");
1301 return (c1 << 8) + c2;
1303 return (c2 << 8) + c1;
1307 static unsigned int readuint(FILE * f, int bigendian)
1309 unsigned char c1, c2, c3, c4;
1310 if (!fread(&c1, 1, 1, f)) {
1312 "\nError: fread return a number of element different from the expected.\n");
1315 if (!fread(&c2, 1, 1, f)) {
1317 "\nError: fread return a number of element different from the expected.\n");
1320 if (!fread(&c3, 1, 1, f)) {
1322 "\nError: fread return a number of element different from the expected.\n");
1325 if (!fread(&c4, 1, 1, f)) {
1327 "\nError: fread return a number of element different from the expected.\n");
1331 return (c1 << 24) + (c2 << 16) + (c3 << 8) + c4;
1333 return (c4 << 24) + (c3 << 16) + (c2 << 8) + c1;
1337 opj_image_t* pgxtoimage(const char *filename, opj_cparameters_t *parameters)
1341 int i, numcomps, max;
1342 OPJ_COLOR_SPACE color_space;
1343 opj_image_cmptparm_t cmptparm; /* maximum of 1 component */
1344 opj_image_t * image = NULL;
1345 int adjustS, ushift, dshift, force8;
1347 char endian1, endian2, sign;
1352 opj_image_comp_t *comp = NULL;
1355 color_space = CLRSPC_GRAY;
1357 memset(&cmptparm, 0, sizeof(opj_image_cmptparm_t));
1361 f = fopen(filename, "rb");
1363 fprintf(stderr, "Failed to open %s for reading !\n", filename);
1367 fseek(f, 0, SEEK_SET);
1368 if (fscanf(f, "PG%31[ \t]%c%c%31[ \t+-]%d%31[ \t]%d%31[ \t]%d", temp, &endian1,
1369 &endian2, signtmp, &prec, temp, &w, temp, &h) != 9) {
1371 "ERROR: Failed to read the right number of element from the fscanf() function!\n");
1378 while (signtmp[i] != '\0') {
1379 if (signtmp[i] == '-') {
1386 if (endian1 == 'M' && endian2 == 'L') {
1388 } else if (endian2 == 'M' && endian1 == 'L') {
1391 fprintf(stderr, "Bad pgx header, please check input file\n");
1396 /* initialize image component */
1398 cmptparm.x0 = parameters->image_offset_x0;
1399 cmptparm.y0 = parameters->image_offset_y0;
1400 cmptparm.w = !cmptparm.x0 ? (w - 1) * parameters->subsampling_dx + 1 :
1401 cmptparm.x0 + (w - 1) * parameters->subsampling_dx + 1;
1402 cmptparm.h = !cmptparm.y0 ? (h - 1) * parameters->subsampling_dy + 1 :
1403 cmptparm.y0 + (h - 1) * parameters->subsampling_dy + 1;
1413 dshift = prec - ushift;
1414 if (cmptparm.sgnd) {
1415 adjustS = (1 << (prec - 1));
1422 ushift = dshift = force8 = adjustS = 0;
1425 cmptparm.prec = prec;
1426 cmptparm.bpp = prec;
1427 cmptparm.dx = parameters->subsampling_dx;
1428 cmptparm.dy = parameters->subsampling_dy;
1430 /* create the image */
1431 image = opj_image_create(numcomps, &cmptparm, color_space);
1436 /* set image offset and reference grid */
1437 image->x0 = cmptparm.x0;
1438 image->y0 = cmptparm.x0;
1439 image->x1 = cmptparm.w;
1440 image->y1 = cmptparm.h;
1442 /* set image data */
1444 comp = &image->comps[0];
1446 for (i = 0; i < w * h; i++) {
1449 v = readuchar(f) + adjustS;
1450 v = (v << ushift) + (v >> dshift);
1451 comp->data[i] = (unsigned char)v;
1459 if (comp->prec == 8) {
1463 v = (char) readuchar(f);
1465 } else if (comp->prec <= 16) {
1467 v = readushort(f, bigendian);
1469 v = (short) readushort(f, bigendian);
1473 v = readuint(f, bigendian);
1475 v = (int) readuint(f, bigendian);
1484 comp->bpp = int_floorlog2(max) + 1;
1489 int imagetopgx(opj_image_t * image, const char *outfile)
1495 for (compno = 0; compno < image->numcomps; compno++) {
1496 opj_image_comp_t *comp = &image->comps[compno];
1497 char bname[256]; /* buffer for name */
1498 char *name = bname; /* pointer */
1501 const size_t olen = strlen(outfile);
1502 const size_t dotpos = olen - 4;
1503 const size_t total = dotpos + 1 + 1 + 4; /* '-' + '[1-3]' + '.pgx' */
1504 if (outfile[dotpos] != '.') {
1505 /* `pgx` was recognized but there is no dot at expected position */
1506 fprintf(stderr, "ERROR -> Impossible happen.");
1510 name = (char*)malloc(total + 1);
1512 strncpy(name, outfile, dotpos);
1513 /*if (image->numcomps > 1) {*/
1514 sprintf(name + dotpos, "_%d.pgx", compno);
1516 strcpy(name+dotpos, ".pgx");
1518 fdest = fopen(name, "wb");
1520 fprintf(stderr, "ERROR -> failed to open %s for writing\n", name);
1523 /* don't need name anymore */
1528 w = image->comps[compno].w;
1529 h = image->comps[compno].h;
1531 fprintf(fdest, "PG ML %c %d %d %d\n", comp->sgnd ? '-' : '+', comp->prec, w, h);
1532 if (comp->prec <= 8) {
1534 } else if (comp->prec <= 16) {
1539 for (i = 0; i < w * h; i++) {
1540 int v = image->comps[compno].data[i];
1541 for (j = nbytes - 1; j >= 0; j--) {
1542 char byte = (char)(v >> (j * 8));
1543 res = fwrite(&byte, 1, 1, fdest);
1545 fprintf(stderr, "failed to write 1 byte for %s\n", name);
1557 /* -->> -->> -->> -->>
1561 <<-- <<-- <<-- <<-- */
1564 int width, height, maxval, depth, format;
1565 char rgb, rgba, gray, graya, bw;
1569 static char *skip_white(char *s)
1572 if (*s == '\n' || *s == '\r') {
1584 static char *skip_int(char *start, int *out_n)
1592 s = skip_white(start);
1606 *out_n = atoi(start);
1611 static char *skip_idf(char *start, char out_idf[256])
1616 s = skip_white(start);
1623 if (isalpha(*s) || *s == '_') {
1631 strncpy(out_idf, start, 255);
1636 static void read_pnm_header(FILE *reader, struct pnm_header *ph)
1639 int format, have_wh, end, ttype;
1640 char idf[256], type[256];
1643 if (fgets(line, 250, reader) == NULL) {
1644 fprintf(stderr, "\nWARNING: fgets return a NULL value");
1648 if (line[0] != 'P') {
1649 fprintf(stderr, "read_pnm_header:PNM:magic P missing\n");
1652 format = atoi(line + 1);
1653 if (format < 1 || format > 7) {
1654 fprintf(stderr, "read_pnm_header:magic format %d invalid\n", format);
1657 ph->format = format;
1658 ttype = end = have_wh = 0;
1660 while (fgets(line, 250, reader)) {
1668 s = skip_idf(s, idf);
1670 if (s == NULL || *s == 0) {
1674 if (strcmp(idf, "ENDHDR") == 0) {
1678 if (strcmp(idf, "WIDTH") == 0) {
1679 s = skip_int(s, &ph->width);
1680 if (s == NULL || *s == 0) {
1686 if (strcmp(idf, "HEIGHT") == 0) {
1687 s = skip_int(s, &ph->height);
1688 if (s == NULL || *s == 0) {
1694 if (strcmp(idf, "DEPTH") == 0) {
1695 s = skip_int(s, &ph->depth);
1696 if (s == NULL || *s == 0) {
1702 if (strcmp(idf, "MAXVAL") == 0) {
1703 s = skip_int(s, &ph->maxval);
1704 if (s == NULL || *s == 0) {
1710 if (strcmp(idf, "TUPLTYPE") == 0) {
1711 s = skip_idf(s, type);
1712 if (s == NULL || *s == 0) {
1716 if (strcmp(type, "BLACKANDWHITE") == 0) {
1721 if (strcmp(type, "GRAYSCALE") == 0) {
1726 if (strcmp(type, "GRAYSCALE_ALPHA") == 0) {
1731 if (strcmp(type, "RGB") == 0) {
1736 if (strcmp(type, "RGB_ALPHA") == 0) {
1741 fprintf(stderr, "read_pnm_header:unknown P7 TUPLTYPE %s\n", type);
1744 fprintf(stderr, "read_pnm_header:unknown P7 idf %s\n", idf);
1746 } /* if(format == 7) */
1749 s = skip_int(s, &ph->width);
1751 s = skip_int(s, &ph->height);
1755 if (format == 1 || format == 4) {
1761 if (format == 2 || format == 3 || format == 5 || format == 6) {
1762 /* P2, P3, P5, P6: */
1763 s = skip_int(s, &ph->maxval);
1765 if (ph->maxval > 65535) {
1770 }/* while(fgets( ) */
1771 if (format == 2 || format == 3 || format > 4) {
1772 if (ph->maxval < 1 || ph->maxval > 65535) {
1776 if (ph->width < 1 || ph->height < 1) {
1782 fprintf(stderr, "read_pnm_header:P7 without ENDHDR\n");
1785 if (ph->depth < 1 || ph->depth > 4) {
1789 if (ph->width && ph->height && ph->depth & ph->maxval && ttype) {
1793 if (format != 1 && format != 4) {
1794 if (ph->width && ph->height && ph->maxval) {
1798 if (ph->width && ph->height) {
1806 static int has_prec(int val)
1856 opj_image_t* pnmtoimage(const char *filename, opj_cparameters_t *parameters)
1858 int subsampling_dx = parameters->subsampling_dx;
1859 int subsampling_dy = parameters->subsampling_dy;
1862 int i, compno, numcomps, w, h, prec, format;
1863 OPJ_COLOR_SPACE color_space;
1864 opj_image_cmptparm_t cmptparm[4]; /* RGBA: max. 4 components */
1865 opj_image_t * image = NULL;
1866 struct pnm_header header_info;
1868 if ((fp = fopen(filename, "rb")) == NULL) {
1869 fprintf(stderr, "pnmtoimage:Failed to open %s for reading!\n", filename);
1872 memset(&header_info, 0, sizeof(struct pnm_header));
1874 read_pnm_header(fp, &header_info);
1876 if (!header_info.ok) {
1881 /* This limitation could be removed by making sure to use size_t below */
1882 if (header_info.height != 0 &&
1883 header_info.width > INT_MAX / header_info.height) {
1884 fprintf(stderr, "pnmtoimage:Image %dx%d too big!\n",
1885 header_info.width, header_info.height);
1890 format = header_info.format;
1893 case 1: /* ascii bitmap */
1894 case 4: /* raw bitmap */
1898 case 2: /* ascii greymap */
1899 case 5: /* raw greymap */
1903 case 3: /* ascii pixmap */
1904 case 6: /* raw pixmap */
1908 case 7: /* arbitrary map */
1909 numcomps = header_info.depth;
1917 color_space = CLRSPC_GRAY; /* GRAY, GRAYA */
1919 color_space = CLRSPC_SRGB; /* RGB, RGBA */
1922 prec = has_prec(header_info.maxval);
1928 w = header_info.width;
1929 h = header_info.height;
1930 subsampling_dx = parameters->subsampling_dx;
1931 subsampling_dy = parameters->subsampling_dy;
1933 memset(&cmptparm[0], 0, numcomps * sizeof(opj_image_cmptparm_t));
1935 for (i = 0; i < numcomps; i++) {
1936 cmptparm[i].prec = prec;
1937 cmptparm[i].bpp = prec;
1938 cmptparm[i].sgnd = 0;
1939 cmptparm[i].dx = subsampling_dx;
1940 cmptparm[i].dy = subsampling_dy;
1944 image = opj_image_create(numcomps, &cmptparm[0], color_space);
1951 /* set image offset and reference grid */
1952 image->x0 = parameters->image_offset_x0;
1953 image->y0 = parameters->image_offset_y0;
1954 image->x1 = parameters->image_offset_x0 + (w - 1) * subsampling_dx + 1;
1955 image->y1 = parameters->image_offset_y0 + (h - 1) * subsampling_dy + 1;
1957 if ((format == 2) || (format == 3)) { /* ascii pixmap */
1960 for (i = 0; i < w * h; i++) {
1961 for (compno = 0; compno < numcomps; compno++) {
1963 if (fscanf(fp, "%u", &index) != 1) {
1965 "\nWARNING: fscanf return a number of element different from the expected.\n");
1968 image->comps[compno].data[i] = (index * 255) / header_info.maxval;
1971 } else if ((format == 5)
1974 && (header_info.gray || header_info.graya
1975 || header_info.rgb || header_info.rgba))) { /* binary pixmap */
1976 unsigned char c0, c1, one;
1980 for (i = 0; i < w * h; i++) {
1981 for (compno = 0; compno < numcomps; compno++) {
1982 if (!fread(&c0, 1, 1, fp)) {
1984 "\nError: fread return a number of element different from the expected.\n");
1987 image->comps[compno].data[i] = c0;
1989 if (!fread(&c1, 1, 1, fp)) {
1991 "\nError: fread return a number of element different from the expected.\n");
1994 image->comps[compno].data[i] = ((c0 << 8) | c1);
1998 } else if (format == 1) { /* ascii bitmap */
1999 for (i = 0; i < w * h; i++) {
2002 if (fscanf(fp, "%u", &index) != 1) {
2004 "\nWARNING: fscanf return a number of element different from the expected.\n");
2007 image->comps[0].data[i] = (index ? 0 : 255);
2009 } else if (format == 4) {
2014 for (y = 0; y < h; ++y) {
2018 for (x = 0; x < w; ++x) {
2021 uc = (unsigned char)getc(fp);
2023 image->comps[0].data[i] = (((uc >> bit) & 1) ? 0 : 255);
2028 } else if ((format == 7 && header_info.bw)) { /*MONO*/
2031 for (i = 0; i < w * h; ++i) {
2032 if (!fread(&uc, 1, 1, fp)) {
2034 "\nError: fread return a number of element different from the expected.\n");
2036 image->comps[0].data[i] = (uc & 1) ? 0 : 255;
2044 int imagetopnm(opj_image_t * image, const char *outfile)
2046 int *red, *green, *blue, *alpha;
2048 int i, compno, ncomp;
2049 int adjustR, adjustG, adjustB, adjustA;
2050 int fails, two, want_gray, has_alpha, triple;
2053 const char *tmp = outfile;
2056 if ((prec = image->comps[0].prec) > 16) {
2057 fprintf(stderr, "%s:%d:imagetopnm\n\tprecision %d is larger than 16"
2058 "\n\t: refused.\n", __FILE__, __LINE__, prec);
2061 two = has_alpha = 0;
2063 ncomp = image->numcomps;
2069 want_gray = (*tmp == 'g' || *tmp == 'G');
2070 ncomp = image->numcomps;
2076 if (ncomp == 2 /* GRAYA */
2077 || (ncomp > 2 /* RGB, RGBA */
2078 && image->comps[0].dx == image->comps[1].dx
2079 && image->comps[1].dx == image->comps[2].dx
2080 && image->comps[0].dy == image->comps[1].dy
2081 && image->comps[1].dy == image->comps[2].dy
2082 && image->comps[0].prec == image->comps[1].prec
2083 && image->comps[1].prec == image->comps[2].prec
2085 fdest = fopen(outfile, "wb");
2088 fprintf(stderr, "ERROR -> failed to open %s for writing\n", outfile);
2092 triple = (ncomp > 2);
2093 wr = image->comps[0].w;
2094 hr = image->comps[0].h;
2095 max = (1 << prec) - 1;
2096 has_alpha = (ncomp == 4 || ncomp == 2);
2098 red = image->comps[0].data;
2101 green = image->comps[1].data;
2102 blue = image->comps[2].data;
2104 green = blue = NULL;
2108 const char *tt = (triple ? "RGB_ALPHA" : "GRAYSCALE_ALPHA");
2110 fprintf(fdest, "P7\n# OpenJPEG-%s\nWIDTH %d\nHEIGHT %d\nDEPTH %d\n"
2111 "MAXVAL %d\nTUPLTYPE %s\nENDHDR\n", opj_version(),
2112 wr, hr, ncomp, max, tt);
2113 alpha = image->comps[ncomp - 1].data;
2114 adjustA = (image->comps[ncomp - 1].sgnd ?
2115 1 << (image->comps[ncomp - 1].prec - 1) : 0);
2117 fprintf(fdest, "P6\n# OpenJPEG-%s\n%d %d\n%d\n",
2118 opj_version(), wr, hr, max);
2121 adjustR = (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
2124 adjustG = (image->comps[1].sgnd ? 1 << (image->comps[1].prec - 1) : 0);
2125 adjustB = (image->comps[2].sgnd ? 1 << (image->comps[2].prec - 1) : 0);
2127 adjustG = adjustB = 0;
2130 for (i = 0; i < wr * hr; ++i) {
2135 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2138 v = *green + adjustG;
2141 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2143 v = *blue + adjustB;
2146 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2151 v = *alpha + adjustA;
2154 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2162 fprintf(fdest, "%c", (unsigned char)*red++);
2164 fprintf(fdest, "%c%c", (unsigned char)*green++, (unsigned char)*blue++);
2168 fprintf(fdest, "%c", (unsigned char)*alpha++);
2179 if (image->numcomps > ncomp) {
2180 fprintf(stderr, "WARNING -> [PGM file] Only the first component\n");
2181 fprintf(stderr, " is written to the file\n");
2183 destname = (char*)malloc(strlen(outfile) + 8);
2185 for (compno = 0; compno < ncomp; compno++) {
2187 sprintf(destname, "%d.%s", compno, outfile);
2189 sprintf(destname, "%s", outfile);
2192 fdest = fopen(destname, "wb");
2194 fprintf(stderr, "ERROR -> failed to open %s for writing\n", destname);
2198 wr = image->comps[compno].w;
2199 hr = image->comps[compno].h;
2200 prec = image->comps[compno].prec;
2201 max = (1 << prec) - 1;
2203 fprintf(fdest, "P5\n#OpenJPEG-%s\n%d %d\n%d\n",
2204 opj_version(), wr, hr, max);
2206 red = image->comps[compno].data;
2208 (image->comps[compno].sgnd ? 1 << (image->comps[compno].prec - 1) : 0);
2211 for (i = 0; i < wr * hr; i++) {
2215 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2220 fprintf(fdest, "%c%c", (unsigned char)(v >> 8), (unsigned char)v);
2223 } else { /* prec <= 8 */
2224 for (i = 0; i < wr * hr; ++i) {
2225 fprintf(fdest, "%c", (unsigned char)(*red + adjustR));
2236 #ifdef OPJ_HAVE_LIBTIFF
2237 /* -->> -->> -->> -->>
2241 <<-- <<-- <<-- <<-- */
2243 int imagetotif(opj_image_t * image, const char *outfile)
2245 int width, height, imgsize;
2246 int bps, index, adjust, sgnd;
2247 int ushift, dshift, has_alpha, force16;
2253 ushift = dshift = force16 = has_alpha = 0;
2254 bps = image->comps[0].prec;
2256 if (bps > 8 && bps < 16) {
2258 dshift = bps - ushift;
2263 if (bps != 8 && bps != 16) {
2264 fprintf(stderr, "imagetotif: Bits=%d, Only 8 and 16 bits implemented\n",
2266 fprintf(stderr, "\tAborting\n");
2269 tif = TIFFOpen(outfile, "wb");
2272 fprintf(stderr, "imagetotif:failed to open %s for writing\n", outfile);
2275 sgnd = image->comps[0].sgnd;
2276 adjust = sgnd ? 1 << (image->comps[0].prec - 1) : 0;
2278 if (image->numcomps >= 3
2279 && image->comps[0].dx == image->comps[1].dx
2280 && image->comps[1].dx == image->comps[2].dx
2281 && image->comps[0].dy == image->comps[1].dy
2282 && image->comps[1].dy == image->comps[2].dy
2283 && image->comps[0].prec == image->comps[1].prec
2284 && image->comps[1].prec == image->comps[2].prec) {
2285 has_alpha = (image->numcomps == 4);
2287 width = image->comps[0].w;
2288 height = image->comps[0].h;
2289 imgsize = width * height ;
2291 TIFFSetField(tif, TIFFTAG_IMAGEWIDTH, width);
2292 TIFFSetField(tif, TIFFTAG_IMAGELENGTH, height);
2293 TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, 3 + has_alpha);
2294 TIFFSetField(tif, TIFFTAG_BITSPERSAMPLE, bps);
2295 TIFFSetField(tif, TIFFTAG_ORIENTATION, ORIENTATION_TOPLEFT);
2296 TIFFSetField(tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG);
2297 TIFFSetField(tif, TIFFTAG_PHOTOMETRIC, PHOTOMETRIC_RGB);
2298 TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, 1);
2299 strip_size = TIFFStripSize(tif);
2300 buf = _TIFFmalloc(strip_size);
2303 for (strip = 0; strip < TIFFNumberOfStrips(tif); strip++) {
2304 unsigned char *dat8;
2305 tsize_t i, ssize, last_i = 0;
2307 ssize = TIFFStripSize(tif);
2308 dat8 = (unsigned char*)buf;
2311 step = 3 + has_alpha;
2314 for (i = 0; i < ssize - restx; i += step) {
2317 if (index < imgsize) {
2318 r = image->comps[0].data[index];
2319 g = image->comps[1].data[index];
2320 b = image->comps[2].data[index];
2322 a = image->comps[3].data[index];
2347 if (last_i < ssize) {
2348 for (i = last_i; i < ssize; i += step) {
2351 if (index < imgsize) {
2352 r = image->comps[0].data[index];
2353 g = image->comps[1].data[index];
2354 b = image->comps[2].data[index];
2356 a = image->comps[3].data[index];
2368 if (i + 1 < ssize) {
2373 if (i + 2 < ssize) {
2379 if (i + 3 < ssize) {
2390 }/*if(last_i < ssize)*/
2393 else if (bps == 16) {
2394 step = 6 + has_alpha + has_alpha;
2397 for (i = 0; i < ssize - restx ; i += step) {
2400 if (index < imgsize) {
2401 r = image->comps[0].data[index];
2402 g = image->comps[1].data[index];
2403 b = image->comps[2].data[index];
2405 a = image->comps[3].data[index];
2417 r = (r << ushift) + (r >> dshift);
2418 g = (g << ushift) + (g >> dshift);
2419 b = (b << ushift) + (b >> dshift);
2421 a = (a << ushift) + (a >> dshift);
2424 dat8[i + 0] = r; /*LSB*/
2425 dat8[i + 1] = (r >> 8); /*MSB*/
2427 dat8[i + 3] = (g >> 8);
2429 dat8[i + 5] = (b >> 8);
2432 dat8[i + 7] = (a >> 8);
2441 if (last_i < ssize) {
2442 for (i = last_i ; i < ssize ; i += step) {
2445 if (index < imgsize) {
2446 r = image->comps[0].data[index];
2447 g = image->comps[1].data[index];
2448 b = image->comps[2].data[index];
2450 a = image->comps[3].data[index];
2462 r = (r << ushift) + (r >> dshift);
2463 g = (g << ushift) + (g >> dshift);
2464 b = (b << ushift) + (b >> dshift);
2466 a = (a << ushift) + (a >> dshift);
2469 dat8[i + 0] = r; /*LSB*/
2470 if (i + 1 < ssize) {
2471 dat8[i + 1] = (r >> 8);
2475 if (i + 2 < ssize) {
2480 if (i + 3 < ssize) {
2481 dat8[i + 3] = (g >> 8);
2485 if (i + 4 < ssize) {
2490 if (i + 5 < ssize) {
2491 dat8[i + 5] = (b >> 8);
2497 if (i + 6 < ssize) {
2502 if (i + 7 < ssize) {
2503 dat8[i + 7] = (a >> 8);
2513 }/*if(last_i < ssize)*/
2516 (void)TIFFWriteEncodedStrip(tif, strip, (void*)buf, strip_size);
2517 }/*for(strip = 0; )*/
2519 _TIFFfree((void*)buf);
2525 if (image->numcomps == 1 /* GRAY */
2526 || (image->numcomps == 2 /* GRAY_ALPHA */
2527 && image->comps[0].dx == image->comps[1].dx
2528 && image->comps[0].dy == image->comps[1].dy
2529 && image->comps[0].prec == image->comps[1].prec)) {
2532 has_alpha = (image->numcomps == 2);
2534 width = image->comps[0].w;
2535 height = image->comps[0].h;
2536 imgsize = width * height;
2539 TIFFSetField(tif, TIFFTAG_IMAGEWIDTH, width);
2540 TIFFSetField(tif, TIFFTAG_IMAGELENGTH, height);
2541 TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, 1 + has_alpha);
2542 TIFFSetField(tif, TIFFTAG_BITSPERSAMPLE, bps);
2543 TIFFSetField(tif, TIFFTAG_ORIENTATION, ORIENTATION_TOPLEFT);
2544 TIFFSetField(tif, TIFFTAG_PLANARCONFIG, PLANARCONFIG_CONTIG);
2545 TIFFSetField(tif, TIFFTAG_PHOTOMETRIC, PHOTOMETRIC_MINISBLACK);
2546 TIFFSetField(tif, TIFFTAG_ROWSPERSTRIP, 1);
2548 /* Get a buffer for the data */
2549 strip_size = TIFFStripSize(tif);
2550 buf = _TIFFmalloc(strip_size);
2553 for (strip = 0; strip < TIFFNumberOfStrips(tif); strip++) {
2554 unsigned char *dat8;
2555 tsize_t i, ssize = TIFFStripSize(tif);
2556 dat8 = (unsigned char*)buf;
2559 step = 1 + has_alpha;
2561 for (i = 0; i < ssize; i += step) {
2562 if (index < imgsize) {
2565 r = image->comps[0].data[index];
2567 a = image->comps[1].data[index];
2586 else if (bps == 16) {
2587 step = 2 + has_alpha + has_alpha;
2589 for (i = 0; i < ssize; i += step) {
2590 if (index < imgsize) {
2593 r = image->comps[0].data[index];
2595 a = image->comps[1].data[index];
2605 r = (r << ushift) + (r >> dshift);
2607 a = (a << ushift) + (a >> dshift);
2610 dat8[i + 0] = r; /*LSB*/
2611 dat8[i + 1] = r >> 8; /*MSB*/
2614 dat8[i + 3] = a >> 8;
2617 }/*if(index < imgsize)*/
2623 (void)TIFFWriteEncodedStrip(tif, strip, (void*)buf, strip_size);
2634 fprintf(stderr, "imagetotif: Bad color format.\n"
2635 "\tOnly RGB(A) and GRAY(A) has been implemented\n");
2636 fprintf(stderr, "\tFOUND: numcomps(%d)\n\tAborting\n",
2643 * libtiff/tif_getimage.c : 1,2,4,8,16 bitspersample accepted
2644 * CINEMA : 12 bit precision
2646 opj_image_t* tiftoimage(const char *filename, opj_cparameters_t *parameters)
2648 int subsampling_dx = parameters->subsampling_dx;
2649 int subsampling_dy = parameters->subsampling_dy;
2654 int j, numcomps, w, h, index;
2655 OPJ_COLOR_SPACE color_space;
2656 opj_image_cmptparm_t cmptparm[4]; /* RGBA */
2657 opj_image_t *image = NULL;
2660 unsigned short tiBps, tiPhoto, tiSf, tiSpp, tiPC;
2661 unsigned int tiWidth, tiHeight;
2663 tif = TIFFOpen(filename, "r");
2666 fprintf(stderr, "tiftoimage:Failed to open %s for reading\n", filename);
2669 tiBps = tiPhoto = tiSf = tiSpp = tiPC = 0;
2670 tiWidth = tiHeight = 0;
2672 TIFFGetField(tif, TIFFTAG_IMAGEWIDTH, &tiWidth);
2673 TIFFGetField(tif, TIFFTAG_IMAGELENGTH, &tiHeight);
2674 TIFFGetField(tif, TIFFTAG_BITSPERSAMPLE, &tiBps);
2675 TIFFGetField(tif, TIFFTAG_SAMPLEFORMAT, &tiSf);
2676 TIFFGetField(tif, TIFFTAG_SAMPLESPERPIXEL, &tiSpp);
2677 TIFFGetField(tif, TIFFTAG_PHOTOMETRIC, &tiPhoto);
2678 TIFFGetField(tif, TIFFTAG_PLANARCONFIG, &tiPC);
2683 unsigned short b = tiBps, p = tiPhoto;
2685 if (tiBps != 8 && tiBps != 16 && tiBps != 12) {
2688 if (tiPhoto != 1 && tiPhoto != 2) {
2694 fprintf(stderr, "imagetotif: Bits=%d, Only 8 and 16 bits"
2695 " implemented\n", tiBps);
2697 fprintf(stderr, "tiftoimage: Bad color format %d.\n\tOnly RGB(A)"
2698 " and GRAY(A) has been implemented\n", (int) tiPhoto);
2700 fprintf(stderr, "\tAborting\n");
2706 {/* From: tiff-4.0.x/libtiff/tif_getimage.c : */
2708 uint16 extrasamples;
2710 TIFFGetFieldDefaulted(tif, TIFFTAG_EXTRASAMPLES,
2711 &extrasamples, &sampleinfo);
2713 if (extrasamples >= 1) {
2714 switch (sampleinfo[0]) {
2715 case EXTRASAMPLE_UNSPECIFIED:
2716 /* Workaround for some images without correct info about alpha channel
2723 case EXTRASAMPLE_ASSOCALPHA: /* data pre-multiplied */
2724 case EXTRASAMPLE_UNASSALPHA: /* data not pre-multiplied */
2728 } else /* extrasamples == 0 */
2729 if (tiSpp == 4 || tiSpp == 2) {
2734 /* initialize image components
2736 memset(&cmptparm[0], 0, 4 * sizeof(opj_image_cmptparm_t));
2738 if (tiPhoto == PHOTOMETRIC_RGB) { /* RGB(A) */
2739 numcomps = 3 + has_alpha;
2740 color_space = CLRSPC_SRGB;
2742 for (j = 0; j < numcomps; j++) {
2743 if (parameters->cp_cinema) {
2744 cmptparm[j].prec = 12;
2745 cmptparm[j].bpp = 12;
2747 cmptparm[j].prec = tiBps;
2748 cmptparm[j].bpp = tiBps;
2750 cmptparm[j].dx = subsampling_dx;
2751 cmptparm[j].dy = subsampling_dy;
2756 image = opj_image_create(numcomps, &cmptparm[0], color_space);
2762 /* set image offset and reference grid
2764 image->x0 = parameters->image_offset_x0;
2765 image->y0 = parameters->image_offset_y0;
2766 image->x1 = !image->x0 ? (w - 1) * subsampling_dx + 1 :
2767 image->x0 + (w - 1) * subsampling_dx + 1;
2768 image->y1 = !image->y0 ? (h - 1) * subsampling_dy + 1 :
2769 image->y0 + (h - 1) * subsampling_dy + 1;
2771 buf = _TIFFmalloc(TIFFStripSize(tif));
2773 strip_size = TIFFStripSize(tif);
2775 imgsize = image->comps[0].w * image->comps[0].h ;
2776 /* Read the Image components
2778 for (strip = 0; strip < TIFFNumberOfStrips(tif); strip++) {
2779 unsigned char *dat8;
2782 ssize = TIFFReadEncodedStrip(tif, strip, buf, strip_size);
2783 dat8 = (unsigned char*)buf;
2786 step = 6 + has_alpha + has_alpha;
2788 for (i = 0; i < ssize; i += step) {
2789 if (index < imgsize) {
2790 image->comps[0].data[index] = (dat8[i + 1] << 8) | dat8[i + 0]; /* R */
2791 image->comps[1].data[index] = (dat8[i + 3] << 8) | dat8[i + 2]; /* G */
2792 image->comps[2].data[index] = (dat8[i + 5] << 8) | dat8[i + 4]; /* B */
2794 image->comps[3].data[index] = (dat8[i + 7] << 8) | dat8[i + 6];
2797 if (parameters->cp_cinema) {
2798 /* Rounding 16 to 12 bits
2800 image->comps[0].data[index] =
2801 (image->comps[0].data[index] + 0x08) >> 4 ;
2802 image->comps[1].data[index] =
2803 (image->comps[1].data[index] + 0x08) >> 4 ;
2804 image->comps[2].data[index] =
2805 (image->comps[2].data[index] + 0x08) >> 4 ;
2807 image->comps[3].data[index] =
2808 (image->comps[3].data[index] + 0x08) >> 4 ;
2815 }/*if(tiBps == 16)*/
2816 else if (tiBps == 8) {
2817 step = 3 + has_alpha;
2819 for (i = 0; i < ssize; i += step) {
2820 if (index < imgsize) {
2821 image->comps[0].data[index] = dat8[i + 0]; /* R */
2822 image->comps[1].data[index] = dat8[i + 1]; /* G */
2823 image->comps[2].data[index] = dat8[i + 2]; /* B */
2825 image->comps[3].data[index] = dat8[i + 3];
2828 if (parameters->cp_cinema) {
2829 /* Rounding 8 to 12 bits
2831 image->comps[0].data[index] = image->comps[0].data[index] << 4 ;
2832 image->comps[1].data[index] = image->comps[1].data[index] << 4 ;
2833 image->comps[2].data[index] = image->comps[2].data[index] << 4 ;
2835 image->comps[3].data[index] = image->comps[3].data[index] << 4 ;
2844 }/*if( tiBps == 8)*/
2845 else if (tiBps == 12) { /* CINEMA file */
2848 for (i = 0; i < ssize; i += step) {
2849 if ((index < imgsize) & (index + 1 < imgsize)) {
2850 image->comps[0].data[index] = (dat8[i + 0] << 4) | (dat8[i + 1] >> 4);
2851 image->comps[1].data[index] = ((dat8[i + 1] & 0x0f) << 8) | dat8[i + 2];
2853 image->comps[2].data[index] = (dat8[i + 3] << 4) | (dat8[i + 4] >> 4);
2854 image->comps[0].data[index + 1] = ((dat8[i + 4] & 0x0f) << 8) | dat8[i + 5];
2856 image->comps[1].data[index + 1] = (dat8[i + 6] << 4) |
2858 image->comps[2].data[index + 1] = ((dat8[i + 7] & 0x0f) << 8) | dat8[i + 8];
2866 }/*for(strip = 0; )*/
2874 if (tiPhoto == PHOTOMETRIC_MINISBLACK) { /* GRAY(A) */
2875 numcomps = 1 + has_alpha;
2876 color_space = CLRSPC_GRAY;
2878 for (j = 0; j < numcomps; ++j) {
2879 cmptparm[j].prec = tiBps;
2880 cmptparm[j].bpp = tiBps;
2881 cmptparm[j].dx = subsampling_dx;
2882 cmptparm[j].dy = subsampling_dy;
2886 image = opj_image_create(numcomps, &cmptparm[0], color_space);
2892 /* set image offset and reference grid
2894 image->x0 = parameters->image_offset_x0;
2895 image->y0 = parameters->image_offset_y0;
2896 image->x1 = !image->x0 ? (w - 1) * subsampling_dx + 1 :
2897 image->x0 + (w - 1) * subsampling_dx + 1;
2898 image->y1 = !image->y0 ? (h - 1) * subsampling_dy + 1 :
2899 image->y0 + (h - 1) * subsampling_dy + 1;
2901 buf = _TIFFmalloc(TIFFStripSize(tif));
2903 strip_size = TIFFStripSize(tif);
2905 imgsize = image->comps[0].w * image->comps[0].h ;
2906 /* Read the Image components
2908 for (strip = 0; strip < TIFFNumberOfStrips(tif); strip++) {
2909 unsigned char *dat8;
2913 ssize = TIFFReadEncodedStrip(tif, strip, buf, strip_size);
2914 dat8 = (unsigned char*)buf;
2917 step = 2 + has_alpha + has_alpha;
2919 for (i = 0; i < ssize; i += step) {
2920 if (index < imgsize) {
2921 image->comps[0].data[index] = (dat8[i + 1] << 8) | dat8[i + 0];
2923 image->comps[1].data[index] = (dat8[i + 3] << 8) | dat8[i + 2];
2930 } else if (tiBps == 8) {
2931 step = 1 + has_alpha;
2933 for (i = 0; i < ssize; i += step) {
2934 if (index < imgsize) {
2935 image->comps[0].data[index] = dat8[i + 0];
2937 image->comps[1].data[index] = dat8[i + 1];
2956 #endif /* OPJ_HAVE_LIBTIFF */
2958 /* -->> -->> -->> -->>
2962 <<-- <<-- <<-- <<-- */
2964 opj_image_t* rawtoimage(const char *filename, opj_cparameters_t *parameters,
2965 raw_cparameters_t *raw_cp)
2967 int subsampling_dx = parameters->subsampling_dx;
2968 int subsampling_dy = parameters->subsampling_dy;
2971 int i, compno, numcomps, w, h;
2972 OPJ_COLOR_SPACE color_space;
2973 opj_image_cmptparm_t *cmptparm;
2974 opj_image_t * image = NULL;
2977 if ((!(raw_cp->rawWidth & raw_cp->rawHeight & raw_cp->rawComp &
2978 raw_cp->rawBitDepth)) == 0) {
2979 fprintf(stderr, "\nError: invalid raw image parameters\n");
2980 fprintf(stderr, "Please use the Format option -F:\n");
2982 "-F rawWidth,rawHeight,rawComp,rawBitDepth,s/u (Signed/Unsigned)\n");
2983 fprintf(stderr, "Example: -i lena.raw -o lena.j2k -F 512,512,3,8,u\n");
2984 fprintf(stderr, "Aborting\n");
2988 f = fopen(filename, "rb");
2990 fprintf(stderr, "Failed to open %s for reading !!\n", filename);
2991 fprintf(stderr, "Aborting\n");
2994 numcomps = raw_cp->rawComp;
2995 color_space = CLRSPC_SRGB;
2996 w = raw_cp->rawWidth;
2997 h = raw_cp->rawHeight;
2998 cmptparm = (opj_image_cmptparm_t*) malloc(numcomps * sizeof(
2999 opj_image_cmptparm_t));
3001 /* initialize image components */
3002 memset(&cmptparm[0], 0, numcomps * sizeof(opj_image_cmptparm_t));
3003 for (i = 0; i < numcomps; i++) {
3004 cmptparm[i].prec = raw_cp->rawBitDepth;
3005 cmptparm[i].bpp = raw_cp->rawBitDepth;
3006 cmptparm[i].sgnd = raw_cp->rawSigned;
3007 cmptparm[i].dx = subsampling_dx;
3008 cmptparm[i].dy = subsampling_dy;
3012 /* create the image */
3013 image = opj_image_create(numcomps, &cmptparm[0], color_space);
3018 /* set image offset and reference grid */
3019 image->x0 = parameters->image_offset_x0;
3020 image->y0 = parameters->image_offset_y0;
3021 image->x1 = parameters->image_offset_x0 + (w - 1) * subsampling_dx + 1;
3022 image->y1 = parameters->image_offset_y0 + (h - 1) * subsampling_dy + 1;
3024 if (raw_cp->rawBitDepth <= 8) {
3025 unsigned char value = 0;
3026 for (compno = 0; compno < numcomps; compno++) {
3027 for (i = 0; i < w * h; i++) {
3028 if (!fread(&value, 1, 1, f)) {
3029 fprintf(stderr, "Error reading raw file. End of file probably reached.\n");
3033 image->comps[compno].data[i] = raw_cp->rawSigned ? (char)value : value;
3036 } else if (raw_cp->rawBitDepth <= 16) {
3037 unsigned short value;
3038 for (compno = 0; compno < numcomps; compno++) {
3039 for (i = 0; i < w * h; i++) {
3041 if (!fread(&temp, 1, 1, f)) {
3042 fprintf(stderr, "Error reading raw file. End of file probably reached.\n");
3047 if (!fread(&temp, 1, 1, f)) {
3048 fprintf(stderr, "Error reading raw file. End of file probably reached.\n");
3053 image->comps[compno].data[i] = raw_cp->rawSigned ? (short)value : value;
3058 "OpenJPEG cannot encode raw components with bit depth higher than 16 bits.\n");
3063 if (fread(&ch, 1, 1, f)) {
3064 fprintf(stderr, "Warning. End of raw file not reached... processing anyway\n");
3071 int imagetoraw(opj_image_t * image, const char *outfile)
3073 FILE *rawFile = NULL;
3080 if ((image->numcomps * image->x1 * image->y1) == 0) {
3081 fprintf(stderr, "\nError: invalid raw image parameters\n");
3085 rawFile = fopen(outfile, "wb");
3087 fprintf(stderr, "Failed to open %s for writing !!\n", outfile);
3091 fprintf(stdout, "Raw image characteristics: %d components\n", image->numcomps);
3093 for (compno = 0; compno < image->numcomps; compno++) {
3094 fprintf(stdout, "Component %d characteristics: %dx%dx%d %s\n", compno,
3095 image->comps[compno].w,
3096 image->comps[compno].h, image->comps[compno].prec,
3097 image->comps[compno].sgnd == 1 ? "signed" : "unsigned");
3099 w = image->comps[compno].w;
3100 h = image->comps[compno].h;
3102 if (image->comps[compno].prec <= 8) {
3103 if (image->comps[compno].sgnd == 1) {
3105 int mask = (1 << image->comps[compno].prec) - 1;
3106 ptr = image->comps[compno].data;
3107 for (line = 0; line < h; line++) {
3108 for (row = 0; row < w; row++) {
3109 curr = (signed char)(*ptr & mask);
3110 res = fwrite(&curr, sizeof(signed char), 1, rawFile);
3112 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3118 } else if (image->comps[compno].sgnd == 0) {
3120 int mask = (1 << image->comps[compno].prec) - 1;
3121 ptr = image->comps[compno].data;
3122 for (line = 0; line < h; line++) {
3123 for (row = 0; row < w; row++) {
3124 curr = (unsigned char)(*ptr & mask);
3125 res = fwrite(&curr, sizeof(unsigned char), 1, rawFile);
3127 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3134 } else if (image->comps[compno].prec <= 16) {
3135 if (image->comps[compno].sgnd == 1) {
3136 signed short int curr;
3137 int mask = (1 << image->comps[compno].prec) - 1;
3138 ptr = image->comps[compno].data;
3139 for (line = 0; line < h; line++) {
3140 for (row = 0; row < w; row++) {
3142 curr = (signed short int)(*ptr & mask);
3143 temp = (unsigned char)(curr >> 8);
3144 res = fwrite(&temp, 1, 1, rawFile);
3146 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3149 temp = (unsigned char) curr;
3150 res = fwrite(&temp, 1, 1, rawFile);
3152 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3158 } else if (image->comps[compno].sgnd == 0) {
3159 unsigned short int curr;
3160 int mask = (1 << image->comps[compno].prec) - 1;
3161 ptr = image->comps[compno].data;
3162 for (line = 0; line < h; line++) {
3163 for (row = 0; row < w; row++) {
3165 curr = (unsigned short int)(*ptr & mask);
3166 temp = (unsigned char)(curr >> 8);
3167 res = fwrite(&temp, 1, 1, rawFile);
3169 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3172 temp = (unsigned char) curr;
3173 res = fwrite(&temp, 1, 1, rawFile);
3175 fprintf(stderr, "failed to write 1 byte for %s\n", outfile);
3182 } else if (image->comps[compno].prec <= 32) {
3183 fprintf(stderr, "More than 16 bits per component no handled yet\n");
3186 fprintf(stderr, "Error: invalid precision: %d\n", image->comps[compno].prec);
3194 #ifdef OPJ_HAVE_LIBPNG
3196 #define PNG_MAGIC "\x89PNG\x0d\x0a\x1a\x0a"
3197 #define MAGIC_SIZE 8
3198 /* PNG allows bits per sample: 1, 2, 4, 8, 16 */
3200 opj_image_t *pngtoimage(const char *read_idf, opj_cparameters_t * params)
3204 double gamma, display_exponent;
3205 int bit_depth, interlace_type, compression_type, filter_type;
3207 png_uint_32 resx, resy;
3209 png_uint_32 width, height;
3210 int color_type, has_alpha, is16;
3213 unsigned char **rows;
3216 opj_image_cmptparm_t cmptparm[4];
3218 unsigned int nr_comp;
3220 unsigned char sigbuf[8];
3222 if ((reader = fopen(read_idf, "rb")) == NULL) {
3223 fprintf(stderr, "pngtoimage: can not open %s\n", read_idf);
3230 if (fread(sigbuf, 1, MAGIC_SIZE, reader) != MAGIC_SIZE
3231 || memcmp(sigbuf, PNG_MAGIC, MAGIC_SIZE) != 0) {
3232 fprintf(stderr, "pngtoimage: %s is no valid PNG file\n", read_idf);
3235 /* libpng-VERSION/example.c:
3236 * PC : screen_gamma = 2.2;
3237 * Mac: screen_gamma = 1.7 or 1.0;
3239 display_exponent = 2.2;
3241 if ((png = png_create_read_struct(PNG_LIBPNG_VER_STRING,
3242 NULL, NULL, NULL)) == NULL) {
3245 if ((info = png_create_info_struct(png)) == NULL) {
3249 if (setjmp(png_jmpbuf(png))) {
3253 png_init_io(png, reader);
3254 png_set_sig_bytes(png, MAGIC_SIZE);
3256 png_read_info(png, info);
3258 if (png_get_IHDR(png, info, &width, &height,
3259 &bit_depth, &color_type, &interlace_type,
3260 &compression_type, &filter_type) == 0) {
3264 /* png_set_expand():
3265 * expand paletted images to RGB, expand grayscale images of
3266 * less than 8-bit depth to 8-bit depth, and expand tRNS chunks
3267 * to alpha channels.
3269 if (color_type == PNG_COLOR_TYPE_PALETTE) {
3270 png_set_expand(png);
3271 } else if (color_type == PNG_COLOR_TYPE_GRAY && bit_depth < 8) {
3272 png_set_expand(png);
3275 if (png_get_valid(png, info, PNG_INFO_tRNS)) {
3276 png_set_expand(png);
3279 is16 = (bit_depth == 16);
3281 /* GRAY => RGB; GRAY_ALPHA => RGBA
3283 if (color_type == PNG_COLOR_TYPE_GRAY
3284 || color_type == PNG_COLOR_TYPE_GRAY_ALPHA) {
3285 png_set_gray_to_rgb(png);
3287 (color_type == PNG_COLOR_TYPE_GRAY ? PNG_COLOR_TYPE_RGB :
3288 PNG_COLOR_TYPE_RGB_ALPHA);
3290 if (!png_get_gAMA(png, info, &gamma)) {
3294 png_set_gamma(png, display_exponent, gamma);
3296 png_read_update_info(png, info);
3298 png_get_pHYs(png, info, &resx, &resy, &unit);
3300 color_type = png_get_color_type(png, info);
3302 has_alpha = (color_type == PNG_COLOR_TYPE_RGB_ALPHA);
3304 nr_comp = 3 + has_alpha;
3306 bit_depth = png_get_bit_depth(png, info);
3308 rows = (unsigned char**)calloc(height + 1, sizeof(unsigned char*));
3309 for (i = 0; i < height; ++i) {
3310 rows[i] = (unsigned char*)malloc(png_get_rowbytes(png, info));
3313 png_read_image(png, rows);
3315 memset(&cmptparm, 0, 4 * sizeof(opj_image_cmptparm_t));
3317 sub_dx = params->subsampling_dx;
3318 sub_dy = params->subsampling_dy;
3320 for (i = 0; i < nr_comp; ++i) {
3321 cmptparm[i].prec = bit_depth;
3322 /* bits_per_pixel: 8 or 16 */
3323 cmptparm[i].bpp = bit_depth;
3324 cmptparm[i].sgnd = 0;
3325 cmptparm[i].dx = sub_dx;
3326 cmptparm[i].dy = sub_dy;
3327 cmptparm[i].w = width;
3328 cmptparm[i].h = height;
3331 image = opj_image_create(nr_comp, &cmptparm[0], CLRSPC_SRGB);
3333 if (image == NULL) {
3337 image->x0 = params->image_offset_x0;
3338 image->y0 = params->image_offset_y0;
3339 image->x1 = image->x0 + (width - 1) * sub_dx + 1 + image->x0;
3340 image->y1 = image->y0 + (height - 1) * sub_dy + 1 + image->y0;
3342 r = image->comps[0].data;
3343 g = image->comps[1].data;
3344 b = image->comps[2].data;
3345 a = image->comps[3].data;
3347 for (i = 0; i < height; ++i) {
3350 for (j = 0; j < width; ++j) {
3352 *r++ = s[0] << 8 | s[1];
3355 *g++ = s[0] << 8 | s[1];
3358 *b++ = s[0] << 8 | s[1];
3362 *a++ = s[0] << 8 | s[1];
3379 for (i = 0; i < height; ++i) {
3385 png_destroy_read_struct(&png, &info, NULL);
3394 int imagetopng(opj_image_t * image, const char *write_idf)
3399 int *red, *green, *blue, *alpha;
3400 unsigned char *row_buf, *d;
3401 int has_alpha, width, height, nr_comp, color_type;
3402 int adjustR, adjustG, adjustB, adjustA, x, y, fails;
3403 int prec, ushift, dshift, is16, force16, force8;
3404 unsigned short mask = 0xffff;
3405 png_color_8 sig_bit;
3407 is16 = force16 = force8 = ushift = dshift = 0;
3409 prec = image->comps[0].prec;
3410 nr_comp = image->numcomps;
3412 if (prec > 8 && prec < 16) {
3414 dshift = prec - ushift;
3417 } else if (prec < 8 && nr_comp > 1) { /* GRAY_ALPHA, RGB, RGB_ALPHA */
3419 dshift = 8 - ushift;
3424 if (prec != 1 && prec != 2 && prec != 4 && prec != 8 && prec != 16) {
3425 fprintf(stderr, "imagetopng: can not create %s"
3426 "\n\twrong bit_depth %d\n", write_idf, prec);
3429 writer = fopen(write_idf, "wb");
3431 if (writer == NULL) {
3438 /* Create and initialize the png_struct with the desired error handler
3439 * functions. If you want to use the default stderr and longjump method,
3440 * you can supply NULL for the last three parameters. We also check that
3441 * the library version is compatible with the one used at compile time,
3442 * in case we are using dynamically linked libraries. REQUIRED.
3444 png = png_create_write_struct(PNG_LIBPNG_VER_STRING,
3446 /*png_voidp user_error_ptr, user_error_fn, user_warning_fn); */
3452 /* Allocate/initialize the image information data. REQUIRED
3454 info = png_create_info_struct(png);
3460 /* Set error handling. REQUIRED if you are not supplying your own
3461 * error handling functions in the png_create_write_struct() call.
3463 if (setjmp(png_jmpbuf(png))) {
3467 /* I/O initialization functions is REQUIRED
3469 png_init_io(png, writer);
3471 /* Set the image information here. Width and height are up to 2^31,
3472 * bit_depth is one of 1, 2, 4, 8, or 16, but valid values also depend on
3473 * the color_type selected. color_type is one of PNG_COLOR_TYPE_GRAY,
3474 * PNG_COLOR_TYPE_GRAY_ALPHA, PNG_COLOR_TYPE_PALETTE, PNG_COLOR_TYPE_RGB,
3475 * or PNG_COLOR_TYPE_RGB_ALPHA. interlace is either PNG_INTERLACE_NONE or
3476 * PNG_INTERLACE_ADAM7, and the compression_type and filter_type MUST
3477 * currently be PNG_COMPRESSION_TYPE_BASE and PNG_FILTER_TYPE_BASE.
3482 * color_type == PNG_COLOR_TYPE_PALETTE && bit_depth > 8
3483 * color_type == PNG_COLOR_TYPE_RGB && bit_depth < 8
3484 * color_type == PNG_COLOR_TYPE_GRAY_ALPHA && bit_depth < 8
3485 * color_type == PNG_COLOR_TYPE_RGB_ALPHA) && bit_depth < 8
3488 png_set_compression_level(png, Z_BEST_COMPRESSION);
3492 } else if (prec == 8) {
3494 } else if (prec == 4) {
3496 } else if (prec == 2) {
3498 } else if (prec == 1) {
3503 && image->comps[0].dx == image->comps[1].dx
3504 && image->comps[1].dx == image->comps[2].dx
3505 && image->comps[0].dy == image->comps[1].dy
3506 && image->comps[1].dy == image->comps[2].dy
3507 && image->comps[0].prec == image->comps[1].prec
3508 && image->comps[1].prec == image->comps[2].prec) {
3511 has_alpha = (nr_comp > 3);
3513 is16 = (prec == 16);
3515 width = image->comps[0].w;
3516 height = image->comps[0].h;
3518 red = image->comps[0].data;
3519 green = image->comps[1].data;
3520 blue = image->comps[2].data;
3522 sig_bit.red = sig_bit.green = sig_bit.blue = prec;
3525 sig_bit.alpha = prec;
3526 alpha = image->comps[3].data;
3527 color_type = PNG_COLOR_TYPE_RGB_ALPHA;
3528 adjustA = (image->comps[3].sgnd ? 1 << (image->comps[3].prec - 1) : 0);
3532 color_type = PNG_COLOR_TYPE_RGB;
3535 png_set_sBIT(png, info, &sig_bit);
3537 png_set_IHDR(png, info, width, height, prec,
3540 PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);
3541 /*=============================*/
3542 png_write_info(png, info);
3543 /*=============================*/
3545 png_set_packing(png);
3547 adjustR = (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
3548 adjustG = (image->comps[1].sgnd ? 1 << (image->comps[1].prec - 1) : 0);
3549 adjustB = (image->comps[2].sgnd ? 1 << (image->comps[2].prec - 1) : 0);
3551 row_buf = (unsigned char*)malloc(width * nr_comp * 2);
3553 for (y = 0; y < height; ++y) {
3556 for (x = 0; x < width; ++x) {
3562 v = (v << ushift) + (v >> dshift);
3565 *d++ = (unsigned char)(v >> 8);
3566 *d++ = (unsigned char)v;
3568 v = *green + adjustG;
3572 v = (v << ushift) + (v >> dshift);
3575 *d++ = (unsigned char)(v >> 8);
3576 *d++ = (unsigned char)v;
3578 v = *blue + adjustB;
3582 v = (v << ushift) + (v >> dshift);
3585 *d++ = (unsigned char)(v >> 8);
3586 *d++ = (unsigned char)v;
3589 v = *alpha + adjustA;
3593 v = (v << ushift) + (v >> dshift);
3596 *d++ = (unsigned char)(v >> 8);
3597 *d++ = (unsigned char)v;
3606 v = (v << ushift) + (v >> dshift);
3609 *d++ = (unsigned char)(v & mask);
3611 v = *green + adjustG;
3615 v = (v << ushift) + (v >> dshift);
3618 *d++ = (unsigned char)(v & mask);
3620 v = *blue + adjustB;
3624 v = (v << ushift) + (v >> dshift);
3627 *d++ = (unsigned char)(v & mask);
3630 v = *alpha + adjustA;
3634 v = (v << ushift) + (v >> dshift);
3637 *d++ = (unsigned char)(v & mask);
3641 png_write_row(png, row_buf);
3647 else if (nr_comp == 1 /* GRAY */
3648 || (nr_comp == 2 /* GRAY_ALPHA */
3649 && image->comps[0].dx == image->comps[1].dx
3650 && image->comps[0].dy == image->comps[1].dy
3651 && image->comps[0].prec == image->comps[1].prec)) {
3654 red = image->comps[0].data;
3656 sig_bit.gray = prec;
3657 sig_bit.red = sig_bit.green = sig_bit.blue = sig_bit.alpha = 0;
3660 color_type = PNG_COLOR_TYPE_GRAY;
3664 sig_bit.alpha = prec;
3665 alpha = image->comps[1].data;
3666 color_type = PNG_COLOR_TYPE_GRAY_ALPHA;
3667 adjustA = (image->comps[1].sgnd ? 1 << (image->comps[1].prec - 1) : 0);
3669 width = image->comps[0].w;
3670 height = image->comps[0].h;
3672 png_set_IHDR(png, info, width, height, sig_bit.gray,
3675 PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);
3677 png_set_sBIT(png, info, &sig_bit);
3678 /*=============================*/
3679 png_write_info(png, info);
3680 /*=============================*/
3681 adjustR = (image->comps[0].sgnd ? 1 << (image->comps[0].prec - 1) : 0);
3684 png_set_packing(png);
3688 row_buf = (unsigned char*)
3689 malloc(width * nr_comp * sizeof(unsigned short));
3691 for (y = 0; y < height; ++y) {
3694 for (x = 0; x < width; ++x) {
3699 v = (v << ushift) + (v >> dshift);
3702 *d++ = (unsigned char)(v >> 8);
3703 *d++ = (unsigned char)v;
3709 v = (v << ushift) + (v >> dshift);
3712 *d++ = (unsigned char)(v >> 8);
3713 *d++ = (unsigned char)v;
3716 png_write_row(png, row_buf);
3720 } else { /* prec <= 8 */
3721 row_buf = (unsigned char*)calloc(width, nr_comp * 2);
3723 for (y = 0; y < height; ++y) {
3726 for (x = 0; x < width; ++x) {
3731 v = (v << ushift) + (v >> dshift);
3734 *d++ = (unsigned char)(v & mask);
3737 v = *alpha + adjustA;
3741 v = (v << ushift) + (v >> dshift);
3744 *d++ = (unsigned char)(v & mask);
3748 png_write_row(png, row_buf);
3754 fprintf(stderr, "imagetopng: can not create %s\n", write_idf);
3757 png_write_end(png, info);
3764 png_destroy_write_struct(&png, &info);
3774 #endif /* OPJ_HAVE_LIBPNG */