Prefix MTL textures with the MTL directory path (#5928)

* Prefix MTL textures with the MTL directory path.

Path to textures defined in MTL files are relative to the MTL
file rather than to the OBJ, so we need to prefix them with the
MTL file directory path.

* Adding test issue 2355

* Trying to fix for Windows when file has Linux path

---------

Co-authored-by: Kim Kulling <kimkulling@users.noreply.github.com>
This commit is contained in:
David Campos Rodríguez
2025-01-15 10:03:32 +01:00
committed by GitHub
co-authored by Kim Kulling
parent 2f6dcdfd72
commit 1e44036c36
4 changed files with 76 additions and 2 deletions
+18 -2
View File
@@ -44,6 +44,7 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#include "ObjFileMtlImporter.h"
#include "ObjFileData.h"
#include "ObjTools.h"
#include <assimp/DefaultIOSystem.h>
#include <assimp/ParsingUtils.h>
#include <assimp/fast_atof.h>
#include <assimp/material.h>
@@ -89,8 +90,9 @@ static constexpr char TypeOption[] = "-type";
// -------------------------------------------------------------------
// Constructor
ObjFileMtlImporter::ObjFileMtlImporter(std::vector<char> &buffer,
const std::string &,
const std::string &strAbsPath,
ObjFile::Model *pModel) :
m_strAbsPath(strAbsPath),
m_DataIt(buffer.begin()),
m_DataItEnd(buffer.end()),
m_pModel(pModel),
@@ -103,6 +105,20 @@ ObjFileMtlImporter::ObjFileMtlImporter(std::vector<char> &buffer,
m_pModel->mDefaultMaterial = new ObjFile::Material;
m_pModel->mDefaultMaterial->MaterialName.Set("default");
}
// Try with OS folder separator first
char folderSeparator = DefaultIOSystem().getOsSeparator();
std::size_t found = m_strAbsPath.find_last_of(folderSeparator);
if (found == std::string::npos) {
// Not found, try alternative folder separator
folderSeparator = (folderSeparator == '/' ? '\\' : '/');
found = m_strAbsPath.find_last_of(folderSeparator);
}
if (found != std::string::npos) {
m_strAbsPath = m_strAbsPath.substr(0, found + 1);
} else {
m_strAbsPath = "";
}
load();
}
@@ -442,7 +458,7 @@ void ObjFileMtlImporter::getTexture() {
std::string texture;
m_DataIt = getName<DataArrayIt>(m_DataIt, m_DataItEnd, texture);
if (nullptr != out) {
out->Set(texture);
out->Set(m_strAbsPath + texture);
}
}