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. @@

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
http://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to