OMReader.cc 17.5 KB
Newer Older
Jan Möbius's avatar
Jan Möbius committed
1
/* ========================================================================= *
Jan Möbius's avatar
Jan Möbius committed
2
3
 *                                                                           *
 *                               OpenMesh                                    *
Jan Möbius's avatar
Jan Möbius committed
4
 *           Copyright (c) 2001-2015, RWTH-Aachen University                 *
Jan Möbius's avatar
Typo    
Jan Möbius committed
5
 *           Department of Computer Graphics and Multimedia                  *
Jan Möbius's avatar
Jan Möbius committed
6
7
 *                          All rights reserved.                             *
 *                            www.openmesh.org                               *
Jan Möbius's avatar
Jan Möbius committed
8
 *                                                                           *
9
 *---------------------------------------------------------------------------*
Jan Möbius's avatar
Jan Möbius committed
10
11
 * This file is part of OpenMesh.                                            *
 *---------------------------------------------------------------------------*
12
 *                                                                           *
Jan Möbius's avatar
Jan Möbius committed
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
 * Redistribution and use in source and binary forms, with or without        *
 * modification, are permitted provided that the following conditions        *
 * are met:                                                                  *
 *                                                                           *
 * 1. Redistributions of source code must retain the above copyright notice, *
 *    this list of conditions and the following disclaimer.                  *
 *                                                                           *
 * 2. Redistributions in binary form must reproduce the above copyright      *
 *    notice, this list of conditions and the following disclaimer in the    *
 *    documentation and/or other materials provided with the distribution.   *
 *                                                                           *
 * 3. Neither the name of the copyright holder nor the names of its          *
 *    contributors may be used to endorse or promote products derived from   *
 *    this software without specific prior written permission.               *
 *                                                                           *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS       *
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED *
 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A           *
 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER *
 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,  *
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,       *
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR        *
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF    *
 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING      *
 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS        *
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.              *
Jan Möbius's avatar
Jan Möbius committed
39
40
 *                                                                           *
 * ========================================================================= */
41
42

/*===========================================================================*\
43
 *                                                                           *
44
45
 *   $Revision$                                                         *
 *   $Date$                   *
Jan Möbius's avatar
Jan Möbius committed
46
47
48
49
50
51
52
53
 *                                                                           *
\*===========================================================================*/


//== INCLUDES =================================================================


//STL
54
55
#include <vector>
#include <istream>
Jan Möbius's avatar
Jan Möbius committed
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
#include <fstream>

// OpenMesh
#include <OpenMesh/Core/System/config.h>
#include <OpenMesh/Core/System/omstream.hh>
#include <OpenMesh/Core/Utils/Endian.hh>
#include <OpenMesh/Core/IO/OMFormat.hh>
#include <OpenMesh/Core/IO/reader/OMReader.hh>


//=== NAMESPACES ==============================================================


