diff --git a/src/OpenMesh/Core/IO/reader/PLYReader.cc b/src/OpenMesh/Core/IO/reader/PLYReader.cc
index bdebe908..4137ef86 100644
--- a/src/OpenMesh/Core/IO/reader/PLYReader.cc
+++ b/src/OpenMesh/Core/IO/reader/PLYReader.cc
@@ -4,10 +4,10 @@
* Copyright (C) 2001-2009 by Computer Graphics Group, RWTH Aachen *
* www.openmesh.org *
* *
- *---------------------------------------------------------------------------*
+ *---------------------------------------------------------------------------*
* This file is part of OpenMesh. *
* *
- * OpenMesh is free software: you can redistribute it and/or modify *
+ * OpenMesh is free software: you can redistribute it and/or modify *
* it under the terms of the GNU Lesser General Public License as *
* published by the Free Software Foundation, either version 3 of *
* the License, or (at your option) any later version with the *
@@ -30,19 +30,17 @@
* License along with OpenMesh. If not, *
* see . *
* *
-\*===========================================================================*/
+ \*===========================================================================*/
/*===========================================================================*\
- * *
+ * *
* $Revision$ *
* $Date$ *
* *
-\*===========================================================================*/
-
+ \*===========================================================================*/
#define LINE_LEN 4096
-
//== INCLUDES =================================================================
// OpenMesh
@@ -68,628 +66,586 @@
namespace OpenMesh {
namespace IO {
-
//=============================================================================
//=== INSTANCIATE =============================================================
-_PLYReader_ __PLYReaderInstance;
-_PLYReader_& PLYReader() { return __PLYReaderInstance; }
-
+_PLYReader_ __PLYReaderInstance;
+_PLYReader_& PLYReader() {
+ return __PLYReaderInstance;
+}
//=== IMPLEMENTATION ==========================================================
-
-_PLYReader_::_PLYReader_()
-{
- IOManager().register_module(this);
-}
-
-
-//-----------------------------------------------------------------------------
-
-
-bool
-_PLYReader_::read(const std::string& _filename, BaseImporter& _bi,
- Options& _opt)
-{
- std::fstream in(_filename.c_str(), (options_.is_binary() ? std::ios_base::binary | std::ios_base::in
- : std::ios_base::in) );
-
- if (!in)
- {
- omerr() << "[PLYReader] : cannot not open file "
- << _filename
- << std::endl;
- return false;
- }
-
-
- bool result = read(in, _bi, _opt);
-
-
- in.close();
- return result;
-}
-
-
-//-----------------------------------------------------------------------------
-
-
-bool
-_PLYReader_::read(std::fstream& _in, BaseImporter& _bi, Options& _opt ) const
-{
- // filter relevant options for reading
- bool swap = _opt.check( Options::Swap );
-
-
- userOptions_ = _opt;
-
- // build options to be returned
- _opt.clear();
-
- if (options_.vertex_has_normal() && userOptions_.vertex_has_normal()) _opt += Options::VertexNormal;
- if (options_.vertex_has_texcoord() && userOptions_.vertex_has_texcoord()) _opt += Options::VertexTexCoord;
- if (options_.vertex_has_color() && userOptions_.vertex_has_color()) _opt += Options::VertexColor;
- if (options_.face_has_color() && userOptions_.face_has_color()) _opt += Options::FaceColor;
- if (options_.is_binary()) _opt += Options::Binary;
-
-// //force user-choice for the alpha value when reading binary
-// if ( options_.is_binary() && userOptions_.color_has_alpha() )
-// options_ += Options::ColorAlpha;
-
- return (options_.is_binary() ?
- read_binary(_in, _bi, swap) :
- read_ascii(_in, _bi));
-
-}
-
-
-
-//-----------------------------------------------------------------------------
-
-bool
-_PLYReader_::read_ascii(std::fstream& _in, BaseImporter& _bi) const
-{
-
-
- omlog() << "[PLYReader] : read ascii file\n";
-
- // Reparse the header
- if ( !can_u_read(_in) ) {
- omerr() << "[PLYReader] : Unable to parse header\n";
- return false;
- }
-
-
-
- unsigned int i, j, k, l, idx;
- unsigned int nV;
- OpenMesh::Vec3f v;
- std::string trash;
-// OpenMesh::Vec2f t;
- OpenMesh::Vec4i c;
- float tmp;
- BaseImporter::VHandles vhandles;
- VertexHandle vh;
-
-
- _bi.reserve(vertexCount_, 3*vertexCount_, faceCount_);
-
- if ( vertexDimension_ != 3 ) {
- omerr() << "[PLYReader] : Only vertex dimension 3 is supported." << std::endl;
- return false;
- }
-
- // read vertices:
- for (i=0; i< vertexCount_ && !_in.eof(); ++i)
- {
- v[0] = 0.0;
- v[1] = 0.0;
- v[2] = 0.0;
-
- c[0] = 0;
- c[1] = 0;
- c[2] = 0;
- c[3] = 255;
-
- for ( uint propertyIndex = 0 ; propertyIndex < vertexPropertyCount_; ++propertyIndex ) {
- switch ( vertexPropertyMap_ [ propertyIndex].first ) {
- case XCOORD:
- _in >> v[0];
- break;
- case YCOORD:
- _in >> v[1];
- break;
- case ZCOORD:
- _in >> v[2];
- break;
- case COLORRED:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- _in >> tmp; c[0] = static_cast(tmp * 255.0f);
- }else
- _in >> c[0];
- break;
- case COLORGREEN:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- _in >> tmp; c[1] = static_cast(tmp * 255.0f);
- }else
- _in >> c[1];
- break;
- case COLORBLUE:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- _in >> tmp; c[2] = static_cast(tmp * 255.0f);
- }else
- _in >> c[2];
- break;
- case COLORALPHA:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- _in >> tmp; c[3] = static_cast(tmp * 255.0f);
- }else
- _in >> c[3];
- break;
- default :
- _in >> trash;
- break;
- }
- }
-
- vh = _bi.add_vertex(v);
- _bi.set_color( vh, Vec4uc( c ) );
- }
-
- // faces
- // #N .. [color spec]
- for (i=0; i> nV;
-
- if (nV == 3)
- {
- vhandles.resize(3);
- _in >> j;
- _in >> k;
- _in >> l;
-
- vhandles[0] = VertexHandle(j);
- vhandles[1] = VertexHandle(k);
- vhandles[2] = VertexHandle(l);
- }
- else
- {
- vhandles.clear();
- for (j=0; j> idx;
- vhandles.push_back(VertexHandle(idx));
- }
- }
-
- FaceHandle fh = _bi.add_face(vhandles);
-
- }
-
- // File was successfully parsed.
- return true;
-}
-
-
-//-----------------------------------------------------------------------------
-
-void _PLYReader_::readValue(ValueType _type , std::fstream& _in, float& _value) const{
-
- switch (_type) {
- case ValueTypeFLOAT32:
- case ValueTypeFLOAT:
- float32_t tmp;
- restore( _in , tmp, options_.check(Options::MSB) );
- _value = tmp;
- break;
- default :
- _value = 0.0;
- std::cerr << "unsupported conversion type to float: " << _type << std::endl;
- break;
- }
-}
-
-void _PLYReader_::readValue(ValueType _type , std::fstream& _in, unsigned int& _value) const{
-
- int32_t tmp_int32_t;
- uint8_t tmp_uchar;
-
- switch (_type) {
- case ValueTypeINT:
- case ValueTypeINT32:
- restore( _in , tmp_int32_t, options_.check(Options::MSB) );
- _value = tmp_int32_t;
- break;
- case ValueTypeUCHAR:
- restore( _in , tmp_uchar, options_.check(Options::MSB) );
- _value = tmp_uchar;
- break;
- default :
- _value = 0;
- std::cerr << "unsupported conversion type to int: " << _type << std::endl;
- break;
- }
-}
-
-void _PLYReader_::readValue(ValueType _type , std::fstream& _in, int& _value) const{
-
- int32_t tmp_int32_t;
- uint8_t tmp_uchar;
-
- switch (_type) {
- case ValueTypeINT:
- case ValueTypeINT32:
- restore( _in , tmp_int32_t, options_.check(Options::MSB) );
- _value = tmp_int32_t;
- break;
- case ValueTypeUCHAR:
- restore( _in , tmp_uchar, options_.check(Options::MSB) );
- _value = tmp_uchar;
- break;
- default :
- _value = 0;
- std::cerr << "unsupported conversion type to int: " << _type << std::endl;
- break;
- }
-}
-
-bool
-_PLYReader_::read_binary(std::fstream& _in, BaseImporter& _bi, bool /*_swap*/) const
-{
-
- omlog() << "[PLYReader] : read binary file format\n";
-
- // Reparse the header
- if ( !can_u_read(_in) ) {
- omerr() << "[PLYReader] : Unable to parse header\n";
- return false;
- }
-
- unsigned int i, j, k, l, idx;
- unsigned int nV;
- OpenMesh::Vec3f v;
- BaseImporter::VHandles vhandles;
- VertexHandle vh;
- OpenMesh::Vec4i c;
- float tmp;
-
- _bi.reserve(vertexCount_, 3*vertexCount_, faceCount_);
-
- // read vertices:
- for (i=0; i< vertexCount_ && !_in.eof(); ++i)
- {
- v[0] = 0.0;
- v[1] = 0.0;
- v[2] = 0.0;
-
- c[0] = 0;
- c[1] = 0;
- c[2] = 0;
- c[3] = 255;
-
- for ( uint propertyIndex = 0 ; propertyIndex < vertexPropertyCount_; ++propertyIndex ) {
- switch ( vertexPropertyMap_ [ propertyIndex].first ) {
- case XCOORD:
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,v[0]);
- break;
- case YCOORD:
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,v[1]);
- break;
- case ZCOORD:
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,v[2]);
- break;
- case COLORRED:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,tmp);
-
- c[0] = static_cast(tmp * 255.0f);
- }else
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,c[0]);
- break;
- case COLORGREEN:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,tmp);
- c[1] = static_cast(tmp * 255.0f);
- }else
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,c[1]);
- break;
- case COLORBLUE:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,tmp);
- c[2] = static_cast(tmp * 255.0f);
- }else
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,c[2]);
- break;
- case COLORALPHA:
- if ( vertexPropertyMap_ [ propertyIndex].second == ValueTypeFLOAT32 ){
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,tmp);
- c[3] = static_cast(tmp * 255.0f);
- }else
- readValue(vertexPropertyMap_ [ propertyIndex].second,_in,c[3]);
- break;
- default :
- break;
- }
-
- }
-
- vh = _bi.add_vertex(v);
- _bi.set_color( vh, Vec4uc( c ) );
- }
-
- for (i=0; i> keyword;
- _is >> fileType;
- _is >> version;
-
- if ( _is.bad() ) {
- omerr() << "Defect PLY header detected" << std::endl;
- return false;
- }
-
- if ( fileType == "ascii" ) {
- options_ -= Options::Binary;
- } else if ( fileType == "binary_little_endian" ){
- options_ += Options::Binary;
- options_ += Options::LSB;
- } else if ( fileType == "binary_big_endian" ){
- options_ += Options::Binary;
- options_ += Options::MSB;
- } else {
- omerr() << "Unsupported PLY format: " << fileType << std::endl;
- return false;
- }
-
- unsigned int streamPos = _is.tellg();
- _is >> keyword;
- while ( keyword != "end_header") {
-
- if ( keyword == "comment" ) {
- std::getline(_is,line);
- omlog() << "PLY header comment : " << line << std::endl;
- } else if ( keyword == "element") {
- _is >> elementName;
- if ( elementName == "vertex" ) {
- _is >> vertexCount_;
- } else if ( elementName == "face" ){
- _is >> faceCount_;
- } else {
- omerr() << "PLY header unsupported element type: " << elementName << std::endl;
- }
- } else if ( keyword == "property") {
- std::string tmp1;
- std::string tmp2;
-
- // Read first keyword, as it might be a list
- _is >> tmp1;
-
- if ( tmp1 == "list" ) {
- if ( elementName == "vertex" ) {
- omerr() << "List type not supported for vertices!" << std::endl;
- } else if ( elementName == "face" ) {
- _is >> listIndexType;
- _is >> listEntryType;
- _is >> propertyName;
-
- if ( listIndexType == "uint8" ) {
- faceIndexType_ = ValueTypeUINT8;
- } else if ( listIndexType == "uchar" ) {
- faceIndexType_ = ValueTypeUCHAR;
- } else {
- omerr() << "Unsupported Index type for face list: " << listIndexType << std::endl;
- }
-
- if ( listEntryType == "int32" ) {
- faceEntryType_ = ValueTypeINT32;
- } else if ( listEntryType == "int" ) {
- faceEntryType_ = ValueTypeINT;
- } else {
- omerr() << "Unsupported Entry type for face list: " << listEntryType << std::endl;
- }
-
- }
- } else {
- // as this is not a list property, read second value of property
- _is >> tmp2;
-
- if ( elementName == "vertex" ) {
- // Extract name and type of property
- // As the order seems to be different in some files, autodetect it.
- ValueType valueType = get_property_type(tmp1,tmp2);
- propertyName = get_property_name(tmp1,tmp2);
-
- if ( propertyName == "x" ) {
- std::pair< VertexProperty, ValueType> entry(XCOORD,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- vertexDimension_++;
- } else if ( propertyName == "y" ) {
- std::pair< VertexProperty, ValueType> entry(YCOORD,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- vertexDimension_++;
- } else if ( propertyName == "z" ) {
- std::pair< VertexProperty, ValueType> entry(ZCOORD,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- vertexDimension_++;
- } else if ( propertyName == "red" ) {
- std::pair< VertexProperty, ValueType> entry(COLORRED,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- options_ += Options::VertexColor;
- } else if ( propertyName == "green" ) {
- std::pair< VertexProperty, ValueType> entry(COLORGREEN,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- options_ += Options::VertexColor;
- } else if ( propertyName == "blue" ) {
- std::pair< VertexProperty, ValueType> entry(COLORBLUE,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- options_ += Options::VertexColor;
- } else if ( propertyName == "alpha" ) {
- std::pair< VertexProperty, ValueType> entry(COLORALPHA,valueType);
- vertexPropertyMap_[vertexPropertyCount_] = entry;
- options_ += Options::VertexColor;
- options_ += Options::ColorAlpha;
- } else {
- std::cerr << "Unsupported property : " << propertyName << std::endl;
- }
-
- vertexPropertyCount_++;
-
- } else if ( elementName == "face" ) {
- omerr() << "Properties not supported for faces " << std::endl;
- }
-
- }
-
- } else {
- omlog() << "Unsupported keyword : " << keyword << std::endl;
- }
-
- streamPos = _is.tellg();
- _is >> keyword;
- if ( _is.bad() ) {
- omerr() << "Error while reading PLY file header" << std::endl;
- return false;
- }
- }
-
- // As the binary data is directy after the end_header keyword
- // and the stream removes too many bytes, seek back to the right position
- if ( options_.is_binary() ) {
- _is.seekg(streamPos + 12);
- }
-
- return true;
}
+//-----------------------------------------------------------------------------
+
+bool _PLYReader_::read_ascii(std::fstream& _in, BaseImporter& _bi) const {
+
+ omlog() << "[PLYReader] : read ascii file\n";
+
+ // Reparse the header
+ if (!can_u_read(_in)) {
+ omerr() << "[PLYReader] : Unable to parse header\n";
+ return false;
+ }
+
+ unsigned int i, j, k, l, idx;
+ unsigned int nV;
+ OpenMesh::Vec3f v;
+ std::string trash;
+ // OpenMesh::Vec2f t;
+ OpenMesh::Vec4i c;
+ float tmp;
+ BaseImporter::VHandles vhandles;
+ VertexHandle vh;
+
+ _bi.reserve(vertexCount_, 3* vertexCount_ , faceCount_);
+
+ if (vertexDimension_ != 3) {
+ omerr() << "[PLYReader] : Only vertex dimension 3 is supported." << std::endl;
+ return false;
+ }
+
+ // read vertices:
+ for (i = 0; i < vertexCount_ && !_in.eof(); ++i) {
+ v[0] = 0.0;
+ v[1] = 0.0;
+ v[2] = 0.0;
+
+ c[0] = 0;
+ c[1] = 0;
+ c[2] = 0;
+ c[3] = 255;
+
+ for (uint propertyIndex = 0; propertyIndex < vertexPropertyCount_; ++propertyIndex) {
+ switch (vertexPropertyMap_[propertyIndex].first) {
+ case XCOORD:
+ _in >> v[0];
+ break;
+ case YCOORD:
+ _in >> v[1];
+ break;
+ case ZCOORD:
+ _in >> v[2];
+ break;
+ case COLORRED:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ _in >> tmp;
+ c[0] = static_cast (tmp * 255.0f);
+ } else
+ _in >> c[0];
+ break;
+ case COLORGREEN:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ _in >> tmp;
+ c[1] = static_cast (tmp * 255.0f);
+ } else
+ _in >> c[1];
+ break;
+ case COLORBLUE:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ _in >> tmp;
+ c[2] = static_cast (tmp * 255.0f);
+ } else
+ _in >> c[2];
+ break;
+ case COLORALPHA:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ _in >> tmp;
+ c[3] = static_cast (tmp * 255.0f);
+ } else
+ _in >> c[3];
+ break;
+ default:
+ _in >> trash;
+ break;
+ }
+ }
+
+ vh = _bi.add_vertex(v);
+ _bi.set_color(vh, Vec4uc(c));
+ }
+
+ // faces
+ // #N .. [color spec]
+ for (i = 0; i < faceCount_; ++i) {
+ // nV = number of Vertices for current face
+ _in >> nV;
+
+ if (nV == 3) {
+ vhandles.resize(3);
+ _in >> j;
+ _in >> k;
+ _in >> l;
+
+ vhandles[0] = VertexHandle(j);
+ vhandles[1] = VertexHandle(k);
+ vhandles[2] = VertexHandle(l);
+ } else {
+ vhandles.clear();
+ for (j = 0; j < nV; ++j) {
+ _in >> idx;
+ vhandles.push_back(VertexHandle(idx));
+ }
+ }
+
+ FaceHandle fh = _bi.add_face(vhandles);
+
+ }
+
+ // File was successfully parsed.
+ return true;
+}
+
+//-----------------------------------------------------------------------------
+
+void _PLYReader_::readValue(ValueType _type, std::fstream& _in, float& _value) const {
+
+ switch (_type) {
+ case ValueTypeFLOAT32:
+ case ValueTypeFLOAT:
+ float32_t tmp;
+ restore(_in, tmp, options_.check(Options::MSB));
+ _value = tmp;
+ break;
+ default:
+ _value = 0.0;
+ std::cerr << "unsupported conversion type to float: " << _type << std::endl;
+ break;
+ }
+}
+
+void _PLYReader_::readValue(ValueType _type, std::fstream& _in, unsigned int& _value) const {
+
+ int32_t tmp_int32_t;
+ uint8_t tmp_uchar;
+
+ switch (_type) {
+ case ValueTypeINT:
+ case ValueTypeINT32:
+ restore(_in, tmp_int32_t, options_.check(Options::MSB));
+ _value = tmp_int32_t;
+ break;
+ case ValueTypeUCHAR:
+ restore(_in, tmp_uchar, options_.check(Options::MSB));
+ _value = tmp_uchar;
+ break;
+ default:
+ _value = 0;
+ std::cerr << "unsupported conversion type to int: " << _type << std::endl;
+ break;
+ }
+}
+
+void _PLYReader_::readValue(ValueType _type, std::fstream& _in, int& _value) const {
+
+ int32_t tmp_int32_t;
+ uint8_t tmp_uchar;
+
+ switch (_type) {
+ case ValueTypeINT:
+ case ValueTypeINT32:
+ restore(_in, tmp_int32_t, options_.check(Options::MSB));
+ _value = tmp_int32_t;
+ break;
+ case ValueTypeUCHAR:
+ restore(_in, tmp_uchar, options_.check(Options::MSB));
+ _value = tmp_uchar;
+ break;
+ default:
+ _value = 0;
+ std::cerr << "unsupported conversion type to int: " << _type << std::endl;
+ break;
+ }
+}
+
+bool _PLYReader_::read_binary(std::fstream& _in, BaseImporter& _bi, bool /*_swap*/) const {
+
+ omlog() << "[PLYReader] : read binary file format\n";
+
+ // Reparse the header
+ if (!can_u_read(_in)) {
+ omerr() << "[PLYReader] : Unable to parse header\n";
+ return false;
+ }
+
+ unsigned int i, j, k, l, idx;
+ unsigned int nV;
+ OpenMesh::Vec3f v;
+ BaseImporter::VHandles vhandles;
+ VertexHandle vh;
+ OpenMesh::Vec4i c;
+ float tmp;
+
+ _bi.reserve(vertexCount_, 3* vertexCount_ , faceCount_);
+
+ // read vertices:
+ for (i = 0; i < vertexCount_ && !_in.eof(); ++i) {
+ v[0] = 0.0;
+ v[1] = 0.0;
+ v[2] = 0.0;
+
+ c[0] = 0;
+ c[1] = 0;
+ c[2] = 0;
+ c[3] = 255;
+
+ for (uint propertyIndex = 0; propertyIndex < vertexPropertyCount_; ++propertyIndex) {
+ switch (vertexPropertyMap_[propertyIndex].first) {
+ case XCOORD:
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, v[0]);
+ break;
+ case YCOORD:
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, v[1]);
+ break;
+ case ZCOORD:
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, v[2]);
+ break;
+ case COLORRED:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, tmp);
+
+ c[0] = static_cast (tmp * 255.0f);
+ } else
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, c[0]);
+ break;
+ case COLORGREEN:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, tmp);
+ c[1] = static_cast (tmp * 255.0f);
+ } else
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, c[1]);
+ break;
+ case COLORBLUE:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, tmp);
+ c[2] = static_cast (tmp * 255.0f);
+ } else
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, c[2]);
+ break;
+ case COLORALPHA:
+ if (vertexPropertyMap_[propertyIndex].second == ValueTypeFLOAT32) {
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, tmp);
+ c[3] = static_cast (tmp * 255.0f);
+ } else
+ readValue(vertexPropertyMap_[propertyIndex].second, _in, c[3]);
+ break;
+ default:
+ break;
+ }
+
+ }
+
+ vh = _bi.add_vertex(v);
+ _bi.set_color(vh, Vec4uc(c));
+ }
+
+ for (i = 0; i < faceCount_; ++i) {
+ // Read number of vertices for the current face
+ readValue(faceIndexType_, _in, nV);
+
+ if (nV == 3) {
+ vhandles.resize(3);
+ readValue(faceEntryType_, _in, j);
+ readValue(faceEntryType_, _in, k);
+ readValue(faceEntryType_, _in, l);
+
+ vhandles[0] = VertexHandle(j);
+ vhandles[1] = VertexHandle(k);
+ vhandles[2] = VertexHandle(l);
+ } else {
+ vhandles.clear();
+ for (j = 0; j < nV; ++j) {
+ readValue(faceEntryType_, _in, idx);
+ vhandles.push_back(VertexHandle(idx));
+ }
+ }
+
+ FaceHandle fh = _bi.add_face(vhandles);
+ }
+
+ return true;
+}
+
+//-----------------------------------------------------------------------------
+
+
+bool _PLYReader_::can_u_read(const std::string& _filename) const {
+ // !!! Assuming BaseReader::can_u_parse( std::string& )
+ // does not call BaseReader::read_magic()!!!
+ if (BaseReader::can_u_read(_filename)) {
+ std::ifstream ifs(_filename.c_str());
+ if (ifs.is_open() && can_u_read(ifs)) {
+ ifs.close();
+ return true;
+ }
+ }
+ return false;
+}
+
+//-----------------------------------------------------------------------------
+
+std::string get_property_name(std::string _string1, std::string _string2) {
+ if (_string1 == "float32" || _string1 == "uint8" || _string1 == "uchar" || _string1 == "float" || _string1
+ == "int32")
+ return _string2;
+
+ if (_string2 == "float32" || _string2 == "uint8" || _string2 == "uchar" || _string2 == "float" || _string2
+ == "int32")
+ return _string1;
+
+ std::cerr << "Unsupported entry type" << std::endl;
+ return "Unsupported";
+}
+
+//-----------------------------------------------------------------------------
+
+_PLYReader_::ValueType get_property_type(std::string _string1, std::string _string2) {
+ if (_string1 == "float32" || _string2 == "float32")
+ return _PLYReader_::ValueTypeFLOAT32;
+ else if (_string1 == "uint8" || _string2 == "float32")
+ return _PLYReader_::ValueTypeUINT8;
+ else if (_string1 == "int32" || _string2 == "float32")
+ return _PLYReader_::ValueTypeINT32;
+ else if (_string1 == "uchar" || _string2 == "uchar")
+ return _PLYReader_::ValueTypeUCHAR;
+ else if (_string1 == "float" || _string2 == "float")
+ return _PLYReader_::ValueTypeFLOAT;
+
+ return _PLYReader_::Unsupported;
+}
+
+//-----------------------------------------------------------------------------
+
+bool _PLYReader_::can_u_read(std::istream& _is) const {
+ // Clear per file options
+ options_.cleanup();
+
+ // clear vertex property map, will be recreated
+ vertexPropertyMap_.clear();
+ vertexPropertyCount_ = 0;
+
+ // read 1st line
+ std::string line;
+ std::getline(_is, line);
+
+ //Check if this file is really a ply format
+ if (line != "PLY" && line != "ply")
+ return false;
+
+ // omlog() << "PLY header found" << std::endl;
+
+ vertexCount_ = 0;
+ faceCount_ = 0;
+ vertexDimension_ = 0;
+
+ std::string keyword;
+ std::string fileType;
+ std::string elementName = "";
+ std::string propertyType;
+ std::string propertyName;
+ std::string listIndexType;
+ std::string listEntryType;
+ float version;
+
+ _is >> keyword;
+ _is >> fileType;
+ _is >> version;
+
+ if (_is.bad()) {
+ omerr() << "Defect PLY header detected" << std::endl;
+ return false;
+ }
+
+ if (fileType == "ascii") {
+ options_ -= Options::Binary;
+ } else if (fileType == "binary_little_endian") {
+ options_ += Options::Binary;
+ options_ += Options::LSB;
+ } else if (fileType == "binary_big_endian") {
+ options_ += Options::Binary;
+ options_ += Options::MSB;
+ } else {
+ omerr() << "Unsupported PLY format: " << fileType << std::endl;
+ return false;
+ }
+
+ unsigned int streamPos = _is.tellg();
+ _is >> keyword;
+ while (keyword != "end_header") {
+
+ if (keyword == "comment") {
+ std::getline(_is, line);
+ omlog() << "PLY header comment : " << line << std::endl;
+ } else if (keyword == "element") {
+ _is >> elementName;
+ if (elementName == "vertex") {
+ _is >> vertexCount_;
+ } else if (elementName == "face") {
+ _is >> faceCount_;
+ } else {
+ omerr() << "PLY header unsupported element type: " << elementName << std::endl;
+ }
+ } else if (keyword == "property") {
+ std::string tmp1;
+ std::string tmp2;
+
+ // Read first keyword, as it might be a list
+ _is >> tmp1;
+
+ if (tmp1 == "list") {
+ if (elementName == "vertex") {
+ omerr() << "List type not supported for vertices!" << std::endl;
+ } else if (elementName == "face") {
+ _is >> listIndexType;
+ _is >> listEntryType;
+ _is >> propertyName;
+
+ if (listIndexType == "uint8") {
+ faceIndexType_ = ValueTypeUINT8;
+ } else if (listIndexType == "uchar") {
+ faceIndexType_ = ValueTypeUCHAR;
+ } else {
+ omerr() << "Unsupported Index type for face list: " << listIndexType << std::endl;
+ }
+
+ if (listEntryType == "int32") {
+ faceEntryType_ = ValueTypeINT32;
+ } else if (listEntryType == "int") {
+ faceEntryType_ = ValueTypeINT;
+ } else {
+ omerr() << "Unsupported Entry type for face list: " << listEntryType << std::endl;
+ }
+
+ }
+ } else {
+ // as this is not a list property, read second value of property
+ _is >> tmp2;
+
+ if (elementName == "vertex") {
+ // Extract name and type of property
+ // As the order seems to be different in some files, autodetect it.
+ ValueType valueType = get_property_type(tmp1, tmp2);
+ propertyName = get_property_name(tmp1, tmp2);
+
+ if (propertyName == "x") {
+ std::pair entry(XCOORD, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ vertexDimension_++;
+ } else if (propertyName == "y") {
+ std::pair entry(YCOORD, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ vertexDimension_++;
+ } else if (propertyName == "z") {
+ std::pair entry(ZCOORD, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ vertexDimension_++;
+ } else if (propertyName == "red") {
+ std::pair entry(COLORRED, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ options_ += Options::VertexColor;
+ } else if (propertyName == "green") {
+ std::pair entry(COLORGREEN, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ options_ += Options::VertexColor;
+ } else if (propertyName == "blue") {
+ std::pair entry(COLORBLUE, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ options_ += Options::VertexColor;
+ } else if (propertyName == "alpha") {
+ std::pair entry(COLORALPHA, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ options_ += Options::VertexColor;
+ options_ += Options::ColorAlpha;
+ } else {
+ std::pair entry(UNSUPPORTED, valueType);
+ vertexPropertyMap_[vertexPropertyCount_] = entry;
+ std::cerr << "Unsupported property : " << propertyName << std::endl;
+ }
+
+ vertexPropertyCount_++;
+
+ } else if (elementName == "face") {
+ omerr() << "Properties not supported for faces " << std::endl;
+ }
+
+ }
+
+ } else {
+ omlog() << "Unsupported keyword : " << keyword << std::endl;
+ }
+
+ streamPos = _is.tellg();
+ _is >> keyword;
+ if (_is.bad()) {
+ omerr() << "Error while reading PLY file header" << std::endl;
+ return false;
+ }
+ }
+
+ // As the binary data is directy after the end_header keyword
+ // and the stream removes too many bytes, seek back to the right position
+ if (options_.is_binary()) {
+ _is.seekg(streamPos + 12);
+ }
+
+ return true;
+}
//=============================================================================
} // namespace IO
diff --git a/src/OpenMesh/Core/IO/reader/PLYReader.hh b/src/OpenMesh/Core/IO/reader/PLYReader.hh
index 6047ed79..feef96ef 100644
--- a/src/OpenMesh/Core/IO/reader/PLYReader.hh
+++ b/src/OpenMesh/Core/IO/reader/PLYReader.hh
@@ -4,10 +4,10 @@
* Copyright (C) 2001-2009 by Computer Graphics Group, RWTH Aachen *
* www.openmesh.org *
* *
- *---------------------------------------------------------------------------*
+ *---------------------------------------------------------------------------*
* This file is part of OpenMesh. *
* *
- * OpenMesh is free software: you can redistribute it and/or modify *
+ * OpenMesh is free software: you can redistribute it and/or modify *
* it under the terms of the GNU Lesser General Public License as *
* published by the Free Software Foundation, either version 3 of *
* the License, or (at your option) any later version with the *
@@ -30,10 +30,10 @@
* License along with OpenMesh. If not, *
* see . *
* *
-\*===========================================================================*/
+\*===========================================================================*/
/*===========================================================================*\
- * *
+ * *
* $Revision$ *
* $Date$ *
* *
@@ -143,7 +143,8 @@ private:
enum VertexProperty {
XCOORD,YCOORD,ZCOORD,
TEXX,TEXY,
- COLORRED,COLORGREEN,COLORBLUE,COLORALPHA
+ COLORRED,COLORGREEN,COLORBLUE,COLORALPHA,
+ UNSUPPORTED
};