Merge branch 'master' into issue_3711

pull/3929/head
Kim Kulling 2021-05-29 08:39:18 +02:00 committed by GitHub
commit 09bb79c68a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
25 changed files with 261 additions and 65 deletions

View File

@ -1,8 +1,8 @@
--- ---
name: Bug report name: Bug report
about: Create a report to help us improve about: Create a report to help us improve
title: '' title: 'Bug:'
labels: '' labels: 'Bug'
assignees: '' assignees: ''
--- ---
@ -23,16 +23,10 @@ A clear and concise description of what you expected to happen.
**Screenshots** **Screenshots**
If applicable, add screenshots to help explain your problem. If applicable, add screenshots to help explain your problem.
**Desktop (please complete the following information):** **Platform (please complete the following information):**
- OS: [e.g. iOS] - OS: [e.g. iOS]
- Browser [e.g. chrome, safari] - Browser [e.g. chrome, safari]
- Version [e.g. 22] - Version [e.g. 22]
**Smartphone (please complete the following information):**
- Device: [e.g. iPhone6]
- OS: [e.g. iOS8.1]
- Browser [e.g. stock browser, safari]
- Version [e.g. 22]
**Additional context** **Additional context**
Add any other context about the problem here. Add any other context about the problem here.

View File

@ -2,7 +2,7 @@
name: Feature request name: Feature request
about: Suggest an idea for this project about: Suggest an idea for this project
title: '' title: ''
labels: '' labels: 'Feature-Request'
assignees: '' assignees: ''
--- ---

View File

@ -0,0 +1,25 @@
---
name: Technical debt
about: Create a report to help us to fix and detect tech debts
title: ''
labels: 'Techdebt'
assignees: ''
---
**Describe the technical debt**
A clear and concise description of what the tech debt is about.
**Better solution**
A clear and concise description of what you would expect.
**Screenshots**
If applicable, add screenshots to help explain your problem.
**Desktop (please complete the following information):**
- OS: [e.g. iOS]
- Browser [e.g. chrome, safari]
- Version [e.g. 22]
**Additional context**
Add any other context about the problem here.

View File

