diff options
Diffstat (limited to 'indra/newview/llfloatermodelpreview.cpp')
-rw-r--r--[-rwxr-xr-x] | indra/newview/llfloatermodelpreview.cpp | 193 |
1 files changed, 130 insertions, 63 deletions
diff --git a/indra/newview/llfloatermodelpreview.cpp b/indra/newview/llfloatermodelpreview.cpp index 18a2729398..0f0fafcce6 100755..100644 --- a/indra/newview/llfloatermodelpreview.cpp +++ b/indra/newview/llfloatermodelpreview.cpp @@ -42,7 +42,6 @@ #include "llcombobox.h" #include "lldatapacker.h" #include "lldrawable.h" -#include "lldrawpoolavatar.h" #include "llrender.h" #include "llface.h" #include "lleconomy.h" @@ -54,6 +53,7 @@ #include "llmeshrepository.h" #include "llnotificationsutil.h" #include "llsdutil_math.h" +#include "llskinningutil.h" #include "lltextbox.h" #include "lltoolmgr.h" #include "llui.h" @@ -338,25 +338,25 @@ BOOL LLFloaterModelPreview::postBuild() LLTextBox* text = getChild<LLTextBox>(lod_label_name[i]); if (text) { - text->setMouseDownCallback(boost::bind(&LLModelPreview::setPreviewLOD, mModelPreview, i)); + text->setMouseDownCallback(boost::bind(&LLFloaterModelPreview::setPreviewLOD, this, i)); } text = getChild<LLTextBox>(lod_triangles_name[i]); if (text) { - text->setMouseDownCallback(boost::bind(&LLModelPreview::setPreviewLOD, mModelPreview, i)); + text->setMouseDownCallback(boost::bind(&LLFloaterModelPreview::setPreviewLOD, this, i)); } text = getChild<LLTextBox>(lod_vertices_name[i]); if (text) { - text->setMouseDownCallback(boost::bind(&LLModelPreview::setPreviewLOD, mModelPreview, i)); + text->setMouseDownCallback(boost::bind(&LLFloaterModelPreview::setPreviewLOD, this, i)); } text = getChild<LLTextBox>(lod_status_name[i]); if (text) { - text->setMouseDownCallback(boost::bind(&LLModelPreview::setPreviewLOD, mModelPreview, i)); + text->setMouseDownCallback(boost::bind(&LLFloaterModelPreview::setPreviewLOD, this, i)); } } std::string current_grid = LLGridManager::getInstance()->getGridId(); @@ -489,10 +489,18 @@ void LLFloaterModelPreview::onClickCalculateBtn() bool upload_skinweights = childGetValue("upload_skin").asBoolean(); bool upload_joint_positions = childGetValue("upload_joints").asBoolean(); + if (upload_joint_positions) + { + // Diagnostic message showing list of joints for which joint offsets are defined. + // FIXME - given time, would be much better to put this in the UI, in updateStatusMessages(). + mModelPreview->getPreviewAvatar()->showAttachmentPosOverrides(); + } + mUploadModelUrl.clear(); gMeshRepo.uploadModel(mModelPreview->mUploadData, mModelPreview->mPreviewScale, - childGetValue("upload_textures").asBoolean(), upload_skinweights, upload_joint_positions, mUploadModelUrl, false, + childGetValue("upload_textures").asBoolean(), upload_skinweights, upload_joint_positions, + mUploadModelUrl, false, getWholeModelFeeObserverHandle()); toggleCalculateButton(false); @@ -610,7 +618,7 @@ void LLFloaterModelPreview::onAutoFillCommit(LLUICtrl* ctrl, void* userdata) { LLFloaterModelPreview* fp = (LLFloaterModelPreview*) userdata; - fp->mModelPreview->genLODs(); + fp->mModelPreview->queryLODs(); } void LLFloaterModelPreview::onLODParamCommit(S32 lod, bool enforce_tri_limit) @@ -638,7 +646,12 @@ void LLFloaterModelPreview::onLODParamCommit(S32 lod, bool enforce_tri_limit) //----------------------------------------------------------------------------- void LLFloaterModelPreview::draw() { - LLFloater::draw(); + LLFloater::draw(); + + if (!mModelPreview) + { + return; + } mModelPreview->update(); @@ -668,7 +681,7 @@ void LLFloaterModelPreview::draw() childSetTextArg("prim_cost", "[PRIM_COST]", llformat("%d", mModelPreview->mResourceCost)); childSetTextArg("description_label", "[TEXTURES]", llformat("%d", mModelPreview->mTextureSet.size())); - if (mModelPreview) + if (mModelPreview->lodsReady()) { gGL.color3f(1.f, 1.f, 1.f); @@ -1178,13 +1191,13 @@ void LLFloaterModelPreview::onMouseCaptureLostModelPreview(LLMouseHandler* handl LLModelPreview::LLModelPreview(S32 width, S32 height, LLFloater* fmp) : LLViewerDynamicTexture(width, height, 3, ORDER_MIDDLE, FALSE), LLMutex(NULL) +, mLodsQuery() , mPelvisZOffset( 0.0f ) , mLegacyRigValid( false ) , mRigValidJointUpload( false ) , mPhysicsSearchLOD( LLModel::LOD_PHYSICS ) , mResetJoints( false ) , mModelNoErrors( true ) -, mRigParityWithScene( false ) , mLastJointUpdate( false ) { mNeedsUpdate = TRUE; @@ -1357,6 +1370,14 @@ void LLFloaterModelPreview::setDetails(F32 x, F32 y, F32 z, F32 streaming_cost, childSetTextArg("import_dimensions", "[Z]", llformat("%.3f", z)); } +void LLFloaterModelPreview::setPreviewLOD(S32 lod) +{ + if (mModelPreview) + { + mModelPreview->setPreviewLOD(lod); + } +} + void LLModelPreview::rebuildUploadData() { @@ -1544,9 +1565,18 @@ void LLModelPreview::rebuildUploadData() } instance.mLOD[i] = lod_model; } - else if (importerDebug) + else { - LL_INFOS() << "List of models does not include " << instance.mLabel << LL_ENDL; + if (i < LLModel::LOD_HIGH && !lodsReady()) + { + // assign a placeholder from previous LOD until lod generation is complete. + // Note: we might need to assign it regardless of conditions like named search does, to prevent crashes. + instance.mLOD[i] = instance.mLOD[i + 1]; + } + if (importerDebug) + { + LL_INFOS() << "List of models does not include " << instance.mLabel << LL_ENDL; + } } } @@ -1708,18 +1738,17 @@ void LLModelPreview::clearModel(S32 lod) mScene[lod].clear(); } -void LLModelPreview::getLegalJointNames(JointNameSet& legal_joint_names) +void LLModelPreview::getJointAliases( JointMap& joint_map) { // Get all standard skeleton joints from the preview avatar. LLVOAvatar *av = getPreviewAvatar(); - const LLVOAvatar::avatar_joint_list_t &skel = av->getSkeleton(); - for (S32 i=0; i<skel.size(); i++) + + //Joint names and aliases come from avatar_skeleton.xml + + joint_map = av->getJointAliases(); + for (S32 i = 0; i < av->mNumCollisionVolumes; i++) { - LLAvatarJoint *joint = skel[i]; - if (joint) - { - legal_joint_names.push_back(joint->getName()); - } + joint_map[av->mCollisionVolumes[i].getName()] = av->mCollisionVolumes[i].getName(); } } @@ -1765,9 +1794,8 @@ void LLModelPreview::loadModel(std::string filename, S32 lod, bool force_disable clearGLODGroup(); } - - JointNameSet legal_joint_names; - getLegalJointNames(legal_joint_names); + std::map<std::string, std::string> joint_alias_map; + getJointAliases(joint_alias_map); mModelLoader = new LLDAELoader( filename, @@ -1779,8 +1807,10 @@ void LLModelPreview::loadModel(std::string filename, S32 lod, bool force_disable this, mJointTransformMap, mJointsFromNode, - legal_joint_names, - gSavedSettings.getU32("ImporterModelLimit")); + joint_alias_map, + LLSkinningUtil::getMaxJointCount(), + gSavedSettings.getU32("ImporterModelLimit"), + gSavedSettings.getBOOL("ImporterPreprocessDAE")); if (force_disable_slm) { @@ -3303,14 +3333,17 @@ void LLModelPreview::genBuffers(S32 lod, bool include_skin_weights) LLVector3 pos(vf.mPositions[i].getF32ptr()); const LLModel::weight_list& weight_list = base_mdl->getJointInfluences(pos); + llassert(weight_list.size()>0 && weight_list.size() <= 4); // LLModel::loadModel() should guarantee this LLVector4 w(0,0,0,0); for (U32 i = 0; i < weight_list.size(); ++i) { - F32 wght = llmin(weight_list[i].mWeight, 0.999999f); + F32 wght = llclamp(weight_list[i].mWeight, 0.001f, 0.999f); F32 joint = (F32) weight_list[i].mJointIdx; w.mV[i] = joint + wght; + llassert(w.mV[i]-(S32)w.mV[i]>0.0f); // because weights are non-zero, and range of wt values + //should not cause floating point precision issues. } *(weights_strider++) = w; @@ -3336,14 +3369,25 @@ void LLModelPreview::genBuffers(S32 lod, bool include_skin_weights) void LLModelPreview::update() { if (mGenLOD) - { - mGenLOD = false; - genLODs(); - refresh(); - updateStatusMessages(); - } + { + bool subscribe_for_generation = mLodsQuery.empty(); + mGenLOD = false; + mDirty = true; + mLodsQuery.clear(); - if (mDirty) + for (S32 lod = LLModel::LOD_HIGH; lod >= 0; --lod) + { + // adding all lods into query for generation + mLodsQuery.push_back(lod); + } + + if (subscribe_for_generation) + { + doOnIdleRepeating(lodQueryCallback); + } + } + + if (mDirty && mLodsQuery.empty()) { mDirty = false; mResourceCost = calcResourceCost(); @@ -3353,19 +3397,6 @@ void LLModelPreview::update() } //----------------------------------------------------------------------------- -// getTranslationForJointOffset() -//----------------------------------------------------------------------------- -LLVector3 LLModelPreview::getTranslationForJointOffset( std::string joint ) -{ - LLMatrix4 jointTransform; - if ( mJointTransformMap.find( joint ) != mJointTransformMap.end() ) - { - jointTransform = mJointTransformMap[joint]; - return jointTransform.getTranslation(); - } - return LLVector3(0.0f,0.0f,0.0f); -} -//----------------------------------------------------------------------------- // createPreviewAvatar //----------------------------------------------------------------------------- void LLModelPreview::createPreviewAvatar( void ) @@ -3584,6 +3615,7 @@ BOOL LLModelPreview::render() fmp->enableViewOption("show_skin_weight"); fmp->setViewOptionEnabled("show_joint_positions", skin_weight); mFMP->childEnable("upload_skin"); + mFMP->childSetValue("show_skin_weight", skin_weight); } } else @@ -3987,20 +4019,6 @@ BOOL LLModelPreview::render() LLVector3::z_axis, // up target_pos); // point of interest - if (joint_positions) - { - LLGLSLShader* shader = LLGLSLShader::sCurBoundShaderPtr; - if (shader) - { - gDebugProgram.bind(); - } - getPreviewAvatar()->renderCollisionVolumes(); - if (shader) - { - shader->bind(); - } - } - for (LLModelLoader::scene::iterator iter = mScene[mPreviewLOD].begin(); iter != mScene[mPreviewLOD].end(); ++iter) { for (LLModelLoader::model_instance_list::iterator model_iter = iter->second.begin(); model_iter != iter->second.end(); ++model_iter) @@ -4028,16 +4046,17 @@ BOOL LLModelPreview::render() LLMatrix4a mat[LL_MAX_JOINTS_PER_MESH_OBJECT]; const LLMeshSkinInfo *skin = &model->mSkinInfo; - U32 count = llmin((U32) skin->mJointNames.size(), (U32) LL_MAX_JOINTS_PER_MESH_OBJECT); - LLDrawPoolAvatar::initSkinningMatrixPalette((LLMatrix4*)mat, count, + U32 count = LLSkinningUtil::getMeshJointCount(skin); + LLSkinningUtil::initSkinningMatrixPalette((LLMatrix4*)mat, count, skin, getPreviewAvatar()); LLMatrix4a bind_shape_matrix; bind_shape_matrix.loadu(skin->mBindShapeMatrix); + U32 max_joints = LLSkinningUtil::getMaxJointCount(); for (U32 j = 0; j < buffer->getNumVerts(); ++j) { LLMatrix4a final_mat; F32 *wptr = weight[j].mV; - LLDrawPoolAvatar::getPerVertexSkinMatrix(wptr, mat, true, final_mat); + LLSkinningUtil::getPerVertexSkinMatrix(wptr, mat, true, final_mat, max_joints); //VECTORIZE THIS LLVector4a& v = face.mPositions[j]; @@ -4083,6 +4102,22 @@ BOOL LLModelPreview::render() } } } + + if (joint_positions) + { + LLGLSLShader* shader = LLGLSLShader::sCurBoundShaderPtr; + if (shader) + { + gDebugProgram.bind(); + } + getPreviewAvatar()->renderCollisionVolumes(); + getPreviewAvatar()->renderBones(); + if (shader) + { + shader->bind(); + } + } + } } @@ -4240,6 +4275,29 @@ void LLModelPreview::textureLoadedCallback( } } +// static +bool LLModelPreview::lodQueryCallback() +{ + // not the best solution, but model preview belongs to floater + // so it is an easy way to check that preview still exists. + LLFloaterModelPreview* fmp = LLFloaterModelPreview::sInstance; + if (fmp && fmp->mModelPreview) + { + LLModelPreview* preview = fmp->mModelPreview; + if (preview->mLodsQuery.size() > 0) + { + S32 lod = preview->mLodsQuery.back(); + preview->mLodsQuery.pop_back(); + preview->genLODs(lod); + + // return false to continue cycle + return false; + } + } + // nothing to process + return true; +} + void LLModelPreview::onLODParamCommit(S32 lod, bool enforce_tri_limit) { if (!mLODFrozen) @@ -4437,6 +4495,15 @@ void LLFloaterModelPreview::onPermissionsReceived(const LLSD& result) // BAP HACK: handle "" for case that MeshUploadFlag cap is broken. mHasUploadPerm = (("" == upload_status) || ("valid" == upload_status)); + if (!mHasUploadPerm) + { + LL_WARNS() << "Upload permission set to false because upload_status=\"" << upload_status << "\"" << LL_ENDL; + } + else if (mHasUploadPerm && mUploadModelUrl.empty()) + { + LL_WARNS() << "Upload permission set to true but uploadModelUrl is empty!" << LL_ENDL; + } + // isModelUploadAllowed() includes mHasUploadPerm mUploadBtn->setEnabled(isModelUploadAllowed()); getChild<LLTextBox>("warning_title")->setVisible(!mHasUploadPerm); |