Added new process - Scale-to-unit-box

This allows to transform input meshes, scaling its
vertices to unit box in order to let mesh become visible
for small scenes or limited frustums.
pull/435/head
Alov Maxim 2015-01-20 18:02:33 +04:00
parent af48644e56
commit 16d9addf7b
5 changed files with 167 additions and 1 deletions

View File

@ -482,6 +482,8 @@ SET( PostProcessing_SRCS
RemoveRedundantMaterials.h RemoveRedundantMaterials.h
RemoveVCProcess.cpp RemoveVCProcess.cpp
RemoveVCProcess.h RemoveVCProcess.h
ScaleToUnitBoxProcess.cpp
ScaleToUnitBoxProcess.h
SortByPTypeProcess.cpp SortByPTypeProcess.cpp
SortByPTypeProcess.h SortByPTypeProcess.h
SplitLargeMeshes.cpp SplitLargeMeshes.cpp

View File

@ -121,6 +121,9 @@ corresponding preprocessor flag to selectively disable steps.
#ifndef ASSIMP_BUILD_NO_DEBONE_PROCESS #ifndef ASSIMP_BUILD_NO_DEBONE_PROCESS
# include "DeboneProcess.h" # include "DeboneProcess.h"
#endif #endif
#ifndef ASSIMP_BUILD_NO_SCALETOUNITBOX_PROCESS
# include "ScaleToUnitBoxProcess.h"
#endif
namespace Assimp { namespace Assimp {
@ -190,6 +193,9 @@ void GetPostProcessingStepInstanceList(std::vector< BaseProcess* >& out)
#if (!defined ASSIMP_BUILD_NO_GENFACENORMALS_PROCESS) #if (!defined ASSIMP_BUILD_NO_GENFACENORMALS_PROCESS)
out.push_back( new GenFaceNormalsProcess()); out.push_back( new GenFaceNormalsProcess());
#endif #endif
#if (!defined ASSIMP_BUILD_NO_SCALETOUNITBOX_PROCESS)
out.push_back( new ScaleToUnitBoxProcess());
#endif
// ......................................................................... // .........................................................................
// DON'T change the order of these five .. // DON'T change the order of these five ..

View File

@ -0,0 +1,87 @@
/*
* ScaleToUnitBoxProcess.cpp
*
* Created on: Jan 20, 2015
* Author: Alov Maxim <alovmax@yandex.ru>
*/
/// @file ScaleToUnitBoxProcess.cpp
/// Implementation of the ScaleToUnitBox postprocessing step
#include "AssimpPCH.h"
// internal headers of the post-processing framework
#include "ScaleToUnitBoxProcess.h"
using namespace Assimp;
// ------------------------------------------------------------------------------------------------
// Constructor
ScaleToUnitBoxProcess::ScaleToUnitBoxProcess()
{
// nothing to do here
}
// ------------------------------------------------------------------------------------------------
// Destructor
ScaleToUnitBoxProcess::~ScaleToUnitBoxProcess()
{
// nothing to do here
}
// ------------------------------------------------------------------------------------------------
// Returns whether the processing step is present in the given flag.
bool ScaleToUnitBoxProcess::IsActive( unsigned int pFlags) const
{
return !!(pFlags & aiProcess_ScaleToUnitBox);
}
// ------------------------------------------------------------------------------------------------
// Updates internal properties
void ScaleToUnitBoxProcess::SetupProperties(const Importer* pImp)
{
// nothing to do here
}
// ------------------------------------------------------------------------------------------------
// Executes the post processing step on the given imported data.
void ScaleToUnitBoxProcess::Execute( aiScene* pScene)
{
DefaultLogger::get()->debug("ScaleToUnitBoxProcess begin");
if (pScene->mFlags & AI_SCENE_FLAGS_NON_VERBOSE_FORMAT) {
throw DeadlyImportError("Post-processing order mismatch: expecting pseudo-indexed (\"verbose\") vertices here");
}
for( unsigned int a = 0; a < pScene->mNumMeshes; a++) {
this->ScaleMesh( pScene->mMeshes[a]);
}
DefaultLogger::get()->info("ScaleToUnitBoxProcess finished. "
"Mesh vertices have been scaled to unit box");
}
// ------------------------------------------------------------------------------------------------
// Scales all vertices of the given mesh to conform unit box.
void ScaleToUnitBoxProcess::ScaleMesh( const aiMesh* pMesh) const
{
aiVector3D center = aiVector3D(0.0f, 0.0f, 0.0f);
for (unsigned int i = 0; i < pMesh->mNumVertices; ++i) {
center += pMesh->mVertices[i];
}
center /= float(pMesh->mNumVertices);
float radius = 0.0f;
for (unsigned int i = 0; i < pMesh->mNumVertices; ++i) {
aiVector3D distanceValues = center;
distanceValues -= pMesh->mVertices[i];
float vDistance = distanceValues.Length();
if (vDistance > radius) {
radius = vDistance;
}
}
for (unsigned int i = 0; i < pMesh->mNumVertices; ++i) {
aiVector3D segment = pMesh->mVertices[i];
segment -= center;
segment /= radius;
pMesh->mVertices[i].Set(segment.x, segment.y, segment.z);
}
}

View File

@ -0,0 +1,59 @@
/*
* ScaleToUnitBoxProcess.h
*
* Created on: Jan 20, 2015
* Author: Alov Maxim <alovmax@yandex.ru>
*/
/// @file ScaleToUnitBoxProcess.h
/// Defines a post processing step to scale mesh vertices into unit box
#ifndef AI_SCALETOUNITBOXPROCESS_H_INC
#define AI_SCALETOUNITBOXPROCESS_H_INC
#include <vector>
#include "BaseProcess.h"
#include "../include/assimp/mesh.h"
#include "../include/assimp/scene.h"
namespace Assimp
{
class ScaleToUnitBoxProcess : public BaseProcess
{
public:
ScaleToUnitBoxProcess();
~ScaleToUnitBoxProcess();
public:
/** Returns whether the processing step is present in the given flag.
* @param pFlags The processing flags the importer was called with. A
* bitwise combination of #aiPostProcessSteps.
* @return true if the process is present in this flag fields,
* false if not.
*/
bool IsActive( unsigned int pFlags) const;
/** Called prior to ExecuteOnScene().
* The function is a request to the process to update its configuration
* basing on the Importer's configuration property list.
*/
virtual void SetupProperties(const Importer* pImp);
protected:
/** Executes the post processing step on the given imported data.
* At the moment a process is not supposed to fail.
* @param pScene The imported data to work at.
*/
void Execute( aiScene* pScene);
/// Scales all vertices of the given mesh to conform unit box.
/// @param pMesh the Mesh which vertices to be scaled.
void ScaleMesh( const aiMesh* pMesh) const;
};
} // end of namespace Assimp
#endif // !!AI_SCALETOUNITBOXPROCESS_H_INC

View File

@ -523,11 +523,23 @@ enum aiPostProcessSteps
* Use <tt>#AI_CONFIG_PP_DB_ALL_OR_NONE</tt> if you want bones removed if and * Use <tt>#AI_CONFIG_PP_DB_ALL_OR_NONE</tt> if you want bones removed if and
* only if all bones within the scene qualify for removal. * only if all bones within the scene qualify for removal.
*/ */
aiProcess_Debone = 0x4000000 aiProcess_Debone = 0x4000000,
// aiProcess_GenEntityMeshes = 0x100000, // aiProcess_GenEntityMeshes = 0x100000,
// aiProcess_OptimizeAnimations = 0x200000 // aiProcess_OptimizeAnimations = 0x200000
// aiProcess_FixTexturePaths = 0x200000 // aiProcess_FixTexturePaths = 0x200000
// -------------------------------------------------------------------------
/**
* <hr>This step scales meshes' vertices to unit box obtaining
* center and radius of resulting scene.
*
* It is recommended to use this flag with aiProcess_GenNormals or
* aiProcess_GenSmoothNormals to ensure normals being recomputed.
*
* <author> Alov Maxim <alovmaxy@yandex.ru>
*/
aiProcess_ScaleToUnitBox = 0x8000000
}; };