229 lines
8.3 KiB
C++
229 lines
8.3 KiB
C++
/**
|
|
* @file llmodelloader.h
|
|
* @brief LLModelLoader class definition
|
|
*
|
|
* $LicenseInfo:firstyear=2004&license=viewerlgpl$
|
|
* Second Life Viewer Source Code
|
|
* Copyright (C) 2010, Linden Research, Inc.
|
|
*
|
|
* This library is free software; you can redistribute it and/or
|
|
* modify it under the terms of the GNU Lesser General Public
|
|
* License as published by the Free Software Foundation;
|
|
* version 2.1 of the License only.
|
|
*
|
|
* This library is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
* Lesser General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU Lesser General Public
|
|
* License along with this library; if not, write to the Free Software
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
|
*
|
|
* Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
|
|
* $/LicenseInfo$
|
|
*/
|
|
|
|
#ifndef LL_LLMODELLOADER_H
|
|
#define LL_LLMODELLOADER_H
|
|
|
|
#include "llmodel.h"
|
|
#include "llthread.h"
|
|
#include <boost/function.hpp>
|
|
#include <list>
|
|
|
|
class LLJoint;
|
|
|
|
typedef std::map<std::string, LLMatrix4> JointTransformMap;
|
|
typedef std::map<std::string, LLMatrix4>::iterator JointTransformMapIt;
|
|
typedef std::map<std::string, std::string, std::less<>> JointMap;
|
|
typedef std::deque<std::string> JointNameSet;
|
|
|
|
const S32 SLM_SUPPORTED_VERSION = 3;
|
|
const S32 NUM_LOD = 4;
|
|
|
|
const U32 LEGACY_RIG_OK = 0;
|
|
const U32 LEGACY_RIG_FLAG_TOO_MANY_JOINTS = 1;
|
|
const U32 LEGACY_RIG_FLAG_UNKNOWN_JOINT = 2;
|
|
|
|
class LLModelLoader : public LLThread
|
|
{
|
|
public:
|
|
|
|
typedef std::map<std::string, LLImportMaterial> material_map;
|
|
typedef std::vector<LLPointer<LLModel>> model_list;
|
|
typedef std::vector<LLModelInstance> model_instance_list;
|
|
typedef std::map<LLMatrix4, model_instance_list> scene;
|
|
|
|
// Callback with loaded model data and loaded LoD
|
|
//
|
|
typedef boost::function<void (scene&, model_list&, S32, void*)> load_callback_t;
|
|
|
|
// Function to provide joint lookup by name
|
|
// (within preview avi skeleton, for example)
|
|
//
|
|
typedef boost::function<LLJoint* (const std::string&, void*)> joint_lookup_func_t;
|
|
|
|
// Func to load and associate material with all it's textures,
|
|
// returned value is the number of textures loaded
|
|
// intentionally non-const so func can modify material to
|
|
// store platform-specific data
|
|
//
|
|
typedef boost::function<U32 (LLImportMaterial&, void*)> texture_load_func_t;
|
|
|
|
// Callback to inform client of state changes
|
|
// during loading process (errors will be reported
|
|
// as state changes here as well)
|
|
//
|
|
typedef boost::function<void (U32, void*)> state_callback_t;
|
|
|
|
typedef enum
|
|
{
|
|
STARTING = 0,
|
|
READING_FILE,
|
|
CREATING_FACES,
|
|
GENERATING_VERTEX_BUFFERS,
|
|
GENERATING_LOD,
|
|
DONE,
|
|
WARNING_BIND_SHAPE_ORIENTATION,
|
|
ERROR_PARSING, //basically loading failed
|
|
ERROR_MATERIALS_NOT_A_SUBSET, // <FS:Beq/> FIRE-30965 - better error differentiation
|
|
ERROR_PASSWORD_REQUIRED,
|
|
ERROR_NEED_MORE_MEMORY,
|
|
ERROR_INVALID_FILE,
|
|
ERROR_LOADER_SETUP,
|
|
ERROR_INVALID_PARAMETERS,
|
|
ERROR_OUT_OF_RANGE,
|
|
ERROR_FILE_VERSION_INVALID,
|
|
ERROR_LOD_MODEL_MISMATCH, // <FS:Beq/> clean up and improve error reporting
|
|
ERROR_HIGH_LOD_MODEL_MISSING, // <FS:Beq/> clean up and improve error reporting
|
|
ERROR_MODEL // this error should always be last in this list, error code is passed as ERROR_MODEL+error_code
|
|
} eLoadState;
|
|
|
|
U32 mState;
|
|
std::string mFilename;
|
|
|
|
S32 mLod;
|
|
|
|
LLMatrix4 mTransform;
|
|
bool mFirstTransform;
|
|
LLVector3 mExtents[2];
|
|
|
|
bool mTrySLM;
|
|
bool mCacheOnlyHitIfRigged; // ignore cached SLM if it does not contain rig info (and we want rig info)
|
|
bool mTexturesNeedScaling;
|
|
|
|
model_list mModelList;
|
|
// The scene is pretty much what ends up getting loaded for upload. Basically assign things to this guy if you want something uploaded.
|
|
scene mScene;
|
|
|
|
typedef std::queue<LLPointer<LLModel> > model_queue;
|
|
|
|
//queue of models that need a physics rep
|
|
model_queue mPhysicsQ;
|
|
|
|
//map of avatar joints as named in COLLADA assets to internal joint names
|
|
// Do not use this for anything other than looking up the name of a joint. This is populated elsewhere.
|
|
JointMap mJointMap;
|
|
|
|
// The joint list is what you want to use to actually setup the specific joint transformations.
|
|
JointTransformMap& mJointList;
|
|
JointNameSet& mJointsFromNode;
|
|
|
|
|
|
U32 mMaxJointsPerMesh;
|
|
U32 mDebugMode; // see dumDebugData() for details
|
|
|
|
LLModelLoader(
|
|
std::string filename,
|
|
S32 lod,
|
|
LLModelLoader::load_callback_t load_cb,
|
|
LLModelLoader::joint_lookup_func_t joint_lookup_func,
|
|
LLModelLoader::texture_load_func_t texture_load_func,
|
|
LLModelLoader::state_callback_t state_cb,
|
|
void* opaque_userdata,
|
|
JointTransformMap& jointTransformMap,
|
|
JointNameSet& jointsFromNodes,
|
|
JointMap& legalJointNamesMap,
|
|
U32 maxJointsPerMesh,
|
|
U32 modelLimit,
|
|
U32 debugMode);
|
|
virtual ~LLModelLoader();
|
|
|
|
virtual void setNoNormalize() { mNoNormalize = true; }
|
|
virtual void setNoOptimize() { mNoOptimize = true; }
|
|
|
|
virtual void run();
|
|
|
|
static bool getSLMFilename(const std::string& model_filename, std::string& slm_filename);
|
|
|
|
// Will try SLM or derived class OpenFile as appropriate
|
|
//
|
|
virtual bool doLoadModel();
|
|
|
|
// Derived classes need to provide their parsing of files here
|
|
//
|
|
virtual bool OpenFile(const std::string& filename) = 0;
|
|
|
|
bool loadFromSLM(const std::string& filename);
|
|
|
|
void loadModelCallback();
|
|
void loadTextures() ; // called in the main thread.
|
|
void setLoadState(U32 state);
|
|
|
|
void stretch_extents(const LLModel* model, const LLMatrix4& mat);
|
|
|
|
bool verifyCount( int expected, int result );
|
|
|
|
//Determines the viability of an asset to be used as an avatar rig (w or w/o joint upload caps)
|
|
void critiqueRigForUploadApplicability( const std::vector<std::string> &jointListFromAsset );
|
|
|
|
//Determines if a rig is a legacy from the joint list
|
|
U32 determineRigLegacyFlags( const std::vector<std::string> &jointListFromAsset );
|
|
|
|
//Determines if a rig is suitable for upload
|
|
bool isRigSuitableForJointPositionUpload( const std::vector<std::string> &jointListFromAsset );
|
|
|
|
const bool isRigValidForJointPositionUpload( void ) const { return mRigValidJointUpload; }
|
|
void setRigValidForJointPositionUpload( bool rigValid ) { mRigValidJointUpload = rigValid; }
|
|
|
|
const bool isLegacyRigValid(void) const { return mLegacyRigFlags == 0; }
|
|
U32 getLegacyRigFlags() const { return mLegacyRigFlags; }
|
|
void setLegacyRigFlags( U32 rigFlags ) { mLegacyRigFlags = rigFlags; }
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// isNodeAJoint()
|
|
//-----------------------------------------------------------------------------
|
|
bool isNodeAJoint(const char* name)
|
|
{
|
|
return name != NULL && mJointMap.find(name) != mJointMap.end();
|
|
}
|
|
|
|
const LLSD logOut() const { return mWarningsArray; }
|
|
void clearLog() { mWarningsArray.clear(); }
|
|
void dumpDebugData();
|
|
|
|
protected:
|
|
LLModelLoader::load_callback_t mLoadCallback;
|
|
LLModelLoader::joint_lookup_func_t mJointLookupFunc;
|
|
LLModelLoader::texture_load_func_t mTextureLoadFunc;
|
|
LLModelLoader::state_callback_t mStateCallback;
|
|
void* mOpaqueData;
|
|
|
|
bool mRigValidJointUpload;
|
|
U32 mLegacyRigFlags;
|
|
U32 mGeneratedModelLimit; // Attempt to limit amount of generated submodels
|
|
|
|
bool mNoNormalize;
|
|
bool mNoOptimize;
|
|
|
|
JointTransformMap mJointTransformMap;
|
|
|
|
LLSD mWarningsArray; // preview floater will pull logs from here
|
|
|
|
static std::list<LLModelLoader*> sActiveLoaderList;
|
|
static bool isAlive(LLModelLoader* loader);
|
|
};
|
|
|
|
#endif // LL_LLMODELLOADER_H
|