[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [34304] trunk/blender/source/blender/ python: misc python api improvements

Campbell Barton ideasman42 at gmail.com
Thu Jan 13 22:44:18 CET 2011


Revision: 34304
          http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=34304
Author:   campbellbarton
Date:     2011-01-13 21:44:18 +0000 (Thu, 13 Jan 2011)
Log Message:
-----------
misc python api improvements
- rna array parsing was using PySequence_Size() in a loop, this can  be slow to run so only call once.
- assigning a single value to a multi-dimensional array was missing type check.
- improve exception messages for rna array type errors.
- simplify vector slice assignment by using mathutils_array_parse(...)

Modified Paths:
--------------
    trunk/blender/source/blender/python/generic/mathutils_vector.c
    trunk/blender/source/blender/python/intern/bpy_rna_array.c

Modified: trunk/blender/source/blender/python/generic/mathutils_vector.c
===================================================================
--- trunk/blender/source/blender/python/generic/mathutils_vector.c	2011-01-13 20:16:36 UTC (rev 34303)
+++ trunk/blender/source/blender/python/generic/mathutils_vector.c	2011-01-13 21:44:18 UTC (rev 34304)
@@ -832,48 +832,28 @@
 static int Vector_ass_slice(VectorObject *self, int begin, int end,
 				 PyObject * seq)
 {
-	int i, y, size = 0;
-	float vec[4], scalar;
-	PyObject *v;
+	int y, size = 0;
+	float vec[MAX_DIMENSIONS];
 
 	if(!BaseMath_ReadCallback(self))
 		return -1;
-	
+
 	CLAMP(begin, 0, self->size);
-	if (end<0) end= self->size+end+1;
 	CLAMP(end, 0, self->size);
 	begin = MIN2(begin,end);
 
-	size = PySequence_Size(seq);
-	if(size != (end - begin)){
-		PyErr_SetString(PyExc_TypeError, "vector[begin:end] = []: size mismatch in slice assignment");
+	size = (end - begin);
+	if(mathutils_array_parse(vec, size, size, seq, "vector[begin:end] = [...]:") == -1)
 		return -1;
-	}
 
-	for (i = 0; i < size; i++) {
-		v = PySequence_GetItem(seq, i);
-		if (v == NULL) { /* Failed to read sequence */
-			PyErr_SetString(PyExc_RuntimeError, "vector[begin:end] = []: unable to read sequence");
-			return -1;
-		}
-		
-		if((scalar=PyFloat_AsDouble(v)) == -1.0f && PyErr_Occurred()) { /* parsed item not a number */
-			Py_DECREF(v);
-			PyErr_SetString(PyExc_TypeError, "vector[begin:end] = []: sequence argument not a number");
-			return -1;
-		}
-
-		vec[i] = scalar;
-		Py_DECREF(v);
-	}
 	/*parsed well - now set in vector*/
 	for(y = 0; y < size; y++){
 		self->vec[begin + y] = vec[y];
 	}
-	
+
 	if(!BaseMath_WriteCallback(self))
 		return -1;
-	
+
 	return 0;
 }
 /*------------------------NUMERIC PROTOCOLS----------------------

Modified: trunk/blender/source/blender/python/intern/bpy_rna_array.c
===================================================================
--- trunk/blender/source/blender/python/intern/bpy_rna_array.c	2011-01-13 20:16:36 UTC (rev 34303)
+++ trunk/blender/source/blender/python/intern/bpy_rna_array.c	2011-01-13 21:44:18 UTC (rev 34304)
@@ -56,15 +56,15 @@
 	/* not the last dimension */
 	if (dim + 1 < totdim) {
 		/* check that a sequence contains dimsize[dim] items */
-
-		for (i= 0; i < PySequence_Size(seq); i++) {
+		const int seq_size= PySequence_Size(seq);
+		for (i= 0; i < seq_size; i++) {
 			PyObject *item;
 			int ok= 1;
 			item= PySequence_GetItem(seq, i);
 
 			if (!PySequence_Check(item)) {
 				/* BLI_snprintf(error_str, error_str_size, "expected a sequence of %s", item_type_str); */
-				PyErr_Format(PyExc_TypeError, "%s expected a sequence of %s", error_prefix, item_type_str);
+				PyErr_Format(PyExc_TypeError, "%s expected a sequence of %s, not %s", error_prefix, item_type_str, Py_TYPE(item)->tp_name);
 				ok= 0;
 			}
 			/* arr[3][4][5]
@@ -89,14 +89,15 @@
 	}
 	else {
 		/* check that items are of correct type */
-		for (i= 0; i < PySequence_Size(seq); i++) {
+		const int seq_size= PySequence_Size(seq);
+		for (i= 0; i < seq_size; i++) {
 			PyObject *item= PySequence_GetItem(seq, i);
 
 			if (!check_item_type(item)) {
 				Py_DECREF(item);
 
 				/* BLI_snprintf(error_str, error_str_size, "sequence items should be of type %s", item_type_str); */
-				PyErr_Format(PyExc_TypeError, "sequence items should be of type %s", item_type_str);
+				PyErr_Format(PyExc_TypeError, "expected sequence items of type %s, not %s", item_type_str, Py_TYPE(item)->tp_name);
 				return 0;
 			}
 
@@ -113,8 +114,9 @@
 	int totitem= 0;
 
 	if (PySequence_Check(seq)) {
+		const int seq_size= PySequence_Size(seq);
 		int i;
-		for (i= 0; i < PySequence_Size(seq); i++) {
+		for (i= 0; i < seq_size; i++) {
 			PyObject *item= PySequence_GetItem(seq, i);
 			totitem += count_items(item);
 			Py_DECREF(item);
@@ -183,7 +185,7 @@
 
 		if (tot != len) {
 			/* BLI_snprintf(error_str, error_str_size, "sequence must have length of %d", len); */
-			PyErr_Format(PyExc_ValueError, "%s sequence must have %d items total", error_prefix, len);
+			PyErr_Format(PyExc_ValueError, "%s sequence must have %d items total, not %d", error_prefix, len, tot);
 			return 0;
 		}
 	}
@@ -227,8 +229,9 @@
 {
 	unsigned int i;
 	int totdim= RNA_property_array_dimension(ptr, prop, NULL);
+	const int seq_size= PySequence_Size(seq);
 
-	for (i= 0; i < PySequence_Size(seq); i++) {
+	for (i= 0; i < seq_size; i++) {
 		PyObject *item= PySequence_GetItem(seq, i);
 
 		if (dim + 1 < totdim) {
@@ -310,6 +313,10 @@
 	index += arrayoffset;
 
 	if(lvalue_dim == totdim) { /* single item, assign directly */
+		if(!check_item_type(py)) {
+			PyErr_Format(PyExc_TypeError, "%s expected a %s type, not %s", error_prefix, item_type_str, Py_TYPE(py)->tp_name);
+			return 0;
+		}
 		copy_value_single(py, ptr, prop, NULL, 0, &index, convert_item, rna_set_index);
 	}
 	else {
@@ -342,7 +349,7 @@
 static int py_float_check(PyObject *py)
 {
 	/* accept both floats and integers */
-	return PyFloat_Check(py) || PyLong_Check(py);
+	return PyNumber_Check(py);
 }
 
 static int py_int_check(PyObject *py)




More information about the Bf-blender-cvs mailing list