diff options
Diffstat (limited to 'indra/newview/llvoavatar.cpp')
-rw-r--r-- | indra/newview/llvoavatar.cpp | 121 |
1 files changed, 121 insertions, 0 deletions
diff --git a/indra/newview/llvoavatar.cpp b/indra/newview/llvoavatar.cpp index ba0da9a4c6..43a9bd2b2f 100644 --- a/indra/newview/llvoavatar.cpp +++ b/indra/newview/llvoavatar.cpp @@ -64,6 +64,7 @@ #include "llkeyframefallmotion.h" #include "llkeyframestandmotion.h" #include "llkeyframewalkmotion.h" +#include "llmeshrepository.h" #include "llmutelist.h" #include "llmoveview.h" #include "llquantize.h" @@ -79,6 +80,7 @@ #include "llviewermenu.h" #include "llviewerobjectlist.h" #include "llviewerparcelmgr.h" +#include "llviewershadermgr.h" #include "llviewerstats.h" #include "llvoavatarself.h" #include "llvovolume.h" @@ -3639,6 +3641,125 @@ bool LLVOAvatar::shouldAlphaMask() } +U32 LLVOAvatar::renderSkinnedAttachments() +{ + U32 num_indices = 0; + + const U32 data_mask = LLVertexBuffer::MAP_VERTEX | + LLVertexBuffer::MAP_NORMAL | + LLVertexBuffer::MAP_TEXCOORD0 | + LLVertexBuffer::MAP_COLOR | + LLVertexBuffer::MAP_WEIGHT4; + + for (attachment_map_t::const_iterator iter = mAttachmentPoints.begin(); + iter != mAttachmentPoints.end(); + ++iter) + { + LLViewerJointAttachment* attachment = iter->second; + for (LLViewerJointAttachment::attachedobjs_vec_t::iterator attachment_iter = attachment->mAttachedObjects.begin(); + attachment_iter != attachment->mAttachedObjects.end(); + ++attachment_iter) + { + const LLViewerObject* attached_object = (*attachment_iter); + if (attached_object && !attached_object->isHUDAttachment()) + { + const LLDrawable* drawable = attached_object->mDrawable; + if (drawable) + { + for (S32 i = 0; i < drawable->getNumFaces(); ++i) + { + LLFace* face = drawable->getFace(i); + if (face->isState(LLFace::RIGGED)) + { + LLVolume* volume = attached_object->getVolume(); + if (!volume || volume->getNumVolumeFaces() <= i) + { + continue; + } + + const LLVolumeFace& vol_face = volume->getVolumeFace(i); + + const LLMeshSkinInfo* skin = NULL; + LLVertexBuffer* buff = face->mVertexBuffer; + LLUUID mesh_id = volume->getParams().getSculptID();; + + if (!buff || + !buff->hasDataType(LLVertexBuffer::TYPE_WEIGHT4) || + buff->getRequestedVerts() != vol_face.mVertices.size()) + { + face->mVertexBuffer = NULL; + face->mLastVertexBuffer = NULL; + buff = NULL; + + if (mesh_id.notNull()) + { + skin = gMeshRepo.getSkinInfo(mesh_id); + if (skin) + { + face->mVertexBuffer = new LLVertexBuffer(data_mask, 0); + face->mVertexBuffer->allocateBuffer(vol_face.mVertices.size(), vol_face.mIndices.size(), true); + + face->setGeomIndex(0); + face->setIndicesIndex(0); + face->setSize(vol_face.mVertices.size(), vol_face.mIndices.size()); + + U16 offset = 0; + + LLMatrix4 mat_vert = skin->mBindShapeMatrix; + LLMatrix3 mat_normal; + + face->getGeometryVolume(*volume, i, mat_vert, mat_normal, offset, true); + buff = face->mVertexBuffer; + } + } + } + + if (buff && mesh_id.notNull()) + { + if (!skin) + { + skin = gMeshRepo.getSkinInfo(mesh_id); + } + + if (skin) + { + LLMatrix4 mat[64]; + + for (U32 i = 0; i < skin->mJointNames.size(); ++i) + { + LLJoint* joint = getJoint(skin->mJointNames[i]); + if (joint) + { + mat[i] = skin->mInvBindMatrix[i]; + mat[i] *= joint->getWorldMatrix(); + } + } + + gSkinnedObjectSimpleProgram.uniformMatrix4fv("matrixPalette", + skin->mJointNames.size(), + FALSE, + (GLfloat*) mat[0].mMatrix); + + buff->setBuffer(data_mask); + + U16 start = face->getGeomStart(); + U16 end = start + face->getGeomCount()-1; + S32 offset = face->getIndicesStart(); + U32 count = face->getIndicesCount(); + + buff->drawRange(LLRender::TRIANGLES, start, end, count, offset); + } + } + } + } + } + } + } + } + + return num_indices; +} + //----------------------------------------------------------------------------- // renderSkinned() //----------------------------------------------------------------------------- |