Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCampbell Barton <ideasman42@gmail.com>2009-07-26 05:32:37 +0400
committerCampbell Barton <ideasman42@gmail.com>2009-07-26 05:32:37 +0400
commitdd918da8de8b885d90420dc86351a4996dbd6ea6 (patch)
tree71941227e76d9fd815b451c07a4f6a610720c6db
parente9ca43521f99c6b9baf6d9278f85323086fcade2 (diff)
ReplaceMesh Actuator option to replace the physics mesh and display mesh + python api options.
When the mesh field is left blank and Physics option is enabled, it reinstances the physics mesh from the existing mesh. like calling gameOb.reinstancePhysicsMesh() from python.
-rw-r--r--source/blender/makesdna/DNA_actuator_types.h4
-rw-r--r--source/blender/src/buttons_logic.c5
-rw-r--r--source/gameengine/Converter/KX_ConvertActuators.cpp5
-rw-r--r--source/gameengine/GameLogic/SCA_IScene.h2
-rw-r--r--source/gameengine/Ketsji/KX_GameObject.cpp14
-rw-r--r--source/gameengine/Ketsji/KX_GameObject.h2
-rw-r--r--source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp13
-rw-r--r--source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h4
-rw-r--r--source/gameengine/Ketsji/KX_Scene.cpp220
-rw-r--r--source/gameengine/Ketsji/KX_Scene.h2
-rw-r--r--source/gameengine/PyDoc/GameTypes.py11
11 files changed, 162 insertions, 120 deletions
diff --git a/source/blender/makesdna/DNA_actuator_types.h b/source/blender/makesdna/DNA_actuator_types.h
index f713b4a8acc..c3f668ff622 100644
--- a/source/blender/makesdna/DNA_actuator_types.h
+++ b/source/blender/makesdna/DNA_actuator_types.h
@@ -405,6 +405,10 @@ typedef struct FreeCamera {
/* editObjectActuator->flag */
#define ACT_TRACK_3D 1
+/* editObjectActuator->flag for replace mesh actuator */
+#define ACT_EDOB_REPLACE_MESH_NOGFX 2 /* use for replace mesh actuator */
+#define ACT_EDOB_REPLACE_MESH_PHYS 4
+
/* SceneActuator->type */
#define ACT_SCENE_RESTART 0
#define ACT_SCENE_SET 1
diff --git a/source/blender/src/buttons_logic.c b/source/blender/src/buttons_logic.c
index f9e109b98e7..a57bcf5d7df 100644
--- a/source/blender/src/buttons_logic.c
+++ b/source/blender/src/buttons_logic.c
@@ -2177,7 +2177,10 @@ static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, sh
glRects(xco, yco-ysize, xco+width, yco);
uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1);
- uiDefIDPoinBut(block, test_meshpoin_but, ID_ME, 1, "ME:", xco+40, yco-44, (width-80), 19, &(eoa->me), "replace the existing mesh with this one");
+ uiDefIDPoinBut(block, test_meshpoin_but, ID_ME, 1, "ME:", xco+40, yco-44, (width-80)/2, 19, &(eoa->me), "replace the existing, when left blank 'Phys' will remake the existing physics mesh");
+
+ uiDefButBitS(block, TOGN, ACT_EDOB_REPLACE_MESH_NOGFX, B_NOP, "Gfx", xco+40 + (width-80)/2, yco-44, (width-80)/4, 19, &eoa->flag, 0, 0, 0, 0, "Replace the display mesh");
+ uiDefButBitS(block, TOG, ACT_EDOB_REPLACE_MESH_PHYS, B_NOP, "Phys", xco+40 + (width-80)/2 +(width-80)/4, yco-44, (width-80)/4, 19, &eoa->flag, 0, 0, 0, 0, "Replace the physics mesh (triangle bounds only. compound shapes not supported)");
}
else if(eoa->type==ACT_EDOB_TRACK_TO) {
ysize= 48;
diff --git a/source/gameengine/Converter/KX_ConvertActuators.cpp b/source/gameengine/Converter/KX_ConvertActuators.cpp
index ea812a71fdd..b6fc7f1dbba 100644
--- a/source/gameengine/Converter/KX_ConvertActuators.cpp
+++ b/source/gameengine/Converter/KX_ConvertActuators.cpp
@@ -638,7 +638,10 @@ void BL_ConvertActuators(char* maggiename,
= new KX_SCA_ReplaceMeshActuator(
gameobj,
tmpmesh,
- scene
+ scene,
+ (editobact->flag & ACT_EDOB_REPLACE_MESH_NOGFX)==0,
+ (editobact->flag & ACT_EDOB_REPLACE_MESH_PHYS)!=0
+
);
baseact = tmpreplaceact;
diff --git a/source/gameengine/GameLogic/SCA_IScene.h b/source/gameengine/GameLogic/SCA_IScene.h
index b641efc6ee1..79d922a998e 100644
--- a/source/gameengine/GameLogic/SCA_IScene.h
+++ b/source/gameengine/GameLogic/SCA_IScene.h
@@ -55,7 +55,7 @@ public:
//virtual void DelayedReleaseObject(class CValue* gameobj)=0;
virtual void ReplaceMesh(class CValue* gameobj,
- void* meshobj)=0;
+ void* meshobj, bool use_gfx, bool use_phys)=0;
std::vector<SCA_DebugProp*>& GetDebugProperties();
void AddDebugProperty(class CValue* debugprop,
const STR_String &name);
diff --git a/source/gameengine/Ketsji/KX_GameObject.cpp b/source/gameengine/Ketsji/KX_GameObject.cpp
index 36a9efe5b91..e9263ee62e0 100644
--- a/source/gameengine/Ketsji/KX_GameObject.cpp
+++ b/source/gameengine/Ketsji/KX_GameObject.cpp
@@ -1182,7 +1182,7 @@ PyMethodDef KX_GameObject::Methods[] = {
{"getChildrenRecursive", (PyCFunction)KX_GameObject::sPyGetChildrenRecursive,METH_NOARGS},
{"getPhysicsId", (PyCFunction)KX_GameObject::sPyGetPhysicsId,METH_NOARGS},
{"getPropertyNames", (PyCFunction)KX_GameObject::sPyGetPropertyNames,METH_NOARGS},
- {"replaceMesh",(PyCFunction) KX_GameObject::sPyReplaceMesh, METH_O},
+ {"replaceMesh",(PyCFunction) KX_GameObject::sPyReplaceMesh, METH_VARARGS},
{"endObject",(PyCFunction) KX_GameObject::sPyEndObject, METH_NOARGS},
{"reinstancePhysicsMesh", (PyCFunction)KX_GameObject::sPyReinstancePhysicsMesh,METH_VARARGS},
@@ -1260,15 +1260,21 @@ bool KX_GameObject::ConvertPythonVectorArgs(PyObject* args,
}
*/
-PyObject* KX_GameObject::PyReplaceMesh(PyObject* value)
+PyObject* KX_GameObject::PyReplaceMesh(PyObject* args)
{
KX_Scene *scene = KX_GetActiveScene();
- RAS_MeshObject* new_mesh;
+
+ PyObject *value;
+ int use_gfx= 1, use_phys= 0;
+ RAS_MeshObject *new_mesh;
+
+ if (!PyArg_ParseTuple(args,"O|ii:replaceMesh", &value, &use_gfx, &use_phys))
+ return NULL;
if (!ConvertPythonToMesh(value, &new_mesh, false, "gameOb.replaceMesh(value): KX_GameObject"))
return NULL;
- scene->ReplaceMesh(this, new_mesh);
+ scene->ReplaceMesh(this, new_mesh, (bool)use_gfx, (bool)use_phys);
Py_RETURN_NONE;
}
diff --git a/source/gameengine/Ketsji/KX_GameObject.h b/source/gameengine/Ketsji/KX_GameObject.h
index d2450d342c1..32df5803f31 100644
--- a/source/gameengine/Ketsji/KX_GameObject.h
+++ b/source/gameengine/Ketsji/KX_GameObject.h
@@ -865,7 +865,7 @@ public:
KX_PYMETHOD_VARARGS(KX_GameObject,GetMesh);
KX_PYMETHOD_NOARGS(KX_GameObject,GetPhysicsId);
KX_PYMETHOD_NOARGS(KX_GameObject,GetPropertyNames);
- KX_PYMETHOD_O(KX_GameObject,ReplaceMesh);
+ KX_PYMETHOD_VARARGS(KX_GameObject,ReplaceMesh);
KX_PYMETHOD_NOARGS(KX_GameObject,EndObject);
KX_PYMETHOD_DOC(KX_GameObject,rayCastTo);
KX_PYMETHOD_DOC(KX_GameObject,rayCast);
diff --git a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
index 00842d7012a..6bb9385889f 100644
--- a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
+++ b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
@@ -96,6 +96,8 @@ PyMethodDef KX_SCA_ReplaceMeshActuator::Methods[] = {
PyAttributeDef KX_SCA_ReplaceMeshActuator::Attributes[] = {
KX_PYATTRIBUTE_RW_FUNCTION("mesh", KX_SCA_ReplaceMeshActuator, pyattr_get_mesh, pyattr_set_mesh),
+ KX_PYATTRIBUTE_BOOL_RW ("useDisplayMesh", KX_SCA_ReplaceMeshActuator, m_use_gfx),
+ KX_PYATTRIBUTE_BOOL_RW ("usePhysicsMesh", KX_SCA_ReplaceMeshActuator, m_use_phys),
{ NULL } //Sentinel
};
@@ -179,11 +181,15 @@ KX_PYMETHODDEF_DOC(KX_SCA_ReplaceMeshActuator, instantReplaceMesh,
KX_SCA_ReplaceMeshActuator::KX_SCA_ReplaceMeshActuator(SCA_IObject *gameobj,
class RAS_MeshObject *mesh,
SCA_IScene* scene,
+ bool use_gfx,
+ bool use_phys,
PyTypeObject* T) :
SCA_IActuator(gameobj, T),
m_mesh(mesh),
- m_scene(scene)
+ m_scene(scene),
+ m_use_gfx(use_gfx),
+ m_use_phys(use_phys)
{
} /* End of constructor */
@@ -205,7 +211,8 @@ bool KX_SCA_ReplaceMeshActuator::Update()
if (bNegativeEvent)
return false; // do nothing on negative events
- if (m_mesh) m_scene->ReplaceMesh(GetParent(),m_mesh);
+ if (m_mesh || m_use_phys) /* NULL mesh is ok if were updating physics */
+ m_scene->ReplaceMesh(GetParent(),m_mesh, m_use_gfx, m_use_phys);
return false;
}
@@ -227,7 +234,7 @@ CValue* KX_SCA_ReplaceMeshActuator::GetReplica()
void KX_SCA_ReplaceMeshActuator::InstantReplaceMesh()
{
- if (m_mesh) m_scene->ReplaceMesh(GetParent(),m_mesh);
+ if (m_mesh) m_scene->ReplaceMesh(GetParent(),m_mesh, m_use_gfx, m_use_phys);
}
/* eof */
diff --git a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h
index 0e7f7852701..46d6f3eebf1 100644
--- a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h
+++ b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.h
@@ -50,12 +50,16 @@ class KX_SCA_ReplaceMeshActuator : public SCA_IActuator
// mesh reference (mesh to replace)
RAS_MeshObject* m_mesh;
SCA_IScene* m_scene;
+ bool m_use_phys;
+ bool m_use_gfx;
public:
KX_SCA_ReplaceMeshActuator(
SCA_IObject* gameobj,
RAS_MeshObject *mesh,
SCA_IScene* scene,
+ bool use_gfx,
+ bool use_phys,
PyTypeObject* T=&Type
);
diff --git a/source/gameengine/Ketsji/KX_Scene.cpp b/source/gameengine/Ketsji/KX_Scene.cpp
index b57a07779cb..caab0f38db9 100644
--- a/source/gameengine/Ketsji/KX_Scene.cpp
+++ b/source/gameengine/Ketsji/KX_Scene.cpp
@@ -1017,92 +1017,119 @@ int KX_Scene::NewRemoveObject(class CValue* gameobj)
-void KX_Scene::ReplaceMesh(class CValue* obj,void* meshobj)
+void KX_Scene::ReplaceMesh(class CValue* obj,void* meshobj, bool use_gfx, bool use_phys)
{
KX_GameObject* gameobj = static_cast<KX_GameObject*>(obj);
RAS_MeshObject* mesh = static_cast<RAS_MeshObject*>(meshobj);
- if(!gameobj || !mesh)
- {
- std::cout << "warning: invalid object, mesh will not be replaced" << std::endl;
+ if(!gameobj) {
+ std::cout << "KX_Scene::ReplaceMesh Warning: invalid object, doing nothing" << std::endl;
return;
}
-
- gameobj->RemoveMeshes();
- gameobj->AddMesh(mesh);
- if (gameobj->m_isDeformable)
- {
- BL_DeformableGameObject* newobj = static_cast<BL_DeformableGameObject*>( gameobj );
+ if(use_gfx && mesh != NULL)
+ {
+ gameobj->RemoveMeshes();
+ gameobj->AddMesh(mesh);
- if (newobj->GetDeformer())
+ if (gameobj->m_isDeformable)
{
- delete newobj->GetDeformer();
- newobj->SetDeformer(NULL);
- }
-
- if (mesh->IsDeformed())
- {
- // we must create a new deformer but which one?
- KX_GameObject* parentobj = newobj->GetParent();
- // this always return the original game object (also for replicate)
- Object* blendobj = newobj->GetBlenderObject();
- // object that owns the new mesh
- Object* oldblendobj = static_cast<struct Object*>(m_logicmgr->FindBlendObjByGameMeshName(mesh->GetName()));
- Mesh* blendmesh = mesh->GetMesh();
-
- bool bHasModifier = BL_ModifierDeformer::HasCompatibleDeformer(blendobj);
- bool bHasShapeKey = blendmesh->key != NULL && blendmesh->key->type==KEY_RELATIVE;
- bool bHasDvert = blendmesh->dvert != NULL;
- bool bHasArmature =
- parentobj && // current parent is armature
- parentobj->GetGameObjectType() == SCA_IObject::OBJ_ARMATURE &&
- oldblendobj && // needed for mesh deform
- blendobj->parent && // original object had armature (not sure this test is needed)
- blendobj->parent->type == OB_ARMATURE &&
- blendobj->partype==PARSKEL &&
- blendmesh->dvert!=NULL; // mesh has vertex group
- bool releaseParent = true;
-
+ BL_DeformableGameObject* newobj = static_cast<BL_DeformableGameObject*>( gameobj );
- if (oldblendobj==NULL) {
- std::cout << "warning: ReplaceMesh() new mesh is not used in an object from the current scene, you will get incorrect behavior" << std::endl;
- bHasShapeKey= bHasDvert= bHasArmature=bHasModifier= false;
+ if (newobj->GetDeformer())
+ {
+ delete newobj->GetDeformer();
+ newobj->SetDeformer(NULL);
}
-
- if (bHasModifier)
+
+ if (mesh->IsDeformed())
{
- BL_ModifierDeformer* modifierDeformer;
- if (bHasShapeKey || bHasArmature)
- {
- modifierDeformer = new BL_ModifierDeformer(
- newobj,
- oldblendobj, blendobj,
- static_cast<BL_SkinMeshObject*>(mesh),
- true,
- static_cast<BL_ArmatureObject*>( parentobj )
- );
- releaseParent= false;
- modifierDeformer->LoadShapeDrivers(blendobj->parent);
+ // we must create a new deformer but which one?
+ KX_GameObject* parentobj = newobj->GetParent();
+ // this always return the original game object (also for replicate)
+ Object* blendobj = newobj->GetBlenderObject();
+ // object that owns the new mesh
+ Object* oldblendobj = static_cast<struct Object*>(m_logicmgr->FindBlendObjByGameMeshName(mesh->GetName()));
+ Mesh* blendmesh = mesh->GetMesh();
+
+ bool bHasModifier = BL_ModifierDeformer::HasCompatibleDeformer(blendobj);
+ bool bHasShapeKey = blendmesh->key != NULL && blendmesh->key->type==KEY_RELATIVE;
+ bool bHasDvert = blendmesh->dvert != NULL;
+ bool bHasArmature =
+ parentobj && // current parent is armature
+ parentobj->GetGameObjectType() == SCA_IObject::OBJ_ARMATURE &&
+ oldblendobj && // needed for mesh deform
+ blendobj->parent && // original object had armature (not sure this test is needed)
+ blendobj->parent->type == OB_ARMATURE &&
+ blendobj->partype==PARSKEL &&
+ blendmesh->dvert!=NULL; // mesh has vertex group
+ bool releaseParent = true;
+
+
+ if (oldblendobj==NULL) {
+ std::cout << "warning: ReplaceMesh() new mesh is not used in an object from the current scene, you will get incorrect behavior" << std::endl;
+ bHasShapeKey= bHasDvert= bHasArmature=bHasModifier= false;
}
- else
+
+ if (bHasModifier)
{
- modifierDeformer = new BL_ModifierDeformer(
- newobj,
- oldblendobj, blendobj,
- static_cast<BL_SkinMeshObject*>(mesh),
- false,
- NULL
- );
+ BL_ModifierDeformer* modifierDeformer;
+ if (bHasShapeKey || bHasArmature)
+ {
+ modifierDeformer = new BL_ModifierDeformer(
+ newobj,
+ oldblendobj, blendobj,
+ static_cast<BL_SkinMeshObject*>(mesh),
+ true,
+ static_cast<BL_ArmatureObject*>( parentobj )
+ );
+ releaseParent= false;
+ modifierDeformer->LoadShapeDrivers(blendobj->parent);
+ }
+ else
+ {
+ modifierDeformer = new BL_ModifierDeformer(
+ newobj,
+ oldblendobj, blendobj,
+ static_cast<BL_SkinMeshObject*>(mesh),
+ false,
+ NULL
+ );
+ }
+ newobj->SetDeformer(modifierDeformer);
+ }
+ else if (bHasShapeKey)
+ {
+ BL_ShapeDeformer* shapeDeformer;
+ if (bHasArmature)
+ {
+ shapeDeformer = new BL_ShapeDeformer(
+ newobj,
+ oldblendobj, blendobj,
+ static_cast<BL_SkinMeshObject*>(mesh),
+ true,
+ true,
+ static_cast<BL_ArmatureObject*>( parentobj )
+ );
+ releaseParent= false;
+ shapeDeformer->LoadShapeDrivers(blendobj->parent);
+ }
+ else
+ {
+ shapeDeformer = new BL_ShapeDeformer(
+ newobj,
+ oldblendobj, blendobj,
+ static_cast<BL_SkinMeshObject*>(mesh),
+ false,
+ true,
+ NULL
+ );
+ }
+ newobj->SetDeformer( shapeDeformer);
}
- newobj->SetDeformer(modifierDeformer);
- }
- else if (bHasShapeKey)
- {
- BL_ShapeDeformer* shapeDeformer;
- if (bHasArmature)
+ else if (bHasArmature)
{
- shapeDeformer = new BL_ShapeDeformer(
+ BL_SkinDeformer* skinDeformer = new BL_SkinDeformer(
newobj,
oldblendobj, blendobj,
static_cast<BL_SkinMeshObject*>(mesh),
@@ -1111,49 +1138,28 @@ void KX_Scene::ReplaceMesh(class CValue* obj,void* meshobj)
static_cast<BL_ArmatureObject*>( parentobj )
);
releaseParent= false;
- shapeDeformer->LoadShapeDrivers(blendobj->parent);
+ newobj->SetDeformer(skinDeformer);
}
- else
+ else if (bHasDvert)
{
- shapeDeformer = new BL_ShapeDeformer(
- newobj,
- oldblendobj, blendobj,
- static_cast<BL_SkinMeshObject*>(mesh),
- false,
- true,
- NULL
+ BL_MeshDeformer* meshdeformer = new BL_MeshDeformer(
+ newobj, oldblendobj, static_cast<BL_SkinMeshObject*>(mesh)
);
+ newobj->SetDeformer(meshdeformer);
}
- newobj->SetDeformer( shapeDeformer);
- }
- else if (bHasArmature)
- {
- BL_SkinDeformer* skinDeformer = new BL_SkinDeformer(
- newobj,
- oldblendobj, blendobj,
- static_cast<BL_SkinMeshObject*>(mesh),
- true,
- true,
- static_cast<BL_ArmatureObject*>( parentobj )
- );
- releaseParent= false;
- newobj->SetDeformer(skinDeformer);
- }
- else if (bHasDvert)
- {
- BL_MeshDeformer* meshdeformer = new BL_MeshDeformer(
- newobj, oldblendobj, static_cast<BL_SkinMeshObject*>(mesh)
- );
- newobj->SetDeformer(meshdeformer);
+
+ // release parent reference if its not being used
+ if( releaseParent && parentobj)
+ parentobj->Release();
}
-
- // release parent reference if its not being used
- if( releaseParent && parentobj)
- parentobj->Release();
}
- }
- gameobj->AddMeshUser();
+ gameobj->AddMeshUser();
+ }
+
+ if(use_phys) { /* update the new assigned mesh with the physics mesh */
+ KX_ReInstanceBulletShapeFromMesh(gameobj, NULL, use_gfx?NULL:mesh);
+ }
}
KX_Camera* KX_Scene::FindCamera(KX_Camera* cam)
@@ -1844,4 +1850,4 @@ KX_PYMETHODDEF_DOC(KX_Scene, addObject,
// the object is added to the scene so we dont want python to own a reference
replica->Release();
return replica->GetProxy();
-} \ No newline at end of file
+}
diff --git a/source/gameengine/Ketsji/KX_Scene.h b/source/gameengine/Ketsji/KX_Scene.h
index 79d3f7fd828..c4f868f6a02 100644
--- a/source/gameengine/Ketsji/KX_Scene.h
+++ b/source/gameengine/Ketsji/KX_Scene.h
@@ -323,7 +323,7 @@ public:
int NewRemoveObject(CValue* gameobj);
void ReplaceMesh(CValue* gameobj,
- void* meshobj);
+ void* meshob, bool use_gfx, bool use_phys);
/**
* @section Logic stuff
* Initiate an update of the logic system.
diff --git a/source/gameengine/PyDoc/GameTypes.py b/source/gameengine/PyDoc/GameTypes.py
index 6a554a7c42e..b1d1ce71173 100644
--- a/source/gameengine/PyDoc/GameTypes.py
+++ b/source/gameengine/PyDoc/GameTypes.py
@@ -1642,10 +1642,14 @@ class KX_GameObject(SCA_IObject):
Delete this object, can be used inpace of the EndObject Actuator.
The actual removal of the object from the scene is delayed.
"""
- def replaceMesh(mesh):
+ def replaceMesh(mesh, useDisplayMesh=True, usePhysicsMesh=False):
"""
Replace the mesh of this object with a new mesh. This works the same was as the actuator.
@type mesh: L{KX_MeshProxy} or mesh name
+ @type useDisplayMesh: bool
+ @param useDisplayMesh: when enabled the display mesh will be replaced (optional argument).
+ @type usePhysicsMesh: bool
+ @param usePhysicsMesh: when enabled the physics mesh will be replaced (optional argument).
"""
def getVisible():
"""
@@ -3791,6 +3795,11 @@ class KX_SCA_ReplaceMeshActuator(SCA_IActuator):
@ivar mesh: L{KX_MeshProxy} or the name of the mesh that will replace the current one
Set to None to disable actuator
@type mesh: L{KX_MeshProxy} or None if no mesh is set
+
+ @ivar useDisplayMesh: when true the displayed mesh is replaced.
+ @type useDisplayMesh: boolean
+ @ivar usePhysicsMesh: when true the physics mesh is replaced.
+ @type usePhysicsMesh: boolean
"""
def setMesh(name):
"""