SMIL  1.0.4
DImageIO_PBM.hpp
1 /*
2  * Copyright (c) 2011-2016, Matthieu FAESSEL and ARMINES
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * * Redistributions of source code must retain the above copyright
9  * notice, this list of conditions and the following disclaimer.
10  * * Redistributions in binary form must reproduce the above copyright
11  * notice, this list of conditions and the following disclaimer in the
12  * documentation and/or other materials provided with the distribution.
13  * * Neither the name of Matthieu FAESSEL, or ARMINES nor the
14  * names of its contributors may be used to endorse or promote products
15  * derived from this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS''
18  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS AND CONTRIBUTORS BE
21  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27  * POSSIBILITY OF SUCH DAMAGE.
28  */
29 
30 #ifndef _D_IMAGE_IO_PBM_H
31 #define _D_IMAGE_IO_PBM_H
32 
33 #include <fstream>
34 #include <iostream>
35 
36 #include "Core/include/private/DTypes.hpp"
37 #include "Core/include/private/DImage.hpp"
38 #include "IO/include/private/DImageIO.hpp"
39 
40 namespace smil
41 {
45  /* *@{*/
46 
47  RES_T readNetPBMFileInfo(ifstream &fp, ImageFileInfo &fInfo,
48  unsigned int &maxval);
49  RES_T readNetPBMFileInfo(const char *filename, ImageFileInfo &fInfo,
50  unsigned int &maxval);
51 
52  template <class T> class Image;
53 
54  template <class T = void>
56  {
57  public:
59  {
60  }
61 
62  virtual RES_T getFileInfo(const char *filename, ImageFileInfo &fInfo)
63  {
64  unsigned int dum;
65  fInfo.filename = filename;
66  return readNetPBMFileInfo(filename, fInfo, dum);
67  }
68 
69  virtual RES_T read(const char *filename, Image<T> &image)
70  {
71  return ImageFileHandler<T>::read(filename, image);
72  }
73  virtual RES_T write(const Image<T> &image, const char *filename)
74  {
75  return ImageFileHandler<T>::write(image, filename);
76  }
77  };
78 
79  template <class T = void>
81  {
82  public:
84  {
85  }
86 
87  virtual RES_T getFileInfo(const char *filename, ImageFileInfo &fInfo)
88  {
89  unsigned int dum;
90  return readNetPBMFileInfo(filename, fInfo, dum);
91  }
92 
93  virtual RES_T read(const char *filename, Image<T> &image)
94  {
95  /* open image file */
96  ifstream fp(filename, ios_base::binary);
97 
98  if (!fp.is_open()) {
99  cout << "Cannot open file " << filename << endl;
100  return RES_ERR_IO;
101  }
102 
103  ImageFileInfo fInfo;
104  unsigned int dum; // no maxval in PBM format
105  ASSERT(readNetPBMFileInfo(fp, fInfo, dum) == RES_OK, RES_ERR_IO);
106  ASSERT(fInfo.colorType == ImageFileInfo::COLOR_TYPE_BINARY,
107  "Not an binary image", RES_ERR_IO);
108 
109  size_t width = fInfo.width;
110  size_t height = fInfo.height;
111 
112  ASSERT((image.setSize(width, height) == RES_OK), RES_ERR_BAD_ALLOCATION);
113 
114  if (fInfo.fileType == ImageFileInfo::FILE_TYPE_BINARY) {
115  typename ImDtTypes<T>::sliceType lines = image.getLines();
116 
117  // int nBytePerLine = width%8==0 ? width/8 : width/8+1;
118  char val;
119  int k;
120 
121  for (size_t j = 0; j < height; j++) {
122  typename ImDtTypes<T>::lineType pixels = lines[j];
123 
124  for (size_t i = 0; i < width; i++) {
125  if (i % 8 == 0)
126  fp.read(&val, 1);
127 
128  k = 7 - i % 8;
129  pixels[i] = ((val >> k) % 2) == 0 ? T(0) : ImDtTypes<T>::max();
130  }
131  }
132  } else {
133  typename ImDtTypes<T>::lineType pixels = image.getPixels();
134 
135  int val;
136  for (size_t i = 0; i < image.getPixelCount(); i++) {
137  fp >> val;
138  pixels[i] = val == 0 ? T(0) : ImDtTypes<T>::max();
139  }
140  }
141 
142  fp.close();
143 
144  return RES_OK;
145  }
146  virtual RES_T write(const Image<T> &image, const char *filename)
147  {
148  return ImageFileHandler<T>::write(image, filename);
149  }
150  };
151 
152  template <>
153  inline RES_T PBMImageFileHandler<void>::read(const char *, Image<void> &)
154  {
155  return RES_ERR;
156  }
157 
158  template <>
159  inline RES_T PBMImageFileHandler<void>::write(const Image<void> &,
160  const char *)
161  {
162  return RES_ERR;
163  }
164 
165  // Specializations
166  IMAGEFILEHANDLER_TEMP_SPEC(PGM, UINT8);
167 
168 #ifdef SMIL_WRAP_RGB
169  IMAGEFILEHANDLER_TEMP_SPEC(PGM, RGB);
170 #endif // SMIL_WRAP_RGB
171 
172  /* *@}*/
173 
174 } // namespace smil
175 
176 #endif // _D_IMAGE_IO_PBM_H
size_t getPixelCount() const
Get the number of pixels.
Definition: DBaseImage.h:160
Definition: DImageIO.hpp:45
Main Image class.
Definition: DImage.hpp:57
lineType getPixels() const
Get the pixels as a 1D array.
Definition: DImage.hpp:105
sliceType getLines() const
Get an array containing the start offset of each line.
Definition: DImage.hpp:111
virtual RES_T setSize(size_t w, size_t h, size_t d=1, bool doAllocate=true)
Set the size of image.
Definition: DImageIO_PBM.hpp:81
Definition: DImageIO_PBM.hpp:56
Definition: DTypes.hpp:88
Definition: DCommonIO.h:72