[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [19662] branches/blender2.5/blender/source /blender/makesrna/intern/rna_access.c: 2.5 / RNA

Elia Sarti vekoon at gmail.com
Sat Apr 11 17:46:35 CEST 2009


Revision: 19662
          http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=19662
Author:   vekoon
Date:     2009-04-11 17:46:35 +0200 (Sat, 11 Apr 2009)

Log Message:
-----------
2.5 / RNA
API, added support for return values for RNA_function_call_direct and completed the code. Didn't test it though.

Returns works exact the same way as other parameters for format strings except you put a R in front of it. For instance for a function that accepts two vectors and returns a vector you use a format like "f[4]f[4]Rf[4]". 
I'm thinking about allowing arbitrary white space in the format string (or use comas as separators) to make it more readable. 
The return format *must* always come last and of course the corresponding argument you pass to the function has to be a pointer so that it can be filled with the return value.

Modified Paths:
--------------
    branches/blender2.5/blender/source/blender/makesrna/intern/rna_access.c

Modified: branches/blender2.5/blender/source/blender/makesrna/intern/rna_access.c
===================================================================
--- branches/blender2.5/blender/source/blender/makesrna/intern/rna_access.c	2009-04-11 15:05:42 UTC (rev 19661)
+++ branches/blender2.5/blender/source/blender/makesrna/intern/rna_access.c	2009-04-11 15:46:35 UTC (rev 19662)
@@ -2367,6 +2367,145 @@
 	return -1;
 }
 
+static int rna_function_format_array_length(const char *format, int ofs, int flen)
+{
+	char lenbuf[16];
+	int idx= 0;
+
+	if (format[ofs++]=='[')
+		for (; ofs<flen && format[ofs]!=']' && idx<sizeof(*lenbuf)-1; idx++, ofs++)
+			lenbuf[idx]= format[ofs];
+
+	if (ofs<flen && format[ofs++]==']') {
+		/* XXX put better error reporting for ofs>=flen or idx over lenbuf capacity */
+		lenbuf[idx]= '\0';
+		return atoi(lenbuf);
+	}
+
+	return 0;
+}
+
+static int rna_function_parameter_parse(PointerRNA *ptr, PropertyRNA *prop, PropertyType type, char ftype, int len, void *dest, void *src, StructRNA *srna, const char *tid, const char *fid, const char *pid)
+{
+	/* ptr is always a function pointer, prop always a parameter */
+
+	switch (type) {
+	case PROP_BOOLEAN:
+		{
+			if (ftype!='b') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, a boolean was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			if (len==0)
+				*((int*)dest)= *((int*)src);
+			else
+				memcpy(dest, src, len*sizeof(int));
+
+			break;
+		}
+	case PROP_INT:
+		{
+			if (ftype!='i') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, an integer was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			if (len==0)
+				*((int*)dest)= *((int*)src);
+			else
+				memcpy(dest, src, len*sizeof(int));
+
+			break;
+		}
+	case PROP_FLOAT:
+		{
+			if (ftype!='f') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, a float was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			if (len==0)
+				*((float*)dest)= *((float*)src);
+			else
+				memcpy(dest, src, len*sizeof(float));
+
+			break;
+		}
+	case PROP_STRING:
+		{
+			if (ftype!='s') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, a string was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			*((char**)dest)= *((char**)src);
+
+			break;
+		}
+	case PROP_ENUM:
+		{
+			if (ftype!='e') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, an enum was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			*((int*)dest)= *((int*)src);
+
+			break;
+		}
+	case PROP_POINTER:
+		{
+			StructRNA *ptype;
+
+			if (ftype!='O') {
+				fprintf(stderr, "%s.%s: wrong type for parameter %s, an object was expected\n", tid, fid, pid);
+				return -1;
+			}
+
+			ptype= RNA_property_pointer_type(ptr, prop);
+
+			if(ptype == &RNA_AnyType) {
+				*((PointerRNA*)dest)= *((PointerRNA*)src);
+			}
+			else if (ptype!=srna) {
+				PointerRNA pptr;
+
+				RNA_pointer_create(NULL, srna, *((void**)src), &pptr);
+
+				if (!RNA_struct_is_a(&pptr, ptype)) {
+					PointerRNA tmp;
+					RNA_pointer_create(NULL, ptype, NULL, &tmp);
+
+					fprintf(stderr, "%s.%s: wrong type for parameter %s, an object of type %s was expected, passed an object of type %s\n", tid, fid, pid, RNA_struct_identifier(&tmp), RNA_struct_identifier(&pptr));
+					return -1;
+				}
+
+				*((void**)dest)= *((void**)src);
+			}
+
+			break;
+		}
+	case PROP_COLLECTION:
+		{
+			/* XXX collections are not supported yet */
+			fprintf(stderr, "%s.%s: for parameter %s, collections are not supported yet\n", tid, fid, pid);
+			return -1;
+		}
+	default: 
+		{
+			if (len==0)
+				fprintf(stderr, "%s.%s: unknown type for parameter %s\n", tid, fid, pid);
+			else
+				fprintf(stderr, "%s.%s: unknown array type for parameter %s\n", tid, fid, pid);
+
+			return -1;
+		}
+	}
+
+	return 0;
+}
+
 int RNA_function_call_direct_va(PointerRNA *ptr, FunctionRNA *func, const char *format, va_list args)
 {
 	PointerRNA funcptr;
@@ -2376,7 +2515,7 @@
 	PropertyType type;
 	int i, ofs, flen, flag, len, alen, err= 0;
 	const char *tid, *fid, *pid;
-	char ftype, lenbuf[16];
+	char ftype;
 	void **retdata;
 
 	RNA_pointer_create(NULL, &RNA_Function, func, &funcptr);
@@ -2411,164 +2550,113 @@
 		}
 
 		type= RNA_property_type(&funcptr, parm);
