From 8b3e5a123c4204d530fcd2f5ecc80bd1b267ecd7 Mon Sep 17 00:00:00 2001 From: alemuntoni Date: Tue, 20 Apr 2021 16:37:00 +0200 Subject: [PATCH] io_3ds loads multiple layers correctly --- sample/furniture.3ds | Bin 0 -> 48293 bytes src/common/plugins/interfaces/io_plugin.cpp | 4 +- src/common/plugins/interfaces/io_plugin.h | 4 +- src/meshlab/mainwindow_RunTime.cpp | 1 + src/meshlabplugins/io_3ds/meshio.cpp | 178 ++++++++++---------- src/meshlabplugins/io_3ds/meshio.h | 21 ++- 6 files changed, 108 insertions(+), 100 deletions(-) create mode 100644 sample/furniture.3ds diff --git a/sample/furniture.3ds b/sample/furniture.3ds new file mode 100644 index 0000000000000000000000000000000000000000..ea39757e03f23c540e4a51f24d6cd2a21144f6c1 GIT binary patch literal 48293 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 RichParameterList prePar; pCurrentIOPlugin->initPreOpenParameter(extension,prePar); if(!prePar.isEmpty()) diff --git a/src/meshlabplugins/io_3ds/meshio.cpp b/src/meshlabplugins/io_3ds/meshio.cpp index 2cce37448..9154eb210 100644 --- a/src/meshlabplugins/io_3ds/meshio.cpp +++ b/src/meshlabplugins/io_3ds/meshio.cpp @@ -75,28 +75,75 @@ void ExtraMeshIOPlugin::exportMaskCapability(const QString &format, int &capabil return; } -void ExtraMeshIOPlugin::initPreOpenParameter( +unsigned int ExtraMeshIOPlugin::numberMeshesContainedInFile( const QString& format, - RichParameterList& parameters) + const QString& fileName) const { - if (format.toUpper() == tr("3DS")){ - parameters.addParam(RichBool(paramNames[SEPARATE_LAYERS], true, "Separate layers", "Import each mesh contained in the file as a separate layer")); + if (format.toUpper() == tr("3DS")) { + Lib3dsFile *file = NULL; + file = lib3ds_file_load(fileName.toStdString().c_str()); + if (!file) + throw MLException("Malformed file."); + // No nodes? Fabricate nodes to display all the meshes. + if( !file->nodes && file->meshes) { + Lib3dsMesh *mesh; + Lib3dsNode *node; + + for (mesh = file->meshes; mesh != NULL; mesh = mesh->next) { + node = lib3ds_node_new_object(); + strcpy(node->name, mesh->name); + node->parent_id = LIB3DS_NO_PARENT; + lib3ds_file_insert_node(file, node); + } + } + if( !file->nodes) { + lib3ds_file_free(file); + throw MLException("Malformed file."); + } + lib3ds_file_eval(file, 0); + unsigned int i = 0; + Lib3dsNode *p = file->nodes; + while (p) { + i++; + p = p->next; + } + log("Expected meshes in file: " + std::to_string(i) ); + lib3ds_file_free(file); + return i; } + else { + wrongOpenFormat(format); + return 0; + } +} + +void ExtraMeshIOPlugin::open( + const QString& formatName, + const QString&, + MeshModel&, + int&, + const RichParameterList&, + CallBackPos*) +{ + wrongOpenFormat(formatName); } void ExtraMeshIOPlugin::open( const QString &formatName, const QString &fileName, - MeshModel &m, - int& mask, - const RichParameterList& params, + const std::list& meshList, + std::list& maskList, + const RichParameterList&, CallBackPos *cb) { // initializing mask - mask = 0; + maskList.clear(); + for (unsigned int i = 0; i < meshList.size(); i++) + maskList.push_back(0); // initializing progress bar status - if (cb != NULL) (*cb)(0, "Loading..."); + if (cb != nullptr) + (*cb)(0, "Loading..."); QString errorMsgFormat = "Error encountered while loading file:\n\"%1\"\n\nError details: %2"; //QString error_2MsgFormat = "Error encountered while loading file:\n\"%1\"\n\n File with more than a mesh.\n Load only the first!"; @@ -136,92 +183,43 @@ void ExtraMeshIOPlugin::open( } lib3ds_file_eval(file, 0); - - bool singleLayer = true; - if ( file->nodes->next) { - singleLayer = params.getBool(paramNames[SEPARATE_LAYERS]); - } - - if (!singleLayer) - { - Lib3dsNode *p; - mask = 0; - int i=1; - for (p=file->nodes; p!=0; p=p->next, ++i) - { - bool normalsUpdated = false; - - MeshModel &mm = *m.parent->addNewMesh(qUtf8Printable(fileName), QString(p->name), false); - if (cb != NULL) (*cb)(i, (QString("Loading Mesh ")+QString(p->name)).toStdString().c_str()); - - vcg::tri::io::Importer3DS::LoadMask(file, p, info); - mm.Enable(info.mask); - - int result = vcg::tri::io::Importer3DS::Load(mm.cm, file, p, info); - if (result != vcg::tri::io::Importer3DS::E_NOERROR) { - reportWarning("3DS Opening Error: " + errorMsgFormat.arg(fileName, vcg::tri::io::Importer3DS::ErrorMsg(result))); - continue; - } - - if(info.mask & vcg::tri::io::Mask::IOM_WEDGNORMAL) - normalsUpdated = true; - - mask |= info.mask; - - // verify if texture files are present - QString missingTextureFilesMsg = "The following texture files were not found:\n"; - bool someTextureNotFound = false; - for ( unsigned textureIdx = 0; textureIdx < mm.cm.textures.size(); ++textureIdx) - { - FILE* pFile = fopen (mm.cm.textures[textureIdx].c_str(), "r"); - if (pFile == nullptr) { - missingTextureFilesMsg.append("\n"); - missingTextureFilesMsg.append(mm.cm.textures[textureIdx].c_str()); - someTextureNotFound = true; - } - else { - fclose (pFile); - } - } - if (someTextureNotFound){ - reportWarning("Missing texture files: " + missingTextureFilesMsg); - } - - vcg::tri::UpdateBounding::Box(mm.cm); // updates bounding box - if (!normalsUpdated) - vcg::tri::UpdateNormal::PerVertex(mm.cm); // updates normals - } - } - else + + Lib3dsNode *p; + int i=1; + auto iter = meshList.begin(); + auto miter = maskList.begin(); + for (p=file->nodes; p!=nullptr; p=p->next, ++iter, ++miter) { bool normalsUpdated = false; - - vcg::tri::io::Importer3DS::LoadMask(file, 0, info); - m.Enable(info.mask); - - int result = vcg::tri::io::Importer3DS::Load(m.cm, file, 0, info); - if (result != vcg::tri::io::Importer3DS::E_NOERROR) - { - lib3ds_file_free(file); - throw MLException("3DS Opening Error: " + errorMsgFormat.arg(fileName, vcg::tri::io::Importer3DS::ErrorMsg(result))); + + MeshModel &mm = *(*iter); + mm.setLabel(QString(p->name)); + if (cb != nullptr) + (*cb)(i/meshList.size() * 100, (QString("Loading Mesh ")+QString(p->name)).toStdString().c_str()); + + vcg::tri::io::Importer3DS::LoadMask(file, p, info); + mm.Enable(info.mask); + + int result = vcg::tri::io::Importer3DS::Load(mm.cm, file, p, info); + if (result != vcg::tri::io::Importer3DS::E_NOERROR) { + reportWarning("3DS Opening Error: " + errorMsgFormat.arg(fileName, vcg::tri::io::Importer3DS::ErrorMsg(result))); + continue; } - + if(info.mask & vcg::tri::io::Mask::IOM_WEDGNORMAL) normalsUpdated = true; - - mask = info.mask; - - + + (*miter) |= info.mask; + // verify if texture files are present QString missingTextureFilesMsg = "The following texture files were not found:\n"; bool someTextureNotFound = false; - for ( unsigned textureIdx = 0; textureIdx < m.cm.textures.size(); ++textureIdx) + for ( unsigned textureIdx = 0; textureIdx < mm.cm.textures.size(); ++textureIdx) { - FILE* pFile = fopen (m.cm.textures[textureIdx].c_str(), "r"); - if (pFile == nullptr) - { + FILE* pFile = fopen (mm.cm.textures[textureIdx].c_str(), "r"); + if (pFile == nullptr) { missingTextureFilesMsg.append("\n"); - missingTextureFilesMsg.append(m.cm.textures[textureIdx].c_str()); + missingTextureFilesMsg.append(mm.cm.textures[textureIdx].c_str()); someTextureNotFound = true; } else { @@ -231,12 +229,12 @@ void ExtraMeshIOPlugin::open( if (someTextureNotFound){ reportWarning("Missing texture files: " + missingTextureFilesMsg); } - - vcg::tri::UpdateBounding::Box(m.cm); // updates bounding box - if (!normalsUpdated) - vcg::tri::UpdateNormal::PerVertex(m.cm); // updates normals + + vcg::tri::UpdateBounding::Box(mm.cm); // updates bounding box + if (!normalsUpdated) + vcg::tri::UpdateNormal::PerVertex(mm.cm); // updates normals } - + if (cb != NULL) (*cb)(99, "Done"); // freeing memory diff --git a/src/meshlabplugins/io_3ds/meshio.h b/src/meshlabplugins/io_3ds/meshio.h index 0dd8506d7..23ea813d1 100644 --- a/src/meshlabplugins/io_3ds/meshio.h +++ b/src/meshlabplugins/io_3ds/meshio.h @@ -44,15 +44,24 @@ public: void exportMaskCapability(const QString& format, int &capability, int &defaultBits) const; - void initPreOpenParameter( - const QString& format, - RichParameterList& parameters); + unsigned int numberMeshesContainedInFile( + const QString& format, + const QString& fileName) const; - void open(const QString &formatName, + void open( + const QString &formatName, const QString &fileName, - MeshModel &m, + MeshModel& m, int& mask, - const RichParameterList ¶ms, + const RichParameterList& params, + vcg::CallBackPos *cb=0); + + void open( + const QString &formatName, + const QString &fileName, + const std::list& meshList, + std::list& maskList, + const RichParameterList& params, vcg::CallBackPos *cb=0); void save(