namespace OpenMesh {
namespace IO {


//=== INSTANCIATE =============================================================


// register the OMReader singleton with MeshReader
_OMReader_  __OMReaderInstance;
_OMReader_&  OMReader() { return __OMReaderInstance; }



//=== IMPLEMENTATION ==========================================================


_OMReader_::_OMReader_()
{
87
  IOManager().register_module(this);
Jan Möbius's avatar
Jan Möbius committed
88
89
90
91
92
93
}


//-----------------------------------------------------------------------------


94
bool _OMReader_::read(const std::string& _filename, BaseImporter& _bi, Options& _opt)
Jan Möbius's avatar
Jan Möbius committed
95
96
{
  // check whether importer can give us an OpenMesh BaseKernel
97
98
  if (!_bi.kernel())
    return false;
Jan Möbius's avatar
Jan Möbius committed
99
100

  _opt += Options::Binary; // only binary format supported!
101
  fileOptions_ = Options::Binary;
Jan Möbius's avatar
Jan Möbius committed
102
103

  // Open file
104
  std::ifstream ifs(_filename.c_str(), std::ios::binary);
105
106
107
108
109
110
111

  /* Clear formatting flag skipws (Skip whitespaces). If set, operator>> will
   * skip bytes set to whitespace chars (e.g. 0x20 bytes) in
   * Property<bool>::restore.
   */
  ifs.unsetf(std::ios::skipws);

112
113
  if (!ifs.is_open() || !ifs.good()) {
    omerr() << "[OMReader] : cannot not open file " << _filename << std::endl;
Jan Möbius's avatar
Jan Möbius committed
114
115
    return false;
  }
116

Jan Möbius's avatar
Jan Möbius committed
117
118
  // Pass stream to read method, remember result
  bool result = read(ifs, _bi, _opt);
119

Jan Möbius's avatar
Jan Möbius committed
120
121
  // close input stream
  ifs.close();
122

123
124
  _opt = _opt & fileOptions_;

Jan Möbius's avatar
Jan Möbius committed
125
126
127
128
129
130
  return result;
}

//-----------------------------------------------------------------------------


131
bool _OMReader_::read(std::istream& _is, BaseImporter& _bi, Options& _opt)
Jan Möbius's avatar
Jan Möbius committed
132
{
133
  // check whether importer can give us an OpenMesh BaseKernel
134
135
  if (!_bi.kernel())
    return false;
136
137

  _opt += Options::Binary; // only binary format supported!
138
  fileOptions_ = Options::Binary;
139

140
141
  if (!_is.good()) {
    omerr() << "[OMReader] : cannot read from stream " << std::endl;
142
143
144
145
146
147
    return false;
  }

  // Pass stream to read method, remember result
  bool result = read_binary(_is, _bi, _opt);

148
149
  if (result)
    _opt += Options::Binary;
Jan Möbius's avatar
Jan Möbius committed
150

151
152
  _opt = _opt & fileOptions_;

153
  return result;
Jan Möbius's avatar
Jan Möbius committed
154
155
156
157
158
159
}



//-----------------------------------------------------------------------------

160
bool _OMReader_::read_ascii(std::istream& /* _is */, BaseImporter& /* _bi */, Options& /* _opt */) const
Jan Möbius's avatar
Jan Möbius committed
161
162
163
164
165
166
167
168
{
  // not supported yet!
  return false;
}


//-----------------------------------------------------------------------------

169
bool _OMReader_::read_binary(std::istream& _is, BaseImporter& _bi, Options& _opt) const
Jan Möbius's avatar
Jan Möbius committed
170
171
172
{
  bool swap = _opt.check(Options::Swap) || (Endian::local() == Endian::MSB);

173
  // Initialize byte counter
174
  bytes_ = 0;
Jan Möbius's avatar
Jan Möbius committed
175

176
  bytes_ += restore(_is, header_, swap);
Jan Möbius's avatar
Jan Möbius committed
177
178


179
180
  while (!_is.eof()) {
    bytes_ += restore(_is, chunk_header_, swap);
Jan Möbius's avatar
Jan Möbius committed
181

182
    if (_is.eof())
Jan Möbius's avatar
Jan Möbius committed
183
184
185
      break;

    // Is this a named property restore the name
186
    if (chunk_header_.name_) {
Jan Möbius's avatar
Jan Möbius committed
187
      OMFormat::Chunk::PropertyName pn;
188
      bytes_ += restore(_is, property_name_, swap);
Jan Möbius's avatar
Jan Möbius committed
189
190
191
192
    }

    // Read in the property data. If it is an anonymous or unknown named
    // property, then skip data.
193
    switch (chunk_header_.entity_) {
194
      case OMFormat::Chunk::Entity_Vertex:
195
196
197
        if (!read_binary_vertex_chunk(_is, _bi, _opt, swap))
          return false;
        break;
Jan Möbius's avatar
Jan Möbius committed
198
      case OMFormat::Chunk::Entity_Face:
199
200
201
        if (!read_binary_face_chunk(_is, _bi, _opt, swap))
          return false;
        break;
Jan Möbius's avatar
Jan Möbius committed
202
      case OMFormat::Chunk::Entity_Edge:
203
204
205
        if (!read_binary_edge_chunk(_is, _bi, _opt, swap))
          return false;
        break;
Jan Möbius's avatar
Jan Möbius committed
206
      case OMFormat::Chunk::Entity_Halfedge:
207
208
209
        if (!read_binary_halfedge_chunk(_is, _bi, _opt, swap))
          return false;
        break;
Jan Möbius's avatar
Jan Möbius committed
210
      case OMFormat::Chunk::Entity_Mesh:
211
212
213
        if (!read_binary_mesh_chunk(_is, _bi, _opt, swap))
          return false;
        break;
Jan Möbius's avatar
Jan Möbius committed
214
      default:
215
        return false;
Jan Möbius's avatar
Jan Möbius committed
216
    }
Jan Möbius's avatar
Jan Möbius committed
217

Jan Möbius's avatar
Jan Möbius committed
218
219
220
221
222
223
224
225
226
  }

  // File was successfully parsed.
  return true;
}


//-----------------------------------------------------------------------------

227
bool _OMReader_::can_u_read(const std::string& _filename) const
Jan Möbius's avatar
Jan Möbius committed
228
229
230
{
  // !!! Assuming BaseReader::can_u_parse( std::string& )
  // does not call BaseReader::read_magic()!!!
231
232
233
  if (this->BaseReader::can_u_read(_filename)) {
    std::ifstream ifile(_filename.c_str());
    if (ifile && can_u_read(ifile))
234
      return true;
Jan Möbius's avatar
Jan Möbius committed
235
236
237
238
239
  }
  return false;
}

//-----------------------------------------------------------------------------
240

241
bool _OMReader_::can_u_read(std::istream& _is) const
Jan Möbius's avatar
Jan Möbius committed
242
243
244
245
246
{
  std::vector<char> evt;
  evt.reserve(20);

  // read first 4 characters into a buffer
247
248
  while (evt.size() < 4)
    evt.push_back(static_cast<char>(_is.get()));
Jan Möbius's avatar
Jan Möbius committed
249

250
  // put back all read characters
Jan Möbius's avatar
Jan Möbius committed
251
  std::vector<char>::reverse_iterator it = evt.rbegin();
252
253
  while (it != evt.rend())
    _is.putback(*it++);
Jan Möbius's avatar
Jan Möbius committed
254
255

  // evaluate header information
256
  OMFormat::Header *hdr = (OMFormat::Header*) &evt[0];
Jan Möbius's avatar
Jan Möbius committed
257
258
259
260
261
262

  // first two characters must be 'OM'
  if (hdr->magic_[0] != 'O' || hdr->magic_[1] != 'M')
    return false;

  // 3rd characters defines the mesh type:
263
  switch (hdr->mesh_) {
Jan Möbius's avatar
Jan Möbius committed
264
265
266
267
268
269
270
    case 'T': // Triangle Mesh
    case 'Q': // Quad Mesh
    case 'P': // Polygonal Mesh
      break;
    default:  // ?
      return false;
  }
271

Jan Möbius's avatar
Jan Möbius committed
272
  // 4th characters encodes the version
273
  return supports(hdr->version_);
Jan Möbius's avatar
Jan Möbius committed
274
275
276
277
}

//-----------------------------------------------------------------------------

278
bool _OMReader_::supports(const OMFormat::uint8 /* version */) const
Jan Möbius's avatar
Jan Möbius committed
279
280
281
282
283
284
285
{
  return true;
}


//-----------------------------------------------------------------------------

286
bool _OMReader_::read_binary_vertex_chunk(std::istream &_is, BaseImporter &_bi, Options &_opt, bool _swap) const
Jan Möbius's avatar
Jan Möbius committed
287
288
289
{
  using OMFormat::Chunk;

290
  assert( chunk_header_.entity_ == Chunk::Entity_Vertex);
291

292
293
  OpenMesh::Vec3f v3f;
  OpenMesh::Vec2f v2f;
Jan Möbius's avatar
Jan Möbius committed
294
295
296
297
  OpenMesh::Vec3uc v3uc; // rgb

  OMFormat::Chunk::PropertyName custom_prop;

298
299
  size_t vidx = 0;
  switch (chunk_header_.type_) {
Jan Möbius's avatar
Jan Möbius committed
300
    case Chunk::Type_Pos:
301
      assert( OMFormat::dimensions(chunk_header_) == size_t(OpenMesh::Vec3f::dim()));
Jan Möbius's avatar
Jan Möbius committed
302

303
304
305
      for (; vidx < header_.n_vertices_ && !_is.eof(); ++vidx) {
        bytes_ += vector_restore(_is, v3f, _swap);
        _bi.add_vertex(v3f);
Jan Möbius's avatar
Jan Möbius committed
306
307
308
309
      }
      break;

    case Chunk::Type_Normal:
310
      assert( OMFormat::dimensions(chunk_header_) == size_t(OpenMesh::Vec3f::dim()));
Jan Möbius's avatar
Jan Möbius committed
311

312
      fileOptions_ += Options::VertexNormal;
313
314
      for (; vidx < header_.n_vertices_ && !_is.eof(); ++vidx) {
        bytes_ += vector_restore(_is, v3f, _swap);
315
        if (fileOptions_.vertex_has_normal() && _opt.vertex_has_normal())
316
          _bi.set_normal(VertexHandle(int(vidx)), v3f);
Jan Möbius's avatar
Jan Möbius committed
317
318
319
320
      }
      break;

    case Chunk::Type_Texcoord:
321
      assert( OMFormat::dimensions(chunk_header_) == size_t(OpenMesh::Vec2f::dim()));
Jan Möbius's avatar
Jan Möbius committed
322

323
      fileOptions_ += Options::VertexTexCoord;
324
325
      for (; vidx < header_.n_vertices_ && !_is.eof(); ++vidx) {
        bytes_ += vector_restore(_is, v2f, _swap);
326
        if (fileOptions_.vertex_has_texcoord() && _opt.vertex_has_texcoord())
327
          _bi.set_texcoord(VertexHandle(int(vidx)), v2f);
Jan Möbius's avatar
Jan Möbius committed
328
      }
329
      break;
Jan Möbius's avatar
Jan Möbius committed
330
331
332

    case Chunk::Type_Color:

333
      assert( OMFormat::dimensions(chunk_header_) == 3);
Jan Möbius's avatar
Jan Möbius committed
334

335
      fileOptions_ += Options::VertexColor;
336

337
338
      for (; vidx < header_.n_vertices_ && !_is.eof(); ++vidx) {
        bytes_ += vector_restore(_is, v3uc, _swap);
339
        if (fileOptions_.vertex_has_color() && _opt.vertex_has_color())
340
          _bi.set_color(VertexHandle(int(vidx)), v3uc);
Jan Möbius's avatar
Jan Möbius committed
341
342
343
344
      }
      break;

    case Chunk::Type_Custom:
345

346
      bytes_ += restore_binary_custom_data(_is, _bi.kernel()->_get_vprop(property_name_), header_.n_vertices_, _swap);
Jan Möbius's avatar
Jan Möbius committed
347
348
349
350
351
352
353
354

      vidx = header_.n_vertices_;

      break;

    default: // skip unknown chunks
    {
      omerr() << "Unknown chunk type ignored!\n";
355
356
      size_t size_of = header_.n_vertices_ * OMFormat::vector_size(chunk_header_);
      _is.ignore(size_of);
Jan Möbius's avatar
Jan Möbius committed
357
358
359
360
361
362
363
364
365
366
367
      bytes_ += size_of;
    }
  }

  // all chunk data has been read..?!
  return vidx == header_.n_vertices_;
}


//-----------------------------------------------------------------------------

368
bool _OMReader_::read_binary_face_chunk(std::istream &_is, BaseImporter &_bi, Options &_opt, bool _swap) const
Jan Möbius's avatar
Jan Möbius committed
369
370
371
{
  using OMFormat::Chunk;

372
  assert( chunk_header_.entity_ == Chunk::Entity_Face);
Jan Möbius's avatar
Jan Möbius committed
373

374
375
  size_t fidx = 0;
  OpenMesh::Vec3f v3f;  // normal
Jan Möbius's avatar
Jan Möbius committed
376
377
  OpenMesh::Vec3uc v3uc; // rgb

378
379
380
381
382
383
384
385
386
387
388
389
390
  switch (chunk_header_.type_) {
    case Chunk::Type_Topology: {
      BaseImporter::VHandles vhandles;
      size_t nV = 0;
      size_t vidx = 0;

      switch (header_.mesh_) {
        case 'T':
          nV = 3;
          break;
        case 'Q':
          nV = 4;
          break;
Jan Möbius's avatar
Jan Möbius committed
391
      }
392

393
394
395
      for (; fidx < header_.n_faces_; ++fidx) {
        if (header_.mesh_ == 'P')
          bytes_ += restore(_is, nV, Chunk::Integer_16, _swap);
Jan Möbius's avatar
Jan Möbius committed
396

397
398
399
        vhandles.clear();
        for (size_t j = 0; j < nV; ++j) {
          bytes_ += restore(_is, vidx, Chunk::Integer_Size(chunk_header_.bits_), _swap);
Jan Möbius's avatar
Jan Möbius committed
400

401
          vhandles.push_back(VertexHandle(int(vidx)));
402
        }
Jan Möbius's avatar
Jan Möbius committed
403

404
        _bi.add_face(vhandles);
Jan Möbius's avatar
Jan Möbius committed
405
406
      }
    }
407
      break;
Jan Möbius's avatar
Jan Möbius committed
408
409

    case Chunk::Type_Normal:
410
      assert( OMFormat::dimensions(chunk_header_) == size_t(OpenMesh::Vec3f::dim()));
Jan Möbius's avatar
Jan Möbius committed
411

412
      fileOptions_ += Options::FaceNormal;
413
414
      for (; fidx < header_.n_faces_ && !_is.eof(); ++fidx) {
        bytes_ += vector_restore(_is, v3f, _swap);
415
        if( fileOptions_.face_has_normal() && _opt.face_has_normal())
416
          _bi.set_normal(FaceHandle(int(fidx)), v3f);
Jan Möbius's avatar
Jan Möbius committed
417
418
419
420
421
      }
      break;

    case Chunk::Type_Color:

422
      assert( OMFormat::dimensions(chunk_header_) == 3);
Jan Möbius's avatar
Jan Möbius committed
423

424
      fileOptions_ += Options::FaceColor;
425
426
      for (; fidx < header_.n_faces_ && !_is.eof(); ++fidx) {
        bytes_ += vector_restore(_is, v3uc, _swap);
427
        if( fileOptions_.face_has_color() && _opt.face_has_color())
428
          _bi.set_color(FaceHandle(int(fidx)), v3uc);
Jan Möbius's avatar
Jan Möbius committed
429
430
431
432
      }
      break;

    case Chunk::Type_Custom:
433

434
      bytes_ += restore_binary_custom_data(_is, _bi.kernel()->_get_fprop(property_name_), header_.n_faces_, _swap);
Jan Möbius's avatar
Jan Möbius committed
435
436
437
438

      fidx = header_.n_faces_;

      break;
439

Jan Möbius's avatar
Jan Möbius committed
440
441
442
443
    default: // skip unknown chunks
    {
      omerr() << "Unknown chunk type ignore!\n";
      size_t size_of = OMFormat::chunk_data_size(header_, chunk_header_);
444
      _is.ignore(size_of);
445
      bytes_ += size_of;
Jan Möbius's avatar
Jan Möbius committed
446
447
448
449
450
451
452
453
    }
  }
  return fidx == header_.n_faces_;
}


//-----------------------------------------------------------------------------

454
bool _OMReader_::read_binary_edge_chunk(std::istream &_is, BaseImporter &_bi, Options &/*_opt */, bool _swap) const
Jan Möbius's avatar
Jan Möbius committed
455
456
457
{
  using OMFormat::Chunk;

458
  assert( chunk_header_.entity_ == Chunk::Entity_Edge);
Jan Möbius's avatar
Jan Möbius committed
459

460
  size_t b = bytes_;
Jan Möbius's avatar
Jan Möbius committed
461

462
  switch (chunk_header_.type_) {
463
    case Chunk::Type_Custom:
Jan Möbius's avatar
Jan Möbius committed
464

465
      bytes_ += restore_binary_custom_data(_is, _bi.kernel()->_get_eprop(property_name_), header_.n_edges_, _swap);
Jan Möbius's avatar
Jan Möbius committed
466
467
468
469
470
471

      break;

    default:
      // skip unknown type
      size_t size_of = OMFormat::chunk_data_size(header_, chunk_header_);
472
      _is.ignore(size_of);
Jan Möbius's avatar
Jan Möbius committed
473
474
475
476
477
478
479
480
481
      bytes_ += size_of;
  }

  return b < bytes_;
}


//-----------------------------------------------------------------------------

482
bool _OMReader_::read_binary_halfedge_chunk(std::istream &_is, BaseImporter &_bi, Options &/* _opt */, bool _swap) const
Jan Möbius's avatar
Jan Möbius committed
483
484
485
{
  using OMFormat::Chunk;

486
  assert( chunk_header_.entity_ == Chunk::Entity_Halfedge);
Jan Möbius's avatar
Jan Möbius committed
487
488
489

  size_t b = bytes_;

490
  switch (chunk_header_.type_) {
Jan Möbius's avatar
Jan Möbius committed
491
492
    case Chunk::Type_Custom:

493
      bytes_ += restore_binary_custom_data(_is, _bi.kernel()->_get_hprop(property_name_), 2 * header_.n_edges_, _swap);
Jan Möbius's avatar
Jan Möbius committed
494
495
496
497
498
499
      break;

    default:
      // skip unknown chunk
      omerr() << "Unknown chunk type ignored!\n";
      size_t size_of = OMFormat::chunk_data_size(header_, chunk_header_);
500
      _is.ignore(size_of);
Jan Möbius's avatar
Jan Möbius committed
501
502
503
504
505
506
507
508
509
      bytes_ += size_of;
  }

  return b < bytes_;
}


//-----------------------------------------------------------------------------

510
bool _OMReader_::read_binary_mesh_chunk(std::istream &_is, BaseImporter &_bi, Options & /* _opt */, bool _swap) const
Jan Möbius's avatar
Jan Möbius committed
511
512
513
{
  using OMFormat::Chunk;

514
  assert( chunk_header_.entity_ == Chunk::Entity_Mesh);
Jan Möbius's avatar
Jan Möbius committed
515
516
517

  size_t b = bytes_;

518
  switch (chunk_header_.type_) {
Jan Möbius's avatar
Jan Möbius committed
519
    case Chunk::Type_Custom:
520

521
      bytes_ += restore_binary_custom_data(_is, _bi.kernel()->_get_mprop(property_name_), 1, _swap);
522

Jan Möbius's avatar
Jan Möbius committed
523
524
525
526
527
      break;

    default:
      // skip unknown chunk
      size_t size_of = OMFormat::chunk_data_size(header_, chunk_header_);
528
      _is.ignore(size_of);
Jan Möbius's avatar
Jan Möbius committed
529
530
531
532
533
534
535
536
537
538
      bytes_ += size_of;
  }

  return b < bytes_;
}


//-----------------------------------------------------------------------------


539
size_t _OMReader_::restore_binary_custom_data(std::istream& _is, BaseProperty* _bp, size_t _n_elem, bool _swap) const
540
{
541
  assert( !_bp || (_bp->name() == property_name_));
Jan Möbius's avatar
Jan Möbius committed
542
543
544

  using OMFormat::Chunk;

545
546
  size_t bytes = 0;
  Chunk::esize_t block_size;
Jan Möbius's avatar
Jan Möbius committed
547
548
  Chunk::PropertyName custom_prop;

549
  bytes += restore(_is, block_size, OMFormat::Chunk::Integer_32, _swap);
Jan Möbius's avatar
Jan Möbius committed
550

551
552
  if (_bp) {
    size_t n_bytes = _bp->size_of(_n_elem);
Jan Möbius's avatar
Jan Möbius committed
553

554
555
    if (((n_bytes == BaseProperty::UnknownSize) || (n_bytes == block_size))
        && (_bp->element_size() == BaseProperty::UnknownSize || (_n_elem * _bp->element_size() == block_size))) {
Jan Möbius's avatar
Jan Möbius committed
556
#if defined(OM_DEBUG)
Jan Möbius's avatar
Jan Möbius committed
557
      size_t b;
Jan Möbius's avatar
Jan Möbius committed
558
559
      bytes += (b=_bp->restore( _is, _swap ));
#else
560
      bytes += _bp->restore(_is, _swap);
Jan Möbius's avatar
Jan Möbius committed
561
#endif
562

Jan Möbius's avatar
Jan Möbius committed
563
564
565
#if defined(OM_DEBUG)
      assert( block_size == b );
#endif
566
567

      assert( block_size == _bp->size_of());
Jan Möbius's avatar
Jan Möbius committed
568
569

      block_size = 0;
570
571
    } else {
      omerr() << "Warning! Property " << _bp->name() << " not loaded: " << "Mismatching data sizes!n";
Jan Möbius's avatar
Jan Möbius committed
572
573
574
    }
  }

575
576
577
  if (block_size) {
    _is.ignore(block_size);
    bytes += block_size;
Jan Möbius's avatar
Jan Möbius committed
578
579
580
581
582
583
584
585
586
587
588
589
  }

  return bytes;
}


//-----------------------------------------------------------------------------

//=============================================================================
} // namespace IO
} // namespace OpenMesh
//=============================================================================