+		ftype= format[ofs++];
 		len= RNA_property_array_length(&funcptr, parm);
-		alen= 0;
-		ftype= format[ofs++];
+		alen= rna_function_format_array_length(format, ofs, flen);
 
-		if (len>0) {
-			int idx= 0;
-
-			if (format[ofs++]=='[')
-				for (; ofs<flen && format[ofs]!=']' && idx<sizeof(*lenbuf)-1; idx++, ofs++)
-					lenbuf[idx]= format[ofs];
-
-			if (ofs<flen && format[ofs++]==']') {
-				/* XXX put better error reporting for ofs>=flen or idx over lenbuf capacity */
-				lenbuf[idx]= '\0';
-				alen= atoi(lenbuf);
-			}
-		}
-
 		if (len!=alen) {
 			err= -1;
 			fprintf(stderr, "%s.%s: for parameter %s, was expecting an array of %i elements, passed %i elements instead\n", tid, fid, pid, len, alen);
 			break;
 		}
- 
+
 		switch (type) {
 		case PROP_BOOLEAN:
-			{
-				if (format[ofs]!='b') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, a boolean was expected\n", tid, fid, pid);
-					break;
-				}
-
-				if (len==0)
-					*((int*)iter.data)= va_arg(args, int);
-				else
-					memcpy(iter.data, va_arg(args, int*), len);
-
-				break;
-			}
 		case PROP_INT:
+		case PROP_ENUM:
 			{
-				if (format[ofs]!='i') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, an integer was expected\n", tid, fid, pid);
-					break;
-				}
-
-				if (len==0)
-					*((int*)iter.data)= va_arg(args, int);
-				else
-					memcpy(iter.data, va_arg(args, int*), len);
-
+				int arg= va_arg(args, int);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, iter.data, &arg, NULL, tid, fid, pid);
 				break;
 			}
 		case PROP_FLOAT:
 			{
-				if (format[ofs]!='f') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, a float was expected\n", tid, fid, pid);
-					break;
-				}
-
-				if (len==0)
-					*((float*)iter.data)= va_arg(args, float);
-				else
-					memcpy(iter.data, va_arg(args, float*), len);
-
+				float arg= va_arg(args, float);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, iter.data, &arg, NULL, tid, fid, pid);
 				break;
 			}
 		case PROP_STRING:
 			{
-				if (format[ofs]!='s') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, a string was expected\n", tid, fid, pid);
-					break;
-				}
-
-				*((char**)iter.data)= va_arg(args, char*);
-
+				char *arg= va_arg(args, char*);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, iter.data, &arg, NULL, tid, fid, pid);
 				break;
 			}
