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

load.hh

00001 // Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 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_PNM_LOAD_HH
00027 # define MLN_IO_PNM_LOAD_HH
00028 
00033 
00034 # include <iostream>
00035 # include <fstream>
00036 # include <string>
00037 
00038 # include <mln/core/image/image2d.hh>
00039 
00040 # include <mln/value/int_u8.hh>
00041 # include <mln/value/rgb.hh>
00042 
00043 # include <mln/io/pnm/load_header.hh>
00044 # include <mln/io/pnm/max_component.hh>
00045 # include <mln/io/pnm/macros.hh>
00046 
00047 # include <mln/metal/is_a.hh>
00048 
00049 namespace mln
00050 {
00051 
00052   namespace io
00053   {
00054 
00055     namespace pnm
00056     {
00057 
00058 
00059 # ifndef MLN_INCLUDE_ONLY
00060 
00061       template <typename I>
00062       void load_ascii_value(std::ifstream& file, I& ima);
00063 
00064       template <typename I>
00065       void load_ascii_builtin(std::ifstream& file, I& ima);
00066 
00067 
00068       namespace internal
00069       {
00070 
00071         template <typename I>
00072         inline
00073         void
00074         load_ascii_dispatch(std::ifstream& file, I& ima, const metal::bool_<true>&)
00075         {
00076           load_ascii_value(file, ima);
00077         }
00078 
00079         template <typename I>
00080         inline
00081         void
00082         load_ascii_dispatch(std::ifstream& file, I& ima, const metal::bool_<false>&)
00083         {
00084           load_ascii_builtin(file, ima);
00085         }
00086 
00087       } // end of namespace mln::io::pnm::internal
00088 
00089 
00090       // Read a Milena rgb value (sizeof(int_u8) != 1).
00091       template <unsigned int n>
00092       inline
00093       void read_value(std::ifstream& file, value::rgb<n>& v)
00094       {
00095         typedef typename value::int_u<n>::enc E;
00096 
00097         E c;
00098         file.read((char*)(&c), sizeof(E));
00099         v.red() = c;
00100         file.read((char*)(&c), sizeof(E));
00101         v.green() = c;
00102         file.read((char*)(&c), sizeof(E));
00103         v.blue() = c;
00104       }
00105 
00106       // Read a Milena scalar value (sizeof(int_u8) != 1).
00107       template <class V>
00108       inline
00109       void read_value(std::ifstream& file, value::Scalar<V>& v)
00110       {
00111         typedef typename V::enc E;
00112 
00113         E c;
00114         file.read((char*)(&c), sizeof(E));
00115         exact(v) = c;
00116       }
00117 
00118       // Read a builtin scalar value.
00119       template <typename V>
00120       inline
00121       void read_value(std::ifstream& file, V& v)
00122       {
00123         V c;
00124         file.read((char*)(&c), sizeof(V));
00125         v = c;
00126       }
00127 
00128       // used when (sizeof(int_u8) != 1)
00129       template <typename V>
00130       inline
00131       void load_raw_2d_uncontiguous(std::ifstream& file, image2d<V>& ima)
00132       {
00133         const def::coord
00134           min_row = geom::min_row(ima),
00135           max_row = geom::max_row(ima),
00136           min_col = geom::min_col(ima),
00137           max_col = geom::max_col(ima);
00138 
00139         point2d p;
00140         for (p.row() = min_row; p.row() <= max_row; ++p.row())
00141           for (p.col() = min_col; p.col() <= max_col; ++p.col())
00142             read_value(file, ima(p));
00143       }
00144 
00145       // used in g++ > 2.95
00146       template <typename I>
00147       inline
00148       void load_raw_2d_contiguous(std::ifstream& file, I& ima)
00149       {
00150         point2d p = point2d(0, ima.domain().pmin().col());
00151         typedef mln_value(I) V;
00152         const mln_deduce(I, site, coord)
00153           min_row = geom::min_row(ima),
00154           max_row = geom::max_row(ima);
00155 
00156         std::size_t len = geom::ncols(ima) * sizeof(V);
00157         for (p.row() = min_row; p.row() <= max_row; ++p.row())
00158           file.read((char*)(&ima(p)), len);
00159       }
00160 
00162       template <typename I>
00163       inline
00164       void load_ascii_value(std::ifstream& file, I& ima)
00165       {
00166         mln_equiv(mln_value_(I)) c;
00167         mln_fwd_piter(I) p(ima.domain());
00168         for_all(p)
00169         {
00170           file >> c;
00171           ima(p) = c;
00172         }
00173       }
00174 
00176       template <typename I>
00177       inline
00178       void load_ascii_builtin(std::ifstream& file, I& ima)
00179       {
00180         mln_fwd_piter(I) p(ima.domain());
00181 
00182         // FIXME: May be wrong!
00183         // Worked out with an image with a max value of 255
00184         // loaded in an image2d<unsigned char>.
00185         unsigned n;
00186 
00187         for_all(p)
00188         {
00189           file >> n;
00190           ima(p) = n;
00191         }
00192       }
00193 
00196       template <typename I>
00197       inline
00198       void load_raw_2d(std::ifstream& file, I& ima)
00199       {
00200         typedef mln_value(I) V;
00201         if (sizeof(V) == 1)
00202           load_raw_2d_contiguous(file, ima);
00203         else
00204           load_raw_2d_uncontiguous(file, ima);
00205       }
00206 
00208       template <typename V>
00209       inline
00210       image2d<V> load(char type_, const std::string& filename)
00211       {
00212         trace::entering("mln::io::pnm::load");
00213 
00214         std::ifstream file(filename.c_str());
00215         if (! file)
00216         {
00217           std::cerr << "error: file '" << filename
00218                     << "' not found!";
00219           abort();
00220         }
00221         char type = 0;
00222         int nrows, ncols;
00223         unsigned int maxval;
00224         read_header(static_cast<char>(type_ - 3), type_, file, type,
00225                     nrows, ncols, maxval);
00226 
00227         if (max_component(V()) != maxval)
00228         {
00229           std::cerr << "error: file '" << filename
00230                     << "' cannot be loaded into this type of image"
00231                     << std::endl;
00232 
00233           std::cerr << "input image have " << maxval
00234                     << " as maximum value while the destination's one is "
00235                     << max_component(V()) << " (should be the same)."
00236                     << std::endl;
00237           abort();
00238         }
00239 
00240         image2d<V> ima(nrows, ncols);
00241         if (type == type_)
00242           load_raw_2d(file, ima);
00243         else
00244           if (type == (type_ - 3))
00245             pnm::internal::load_ascii_dispatch(file, ima, mlc_is_a(V, mln::Value)());
00246 
00247         trace::exiting("mln::io::pnm::load");
00248 
00249         return ima;
00250       }
00251 
00255       template <typename I>
00256       inline
00257       void load(char type_,
00258                 Image<I>& ima_,
00259                 const std::string& filename)
00260       {
00261         trace::entering("mln::io::pnm::load");
00262 
00263         std::ifstream file(filename.c_str());
00264         if (! file)
00265         {
00266           std::cerr << "error: file '" << filename
00267                     << "' not found!";
00268           abort();
00269         }
00270 
00271         I& ima = exact(ima_);
00272 
00273         char type = 0;
00274         int nrows, ncols;
00275         unsigned int maxval;
00276         read_header(static_cast<char>(type_ - 3), type_, file, type,
00277                     nrows, ncols, maxval);
00278 
00279         if (max_component(mln_value(I)()) != maxval)
00280         {
00281           std::cerr << "error: file '" << filename
00282                     << "' cannot be loaded into this type of image"
00283                     << std::endl;
00284 
00285           std::cerr << "input image have " << maxval
00286                     << " as maximum value while the destination's one is "
00287                     << max_component(mln_value(I)()) << "."
00288                     << std::endl;
00289           abort();
00290         }
00291 
00292         ima.init_(make::box2d(nrows, ncols));
00293         if (type == type_)
00294           load_raw_2d(file, ima);
00295         else
00296           if (type == (type_ - 3))
00297             pnm::internal::load_ascii_dispatch(file, ima, mlc_is_a(mln_value(I), mln::Value)());
00298 
00299         trace::exiting("mln::io::pnm::load");
00300       }
00301 
00302 # endif // ! MLN_INCLUDE_ONLY
00303 
00304     } // end of namespace mln::io::pnm
00305 
00306   } // end of namespace mln::io
00307 
00308 } // end of namespace mln
00309 
00310 
00311 #endif // ! MLN_IO_PNM_LOAD_HH

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