• Main Page
  • Related Pages
  • Modules
  • Namespaces
  • Classes
  • Files
  • File List

load.hh

00001 // Copyright (C) 2009 EPITA Research and Development Laboratory (LRDE)
00002 //
00003 // This file is part of Olena.
00004 //
00005 // Olena is free software: you can redistribute it and/or modify it under
00006 // the terms of the GNU General Public License as published by the Free
00007 // Software Foundation, version 2 of the License.
00008 //
00009 // Olena is distributed in the hope that it will be useful,
00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012 // General Public License for more details.
00013 //
00014 // You should have received a copy of the GNU General Public License
00015 // along with Olena.  If not, see <http://www.gnu.org/licenses/>.
00016 //
00017 // As a special exception, you may use this file as part of a free
00018 // software project without restriction.  Specifically, if other files
00019 // instantiate templates or use macros or inline functions from this
00020 // file, or you compile this file and link it with other files to produce
00021 // an executable, this file does not by itself cause the resulting
00022 // executable to be covered by the GNU General Public License.  This
00023 // exception does not however invalidate any other reasons why the
00024 // executable file might be covered by the GNU General Public License.
00025 
00026 #ifndef MLN_IO_TIFF_LOAD_HH
00027 # define MLN_IO_TIFF_LOAD_HH
00028 
00029 
00037 
00038 
00039 # include <iostream>
00040 # include <fstream>
00041 # include <tiffio.h>
00042 
00043 # include <mln/core/concept/image.hh>
00044 # include <mln/value/rgb8.hh>
00045 
00046 
00047 
00048 namespace mln
00049 {
00050 
00051   namespace io
00052   {
00053 
00054     namespace tiff
00055     {
00056 
00057 
00059       //
00060       template <typename I>
00061       void load(Image<I>& ima_, const std::string& filename);
00062 
00063 
00064 
00065 # ifndef MLN_INCLUDE_ONLY
00066 
00067 
00068       namespace internal
00069       {
00070 
00071         inline
00072         point2d ij2rc_1(int i, int j, int ni_1, int nj_1)
00073         {
00074           (void) nj_1;
00075           return point2d(ni_1 - i, j);
00076         }
00077 
00078         inline
00079         point2d ij2rc_2(int i, int j, int ni_1, int nj_1)
00080         {
00081           return point2d(ni_1 - i, nj_1 - j);
00082         }
00083 
00084         inline
00085         point2d ij2rc_3(int i, int j, int ni_1, int nj_1)
00086         {
00087           (void) ni_1;
00088           return point2d(i, nj_1 - j);
00089         }
00090 
00091         inline
00092         point2d ij2rc_4(int i, int j, int ni_1, int nj_1)
00093         {
00094           (void) ni_1;
00095           (void) nj_1;
00096           return point2d(i, j);
00097         }
00098 
00099         inline
00100         point2d ij2rc_5(int i, int j, int ni_1, int nj_1)
00101         {
00102           (void) nj_1;
00103           return point2d(j, ni_1 - i);
00104         }
00105 
00106         inline
00107         point2d ij2rc_6(int i, int j, int ni_1, int nj_1)
00108         {
00109           return point2d(nj_1 - j, ni_1 - i);
00110         }
00111 
00112         inline
00113         point2d ij2rc_7(int i, int j, int ni_1, int nj_1)
00114         {
00115           (void) ni_1;
00116           return point2d(nj_1 - j, i);
00117         }
00118 
00119         inline
00120         point2d ij2rc_8(int i, int j, int ni_1, int nj_1)
00121         {
00122           (void) ni_1;
00123           (void) nj_1;
00124           return point2d(j, i);
00125         }
00126 
00127 
00128 
00129         template <typename I>
00130         inline
00131         I load_header(TIFF *file)
00132         {
00133           uint32 width, height;
00134 
00135           TIFFGetField(file, TIFFTAG_IMAGEWIDTH, &width);
00136           TIFFGetField(file, TIFFTAG_IMAGELENGTH, &height);
00137 
00138           mln_concrete(I) new_ima(height, width, 0);
00139 
00140           return new_ima;
00141         }
00142 
00143 
00144         template <typename I>
00145         inline
00146         void load_data_rgb8(I& ima, TIFF *file)
00147         {
00148           uint16 bits_per_sample, samples_per_pixel;
00149 
00150           TIFFGetField(file, TIFFTAG_BITSPERSAMPLE, &bits_per_sample);
00151           TIFFGetField(file, TIFFTAG_SAMPLESPERPIXEL, &samples_per_pixel);
00152 
00153           uint16 data_size = bits_per_sample * samples_per_pixel;
00154           if (data_size != 24 && data_size != 32)
00155           {
00156             std::cout << "Trying to load a non color TIFF "
00157                       << "image into a color Milena image." << std::endl;
00158             abort();
00159           }
00160 
00161           uint32 npixels = ima.ncols() * ima.nrows();
00162           uint32 *raster = (uint32 *) _TIFFmalloc(npixels * sizeof (uint32));
00163 
00164           if (!TIFFReadRGBAImage(file, ima.ncols(), ima.nrows(), raster, 0))
00165           {
00166             std::cout << "Error while reading the image file. Is it corrupted?"
00167                       << std::endl;
00168             abort();
00169           }
00170 
00171           uint16 orientation;
00172           TIFFGetField(file, TIFFTAG_ORIENTATION, &orientation);
00173 
00174           typedef point2d (*fun_t)(int, int, int, int);
00175           fun_t funs[] = { 0, ij2rc_1, ij2rc_2, ij2rc_3, ij2rc_4,
00176                               ij2rc_5, ij2rc_6, ij2rc_7, ij2rc_8 };
00177           fun_t fun = funs[orientation];
00178 
00179           int ni_1, nj_1;
00180           unsigned idx = 0;
00181 
00182           if (orientation <= 4)
00183             {
00184               ni_1 = ima.nrows() - 1;
00185               nj_1 = ima.ncols() - 1;
00186               for (int i = 0; i <= ni_1; ++i)
00187                 for (int j = 0; j <= nj_1; ++j)
00188                   {
00189                     value::rgb8 v;
00190 
00191                     v.red() = (unsigned char) TIFFGetR(raster[idx]);
00192                     v.green() = (unsigned char) TIFFGetG(raster[idx]);
00193                     v.blue() = (unsigned char) TIFFGetB(raster[idx]);
00194                     ima((*fun)(i, j, ni_1, nj_1)) = v;
00195 
00196                     ++idx;
00197                   }
00198             }
00199           else
00200             {
00201               nj_1 = ima.nrows() - 1;
00202               ni_1 = ima.ncols() - 1;
00203               for (int j = 0; j <= nj_1; ++j)
00204                 for (int i = 0; i <= ni_1; ++i)
00205                   {
00206                     value::rgb8 v;
00207 
00208                     v.red() = (unsigned char) TIFFGetR(raster[idx]);
00209                     v.green() = (unsigned char) TIFFGetG(raster[idx]);
00210                     v.blue() = (unsigned char) TIFFGetB(raster[idx]);
00211                     ima((*fun)(i, j, ni_1, nj_1)) = v;
00212 
00213                     ++idx;
00214                   }
00215             }
00216 
00217           _TIFFfree(raster);
00218         }
00219 
00220 
00221 
00222 
00223         template <typename I>
00224         inline
00225         void load_data_scalar(I& ima, TIFF *file)
00226         {
00227           uint16 samples_per_pixel;
00228           TIFFGetField(file, TIFFTAG_SAMPLESPERPIXEL, &samples_per_pixel);
00229           if (samples_per_pixel != 1)
00230           {
00231             std::cout << "Trying to load a non grayscale TIFF "
00232                       << "image into a grayscale Milena image." << std::endl;
00233             abort();
00234           }
00235 
00236           uint32 npixels = ima.ncols() * ima.nrows();
00237           uint32 *raster = (uint32 *) _TIFFmalloc(npixels * sizeof (uint32));
00238 
00239           if (!TIFFReadRGBAImage(file, ima.ncols(), ima.nrows(), raster, 0))
00240           {
00241             std::cout << "Error while reading the image file. Is it corrupted?"
00242                       << std::endl;
00243             abort();
00244           }
00245 
00246           uint16 orientation;
00247           TIFFGetField(file, TIFFTAG_ORIENTATION, &orientation);
00248 
00249           typedef point2d (*fun_t)(int, int, int, int);
00250           fun_t funs[] = { 0, ij2rc_1, ij2rc_2, ij2rc_3, ij2rc_4,
00251                               ij2rc_5, ij2rc_6, ij2rc_7, ij2rc_8 };
00252           fun_t fun = funs[orientation];
00253 
00254           int ni_1, nj_1;
00255           unsigned idx = 0;
00256 
00257           if (orientation <= 4)
00258             {
00259               ni_1 = ima.nrows() - 1;
00260               nj_1 = ima.ncols() - 1;
00261               for (int i = 0; i <= ni_1; ++i)
00262                 for (int j = 0; j <= nj_1; ++j)
00263                   {
00264                     ima((*fun)(i, j, ni_1, nj_1)) = (unsigned char) TIFFGetR(raster[idx++]);
00265                   }
00266             }
00267           else
00268             {
00269               nj_1 = ima.nrows() - 1;
00270               ni_1 = ima.ncols() - 1;
00271               for (int j = 0; j <= nj_1; ++j)
00272                 for (int i = 0; i <= ni_1; ++i)
00273                   {
00274                     ima((*fun)(i, j, ni_1, nj_1)) = (unsigned char) TIFFGetR(raster[idx++]);
00275                   }
00276             }
00277 
00278           _TIFFfree(raster);
00279         }
00280 
00281         template <typename I>
00282         inline
00283         void
00284         load_data_dispatch(const value::rgb8&, I& ima, TIFF *file)
00285         {
00286           load_data_rgb8(ima, file);
00287         }
00288 
00289         template <typename S, typename I>
00290         inline
00291         void
00292         load_data_dispatch(const value::Scalar<S>&, I& ima, TIFF *file)
00293         {
00294           load_data_scalar(ima, file);
00295         }
00296 
00297         template <typename I>
00298         inline
00299         void
00300         load_data_dispatch(const bool&, I& ima, TIFF *file)
00301         {
00302           load_data_scalar(ima, file);
00303         }
00304 
00305 
00306         template <typename I>
00307         inline
00308         void
00309         load_data_dispatch(I& ima, TIFF *file)
00310         {
00311           load_data_dispatch(mln_value(I)(), exact(ima), file);
00312         }
00313 
00314 
00315       } // end of namespace mln::io::tiff::internal
00316 
00317 
00318 
00319       // Facade
00320 
00321       template <typename I>
00322       inline
00323       void load(Image<I>& ima_, const std::string& filename)
00324       {
00325         trace::entering("mln::io::tiff::load");
00326 
00327         I& ima = exact(ima_);
00328 
00329         TIFF *file = TIFFOpen(filename.c_str(), "r");
00330         if (file == 0)
00331         {
00332           std::cerr << "io::tiff::load - Error: cannot open file '"
00333                     << filename << "'!"
00334                     << std::endl;
00335           abort();
00336         }
00337 
00338         ima = internal::load_header<I>(file);
00339         internal::load_data_dispatch(ima, file);
00340 
00341         mln_postcondition(ima.is_valid());
00342 
00343         (void) TIFFClose(file);
00344         trace::exiting("mln::io::tiff::load");
00345       }
00346 
00347 # endif // ! MLN_INCLUDE_ONLY
00348 
00349     } // end of namespace mln::io::tiff
00350 
00351   } // end of namespace mln::io
00352 
00353 } // end of namespace mln
00354 
00355 #endif // ! MLN_IO_TIFF_LOAD_HH

Generated on Tue Oct 4 2011 15:24:03 for Milena (Olena) by  doxygen 1.7.1