Visualization 2 - Lab Course
 All Classes Functions Enumerations Enumerator
Volume.h
1 #ifndef VOLUME_H
2 #define VOLUME_H
3 
4 #include <vector>
5 
6 #include <algorithm>
7 #include <functional>
8 
9 #include <iostream>
10 
11 #define min_val(VAL_X, VAL_Y) ((VAL_X < VAL_Y) ? VAL_X : VAL_Y)
12 
13 // Simple linear volume class which supports loading from DAT files
14 class Volume
15 {
16 public:
17 
18  class Voxel
19  {
20  public:
21 
22  Voxel()
23  {
24  SetValue(0.0f);
25  };
26 
27  Voxel(const Voxel & datOther)
28  {
29  m_fValue = datOther.m_fValue;
30  };
31 
32  Voxel(const float fValue)
33  {
34  SetValue(fValue);
35  };
36 
37 
38  ~Voxel()
39  {
40  };
41 
42  void SetValue(const float fValue)
43  {
44  m_fValue = fValue;
45  };
46 
47  float GetValue() const
48  {
49  return m_fValue;
50  };
51 
52  bool operator==(const Voxel &datOther) const
53  {
54  return (GetValue() == datOther.GetValue());
55  };
56 
57  bool operator!=(const Voxel &datOther) const
58  {
59  return !(*this == datOther);
60  };
61 
62  bool operator>(const Voxel &datOther) const
63  {
64  return GetValue() > datOther.GetValue();
65  };
66 
67  bool operator>=(const Voxel &datOther) const
68  {
69  return GetValue() >= datOther.GetValue();
70  };
71 
72  bool operator<(const Voxel &datOther) const
73  {
74  return GetValue() < datOther.GetValue();
75  };
76 
77  bool operator<=(const Voxel &datOther) const
78  {
79  return GetValue() <= datOther.GetValue();
80  };
81 
82  const Voxel & operator+=(const Voxel & datOther)
83  {
84  m_fValue += datOther.m_fValue;
85  return *this;
86  };
87 
88  const Voxel & operator-=(const Voxel & datOther)
89  {
90  m_fValue -= datOther.m_fValue;
91  return *this;
92  };
93 
94  const Voxel & operator*=(const float & fOther)
95  {
96  m_fValue *= fOther;
97  return *this;
98  };
99 
100  const Voxel & operator/=(const float & fOther)
101  {
102  m_fValue /= fOther;
103  return *this;
104  };
105 
106  const Voxel operator+(const Voxel & datOther) const
107  {
108  Voxel voxNew = *this;
109  voxNew += datOther;
110  return voxNew;
111  };
112 
113  const Voxel operator-(const Voxel & datOther) const
114  {
115  Voxel voxNew = *this;
116  voxNew -= datOther;
117  return voxNew;
118  };
119 
120  const Voxel operator*(const float & fOther) const
121  {
122  Voxel voxNew = *this;
123  voxNew *= fOther;
124  return voxNew;
125  };
126 
127  const Voxel operator/(const float & fOther) const
128  {
129  Voxel voxNew = *this;
130  voxNew /= fOther;
131  return voxNew;
132  };
133 
134  private:
135  float m_fValue;
136  };
137 
138 public:
139  Volume() : m_iWidth(1), m_iHeight(1), m_iDepth(1), m_vecVoxels(1)
140  {
141  };
142 
143  Volume(const std::string &strFilename) : m_iWidth(1), m_iHeight(1), m_iDepth(1), m_vecVoxels(1)
144  {
145  loadRaw(strFilename, 64, 64, 64);
146  //load(strFilename);
147  };
148 
149  ~Volume(void)
150  {
151  };
152 
153  const Voxel & Get(const int iX, const int iY, const int iZ) const
154  {
155  return m_vecVoxels[iX + iY*m_iWidth + iZ*m_iWidth*m_iHeight];
156  };
157 
158  const Voxel & Get(const int iIndex) const
159  {
160  return m_vecVoxels[iIndex];
161  };
162 
163  const Voxel * Get() const
164  {
165  return &(m_vecVoxels.front());
166  };
167 
168  int GetWidth() const
169  {
170  return m_iWidth;
171  };
172 
173  int GetHeight() const
174  {
175  return m_iHeight;
176  };
177 
178  int GetDepth() const
179  {
180  return m_iDepth;
181  };
182 
183  int GetSize() const
184  {
185  return int(m_vecVoxels.size());
186  };
187 
188 
189  void load(const std::string & strFilename)
190  {
191  qDebug() << "Loading volume file \'" <<strFilename.c_str() << "\'";
192  FILE* fp = NULL;
193 
194  fp = fopen(strFilename.c_str(),"rb");
195  if (!fp) {
196  std::cerr << "+ Error loading file." << std::endl << std::endl;
197  } else {
198  unsigned short uWidth, uHeight, uDepth;
199  fread(&uWidth,sizeof(unsigned short),1,fp);
200  fread(&uHeight,sizeof(unsigned short),1,fp);
201  fread(&uDepth,sizeof(unsigned short),1,fp);
202 
203  m_iWidth = int(uWidth);
204  m_iHeight = int(uHeight);
205  m_iDepth = int(uDepth);
206 
207  std::cout << "Dataset size: " << m_iWidth << " x " << m_iHeight << " x " << m_iDepth << std::endl;
208 
209  const int iSlice = m_iWidth * m_iHeight;
210  const int iSize = iSlice * m_iDepth;
211  m_vecVoxels.resize(iSize);
212 
213  std::vector<unsigned short> vecData;
214  vecData.resize(iSize);
215 
216  fread((void*)&(vecData.front()),sizeof(unsigned short),iSize,fp);
217  fclose(fp);
218 
219  std::cout << "- File loaded." << std::endl;
220 
221  for (int k=0;k<m_iDepth;k++) {
222  for (int j=0;j<m_iHeight;j++) {
223  for (int i=0;i<m_iWidth;i++) {
224  //we convert the data to float values in an interval of [0..1]
225  const float fValue = min_val(1.0f,float(vecData[i + j*m_iWidth + k*iSlice]) / 4095.0f);
226  m_vecVoxels[i+j*m_iWidth+k*iSlice] = Voxel(fValue);
227  }
228  }
229 
230  std::cout << "\r- Preparing data (" << (k*100) / (m_iDepth-1) << "%) ...";
231  }
232 
233  std::cout << std::endl << "- Data prepared." << std::endl;
234  }
235  };
236 
237  void loadRaw(const std::string & strFilename, const int iWidth, const int iHeight, const int iDepth)
238  {
239  std::cout << "- Loading RAW file '" << strFilename << "' ... " << std::endl;
240  FILE* fp = NULL;
241 
242  fp = fopen(strFilename.c_str(),"rb");
243  if (!fp) {
244  std::cerr << "+ Error loading file." << std::endl << std::endl;
245  return;
246  }
247 
248  m_iWidth = iWidth;
249  m_iHeight = iHeight;
250  m_iDepth = iDepth;
251 
252  const int iSlice = m_iWidth * m_iHeight;
253  const int iSize = iSlice * m_iDepth;
254 
255  m_vecVoxels.resize(iSize);
256 
257  std::vector<unsigned short> vecData;
258  vecData.resize(iSize);
259 
260  fread((void*)&(vecData.front()),sizeof(unsigned short),iSize,fp);
261  fclose(fp);
262 
263  std::cout << "- File loaded." << std::endl;
264 
265  for (int k=0;k<m_iDepth;k++) {
266  for (int j=0;j<m_iHeight;j++) {
267  for (int i=0;i<m_iWidth;i++) {
268  //we convert the data to float values in an interval of [0..1]
269  const float fValue = min_val(1.0f,float(vecData[i + j*m_iWidth + k*iSlice]) / 4095.0f);
270  m_vecVoxels[i+j*m_iWidth+k*iSlice] = Voxel(fValue);
271  }
272  }
273 
274  std::cout << "\r- Preparing data (" << (k*100) / (m_iDepth-1) << "%) ...";
275  }
276 
277  std::cout << std::endl << "- Data prepared." << std::endl;
278  };
279 
280 protected:
281 
282 private:
283  int m_iWidth,m_iHeight,m_iDepth;
284  std::vector<Voxel> m_vecVoxels;
285 
286 };
287 
288 #endif //VOLUME_H