File: GFile_TIFF.cpp

package info (click to toggle)
kdc2tiff 0.35-11
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 556 kB
  • sloc: cpp: 3,107; ansic: 832; sh: 330; makefile: 23
file content (150 lines) | stat: -rw-r--r-- 3,856 bytes parent folder | download | duplicates (8)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
#include <config.h>
#include <stdio.h>
#include <math.h>
#include <errno.h>

#include "GFile_TIFF.h"

/* GFile (ie. GImage) decendent for reading TIFF files.
 *
 * Written by:  Chris Studholme
 * Last Update: 28-May-2000
 * Copyright:   GPL (http://www.fsf.org/copyleft/gpl.html)
 */


//#define _CHECKS
#ifdef _CHECKS
double VerifyImage(GImageComponent* image, const unsigned char* imagedata,
		   int w, int h) {
  double error=0;
  for (int y=0; y<h; ++y)
    for (int x=0; x<w; ++x) {
      int residule = (imagedata[y*w+x]-128)*128 - image->getPixel(x,y,x+1,y+1);
      error += residule*residule;
      //error += residule<0 ? -residule : residule;
    }
  return sqrt(error/w/h)/128;
  //return error/w/h/128;
}
#endif


/* ================ GFile_TIFF methods  ================ */

GFile_TIFF::GFile_TIFF(const char* filename, bool fast) {
  imagefile = TIFFOpen(filename,"r");
  if (imagefile==0) {
    fprintf(stderr,"GFile_TIFF::GFile_TIFF, cannot read file '%s'\n",filename);
    return;
  }
  ReadImage(fast);
}

/*
  GFile_TIFF::GFile_TIFF(FILE* infile) {
  imagefile = infile;
  ReadImage();
}
*/

GFile_TIFF::~GFile_TIFF() {
  if (imagefile)
    TIFFClose(imagefile);
  if (red)
    delete red;
  if (green)
    delete green;
  if (blue)
    delete blue;
}

bool GFile_TIFF::supportsFile(FILE* file) {
  if (fseek(file,0,SEEK_SET)!=0) {
    fprintf(stderr,"GFile_TIFF::supportsFile() fseek() failed %d\n",errno);
    return false;
  }
  unsigned char header[4];
  if (fread(header,sizeof(header),1,file)!=1) {
    fprintf(stderr,"GFile_TIFF::supportsFile() fread() failed %d\n",errno);
    return false;
  }
  return (((header[0]=='M')&&(header[1]=='M')&&
           (header[2]==0)&&(header[3]==42))||
          ((header[0]=='I')&&(header[1]=='I')&&
           (header[2]==42)&&(header[3]==0)));
}

void GFile_TIFF::ReadImage(bool fast) {

  TIFFGetField(imagefile, TIFFTAG_IMAGEWIDTH, &w);
  TIFFGetField(imagefile, TIFFTAG_IMAGELENGTH, &h);

  int npixels = w*h;
  uint32* raster = new uint32[npixels];
  if (raster==NULL) {
    fprintf(stderr,"GFile_TIFF::ReadImage, failed to allocate memory\n");
    TIFFClose(imagefile);
    imagefile=0;
    return;
  }

  if (!TIFFReadRGBAImage(imagefile, w, h, raster, 0)) {
    fprintf(stderr,"GFile_TIFF::ReadImage, failed to read image\n");
    TIFFClose(imagefile);
    imagefile=0;
    return;
  }
  
  // process image
  unsigned char* color = new unsigned char[npixels];

  fprintf(stderr,"Initializing linear matrix... ");
  for (int y=0; y<h; ++y)
    for (int x=0; x<w; ++x)
      color[(h-1-y)*w+x] = TIFFGetR(raster[y*w+x]);
  red = new GImageComponent0(color,w,h,fast?-1:0);
#ifdef _CHECKS
  fprintf(stderr,"\nRed Error(l1): %g\n",red->getTotalError());
  fprintf(stderr,"Red Error(l2): %g\n",VerifyImage(red,color,w,h));
#endif
 
  fprintf(stderr,"red... ");
  for (int y=0; y<h; ++y)
    for (int x=0; x<w; ++x)
      color[(h-1-y)*w+x] = TIFFGetG(raster[y*w+x]);
  green = new GImageComponent0(color,w,h,fast?-1:0);
#ifdef _CHECKS
  fprintf(stderr,"\nGreen Error(l1): %g\n",green->getTotalError());
  fprintf(stderr,"Green Error(l2): %g\n",VerifyImage(green,color,w,h));
#endif

  fprintf(stderr,"green... ");
  for (int y=0; y<h; ++y)
    for (int x=0; x<w; ++x)
      color[(h-1-y)*w+x] = TIFFGetB(raster[y*w+x]);
  blue = new GImageComponent0(color,w,h,fast?-1:0);
#ifdef _CHECKS
  fprintf(stderr,"\nBlue Error(l1): %g\n",blue->getTotalError());
  fprintf(stderr,"Blue Error(l2): %g\n",VerifyImage(blue,color,w,h));
#endif

  fprintf(stderr,"blue, done.\n");
  if (!fast)
    fprintf(stderr,"Total Error is %g\n",red->getTotalError()+
	    green->getTotalError()+blue->getTotalError());

  delete[] color;
  delete[] raster;
}

const char* GFile_TIFF::getComments() {
  return NULL;
}

/* width/height of individual pixel */
double GFile_TIFF::getAspectRatio() {
  return 1;
}