Merge branch 'master' into add-step-extension
commit
73e05ab6d3
|
@ -8,10 +8,10 @@ A library to import and export various 3d-model-formats including scene-post-pro
|
||||||
<img alt="Coverity Scan Build Status"
|
<img alt="Coverity Scan Build Status"
|
||||||
src="https://scan.coverity.com/projects/5607/badge.svg"/>
|
src="https://scan.coverity.com/projects/5607/badge.svg"/>
|
||||||
</a>
|
</a>
|
||||||
|
[![Codacy Badge](https://app.codacy.com/project/badge/Grade/9973693b7bdd4543b07084d5d9cf4745)](https://www.codacy.com/gh/assimp/assimp/dashboard?utm_source=github.com&utm_medium=referral&utm_content=assimp/assimp&utm_campaign=Badge_Grade)
|
||||||
[![Coverage Status](https://coveralls.io/repos/github/assimp/assimp/badge.svg?branch=master)](https://coveralls.io/github/assimp/assimp?branch=master)
|
[![Coverage Status](https://coveralls.io/repos/github/assimp/assimp/badge.svg?branch=master)](https://coveralls.io/github/assimp/assimp?branch=master)
|
||||||
[![Join the chat at https://gitter.im/assimp/assimp](https://badges.gitter.im/assimp/assimp.svg)](https://gitter.im/assimp/assimp?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
|
[![Join the chat at https://gitter.im/assimp/assimp](https://badges.gitter.im/assimp/assimp.svg)](https://gitter.im/assimp/assimp?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
|
||||||
[![Average time to resolve an issue](http://isitmaintained.com/badge/resolution/assimp/assimp.svg)](http://isitmaintained.com/project/assimp/assimp "Average time to resolve an issue")
|
[![Average time to resolve an issue](http://isitmaintained.com/badge/resolution/assimp/assimp.svg)](http://isitmaintained.com/project/assimp/assimp "Average time to resolve an issue")
|
||||||
[![Codacy Badge](https://api.codacy.com/project/badge/Grade/5be56faac64f46fc941ac890fb4febef)](https://www.codacy.com/app/kimkulling/assimp?utm_source=github.com&utm_medium=referral&utm_content=assimp/assimp&utm_campaign=Badge_Grade)
|
|
||||||
[![Total alerts](https://img.shields.io/lgtm/alerts/g/assimp/assimp.svg?logo=lgtm&logoWidth=18)](https://lgtm.com/projects/g/assimp/assimp/alerts/)
|
[![Total alerts](https://img.shields.io/lgtm/alerts/g/assimp/assimp.svg?logo=lgtm&logoWidth=18)](https://lgtm.com/projects/g/assimp/assimp/alerts/)
|
||||||
<br>
|
<br>
|
||||||
|
|
||||||
|
|
|
@ -88,7 +88,7 @@ using namespace Assimp::Blender;
|
||||||
using namespace Assimp::Formatter;
|
using namespace Assimp::Formatter;
|
||||||
|
|
||||||
static const aiImporterDesc blenderDesc = {
|
static const aiImporterDesc blenderDesc = {
|
||||||
"Blender 3D Importer \nhttp://www.blender3d.org",
|
"Blender 3D Importer (http://www.blender3d.org)",
|
||||||
"",
|
"",
|
||||||
"",
|
"",
|
||||||
"No animation support yet",
|
"No animation support yet",
|
||||||
|
|
|
@ -162,6 +162,9 @@ inline static bool ReadValue(Value &val, T &out) {
|
||||||
|
|
||||||
template <class T>
|
template <class T>
|
||||||
inline static bool ReadMember(Value &obj, const char *id, T &out) {
|
inline static bool ReadMember(Value &obj, const char *id, T &out) {
|
||||||
|
if (!obj.IsObject()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
Value::MemberIterator it = obj.FindMember(id);
|
Value::MemberIterator it = obj.FindMember(id);
|
||||||
if (it != obj.MemberEnd()) {
|
if (it != obj.MemberEnd()) {
|
||||||
return ReadHelper<T>::Read(it->value, out);
|
return ReadHelper<T>::Read(it->value, out);
|
||||||
|
@ -176,6 +179,9 @@ inline static T MemberOrDefault(Value &obj, const char *id, T defaultValue) {
|
||||||
}
|
}
|
||||||
|
|
||||||
inline Value *FindMember(Value &val, const char *id) {
|
inline Value *FindMember(Value &val, const char *id) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(id);
|
Value::MemberIterator it = val.FindMember(id);
|
||||||
return (it != val.MemberEnd()) ? &it->value : nullptr;
|
return (it != val.MemberEnd()) ? &it->value : nullptr;
|
||||||
}
|
}
|
||||||
|
@ -193,6 +199,9 @@ inline void throwUnexpectedTypeError(const char (&expectedTypeName)[N], const ch
|
||||||
// Look-up functions with type checks. Context and extra context help the user identify the problem if there's an error.
|
// Look-up functions with type checks. Context and extra context help the user identify the problem if there's an error.
|
||||||
|
|
||||||
inline Value *FindStringInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
inline Value *FindStringInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(memberId);
|
Value::MemberIterator it = val.FindMember(memberId);
|
||||||
if (it == val.MemberEnd()) {
|
if (it == val.MemberEnd()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -204,6 +213,9 @@ inline Value *FindStringInContext(Value &val, const char *memberId, const char*
|
||||||
}
|
}
|
||||||
|
|
||||||
inline Value *FindNumberInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
inline Value *FindNumberInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(memberId);
|
Value::MemberIterator it = val.FindMember(memberId);
|
||||||
if (it == val.MemberEnd()) {
|
if (it == val.MemberEnd()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -215,6 +227,9 @@ inline Value *FindNumberInContext(Value &val, const char *memberId, const char*
|
||||||
}
|
}
|
||||||
|
|
||||||
inline Value *FindUIntInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
inline Value *FindUIntInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(memberId);
|
Value::MemberIterator it = val.FindMember(memberId);
|
||||||
if (it == val.MemberEnd()) {
|
if (it == val.MemberEnd()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -226,6 +241,9 @@ inline Value *FindUIntInContext(Value &val, const char *memberId, const char* co
|
||||||
}
|
}
|
||||||
|
|
||||||
inline Value *FindArrayInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
inline Value *FindArrayInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(memberId);
|
Value::MemberIterator it = val.FindMember(memberId);
|
||||||
if (it == val.MemberEnd()) {
|
if (it == val.MemberEnd()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -237,6 +255,9 @@ inline Value *FindArrayInContext(Value &val, const char *memberId, const char* c
|
||||||
}
|
}
|
||||||
|
|
||||||
inline Value *FindObjectInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
inline Value *FindObjectInContext(Value &val, const char *memberId, const char* context, const char* extraContext = nullptr) {
|
||||||
|
if (!val.IsObject()) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
Value::MemberIterator it = val.FindMember(memberId);
|
Value::MemberIterator it = val.FindMember(memberId);
|
||||||
if (it == val.MemberEnd()) {
|
if (it == val.MemberEnd()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
@ -886,7 +907,7 @@ inline void Accessor::Read(Value &obj, Asset &r) {
|
||||||
componentType = MemberOrDefault(obj, "componentType", ComponentType_BYTE);
|
componentType = MemberOrDefault(obj, "componentType", ComponentType_BYTE);
|
||||||
{
|
{
|
||||||
const Value* countValue = FindUInt(obj, "count");
|
const Value* countValue = FindUInt(obj, "count");
|
||||||
if (!countValue || countValue->GetInt() < 1)
|
if (!countValue || countValue->GetUint() < 1)
|
||||||
{
|
{
|
||||||
throw DeadlyImportError("A strictly positive count value is required, when reading ", id.c_str(), name.empty() ? "" : " (" + name + ")");
|
throw DeadlyImportError("A strictly positive count value is required, when reading ", id.c_str(), name.empty() ? "" : " (" + name + ")");
|
||||||
}
|
}
|
||||||
|
@ -1105,7 +1126,9 @@ inline Accessor::Indexer::Indexer(Accessor &acc) :
|
||||||
template <class T>
|
template <class T>
|
||||||
T Accessor::Indexer::GetValue(int i) {
|
T Accessor::Indexer::GetValue(int i) {
|
||||||
ai_assert(data);
|
ai_assert(data);
|
||||||
ai_assert(i * stride < accessor.GetMaxByteSize());
|
if (i * stride >= accessor.GetMaxByteSize()) {
|
||||||
|
throw DeadlyImportError("GLTF: Invalid index ", i, ", count out of range for buffer with stride ", stride, " and size ", accessor.GetMaxByteSize(), ".");
|
||||||
|
}
|
||||||
// Ensure that the memcpy doesn't overwrite the local.
|
// Ensure that the memcpy doesn't overwrite the local.
|
||||||
const size_t sizeToCopy = std::min(elemSize, sizeof(T));
|
const size_t sizeToCopy = std::min(elemSize, sizeof(T));
|
||||||
T value = T();
|
T value = T();
|
||||||
|
|
|
@ -1172,7 +1172,7 @@ aiNodeAnim *CreateNodeAnim(glTF2::Asset&, Node &node, AnimationSamplers &sampler
|
||||||
|
|
||||||
static const float kMillisecondsFromSeconds = 1000.f;
|
static const float kMillisecondsFromSeconds = 1000.f;
|
||||||
|
|
||||||
if (samplers.translation) {
|
if (samplers.translation && samplers.translation->input && samplers.translation->output) {
|
||||||
float *times = nullptr;
|
float *times = nullptr;
|
||||||
samplers.translation->input->ExtractData(times);
|
samplers.translation->input->ExtractData(times);
|
||||||
aiVector3D *values = nullptr;
|
aiVector3D *values = nullptr;
|
||||||
|
@ -1196,7 +1196,7 @@ aiNodeAnim *CreateNodeAnim(glTF2::Asset&, Node &node, AnimationSamplers &sampler
|
||||||
anim->mPositionKeys->mValue.z = node.translation.value[2];
|
anim->mPositionKeys->mValue.z = node.translation.value[2];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (samplers.rotation) {
|
if (samplers.rotation && samplers.rotation->input && samplers.rotation->output) {
|
||||||
float *times = nullptr;
|
float *times = nullptr;
|
||||||
samplers.rotation->input->ExtractData(times);
|
samplers.rotation->input->ExtractData(times);
|
||||||
aiQuaternion *values = nullptr;
|
aiQuaternion *values = nullptr;
|
||||||
|
@ -1224,7 +1224,7 @@ aiNodeAnim *CreateNodeAnim(glTF2::Asset&, Node &node, AnimationSamplers &sampler
|
||||||
anim->mRotationKeys->mValue.w = node.rotation.value[3];
|
anim->mRotationKeys->mValue.w = node.rotation.value[3];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (samplers.scale) {
|
if (samplers.scale && samplers.scale->input && samplers.scale->output) {
|
||||||
float *times = nullptr;
|
float *times = nullptr;
|
||||||
samplers.scale->input->ExtractData(times);
|
samplers.scale->input->ExtractData(times);
|
||||||
aiVector3D *values = nullptr;
|
aiVector3D *values = nullptr;
|
||||||
|
|
|
@ -90,9 +90,11 @@ DefaultIOStream::~DefaultIOStream() {
|
||||||
size_t DefaultIOStream::Read(void *pvBuffer,
|
size_t DefaultIOStream::Read(void *pvBuffer,
|
||||||
size_t pSize,
|
size_t pSize,
|
||||||
size_t pCount) {
|
size_t pCount) {
|
||||||
|
if (0 == pCount) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
ai_assert(nullptr != pvBuffer);
|
ai_assert(nullptr != pvBuffer);
|
||||||
ai_assert(0 != pSize);
|
ai_assert(0 != pSize);
|
||||||
ai_assert(0 != pCount);
|
|
||||||
|
|
||||||
return (mFile ? ::fread(pvBuffer, pSize, pCount, mFile) : 0);
|
return (mFile ? ::fread(pvBuffer, pSize, pCount, mFile) : 0);
|
||||||
}
|
}
|
||||||
|
|
|
@ -135,7 +135,9 @@ void SortByPTypeProcess::Execute(aiScene *pScene) {
|
||||||
std::vector<unsigned int>::iterator meshIdx = replaceMeshIndex.begin();
|
std::vector<unsigned int>::iterator meshIdx = replaceMeshIndex.begin();
|
||||||
for (unsigned int i = 0; i < pScene->mNumMeshes; ++i) {
|
for (unsigned int i = 0; i < pScene->mNumMeshes; ++i) {
|
||||||
aiMesh *const mesh = pScene->mMeshes[i];
|
aiMesh *const mesh = pScene->mMeshes[i];
|
||||||
ai_assert(0 != mesh->mPrimitiveTypes);
|
if (mesh->mPrimitiveTypes == 0) {
|
||||||
|
throw DeadlyImportError("Mesh with invalid primitive type: ", mesh->mName.C_Str());
|
||||||
|
}
|
||||||
|
|
||||||
// if there's just one primitive type in the mesh there's nothing to do for us
|
// if there's just one primitive type in the mesh there's nothing to do for us
|
||||||
unsigned int num = 0;
|
unsigned int num = 0;
|
||||||
|
|
|
@ -209,9 +209,14 @@ enum aiPostProcessSteps
|
||||||
/** <hr>Removes the node graph and pre-transforms all vertices with
|
/** <hr>Removes the node graph and pre-transforms all vertices with
|
||||||
* the local transformation matrices of their nodes.
|
* the local transformation matrices of their nodes.
|
||||||
*
|
*
|
||||||
* The output scene still contains nodes, however there is only a
|
* If the resulting scene can be reduced to a single mesh, with a single
|
||||||
* root node with children, each one referencing only one mesh,
|
* material, no lights, and no cameras, then the output scene will contain
|
||||||
* and each mesh referencing one material. For rendering, you can
|
* only a root node (with no children) that references the single mesh.
|
||||||
|
* Otherwise, the output scene will be reduced to a root node with a single
|
||||||
|
* level of child nodes, each one referencing one mesh, and each mesh
|
||||||
|
* referencing one material.
|
||||||
|
*
|
||||||
|
* In either case, for rendering, you can
|
||||||
* simply render all meshes in order - you don't need to pay
|
* simply render all meshes in order - you don't need to pay
|
||||||
* attention to local transformations and the node hierarchy.
|
* attention to local transformations and the node hierarchy.
|
||||||
* Animations are removed during this step.
|
* Animations are removed during this step.
|
||||||
|
|
Loading…
Reference in New Issue