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>2011-02-14 14:30:35 +0300
committerCampbell Barton <ideasman42@gmail.com>2011-02-14 14:30:35 +0300
commitd845d6308a241099f5816eed7e747c38762c4a02 (patch)
tree0bcee9d09475518c2e93264ab218e8038961dd71 /source/blender/python
parenta3c2ad34b102d7e0cd23c879578aae70873efa1b (diff)
comments for how py-rna calls api new classes. small speedup for StructRNA.__new__(...) used for creating new classes and corrected exception type.
Diffstat (limited to 'source/blender/python')
-rw-r--r--source/blender/python/intern/bpy_rna.c55
1 files changed, 41 insertions, 14 deletions
diff --git a/source/blender/python/intern/bpy_rna.c b/source/blender/python/intern/bpy_rna.c
index a32f38438f8..e3118ecd057 100644
--- a/source/blender/python/intern/bpy_rna.c
+++ b/source/blender/python/intern/bpy_rna.c
@@ -3677,23 +3677,42 @@ static struct PyMethodDef pyrna_prop_collection_idprop_methods[] = {
/* only needed for subtyping, so a new class gets a valid BPy_StructRNA
* todo - also accept useful args */
-static PyObject * pyrna_struct_new(PyTypeObject *type, PyObject *args, PyObject *UNUSED(kwds)) {
-
- BPy_StructRNA *base;
+static PyObject * pyrna_struct_new(PyTypeObject *type, PyObject *args, PyObject *UNUSED(kwds))
+{
+ if(PyTuple_GET_SIZE(args) == 1) {
+ BPy_StructRNA *base= (BPy_StructRNA *)PyTuple_GET_ITEM(args, 0);
+ if (type == Py_TYPE(base)) {
+ Py_INCREF(base);
+ return (PyObject *)base;
+ }
+ else if (PyType_IsSubtype(type, &pyrna_struct_Type)) {
+ /* this almost never runs, only when using user defined subclasses of built-in object.
+ * this isnt common since its NOT related to registerable subclasses. eg:
+
+ >>> class MyObSubclass(bpy.types.Object):
+ ... def test_func(self):
+ ... print(100)
+ ...
+ >>> myob = MyObSubclass(bpy.context.object)
+ >>> myob.test_func()
+ 100
+ *
+ * Keep this since it could be useful.
+ */
+ BPy_StructRNA *ret;
+ if((ret= (BPy_StructRNA *)type->tp_alloc(type, 0))) {
+ ret->ptr = base->ptr;
+ }
+ /* pass on exception & NULL if tp_alloc fails */
+ return (PyObject *)ret;
+ }
- if (!PyArg_ParseTuple(args, "O!:bpy_struct.__new__", &pyrna_struct_Type, &base))
+ /* error, invalid type given */
+ PyErr_Format(PyExc_TypeError, "bpy_struct.__new__(type): type '%.200s' is not a subtype of bpy_struct", type->tp_name);
return NULL;
-
- if (type == Py_TYPE(base)) {
- Py_INCREF(base);
- return (PyObject *)base;
- } else if (PyType_IsSubtype(type, &pyrna_struct_Type)) {
- BPy_StructRNA *ret = (BPy_StructRNA *) type->tp_alloc(type, 0);
- ret->ptr = base->ptr;
- return (PyObject *)ret;
}
else {
- PyErr_Format(PyExc_TypeError, "bpy_struct.__new__(type): type '%.200s' is not a subtype of bpy_struct", type->tp_name);
+ PyErr_Format(PyExc_TypeError, "bpy_struct.__new__(type): expected a single argument");
return NULL;
}
}
@@ -5310,7 +5329,7 @@ static int bpy_class_validate(PointerRNA *dummyptr, void *py_data, int *have_fun
func_arg_count++;
if (arg_count != func_arg_count) {
- PyErr_Format(PyExc_AttributeError, "expected %.200s, %.200s class \"%.200s\" function to have %d args, found %d", class_type, py_class_name, RNA_function_identifier(func), func_arg_count, arg_count);
+ PyErr_Format(PyExc_ValueError, "expected %.200s, %.200s class \"%.200s\" function to have %d args, found %d", class_type, py_class_name, RNA_function_identifier(func), func_arg_count, arg_count);
return -1;
}
}
@@ -5438,6 +5457,14 @@ static int bpy_class_call(bContext *C, PointerRNA *ptr, FunctionRNA *func, Param
py_class_instance = NULL;
}
else {
+ /* 'almost' all the time calling the class isnt needed.
+ * We could just do...
+ py_class_instance = py_srna;
+ Py_INCREF(py_class_instance);
+ * This would work fine but means __init__ functions wouldnt run.
+ * none of blenders default scripts use __init__ but its nice to call it
+ * for general correctness. just to note why this is here when it could be safely removed.
+ */
args = PyTuple_New(1);
PyTuple_SET_ITEM(args, 0, py_srna);
py_class_instance= PyObject_Call(py_class, args, NULL);