LineReader.cpp
Go to the documentation of this file.
1 
28 /*
29  * LineReader.cpp
30  *
31  * Created on: Aug 15, 2017
32  * Author: Isaak Mitschke
33  */
34 
35 #include <boost/algorithm/string.hpp>
36 #include <cerrno>
37 #include <exception>
38 #include <fstream>
39 #include <iostream>
40 #include <memory>
41 #include <sstream>
42 #include <stdio.h>
43 
44 #include "lvr2/io/LineReader.hpp"
45 
46 namespace lvr2
47 {
48 
50 
51 LineReader::LineReader(std::vector<std::string> filePaths)
53 {
54  open(filePaths);
55 }
56 
57 LineReader::LineReader(std::string filePath)
59 {
60  open(filePath);
61 }
62 
64 {
65  size_t amount = 0;
66  for (size_t i = 0; i < m_fileAttributes.size(); i++)
67  {
68  amount += m_fileAttributes[i].m_elementAmount;
69  }
70  return amount;
71 }
72 
73 void LineReader::open(std::vector<std::string> filePaths)
74 {
75  m_fileAttributes.clear();
76  for (size_t currentFile = 0; currentFile < filePaths.size(); currentFile++)
77  {
78  fileAttribut currentAttr;
79  std::string filePath = filePaths[currentFile];
80  currentAttr.m_filePath = filePath;
81  bool gotxyz = false;
82  bool gotcolor = false;
83  bool gotnormal = false;
84  bool readHeader = false;
85 
86  if (boost::algorithm::contains(filePath, ".ply"))
87  {
88  // Todo: Check if all files are same type;
89  currentAttr.m_ply = true;
90  }
91  else
92  {
93  currentAttr.m_ply = false;
94  }
95 
96  std::ifstream ifs(filePath);
97 
98  if (currentAttr.m_ply)
99  {
100  std::string line;
101  while (!readHeader)
102  {
103  std::getline(ifs, line);
104  if (boost::algorithm::contains(line, "element vertex") ||
105  boost::algorithm::contains(line, "element point"))
106  {
107  std::stringstream ss(line);
108  string tmp;
109  ss >> tmp;
110  ss >> tmp;
111  ss >> currentAttr.m_elementAmount;
112  }
113  else if (boost::algorithm::contains(line, "property float x") ||
114  boost::algorithm::contains(line, "property float y") ||
115  boost::algorithm::contains(line, "property float z") ||
116  boost::algorithm::contains(line, "property float32 x") ||
117  boost::algorithm::contains(line, "property float32 y") ||
118  boost::algorithm::contains(line, "property float32 z"))
119  {
120  gotxyz = true;
121  }
122  else if (boost::algorithm::contains(line, "property uchar red") ||
123  boost::algorithm::contains(line, "property uchar green") ||
124  boost::algorithm::contains(line, "property uchar blue"))
125  {
126  gotcolor = true;
127  }
128  else if (boost::algorithm::contains(line, "property float nx") ||
129  boost::algorithm::contains(line, "property float ny") ||
130  boost::algorithm::contains(line, "property float nz"))
131  {
132  gotnormal = true;
133  }
134  else if (boost::algorithm::contains(line, "end_header"))
135  {
136  readHeader = true;
137  }
138  else if (boost::algorithm::contains(line, "binary"))
139  {
140  currentAttr.m_binary = true;
141  }
142  else if (boost::algorithm::contains(line, "ascii"))
143  {
144  currentAttr.m_binary = false;
145  }
146  else if (boost::algorithm::contains(line, "property list"))
147  {
148  // Todo...
149  }
150  else if (boost::algorithm::contains(line, "property"))
151  {
152  throw readException((line + " is currently not supported \n supported "
153  "properties: x y z [red green blue] [nx ny nz]")
154  .c_str());
155  }
156  }
157  std::cout << "FINISHED READING HEADER" << std::endl;
158  std::cout << "XYT: " << gotxyz << std::endl;
159  std::cout << "COLOR: " << gotcolor << std::endl;
160  std::cout << "NORMAL: " << gotnormal << std::endl;
161  std::cout << "BINARY: " << currentAttr.m_binary << std::endl;
162  std::cout << "Points: " << currentAttr.m_elementAmount << std::endl;
163  }
164  else
165  {
166  std::cout << "File Type is not PLY, checking file... " << std::endl;
167  std::string line;
168  std::getline(ifs, line);
169  std::stringstream ss(line);
170  string tmp;
171  unsigned int number_of_line_elements = 0;
172  while (ss >> tmp)
173  {
174  number_of_line_elements++;
175  if (number_of_line_elements >= 3)
176  gotxyz = true;
177  if (number_of_line_elements == 6)
178  {
179  if (boost::algorithm::contains(tmp, "."))
180  {
181  gotnormal = true;
182  }
183  else
184  {
185  gotcolor = true;
186  }
187  }
188  if (number_of_line_elements == 9)
189  {
190  gotnormal = true;
191  gotcolor = true;
192  }
193  if (number_of_line_elements > 9)
194  {
195  throw std::range_error("Wrong file format, expecting file ascii or ply file "
196  "format, ascii file format must have order: x y z [nx "
197  "ny nz] [cx cy cz] (points, normals, colors)");
198  }
199  }
200  currentAttr.m_line_element_amount = number_of_line_elements;
201  ifs.seekg(0);
202  }
203 
204  currentAttr.m_filePos = ifs.tellg();
205  if (gotxyz && gotcolor && gotnormal)
206  {
207  currentAttr.m_fileType = XYZNRGB;
208  currentAttr.m_PointBlockSize =
209  sizeof(float) * 3 + sizeof(unsigned char) * 3 + sizeof(float) * 3;
210  }
211  else if (gotxyz && gotcolor && !gotnormal)
212  {
213  currentAttr.m_fileType = XYZRGB;
214  currentAttr.m_PointBlockSize = sizeof(float) * 3 + sizeof(unsigned char) * 3;
215  }
216  else if (gotxyz && !gotcolor && gotnormal)
217  {
218  currentAttr.m_fileType = XYZN;
219  currentAttr.m_PointBlockSize = sizeof(float) * 3 + sizeof(float) * 3;
220  }
221  else if (gotxyz && !gotcolor && !gotnormal)
222  {
223  currentAttr.m_fileType = XYZ;
224  currentAttr.m_PointBlockSize = sizeof(float) * 3;
225  }
226  else
227  {
228  throw std::range_error("Did not find any points in data");
229  }
230  ifs.close();
231  m_fileAttributes.push_back(currentAttr);
232  }
233 }
234 
235 void LineReader::open(std::string filePath)
236 {
237  std::vector<std::string> tmp;
238  tmp.push_back(filePath);
239  open(tmp);
240 }
241 
243 {
244  if (i < m_fileAttributes.size())
245  {
246  return m_fileAttributes[i].m_fileType;
247  }
248  else
249  {
250  throw readException("There is no file with selected index\n (maybe you forgot to rewind "
251  "LineReader when reading file again?)");
252  }
253 }
255 
257 
258 boost::shared_ptr<void> LineReader::getNextPoints(size_t& return_amount, size_t amount)
259 {
260 
261  return_amount = 0;
262  if (m_openNextFile)
263  {
264  m_openNextFile = false;
266 
267  if (m_currentReadFile >= m_fileAttributes.size())
268  {
269  boost::shared_ptr<void> tmp;
270  return tmp;
271  }
272  }
273 
274  std::string filePath = m_fileAttributes[m_currentReadFile].m_filePath;
275 
276  FILE* pFile;
277  pFile = fopen(filePath.c_str(), "r");
278  if (pFile != NULL)
279  {
282  {
283  fseek(pFile, m_fileAttributes[m_currentReadFile].m_filePos, SEEK_SET);
284  size_t current_pos = ftell(pFile);
285  fseek(pFile, 0, SEEK_END);
286  size_t last_pos = ftell(pFile);
287  size_t data_left = last_pos - current_pos;
288  size_t bla;
289 
290  data_left = data_left / m_fileAttributes[m_currentReadFile].m_PointBlockSize;
291  size_t readSize = amount;
292  if (data_left < readSize)
293  {
294  readSize = data_left;
295  }
296  fseek(pFile, m_fileAttributes[m_currentReadFile].m_filePos, SEEK_SET);
297  boost::shared_ptr<void> pArray(
299  std::default_delete<char[]>());
300  bla = fread(pArray.get(),
301  m_fileAttributes[m_currentReadFile].m_PointBlockSize,
302  readSize,
303  pFile);
304  fclose(pFile);
305  m_fileAttributes[m_currentReadFile].m_filePos +=
306  readSize * m_fileAttributes[m_currentReadFile].m_PointBlockSize;
307  return_amount = bla;
308 
309  if (return_amount < amount)
310  m_openNextFile = true;
311  return pArray;
312  }
313  else
314  {
315  fseek(pFile, m_fileAttributes[m_currentReadFile].m_filePos, SEEK_SET);
316  size_t readCount = 0;
319  {
320 
321  std::vector<float> input;
322  input.reserve(amount * 3);
323  boost::shared_ptr<void> pArray(
325  std::default_delete<char[]>());
326  float ax, ay, az;
327  char lineBuffer[1024];
328  while ((fgets(lineBuffer, 1024, pFile) != NULL) && readCount < amount)
329  {
330  sscanf(lineBuffer, "%f %f %f", &ax, &ay, &az);
331  readCount++;
332  input.push_back(ax);
333  input.push_back(ay);
334  input.push_back(az);
335  }
336 
337  memcpy(pArray.get(),
338  input.data(),
339  m_fileAttributes[m_currentReadFile].m_PointBlockSize * readCount);
340  return_amount = readCount;
341  if (return_amount < amount)
342  m_openNextFile = true;
343  m_fileAttributes[m_currentReadFile].m_filePos = ftell(pFile);
344  fclose(pFile);
345  return pArray;
346  }
348  {
349  std::vector<float> input;
350  input.reserve(amount * 3);
351  boost::shared_ptr<void> pArray(
353  std::default_delete<char[]>());
354  float ax, ay, az;
355  while ((fscanf(pFile, "%f %f %f", &ax, &ay, &az) != EOF) && readCount < amount)
356  {
357  readCount++;
358  input.push_back(ax);
359  input.push_back(ay);
360  input.push_back(az);
361  }
362 
363  memcpy(pArray.get(),
364  input.data(),
365  m_fileAttributes[m_currentReadFile].m_PointBlockSize * readCount);
366  return_amount = readCount;
367  if (return_amount < amount)
368  {
369  m_openNextFile = true;
370  }
371  else
372  {
373  m_openNextFile = false;
374  }
375  m_fileAttributes[m_currentReadFile].m_filePos = ftell(pFile);
376  fclose(pFile);
377  return pArray;
378  }
380  {
381  std::vector<float> input;
382  input.reserve(amount * 6);
383  boost::shared_ptr<void> pArray(
385  std::default_delete<char[]>());
386  float ax, ay, az, nx, ny, nz;
387  while ((fscanf(pFile, "%f %f %f %f %f %f", &ax, &ay, &az, &nx, &ny, &nz) != EOF) &&
388  readCount < amount)
389  {
390  readCount++;
391  input.push_back(ax);
392  input.push_back(ay);
393  input.push_back(az);
394  }
395  memcpy(pArray.get(),
396  input.data(),
397  m_fileAttributes[m_currentReadFile].m_PointBlockSize * readCount);
398  return_amount = readCount;
399  if (return_amount < amount)
400  m_openNextFile = true;
401  m_fileAttributes[m_currentReadFile].m_filePos = ftell(pFile);
402  fclose(pFile);
403  return pArray;
404  }
406  {
407  std::vector<xyzc> input;
408  input.reserve(amount * 6);
409  boost::shared_ptr<void> pArray(
411  std::default_delete<char[]>());
412  xyzc pc;
413  float tmp_x, tmp_y, tmp_z;
414  unsigned char tmp_r, tmp_g, tmp_b;
415  while ((fscanf(pFile,
416  "%f %f %f %hhu %hhu %hhu", // don't read directly in to struct!
417  &tmp_x,
418  &tmp_y,
419  &tmp_z,
420  &tmp_r,
421  &tmp_g,
422  &tmp_b) != EOF) &&
423  readCount < amount)
424  {
425  pc.point.x = tmp_x;
426  pc.point.y = tmp_y;
427  pc.point.z = tmp_z;
428  pc.color.r = tmp_r;
429  pc.color.g = tmp_g;
430  pc.color.b = tmp_b;
431  readCount++;
432  input.push_back(pc);
433  }
434  memcpy(pArray.get(),
435  input.data(),
436  m_fileAttributes[m_currentReadFile].m_PointBlockSize * readCount);
437  return_amount = readCount;
438  if (return_amount < amount)
439  m_openNextFile = true;
440  m_fileAttributes[m_currentReadFile].m_filePos = ftell(pFile);
441  fclose(pFile);
442  return pArray;
443  }
445  {
446  std::vector<xyznc> input;
447  input.reserve(amount * 6);
448  boost::shared_ptr<void> pArray(
450  std::default_delete<char[]>());
451  xyznc pc;
452  float tmp_x, tmp_y, tmp_z, tmp_nx, tmp_ny, tmp_nz;
453  unsigned char tmp_r, tmp_g, tmp_b;
454  while ((fscanf(pFile,
455  "%f %f %f %hhu %hhu %hhu %f %f %f",
456  &tmp_x,
457  &tmp_y,
458  &tmp_z,
459  &tmp_r,
460  &tmp_g,
461  &tmp_b,
462  &tmp_nx,
463  &tmp_ny,
464  &tmp_nz) != EOF) &&
465  readCount < amount)
466  {
467  pc.point.x = tmp_x;
468  pc.point.y = tmp_y;
469  pc.point.z = tmp_z;
470  pc.color.r = tmp_r;
471  pc.color.g = tmp_g;
472  pc.color.b = tmp_b;
473  pc.normal.x = tmp_nx;
474  pc.normal.y = tmp_ny;
475  pc.normal.z = tmp_nz;
476  readCount++;
477  input.push_back(pc);
478  }
479  memcpy(pArray.get(),
480  input.data(),
481  m_fileAttributes[m_currentReadFile].m_PointBlockSize * readCount);
482  return_amount = readCount;
483  m_fileAttributes[m_currentReadFile].m_filePos = ftell(pFile);
484  if (return_amount < amount)
485  {
486  m_openNextFile = true;
487  }
488  fclose(pFile);
489  return pArray;
490  }
491  }
492  fclose(pFile);
493  }
494  else
495  {
496  std::cout << "SHIT could not open file: " << std::strerror(errno) << std::endl;
497  }
498 
499  // Return empty pointer if all else fails...
500  boost::shared_ptr<void> tmp;
501  return tmp;
502 }
503 
505 {
506  std::vector<std::string> tmp;
507  for (size_t i = 0; i < m_fileAttributes.size(); i++)
508  {
509  tmp.push_back(m_fileAttributes[i].m_filePath);
510  }
511  open(tmp);
512  m_currentReadFile = 0;
513 }
514 
515 void LineReader::rewind(size_t i) { open(m_fileAttributes[i].m_filePath); }
516 
517 } // namespace lvr2
size_t m_PointBlockSize
Definition: LineReader.hpp:124
size_t getNumPoints()
Definition: LineReader.cpp:63
size_t m_line_element_amount
Definition: LineReader.hpp:127
size_t m_line_element_amount
Definition: LineReader.hpp:64
fileType m_fileType
Definition: LineReader.hpp:123
void open(std::string filePath)
Definition: LineReader.cpp:235
size_t m_currentReadFile
Definition: LineReader.hpp:129
boost::shared_ptr< void > getNextPoints(size_t &return_amount, size_t amount=1000000)
Definition: LineReader.cpp:258
std::vector< size_t > m_filePos
Definition: LineReader.hpp:121
fileType getFileType()
Definition: LineReader.cpp:254
std::string m_filePath
Definition: LineReader.hpp:57
std::vector< fileAttribut > m_fileAttributes
Definition: LineReader.hpp:131
#define NULL
Definition: mydefs.hpp:141


lvr2
Author(s): Thomas Wiemann , Sebastian Pütz , Alexander Mock , Lars Kiesow , Lukas Kalbertodt , Tristan Igelbrink , Johan M. von Behren , Dominik Feldschnieders , Alexander Löhr
autogenerated on Mon Feb 28 2022 22:46:08