Predat0R
16-04-2010 18:43:00
Hi, why deformation does not work. I do an example from PhysX 2.8.3 – SampleCloth (Metal).
OgreMesh + BoxShape, but at blow on BoxShape OgreMesh is not deformation.
OgreMesh + BoxShape, but at blow on BoxShape OgreMesh is not deformation.
NxReal impulseThreshold = 50.0f;
NxReal penetrationDepth = 0.5f;
NxReal maxDeformationDistance = 0.5f;
NxActorDesc coreActorDesc;
NxBodyDesc coreBodyDesc;
coreActorDesc.density = 0.1f; // density in actor is used to compute mass
coreBodyDesc.mass = 0.0f; // if body mass is set to zero;
coreBodyDesc.linearDamping = 0.2f;
coreBodyDesc.angularDamping = 0.2f;
coreActorDesc.body = &coreBodyDesc;
coreActorDesc.shapes.pushBack(new NxBoxShapeDesc());
NxActor *coreActor = mScene->createActor(coreActorDesc);
for (NxU32 i = 0; i < coreActorDesc.shapes.size(); i++) delete coreActorDesc.shapes[i];
PhysicalCloth *objCloth = new PhysicalCloth(mSceneMgr, mScene, mPhysicsSDK, "Antena", "Antena.mesh");
objCloth->getCloth()->attachToCore(coreActor, impulseThreshold, penetrationDepth, maxDeformationDistance);
PhysicalCloth::PhysicalCloth(Ogre::SceneManager* mSceneMgr, NxScene* mScene, NxPhysicsSDK* pSDK, const Ogre::String& name, const Ogre::String& nameMesh)
{
bool added_shared = false;
size_t current_offset = 0;
size_t shared_offset = 0;
size_t next_offset = 0;
size_t index_offset = 0;
mVertexCount = 0;
mTriangleCount = 0;
mesh = Ogre::MeshManager::getSingletonPtr()->load(nameMesh, Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME).getPointer();
Ogre::String MatName = mesh->getSubMesh(0)->getMaterialName();
for ( unsigned short i = 0; i < mesh->getNumSubMeshes(); ++i)
{
Ogre::SubMesh* submesh = mesh->getSubMesh( i );
if(submesh->useSharedVertices) {
if( !added_shared ) {
mVertexCount += mesh->sharedVertexData->vertexCount;
added_shared = true;
}
}
else {
mVertexCount += submesh->vertexData->vertexCount;
}
mTriangleCount += submesh->indexData->indexCount;
}
mVertices = new NxVec3[mVertexCount];
mTriangles = new NxU32[mTriangleCount * 3];
mNormals = new Ogre::Vector3[mVertexCount];
mTextCoords = new Ogre::Vector2[mVertexCount];
added_shared = false;
bool use32bitindexes;
NxVec3 *p = mVertices;
Ogre::Vector3 *n = mNormals;
Ogre::Vector2 *t = mTextCoords;
for (unsigned short i=0;i<mesh->getNumSubMeshes();++i)
{
Ogre::SubMesh* submesh = mesh->getSubMesh(i);
Ogre::VertexData* vertex_data = submesh->useSharedVertices ? mesh->sharedVertexData : submesh->vertexData;
if((!submesh->useSharedVertices)||(submesh->useSharedVertices && !added_shared)) {
if(submesh->useSharedVertices) {
added_shared = true;
shared_offset = current_offset;
}
{
const Ogre::VertexElement* posElem = vertex_data->vertexDeclaration->findElementBySemantic(Ogre::VES_POSITION);
Ogre::HardwareVertexBufferSharedPtr vbuf = vertex_data->vertexBufferBinding->getBuffer(posElem->getSource());
unsigned char* vertex = static_cast<unsigned char*>(vbuf->lock(Ogre::HardwareBuffer::HBL_READ_ONLY));
Ogre::Real* pReal;
for( size_t j = 0; j < vertex_data->vertexCount; ++j, vertex += vbuf->getVertexSize()) {
posElem->baseVertexPointerToElement(vertex, &pReal);
p->set(pReal[0], pReal[1], pReal[2]);
*p++;
}
vbuf->unlock();
}
{
const Ogre::VertexElement* posElem = vertex_data->vertexDeclaration->findElementBySemantic(Ogre::VES_NORMAL);
Ogre::HardwareVertexBufferSharedPtr vbuf = vertex_data->vertexBufferBinding->getBuffer(posElem->getSource());
unsigned char* vertex = static_cast<unsigned char*>(vbuf->lock(Ogre::HardwareBuffer::HBL_READ_ONLY));
Ogre::Real* pReal;
for( size_t j = 0; j < vertex_data->vertexCount; ++j, vertex += vbuf->getVertexSize()) {
posElem->baseVertexPointerToElement(vertex, &pReal);
*n = Ogre::Vector3(pReal[0], pReal[1], pReal[2]);
*n++;
}
vbuf->unlock();
}
{
const Ogre::VertexElement* posElem = vertex_data->vertexDeclaration->findElementBySemantic(Ogre::VES_TEXTURE_COORDINATES);
Ogre::HardwareVertexBufferSharedPtr vbuf = vertex_data->vertexBufferBinding->getBuffer(posElem->getSource());
unsigned char* vertex = static_cast<unsigned char*>(vbuf->lock(Ogre::HardwareBuffer::HBL_READ_ONLY));
Ogre::Real* pReal;
for( size_t j = 0; j < vertex_data->vertexCount; ++j, vertex += vbuf->getVertexSize()) {
posElem->baseVertexPointerToElement(vertex, &pReal);
*t = Ogre::Vector2(pReal[0], pReal[1]);
*t++;
}
vbuf->unlock();
}
next_offset += vertex_data->vertexCount;
}
Ogre::IndexData* index_data = submesh->indexData;
size_t numTris = index_data->indexCount / 3;
Ogre::HardwareIndexBufferSharedPtr ibuf = index_data->indexBuffer;
use32bitindexes = (ibuf->getType() == Ogre::HardwareIndexBuffer::IT_32BIT);
if ( use32bitindexes ) {
unsigned int* pInt = static_cast<unsigned int*>(ibuf->lock(Ogre::HardwareBuffer::HBL_READ_ONLY));
size_t offset = (submesh->useSharedVertices)? shared_offset : current_offset;
for ( size_t k = 0; k < mTriangleCount; ++k) {
mTriangles[index_offset++] = pInt[k] + static_cast<unsigned int>(offset);
}
}
else {
unsigned short* pShort = reinterpret_cast<unsigned short*>(ibuf->lock(Ogre::HardwareBuffer::HBL_READ_ONLY));
size_t offset = (submesh->useSharedVertices)? shared_offset : current_offset;
for ( size_t k = 0; k < mTriangleCount; ++k) {
mTriangles[index_offset++] = static_cast<unsigned int>(pShort[k]) + static_cast<unsigned int>(offset);
}
}
ibuf->unlock();
current_offset = next_offset;
}
NxClothMeshDesc desc; NxClothDesc ClothDesc;
if (pSDK->getHWVersion() == NX_HW_VERSION_ATHENA_1_0)
ClothDesc.flags |= NX_CLF_HARDWARE;
ClothDesc.globalPose.t = NxVec3(0, 5.0, 0);
ClothDesc.thickness = 0.1f;
ClothDesc.friction = 0.5f;
ClothDesc.flags |= NX_CLF_BENDING;
NxVec3 myOffset(0.f);
desc.numVertices = mVertexCount;
desc.numTriangles = mTriangleCount / 3;
desc.pointStrideBytes = sizeof(NxVec3);
desc.triangleStrideBytes = 3*sizeof(NxU32);
desc.vertexMassStrideBytes = sizeof(NxReal);
desc.vertexFlagStrideBytes = sizeof(NxU32);
desc.points = (NxVec3*)malloc(sizeof(NxVec3)*desc.numVertices);
desc.triangles = (NxU32*)malloc(sizeof(NxU32)*desc.numTriangles*3);
desc.vertexMasses = 0;
desc.vertexFlags = 0;
desc.flags = NX_CLOTH_MESH_WELD_VERTICES;
desc.weldingDistance = 0.0001f;
NxU32 mMaxVertices = 3 * mVertexCount;
NxU32 mMaxIndices = 3 * mTriangleCount;
// copy positions and indices
NxVec3 *vSrc = (NxVec3*)mVertices;
NxVec3 *vDest = (NxVec3*)desc.points;
for (int i = 0; i < mVertexCount; i++, vDest++, vSrc++)
*vDest = (*vSrc) + myOffset;
memcpy((NxU32*)desc.triangles, mTriangles, sizeof(NxU32)*desc.numTriangles*3);
//desc.flags |= NX_CLOTH_MESH_TEARABLE;
//ClothDesc.flags |= NX_CLOTH_MESH_TEARABLE;
ClothDesc.flags |= NX_CLF_VISUALIZATION;
MemoryWriteBuffer wb;
assert(desc.isValid());
NxCookClothMesh(desc, wb);
MemoryReadBuffer rb(wb.data);
NxClothMesh *mClothMesh = pSDK->createClothMesh(rb);
free((NxVec3*)desc.points); free((NxU32*)desc.triangles);
free((NxReal*)desc.vertexMasses); free((NxU32*)desc.vertexFlags);
/*NxU32 maxVertices = mVertexCount * 3;
mReceiveBuffers.verticesPosBegin = (NxVec3*)malloc(sizeof(NxVec3)*maxVertices);
mReceiveBuffers.verticesNormalBegin= (NxVec3*)malloc(sizeof(NxVec3)*maxVertices);
mReceiveBuffers.verticesPosByteStride = sizeof(NxVec3);
mReceiveBuffers.verticesNormalByteStride = sizeof(NxVec3);
mReceiveBuffers.maxVertices = maxVertices;
mReceiveBuffers.numVerticesPtr = (NxU32*)malloc(sizeof(NxU32));
NxU32 maxIndices = 3 * mTriangleCount;
mReceiveBuffers.indicesBegin = (NxU32*)malloc(sizeof(NxU32)*maxIndices);
mReceiveBuffers.indicesByteStride = sizeof(NxU32);
mReceiveBuffers.maxIndices = maxIndices;
mReceiveBuffers.numIndicesPtr = (NxU32*)malloc(sizeof(NxU32));
int maxParentIndices = maxVertices;
mReceiveBuffers.parentIndicesBegin= (NxU32*)malloc(sizeof(NxU32)*maxParentIndices);
mReceiveBuffers.parentIndicesByteStride = sizeof(NxU32);
mReceiveBuffers.maxParentIndices = maxParentIndices;
mReceiveBuffers.numParentIndicesPtr = (NxU32*)malloc(sizeof(NxU32));
/*struct RenderBufferVertexElement
{
NxVec3 position;
NxVec3 normal;
float texCoord[2];
};
RenderBufferVertexElement* mVertexRenderBuffer;
NxU32* mIndexRenderBuffer;
mVertexRenderBuffer = (RenderBufferVertexElement*)malloc(sizeof(RenderBufferVertexElement) * mMaxVertices);
memset(mVertexRenderBuffer, 0, sizeof(RenderBufferVertexElement) * mMaxVertices);
mIndexRenderBuffer = (NxU32*)malloc(sizeof(NxU32) * mMaxIndices);
memset(mIndexRenderBuffer, 0, sizeof(NxU32) * mMaxIndices);
mReceiveBuffers.verticesPosBegin = &(mVertexRenderBuffer[0].position.x);
mReceiveBuffers.verticesNormalBegin = &(mVertexRenderBuffer[0].normal.x);
mReceiveBuffers.verticesPosByteStride = sizeof(RenderBufferVertexElement);
mReceiveBuffers.verticesNormalByteStride = sizeof(RenderBufferVertexElement);
mReceiveBuffers.maxVertices = mMaxVertices;
mReceiveBuffers.numVerticesPtr = (NxU32*)malloc(sizeof(NxU32));
mReceiveBuffers.indicesBegin = mIndexRenderBuffer;
mReceiveBuffers.indicesByteStride = sizeof(NxU32);
mReceiveBuffers.maxIndices = mMaxIndices;
mReceiveBuffers.numIndicesPtr = (NxU32*)malloc(sizeof(NxU32));
mReceiveBuffers.parentIndicesBegin = (NxU32*)malloc(sizeof(NxU32)*mMaxVertices);
mReceiveBuffers.parentIndicesByteStride = sizeof(NxU32);
mReceiveBuffers.maxParentIndices = mMaxVertices;
mReceiveBuffers.numParentIndicesPtr = (NxU32*)malloc(sizeof(NxU32));
*/
mReceiveBuffers.setToDefault();
NxVec3* verts_12byte = (NxVec3*)malloc(sizeof(Ogre::Vector3)*mVertexCount);
Ogre::Vector3*norms_12byte = (Ogre::Vector3*)malloc(sizeof(Ogre::Vector3)*mVertexCount);
mReceiveBuffers.verticesPosByteStride = sizeof(Ogre::Vector3);
mReceiveBuffers.verticesNormalByteStride = sizeof(Ogre::Vector3);
mReceiveBuffers.maxVertices = mVertexCount;
unsigned v;// вааще не нужно, но физикс хочет
mReceiveBuffers.numVerticesPtr = &v;
mReceiveBuffers.verticesPosBegin = verts_12byte;
mReceiveBuffers.verticesNormalBegin = norms_12byte;
ClothDesc.clothMesh = mClothMesh;
ClothDesc.meshData = mReceiveBuffers;
mCloth = mScene->createCloth(ClothDesc);
}