diff options
| author | Dave Parks <davep@lindenlab.com> | 2011-03-29 11:50:17 -0500 | 
|---|---|---|
| committer | Dave Parks <davep@lindenlab.com> | 2011-03-29 11:50:17 -0500 | 
| commit | 1aecac62eb88125546057be2a2a70a6b2eba1a57 (patch) | |
| tree | 3964591bb451af656f07bc751931272baafe9551 | |
| parent | f28b10608a0883da75c670c5a9d9a5056ee682ad (diff) | |
| parent | 719610e68ba8275f08f51d127ab760799cb1d1c3 (diff) | |
merge
| -rwxr-xr-x | indra/llprimitive/llmodel.cpp | 143 | ||||
| -rwxr-xr-x | indra/llprimitive/llmodel.h | 43 | ||||
| -rw-r--r-- | indra/llrender/llvertexbuffer.cpp | 16 | ||||
| -rw-r--r-- | indra/llrender/llvertexbuffer.h | 2 | ||||
| -rwxr-xr-x | indra/newview/llfloatermodelpreview.cpp | 47 | ||||
| -rw-r--r-- | indra/newview/llfloatermodelpreview.h | 3 | ||||
| -rw-r--r-- | indra/newview/llfloatermodelwizard.cpp | 1 | ||||
| -rwxr-xr-x | indra/newview/llmeshrepository.cpp | 273 | ||||
| -rw-r--r-- | indra/newview/llmeshrepository.h | 28 | ||||
| -rw-r--r-- | indra/newview/llspatialpartition.cpp | 51 | 
10 files changed, 320 insertions, 287 deletions
| diff --git a/indra/llprimitive/llmodel.cpp b/indra/llprimitive/llmodel.cpp index 81420fadb7..595f9aa307 100755 --- a/indra/llprimitive/llmodel.cpp +++ b/indra/llprimitive/llmodel.cpp @@ -1881,24 +1881,29 @@ LLModel::weight_list& LLModel::getJointInfluences(const LLVector3& pos)  void LLModel::setConvexHullDecomposition(  	const LLModel::convex_hull_decomposition& decomp)  { -	mConvexHullDecomp = decomp; +	mPhysics.mHull = decomp; +	mPhysics.mMesh.clear(); +	updateHullCenters(); +} -	mHullCenter.resize(mConvexHullDecomp.size()); +void LLModel::updateHullCenters() +{ +	mHullCenter.resize(mPhysics.mHull.size());  	mHullPoints = 0;  	mCenterOfHullCenters.clear(); -	for (U32 i = 0; i < decomp.size(); ++i) +	for (U32 i = 0; i < mPhysics.mHull.size(); ++i)  	{  		LLVector3 cur_center; -		for (U32 j = 0; j < decomp[i].size(); ++j) +		for (U32 j = 0; j < mPhysics.mHull[i].size(); ++j)  		{ -			cur_center += decomp[i][j]; +			cur_center += mPhysics.mHull[i][j];  		}  		mCenterOfHullCenters += cur_center; -		cur_center *= 1.f/decomp[i].size(); +		cur_center *= 1.f/mPhysics.mHull[i].size();  		mHullCenter[i] = cur_center; -		mHullPoints += decomp[i].size(); +		mHullPoints += mPhysics.mHull[i].size();  	}  	mCenterOfHullCenters *= 1.f / mHullPoints; @@ -1944,12 +1949,15 @@ bool LLModel::loadModel(std::istream& is)  		std::ios::pos_type cur_pos = is.tellg();
  		loadSkinInfo(header, is);
  		is.seekg(cur_pos);
 +	}
 +
 +	if (lod == LLModel::LOD_PHYSICS)
 +	{
 +		std::ios::pos_type cur_pos = is.tellg();
  		loadDecomposition(header, is);
  		is.seekg(cur_pos);
  	}
 -	
 -
  	is.seekg(header[nm[lod]]["offset"].asInteger(), std::ios_base::cur);
  	if (unpackVolumeFaces(is, header[nm[lod]]["size"].asInteger()))
 @@ -2019,6 +2027,22 @@ bool LLModel::loadSkinInfo(LLSD& header, std::istream &is)  bool LLModel::loadDecomposition(LLSD& header, std::istream& is)  { +	S32 offset = header["decomposition"]["offset"].asInteger(); +	S32 size = header["decomposition"]["size"].asInteger(); + +	if (offset >= 0 && size > 0) +	{ +		is.seekg(offset, std::ios_base::cur); + +		LLSD data; + +		if (unzip_llsd(data, is, size)) +		{ +			mPhysics.fromLLSD(data); +			updateHullCenters(); +		} +	} +  	return true;  } @@ -2133,3 +2157,104 @@ LLSD LLMeshSkinInfo::asLLSD(bool include_joints) const  	return ret;  } +LLModel::Decomposition::Decomposition(LLSD& data) +{ +	fromLLSD(data); +} + +void LLModel::Decomposition::fromLLSD(LLSD& decomp) +{ +	if (decomp.has("HullList")) +	{ +		// updated for const-correctness. gcc is picky about this type of thing - Nyx +		const LLSD::Binary& hulls = decomp["HullList"].asBinary(); +		const LLSD::Binary& position = decomp["Position"].asBinary(); + +		U16* p = (U16*) &position[0]; + +		mHull.resize(hulls.size()); + +		LLVector3 min; +		LLVector3 max; +		LLVector3 range; + +		min.setValue(decomp["Min"]); +		max.setValue(decomp["Max"]); +		range = max-min; + +		for (U32 i = 0; i < hulls.size(); ++i) +		{ +			U16 count = (hulls[i] == 0) ? 256 : hulls[i]; +			 +			for (U32 j = 0; j < count; ++j) +			{ +				mHull[i].push_back(LLVector3( +					(F32) p[0]/65535.f*range.mV[0]+min.mV[0], +					(F32) p[1]/65535.f*range.mV[1]+min.mV[1], +					(F32) p[2]/65535.f*range.mV[2]+min.mV[2])); +				p += 3; +			}		  + +		} +	} + +	if (decomp.has("Hull")) +	{ +		const LLSD::Binary& position = decomp["Hull"].asBinary(); + +		U16* p = (U16*) &position[0]; + +		LLVector3 min; +		LLVector3 max; +		LLVector3 range; + +		min.setValue(decomp["Min"]); +		max.setValue(decomp["Max"]); +		range = max-min; + +		U16 count = position.size()/6; +		 +		for (U32 j = 0; j < count; ++j) +		{ +			mBaseHull.push_back(LLVector3( +				(F32) p[0]/65535.f*range.mV[0]+min.mV[0], +				(F32) p[1]/65535.f*range.mV[1]+min.mV[1], +				(F32) p[2]/65535.f*range.mV[2]+min.mV[2])); +			p += 3; +		}		  +	} +	else +	{ +		//empty base hull mesh to indicate decomposition has been loaded +		//but contains no base hull +		mBaseHullMesh.clear();; +	} + +} + +void LLModel::Decomposition::merge(const LLModel::Decomposition* rhs) +{ +	if (!rhs) +	{ +		return; +	} + +	if (mMeshID != rhs->mMeshID) +	{ +		llerrs << "Attempted to merge with decomposition of some other mesh." << llendl; +	} + +	if (mBaseHull.empty()) +	{ //take base hull and decomposition from rhs +		mHull = rhs->mHull; +		mBaseHull = rhs->mBaseHull; +		mMesh = rhs->mMesh; +		mBaseHullMesh = rhs->mBaseHullMesh; +	} + +	if (mPhysicsShapeMesh.empty()) +	{ //take physics shape mesh from rhs +		mPhysicsShapeMesh = rhs->mPhysicsShapeMesh; +	} +} + diff --git a/indra/llprimitive/llmodel.h b/indra/llprimitive/llmodel.h index 81be9d1835..e9450d2967 100755 --- a/indra/llprimitive/llmodel.h +++ b/indra/llprimitive/llmodel.h @@ -27,6 +27,7 @@  #ifndef LL_LLMODEL_H  #define LL_LLMODEL_H +#include "llpointer.h"  #include "llvolume.h"  #include "v4math.h"  #include "m4math.h" @@ -54,7 +55,6 @@ public:  	float mPelvisOffset;  }; -  class LLModel : public LLVolume  {  public: @@ -208,9 +208,10 @@ public:  	float	mPelvisOffset;  	// convex hull decomposition  	S32 mDecompID; -	convex_hull_decomposition mConvexHullDecomp; +	  	void setConvexHullDecomposition(  		const convex_hull_decomposition& decomp); +	void updateHullCenters();  	LLVector3 mCenterOfHullCenters;  	std::vector<LLVector3> mHullCenter; @@ -219,6 +220,44 @@ public:  	//ID for storing this model in a .slm file  	S32 mLocalID; +	class PhysicsMesh +	{ +	public: +		std::vector<LLVector3> mPositions; +		std::vector<LLVector3> mNormals; + +		void clear() +		{ +			mPositions.clear(); +			mNormals.clear(); +		} + +		bool empty() const +		{ +			return mPositions.empty(); +		} +	}; + +	class Decomposition +	{ +	public: +		Decomposition() { } +		Decomposition(LLSD& data); +		void fromLLSD(LLSD& data); +		 +		void merge(const Decomposition* rhs); + +		LLUUID mMeshID; +		LLModel::convex_hull_decomposition mHull; +		LLModel::hull mBaseHull; + +		std::vector<LLModel::PhysicsMesh> mMesh; +		LLModel::PhysicsMesh mBaseHullMesh; +		LLModel::PhysicsMesh mPhysicsShapeMesh; +	}; + +	Decomposition mPhysics; +  protected:  	void addVolumeFacesFromDomMesh(domMesh* mesh);  	virtual BOOL createVolumeFacesFromDomMesh(domMesh *mesh); diff --git a/indra/llrender/llvertexbuffer.cpp b/indra/llrender/llvertexbuffer.cpp index 0d3f5b81bc..73efbfc999 100644 --- a/indra/llrender/llvertexbuffer.cpp +++ b/indra/llrender/llvertexbuffer.cpp @@ -236,6 +236,22 @@ void LLVertexBuffer::setupClientArrays(U32 data_mask)  	}  } +//static +void LLVertexBuffer::drawArrays(U32 mode, const std::vector<LLVector3>& pos, const std::vector<LLVector3>& norm) +{ +	U32 count = pos.size(); +	llassert(norm.size() >= pos.size()); + +	unbind(); +	 +	setupClientArrays(MAP_VERTEX | MAP_NORMAL); + +	glVertexPointer(3, GL_FLOAT, 0, pos[0].mV); +	glNormalPointer(GL_FLOAT, 0, norm[0].mV); + +	glDrawArrays(sGLMode[mode], 0, count); +} +  void LLVertexBuffer::validateRange(U32 start, U32 end, U32 count, U32 indices_offset) const  {  	if (start >= (U32) mRequestedNumVerts || diff --git a/indra/llrender/llvertexbuffer.h b/indra/llrender/llvertexbuffer.h index 2bbc17fb12..6c0895512e 100644 --- a/indra/llrender/llvertexbuffer.h +++ b/indra/llrender/llvertexbuffer.h @@ -97,6 +97,8 @@ public:  	static void initClass(bool use_vbo, bool no_vbo_mapping);  	static void cleanupClass();  	static void setupClientArrays(U32 data_mask); +	static void drawArrays(U32 mode, const std::vector<LLVector3>& pos, const std::vector<LLVector3>& norm); +   	static void clientCopy(F64 max_time = 0.005); //copy data from client to GL  	static void unbind(); //unbind any bound vertex buffer diff --git a/indra/newview/llfloatermodelpreview.cpp b/indra/newview/llfloatermodelpreview.cpp index d8088e2f51..541511e448 100755 --- a/indra/newview/llfloatermodelpreview.cpp +++ b/indra/newview/llfloatermodelpreview.cpp @@ -2520,8 +2520,8 @@ U32 LLModelPreview::calcResourceCost()  			LLModel::convex_hull_decomposition& decomp =
  			instance.mLOD[LLModel::LOD_PHYSICS] ?
 -			instance.mLOD[LLModel::LOD_PHYSICS]->mConvexHullDecomp :
 -			instance.mModel->mConvexHullDecomp;
 +			instance.mLOD[LLModel::LOD_PHYSICS]->mPhysics.mHull :
 +			instance.mModel->mPhysics.mHull;
  			LLSD ret = LLModel::writeModel(
  										   "",
 @@ -2739,8 +2739,8 @@ void LLModelPreview::saveUploadData(const std::string& filename, bool save_skinw  			LLModel::convex_hull_decomposition& decomp =
  				instance.mLOD[LLModel::LOD_PHYSICS].notNull() ? 
 -				instance.mLOD[LLModel::LOD_PHYSICS]->mConvexHullDecomp : 
 -				instance.mModel->mConvexHullDecomp;
 +				instance.mLOD[LLModel::LOD_PHYSICS]->mPhysics.mHull : 
 +				instance.mModel->mPhysics.mHull;
  			LLModel::writeModel(str, 
  				instance.mLOD[LLModel::LOD_PHYSICS], 
 @@ -2993,14 +2993,8 @@ void LLModelPreview::loadModelCallback(S32 lod)  		mScene[lod] = mModelLoader->mScene;
  		mVertexBuffer[lod].clear();
 -		if (lod == LLModel::LOD_PHYSICS)
 -		{
 -			mPhysicsMesh.clear();
 -		}
 -
  		setPreviewLOD(lod);
 -
  		if (lod == LLModel::LOD_HIGH)
  		{ //save a copy of the highest LOD for automatic LOD manipulation
  			if (mBaseModel.empty())
 @@ -3123,11 +3117,6 @@ void LLModelPreview::genLODs(S32 which_lod, U32 decimation, bool enforce_tri_lim  		return;
  	}
 -	if (which_lod == LLModel::LOD_PHYSICS)
 -	{ //clear physics mesh map
 -		mPhysicsMesh.clear();
 -	}
 -
  	LLVertexBuffer::unbind();
  	stop_gloderror();
 @@ -3676,7 +3665,7 @@ void LLModelPreview::updateStatusMessages()  		LLModel* model = mModel[LLModel::LOD_PHYSICS][i];
  		S32 cur_submeshes = model->getNumVolumeFaces();
 -		LLModel::convex_hull_decomposition& decomp = model->mConvexHullDecomp;
 +		LLModel::convex_hull_decomposition& decomp = model->mPhysics.mHull;
  		if (!decomp.empty())
  		{
 @@ -4313,12 +4302,17 @@ BOOL LLModelPreview::render()  					{
  						LLMutexLock(decomp->mMutex);
 -						std::map<LLPointer<LLModel>, std::vector<LLPointer<LLVertexBuffer> > >::iterator iter =
 -							mPhysicsMesh.find(model);
 -						if (iter != mPhysicsMesh.end())
 +						LLModel::Decomposition& physics = model->mPhysics;
 +
 +						if (physics.mMesh.empty())
 +						{ //build vertex buffer for physics mesh
 +							gMeshRepo.buildPhysicsMesh(physics);
 +						}
 +							
 +						if (!physics.mMesh.empty())
  						{ //render hull instead of mesh
  							render_mesh = false;
 -							for (U32 i = 0; i < iter->second.size(); ++i)
 +							for (U32 i = 0; i < physics.mMesh.size(); ++i)
  							{
  								if (explode > 0.f)
  								{
 @@ -4337,15 +4331,9 @@ BOOL LLModelPreview::render()  									hull_colors.push_back(LLColor4U(rand()%128+127, rand()%128+127, rand()%128+127, 255));
  								}
 -								LLVertexBuffer* buff = iter->second[i];
 -								if (buff)
 -								{
 -									buff->setBuffer(LLVertexBuffer::MAP_VERTEX | LLVertexBuffer::MAP_NORMAL);
 -
 -									glColor4ubv(hull_colors[i].mV);
 -									buff->drawArrays(LLRender::TRIANGLES, 0, buff->getNumVerts());
 -								}
 -
 +								glColor4ubv(hull_colors[i].mV);
 +								LLVertexBuffer::drawArrays(LLRender::TRIANGLES, physics.mMesh[i].mPositions, physics.mMesh[i].mNormals);
 +								
  								if (explode > 0.f)
  								{
  									gGL.popMatrix();
 @@ -4724,7 +4712,6 @@ void LLFloaterModelPreview::DecompRequest::completed()  			{
  				if (sInstance->mModelPreview)
  				{
 -					sInstance->mModelPreview->mPhysicsMesh[mModel] = mHullMesh;
  					sInstance->mModelPreview->mDirty = true;
  					LLFloaterModelPreview::sInstance->mModelPreview->refresh();
  				}
 diff --git a/indra/newview/llfloatermodelpreview.h b/indra/newview/llfloatermodelpreview.h index 68fa0fa4c1..6542ed4fbe 100644 --- a/indra/newview/llfloatermodelpreview.h +++ b/indra/newview/llfloatermodelpreview.h @@ -358,8 +358,7 @@ public:  	U32 mGroup;  	std::map<LLPointer<LLModel>, U32> mObject;  	U32 mMaxTriangleLimit; -	std::map<LLPointer<LLModel>, std::vector<LLPointer<LLVertexBuffer> > > mPhysicsMesh; - +	  	LLMeshUploadThread::instance_list mUploadData;  	std::set<LLViewerFetchedTexture* > mTextureSet; diff --git a/indra/newview/llfloatermodelwizard.cpp b/indra/newview/llfloatermodelwizard.cpp index ad6e4ebe9c..8428ddb255 100644 --- a/indra/newview/llfloatermodelwizard.cpp +++ b/indra/newview/llfloatermodelwizard.cpp @@ -485,7 +485,6 @@ void LLFloaterModelWizard::DecompRequest::completed()  	{  		if (sInstance->mModelPreview)  		{ -			sInstance->mModelPreview->mPhysicsMesh[mModel] = mHullMesh;  			sInstance->mModelPreview->mDirty = true;  			LLFloaterModelWizard::sInstance->mModelPreview->refresh();  		} diff --git a/indra/newview/llmeshrepository.cpp b/indra/newview/llmeshrepository.cpp index f5fc0de0d3..752e4c8744 100755 --- a/indra/newview/llmeshrepository.cpp +++ b/indra/newview/llmeshrepository.cpp @@ -108,19 +108,13 @@ U32 get_volume_memory_size(const LLVolume* volume)  	return indices*2+vertices*11+sizeof(LLVolume)+sizeof(LLVolumeFace)*volume->getNumVolumeFaces();  } -LLVertexBuffer* get_vertex_buffer_from_mesh(LLCDMeshData& mesh, F32 scale = 1.f) +void get_vertex_buffer_from_mesh(LLCDMeshData& mesh, LLModel::PhysicsMesh& res, F32 scale = 1.f)  { -	LLVertexBuffer* buff = new LLVertexBuffer(LLVertexBuffer::MAP_VERTEX | LLVertexBuffer::MAP_NORMAL, 0); -	buff->allocateBuffer(mesh.mNumTriangles*3, 0, true); - -	LLStrider<LLVector3> pos; -	LLStrider<LLVector3> norm; +	res.mPositions.clear(); +	res.mNormals.clear(); -	buff->getVertexStrider(pos); -	buff->getNormalStrider(norm); -  	const F32* v = mesh.mVertexBase; -	 +  	if (mesh.mIndexType == LLCDMeshData::INT_16)  	{  		U16* idx = (U16*) mesh.mIndexBase; @@ -139,13 +133,13 @@ LLVertexBuffer* get_vertex_buffer_from_mesh(LLCDMeshData& mesh, F32 scale = 1.f)  			LLVector3 n = (v1-v0)%(v2-v0);  			n.normalize(); -			*pos++ = v0*scale; -			*pos++ = v1*scale; -			*pos++ = v2*scale; +			res.mPositions.push_back(v0*scale); +			res.mPositions.push_back(v1*scale); +			res.mPositions.push_back(v2*scale); -			*norm++ = n; -			*norm++ = n; -			*norm++ = n;			 +			res.mNormals.push_back(n); +			res.mNormals.push_back(n); +			res.mNormals.push_back(n);			  		}  	}  	else @@ -166,17 +160,15 @@ LLVertexBuffer* get_vertex_buffer_from_mesh(LLCDMeshData& mesh, F32 scale = 1.f)  			LLVector3 n = (v1-v0)%(v2-v0);  			n.normalize(); -			*(pos++) = v0*scale; -			*(pos++) = v1*scale; -			*(pos++) = v2*scale; +			res.mPositions.push_back(v0*scale); +			res.mPositions.push_back(v1*scale); +			res.mPositions.push_back(v2*scale); -			*(norm++) = n; -			*(norm++) = n; -			*(norm++) = n;			 +			res.mNormals.push_back(n); +			res.mNormals.push_back(n); +			res.mNormals.push_back(n);			  		}  	} - -	return buff;  }  S32 LLMeshRepoThread::sActiveHeaderRequests = 0; @@ -1139,119 +1131,8 @@ bool LLMeshRepoThread::decompositionReceived(const LLUUID& mesh_id, U8* data, S3  	}  	{ -		LLMeshDecomposition* d = new LLMeshDecomposition(); +		LLModel::Decomposition* d = new LLModel::Decomposition(decomp);  		d->mMeshID = mesh_id; - -		if (decomp.has("HullList")) -		{ -			// updated for const-correctness. gcc is picky about this type of thing - Nyx -			const LLSD::Binary& hulls = decomp["HullList"].asBinary(); -			const LLSD::Binary& position = decomp["Position"].asBinary(); - -			U16* p = (U16*) &position[0]; - -			d->mHull.resize(hulls.size()); - -			LLVector3 min; -			LLVector3 max; -			LLVector3 range; - -			min.setValue(decomp["Min"]); -			max.setValue(decomp["Max"]); -			range = max-min; - -			for (U32 i = 0; i < hulls.size(); ++i) -			{ -				U16 count = (hulls[i] == 0) ? 256 : hulls[i]; -				 -				for (U32 j = 0; j < count; ++j) -				{ -					d->mHull[i].push_back(LLVector3( -						(F32) p[0]/65535.f*range.mV[0]+min.mV[0], -						(F32) p[1]/65535.f*range.mV[1]+min.mV[1], -						(F32) p[2]/65535.f*range.mV[2]+min.mV[2])); -					p += 3; -				}		  - -			} -				 -			//get mesh for decomposition -			for (U32 i = 0; i < d->mHull.size(); ++i) -			{ -				LLCDHull hull; -				hull.mNumVertices = d->mHull[i].size(); -				hull.mVertexBase = d->mHull[i][0].mV; -				hull.mVertexStrideBytes = 12; - -				LLCDMeshData mesh; -				LLCDResult res = LLCD_OK; -				if (LLConvexDecomposition::getInstance() != NULL) -				{ -					res = LLConvexDecomposition::getInstance()->getMeshFromHull(&hull, &mesh); -				} -				if (res != LLCD_OK) -				{ -					llwarns << "could not get mesh from hull from convex decomposition lib." << llendl; -					return false; -				} - - -				d->mMesh.push_back(get_vertex_buffer_from_mesh(mesh)); -			}	 -		} - -		if (decomp.has("Hull")) -		{ -			const LLSD::Binary& position = decomp["Hull"].asBinary(); - -			U16* p = (U16*) &position[0]; - -			LLVector3 min; -			LLVector3 max; -			LLVector3 range; - -			min.setValue(decomp["Min"]); -			max.setValue(decomp["Max"]); -			range = max-min; - -			U16 count = position.size()/6; -			 -			for (U32 j = 0; j < count; ++j) -			{ -				d->mBaseHull.push_back(LLVector3( -					(F32) p[0]/65535.f*range.mV[0]+min.mV[0], -					(F32) p[1]/65535.f*range.mV[1]+min.mV[1], -					(F32) p[2]/65535.f*range.mV[2]+min.mV[2])); -				p += 3; -			}		  -				 -			//get mesh for decomposition -			LLCDHull hull; -			hull.mNumVertices = d->mBaseHull.size(); -			hull.mVertexBase = d->mBaseHull[0].mV; -			hull.mVertexStrideBytes = 12; - -			LLCDMeshData mesh; -			LLCDResult res = LLCD_OK; -			if (LLConvexDecomposition::getInstance() != NULL) -			{ -				res = LLConvexDecomposition::getInstance()->getMeshFromHull(&hull, &mesh); -			} -			if (res != LLCD_OK) -			{ -				llwarns << "could not get mesh from hull from convex decomposition lib." << llendl; -				return false; -			} - -			d->mBaseHullMesh = get_vertex_buffer_from_mesh(mesh); -		} -		else -		{ -			//empty vertex buffer to indicate decomposition has been fetched -			//but contains no base hull -			d->mBaseHullMesh = new LLVertexBuffer(0, 0); -		} -  		mDecompositionQ.push(d);  	} @@ -1262,12 +1143,12 @@ bool LLMeshRepoThread::physicsShapeReceived(const LLUUID& mesh_id, U8* data, S32  {  	LLSD physics_shape; -	LLMeshDecomposition* d = new LLMeshDecomposition(); +	LLModel::Decomposition* d = new LLModel::Decomposition();  	d->mMeshID = mesh_id;  	if (data == NULL)  	{ //no data, no physics shape exists -		d->mPhysicsShapeMesh = new LLVertexBuffer(0,0); +		d->mPhysicsShapeMesh.clear();  	}  	else  	{ @@ -1291,33 +1172,22 @@ bool LLMeshRepoThread::physicsShapeReceived(const LLUUID& mesh_id, U8* data, S32  				index_count += face.mNumIndices;  			} -			d->mPhysicsShapeMesh = new LLVertexBuffer(LLVertexBuffer::MAP_VERTEX, 0); - -			d->mPhysicsShapeMesh->allocateBuffer(vertex_count, index_count, true); +			d->mPhysicsShapeMesh.clear(); -			LLStrider<LLVector3> pos; -			LLStrider<U16> idx; +			std::vector<LLVector3>& pos = d->mPhysicsShapeMesh.mPositions; +			std::vector<LLVector3>& norm = d->mPhysicsShapeMesh.mNormals; -			d->mPhysicsShapeMesh->getVertexStrider(pos); -			d->mPhysicsShapeMesh->getIndexStrider(idx); - -			S32 idx_offset = 0;  			for (S32 i = 0; i < volume->getNumVolumeFaces(); ++i)  			{  				const LLVolumeFace& face = volume->getVolumeFace(i); -				if (idx_offset + face.mNumIndices > 65535) -				{ //avoid 16-bit index overflow -					continue; -				} - -				LLVector4a::memcpyNonAliased16(pos[idx_offset].mV, face.mPositions[0].getF32ptr(), face.mNumVertices*sizeof(LLVector4a));  				for (S32 i = 0; i < face.mNumIndices; ++i)  				{ -					*idx++ = face.mIndices[i] + idx_offset; -				} +					U16 idx = face.mIndices[i]; -				idx_offset += face.mNumVertices; +					pos.push_back(LLVector3(face.mPositions[idx].getF32ptr())); +					norm.push_back(LLVector3(face.mNormals[idx].getF32ptr()));				 +				}			  			}  		}  	} @@ -2428,33 +2298,7 @@ void LLMeshRepository::notifySkinInfoReceived(LLMeshSkinInfo& info)  	mLoadingSkins.erase(info.mMeshID);  } -void LLMeshDecomposition::merge(const LLMeshDecomposition* rhs) -{ -	if (!rhs) -	{ -		return; -	} - -	if (mMeshID != rhs->mMeshID) -	{ -		llerrs << "Attempted to merge with decomposition of some other mesh." << llendl; -	} - -	if (mBaseHull.empty()) -	{ //take base hull and decomposition from rhs -		mHull = rhs->mHull; -		mBaseHull = rhs->mBaseHull; -		mMesh = rhs->mMesh; -		mBaseHullMesh = rhs->mBaseHullMesh; -	} - -	if (mPhysicsShapeMesh.isNull()) -	{ //take physics shape mesh from rhs -		mPhysicsShapeMesh = rhs->mPhysicsShapeMesh; -	} -} - -void LLMeshRepository::notifyDecompositionReceived(LLMeshDecomposition* decomp) +void LLMeshRepository::notifyDecompositionReceived(LLModel::Decomposition* decomp)  {  	decomposition_map::iterator iter = mDecompositionMap.find(decomp->mMeshID);  	if (iter == mDecompositionMap.end()) @@ -2596,7 +2440,7 @@ void LLMeshRepository::fetchPhysicsShape(const LLUUID& mesh_id)  {  	if (mesh_id.notNull())  	{ -		LLMeshDecomposition* decomp = NULL; +		LLModel::Decomposition* decomp = NULL;  		decomposition_map::iterator iter = mDecompositionMap.find(mesh_id);  		if (iter != mDecompositionMap.end())  		{ @@ -2604,7 +2448,7 @@ void LLMeshRepository::fetchPhysicsShape(const LLUUID& mesh_id)  		}  		//decomposition block hasn't been fetched yet -		if (!decomp || decomp->mPhysicsShapeMesh.isNull()) +		if (!decomp || decomp->mPhysicsShapeMesh.empty())  		{  			LLMutexLock lock(mMeshMutex);  			//add volume to list of loading meshes @@ -2619,9 +2463,9 @@ void LLMeshRepository::fetchPhysicsShape(const LLUUID& mesh_id)  } -const LLMeshDecomposition* LLMeshRepository::getDecomposition(const LLUUID& mesh_id) +LLModel::Decomposition* LLMeshRepository::getDecomposition(const LLUUID& mesh_id)  { -	LLMeshDecomposition* ret = NULL; +	LLModel::Decomposition* ret = NULL;  	if (mesh_id.notNull())  	{ @@ -2632,7 +2476,7 @@ const LLMeshDecomposition* LLMeshRepository::getDecomposition(const LLUUID& mesh  		}  		//decomposition block hasn't been fetched yet -		if (!ret || ret->mBaseHullMesh.isNull()) +		if (!ret || ret->mBaseHullMesh.empty())  		{  			LLMutexLock lock(mMeshMutex);  			//add volume to list of loading meshes @@ -2735,8 +2579,8 @@ void LLMeshUploadThread::sendCostRequest(LLMeshUploadData& data)  	LLModel::convex_hull_decomposition& decomp =  		data.mModel[LLModel::LOD_PHYSICS].notNull() ?  -		data.mModel[LLModel::LOD_PHYSICS]->mConvexHullDecomp :  -		data.mBaseModel->mConvexHullDecomp; +		data.mModel[LLModel::LOD_PHYSICS]->mPhysics.mHull :  +		data.mBaseModel->mPhysics.mHull;  	LLModel::hull dummy_hull; @@ -2836,8 +2680,8 @@ void LLMeshUploadThread::doUploadModel(LLMeshUploadData& data)  		LLModel::convex_hull_decomposition& decomp =  			data.mModel[LLModel::LOD_PHYSICS].notNull() ?  -			data.mModel[LLModel::LOD_PHYSICS]->mConvexHullDecomp :  -			data.mBaseModel->mConvexHullDecomp; +			data.mModel[LLModel::LOD_PHYSICS]->mPhysics.mHull :  +			data.mBaseModel->mPhysics.mHull;  		LLModel::writeModel(  			ostr,   @@ -3355,7 +3199,7 @@ void LLPhysicsDecomp::doDecomposition()  			// if LLConvexDecomposition is a stub, num_hulls should have been set to 0 above, and we should not reach this code  			LLConvexDecomposition::getInstance()->getMeshFromStage(stage, i, &mesh); -			mCurRequest->mHullMesh[i] = get_vertex_buffer_from_mesh(mesh); +			get_vertex_buffer_from_mesh(mesh, mCurRequest->mHullMesh[i]);  			mMutex->lock();  			mCurRequest->mHull[i] = p; @@ -3628,3 +3472,46 @@ LLSD LLImportMaterial::asLLSD()  	return ret;  } + +void LLMeshRepository::buildPhysicsMesh(LLModel::Decomposition& decomp) +{ +	decomp.mMesh.resize(decomp.mHull.size());
 +
 +	for (U32 i = 0; i < decomp.mHull.size(); ++i)
 +	{
 +		LLCDHull hull; +		hull.mNumVertices = decomp.mHull[i].size(); +		hull.mVertexBase = decomp.mHull[i][0].mV; +		hull.mVertexStrideBytes = 12; + +		LLCDMeshData mesh; +		LLCDResult res = LLCD_OK; +		if (LLConvexDecomposition::getInstance() != NULL) +		{ +			res = LLConvexDecomposition::getInstance()->getMeshFromHull(&hull, &mesh); +		} +		if (res == LLCD_OK) +		{ +			get_vertex_buffer_from_mesh(mesh, decomp.mMesh[i]);
 +		}
 +	} + +	if (!decomp.mBaseHull.empty() && decomp.mBaseHullMesh.empty()) +	{ //get mesh for base hull +		LLCDHull hull; +		hull.mNumVertices = decomp.mBaseHull.size(); +		hull.mVertexBase = decomp.mBaseHull[0].mV; +		hull.mVertexStrideBytes = 12; + +		LLCDMeshData mesh; +		LLCDResult res = LLCD_OK; +		if (LLConvexDecomposition::getInstance() != NULL) +		{ +			res = LLConvexDecomposition::getInstance()->getMeshFromHull(&hull, &mesh); +		} +		if (res == LLCD_OK) +		{ +			get_vertex_buffer_from_mesh(mesh, decomp.mBaseHullMesh); +		} +	} +} diff --git a/indra/newview/llmeshrepository.h b/indra/newview/llmeshrepository.h index 5960fe2949..31c2049c32 100644 --- a/indra/newview/llmeshrepository.h +++ b/indra/newview/llmeshrepository.h @@ -132,22 +132,6 @@ public:  	LLSD asLLSD();  }; -class LLMeshDecomposition -{ -public: -	LLMeshDecomposition() { } - -	void merge(const LLMeshDecomposition* rhs); - -	LLUUID mMeshID; -	LLModel::convex_hull_decomposition mHull; -	LLModel::hull mBaseHull; - -	std::vector<LLPointer<LLVertexBuffer> > mMesh; -	LLPointer<LLVertexBuffer> mBaseHullMesh; -	LLPointer<LLVertexBuffer> mPhysicsShapeMesh; -}; -  class LLPhysicsDecomp : public LLThread  {  public: @@ -166,7 +150,7 @@ public:  		//output state  		std::string mStatusMessage; -		std::vector<LLPointer<LLVertexBuffer> > mHullMesh; +		std::vector<LLModel::PhysicsMesh> mHullMesh;  		LLModel::convex_hull_decomposition mHull;  		//status message callback, called from decomposition thread @@ -301,7 +285,7 @@ public:  	std::set<LLUUID> mPhysicsShapeRequests;  	//queue of completed Decomposition info requests -	std::queue<LLMeshDecomposition*> mDecompositionQ; +	std::queue<LLModel::Decomposition*> mDecompositionQ;  	//queue of requested headers  	std::queue<HeaderRequest> mHeaderReqQ; @@ -465,17 +449,19 @@ public:  	void notifyMeshLoaded(const LLVolumeParams& mesh_params, LLVolume* volume);  	void notifyMeshUnavailable(const LLVolumeParams& mesh_params, S32 lod);  	void notifySkinInfoReceived(LLMeshSkinInfo& info); -	void notifyDecompositionReceived(LLMeshDecomposition* info); +	void notifyDecompositionReceived(LLModel::Decomposition* info);  	S32 getActualMeshLOD(const LLVolumeParams& mesh_params, S32 lod);  	U32 calcResourceCost(LLSD& header);  	U32 getResourceCost(const LLUUID& mesh_params);  	const LLMeshSkinInfo* getSkinInfo(const LLUUID& mesh_id); -	const LLMeshDecomposition* getDecomposition(const LLUUID& mesh_id); +	LLModel::Decomposition* getDecomposition(const LLUUID& mesh_id);  	void fetchPhysicsShape(const LLUUID& mesh_id);  	bool hasPhysicsShape(const LLUUID& mesh_id);  	void buildHull(const LLVolumeParams& params, S32 detail); +	void buildPhysicsMesh(LLModel::Decomposition& decomp); +  	const LLSD& getMeshHeader(const LLUUID& mesh_id);  	void uploadModel(std::vector<LLModelInstance>& data, LLVector3& scale, bool upload_textures, @@ -489,7 +475,7 @@ public:  	typedef std::map<LLUUID, LLMeshSkinInfo> skin_map;  	skin_map mSkinMap; -	typedef std::map<LLUUID, LLMeshDecomposition*> decomposition_map; +	typedef std::map<LLUUID, LLModel::Decomposition*> decomposition_map;  	decomposition_map mDecompositionMap;  	LLMutex*					mMeshMutex; diff --git a/indra/newview/llspatialpartition.cpp b/indra/newview/llspatialpartition.cpp index 5e7af6bbb3..65f7d299bc 100644 --- a/indra/newview/llspatialpartition.cpp +++ b/indra/newview/llspatialpartition.cpp @@ -2961,31 +2961,21 @@ S32 get_physics_detail(const LLVolumeParams& volume_params, const LLVector3& sca  void renderMeshBaseHull(LLVOVolume* volume, U32 data_mask, LLColor4& color, LLColor4& line_color)  {  	LLUUID mesh_id = volume->getVolume()->getParams().getSculptID(); -	const LLMeshDecomposition* decomp = gMeshRepo.getDecomposition(mesh_id); +	LLModel::Decomposition* decomp = gMeshRepo.getDecomposition(mesh_id);  	const LLVector3 center(0,0,0);  	const LLVector3 size(0.25f,0.25f,0.25f);  	if (decomp)  	{		 -		LLVertexBuffer* buff = decomp->mBaseHullMesh; - -		if (buff && buff->getNumVerts() > 0) +		if (!decomp->mBaseHullMesh.empty())  		{ -			buff->setBuffer(data_mask); - -		/*	glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); -			glColor4fv(line_color.mV); -			buff->drawArrays(LLRender::TRIANGLES, 0, buff->getNumVerts()); -			glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);*/ - -			{ -				glColor4fv(color.mV); -				buff->drawArrays(LLRender::TRIANGLES, 0, buff->getNumVerts()); -			} +			glColor4fv(color.mV); +			LLVertexBuffer::drawArrays(LLRender::TRIANGLES, decomp->mBaseHullMesh.mPositions, decomp->mBaseHullMesh.mNormals);  		}  		else  		{ +			gMeshRepo.buildPhysicsMesh(*decomp);  			gGL.color3f(0,1,1);  			drawBoxOutline(center, size);  		} @@ -2998,19 +2988,16 @@ void renderMeshBaseHull(LLVOVolume* volume, U32 data_mask, LLColor4& color, LLCo  	}  } -void render_hull(LLVertexBuffer* buff, U32 data_mask, const LLColor4& color, const LLColor4& line_color) +void render_hull(LLModel::PhysicsMesh& mesh, const LLColor4& color, const LLColor4& line_color)  { -	buff->setBuffer(data_mask); -  	glColor4fv(color.mV); -	buff->drawArrays(LLRender::TRIANGLES, 0, buff->getNumVerts()); - +	LLVertexBuffer::drawArrays(LLRender::TRIANGLES, mesh.mPositions, mesh.mNormals);  	LLGLEnable offset(GL_POLYGON_OFFSET_LINE);  	glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);  	glPolygonOffset(3.f, 3.f);  	glLineWidth(3.f);  	glColor4fv(line_color.mV); -	buff->drawArrays(LLRender::TRIANGLES, 0, buff->getNumVerts()); +	LLVertexBuffer::drawArrays(LLRender::TRIANGLES, mesh.mPositions, mesh.mNormals);  	glLineWidth(1.f);  	glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);  } @@ -3075,7 +3062,7 @@ void renderPhysicsShape(LLDrawable* drawable, LLVOVolume* volume)  	if (type == LLPhysicsShapeBuilderUtil::PhysicsShapeSpecification::USER_MESH)  	{  		LLUUID mesh_id = volume->getVolume()->getParams().getSculptID(); -		const LLMeshDecomposition* decomp = gMeshRepo.getDecomposition(mesh_id); +		LLModel::Decomposition* decomp = gMeshRepo.getDecomposition(mesh_id);  		if (decomp)  		{ //render a physics based mesh @@ -3084,27 +3071,33 @@ void renderPhysicsShape(LLDrawable* drawable, LLVOVolume* volume)  			if (!decomp->mHull.empty())  			{ //decomposition exists, use that -				for (U32 i = 0; i < decomp->mHull.size(); ++i) + +				if (decomp->mMesh.empty()) +				{ +					gMeshRepo.buildPhysicsMesh(*decomp); +				} + +				for (U32 i = 0; i < decomp->mMesh.size(); ++i)  				{		 -					render_hull(decomp->mMesh[i], data_mask, color, line_color); +					render_hull(decomp->mMesh[i], color, line_color);  				}  			} -			else if (decomp->mPhysicsShapeMesh.notNull() && decomp->mPhysicsShapeMesh->getNumVerts() > 0) +			else if (!decomp->mPhysicsShapeMesh.empty())  			{   				//decomp has physics mesh, render that mesh  				glColor4fv(color.mV); -				pushBufferVerts(decomp->mPhysicsShapeMesh, data_mask); -				 +				LLVertexBuffer::drawArrays(LLRender::TRIANGLES, decomp->mPhysicsShapeMesh.mPositions, decomp->mPhysicsShapeMesh.mNormals); +								  				glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);  				glColor4fv(line_color.mV); -				pushBufferVerts(decomp->mPhysicsShapeMesh, data_mask); +				LLVertexBuffer::drawArrays(LLRender::TRIANGLES, decomp->mPhysicsShapeMesh.mPositions, decomp->mPhysicsShapeMesh.mNormals);  				glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);  			}  			else  			{ //no mesh or decomposition, render base hull  				renderMeshBaseHull(volume, data_mask, color, line_color); -				if (decomp->mPhysicsShapeMesh.isNull()) +				if (decomp->mPhysicsShapeMesh.empty())  				{  					//attempt to fetch physics shape mesh if available  					gMeshRepo.fetchPhysicsShape(mesh_id); | 