-		case PROP_ENUM:
+		case PROP_POINTER:
 			{
-				if (format[ofs]!='e') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, an enum was expected\n", tid, fid, pid);
-					break;
-				}
-
-				*((int*)iter.data)= va_arg(args, int);
-
+				StructRNA *srna= va_arg(args, StructRNA*);
+				void *arg= va_arg(args, void*);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, iter.data, &arg, srna, tid, fid, pid);
 				break;
 			}
-		case PROP_POINTER:
+		default:
 			{
-				StructRNA *ptype, *srna;
-				void *data;
+				/* handle errors */
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, iter.data, NULL, NULL, tid, fid, pid);
+				break;
+			}
+		}
 
-				if (format[ofs]!='O') {
-					err= -1;
-					fprintf(stderr, "%s.%s: wrong type for parameter %s, an object was expected\n", tid, fid, pid);
-					break;
-				}
+		if (err!=0)
+			break;
+	}
 
-				ptype= RNA_property_pointer_type(&funcptr, parm);
-				/* for objects we use two parms: the first is the type and the second is the data */
-				srna= va_arg(args, StructRNA*);
+	if (err==0)
+		err= RNA_function_call(ptr, func, parms);
 
-				if(ptype == &RNA_AnyType) {
-					*((PointerRNA*)iter.data)= va_arg(args, PointerRNA);
-				}
-				else if (ptype!=srna) {
-					PointerRNA pptr;
+	/* XXX throw error when more parameters than those needed are passed or leave silent? */
+	if (err==0 && pret && ofs<flen && format[ofs++]=='R') {
+		parm= pret;
 
-					data= va_arg(args, void*);
-					RNA_pointer_create(NULL, srna, data, &pptr);
+		type= RNA_property_type(&funcptr, parm);
+		ftype= format[ofs++];
+		len= RNA_property_array_length(&funcptr, parm);
+		alen= rna_function_format_array_length(format, ofs, flen);
 
-					if (!RNA_struct_is_a(&pptr, ptype)) {
-						PointerRNA tmp;
-						RNA_pointer_create(NULL, ptype, NULL, &tmp);
+		if (len!=alen) {
+			err= -1;
+			fprintf(stderr, "%s.%s: for return parameter %s, was expecting an array of %i elements, passed %i elements instead\n", tid, fid, pid, len, alen);
+			break;
+		}
 
-						err= -1;
-						fprintf(stderr, "%s.%s: wrong type for parameter %s, an object of type %s was expected, passed an object of type %s\n", tid, fid, pid, RNA_struct_identifier(&tmp), RNA_struct_identifier(&pptr));
-						break;
-					}
-
-					*((void**)iter.data)= data;
-				}
-
+		switch (type) {
+		case PROP_BOOLEAN:
+		case PROP_INT:
+		case PROP_ENUM:
+			{
+				int *arg= va_arg(args, int*);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, arg, retdata, NULL, tid, fid, pid);
 				break;
 			}
-		case PROP_COLLECTION:
+		case PROP_FLOAT:
 			{
-				/* XXX collections are not supported yet */
-				err= -1;
-				fprintf(stderr, "%s.%s: for parameter %s, collections are not supported yet\n", tid, fid, pid);
+				float *arg= va_arg(args, float*);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, arg, retdata, NULL, tid, fid, pid);
 				break;
 			}
-		default: 
+		case PROP_STRING:
 			{
-				err= -1;
-				if (len==0)
-					fprintf(stderr, "%s.%s: unknown type for parameter %s\n", tid, fid, pid);
-				else
-					fprintf(stderr, "%s.%s: unknown array type for parameter %s\n", tid, fid, pid);
-
+				char **arg= va_arg(args, char**);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, arg, retdata, NULL, tid, fid, pid);
 				break;
 			}
+		case PROP_POINTER:
+			{
+				StructRNA *srna= va_arg(args, StructRNA*);
+				void **arg= va_arg(args, void**);
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, arg, retdata, srna, tid, fid, pid);
+				break;
+			}
+		default:
+			{
+				/* handle errors */
+				err= rna_function_parameter_parse(&funcptr, parm, type, ftype, len, arg, NULL, NULL, tid, fid, pid);
+				break;
+			}
 		}
-
-		if (err!=0)
-			break;
 	}
 
-	if (err==0 && pret) {

@@ Diff output truncated at 10240 characters. @@




More information about the Bf-blender-cvs mailing list