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-04-19 16:46:39 +0400
committerCampbell Barton <ideasman42@gmail.com>2009-04-19 16:46:39 +0400
commit8d2cb5bea44f4245dd17f2d82cbd0251d8090fd5 (patch)
treeb28e45f1edaf083c15d2176079836a4497685e57 /source/gameengine/Ketsji
parent92cea7c1b1540d11ed9729bacfabd23ccb7a79c7 (diff)
BGE Python API
This changes how the BGE classes and Python work together, which hasnt changed since blender went opensource. The main difference is PyObjectPlus - the base class for most game engine classes, no longer inherit from PyObject, and cannot be cast to a PyObject. This has the advantage that the BGE does not have to keep 2 reference counts valid for C++ and Python. Previously C++ classes would never be freed while python held a reference, however this reference could be problematic eg: a GameObject that isnt in a scene anymore should not be used by python, doing so could even crash blender in some cases. Instead PyObjectPlus has a member "PyObject *m_proxy" which is lazily initialized when python needs it. m_proxy reference counts are managed by python, though it should never be freed while the C++ class exists since it holds a reference to avoid making and freeing it all the time. When the C++ class is free'd it sets the m_proxy reference to NULL, If python accesses this variable it will raise a RuntimeError, (check the isValid attribute to see if its valid without raising an error). - This replaces the m_zombie bool and IsZombie() tests added recently. In python return values that used to be.. return value->AddRef(); Are now return value->GetProxy(); or... return value->NewProxy(true); // true means python owns this C++ value which will be deleted when the PyObject is freed
Diffstat (limited to 'source/gameengine/Ketsji')
-rw-r--r--source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp16
-rw-r--r--source/gameengine/Ketsji/KX_BlenderMaterial.cpp12
-rw-r--r--source/gameengine/Ketsji/KX_CameraActuator.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_GameObject.cpp135
-rw-r--r--source/gameengine/Ketsji/KX_GameObject.h6
-rw-r--r--source/gameengine/Ketsji/KX_MeshProxy.cpp10
-rw-r--r--source/gameengine/Ketsji/KX_MouseFocusSensor.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_ParentActuator.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_PolyProxy.cpp14
-rw-r--r--source/gameengine/Ketsji/KX_PolygonMaterial.cpp3
-rw-r--r--source/gameengine/Ketsji/KX_PyConstraintBinding.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_PythonInit.cpp11
-rw-r--r--source/gameengine/Ketsji/KX_PythonInitTypes.cpp6
-rw-r--r--source/gameengine/Ketsji/KX_RaySensor.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp9
-rw-r--r--source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp2
-rw-r--r--source/gameengine/Ketsji/KX_Scene.cpp13
-rw-r--r--source/gameengine/Ketsji/KX_SceneActuator.cpp44
-rw-r--r--source/gameengine/Ketsji/KX_TouchSensor.cpp8
-rw-r--r--source/gameengine/Ketsji/KX_TrackToActuator.cpp4
-rw-r--r--source/gameengine/Ketsji/KX_VehicleWrapper.cpp5
21 files changed, 163 insertions, 155 deletions
diff --git a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp
index 65600856377..8aca2e372d1 100644
--- a/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp
+++ b/source/gameengine/Ketsji/KXNetwork/KX_NetworkMessageSensor.cpp
@@ -235,9 +235,9 @@ PyObject* KX_NetworkMessageSensor::pyattr_get_bodies(void *self_v, const KX_PYAT
{
KX_NetworkMessageSensor *self = static_cast<KX_NetworkMessageSensor*>(self_v);
if (self->m_BodyList) {
- return ((PyObject*) self->m_BodyList->AddRef());
+ return self->m_BodyList->GetProxy();
} else {
- return ((PyObject*) new CListValue());
+ return (new CListValue())->NewProxy(true);
}
}
@@ -245,9 +245,9 @@ PyObject* KX_NetworkMessageSensor::pyattr_get_subjects(void *self_v, const KX_PY
{
KX_NetworkMessageSensor *self = static_cast<KX_NetworkMessageSensor*>(self_v);
if (self->m_SubjectList) {
- return ((PyObject*) self->m_SubjectList->AddRef());
+ return self->m_SubjectList->GetProxy();
} else {
- return ((PyObject*) new CListValue());
+ return (new CListValue())->NewProxy(true);
}
}
@@ -290,9 +290,9 @@ PyObject* KX_NetworkMessageSensor::PyGetBodies( PyObject* )
{
ShowDeprecationWarning("getBodies()", "bodies");
if (m_BodyList) {
- return ((PyObject*) m_BodyList->AddRef());
+ return m_BodyList->GetProxy();
} else {
- return ((PyObject*) new CListValue());
+ return (new CListValue())->NewProxy(true);
}
}
@@ -316,9 +316,9 @@ PyObject* KX_NetworkMessageSensor::PyGetSubjects( PyObject* )
{
ShowDeprecationWarning("getSubjects()", "subjects");
if (m_SubjectList) {
- return ((PyObject*) m_SubjectList->AddRef());
+ return m_SubjectList->GetProxy();
} else {
- return ((PyObject*) new CListValue());
+ return (new CListValue())->NewProxy(true);
}
}
// <----- Deprecated \ No newline at end of file
diff --git a/source/gameengine/Ketsji/KX_BlenderMaterial.cpp b/source/gameengine/Ketsji/KX_BlenderMaterial.cpp
index 0e417dde5d2..bdad21f76eb 100644
--- a/source/gameengine/Ketsji/KX_BlenderMaterial.cpp
+++ b/source/gameengine/Ketsji/KX_BlenderMaterial.cpp
@@ -827,8 +827,7 @@ KX_PYMETHODDEF_DOC( KX_BlenderMaterial, getShader , "getShader()")
m_flag &= ~RAS_BLENDERGLSL;
mMaterial->SetSharedMaterial(true);
mScene->GetBucketManager()->ReleaseDisplayLists(this);
- Py_INCREF(mShader);
- return mShader;
+ return mShader->GetProxy();
}else
{
// decref all references to the object
@@ -836,13 +835,8 @@ KX_PYMETHODDEF_DOC( KX_BlenderMaterial, getShader , "getShader()")
// We will then go back to fixed functionality
// for this material
if(mShader) {
- if(mShader->ob_refcnt > 1) {
- Py_DECREF(mShader);
- }
- else {
- delete mShader;
- mShader=0;
- }
+ delete mShader; /* will handle python de-referencing */
+ mShader=0;
}
}
Py_RETURN_NONE;
diff --git a/source/gameengine/Ketsji/KX_CameraActuator.cpp b/source/gameengine/Ketsji/KX_CameraActuator.cpp
index 329d31cfa25..a1159dbc23f 100644
--- a/source/gameengine/Ketsji/KX_CameraActuator.cpp
+++ b/source/gameengine/Ketsji/KX_CameraActuator.cpp
@@ -449,7 +449,7 @@ PyObject* KX_CameraActuator::PyGetObject(PyObject* self, PyObject* args)
if (ret_name_only)
return PyString_FromString(m_ob->GetName());
else
- return m_ob->AddRef();
+ return m_ob->GetProxy();
}
/* set obj ---------------------------------------------------------- */
const char KX_CameraActuator::SetObject_doc[] =
@@ -597,7 +597,7 @@ PyObject* KX_CameraActuator::pyattr_get_object(void *self_v, const KX_PYATTRIBUT
if (self->m_ob==NULL)
Py_RETURN_NONE;
else
- return self->m_ob->AddRef();
+ return self->m_ob->GetProxy();
}
int KX_CameraActuator::pyattr_set_object(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
diff --git a/source/gameengine/Ketsji/KX_GameObject.cpp b/source/gameengine/Ketsji/KX_GameObject.cpp
index 3e7c99dc472..402c242315a 100644
--- a/source/gameengine/Ketsji/KX_GameObject.cpp
+++ b/source/gameengine/Ketsji/KX_GameObject.cpp
@@ -1039,7 +1039,43 @@ void KX_GameObject::Suspend()
}
}
+static void walk_children(SG_Node* node, CListValue* list, bool recursive)
+{
+ if (!node)
+ return;
+ NodeList& children = node->GetSGChildren();
+
+ for (NodeList::iterator childit = children.begin();!(childit==children.end());++childit)
+ {
+ SG_Node* childnode = (*childit);
+ CValue* childobj = (CValue*)childnode->GetSGClientObject();
+ if (childobj != NULL) // This is a GameObject
+ {
+ // add to the list
+ list->Add(childobj->AddRef());
+ }
+
+ // if the childobj is NULL then this may be an inverse parent link
+ // so a non recursive search should still look down this node.
+ if (recursive || childobj==NULL) {
+ walk_children(childnode, list, recursive);
+ }
+ }
+}
+
+CListValue* KX_GameObject::GetChildren()
+{
+ CListValue* list = new CListValue();
+ walk_children(GetSGNode(), list, 0); /* GetSGNode() is always valid or it would have raised an exception before this */
+ return list;
+}
+CListValue* KX_GameObject::GetChildrenRecursive()
+{
+ CListValue* list = new CListValue();
+ walk_children(GetSGNode(), list, 1);
+ return list;
+}
/* ------- python stuff ---------------------------------------------------*/
@@ -1185,13 +1221,10 @@ PyObject* KX_GameObject::PyGetPosition(PyObject* self)
Py_ssize_t KX_GameObject::Map_Len(PyObject* self_v)
{
- KX_GameObject* self= static_cast<KX_GameObject*>(self_v);
+ KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v);
- if (self->IsZombie()) /* not sure what to do here */
- {
- PyErr_Clear();
+ if (self==NULL) /* not sure what to do here */
return 0;
- }
Py_ssize_t len= self->GetPropertyCount();
if(self->m_attr_dict)
@@ -1202,18 +1235,20 @@ Py_ssize_t KX_GameObject::Map_Len(PyObject* self_v)
PyObject *KX_GameObject::Map_GetItem(PyObject *self_v, PyObject *item)
{
- KX_GameObject* self= static_cast<KX_GameObject*>(self_v);
+ KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v);
const char *attr_str= PyString_AsString(item);
CValue* resultattr;
PyObject* pyconvert;
- if (self->IsZombiePyErr())
+ if (self==NULL) {
+ PyErr_SetString(PyExc_RuntimeError, BGE_PROXY_ERROR_MSG);
return NULL;
+ }
/* first see if the attributes a string and try get the cvalue attribute */
if(attr_str && (resultattr=self->GetProperty(attr_str))) {
pyconvert = resultattr->ConvertValueToPython();
- return pyconvert ? pyconvert:resultattr;
+ return pyconvert ? pyconvert:resultattr->GetProxy();
}
/* no CValue attribute, try get the python only m_attr_dict attribute */
else if (self->m_attr_dict && (pyconvert=PyDict_GetItem(self->m_attr_dict, item))) {
@@ -1234,13 +1269,15 @@ PyObject *KX_GameObject::Map_GetItem(PyObject *self_v, PyObject *item)
int KX_GameObject::Map_SetItem(PyObject *self_v, PyObject *key, PyObject *val)
{
- KX_GameObject* self= static_cast<KX_GameObject*>(self_v);
+ KX_GameObject* self= static_cast<KX_GameObject*>BGE_PROXY_REF(self_v);
const char *attr_str= PyString_AsString(key);
if(attr_str==NULL)
PyErr_Clear();
- if (self->IsZombiePyErr())
+ if (self==NULL) {
+ PyErr_SetString(PyExc_RuntimeError, BGE_PROXY_ERROR_MSG);
return -1;
+ }
if (val==NULL) { /* del ob["key"] */
int del= 0;
@@ -1370,7 +1407,7 @@ PyObject* KX_GameObject::pyattr_get_parent(void *self_v, const KX_PYATTRIBUTE_DE
KX_GameObject* self= static_cast<KX_GameObject*>(self_v);
KX_GameObject* parent = self->GetParent();
if (parent)
- return parent->AddRef();
+ return parent->GetProxy();
Py_RETURN_NONE;
}
@@ -1667,7 +1704,7 @@ PyObject* KX_GameObject::pyattr_get_meshes(void *self_v, const KX_PYATTRIBUTE_DE
for(i=0; i < self->m_meshes.size(); i++)
{
KX_MeshProxy* meshproxy = new KX_MeshProxy(self->m_meshes[i]);
- PyList_SET_ITEM(meshes, i, meshproxy);
+ PyList_SET_ITEM(meshes, i, meshproxy->GetProxy());
}
return meshes;
@@ -1681,7 +1718,7 @@ PyObject* KX_GameObject::pyattr_get_sensors(void *self_v, const KX_PYATTRIBUTE_D
PyObject* resultlist = PyList_New(sensors.size());
for (unsigned int index=0;index<sensors.size();index++)
- PyList_SET_ITEM(resultlist, index, sensors[index]->AddRef());
+ PyList_SET_ITEM(resultlist, index, sensors[index]->GetProxy());
return resultlist;
}
@@ -1693,7 +1730,7 @@ PyObject* KX_GameObject::pyattr_get_controllers(void *self_v, const KX_PYATTRIBU
PyObject* resultlist = PyList_New(controllers.size());
for (unsigned int index=0;index<controllers.size();index++)
- PyList_SET_ITEM(resultlist, index, controllers[index]->AddRef());
+ PyList_SET_ITEM(resultlist, index, controllers[index]->GetProxy());
return resultlist;
}
@@ -1705,7 +1742,7 @@ PyObject* KX_GameObject::pyattr_get_actuators(void *self_v, const KX_PYATTRIBUTE
PyObject* resultlist = PyList_New(actuators.size());
for (unsigned int index=0;index<actuators.size();index++)
- PyList_SET_ITEM(resultlist, index, actuators[index]->AddRef());
+ PyList_SET_ITEM(resultlist, index, actuators[index]->GetProxy());
return resultlist;
}
@@ -2083,28 +2120,17 @@ PyObject* KX_GameObject::PyGetParent(PyObject* self)
ShowDeprecationWarning("getParent()", "the parent property");
KX_GameObject* parent = this->GetParent();
if (parent)
- return parent->AddRef();
+ return parent->GetProxy();
Py_RETURN_NONE;
}
PyObject* KX_GameObject::PySetParent(PyObject* self, PyObject* value)
{
- if (!PyObject_TypeCheck(value, &KX_GameObject::Type)) {
- PyErr_SetString(PyExc_TypeError, "expected a KX_GameObject type");
+ KX_GameObject *obj;
+ if (!ConvertPythonToGameObject(value, &obj, false))
return NULL;
- }
- if (self==value) {
- PyErr_SetString(PyExc_ValueError, "cannot set the object to be its own parent!");
- return NULL;
- }
- // The object we want to set as parent
- CValue *m_ob = (CValue*)value;
- KX_GameObject *obj = ((KX_GameObject*)m_ob);
- KX_Scene *scene = KX_GetActiveScene();
-
- this->SetParent(scene, obj);
-
+ this->SetParent(KX_GetActiveScene(), obj);
Py_RETURN_NONE;
}
@@ -2115,43 +2141,14 @@ PyObject* KX_GameObject::PyRemoveParent(PyObject* self)
Py_RETURN_NONE;
}
-
-static void walk_children(SG_Node* node, CListValue* list, bool recursive)
-{
- if (!node)
- return;
- NodeList& children = node->GetSGChildren();
-
- for (NodeList::iterator childit = children.begin();!(childit==children.end());++childit)
- {
- SG_Node* childnode = (*childit);
- CValue* childobj = (CValue*)childnode->GetSGClientObject();
- if (childobj != NULL) // This is a GameObject
- {
- // add to the list
- list->Add(childobj->AddRef());
- }
-
- // if the childobj is NULL then this may be an inverse parent link
- // so a non recursive search should still look down this node.
- if (recursive || childobj==NULL) {
- walk_children(childnode, list, recursive);
- }
- }
-}
-
PyObject* KX_GameObject::PyGetChildren(PyObject* self)
{
- CListValue* list = new CListValue();
- walk_children(GetSGNode(), list, 0); /* GetSGNode() is always valid or it would have raised an exception before this */
- return list;
+ return GetChildren()->NewProxy(true);
}
PyObject* KX_GameObject::PyGetChildrenRecursive(PyObject* self)
{
- CListValue* list = new CListValue();
- walk_children(GetSGNode(), list, 1);
- return list;
+ return GetChildrenRecursive()->NewProxy(true);
}
PyObject* KX_GameObject::PyGetMesh(PyObject* self, PyObject* args)
@@ -2166,7 +2163,7 @@ PyObject* KX_GameObject::PyGetMesh(PyObject* self, PyObject* args)
if (((unsigned int)mesh < m_meshes.size()) && mesh >= 0)
{
KX_MeshProxy* meshproxy = new KX_MeshProxy(m_meshes[mesh]);
- return meshproxy;
+ return meshproxy->NewProxy(true); // XXX Todo Python own.
}
Py_RETURN_NONE;
@@ -2516,7 +2513,7 @@ KX_PYMETHODDEF_DOC(KX_GameObject, rayCastTo,
KX_RayCast::RayTest(pe, fromPoint, toPoint, callback);
if (m_pHitObject)
- return m_pHitObject->AddRef();
+ return m_pHitObject->GetProxy();
Py_RETURN_NONE;
}
@@ -2618,7 +2615,7 @@ KX_PYMETHODDEF_DOC(KX_GameObject, rayCast,
{
PyObject* returnValue = (poly) ? PyTuple_New(4) : PyTuple_New(3);
if (returnValue) { // unlikely this would ever fail, if it does python sets an error
- PyTuple_SET_ITEM(returnValue, 0, m_pHitObject->AddRef());
+ PyTuple_SET_ITEM(returnValue, 0, m_pHitObject->GetProxy());
PyTuple_SET_ITEM(returnValue, 1, PyObjectFrom(callback.m_hitPoint));
PyTuple_SET_ITEM(returnValue, 2, PyObjectFrom(callback.m_hitNormal));
if (poly)
@@ -2628,7 +2625,7 @@ KX_PYMETHODDEF_DOC(KX_GameObject, rayCast,
// if this field is set, then we can trust that m_hitPolygon is a valid polygon
RAS_Polygon* polygon = callback.m_hitMesh->GetPolygon(callback.m_hitPolygon);
KX_PolyProxy* polyproxy = new KX_PolyProxy(callback.m_hitMesh, polygon);
- PyTuple_SET_ITEM(returnValue, 3, polyproxy);
+ PyTuple_SET_ITEM(returnValue, 3, polyproxy->NewProxy(true));
}
else
{
@@ -2708,7 +2705,7 @@ bool ConvertPythonToGameObject(PyObject * value, KX_GameObject **object, bool py
}
if (PyString_Check(value)) {
- *object = (KX_GameObject *)SCA_ILogicBrick::m_sCurrentLogicManager->GetGameObjectByName(STR_String( PyString_AsString(value) ));
+ *object = (KX_GameObject*)SCA_ILogicBrick::m_sCurrentLogicManager->GetGameObjectByName(STR_String( PyString_AsString(value) ));
if (*object) {
return true;
@@ -2719,11 +2716,13 @@ bool ConvertPythonToGameObject(PyObject * value, KX_GameObject **object, bool py
}
if (PyObject_TypeCheck(value, &KX_GameObject::Type)) {
- *object = static_cast<KX_GameObject*>(value);
+ *object = static_cast<KX_GameObject*>BGE_PROXY_REF(value);
/* sets the error */
- if ((*object)->IsZombiePyErr())
+ if (*object==NULL) {
+ PyErr_SetString(PyExc_RuntimeError, BGE_PROXY_ERROR_MSG);
return false;
+ }
return true;
}
diff --git a/source/gameengine/Ketsji/KX_GameObject.h b/source/gameengine/Ketsji/KX_GameObject.h
index dd85c2f2faa..89517bd76ce 100644
--- a/source/gameengine/Ketsji/KX_GameObject.h
+++ b/source/gameengine/Ketsji/KX_GameObject.h
@@ -807,6 +807,10 @@ public:
}
KX_ClientObjectInfo* getClientInfo() { return m_pClient_info; }
+
+ CListValue* GetChildren();
+ CListValue* GetChildrenRecursive();
+
/**
* @section Python interface functions.
*/
@@ -816,8 +820,6 @@ public:
virtual int py_delattro(PyObject *attr);
virtual PyObject* py_repr(void)
{
- if (IsZombiePyErr())
- return NULL;
return PyString_FromString(GetName().ReadPtr());
}
diff --git a/source/gameengine/Ketsji/KX_MeshProxy.cpp b/source/gameengine/Ketsji/KX_MeshProxy.cpp
index 93d92480b3d..09e19933dd9 100644
--- a/source/gameengine/Ketsji/KX_MeshProxy.cpp
+++ b/source/gameengine/Ketsji/KX_MeshProxy.cpp
@@ -232,7 +232,7 @@ PyObject* KX_MeshProxy::PyGetVertex(PyObject* self,
RAS_TexVert* vertex = m_meshobj->GetVertex(matindex,vertexindex);
if (vertex)
{
- vertexob = new KX_VertexProxy(this, vertex);
+ vertexob = (new KX_VertexProxy(this, vertex))->NewProxy(true);
}
}
else {
@@ -263,7 +263,7 @@ PyObject* KX_MeshProxy::PyGetPolygon(PyObject* self,
RAS_Polygon* polygon = m_meshobj->GetPolygon(polyindex);
if (polygon)
{
- polyob = new KX_PolyProxy(m_meshobj, polygon);
+ polyob = (new KX_PolyProxy(m_meshobj, polygon))->NewProxy(true);
}
else {
PyErr_SetString(PyExc_AttributeError, "polygon is NULL, unknown reason");
@@ -297,13 +297,11 @@ PyObject* KX_MeshProxy::pyattr_get_materials(void *self_v, const KX_PYATTRIBUTE_
if(polymat->GetFlag() & RAS_BLENDERMAT)
{
KX_BlenderMaterial *mat = static_cast<KX_BlenderMaterial*>(polymat);
- PyList_SET_ITEM(materials, i, mat);
- Py_INCREF(mat);
+ PyList_SET_ITEM(materials, i, mat->GetProxy());
}
else {
KX_PolygonMaterial *mat = static_cast<KX_PolygonMaterial*>(polymat);
- PyList_SET_ITEM(materials, i, mat);
- Py_INCREF(mat);
+ PyList_SET_ITEM(materials, i, mat->GetProxy());
}
}
return materials;
diff --git a/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp b/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp
index 65190937f35..e1b89eb3095 100644
--- a/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp
+++ b/source/gameengine/Ketsji/KX_MouseFocusSensor.cpp
@@ -396,7 +396,7 @@ PyObject* KX_MouseFocusSensor::PyGetHitObject(PyObject* self)
ShowDeprecationWarning("GetHitObject()", "the hitObject property");
if (m_hitObject)
- return m_hitObject->AddRef();
+ return m_hitObject->GetProxy();
Py_RETURN_NONE;
}
@@ -487,7 +487,7 @@ PyObject* KX_MouseFocusSensor::pyattr_get_hit_object(void *self_v, const KX_PYAT
KX_MouseFocusSensor* self= static_cast<KX_MouseFocusSensor*>(self_v);
if(self->m_hitObject)
- return self->m_hitObject->AddRef();
+ return self->m_hitObject->GetProxy();
Py_RETURN_NONE;
}
diff --git a/source/gameengine/Ketsji/KX_ParentActuator.cpp b/source/gameengine/Ketsji/KX_ParentActuator.cpp
index d0d441e2c1c..a667b459c22 100644
--- a/source/gameengine/Ketsji/KX_ParentActuator.cpp
+++ b/source/gameengine/Ketsji/KX_ParentActuator.cpp
@@ -184,7 +184,7 @@ PyObject* KX_ParentActuator::pyattr_get_object(void *self, const struct KX_PYATT
if (!actuator->m_ob)
Py_RETURN_NONE;
else
- return actuator->m_ob->AddRef();
+ return actuator->m_ob->GetProxy();
}
int KX_ParentActuator::pyattr_set_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
@@ -261,7 +261,7 @@ PyObject* KX_ParentActuator::PyGetObject(PyObject* self, PyObject* args)
if (ret_name_only)
return PyString_FromString(m_ob->GetName());
else
- return m_ob->AddRef();
+ return m_ob->GetProxy();
}
/* <----- */
diff --git a/source/gameengine/Ketsji/KX_PolyProxy.cpp b/source/gameengine/Ketsji/KX_PolyProxy.cpp
index e102ca4e0e6..c03d585395c 100644
--- a/source/gameengine/Ketsji/KX_PolyProxy.cpp
+++ b/source/gameengine/Ketsji/KX_PolyProxy.cpp
@@ -109,14 +109,12 @@ PyObject* KX_PolyProxy::py_getattro(PyObject *attr)
if(polymat->GetFlag() & RAS_BLENDERMAT)
{
KX_BlenderMaterial* mat = static_cast<KX_BlenderMaterial*>(polymat);
- Py_INCREF(mat);
- return mat;
+ return mat->GetProxy();
}
else
{
KX_PolygonMaterial* mat = static_cast<KX_PolygonMaterial*>(polymat);
- Py_INCREF(mat);
- return mat;
+ return mat->GetProxy();
}
}
if (!strcmp(attr_str, "matid"))
@@ -258,7 +256,7 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMesh,
"getMesh() : returns a mesh proxy\n")
{
KX_MeshProxy* meshproxy = new KX_MeshProxy((RAS_MeshObject*)m_mesh);
- return meshproxy;
+ return meshproxy->NewProxy(true);
}
KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMaterial,
@@ -268,13 +266,11 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_PolyProxy, getMaterial,
if(polymat->GetFlag() & RAS_BLENDERMAT)
{
KX_BlenderMaterial* mat = static_cast<KX_BlenderMaterial*>(polymat);
- Py_INCREF(mat);
- return mat;
+ return mat->GetProxy();
}
else
{
KX_PolygonMaterial* mat = static_cast<KX_PolygonMaterial*>(polymat);
- Py_INCREF(mat);
- return mat;
+ return mat->GetProxy();
}
}
diff --git a/source/gameengine/Ketsji/KX_PolygonMaterial.cpp b/source/gameengine/Ketsji/KX_PolygonMaterial.cpp
index 056442f77d9..bf1fbe386e6 100644
--- a/source/gameengine/Ketsji/KX_PolygonMaterial.cpp
+++ b/source/gameengine/Ketsji/KX_PolygonMaterial.cpp
@@ -98,8 +98,7 @@ bool KX_PolygonMaterial::Activate(RAS_IRasterizer* rasty, TCachingInfo& cachingI
{
PyObject *pyRasty = PyCObject_FromVoidPtr((void*)rasty, NULL); /* new reference */
PyObject *pyCachingInfo = PyCObject_FromVoidPtr((void*) &cachingInfo, NULL); /* new reference */
-
- PyObject *ret = PyObject_CallMethod(m_pymaterial, "activate", "(NNO)", pyRasty, pyCachingInfo, (PyObject*) this);
+ PyObject *ret = PyObject_CallMethod(m_pymaterial, "activate", "(NNO)", pyRasty, pyCachingInfo, (PyObject*) this->m_proxy);
if (ret)
{
bool value = PyInt_AsLong(ret);
diff --git a/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp b/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp
index 34c975f6bf6..2c65c184a9c 100644
--- a/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp
+++ b/source/gameengine/Ketsji/KX_PyConstraintBinding.cpp
@@ -381,7 +381,7 @@ static PyObject* gPyGetVehicleConstraint(PyObject* self,
if (vehicle)
{
KX_VehicleWrapper* pyWrapper = new KX_VehicleWrapper(vehicle,PHY_GetActiveEnvironment());
- return pyWrapper;
+ return pyWrapper->NewProxy(true);
}
}
@@ -440,7 +440,7 @@ static PyObject* gPyCreateConstraint(PyObject* self,
KX_ConstraintWrapper* wrap = new KX_ConstraintWrapper((enum PHY_ConstraintType)constrainttype,constraintid,PHY_GetActiveEnvironment());
- return wrap;
+ return wrap->NewProxy(true);
}
diff --git a/source/gameengine/Ketsji/KX_PythonInit.cpp b/source/gameengine/Ketsji/KX_PythonInit.cpp
index 7643a043a7c..1c3bb250b03 100644
--- a/source/gameengine/Ketsji/KX_PythonInit.cpp
+++ b/source/gameengine/Ketsji/KX_PythonInit.cpp
@@ -359,8 +359,7 @@ static STR_String gPyGetCurrentScene_doc =
"Gets a reference to the current scene.\n";
static PyObject* gPyGetCurrentScene(PyObject* self)
{
- Py_INCREF(gp_KetsjiScene);
- return (PyObject*) gp_KetsjiScene;
+ return gp_KetsjiScene->GetProxy();
}
static STR_String gPyGetSceneList_doc =
@@ -369,7 +368,6 @@ static STR_String gPyGetSceneList_doc =
static PyObject* gPyGetSceneList(PyObject* self)
{
KX_KetsjiEngine* m_engine = KX_GetActiveEngine();
- //CListValue* list = new CListValue();
PyObject* list;
KX_SceneList* scenes = m_engine->CurrentScenes();
int numScenes = scenes->size();
@@ -380,13 +378,10 @@ static PyObject* gPyGetSceneList(PyObject* self)
for (i=0;i<numScenes;i++)
{
KX_Scene* scene = scenes->at(i);
- //list->Add(scene);
- PyList_SET_ITEM(list, i, scene);
- Py_INCREF(scene);
-
+ PyList_SET_ITEM(list, i, scene->GetProxy());
}
- return (PyObject*)list;
+ return list;
}
static PyObject *pyPrintExt(PyObject *,PyObject *,PyObject *)
diff --git a/source/gameengine/Ketsji/KX_PythonInitTypes.cpp b/source/gameengine/Ketsji/KX_PythonInitTypes.cpp
index 06163ec8c4f..2bf60dbc102 100644
--- a/source/gameengine/Ketsji/KX_PythonInitTypes.cpp
+++ b/source/gameengine/Ketsji/KX_PythonInitTypes.cpp
@@ -98,7 +98,7 @@ void initPyObjectPlusType(PyTypeObject **parents)
}
#if 0
- PyObject_Print((PyObject *)parents[i], stderr, 0);
+ PyObject_Print(reinterpret_cast<PyObject *>parents[i], stderr, 0);
fprintf(stderr, "\n");
PyObject_Print(parents[i]->tp_dict, stderr, 0);
fprintf(stderr, "\n\n");
@@ -117,7 +117,7 @@ void initPyObjectPlusType(PyTypeObject **parents)
dict= parents[i]->tp_dict;
#if 1
- PyObject_Print((PyObject *)parents[i], stderr, 0);
+ PyObject_Print(reinterpret_cast<PyObject *>(parents[i]), stderr, 0);
fprintf(stderr, "\n");
PyObject_Print(parents[i]->tp_dict, stderr, 0);
fprintf(stderr, "\n\n");
@@ -135,7 +135,7 @@ static void PyType_Ready_ADD(PyObject *dict, PyTypeObject *tp, PyAttributeDef *a
PyObject *item;
PyType_Ready(tp);
- PyDict_SetItemString(dict, tp->tp_name, (PyObject *)tp);
+ PyDict_SetItemString(dict, tp->tp_name, reinterpret_cast<PyObject *>(tp));
/* store attr defs in the tp_dict for to avoid string lookups */
for(attr= attributes; attr->m_name; attr++) {
diff --git a/source/gameengine/Ketsji/KX_RaySensor.cpp b/source/gameengine/Ketsji/KX_RaySensor.cpp
index 42e2fdc3e14..9dfc8243330 100644
--- a/source/gameengine/Ketsji/KX_RaySensor.cpp
+++ b/source/gameengine/Ketsji/KX_RaySensor.cpp
@@ -375,7 +375,7 @@ PyObject* KX_RaySensor::pyattr_get_hitobject(void *self_v, const KX_PYATTRIBUTE_
{
KX_RaySensor* self = static_cast<KX_RaySensor*>(self_v);
if (self->m_hitObject)
- return self->m_hitObject->AddRef();
+ return self->m_hitObject->GetProxy();
Py_RETURN_NONE;
}
@@ -389,7 +389,7 @@ PyObject* KX_RaySensor::PyGetHitObject(PyObject* self)
ShowDeprecationWarning("getHitObject()", "the hitObject property");
if (m_hitObject)
{
- return m_hitObject->AddRef();
+ return m_hitObject->GetProxy();
}
Py_RETURN_NONE;
}
diff --git a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp
index 65b654ccba4..975e6d9d6cc 100644
--- a/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp
+++ b/source/gameengine/Ketsji/KX_SCA_AddObjectActuator.cpp
@@ -223,7 +223,7 @@ PyObject* KX_SCA_AddObjectActuator::pyattr_get_object(void *self, const struct K
if (!actuator->m_OriginalObject)
Py_RETURN_NONE;
else
- return actuator->m_OriginalObject->AddRef();
+ return actuator->m_OriginalObject->GetProxy();
}
int KX_SCA_AddObjectActuator::pyattr_set_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
@@ -251,7 +251,7 @@ PyObject* KX_SCA_AddObjectActuator::pyattr_get_objectLastCreated(void *self, con
if (!actuator->m_lastCreatedObject)
Py_RETURN_NONE;
else
- return actuator->m_lastCreatedObject->AddRef();
+ return actuator->m_lastCreatedObject->GetProxy();
}
@@ -350,7 +350,7 @@ PyObject* KX_SCA_AddObjectActuator::PyGetObject(PyObject* self, PyObject* args)
if (ret_name_only)
return PyString_FromString(m_OriginalObject->GetName());
else
- return m_OriginalObject->AddRef();
+ return m_OriginalObject->GetProxy();
}
@@ -492,8 +492,7 @@ PyObject* KX_SCA_AddObjectActuator::PyGetLastCreatedObject(PyObject* self)
// it means the object has ended, The BGE python api crashes in many places if the object is returned.
if (result && (static_cast<KX_GameObject *>(result))->GetSGNode())
{
- result->AddRef();
- return result;
+ return result->GetProxy();
}
// don't return NULL to python anymore, it gives trouble in the scripts
Py_RETURN_NONE;
diff --git a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
index 9097ca6c85e..999b017b64c 100644
--- a/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
+++ b/source/gameengine/Ketsji/KX_SCA_ReplaceMeshActuator.cpp
@@ -110,7 +110,7 @@ PyObject* KX_SCA_ReplaceMeshActuator::pyattr_get_mesh(void *self, const struct K
if (!actuator->m_mesh)
Py_RETURN_NONE;
KX_MeshProxy* meshproxy = new KX_MeshProxy(actuator->m_mesh);
- return meshproxy;
+ return meshproxy->NewProxy(true);
}
int KX_SCA_ReplaceMeshActuator::pyattr_set_mesh(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
diff --git a/source/gameengine/Ketsji/KX_Scene.cpp b/source/gameengine/Ketsji/KX_Scene.cpp
index c99fa363ffe..d8d6f215213 100644
--- a/source/gameengine/Ketsji/KX_Scene.cpp
+++ b/source/gameengine/Ketsji/KX_Scene.cpp
@@ -924,8 +924,6 @@ int KX_Scene::NewRemoveObject(class CValue* gameobj)
{
int ret;
KX_GameObject* newobj = (KX_GameObject*) gameobj;
-
- gameobj->SetZombie(true); /* disallow future python access */
// keep the blender->game object association up to date
// note that all the replicas of an object will have the same
@@ -1623,13 +1621,13 @@ PyObject* KX_Scene::pyattr_get_name(void *self_v, const KX_PYATTRIBUTE_DEF *attr
PyObject* KX_Scene::pyattr_get_objects(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef)
{
KX_Scene* self= static_cast<KX_Scene*>(self_v);
- return self->GetObjectList()->AddRef();
+ return self->GetObjectList()->GetProxy();
}
PyObject* KX_Scene::pyattr_get_active_camera(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef)
{
KX_Scene* self= static_cast<KX_Scene*>(self_v);
- return self->GetActiveCamera()->AddRef();
+ return self->GetActiveCamera()->GetProxy();
}
/* __dict__ only for the purpose of giving useful dir() results */
@@ -1717,7 +1715,7 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getLightList,
"Returns a list of all lights in the scene.\n"
)
{
- return (PyObject*) m_lightlist->AddRef();
+ return m_lightlist->GetProxy();
}
KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getObjectList,
@@ -1726,7 +1724,7 @@ KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getObjectList,
)
{
// ShowDeprecationWarning("getObjectList()", "the objects property"); // XXX Grr, why doesnt this work?
- return (PyObject*) m_objectlist->AddRef();
+ return m_objectlist->GetProxy();
}
KX_PYMETHODDEF_DOC_NOARGS(KX_Scene, getName,
@@ -1755,6 +1753,5 @@ KX_PYMETHODDEF_DOC(KX_Scene, addObject,
SCA_IObject* replica = AddReplicaObject((SCA_IObject*)ob, other, time);
- replica->AddRef();
- return replica;
+ return replica->GetProxy();
} \ No newline at end of file
diff --git a/source/gameengine/Ketsji/KX_SceneActuator.cpp b/source/gameengine/Ketsji/KX_SceneActuator.cpp
index 2d3022a68f7..b52cc81f68b 100644
--- a/source/gameengine/Ketsji/KX_SceneActuator.cpp
+++ b/source/gameengine/Ketsji/KX_SceneActuator.cpp
@@ -291,23 +291,39 @@ PyObject* KX_SceneActuator::pyattr_get_camera(void *self, const struct KX_PYATTR
KX_SceneActuator* actuator = static_cast<KX_SceneActuator*>(self);
if (!actuator->m_camera)
Py_RETURN_NONE;
- actuator->m_camera->AddRef();
- return actuator->m_camera;
+
+ return actuator->m_camera->GetProxy();
}
int KX_SceneActuator::pyattr_set_camera(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
{
KX_SceneActuator* actuator = static_cast<KX_SceneActuator*>(self);
KX_Camera *camOb;
-
+
+ if(value==Py_None)
+ {
+ if (actuator->m_camera)
+ actuator->m_camera->UnregisterActuator(actuator);
+
+ actuator->m_camera= NULL;
+ return 0;
+ }
+
if (PyObject_TypeCheck(value, &KX_Camera::Type))
{
- camOb = static_cast<KX_Camera*>(value);
+ KX_Camera *camOb= static_cast<KX_Camera*>BGE_PROXY_REF(value);
+
+ if(camOb==NULL)
+ {
+ PyErr_SetString(PyExc_RuntimeError, BGE_PROXY_ERROR_MSG);
+ return 1;
+ }
+
if (actuator->m_camera)
actuator->m_camera->UnregisterActuator(actuator);
+
actuator->m_camera = camOb;
- if (actuator->m_camera)
- actuator->m_camera->RegisterActuator(actuator);
+ actuator->m_camera->RegisterActuator(actuator);
return 0;
}
@@ -423,11 +439,21 @@ PyObject* KX_SceneActuator::PySetCamera(PyObject* self,
PyObject *cam;
if (PyArg_ParseTuple(args, "O!:setCamera", &KX_Camera::Type, &cam))
{
+ KX_Camera *new_camera;
+
+ new_camera = static_cast<KX_Camera*>BGE_PROXY_REF(cam);
+ if(new_camera==NULL)
+ {
+ PyErr_SetString(PyExc_RuntimeError, BGE_PROXY_ERROR_MSG);
+ return NULL;
+ }
+
if (m_camera)
m_camera->UnregisterActuator(this);
- m_camera = (KX_Camera*) cam;
- if (m_camera)
- m_camera->RegisterActuator(this);
+
+ m_camera= new_camera;
+
+ m_camera->RegisterActuator(this);
Py_RETURN_NONE;
}
PyErr_Clear();
diff --git a/source/gameengine/Ketsji/KX_TouchSensor.cpp b/source/gameengine/Ketsji/KX_TouchSensor.cpp
index 70fa6326c19..7265ade6789 100644
--- a/source/gameengine/Ketsji/KX_TouchSensor.cpp
+++ b/source/gameengine/Ketsji/KX_TouchSensor.cpp
@@ -342,7 +342,7 @@ PyObject* KX_TouchSensor::PyGetHitObject(PyObject* self)
/* otherwise, this leaks memory */
if (m_hitObject)
{
- return m_hitObject->AddRef();
+ return m_hitObject->GetProxy();
}
Py_RETURN_NONE;
}
@@ -356,7 +356,7 @@ PyObject* KX_TouchSensor::PyGetHitObjectList(PyObject* self)
ShowDeprecationWarning("getHitObjectList()", "the objectHitList property");
/* to do: do Py_IncRef if the object is already known in Python */
/* otherwise, this leaks memory */ /* Edit, this seems ok and not to leak memory - Campbell */
- return m_colliders->AddRef();
+ return m_colliders->GetProxy();
}
/*getTouchMaterial and setTouchMaterial were never added to the api,
@@ -400,7 +400,7 @@ PyObject* KX_TouchSensor::pyattr_get_object_hit(void *self_v, const KX_PYATTRIBU
KX_TouchSensor* self= static_cast<KX_TouchSensor*>(self_v);
if (self->m_hitObject)
- return self->m_hitObject->AddRef();
+ return self->m_hitObject->GetProxy();
else
Py_RETURN_NONE;
}
@@ -408,7 +408,7 @@ PyObject* KX_TouchSensor::pyattr_get_object_hit(void *self_v, const KX_PYATTRIBU
PyObject* KX_TouchSensor::pyattr_get_object_hit_list(void *self_v, const KX_PYATTRIBUTE_DEF *attrdef)
{
KX_TouchSensor* self= static_cast<KX_TouchSensor*>(self_v);
- return self->m_colliders->AddRef();
+ return self->m_colliders->GetProxy();
}
diff --git a/source/gameengine/Ketsji/KX_TrackToActuator.cpp b/source/gameengine/Ketsji/KX_TrackToActuator.cpp
index 29c6a21b0b3..5ea08f855a3 100644
--- a/source/gameengine/Ketsji/KX_TrackToActuator.cpp
+++ b/source/gameengine/Ketsji/KX_TrackToActuator.cpp
@@ -481,7 +481,7 @@ PyObject* KX_TrackToActuator::pyattr_get_object(void *self, const struct KX_PYAT
if (!actuator->m_object)
Py_RETURN_NONE;
else
- return actuator->m_object->AddRef();
+ return actuator->m_object->GetProxy();
}
int KX_TrackToActuator::pyattr_set_object(void *self, const struct KX_PYATTRIBUTE_DEF *attrdef, PyObject *value)
@@ -560,7 +560,7 @@ PyObject* KX_TrackToActuator::PyGetObject(PyObject* self, PyObject* args)
if (ret_name_only)
return PyString_FromString(m_object->GetName());
else
- return m_object->AddRef();
+ return m_object->GetProxy();
}
diff --git a/source/gameengine/Ketsji/KX_VehicleWrapper.cpp b/source/gameengine/Ketsji/KX_VehicleWrapper.cpp
index 98f5a1ea87d..0ba55fe5986 100644
--- a/source/gameengine/Ketsji/KX_VehicleWrapper.cpp
+++ b/source/gameengine/Ketsji/KX_VehicleWrapper.cpp
@@ -48,7 +48,10 @@ PyObject* KX_VehicleWrapper::PyAddWheel(PyObject* self,
if (PyArg_ParseTuple(args,"OOOOffi:addWheel",&wheelGameObject,&pylistPos,&pylistDir,&pylistAxleDir,&suspensionRestLength,&wheelRadius,&hasSteering))
{
- KX_GameObject* gameOb = (KX_GameObject*) wheelGameObject;
+ KX_GameObject *gameOb;
+ if (!ConvertPythonToGameObject(wheelGameObject, &gameOb, false))
+ return NULL;
+
if (gameOb->GetSGNode())
{