@ -598,8 +598,11 @@ static void WriteDump(const char *pFile, const char *cmd, const aiScene *scene,
if (!mesh->mTextureCoords[a]) if (!mesh->mTextureCoords[a])
break; break;
ioprintf(io, "\t\t<TextureCoords num=\"%u\" set=\"%u\" num_components=\"%u\"> \n", mesh->mNumVertices, ioprintf(io, "\t\t<TextureCoords num=\"%u\" set=\"%u\" name=\"%s\" num_components=\"%u\"> \n",
a, mesh->mNumUVComponents[a]); mesh->mNumVertices,
a,
mesh->mTextureCoordsNames[a].C_Str(),
mesh->mNumUVComponents[a]);
if (!shortened) { if (!shortened) {
if (mesh->mNumUVComponents[a] == 3) { if (mesh->mNumUVComponents[a] == 3) {

View File

@ -63,11 +63,11 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
using namespace Assimp; using namespace Assimp;
// AutoCAD Binary DXF<CR><LF><SUB><NULL> // AutoCAD Binary DXF<CR><LF><SUB><NULL>
const std::string AI_DXF_BINARY_IDENT = std::string("AutoCAD Binary DXF\r\n\x1a\0"); static constexpr char AI_DXF_BINARY_IDENT[] = "AutoCAD Binary DXF\r\n\x1a";
const size_t AI_DXF_BINARY_IDENT_LEN = 24u; static constexpr size_t AI_DXF_BINARY_IDENT_LEN = sizeof AI_DXF_BINARY_IDENT;
// default vertex color that all uncolored vertices will receive // default vertex color that all uncolored vertices will receive
const aiColor4D AI_DXF_DEFAULT_COLOR(aiColor4D(0.6f, 0.6f, 0.6f, 0.6f)); static const aiColor4D AI_DXF_DEFAULT_COLOR(aiColor4D(0.6f, 0.6f, 0.6f, 0.6f));
// color indices for DXF - 16 are supported, the table is // color indices for DXF - 16 are supported, the table is
// taken directly from the DXF spec. // taken directly from the DXF spec.
@ -156,10 +156,10 @@ void DXFImporter::InternReadFile( const std::string& filename, aiScene* pScene,
} }
// Check whether this is a binary DXF file - we can't read binary DXF files :-( // Check whether this is a binary DXF file - we can't read binary DXF files :-(
char buff[AI_DXF_BINARY_IDENT_LEN+1] = {0}; char buff[AI_DXF_BINARY_IDENT_LEN] = {0};
file->Read(buff,AI_DXF_BINARY_IDENT_LEN,1); file->Read(buff,AI_DXF_BINARY_IDENT_LEN,1);
if (0 == strncmp(AI_DXF_BINARY_IDENT.c_str(),buff,AI_DXF_BINARY_IDENT_LEN)) { if (0 == memcmp(AI_DXF_BINARY_IDENT,buff,AI_DXF_BINARY_IDENT_LEN)) {
throw DeadlyImportError("DXF: Binary files are not supported at the moment"); throw DeadlyImportError("DXF: Binary files are not supported at the moment");
} }

View File

@ -1126,6 +1126,8 @@ unsigned int FBXConverter::ConvertMeshSingleMaterial(const MeshGeometry &mesh, c
*out_uv++ = aiVector3D(v.x, v.y, 0.0f); *out_uv++ = aiVector3D(v.x, v.y, 0.0f);
} }
out_mesh->mTextureCoordsNames[i] = mesh.GetTextureCoordChannelName(i);
out_mesh->mNumUVComponents[i] = 2; out_mesh->mNumUVComponents[i] = 2;
} }
@ -2126,7 +2128,12 @@ void FBXConverter::SetShadingPropertiesCommon(aiMaterial *out_mat, const Propert
const aiColor3D &Emissive = GetColorPropertyFromMaterial(props, "Emissive", ok); const aiColor3D &Emissive = GetColorPropertyFromMaterial(props, "Emissive", ok);
if (ok) { if (ok) {
out_mat->AddProperty(&Emissive, 1, AI_MATKEY_COLOR_EMISSIVE); out_mat->AddProperty(&Emissive, 1, AI_MATKEY_COLOR_EMISSIVE);
} } else {
const aiColor3D &emissiveColor = GetColorPropertyFromMaterial(props, "Maya|emissive", ok);
if (ok) {
out_mat->AddProperty(&emissiveColor, 1, AI_MATKEY_COLOR_EMISSIVE);
}
}
const aiColor3D &Ambient = GetColorPropertyFromMaterial(props, "Ambient", ok); const aiColor3D &Ambient = GetColorPropertyFromMaterial(props, "Ambient", ok);
if (ok) { if (ok) {
@ -2207,6 +2214,52 @@ void FBXConverter::SetShadingPropertiesCommon(aiMaterial *out_mat, const Propert
if (ok) { if (ok) {
out_mat->AddProperty(&DispFactor, 1, "$mat.displacementscaling", 0, 0); out_mat->AddProperty(&DispFactor, 1, "$mat.displacementscaling", 0, 0);
} }
// PBR material information
const aiColor3D &baseColor = GetColorPropertyFromMaterial(props, "Maya|base_color", ok);
if (ok) {
out_mat->AddProperty(&baseColor, 1, AI_MATKEY_BASE_COLOR);
}
const float useColorMap = PropertyGet<float>(props, "Maya|use_color_map", ok);
if (ok) {
out_mat->AddProperty(&useColorMap, 1, AI_MATKEY_USE_COLOR_MAP);
}
const float useMetallicMap = PropertyGet<float>(props, "Maya|use_metallic_map", ok);
if (ok) {
out_mat->AddProperty(&useMetallicMap, 1, AI_MATKEY_USE_METALLIC_MAP);
}
const float metallicFactor = PropertyGet<float>(props, "Maya|metallic", ok);
if (ok) {
out_mat->AddProperty(&metallicFactor, 1, AI_MATKEY_METALLIC_FACTOR);
}
const float useRoughnessMap = PropertyGet<float>(props, "Maya|use_roughness_map", ok);
if (ok) {
out_mat->AddProperty(&useRoughnessMap, 1, AI_MATKEY_USE_ROUGHNESS_MAP);
}
const float roughnessFactor = PropertyGet<float>(props, "Maya|roughness", ok);
if (ok) {
out_mat->AddProperty(&roughnessFactor, 1, AI_MATKEY_ROUGHNESS_FACTOR);
}
const float useEmissiveMap = PropertyGet<float>(props, "Maya|use_emissive_map", ok);
if (ok) {
out_mat->AddProperty(&useEmissiveMap, 1, AI_MATKEY_USE_EMISSIVE_MAP);
}
const float emissiveIntensity = PropertyGet<float>(props, "Maya|emissive_intensity", ok);
if (ok) {
out_mat->AddProperty(&emissiveIntensity, 1, AI_MATKEY_EMISSIVE_INTENSITY);
}
const float useAOMap = PropertyGet<float>(props, "Maya|use_ao_map", ok);
if (ok) {
out_mat->AddProperty(&useAOMap, 1, AI_MATKEY_USE_AO_MAP);
}
} }
void FBXConverter::SetShadingPropertiesRaw(aiMaterial *out_mat, const PropertyTable &props, const TextureMap &_textures, const MeshGeometry *const mesh) { void FBXConverter::SetShadingPropertiesRaw(aiMaterial *out_mat, const PropertyTable &props, const TextureMap &_textures, const MeshGeometry *const mesh) {

View File

@ -604,15 +604,15 @@ void MeshGeometry::ReadVertexDataTangents(std::vector<aiVector3D>& tangents_out,
} }
// ------------------------------------------------------------------------------------------------ // ------------------------------------------------------------------------------------------------
static const std::string BinormalIndexToken = "BinormalIndex"; static const char * BinormalIndexToken = "BinormalIndex";
static const std::string BinormalsIndexToken = "BinormalsIndex"; static const char * BinormalsIndexToken = "BinormalsIndex";
void MeshGeometry::ReadVertexDataBinormals(std::vector<aiVector3D>& binormals_out, const Scope& source, void MeshGeometry::ReadVertexDataBinormals(std::vector<aiVector3D>& binormals_out, const Scope& source,
const std::string& MappingInformationType, const std::string& MappingInformationType,
const std::string& ReferenceInformationType) const std::string& ReferenceInformationType)
{ {
const char * str = source.Elements().count( "Binormals" ) > 0 ? "Binormals" : "Binormal"; const char * str = source.Elements().count( "Binormals" ) > 0 ? "Binormals" : "Binormal";
const char * strIdx = source.Elements().count( "Binormals" ) > 0 ? BinormalsIndexToken.c_str() : BinormalIndexToken.c_str(); const char * strIdx = source.Elements().count( "Binormals" ) > 0 ? BinormalsIndexToken : BinormalIndexToken;
ResolveVertexDataArray(binormals_out,source,MappingInformationType,ReferenceInformationType, ResolveVertexDataArray(binormals_out,source,MappingInformationType,ReferenceInformationType,
str, str,
strIdx, strIdx,

View File

@ -131,7 +131,7 @@ Property* ReadTypedProperty(const Element& element)
ParseTokenAsFloat(*tok[6])) ParseTokenAsFloat(*tok[6]))
); );
} }
else if (!strcmp(cs,"double") || !strcmp(cs,"Number") || !strcmp(cs,"Float") || !strcmp(cs,"FieldOfView") || !strcmp( cs, "UnitScaleFactor" ) ) { else if (!strcmp(cs,"double") || !strcmp(cs,"Number") || !strcmp(cs,"float") || !strcmp(cs,"Float") || !strcmp(cs,"FieldOfView") || !strcmp( cs, "UnitScaleFactor" ) ) {
checkTokenCount(tok, 5); checkTokenCount(tok, 5);
return new TypedProperty<float>(ParseTokenAsFloat(*tok[4])); return new TypedProperty<float>(ParseTokenAsFloat(*tok[4]));
} }

View File

@ -55,9 +55,9 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
namespace Assimp { namespace Assimp {
namespace Ogre { namespace Ogre {
const std::string MESH_VERSION_1_8 = "[MeshSerializer_v1.8]"; static constexpr auto MESH_VERSION_1_8 = "[MeshSerializer_v1.8]";
const std::string SKELETON_VERSION_1_8 = "[Serializer_v1.80]"; static constexpr auto SKELETON_VERSION_1_8 = "[Serializer_v1.80]";
const std::string SKELETON_VERSION_1_1 = "[Serializer_v1.10]"; static constexpr auto SKELETON_VERSION_1_1 = "[Serializer_v1.10]";
const unsigned short HEADER_CHUNK_ID = 0x1000; const unsigned short HEADER_CHUNK_ID = 0x1000;

View File

@ -749,22 +749,22 @@ enum MeshAttribute {
TexCoord TexCoord
}; };
static const std::string PosToken = "position"; constexpr auto PosToken = "position";
static const std::string ColToken = "color"; constexpr auto ColToken = "color";
static const std::string NormalToken = "normal"; constexpr auto NormalToken = "normal";
static const std::string TexCoordToken = "texcoord"; constexpr auto TexCoordToken = "texcoord";
//------------------------------------------------------------------------------------------------ //------------------------------------------------------------------------------------------------
static MeshAttribute getAttributeByName(const char *attribName) { static MeshAttribute getAttributeByName(const char *attribName) {
ai_assert(nullptr != attribName); ai_assert(nullptr != attribName);
if (0 == strncmp(PosToken.c_str(), attribName, PosToken.size())) { if (0 == strcmp(PosToken, attribName)) {
return Position; return Position;
} else if (0 == strncmp(ColToken.c_str(), attribName, ColToken.size())) { } else if (0 == strcmp(ColToken, attribName)) {
return Color; return Color;
} else if (0 == strncmp(NormalToken.c_str(), attribName, NormalToken.size())) { } else if (0 == strcmp(NormalToken, attribName)) {
return Normal; return Normal;
} else if (0 == strncmp(TexCoordToken.c_str(), attribName, TexCoordToken.size())) { } else if (0 == strcmp(TexCoordToken, attribName)) {
return TexCoord; return TexCoord;
} }

View File

@ -1118,11 +1118,13 @@ public:
bool KHR_materials_transmission; bool KHR_materials_transmission;
bool KHR_draco_mesh_compression; bool KHR_draco_mesh_compression;
bool FB_ngon_encoding; bool FB_ngon_encoding;
bool KHR_texture_basisu;
} extensionsUsed; } extensionsUsed;
//! Keeps info about the required extensions //! Keeps info about the required extensions
struct RequiredExtensions { struct RequiredExtensions {
bool KHR_draco_mesh_compression; bool KHR_draco_mesh_compression;
bool KHR_texture_basisu;
} extensionsRequired; } extensionsRequired;
AssetMetadata asset; AssetMetadata asset;

View File

@ -58,7 +58,9 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#pragma clang diagnostic ignored "-Wsign-compare" #pragma clang diagnostic ignored "-Wsign-compare"
#elif defined(__GNUC__) #elif defined(__GNUC__)
#pragma GCC diagnostic push #pragma GCC diagnostic push
#if (__GNUC__ > 4)
#pragma GCC diagnostic ignored "-Wbool-compare" #pragma GCC diagnostic ignored "-Wbool-compare"
#endif
#pragma GCC diagnostic ignored "-Wsign-compare" #pragma GCC diagnostic ignored "-Wsign-compare"
#endif #endif
@ -1144,6 +1146,7 @@ inline Image::Image() :
} }
inline void Image::Read(Value &obj, Asset &r) { inline void Image::Read(Value &obj, Asset &r) {
//basisu: no need to handle .ktx2, .basis, load as is
if (!mDataLength) { if (!mDataLength) {
Value *curUri = FindString(obj, "uri"); Value *curUri = FindString(obj, "uri");
if (nullptr != curUri) { if (nullptr != curUri) {
@ -2124,6 +2127,7 @@ inline void Asset::ReadExtensionsUsed(Document &doc) {
CHECK_EXT(KHR_materials_clearcoat); CHECK_EXT(KHR_materials_clearcoat);
CHECK_EXT(KHR_materials_transmission); CHECK_EXT(KHR_materials_transmission);
CHECK_EXT(KHR_draco_mesh_compression); CHECK_EXT(KHR_draco_mesh_compression);
CHECK_EXT(KHR_texture_basisu);
#undef CHECK_EXT #undef CHECK_EXT
} }

View File

@ -250,6 +250,7 @@ namespace glTF2 {
inline void Write(Value& obj, Image& img, AssetWriter& w) inline void Write(Value& obj, Image& img, AssetWriter& w)
{ {
//basisu: no need to handle .ktx2, .basis, write as is
if (img.bufferView) { if (img.bufferView) {
obj.AddMember("bufferView", img.bufferView->index, w.mAl); obj.AddMember("bufferView", img.bufferView->index, w.mAl);
obj.AddMember("mimeType", Value(img.mimeType, w.mAl).Move(), w.mAl); obj.AddMember("mimeType", Value(img.mimeType, w.mAl).Move(), w.mAl);
@ -892,10 +893,22 @@ namespace glTF2 {
if (this->mAsset.extensionsUsed.FB_ngon_encoding) { if (this->mAsset.extensionsUsed.FB_ngon_encoding) {
exts.PushBack(StringRef("FB_ngon_encoding"), mAl); exts.PushBack(StringRef("FB_ngon_encoding"), mAl);
} }
if (this->mAsset.extensionsUsed.KHR_texture_basisu) {
exts.PushBack(StringRef("KHR_texture_basisu"), mAl);
}
} }
if (!exts.Empty()) if (!exts.Empty())
mDoc.AddMember("extensionsUsed", exts, mAl); mDoc.AddMember("extensionsUsed", exts, mAl);
//basisu extensionRequired
Value extsReq;
extsReq.SetArray();
if (this->mAsset.extensionsUsed.KHR_texture_basisu) {
extsReq.PushBack(StringRef("KHR_texture_basisu"), mAl);
mDoc.AddMember("extensionsRequired", extsReq, mAl);
}
} }
template<class T> template<class T>

View File

@ -494,7 +494,6 @@ void glTF2Exporter::GetMatTexProp(const aiMaterial* mat, float& prop, const char
void glTF2Exporter::GetMatTex(const aiMaterial* mat, Ref<Texture>& texture, aiTextureType tt, unsigned int slot = 0) void glTF2Exporter::GetMatTex(const aiMaterial* mat, Ref<Texture>& texture, aiTextureType tt, unsigned int slot = 0)
{ {
if (mat->GetTextureCount(tt) > 0) { if (mat->GetTextureCount(tt) > 0) {
aiString tex; aiString tex;
@ -507,6 +506,7 @@ void glTF2Exporter::GetMatTex(const aiMaterial* mat, Ref<Texture>& texture, aiTe
texture = mAsset->textures.Get(it->second); texture = mAsset->textures.Get(it->second);
} }
bool useBasisUniversal = false;
if (!texture) { if (!texture) {
std::string texId = mAsset->FindUniqueID("", "texture"); std::string texId = mAsset->FindUniqueID("", "texture");
texture = mAsset->textures.Create(texId); texture = mAsset->textures.Create(texId);
@ -519,18 +519,46 @@ void glTF2Exporter::GetMatTex(const aiMaterial* mat, Ref<Texture>& texture, aiTe
aiTexture* curTex = mScene->mTextures[atoi(&path[1])]; aiTexture* curTex = mScene->mTextures[atoi(&path[1])];
texture->source->name = curTex->mFilename.C_Str(); texture->source->name = curTex->mFilename.C_Str();
// The asset has its own buffer, see Image::SetData //basisu: embedded ktx2, bu
texture->source->SetData(reinterpret_cast<uint8_t *>(curTex->pcData), curTex->mWidth, *mAsset);
if (curTex->achFormatHint[0]) { if (curTex->achFormatHint[0]) {
std::string mimeType = "image/"; std::string mimeType = "image/";
mimeType += (memcmp(curTex->achFormatHint, "jpg", 3) == 0) ? "jpeg" : curTex->achFormatHint; if(memcmp(curTex->achFormatHint, "jpg", 3) == 0)
mimeType += "jpeg";
else if(memcmp(curTex->achFormatHint, "ktx", 3) == 0) {
useBasisUniversal = true;
mimeType += "ktx";
}
else if(memcmp(curTex->achFormatHint, "kx2", 3) == 0) {
useBasisUniversal = true;
mimeType += "ktx2";
}
else if(memcmp(curTex->achFormatHint, "bu", 2) == 0) {
useBasisUniversal = true;
mimeType += "basis";
}
else
mimeType += curTex->achFormatHint;
texture->source->mimeType = mimeType; texture->source->mimeType = mimeType;
} }
// The asset has its own buffer, see Image::SetData
//basisu: "image/ktx2", "image/basis" as is
texture->source->SetData(reinterpret_cast<uint8_t *>(curTex->pcData), curTex->mWidth, *mAsset);
} }
else { else {
texture->source->uri = path; texture->source->uri = path;
if(texture->source->uri.find(".ktx")!=std::string::npos ||
texture->source->uri.find(".basis")!=std::string::npos)
{
useBasisUniversal = true;
}
}
//basisu
if(useBasisUniversal) {
mAsset->extensionsUsed.KHR_texture_basisu = true;
mAsset->extensionsRequired.KHR_texture_basisu = true;
} }
GetTexSampler(mat, texture, tt, slot); GetTexSampler(mat, texture, tt, slot);

View File

@ -1263,7 +1263,7 @@ aiMeshMorphAnim *CreateMeshMorphAnim(glTF2::Asset&, Node &node, AnimationSampler
static const float kMillisecondsFromSeconds = 1000.f; static const float kMillisecondsFromSeconds = 1000.f;
if (nullptr != samplers.weight) { if (samplers.weight && samplers.weight->input && samplers.weight->output) {
float *times = nullptr; float *times = nullptr;
samplers.weight->input->ExtractData(times); samplers.weight->input->ExtractData(times);
float *values = nullptr; float *values = nullptr;
@ -1476,6 +1476,12 @@ void glTF2Importer::ImportEmbeddedTextures(glTF2::Asset &r) {
if (strcmp(ext, "jpeg") == 0) { if (strcmp(ext, "jpeg") == 0) {
ext = "jpg"; ext = "jpg";
} }
else if(strcmp(ext, "ktx2") == 0) { //basisu: ktx remains
ext = "kx2";
}
else if(strcmp(ext, "basis") == 0) { //basisu
ext = "bu";
}
size_t len = strlen(ext); size_t len = strlen(ext);
if (len <= 3) { if (len <= 3) {

View File

@ -1137,6 +1137,9 @@ ELSE()
TARGET_COMPILE_OPTIONS(assimp PRIVATE -Werror) TARGET_COMPILE_OPTIONS(assimp PRIVATE -Werror)
ENDIF() ENDIF()
# adds C_FLAGS required to compile zip.c on old GCC 4.x compiler
TARGET_COMPILE_FEATURES(assimp PUBLIC c_std_99)
TARGET_INCLUDE_DIRECTORIES ( assimp PUBLIC TARGET_INCLUDE_DIRECTORIES ( assimp PUBLIC
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/../include> $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/../include>
$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}/../include> $<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}/../include>

View File

@ -169,7 +169,7 @@ void Logger::debug(const char *message) {
// sometimes importers will include data from the input file // sometimes importers will include data from the input file
// (i.e. node names) in their messages. // (i.e. node names) in their messages.
if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) { if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) {
return; return OnDebug("<fixme: long message discarded>");
} }
return OnDebug(message); return OnDebug(message);
} }
@ -179,7 +179,7 @@ void Logger::verboseDebug(const char *message) {
// SECURITY FIX: see above // SECURITY FIX: see above
if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) { if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) {
return; return OnVerboseDebug("<fixme: long message discarded>");
} }
return OnVerboseDebug(message); return OnVerboseDebug(message);
} }
@ -189,7 +189,7 @@ void Logger::info(const char *message) {
// SECURITY FIX: see above // SECURITY FIX: see above
if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) { if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) {
return; return OnInfo("<fixme: long message discarded>");
} }
return OnInfo(message); return OnInfo(message);
} }
@ -199,7 +199,7 @@ void Logger::warn(const char *message) {
// SECURITY FIX: see above // SECURITY FIX: see above
if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) { if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) {
return; return OnWarn("<fixme: long message discarded>");
} }
return OnWarn(message); return OnWarn(message);
} }
@ -208,7 +208,7 @@ void Logger::warn(const char *message) {
void Logger::error(const char *message) { void Logger::error(const char *message) {
// SECURITY FIX: see above // SECURITY FIX: see above
if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) { if (strlen(message) > MAX_LOG_MESSAGE_LENGTH) {
return; return OnError("<fixme: long message discarded>");
} }
return OnError(message); return OnError(message);
} }

View File

@ -343,9 +343,11 @@ const aiExportDataBlob* Exporter::ExportToBlob( const aiScene* pScene, const cha
delete pimpl->blob; delete pimpl->blob;
pimpl->blob = nullptr; pimpl->blob = nullptr;
} }
auto baseName = pProperties ? pProperties->GetPropertyString(AI_CONFIG_EXPORT_BLOB_NAME, AI_BLOBIO_MAGIC) : AI_BLOBIO_MAGIC;
std::shared_ptr<IOSystem> old = pimpl->mIOSystem; std::shared_ptr<IOSystem> old = pimpl->mIOSystem;
BlobIOSystem* blobio = new BlobIOSystem(); BlobIOSystem *blobio = new BlobIOSystem(baseName);
pimpl->mIOSystem = std::shared_ptr<IOSystem>( blobio ); pimpl->mIOSystem = std::shared_ptr<IOSystem>( blobio );
if (AI_SUCCESS != Export(pScene,pFormatId,blobio->GetMagicFileName(), pPreprocessing, pProperties)) { if (AI_SUCCESS != Export(pScene,pFormatId,blobio->GetMagicFileName(), pPreprocessing, pProperties)) {

View File

@ -194,8 +194,14 @@ class BlobIOSystem : public IOSystem {
friend class BlobIOStream; friend class BlobIOStream;
typedef std::pair<std::string, aiExportDataBlob *> BlobEntry; typedef std::pair<std::string, aiExportDataBlob *> BlobEntry;
public: public:
BlobIOSystem() { BlobIOSystem() :
baseName{AI_BLOBIO_MAGIC} {
}
BlobIOSystem(const std::string &baseName) :
baseName(baseName) {
} }
virtual ~BlobIOSystem() { virtual ~BlobIOSystem() {
@ -207,27 +213,32 @@ public:
public: public:
// ------------------------------------------------------------------- // -------------------------------------------------------------------
const char *GetMagicFileName() const { const char *GetMagicFileName() const {
return AI_BLOBIO_MAGIC; return baseName.c_str();
} }
// ------------------------------------------------------------------- // -------------------------------------------------------------------
aiExportDataBlob *GetBlobChain() { aiExportDataBlob *GetBlobChain() {
const auto magicName = std::string(this->GetMagicFileName());
const bool hasBaseName = baseName != AI_BLOBIO_MAGIC;
// one must be the master // one must be the master
aiExportDataBlob *master = nullptr, *cur; aiExportDataBlob *master = nullptr, *cur;
for (const BlobEntry &blobby : blobs) { for (const BlobEntry &blobby : blobs) {
if (blobby.first == AI_BLOBIO_MAGIC) { if (blobby.first == magicName) {
master = blobby.second; master = blobby.second;
master->name.Set(hasBaseName ? blobby.first : "");
break; break;
} }
} }
if (!master) { if (!master) {
ASSIMP_LOG_ERROR("BlobIOSystem: no data written or master file was not closed properly."); ASSIMP_LOG_ERROR("BlobIOSystem: no data written or master file was not closed properly.");
return nullptr; return nullptr;
} }
master->name.Set("");
cur = master; cur = master;
for (const BlobEntry &blobby : blobs) { for (const BlobEntry &blobby : blobs) {
if (blobby.second == master) { if (blobby.second == master) {
continue; continue;
@ -236,9 +247,13 @@ public:
cur->next = blobby.second; cur->next = blobby.second;
cur = cur->next; cur = cur->next;
// extract the file extension from the file written if (hasBaseName) {
const std::string::size_type s = blobby.first.find_first_of('.'); cur->name.Set(blobby.first);
cur->name.Set(s == std::string::npos ? blobby.first : blobby.first.substr(s + 1)); } else {
// extract the file extension from the file written
const std::string::size_type s = blobby.first.find_first_of('.');
cur->name.Set(s == std::string::npos ? blobby.first : blobby.first.substr(s + 1));
}
} }
// give up blob ownership // give up blob ownership
@ -283,6 +298,7 @@ private:
} }
private: private:
std::string baseName;
std::set<std::string> created; std::set<std::string> created;
std::vector<BlobEntry> blobs; std::vector<BlobEntry> blobs;
}; };

View File

@ -88,9 +88,17 @@ public:
underlying << sin; underlying << sin;
} }
// Same problem as the copy constructor below, but with root cause is that stream move
// is not permitted on older GCC versions. Small performance impact on those platforms.
#if defined(__GNUC__) && (__GNUC__ == 4 && __GNUC_MINOR__ <= 9)
basic_formatter(basic_formatter&& other) {
underlying << (string)other;
}
#else
basic_formatter(basic_formatter&& other) basic_formatter(basic_formatter&& other)
: underlying(std::move(other.underlying)) { : underlying(std::move(other.underlying)) {
} }
#endif
// The problem described here: // The problem described here:
// https://sourceforge.net/tracker/?func=detail&atid=1067632&aid=3358562&group_id=226462 // https://sourceforge.net/tracker/?func=detail&atid=1067632&aid=3358562&group_id=226462

View File

@ -137,7 +137,7 @@ struct aiCamera
*/ */
C_STRUCT aiVector3D mLookAt; C_STRUCT aiVector3D mLookAt;
/** Half horizontal field of view angle, in radians. /** Horizontal field of view angle, in radians.
* *
* The field of view angle is the angle between the center * The field of view angle is the angle between the center
* line of the screen and the left or right border. * line of the screen and the left or right border.

View File

@ -205,16 +205,22 @@ struct aiExportDataBlob {
void *data; void *data;
/** Name of the blob. An empty string always /** Name of the blob. An empty string always
indicates the first (and primary) blob, * indicates the first (and primary) blob,
which contains the actual file data. * which contains the actual file data.
Any other blobs are auxiliary files produced * Any other blobs are auxiliary files produced
by exporters (i.e. material files). Existence * by exporters (i.e. material files). Existence
of such files depends on the file format. Most * of such files depends on the file format. Most
formats don't split assets across multiple files. * formats don't split assets across multiple files.
*
If used, blob names usually contain the file * If used, blob names usually contain the file
extension that should be used when writing * extension that should be used when writing
the data to disc. * the data to disc.
*
* The blob names generated can be influenced by
* setting the #AI_CONFIG_EXPORT_BLOB_NAME export
* property to the name that is used for the master
* blob. All other names are typically derived from
* the base name, by the file format exporter.
*/ */
C_STRUCT aiString name; C_STRUCT aiString name;

View File

@ -1075,6 +1075,23 @@ enum aiComponent
*/ */
#define AI_CONFIG_EXPORT_POINT_CLOUDS "EXPORT_POINT_CLOUDS" #define AI_CONFIG_EXPORT_POINT_CLOUDS "EXPORT_POINT_CLOUDS"
/**
* @brief Specifies the blob name, assimp uses for exporting.
*
* Some formats require auxiliary files to be written, that need to be linked back into
* the original file. For example, OBJ files export materials to a separate MTL file and
* use the `mtllib` keyword to reference this file.
*
* When exporting blobs using #ExportToBlob, assimp does not know the name of the blob
* file and thus outputs `mtllib $blobfile.mtl`, which might not be desired, since the
* MTL file might be called differently.
*
* This property can be used to give the exporter a hint on how to use the magic
* `$blobfile` keyword. If the exporter detects the keyword and is provided with a name
* for the blob, it instead uses this name.
*/
#define AI_CONFIG_EXPORT_BLOB_NAME "EXPORT_BLOB_NAME"
/** /**
* @brief Specifies a gobal key factor for scale, float value * @brief Specifies a gobal key factor for scale, float value
*/ */

View File

@ -920,6 +920,18 @@ extern "C" {
#define AI_MATKEY_SHADER_PRIMITIVE "?sh.ps", 0, 0 #define AI_MATKEY_SHADER_PRIMITIVE "?sh.ps", 0, 0
#define AI_MATKEY_SHADER_COMPUTE "?sh.cs", 0, 0 #define AI_MATKEY_SHADER_COMPUTE "?sh.cs", 0, 0
// ---------------------------------------------------------------------------
// PBR material support
#define AI_MATKEY_USE_COLOR_MAP "$mat.useColorMap", 0, 0
#define AI_MATKEY_BASE_COLOR "$clr.base", 0, 0
#define AI_MATKEY_USE_METALLIC_MAP "$mat.useMetallicMap", 0, 0
#define AI_MATKEY_METALLIC_FACTOR "$mat.metallicFactor", 0, 0
#define AI_MATKEY_USE_ROUGHNESS_MAP "$mat.useRoughnessMap", 0, 0
#define AI_MATKEY_ROUGHNESS_FACTOR "$mat.roughnessFactor", 0, 0
#define AI_MATKEY_USE_EMISSIVE_MAP "$mat.useEmissiveMap", 0, 0
#define AI_MATKEY_EMISSIVE_INTENSITY "$mat.emissiveIntensity", 0, 0
#define AI_MATKEY_USE_AO_MAP "$mat.useAOMap", 0, 0
// --------------------------------------------------------------------------- // ---------------------------------------------------------------------------
// Pure key names for all texture-related properties // Pure key names for all texture-related properties
//! @cond MATS_DOC_FULL //! @cond MATS_DOC_FULL

View File

@ -674,6 +674,10 @@ struct aiMesh {
*/ */
C_STRUCT aiVector3D *mTextureCoords[AI_MAX_NUMBER_OF_TEXTURECOORDS]; C_STRUCT aiVector3D *mTextureCoords[AI_MAX_NUMBER_OF_TEXTURECOORDS];
/** Vertex stream names.
*/
C_STRUCT aiString mTextureCoordsNames[AI_MAX_NUMBER_OF_TEXTURECOORDS];
/** Specifies the number of components for a given UV channel. /** Specifies the number of components for a given UV channel.
* Up to three channels are supported (UVW, for accessing volume * Up to three channels are supported (UVW, for accessing volume
* or cube maps). If the value is 2 for a given channel n, the * or cube maps). If the value is 2 for a given channel n, the