00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00035 #include <stdlib.h>
00036 #include <string.h>
00037
00038 #include "tiffio.h"
00039
00040
00041
00042
00043
00057 static uint8 *read_tiff_rgba_raw(const char *fname,
00058 size_t * nx, size_t * ny, size_t * nc)
00059 {
00060 TIFF *tiffp = NULL;
00061 uint32 width = 0, height = 0, nbsamples = 0;
00062 uint32 *data_tiff = NULL;
00063 uint32 *ptr_in, *ptr_end;
00064 uint8 *data = NULL;
00065 uint8 *ptr_r, *ptr_g, *ptr_b;
00066
00067
00068 if ((NULL == nx) || (NULL == ny) || (NULL == nc))
00069 return NULL;
00070
00071
00072 (void) TIFFSetWarningHandler(NULL);
00073
00074
00075 if (NULL == (tiffp = TIFFOpen(fname, "r")))
00076 return NULL;
00077
00078
00079 if (1 != TIFFGetField(tiffp, TIFFTAG_IMAGEWIDTH, &width)
00080 || 1 != TIFFGetField(tiffp, TIFFTAG_IMAGELENGTH, &height)
00081 || 1 != TIFFGetField(tiffp, TIFFTAG_SAMPLESPERPIXEL, &nbsamples)
00082 || NULL == (data_tiff = (uint32 *) malloc(width * height
00083 * sizeof(uint32)))) {
00084 TIFFClose(tiffp);
00085 return NULL;
00086 }
00087
00088
00089 if (1 != TIFFReadRGBAImageOriented(tiffp, width, height, data_tiff,
00090 ORIENTATION_TOPLEFT, 1)) {
00091 free(data_tiff);
00092 TIFFClose(tiffp);
00093 return NULL;
00094 }
00095
00096 TIFFClose(tiffp);
00097
00098 *nx = (size_t) width;
00099 *ny = (size_t) height;
00100 *nc = (size_t) nbsamples;
00101
00102
00103
00104
00105
00106
00107 if (NULL == (data = (uint8 *) malloc(*nx * *ny * 3 * sizeof(uint8)))) {
00108 free(data_tiff);
00109 return NULL;
00110 }
00111
00112
00113
00114
00115
00116 ptr_in = data_tiff;
00117 ptr_end = ptr_in + *nx * *ny;
00118 ptr_r = data;
00119 ptr_g = ptr_r + *nx * *ny;
00120 ptr_b = ptr_g + *nx * *ny;
00121 while (ptr_in < ptr_end) {
00122 *ptr_r++ = (uint8) TIFFGetR(*ptr_in);
00123 *ptr_g++ = (uint8) TIFFGetG(*ptr_in);
00124 *ptr_b++ = (uint8) TIFFGetB(*ptr_in);
00125 ptr_in++;
00126 }
00127 free(data_tiff);
00128
00129
00130 if ((3 == *nc)
00131 || (3 < *nc))
00132 *nc = 3;
00133 else if ((1 == *nc)
00134 || (2 == *nc)) {
00135 *nc = 1;
00136
00137 data = (uint8 *) realloc(data, *nx * *ny * *nc * sizeof(float));
00138 } else {
00139 free(data);
00140 return NULL;
00141 }
00142 return data;
00143 }
00144
00159 float *read_tiff_f32(const char *fname, size_t * nx, size_t * ny, size_t * nc)
00160 {
00161 uint8 *data_tiff = NULL;
00162 uint8 *ptr_in, *ptr_end;
00163 float *data = NULL;
00164 float *ptr_out;
00165
00166
00167 if ((NULL == nx) || (NULL == ny) || (NULL == nc))
00168 return NULL;
00169
00170
00171 if (NULL == (data_tiff = read_tiff_rgba_raw(fname, nx, ny, nc)))
00172 return NULL;
00173 if (NULL == (data = (float *) malloc(*nx * *ny * *nc * sizeof(float)))) {
00174 free(data_tiff);
00175 return NULL;
00176 }
00177
00178
00179 ptr_in = data_tiff;
00180 ptr_end = ptr_in + *nx * *ny * *nc;
00181 ptr_out = data;
00182 while (ptr_in < ptr_end)
00183 *ptr_out++ = (float) *ptr_in++;
00184
00185 free(data_tiff);
00186
00187 return data;
00188 }
00189
00204 unsigned char *read_tiff_u8(const char *fname,
00205 size_t * nx, size_t * ny, size_t * nc)
00206
00207
00208
00209 {
00210 uint8 *data_tiff = NULL;
00211 uint8 *ptr_in, *ptr_end;
00212 unsigned char *data = NULL;
00213 unsigned char *ptr_out;
00214
00215
00216 if ((NULL == nx) || (NULL == ny) || (NULL == nc))
00217 return NULL;
00218
00219
00220 if (NULL == (data_tiff = read_tiff_rgba_raw(fname, nx, ny, nc)))
00221 return NULL;
00222
00223
00224 if (NULL == (data = (unsigned char *)
00225 malloc(*nx * *ny * *nc * sizeof(unsigned char)))) {
00226 free(data_tiff);
00227 return NULL;
00228 }
00229
00230
00231 ptr_in = data_tiff;
00232 ptr_end = ptr_in + *nx * *ny;
00233 ptr_out = data;
00234 while (ptr_in < ptr_end)
00235 *ptr_out++ = (unsigned char) *ptr_in++;
00236
00237 free(data_tiff);
00238
00239 return data;
00240 }
00241
00242
00243
00244
00245
00263 static int write_tiff_raw(const char *fname, const uint8 * data_raw,
00264 size_t nx, size_t ny, size_t nc)
00265 {
00266 TIFF *tiffp = NULL;
00267 uint8 *data_tiff = NULL;
00268 uint16 ttag_photometric;
00269
00270
00271
00272
00273
00274
00275
00276 if (NULL == data_raw
00277 || 4294967295. < (double) nx || 4294967295. < (double) ny)
00278 return -1;
00279
00280 if (1 == nc) {
00281
00282 if (NULL == (data_tiff = (uint8 *) malloc(nx * ny * nc
00283 * sizeof(uint8))))
00284 return -1;
00285 memcpy(data_tiff, data_raw, nx * ny * nc * sizeof(uint8));
00286 ttag_photometric = PHOTOMETRIC_MINISBLACK;
00287 } else if (3 == nc) {
00288 uint8 *ptr_out, *ptr_end, *ptr_r, *ptr_g, *ptr_b;
00289
00290
00291 if (NULL == (data_tiff = (uint8 *) malloc(nx * ny * nc
00292 * sizeof(uint8))))
00293 return -1;
00294
00295 ptr_out = data_tiff;
00296 ptr_end = ptr_out + nx * ny * nc;
00297 ptr_r = (uint8 *) data_raw;
00298 ptr_g = ptr_r + nx * ny;
00299 ptr_b = ptr_g + nx * ny;
00300 while (ptr_out < ptr_end) {
00301 *ptr_out++ = *ptr_r++;
00302 *ptr_out++ = *ptr_g++;
00303 *ptr_out++ = *ptr_b++;
00304 }
00305 ttag_photometric = PHOTOMETRIC_RGB;
00306 } else
00307 return -1;
00308
00309
00310 (void) TIFFSetWarningHandler(NULL);
00311
00312
00313 if (NULL == (tiffp = TIFFOpen(fname, "w"))) {
00314 free(data_tiff);
00315 return -1;
00316 }
00317
00318
00319 if (1 != TIFFSetField(tiffp, TIFFTAG_IMAGEWIDTH, nx)
00320 || 1 != TIFFSetField(tiffp, TIFFTAG_IMAGELENGTH, ny)
00321 || 1 != TIFFSetField(tiffp, TIFFTAG_ORIENTATION,
00322 ORIENTATION_TOPLEFT)
00323 || 1 != TIFFSetField(tiffp, TIFFTAG_PLANARCONFIG,
00324 PLANARCONFIG_CONTIG)
00325 || 1 != TIFFSetField(tiffp, TIFFTAG_BITSPERSAMPLE, 8)
00326 || 1 != TIFFSetField(tiffp, TIFFTAG_ROWSPERSTRIP, ny)
00327 || 1 != TIFFSetField(tiffp, TIFFTAG_COMPRESSION, COMPRESSION_LZW)
00328
00329 || 1 != TIFFSetField(tiffp, TIFFTAG_SAMPLESPERPIXEL, nc)
00330 || 1 != TIFFSetField(tiffp, TIFFTAG_PHOTOMETRIC, ttag_photometric)
00331
00332 || (nx * ny * nc != (unsigned int)
00333 TIFFWriteEncodedStrip(tiffp, (tstrip_t) 0, (tdata_t) data_tiff,
00334 (tsize_t) (nx * ny * nc)))) {
00335 free(data_tiff);
00336 TIFFClose(tiffp);
00337 return -1;
00338 }
00339
00340
00341 free(data_tiff);
00342 TIFFClose(tiffp);
00343 return 0;
00344 }
00345
00358 int write_tiff_f32(const char *fname, const float *data,
00359 size_t nx, size_t ny, size_t nc)
00360 {
00361 uint8 *data_tiff = NULL;
00362 uint8 *ptr_out, *ptr_end;
00363 const float *ptr_in;
00364 int retval;
00365
00366
00367 if (NULL == data)
00368 return -1;
00369
00370
00371 if (NULL == (data_tiff = (uint8 *) malloc(nx * ny * nc * sizeof(uint8))))
00372 return -1;
00373
00374
00375 ptr_out = data_tiff;
00376 ptr_end = ptr_out + nx * ny * nc;
00377 ptr_in = data;
00378 while (ptr_out < ptr_end)
00379 *ptr_out++ = (uint8) (*ptr_in++ + .5);
00380
00381
00382 retval = write_tiff_raw(fname, data_tiff, nx, ny, nc);
00383
00384 free(data_tiff);
00385
00386 return retval;
00387 }
00388
00403 int write_tiff_u8(const char *fname, const unsigned char *data,
00404 size_t nx, size_t ny, size_t nc)
00405
00406
00407
00408
00409 {
00410 uint8 *data_tiff = NULL;
00411 uint8 *ptr_out, *ptr_end;
00412 const unsigned char *ptr_in;
00413 int retval;
00414
00415
00416 if (NULL == data)
00417 return -1;
00418
00419
00420 if (NULL == (data_tiff = (uint8 *) malloc(nx * ny * nc * sizeof(uint8))))
00421 return -1;
00422
00423
00424 ptr_out = data_tiff;
00425 ptr_end = ptr_out + nx * ny;
00426 ptr_in = data;
00427 while (ptr_out < ptr_end)
00428 *ptr_out++ = (uint8) (*ptr_in++ + .5);
00429
00430
00431 retval = write_tiff_raw(fname, data_tiff, nx, ny, nc);
00432
00433 free(data_tiff);
00434
00435 return retval;
00436 }