Code style edits (mostly spliting long lines, and removing trailing spaces).
[blender-staging.git] / source / blender / makesrna / intern / rna_define.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * Contributor(s): Blender Foundation (2008).
19  *
20  * ***** END GPL LICENSE BLOCK *****
21  */
22
23 /** \file blender/makesrna/intern/rna_define.c
24  *  \ingroup RNA
25  */
26
27
28 #include <float.h>
29 #include <limits.h>
30 #include <stdio.h>
31 #include <stdlib.h>
32 #include <string.h>
33 #include <ctype.h>
34
35 #include "MEM_guardedalloc.h"
36
37 #include "DNA_genfile.h"
38 #include "DNA_sdna_types.h"
39
40 #include "BLI_utildefines.h"
41 #include "BLI_ghash.h"
42
43 #include "RNA_define.h"
44
45 #include "rna_internal.h"
46
47 /* Global used during defining */
48
49 BlenderDefRNA DefRNA = {NULL, {NULL, NULL}, {NULL, NULL}, NULL, 0, 0, 0, 1};
50
51 /* Duplicated code since we can't link in blenkernel or blenlib */
52
53 #ifndef MIN2
54 #define MIN2(x,y) ((x)<(y)? (x): (y))
55 #define MAX2(x,y) ((x)>(y)? (x): (y))
56 #endif
57
58 /* pedantic check for '.', do this since its a hassle for translators */
59 #ifndef NDEBUG
60 #  define DESCR_CHECK(description, id1, id2)                                  \
61         if (description && (description)[0]) {                                    \
62                 int i = strlen(description);                                          \
63                 if ((description)[i - 1] == '.') {                                    \
64                         fprintf(stderr, "%s: '%s' '%s' description ends with a '.' !\n",  \
65                                 __func__, id1 ? id1 : "", id2 ? id2 : "");                \
66                 }                                                                     \
67         }                                                                         \
68
69 #else
70 #  define DESCR_CHECK(description, id1, id2)
71 #endif
72
73 void rna_addtail(ListBase *listbase, void *vlink)
74 {
75         Link *link = vlink;
76
77         link->next = NULL;
78         link->prev = listbase->last;
79
80         if (listbase->last) ((Link *)listbase->last)->next = link;
81         if (listbase->first == NULL) listbase->first = link;
82         listbase->last = link;
83 }
84
85 static void rna_remlink(ListBase *listbase, void *vlink)
86 {
87         Link *link = vlink;
88
89         if (link->next) link->next->prev = link->prev;
90         if (link->prev) link->prev->next = link->next;
91
92         if (listbase->last == link) listbase->last = link->prev;
93         if (listbase->first == link) listbase->first = link->next;
94 }
95
96 PropertyDefRNA *rna_findlink(ListBase *listbase, const char *identifier)
97 {
98         Link *link;
99
100         for (link = listbase->first; link; link = link->next) {
101                 PropertyRNA *prop = ((PropertyDefRNA *)link)->prop;
102                 if (prop && (strcmp(prop->identifier, identifier) == 0)) {
103                         return (PropertyDefRNA *)link;
104                 }
105         }
106
107         return NULL;
108 }
109
110 void rna_freelinkN(ListBase *listbase, void *vlink)
111 {
112         rna_remlink(listbase, vlink);
113         MEM_freeN(vlink);
114 }
115
116 void rna_freelistN(ListBase *listbase)
117 {
118         Link *link, *next;
119         
120         for (link = listbase->first; link; link = next) {
121                 next = link->next;
122                 MEM_freeN(link);
123         }
124         
125         listbase->first = listbase->last = NULL;
126 }
127
128 StructDefRNA *rna_find_struct_def(StructRNA *srna)
129 {
130         StructDefRNA *dsrna;
131
132         if (!DefRNA.preprocess) {
133                 /* we should never get here */
134                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
135                 return NULL;
136         }
137
138         dsrna = DefRNA.structs.last;
139         for (; dsrna; dsrna = dsrna->cont.prev)
140                 if (dsrna->srna == srna)
141                         return dsrna;
142
143         return NULL;
144 }
145
146 PropertyDefRNA *rna_find_struct_property_def(StructRNA *srna, PropertyRNA *prop)
147 {
148         StructDefRNA *dsrna;
149         PropertyDefRNA *dprop;
150
151         if (!DefRNA.preprocess) {
152                 /* we should never get here */
153                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
154                 return NULL;
155         }
156
157         dsrna = rna_find_struct_def(srna);
158         dprop = dsrna->cont.properties.last;
159         for (; dprop; dprop = dprop->prev)
160                 if (dprop->prop == prop)
161                         return dprop;
162
163         dsrna = DefRNA.structs.last;
164         for (; dsrna; dsrna = dsrna->cont.prev) {
165                 dprop = dsrna->cont.properties.last;
166                 for (; dprop; dprop = dprop->prev)
167                         if (dprop->prop == prop)
168                                 return dprop;
169         }
170
171         return NULL;
172 }
173
174 #if 0
175 static PropertyDefRNA *rna_find_property_def(PropertyRNA *prop)
176 {
177         PropertyDefRNA *dprop;
178
179         if (!DefRNA.preprocess) {
180                 /* we should never get here */
181                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
182                 return NULL;
183         }
184
185         dprop = rna_find_struct_property_def(DefRNA.laststruct, prop);
186         if (dprop)
187                 return dprop;
188
189         dprop = rna_find_parameter_def(prop);
190         if (dprop)
191                 return dprop;
192
193         return NULL;
194 }
195 #endif
196
197 FunctionDefRNA *rna_find_function_def(FunctionRNA *func)
198 {
199         StructDefRNA *dsrna;
200         FunctionDefRNA *dfunc;
201
202         if (!DefRNA.preprocess) {
203                 /* we should never get here */
204                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
205                 return NULL;
206         }
207
208         dsrna = rna_find_struct_def(DefRNA.laststruct);
209         dfunc = dsrna->functions.last;
210         for (; dfunc; dfunc = dfunc->cont.prev)
211                 if (dfunc->func == func)
212                         return dfunc;
213
214         dsrna = DefRNA.structs.last;
215         for (; dsrna; dsrna = dsrna->cont.prev) {
216                 dfunc = dsrna->functions.last;
217                 for (; dfunc; dfunc = dfunc->cont.prev)
218                         if (dfunc->func == func)
219                                 return dfunc;
220         }
221
222         return NULL;
223 }
224
225 PropertyDefRNA *rna_find_parameter_def(PropertyRNA *parm)
226 {
227         StructDefRNA *dsrna;
228         FunctionDefRNA *dfunc;
229         PropertyDefRNA *dparm;
230
231         if (!DefRNA.preprocess) {
232                 /* we should never get here */
233                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
234                 return NULL;
235         }
236
237         dsrna = rna_find_struct_def(DefRNA.laststruct);
238         dfunc = dsrna->functions.last;
239         for (; dfunc; dfunc = dfunc->cont.prev) {
240                 dparm = dfunc->cont.properties.last;
241                 for (; dparm; dparm = dparm->prev)
242                         if (dparm->prop == parm)
243                                 return dparm;
244         }
245
246         dsrna = DefRNA.structs.last;
247         for (; dsrna; dsrna = dsrna->cont.prev) {
248                 dfunc = dsrna->functions.last;
249                 for (; dfunc; dfunc = dfunc->cont.prev) {
250                         dparm = dfunc->cont.properties.last;
251                         for (; dparm; dparm = dparm->prev)
252                                 if (dparm->prop == parm)
253                                         return dparm;
254                 }
255         }
256
257         return NULL;
258 }
259
260 static ContainerDefRNA *rna_find_container_def(ContainerRNA *cont)
261 {
262         StructDefRNA *ds;
263         FunctionDefRNA *dfunc;
264
265         if (!DefRNA.preprocess) {
266                 /* we should never get here */
267                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
268                 return NULL;
269         }
270
271         ds = rna_find_struct_def((StructRNA*)cont);
272         if (ds)
273                 return &ds->cont;
274
275         dfunc = rna_find_function_def((FunctionRNA*)cont);
276         if (dfunc)
277                 return &dfunc->cont;
278
279         return NULL;
280 }
281
282 /* DNA utility function for looking up members */
283
284 typedef struct DNAStructMember {
285         const char *type;
286         const char *name;
287         int arraylength;
288         int pointerlevel;
289 } DNAStructMember;
290
291 static int rna_member_cmp(const char *name, const char *oname)
292 {
293         int a = 0;
294         
295         /* compare without pointer or array part */
296         while (name[0] =='*')
297                 name++;
298         while (oname[0] =='*')
299                 oname++;
300         
301         while (1) {
302                 if (name[a] =='[' && oname[a] == 0) return 1;
303                 if (name[a] =='[' && oname[a] =='[') return 1;
304                 if (name[a] == 0) break;
305                 if (name[a] != oname[a]) return 0;
306                 a++;
307         }
308         if (name[a] == 0 && oname[a] == '.') return 2;
309         if (name[a] == 0 && oname[a] == '-' && oname[a+1] == '>') return 3;
310
311         return (name[a] == oname[a]);
312 }
313
314 static int rna_find_sdna_member(SDNA *sdna, const char *structname, const char *membername, DNAStructMember *smember)
315 {
316         const char *dnaname;
317         short *sp;
318         int a, b, structnr, totmember, cmp;
319
320         structnr = DNA_struct_find_nr(sdna, structname);
321         if (structnr == -1)
322                 return 0;
323
324         sp = sdna->structs[structnr];
325         totmember = sp[1];
326         sp += 2;
327
328         for (a = 0; a<totmember; a++, sp += 2) {
329                 dnaname = sdna->names[sp[1]];
330
331                 cmp = rna_member_cmp(dnaname, membername);
332
333                 if (cmp == 1) {
334                         smember->type = sdna->types[sp[0]];
335                         smember->name = dnaname;
336
337                         if (strstr(membername, "["))
338                                 smember->arraylength = 0;
339                         else
340                                 smember->arraylength = DNA_elem_array_size(smember->name, strlen(smember->name));
341
342                         smember->pointerlevel = 0;
343                         for (b = 0; dnaname[b] == '*'; b++)
344                                 smember->pointerlevel++;
345
346                         return 1;
347                 }
348                 else if (cmp == 2) {
349                         smember->type = "";
350                         smember->name = dnaname;
351                         smember->pointerlevel = 0;
352                         smember->arraylength = 0;
353
354                         membername = strstr(membername, ".") + strlen(".");
355                         rna_find_sdna_member(sdna, sdna->types[sp[0]], membername, smember);
356
357                         return 1;
358                 }
359                 else if (cmp == 3) {
360                         smember->type = "";
361                         smember->name = dnaname;
362                         smember->pointerlevel = 0;
363                         smember->arraylength = 0;
364
365                         membername = strstr(membername, "->") + strlen("->");
366                         rna_find_sdna_member(sdna, sdna->types[sp[0]], membername, smember);
367
368                         return 1;
369                 }
370         }
371
372         return 0;
373 }
374
375 static int rna_validate_identifier(const char *identifier, char *error, int property)
376 {
377         int a = 0;
378         
379         /*  list from http://docs.python.org/reference/lexical_analysis.html#id5 */
380         static const char *kwlist[] = {
381                 "and", "as", "assert", "break",
382                 "class", "continue", "def", "del",
383                 "elif", "else", "except", "exec",
384                 "finally", "for", "from", "global",
385                 "if", "import", "in", "is",
386                 "lambda", "not", "or", "pass",
387                 "print", "raise", "return", "try",
388                 "while", "with", "yield", NULL
389         };
390         
391         
392         if (!isalpha(identifier[0])) {
393                 strcpy(error, "first character failed isalpha() check");
394                 return 0;
395         }
396         
397         for (a = 0; identifier[a]; a++) {
398                 if (DefRNA.preprocess && property) {
399                         if (isalpha(identifier[a]) && isupper(identifier[a])) {
400                                 strcpy(error, "property names must contain lower case characters only");
401                                 return 0;
402                         }
403                 }
404                 
405                 if (identifier[a] =='_') {
406                         continue;
407                 }
408
409                 if (identifier[a] ==' ') {
410                         strcpy(error, "spaces are not okay in identifier names");
411                         return 0;
412                 }
413
414                 if (isalnum(identifier[a]) == 0) {
415                         strcpy(error, "one of the characters failed an isalnum() check and is not an underscore");
416                         return 0;
417                 }
418         }
419         
420         for (a = 0; kwlist[a]; a++) {
421                 if (strcmp(identifier, kwlist[a]) == 0) {
422                         strcpy(error, "this keyword is reserved by python");
423                         return 0;
424                 }
425         }
426
427         if (property) {
428                 static const char *kwlist_prop[] = {
429                         /* not keywords but reserved all the same because py uses */
430                         "keys", "values", "items", "get",
431                         NULL
432                 };
433
434                 for (a = 0; kwlist_prop[a]; a++) {
435                         if (strcmp(identifier, kwlist_prop[a]) == 0) {
436                                 strcpy(error, "this keyword is reserved by python");
437                                 return 0;
438                         }
439                 }
440         }
441         
442         return 1;
443 }
444
445 /* Blender Data Definition */
446
447 BlenderRNA *RNA_create(void)
448 {
449         BlenderRNA *brna;
450
451         brna = MEM_callocN(sizeof(BlenderRNA), "BlenderRNA");
452
453         DefRNA.sdna = DNA_sdna_from_data(DNAstr,  DNAlen, 0);
454         DefRNA.structs.first = DefRNA.structs.last = NULL;
455         DefRNA.error = 0;
456         DefRNA.preprocess = 1;
457
458         return brna;
459 }
460
461 void RNA_define_free(BlenderRNA *UNUSED(brna))
462 {
463         StructDefRNA *ds;
464         FunctionDefRNA *dfunc;
465         AllocDefRNA *alloc;
466
467         for (alloc = DefRNA.allocs.first; alloc; alloc = alloc->next)
468                 MEM_freeN(alloc->mem);
469         rna_freelistN(&DefRNA.allocs);
470
471         for (ds = DefRNA.structs.first; ds; ds = ds->cont.next) {
472                 for (dfunc = ds->functions.first; dfunc; dfunc = dfunc->cont.next)
473                         rna_freelistN(&dfunc->cont.properties);
474
475                 rna_freelistN(&ds->cont.properties);
476                 rna_freelistN(&ds->functions);
477         }
478
479         rna_freelistN(&DefRNA.structs);
480
481         if (DefRNA.sdna) {
482                 DNA_sdna_free(DefRNA.sdna);
483                 DefRNA.sdna = NULL;
484         }
485
486         DefRNA.error = 0;
487 }
488
489 void RNA_define_verify_sdna(int verify)
490 {
491         DefRNA.verify = verify;
492 }
493
494 void RNA_struct_free_extension(StructRNA *srna, ExtensionRNA *ext)
495 {
496 #ifdef RNA_RUNTIME
497         ext->free(ext->data);                   /* decref's the PyObject that the srna owns */
498         RNA_struct_blender_type_set(srna, NULL); /* this gets accessed again - XXX fixme */
499         RNA_struct_py_type_set(srna, NULL);     /* NULL the srna's value so RNA_struct_free wont complain of a leak */
500 #endif
501 }
502
503 void RNA_struct_free(BlenderRNA *brna, StructRNA *srna)
504 {
505 #ifdef RNA_RUNTIME
506         FunctionRNA *func, *nextfunc;
507         PropertyRNA *prop, *nextprop;
508         PropertyRNA *parm, *nextparm;
509
510         /*
511         if(srna->flag & STRUCT_RUNTIME) {
512                 if(RNA_struct_py_type_get(srna)) {
513                         fprintf(stderr, "%s '%s' freed while holding a python reference\n", __func__, srna->identifier);
514                 }
515         } */
516
517         for (prop = srna->cont.properties.first; prop; prop = nextprop) {
518                 nextprop = prop->next;
519
520                 RNA_def_property_free_pointers(prop);
521
522                 if (prop->flag & PROP_RUNTIME)
523                         rna_freelinkN(&srna->cont.properties, prop);
524         }
525
526         for (func = srna->functions.first; func; func = nextfunc) {
527                 nextfunc = func->cont.next;
528
529                 for (parm = func->cont.properties.first; parm; parm = nextparm) {
530                         nextparm = parm->next;
531
532                         RNA_def_property_free_pointers(parm);
533
534                         if (parm->flag & PROP_RUNTIME)
535                                 rna_freelinkN(&func->cont.properties, parm);
536                 }
537
538                 RNA_def_func_free_pointers(func);
539
540                 if (func->flag & FUNC_RUNTIME)
541                         rna_freelinkN(&srna->functions, func);
542         }
543
544         RNA_def_struct_free_pointers(srna);
545
546         if (srna->flag & STRUCT_RUNTIME)
547                 rna_freelinkN(&brna->structs, srna);
548
549 #endif
550 }
551
552 void RNA_free(BlenderRNA *brna)
553 {
554         StructRNA *srna, *nextsrna;
555         FunctionRNA *func;
556
557         if (DefRNA.preprocess) {
558                 RNA_define_free(brna);
559
560                 for (srna = brna->structs.first; srna; srna = srna->cont.next) {
561                         for (func = srna->functions.first; func; func = func->cont.next)
562                                 rna_freelistN(&func->cont.properties);
563
564                         rna_freelistN(&srna->cont.properties);
565                         rna_freelistN(&srna->functions);
566                 }
567
568                 rna_freelistN(&brna->structs);
569                 
570                 MEM_freeN(brna);
571         }
572         else {
573                 for (srna = brna->structs.first; srna; srna = nextsrna) {
574                         nextsrna = srna->cont.next;
575                         RNA_struct_free(brna, srna);
576                 }
577         }
578 }
579
580 static size_t rna_property_type_sizeof(PropertyType type)
581 {
582         switch (type) {
583                 case PROP_BOOLEAN: return sizeof(BoolPropertyRNA);
584                 case PROP_INT: return sizeof(IntPropertyRNA);
585                 case PROP_FLOAT: return sizeof(FloatPropertyRNA);
586                 case PROP_STRING: return sizeof(StringPropertyRNA);
587                 case PROP_ENUM: return sizeof(EnumPropertyRNA);
588                 case PROP_POINTER: return sizeof(PointerPropertyRNA);
589                 case PROP_COLLECTION: return sizeof(CollectionPropertyRNA);
590                 default: return 0;
591         }
592 }
593
594 static StructDefRNA *rna_find_def_struct(StructRNA *srna)
595 {
596         StructDefRNA *ds;
597
598         for (ds = DefRNA.structs.first; ds; ds = ds->cont.next)
599                 if (ds->srna == srna)
600                         return ds;
601
602         return NULL;
603 }
604
605 /* Struct Definition */
606
607 StructRNA *RNA_def_struct(BlenderRNA *brna, const char *identifier, const char *from)
608 {
609         StructRNA *srna, *srnafrom = NULL;
610         StructDefRNA *ds = NULL, *dsfrom = NULL;
611         PropertyRNA *prop;
612         
613         if (DefRNA.preprocess) {
614                 char error[512];
615
616                 if (rna_validate_identifier(identifier, error, 0) == 0) {
617                         fprintf(stderr, "%s: struct identifier \"%s\" error - %s\n", __func__, identifier, error);
618                         DefRNA.error = 1;
619                 }
620         }
621         
622         if (from) {
623                 /* find struct to derive from */
624                 for (srnafrom = brna->structs.first; srnafrom; srnafrom = srnafrom->cont.next)
625                         if (strcmp(srnafrom->identifier, from) == 0)
626                                 break;
627
628                 if (!srnafrom) {
629                         fprintf(stderr, "%s: struct %s not found to define %s.\n", __func__, from, identifier);
630                         DefRNA.error = 1;
631                 }
632         }
633
634         srna = MEM_callocN(sizeof(StructRNA), "StructRNA");
635         DefRNA.laststruct = srna;
636
637         if (srnafrom) {
638                 /* copy from struct to derive stuff, a bit clumsy since we can't
639                  * use MEM_dupallocN, data structs may not be alloced but builtin */
640                 memcpy(srna, srnafrom, sizeof(StructRNA));
641                 srna->cont.prophash = NULL;
642                 srna->cont.properties.first = srna->cont.properties.last = NULL;
643                 srna->functions.first = srna->functions.last = NULL;
644                 srna->py_type = NULL;
645
646                 if (DefRNA.preprocess) {
647                         srna->base = srnafrom;
648                         dsfrom = rna_find_def_struct(srnafrom);
649                 }
650                 else
651                         srna->base = srnafrom;
652         }
653         
654         srna->identifier = identifier;
655         srna->name = identifier; /* may be overwritten later RNA_def_struct_ui_text */
656         srna->description = "";
657         srna->flag |= STRUCT_UNDO;
658         if (!srnafrom)
659                 srna->icon = ICON_DOT;
660
661         rna_addtail(&brna->structs, srna);
662
663         if (DefRNA.preprocess) {
664                 ds = MEM_callocN(sizeof(StructDefRNA), "StructDefRNA");
665                 ds->srna = srna;
666                 rna_addtail(&DefRNA.structs, ds);
667
668                 if (dsfrom)
669                         ds->dnafromname = dsfrom->dnaname;
670         }
671
672         /* in preprocess, try to find sdna */
673         if (DefRNA.preprocess)
674                 RNA_def_struct_sdna(srna, srna->identifier);
675         else
676                 srna->flag |= STRUCT_RUNTIME;
677
678         if (srnafrom) {
679                 srna->nameproperty = srnafrom->nameproperty;
680                 srna->iteratorproperty = srnafrom->iteratorproperty;
681         }
682         else {
683                 /* define some builtin properties */
684                 prop = RNA_def_property(&srna->cont, "rna_properties", PROP_COLLECTION, PROP_NONE);
685                 RNA_def_property_flag(prop, PROP_BUILTIN);
686                 RNA_def_property_ui_text(prop, "Properties", "RNA property collection");
687
688                 if (DefRNA.preprocess) {
689                         RNA_def_property_struct_type(prop, "Property");
690                         RNA_def_property_collection_funcs(prop, "rna_builtin_properties_begin", "rna_builtin_properties_next",
691                                                           "rna_iterator_listbase_end", "rna_builtin_properties_get", NULL, NULL,
692                                                           "rna_builtin_properties_lookup_string", NULL);
693                 }
694                 else {
695 #ifdef RNA_RUNTIME
696                         CollectionPropertyRNA *cprop = (CollectionPropertyRNA*)prop;
697                         cprop->begin = rna_builtin_properties_begin;
698                         cprop->next = rna_builtin_properties_next;
699                         cprop->get = rna_builtin_properties_get;
700                         cprop->item_type = &RNA_Property;
701 #endif
702                 }
703
704                 prop = RNA_def_property(&srna->cont, "rna_type", PROP_POINTER, PROP_NONE);
705                 RNA_def_property_flag(prop, PROP_HIDDEN);
706                 RNA_def_property_ui_text(prop, "RNA", "RNA type definition");
707
708                 if (DefRNA.preprocess) {
709                         RNA_def_property_struct_type(prop, "Struct");
710                         RNA_def_property_pointer_funcs(prop, "rna_builtin_type_get", NULL, NULL, NULL);
711                 }
712                 else {
713 #ifdef RNA_RUNTIME
714                         PointerPropertyRNA *pprop = (PointerPropertyRNA*)prop;
715                         pprop->get = rna_builtin_type_get;
716                         pprop->type = &RNA_Struct;
717 #endif
718                 }
719         }
720
721         return srna;
722 }
723
724 void RNA_def_struct_sdna(StructRNA *srna, const char *structname)
725 {
726         StructDefRNA *ds;
727
728         if (!DefRNA.preprocess) {
729                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
730                 return;
731         }
732
733         ds = rna_find_def_struct(srna);
734
735         if (!DNA_struct_find_nr(DefRNA.sdna, structname)) {
736                 if (!DefRNA.silent) {
737                         fprintf(stderr, "%s: %s not found.\n", __func__, structname);
738                         DefRNA.error = 1;
739                 }
740                 return;
741         }
742
743         ds->dnaname = structname;
744 }
745
746 void RNA_def_struct_sdna_from(StructRNA *srna, const char *structname, const char *propname)
747 {
748         StructDefRNA *ds;
749
750         if (!DefRNA.preprocess) {
751                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
752                 return;
753         }
754
755         ds = rna_find_def_struct(srna);
756
757         if (!ds->dnaname) {
758                 fprintf(stderr, "%s: %s base struct must know DNA already.\n", __func__, structname);
759                 return;
760         }
761
762         if (!DNA_struct_find_nr(DefRNA.sdna, structname)) {
763                 if (!DefRNA.silent) {
764                         fprintf(stderr, "%s: %s not found.\n", __func__, structname);
765                         DefRNA.error = 1;
766                 }
767                 return;
768         }
769
770         ds->dnafromprop = propname;
771         ds->dnaname = structname;
772 }
773
774 void RNA_def_struct_name_property(struct StructRNA *srna, struct PropertyRNA *prop)
775 {
776         if (prop->type != PROP_STRING) {
777                 fprintf(stderr, "%s: \"%s.%s\", must be a string property.\n", __func__, srna->identifier, prop->identifier);
778                 DefRNA.error = 1;
779         }
780         else
781                 srna->nameproperty = prop;
782 }
783
784 void RNA_def_struct_nested(BlenderRNA *brna, StructRNA *srna, const char *structname)
785 {
786         StructRNA *srnafrom;
787
788         /* find struct to derive from */
789         for (srnafrom = brna->structs.first; srnafrom; srnafrom = srnafrom->cont.next)
790                 if (strcmp(srnafrom->identifier, structname) == 0)
791                         break;
792
793         if (!srnafrom) {
794                 fprintf(stderr, "%s: struct %s not found for %s.\n", __func__, structname, srna->identifier);
795                 DefRNA.error = 1;
796         }
797
798         srna->nested = srnafrom;
799 }
800
801 void RNA_def_struct_flag(StructRNA *srna, int flag)
802 {
803         srna->flag |= flag;
804 }
805
806 void RNA_def_struct_clear_flag(StructRNA *srna, int flag)
807 {
808         srna->flag &= ~flag;
809 }
810
811 void RNA_def_struct_refine_func(StructRNA *srna, const char *refine)
812 {
813         if (!DefRNA.preprocess) {
814                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
815                 return;
816         }
817
818         if (refine) srna->refine = (StructRefineFunc)refine;
819 }
820
821 void RNA_def_struct_idprops_func(StructRNA *srna, const char *idproperties)
822 {
823         if (!DefRNA.preprocess) {
824                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
825                 return;
826         }
827
828         if (idproperties) srna->idproperties = (IDPropertiesFunc)idproperties;
829 }
830
831 void RNA_def_struct_register_funcs(StructRNA *srna, const char *reg, const char *unreg, const char *instance)
832 {
833         if (!DefRNA.preprocess) {
834                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
835                 return;
836         }
837
838         if (reg) srna->reg = (StructRegisterFunc)reg;
839         if (unreg) srna->unreg = (StructUnregisterFunc)unreg;
840         if (instance) srna->instance = (StructInstanceFunc)instance;
841 }
842
843 void RNA_def_struct_path_func(StructRNA *srna, const char *path)
844 {
845         if (!DefRNA.preprocess) {
846                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
847                 return;
848         }
849
850         if (path) srna->path = (StructPathFunc)path;
851 }
852
853 void RNA_def_struct_identifier(StructRNA *srna, const char *identifier)
854 {
855         if (DefRNA.preprocess) {
856                 fprintf(stderr, "%s: only at runtime.\n", __func__);
857                 return;
858         }
859
860         srna->identifier = identifier;
861 }
862
863 void RNA_def_struct_ui_text(StructRNA *srna, const char *name, const char *description)
864 {
865         DESCR_CHECK(description, srna->identifier, NULL);
866
867         srna->name = name;
868         srna->description = description;
869 }
870
871 void RNA_def_struct_ui_icon(StructRNA *srna, int icon)
872 {
873         srna->icon = icon;
874 }
875
876 void RNA_def_struct_translation_context(StructRNA *srna, const char *context)
877 {
878         srna->translation_context = context;
879 }
880
881 /* Property Definition */
882
883 PropertyRNA *RNA_def_property(StructOrFunctionRNA *cont_, const char *identifier, int type, int subtype)
884 {
885         /*StructRNA *srna= DefRNA.laststruct;*/ /* invalid for python defined props */
886         ContainerRNA *cont = cont_;
887         ContainerDefRNA *dcont;
888         PropertyDefRNA *dprop = NULL;
889         PropertyRNA *prop;
890
891         if (DefRNA.preprocess) {
892                 char error[512];
893                 
894                 if (rna_validate_identifier(identifier, error, 1) == 0) {
895                         fprintf(stderr, "%s: property identifier \"%s.%s\" - %s\n", __func__,
896                                 CONTAINER_RNA_ID(cont), identifier, error);
897                         DefRNA.error = 1;
898                 }
899                 
900                 dcont = rna_find_container_def(cont);
901
902                 /* XXX - toto, detect supertype collisions */
903                 if (rna_findlink(&dcont->properties, identifier)) {
904                         fprintf(stderr, "%s: duplicate identifier \"%s.%s\"\n", __func__, CONTAINER_RNA_ID(cont), identifier);
905                         DefRNA.error = 1;
906                 }
907
908                 dprop = MEM_callocN(sizeof(PropertyDefRNA), "PropertyDefRNA");
909                 rna_addtail(&dcont->properties, dprop);
910         }
911
912         prop = MEM_callocN(rna_property_type_sizeof(type), "PropertyRNA");
913
914         switch (type) {
915                 case PROP_BOOLEAN:
916                         break;
917                 case PROP_INT: {
918                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
919
920                         iprop->hardmin = (subtype == PROP_UNSIGNED)? 0: INT_MIN;
921                         iprop->hardmax = INT_MAX;
922
923                         iprop->softmin = (subtype == PROP_UNSIGNED)? 0: -10000; /* rather arbitrary .. */
924                         iprop->softmax = 10000;
925                         iprop->step = 1;
926                         break;
927                 }
928                 case PROP_FLOAT: {
929                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
930
931                         fprop->hardmin = (subtype == PROP_UNSIGNED)? 0.0f: -FLT_MAX;
932                         fprop->hardmax = FLT_MAX;
933
934                         if (ELEM(subtype, PROP_COLOR, PROP_COLOR_GAMMA)) {
935                                 fprop->softmin = 0.0f;
936                                 fprop->softmax = 1.0f;
937                         }
938                         else if (subtype == PROP_FACTOR) {
939                                 fprop->softmin = fprop->hardmin = 0.0f;
940                                 fprop->softmax = fprop->hardmax = 1.0f;
941                         }
942                         else {
943                                 fprop->softmin = (subtype == PROP_UNSIGNED)? 0.0f: -10000.0f; /* rather arbitrary .. */
944                                 fprop->softmax = 10000.0f;
945                         }
946                         fprop->step = 10;
947                         fprop->precision = 3;
948                         break;
949                 }
950                 case PROP_STRING: {
951                         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
952
953                         sprop->defaultvalue = "";
954                         sprop->maxlength = 0;
955                         break;
956                 }
957                 case PROP_ENUM:
958                 case PROP_POINTER:
959                 case PROP_COLLECTION:
960                         break;
961                 default:
962                         fprintf(stderr, "%s: \"%s.%s\", invalid property type.\n", __func__, CONTAINER_RNA_ID(cont), identifier);
963                         DefRNA.error = 1;
964                         return NULL;
965         }
966
967         if (DefRNA.preprocess) {
968                 dprop->cont = cont;
969                 dprop->prop = prop;
970         }
971
972         prop->magic = RNA_MAGIC;
973         prop->identifier = identifier;
974         prop->type = type;
975         prop->subtype = subtype;
976         prop->name = identifier;
977         prop->description = "";
978         /* a priori not raw editable */
979         prop->rawtype = -1;
980
981         if (type != PROP_COLLECTION && type != PROP_POINTER) {
982                 prop->flag = PROP_EDITABLE;
983         
984                 if (type != PROP_STRING)
985                         prop->flag |= PROP_ANIMATABLE;
986         }
987
988         if (DefRNA.preprocess) {
989                 switch (type) {
990                         case PROP_BOOLEAN:
991                                 DefRNA.silent = 1;
992                                 RNA_def_property_boolean_sdna(prop, NULL, identifier, 0);
993                                 DefRNA.silent = 0;
994                                 break;
995                         case PROP_INT: {
996                                 DefRNA.silent = 1;
997                                 RNA_def_property_int_sdna(prop, NULL, identifier);
998                                 DefRNA.silent = 0;
999                                 break;
1000                         }
1001                         case PROP_FLOAT: {
1002                                 DefRNA.silent = 1;
1003                                 RNA_def_property_float_sdna(prop, NULL, identifier);
1004                                 DefRNA.silent = 0;
1005                                 break;
1006                         }
1007                         case PROP_STRING: {
1008                                 DefRNA.silent = 1;
1009                                 RNA_def_property_string_sdna(prop, NULL, identifier);
1010                                 DefRNA.silent = 0;
1011                                 break;
1012                         }
1013                         case PROP_ENUM:
1014                                 DefRNA.silent = 1;
1015                                 RNA_def_property_enum_sdna(prop, NULL, identifier);
1016                                 DefRNA.silent = 0;
1017                                 break;
1018                         case PROP_POINTER:
1019                                 DefRNA.silent = 1;
1020                                 RNA_def_property_pointer_sdna(prop, NULL, identifier);
1021                                 DefRNA.silent = 0;
1022                                 break;
1023                         case PROP_COLLECTION:
1024                                 DefRNA.silent = 1;
1025                                 RNA_def_property_collection_sdna(prop, NULL, identifier, NULL);
1026                                 DefRNA.silent = 0;
1027                                 break;
1028                 }
1029         }
1030         else {
1031                 prop->flag |= PROP_IDPROPERTY|PROP_RUNTIME;
1032 #ifdef RNA_RUNTIME
1033                 if (cont->prophash)
1034                         BLI_ghash_insert(cont->prophash, (void*)prop->identifier, prop);
1035 #endif
1036         }
1037
1038         rna_addtail(&cont->properties, prop);
1039
1040         return prop;
1041 }
1042
1043 void RNA_def_property_flag(PropertyRNA *prop, int flag)
1044 {
1045         prop->flag |= flag;
1046 }
1047
1048 void RNA_def_property_clear_flag(PropertyRNA *prop, int flag)
1049 {
1050         prop->flag &= ~flag;
1051 }
1052
1053 void RNA_def_property_subtype(PropertyRNA *prop, PropertySubType subtype)
1054 {
1055         prop->subtype = subtype;
1056 }
1057
1058 void RNA_def_property_array(PropertyRNA *prop, int length)
1059 {
1060         StructRNA *srna = DefRNA.laststruct;
1061
1062         if (length<0) {
1063                 fprintf(stderr, "%s: \"%s.%s\", array length must be zero of greater.\n", __func__,
1064                         srna->identifier, prop->identifier);
1065                 DefRNA.error = 1;
1066                 return;
1067         }
1068
1069         if (length>RNA_MAX_ARRAY_LENGTH) {
1070                 fprintf(stderr, "%s: \"%s.%s\", array length must be smaller than %d.\n", __func__,
1071                         srna->identifier, prop->identifier, RNA_MAX_ARRAY_LENGTH);
1072                 DefRNA.error = 1;
1073                 return;
1074         }
1075
1076         if (prop->arraydimension > 1) {
1077                 fprintf(stderr, "%s: \"%s.%s\", array dimensions has been set to %u but would be overwritten as 1.\n",
1078                         __func__, srna->identifier, prop->identifier, prop->arraydimension);
1079                 DefRNA.error = 1;
1080                 return;
1081         }
1082
1083         switch (prop->type) {
1084                 case PROP_BOOLEAN:
1085                 case PROP_INT:
1086                 case PROP_FLOAT:
1087                         prop->arraylength[0] = length;
1088                         prop->totarraylength = length;
1089                         prop->arraydimension = 1;
1090                         break;
1091                 default:
1092                         fprintf(stderr, "%s: \"%s.%s\", only boolean/int/float can be array.\n",
1093                                 __func__, srna->identifier, prop->identifier);
1094                         DefRNA.error = 1;
1095                         break;
1096         }
1097 }
1098
1099 void RNA_def_property_multi_array(PropertyRNA *prop, int dimension, const int length[])
1100 {
1101         StructRNA *srna = DefRNA.laststruct;
1102         int i;
1103         
1104         if (dimension < 1 || dimension > RNA_MAX_ARRAY_DIMENSION) {
1105                 fprintf(stderr, "%s: \"%s.%s\", array dimension must be between 1 and %d.\n",
1106                         __func__, srna->identifier, prop->identifier, RNA_MAX_ARRAY_DIMENSION);
1107                 DefRNA.error = 1;
1108                 return;
1109         }
1110
1111         switch (prop->type) {
1112                 case PROP_BOOLEAN:
1113                 case PROP_INT:
1114                 case PROP_FLOAT:
1115                         break;
1116                 default:
1117                         fprintf(stderr, "%s: \"%s.%s\", only boolean/int/float can be array.\n",
1118                                 __func__, srna->identifier, prop->identifier);
1119                         DefRNA.error = 1;
1120                         break;
1121         }
1122
1123         prop->arraydimension = dimension;
1124         prop->totarraylength = 0;
1125
1126         if (length) {
1127                 memcpy(prop->arraylength, length, sizeof(int)*dimension);
1128
1129                 prop->totarraylength = length[0];
1130                 for (i = 1; i<dimension; i++)
1131                         prop->totarraylength *= length[i];
1132         }
1133         else
1134                 memset(prop->arraylength, 0, sizeof(prop->arraylength));
1135
1136         /* TODO make sure arraylength values are sane  */
1137 }
1138
1139 void RNA_def_property_ui_text(PropertyRNA *prop, const char *name, const char *description)
1140 {
1141         DESCR_CHECK(description, prop->identifier, NULL);
1142
1143         prop->name = name;
1144         prop->description = description;
1145 }
1146
1147 void RNA_def_property_ui_icon(PropertyRNA *prop, int icon, int consecutive)
1148 {
1149         prop->icon = icon;
1150         if (consecutive)
1151                 prop->flag |= PROP_ICONS_CONSECUTIVE;
1152 }
1153
1154 void RNA_def_property_ui_range(PropertyRNA *prop, double min, double max, double step, int precision)
1155 {
1156         StructRNA *srna = DefRNA.laststruct;
1157
1158         switch (prop->type) {
1159                 case PROP_INT: {
1160                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1161                         iprop->softmin = (int)min;
1162                         iprop->softmax = (int)max;
1163                         iprop->step = (int)step;
1164                         break;
1165                 }
1166                 case PROP_FLOAT: {
1167                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1168                         fprop->softmin = (float)min;
1169                         fprop->softmax = (float)max;
1170                         fprop->step = (float)step;
1171                         fprop->precision = (int)precision;
1172                         break;
1173                 }
1174                 default:
1175                         fprintf(stderr, "%s: \"%s.%s\", invalid type for ui range.\n",
1176                                 __func__, srna->identifier, prop->identifier);
1177                         DefRNA.error = 1;
1178                         break;
1179         }
1180 }
1181
1182 void RNA_def_property_range(PropertyRNA *prop, double min, double max)
1183 {
1184         StructRNA *srna = DefRNA.laststruct;
1185
1186         switch (prop->type) {
1187                 case PROP_INT: {
1188                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1189                         iprop->hardmin = (int)min;
1190                         iprop->hardmax = (int)max;
1191                         iprop->softmin = MAX2((int)min, iprop->hardmin);
1192                         iprop->softmax = MIN2((int)max, iprop->hardmax);
1193                         break;
1194                 }
1195                 case PROP_FLOAT: {
1196                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1197                         fprop->hardmin = (float)min;
1198                         fprop->hardmax = (float)max;
1199                         fprop->softmin = MAX2((float)min, fprop->hardmin);
1200                         fprop->softmax = MIN2((float)max, fprop->hardmax);
1201                         break;
1202                 }
1203                 default:
1204                         fprintf(stderr, "%s: \"%s.%s\", invalid type for range.\n", __func__, srna->identifier, prop->identifier);
1205                         DefRNA.error = 1;
1206                         break;
1207         }
1208 }
1209
1210 void RNA_def_property_struct_type(PropertyRNA *prop, const char *type)
1211 {
1212         StructRNA *srna = DefRNA.laststruct;
1213
1214         if (!DefRNA.preprocess) {
1215                 fprintf(stderr, "%s \"%s.%s\": only during preprocessing.\n", __func__, srna->identifier, prop->identifier);
1216                 return;
1217         }
1218
1219         switch (prop->type) {
1220                 case PROP_POINTER: {
1221                         PointerPropertyRNA *pprop = (PointerPropertyRNA*)prop;
1222                         pprop->type = (StructRNA*)type;
1223                         break;
1224                 }
1225                 case PROP_COLLECTION: {
1226                         CollectionPropertyRNA *cprop = (CollectionPropertyRNA*)prop;
1227                         cprop->item_type = (StructRNA*)type;
1228                         break;
1229                 }
1230                 default:
1231                         fprintf(stderr, "%s: \"%s.%s\", invalid type for struct type.\n",
1232                                 __func__, srna->identifier, prop->identifier);
1233                         DefRNA.error = 1;
1234                         break;
1235         }
1236 }
1237
1238 void RNA_def_property_struct_runtime(PropertyRNA *prop, StructRNA *type)
1239 {
1240         StructRNA *srna = DefRNA.laststruct;
1241
1242         if (DefRNA.preprocess) {
1243                 fprintf(stderr, "%s: only at runtime.\n", __func__);
1244                 return;
1245         }
1246
1247         switch (prop->type) {
1248                 case PROP_POINTER: {
1249                         PointerPropertyRNA *pprop = (PointerPropertyRNA*)prop;
1250                         pprop->type = type;
1251
1252                         if (type && (type->flag & STRUCT_ID_REFCOUNT))
1253                                 prop->flag |= PROP_ID_REFCOUNT;
1254
1255                         break;
1256                 }
1257                 case PROP_COLLECTION: {
1258                         CollectionPropertyRNA *cprop = (CollectionPropertyRNA*)prop;
1259                         cprop->item_type = type;
1260                         break;
1261                 }
1262                 default:
1263                         fprintf(stderr, "%s: \"%s.%s\", invalid type for struct type.\n",
1264                                 __func__, srna->identifier, prop->identifier);
1265                         DefRNA.error = 1;
1266                         break;
1267         }
1268 }
1269
1270 void RNA_def_property_enum_items(PropertyRNA *prop, const EnumPropertyItem *item)
1271 {
1272         StructRNA *srna = DefRNA.laststruct;
1273         int i, defaultfound = 0;
1274
1275         switch (prop->type) {
1276                 case PROP_ENUM: {
1277                         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
1278                         eprop->item = (EnumPropertyItem*)item;
1279                         eprop->totitem = 0;
1280                         for (i = 0; item[i].identifier; i++) {
1281                                 eprop->totitem++;
1282
1283                                 if (item[i].identifier[0] && item[i].value == eprop->defaultvalue)
1284                                         defaultfound = 1;
1285                         }
1286
1287                         if (!defaultfound) {
1288                                 for (i = 0; item[i].identifier; i++) {
1289                                         if (item[i].identifier[0]) {
1290                                                 eprop->defaultvalue = item[i].value;
1291                                                 break;
1292                                         }
1293                                 }
1294                         }
1295
1296                         break;
1297                 }
1298                 default:
1299                         fprintf(stderr, "%s: \"%s.%s\", invalid type for struct type.\n",
1300                                 __func__, srna->identifier, prop->identifier);
1301                         DefRNA.error = 1;
1302                         break;
1303         }
1304 }
1305
1306 void RNA_def_property_string_maxlength(PropertyRNA *prop, int maxlength)
1307 {
1308         StructRNA *srna = DefRNA.laststruct;
1309
1310         switch (prop->type) {
1311                 case PROP_STRING: {
1312                         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
1313                         sprop->maxlength = maxlength;
1314                         break;
1315                 }
1316                 default:
1317                         fprintf(stderr, "%s: \"%s.%s\", type is not string.\n", __func__, srna->identifier, prop->identifier);
1318                         DefRNA.error = 1;
1319                         break;
1320         }
1321 }
1322
1323 void RNA_def_property_boolean_default(PropertyRNA *prop, int value)
1324 {
1325         StructRNA *srna = DefRNA.laststruct;
1326
1327         switch (prop->type) {
1328                 case PROP_BOOLEAN: {
1329                         BoolPropertyRNA *bprop = (BoolPropertyRNA*)prop;
1330                         bprop->defaultvalue = value;
1331                         break;
1332                 }
1333                 default:
1334                         fprintf(stderr, "%s: \"%s.%s\", type is not boolean.\n", __func__, srna->identifier, prop->identifier);
1335                         DefRNA.error = 1;
1336                         break;
1337         }
1338 }
1339
1340 void RNA_def_property_boolean_array_default(PropertyRNA *prop, const int *array)
1341 {
1342         StructRNA *srna = DefRNA.laststruct;
1343
1344         switch (prop->type) {
1345                 case PROP_BOOLEAN: {
1346                         BoolPropertyRNA *bprop = (BoolPropertyRNA*)prop;
1347                         bprop->defaultarray = array;
1348                         break;
1349                 }
1350                 default:
1351                         fprintf(stderr, "%s: \"%s.%s\", type is not boolean.\n", __func__, srna->identifier, prop->identifier);
1352                         DefRNA.error = 1;
1353                         break;
1354         }
1355 }
1356
1357 void RNA_def_property_int_default(PropertyRNA *prop, int value)
1358 {
1359         StructRNA *srna = DefRNA.laststruct;
1360
1361         switch (prop->type) {
1362                 case PROP_INT: {
1363                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1364                         iprop->defaultvalue = value;
1365                         break;
1366                 }
1367                 default:
1368                         fprintf(stderr, "%s: \"%s.%s\", type is not int.\n", __func__, srna->identifier, prop->identifier);
1369                         DefRNA.error = 1;
1370                         break;
1371         }
1372 }
1373
1374 void RNA_def_property_int_array_default(PropertyRNA *prop, const int *array)
1375 {
1376         StructRNA *srna = DefRNA.laststruct;
1377
1378         switch (prop->type) {
1379                 case PROP_INT: {
1380                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1381                         iprop->defaultarray = array;
1382                         break;
1383                 }
1384                 default:
1385                         fprintf(stderr, "%s: \"%s.%s\", type is not int.\n", __func__, srna->identifier, prop->identifier);
1386                         DefRNA.error = 1;
1387                         break;
1388         }
1389 }
1390
1391 void RNA_def_property_float_default(PropertyRNA *prop, float value)
1392 {
1393         StructRNA *srna = DefRNA.laststruct;
1394
1395         switch (prop->type) {
1396                 case PROP_FLOAT: {
1397                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1398                         fprop->defaultvalue = value;
1399                         break;
1400                 }
1401                 default:
1402                         fprintf(stderr, "%s: \"%s.%s\", type is not float.\n", __func__, srna->identifier, prop->identifier);
1403                         DefRNA.error = 1;
1404                         break;
1405         }
1406 }
1407 /* array must remain valid after this function finishes */
1408 void RNA_def_property_float_array_default(PropertyRNA *prop, const float *array)
1409 {
1410         StructRNA *srna = DefRNA.laststruct;
1411
1412         switch (prop->type) {
1413                 case PROP_FLOAT: {
1414                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1415                         fprop->defaultarray = array; /* WARNING, this array must not come from the stack and lost */
1416                         break;
1417                 }
1418                 default:
1419                         fprintf(stderr, "%s: \"%s.%s\", type is not float.\n", __func__, srna->identifier, prop->identifier);
1420                         DefRNA.error = 1;
1421                         break;
1422         }
1423 }
1424
1425 void RNA_def_property_string_default(PropertyRNA *prop, const char *value)
1426 {
1427         StructRNA *srna = DefRNA.laststruct;
1428
1429         switch (prop->type) {
1430                 case PROP_STRING: {
1431                         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
1432                         sprop->defaultvalue = value;
1433                         break;
1434                 }
1435                 default:
1436                         fprintf(stderr, "%s: \"%s.%s\", type is not string.\n", __func__, srna->identifier, prop->identifier);
1437                         DefRNA.error = 1;
1438                         break;
1439         }
1440 }
1441
1442 void RNA_def_property_enum_default(PropertyRNA *prop, int value)
1443 {
1444         StructRNA *srna = DefRNA.laststruct;
1445         int i, defaultfound = 0;
1446
1447         switch (prop->type) {
1448                 case PROP_ENUM: {
1449                         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
1450                         eprop->defaultvalue = value;
1451
1452                         if (prop->flag & PROP_ENUM_FLAG) {
1453                                 /* check all bits are accounted for */
1454                                 int totflag = 0;
1455                                 for (i = 0; i<eprop->totitem; i++) {
1456                                         if (eprop->item[i].identifier[0]) {
1457                                                 totflag |= eprop->item[i].value;
1458                                         }
1459                                 }
1460
1461                                 if (eprop->defaultvalue & ~totflag) {
1462                                         fprintf(stderr, "%s: \"%s.%s\", default includes unused bits (%d).\n",
1463                                                 __func__, srna->identifier, prop->identifier, eprop->defaultvalue & ~totflag);
1464                                         DefRNA.error = 1;
1465                                 }
1466                         }
1467                         else {
1468                                 for (i = 0; i<eprop->totitem; i++) {
1469                                         if (eprop->item[i].identifier[0] && eprop->item[i].value == eprop->defaultvalue)
1470                                                 defaultfound = 1;
1471                                 }
1472
1473                                 if (!defaultfound && eprop->totitem) {
1474                                         if (value == 0) {
1475                                                 eprop->defaultvalue = eprop->item[0].value;
1476                                         }
1477                                         else {
1478                                                 fprintf(stderr, "%s: \"%s.%s\", default is not in items.\n",
1479                                                         __func__, srna->identifier, prop->identifier);
1480                                                 DefRNA.error = 1;
1481                                         }
1482                                 }
1483                         }
1484
1485                         break;
1486                 }
1487                 default:
1488                         fprintf(stderr, "%s: \"%s.%s\", type is not enum.\n", __func__, srna->identifier, prop->identifier);
1489                         DefRNA.error = 1;
1490                         break;
1491         }
1492 }
1493
1494 /* SDNA */
1495
1496 static PropertyDefRNA *rna_def_property_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1497 {
1498         DNAStructMember smember;
1499         StructDefRNA *ds;
1500         PropertyDefRNA *dp;
1501
1502         dp = rna_find_struct_property_def(DefRNA.laststruct, prop);
1503         if (dp == NULL) return NULL;
1504
1505         ds = rna_find_struct_def((StructRNA*)dp->cont);
1506
1507         if (!structname)
1508                 structname = ds->dnaname;
1509         if (!propname)
1510                 propname = prop->identifier;
1511
1512         if (!rna_find_sdna_member(DefRNA.sdna, structname, propname, &smember)) {
1513                 if (DefRNA.silent) {
1514                         return NULL;
1515                 }
1516                 else if (!DefRNA.verify) {
1517                         /* some basic values to survive even with sdna info */
1518                         dp->dnastructname = structname;
1519                         dp->dnaname = propname;
1520                         if (prop->type == PROP_BOOLEAN)
1521                                 dp->dnaarraylength = 1;
1522                         if (prop->type == PROP_POINTER)
1523                                 dp->dnapointerlevel = 1;
1524                         return dp;
1525                 }
1526                 else {
1527                         fprintf(stderr, "%s: \"%s.%s\" (identifier \"%s\") not found.\n",
1528                                 __func__, structname, propname, prop->identifier);
1529                         DefRNA.error = 1;
1530                         return NULL;
1531                 }
1532         }
1533
1534         if (smember.arraylength > 1) {
1535                 prop->arraylength[0] = smember.arraylength;
1536                 prop->totarraylength = smember.arraylength;
1537                 prop->arraydimension = 1;
1538         }
1539         else {
1540                 prop->arraydimension = 0;
1541                 prop->totarraylength = 0;
1542         }
1543         
1544         dp->dnastructname = structname;
1545         dp->dnastructfromname = ds->dnafromname;
1546         dp->dnastructfromprop = ds->dnafromprop;
1547         dp->dnaname = propname;
1548         dp->dnatype = smember.type;
1549         dp->dnaarraylength = smember.arraylength;
1550         dp->dnapointerlevel = smember.pointerlevel;
1551
1552         return dp;
1553 }
1554
1555 void RNA_def_property_boolean_sdna(PropertyRNA *prop, const char *structname, const char *propname, int bit)
1556 {
1557         PropertyDefRNA *dp;
1558         StructRNA *srna = DefRNA.laststruct;
1559         
1560         if (!DefRNA.preprocess) {
1561                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1562                 return;
1563         }
1564
1565         if (prop->type != PROP_BOOLEAN) {
1566                 fprintf(stderr, "%s: \"%s.%s\", type is not boolean.\n", __func__, srna->identifier, prop->identifier);
1567                 DefRNA.error = 1;
1568                 return;
1569         }
1570
1571         if ((dp = rna_def_property_sdna(prop, structname, propname))) {
1572
1573                 if (DefRNA.silent == 0) {
1574                         /* error check to ensure floats are not wrapped as ints/bools */
1575                         if (dp->dnatype && *dp->dnatype && IS_DNATYPE_INT_COMPAT(dp->dnatype) == 0) {
1576                                 fprintf(stderr, "%s: %s.%s is a '%s' but wrapped as type '%s'.\n",
1577                                         __func__, srna->identifier, prop->identifier, dp->dnatype, RNA_property_typename(prop->type));
1578                                 DefRNA.error = 1;
1579                                 return;
1580                         }
1581                 }
1582
1583                 dp->booleanbit = bit;
1584         }
1585 }
1586
1587 void RNA_def_property_boolean_negative_sdna(PropertyRNA *prop, const char *structname,
1588                                             const char *propname, int booleanbit)
1589 {
1590         PropertyDefRNA *dp;
1591
1592         RNA_def_property_boolean_sdna(prop, structname, propname, booleanbit);
1593
1594         dp = rna_find_struct_property_def(DefRNA.laststruct, prop);
1595
1596         if (dp)
1597                 dp->booleannegative = 1;
1598 }
1599
1600 void RNA_def_property_int_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1601 {
1602         PropertyDefRNA *dp;
1603         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1604         StructRNA *srna = DefRNA.laststruct;
1605         
1606         if (!DefRNA.preprocess) {
1607                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1608                 return;
1609         }
1610
1611         if (prop->type != PROP_INT) {
1612                 fprintf(stderr, "%s: \"%s.%s\", type is not int.\n", __func__, srna->identifier, prop->identifier);
1613                 DefRNA.error = 1;
1614                 return;
1615         }
1616
1617         if ((dp = rna_def_property_sdna(prop, structname, propname))) {
1618
1619                 /* error check to ensure floats are not wrapped as ints/bools */
1620                 if (DefRNA.silent == 0) {
1621                         if (dp->dnatype && *dp->dnatype && IS_DNATYPE_INT_COMPAT(dp->dnatype) == 0) {
1622                                 fprintf(stderr, "%s: %s.%s is a '%s' but wrapped as type '%s'.\n",
1623                                         __func__, srna->identifier, prop->identifier, dp->dnatype, RNA_property_typename(prop->type));
1624                                 DefRNA.error = 1;
1625                                 return;
1626                         }
1627                 }
1628
1629                 /* SDNA doesn't pass us unsigned unfortunately .. */
1630                 if (dp->dnatype && strcmp(dp->dnatype, "char") == 0) {
1631                         iprop->hardmin = iprop->softmin = CHAR_MIN;
1632                         iprop->hardmax = iprop->softmax = CHAR_MAX;
1633                 }
1634                 else if (dp->dnatype && strcmp(dp->dnatype, "short") == 0) {
1635                         iprop->hardmin = iprop->softmin = SHRT_MIN;
1636                         iprop->hardmax = iprop->softmax = SHRT_MAX;
1637                 }
1638                 else if (dp->dnatype && strcmp(dp->dnatype, "int") == 0) {
1639                         iprop->hardmin = INT_MIN;
1640                         iprop->hardmax = INT_MAX;
1641
1642                         iprop->softmin = -10000; /* rather arbitrary .. */
1643                         iprop->softmax = 10000;
1644                 }
1645
1646                 if (prop->subtype == PROP_UNSIGNED || prop->subtype == PROP_PERCENTAGE || prop->subtype == PROP_FACTOR)
1647                         iprop->hardmin = iprop->softmin = 0;
1648         }
1649 }
1650
1651 void RNA_def_property_float_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1652 {
1653         PropertyDefRNA *dp;
1654         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1655         StructRNA *srna = DefRNA.laststruct;
1656
1657         if (!DefRNA.preprocess) {
1658                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1659                 return;
1660         }
1661
1662         if (prop->type != PROP_FLOAT) {
1663                 fprintf(stderr, "%s: \"%s.%s\", type is not float.\n", __func__, srna->identifier, prop->identifier);
1664                 DefRNA.error = 1;
1665                 return;
1666         }
1667
1668         if ((dp = rna_def_property_sdna(prop, structname, propname))) {
1669                 /* silent is for internal use */
1670                 if (DefRNA.silent == 0) {
1671                         if (dp->dnatype && *dp->dnatype && IS_DNATYPE_FLOAT_COMPAT(dp->dnatype) == 0) {
1672                                 if (prop->subtype != PROP_COLOR_GAMMA) { /* colors are an exception. these get translated */
1673                                         fprintf(stderr, "%s: %s.%s is a '%s' but wrapped as type '%s'.\n",
1674                                                 __func__, srna->identifier, prop->identifier, dp->dnatype,
1675                                                 RNA_property_typename(prop->type));
1676                                         DefRNA.error = 1;
1677                                         return;
1678                                 }
1679                         }
1680                 }
1681
1682                 if (dp->dnatype && strcmp(dp->dnatype, "char") == 0) {
1683                         fprop->hardmin = fprop->softmin = 0.0f;
1684                         fprop->hardmax = fprop->softmax = 1.0f;
1685                 }
1686         }
1687
1688         rna_def_property_sdna(prop, structname, propname);
1689 }
1690
1691 void RNA_def_property_enum_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1692 {
1693         /* PropertyDefRNA *dp; */
1694         StructRNA *srna = DefRNA.laststruct;
1695         
1696         if (!DefRNA.preprocess) {
1697                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1698                 return;
1699         }
1700
1701         if (prop->type != PROP_ENUM) {
1702                 fprintf(stderr, "%s: \"%s.%s\", type is not enum.\n", __func__, srna->identifier, prop->identifier);
1703                 DefRNA.error = 1;
1704                 return;
1705         }
1706
1707         if (( /* dp= */ rna_def_property_sdna(prop, structname, propname))) {
1708                 if (prop->arraydimension) {
1709                         prop->arraydimension = 0;
1710                         prop->totarraylength = 0;
1711
1712                         if (!DefRNA.silent) {
1713                                 fprintf(stderr, "%s: \"%s.%s\", array not supported for enum type.\n",
1714                                         __func__, structname, propname);
1715                                 DefRNA.error = 1;
1716                         }
1717                 }
1718         }
1719 }
1720
1721 void RNA_def_property_enum_bitflag_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1722 {
1723         PropertyDefRNA *dp;
1724
1725         RNA_def_property_enum_sdna(prop, structname, propname);
1726
1727         dp = rna_find_struct_property_def(DefRNA.laststruct, prop);
1728
1729         if (dp)
1730                 dp->enumbitflags = 1;
1731 }
1732
1733 void RNA_def_property_string_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1734 {
1735         /* PropertyDefRNA *dp; */
1736         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
1737         StructRNA *srna = DefRNA.laststruct;
1738
1739         if (!DefRNA.preprocess) {
1740                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1741                 return;
1742         }
1743
1744         if (prop->type != PROP_STRING) {
1745                 fprintf(stderr, "%s: \"%s.%s\", type is not string.\n", __func__, srna->identifier, prop->identifier);
1746                 DefRNA.error = 1;
1747                 return;
1748         }
1749
1750         if ((/* dp= */ rna_def_property_sdna(prop, structname, propname))) {
1751                 if (prop->arraydimension) {
1752                         sprop->maxlength = prop->totarraylength;
1753                         prop->arraydimension = 0;
1754                         prop->totarraylength = 0;
1755                 }
1756         }
1757 }
1758
1759 void RNA_def_property_pointer_sdna(PropertyRNA *prop, const char *structname, const char *propname)
1760 {
1761         /* PropertyDefRNA *dp; */
1762         StructRNA *srna = DefRNA.laststruct;
1763         
1764         if (!DefRNA.preprocess) {
1765                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1766                 return;
1767         }
1768
1769         if (prop->type != PROP_POINTER) {
1770                 fprintf(stderr, "%s: \"%s.%s\", type is not pointer.\n", __func__, srna->identifier, prop->identifier);
1771                 DefRNA.error = 1;
1772                 return;
1773         }
1774
1775         if ((/* dp= */ rna_def_property_sdna(prop, structname, propname))) {
1776                 if (prop->arraydimension) {
1777                         prop->arraydimension = 0;
1778                         prop->totarraylength = 0;
1779
1780                         if (!DefRNA.silent) {
1781                                 fprintf(stderr, "%s: \"%s.%s\", array not supported for pointer type.\n",
1782                                         __func__, structname, propname);
1783                                 DefRNA.error = 1;
1784                         }
1785                 }
1786         }
1787 }
1788
1789 void RNA_def_property_collection_sdna(PropertyRNA *prop, const char *structname, const char *propname,
1790                                       const char *lengthpropname)
1791 {
1792         PropertyDefRNA *dp;
1793         CollectionPropertyRNA *cprop = (CollectionPropertyRNA*)prop;
1794         StructRNA *srna = DefRNA.laststruct;
1795
1796         if (!DefRNA.preprocess) {
1797                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1798                 return;
1799         }
1800
1801         if (prop->type != PROP_COLLECTION) {
1802                 fprintf(stderr, "%s: \"%s.%s\", type is not collection.\n", __func__, srna->identifier, prop->identifier);
1803                 DefRNA.error = 1;
1804                 return;
1805         }
1806
1807         if ((dp = rna_def_property_sdna(prop, structname, propname))) {
1808                 if (prop->arraydimension && !lengthpropname) {
1809                         prop->arraydimension = 0;
1810                         prop->totarraylength = 0;
1811
1812                         if (!DefRNA.silent) {
1813                                 fprintf(stderr, "%s: \"%s.%s\", array of collections not supported.\n",
1814                                         __func__, structname, propname);
1815                                 DefRNA.error = 1;
1816                         }
1817                 }
1818
1819                 if (dp->dnatype && strcmp(dp->dnatype, "ListBase") == 0) {
1820                         cprop->next = (PropCollectionNextFunc)"rna_iterator_listbase_next";
1821                         cprop->get = (PropCollectionGetFunc)"rna_iterator_listbase_get";
1822                         cprop->end = (PropCollectionEndFunc)"rna_iterator_listbase_end";
1823                 }
1824         }
1825
1826         if (dp && lengthpropname) {
1827                 DNAStructMember smember;
1828                 StructDefRNA *ds = rna_find_struct_def((StructRNA*)dp->cont);
1829
1830                 if (!structname)
1831                         structname = ds->dnaname;
1832
1833                 if (lengthpropname[0] == 0 || rna_find_sdna_member(DefRNA.sdna, structname, lengthpropname, &smember)) {
1834                         if (lengthpropname[0] == 0) {
1835                                 dp->dnalengthfixed = prop->totarraylength;
1836                                 prop->arraydimension = 0;
1837                                 prop->totarraylength = 0;
1838                         }
1839                         else {
1840                                 dp->dnalengthstructname = structname;
1841                                 dp->dnalengthname = lengthpropname;
1842                                 prop->totarraylength = 0;
1843                         }
1844
1845                         cprop->next = (PropCollectionNextFunc)"rna_iterator_array_next";
1846                         cprop->end = (PropCollectionEndFunc)"rna_iterator_array_end";
1847
1848                         if (dp->dnapointerlevel >= 2)
1849                                 cprop->get = (PropCollectionGetFunc)"rna_iterator_array_dereference_get";
1850                         else
1851                                 cprop->get = (PropCollectionGetFunc)"rna_iterator_array_get";
1852                 }
1853                 else {
1854                         if (!DefRNA.silent) {
1855                                 fprintf(stderr, "%s: \"%s.%s\" not found.\n", __func__, structname, lengthpropname);
1856                                 DefRNA.error = 1;
1857                         }
1858                 }
1859         }
1860 }
1861
1862 void RNA_def_property_translation_context(PropertyRNA *prop, const char *context)
1863 {
1864         prop->translation_context = context;
1865 }
1866
1867 /* Functions */
1868
1869 void RNA_def_property_editable_func(PropertyRNA *prop, const char *editable)
1870 {
1871         if (!DefRNA.preprocess) {
1872                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1873                 return;
1874         }
1875
1876         if (editable) prop->editable = (EditableFunc)editable;
1877 }
1878
1879 void RNA_def_property_editable_array_func(PropertyRNA *prop, const char *editable)
1880 {
1881         if (!DefRNA.preprocess) {
1882                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1883                 return;
1884         }
1885
1886         if (editable) prop->itemeditable = (ItemEditableFunc)editable;
1887 }
1888
1889 void RNA_def_property_update(PropertyRNA *prop, int noteflag, const char *func)
1890 {
1891         if (!DefRNA.preprocess) {
1892                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1893                 return;
1894         }
1895
1896         prop->noteflag = noteflag;
1897         prop->update = (UpdateFunc)func;
1898 }
1899
1900 void RNA_def_property_update_runtime(PropertyRNA *prop, void *func)
1901 {
1902         prop->update = func;
1903 }
1904
1905 void RNA_def_property_dynamic_array_funcs(PropertyRNA *prop, const char *getlength)
1906 {
1907         if (!DefRNA.preprocess) {
1908                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1909                 return;
1910         }
1911
1912         if (!(prop->flag & PROP_DYNAMIC)) {
1913                 fprintf(stderr, "%s: property is a not dynamic array.\n", __func__);
1914                 DefRNA.error = 1;
1915                 return;
1916         }
1917
1918         if (getlength) prop->getlength = (PropArrayLengthGetFunc)getlength;
1919 }
1920
1921 void RNA_def_property_boolean_funcs(PropertyRNA *prop, const char *get, const char *set)
1922 {
1923         StructRNA *srna = DefRNA.laststruct;
1924
1925         if (!DefRNA.preprocess) {
1926                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1927                 return;
1928         }
1929
1930         switch (prop->type) {
1931                 case PROP_BOOLEAN: {
1932                         BoolPropertyRNA *bprop = (BoolPropertyRNA*)prop;
1933
1934                         if (prop->arraydimension) {
1935                                 if (get) bprop->getarray = (PropBooleanArrayGetFunc)get;
1936                                 if (set) bprop->setarray = (PropBooleanArraySetFunc)set;
1937                         }
1938                         else {
1939                                 if (get) bprop->get = (PropBooleanGetFunc)get;
1940                                 if (set) bprop->set = (PropBooleanSetFunc)set;
1941                         }
1942                         break;
1943                 }
1944                 default:
1945                         fprintf(stderr, "%s: \"%s.%s\", type is not boolean.\n", __func__, srna->identifier, prop->identifier);
1946                         DefRNA.error = 1;
1947                         break;
1948         }
1949 }
1950
1951 void RNA_def_property_int_funcs(PropertyRNA *prop, const char *get, const char *set, const char *range)
1952 {
1953         StructRNA *srna = DefRNA.laststruct;
1954
1955         if (!DefRNA.preprocess) {
1956                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1957                 return;
1958         }
1959
1960         switch (prop->type) {
1961                 case PROP_INT: {
1962                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
1963
1964                         if (prop->arraydimension) {
1965                                 if (get) iprop->getarray = (PropIntArrayGetFunc)get;
1966                                 if (set) iprop->setarray = (PropIntArraySetFunc)set;
1967                         }
1968                         else {
1969                                 if (get) iprop->get = (PropIntGetFunc)get;
1970                                 if (set) iprop->set = (PropIntSetFunc)set;
1971                         }
1972                         if (range) iprop->range = (PropIntRangeFunc)range;
1973                         break;
1974                 }
1975                 default:
1976                         fprintf(stderr, "%s: \"%s.%s\", type is not int.\n", __func__, srna->identifier, prop->identifier);
1977                         DefRNA.error = 1;
1978                         break;
1979         }
1980 }
1981
1982 void RNA_def_property_float_funcs(PropertyRNA *prop, const char *get, const char *set, const char *range)
1983 {
1984         StructRNA *srna = DefRNA.laststruct;
1985
1986         if (!DefRNA.preprocess) {
1987                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
1988                 return;
1989         }
1990
1991         switch (prop->type) {
1992                 case PROP_FLOAT: {
1993                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
1994
1995                         if (prop->arraydimension) {
1996                                 if (get) fprop->getarray = (PropFloatArrayGetFunc)get;
1997                                 if (set) fprop->setarray = (PropFloatArraySetFunc)set;
1998                         }
1999                         else {
2000                                 if (get) fprop->get = (PropFloatGetFunc)get;
2001                                 if (set) fprop->set = (PropFloatSetFunc)set;
2002                         }
2003                         if (range) fprop->range = (PropFloatRangeFunc)range;
2004                         break;
2005                 }
2006                 default:
2007                         fprintf(stderr, "%s: \"%s.%s\", type is not float.\n", __func__, srna->identifier, prop->identifier);
2008                         DefRNA.error = 1;
2009                         break;
2010         }
2011 }
2012
2013 void RNA_def_property_enum_funcs(PropertyRNA *prop, const char *get, const char *set, const char *item)
2014 {
2015         StructRNA *srna = DefRNA.laststruct;
2016
2017         if (!DefRNA.preprocess) {
2018                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
2019                 return;
2020         }
2021
2022         switch (prop->type) {
2023                 case PROP_ENUM: {
2024                         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
2025
2026                         if (get) eprop->get = (PropEnumGetFunc)get;
2027                         if (set) eprop->set = (PropEnumSetFunc)set;
2028                         if (item) eprop->itemf = (PropEnumItemFunc)item;
2029                         break;
2030                 }
2031                 default:
2032                         fprintf(stderr, "%s: \"%s.%s\", type is not enum.\n", __func__, srna->identifier, prop->identifier);
2033                         DefRNA.error = 1;
2034                         break;
2035         }
2036 }
2037
2038 void RNA_def_property_string_funcs(PropertyRNA *prop, const char *get, const char *length, const char *set)
2039 {
2040         StructRNA *srna = DefRNA.laststruct;
2041
2042         if (!DefRNA.preprocess) {
2043                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
2044                 return;
2045         }
2046
2047         switch (prop->type) {
2048                 case PROP_STRING: {
2049                         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
2050
2051                         if (get) sprop->get = (PropStringGetFunc)get;
2052                         if (length) sprop->length = (PropStringLengthFunc)length;
2053                         if (set) sprop->set = (PropStringSetFunc)set;
2054                         break;
2055                 }
2056                 default:
2057                         fprintf(stderr, "%s: \"%s.%s\", type is not string.\n", __func__, srna->identifier, prop->identifier);
2058                         DefRNA.error = 1;
2059                         break;
2060         }
2061 }
2062
2063 void RNA_def_property_pointer_funcs(PropertyRNA *prop, const char *get, const char *set,
2064                                     const char *typef, const char *poll)
2065 {
2066         StructRNA *srna = DefRNA.laststruct;
2067
2068         if (!DefRNA.preprocess) {
2069                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
2070                 return;
2071         }
2072
2073         switch (prop->type) {
2074                 case PROP_POINTER: {
2075                         PointerPropertyRNA *pprop = (PointerPropertyRNA*)prop;
2076
2077                         if (get) pprop->get = (PropPointerGetFunc)get;
2078                         if (set) pprop->set = (PropPointerSetFunc)set;
2079                         if (typef) pprop->typef = (PropPointerTypeFunc)typef;
2080                         if (poll) pprop->poll = (PropPointerPollFunc)poll;
2081                         break;
2082                 }
2083                 default:
2084                         fprintf(stderr, "%s: \"%s.%s\", type is not pointer.\n", __func__, srna->identifier, prop->identifier);
2085                         DefRNA.error = 1;
2086                         break;
2087         }
2088 }
2089
2090 void RNA_def_property_collection_funcs(PropertyRNA *prop, const char *begin, const char *next, const char *end,
2091                                        const char *get, const char *length, const char *lookupint,
2092                                        const char *lookupstring, const char *assignint)
2093 {
2094         StructRNA *srna = DefRNA.laststruct;
2095
2096         if (!DefRNA.preprocess) {
2097                 fprintf(stderr, "%s: only during preprocessing.\n", __func__);
2098                 return;
2099         }
2100
2101         switch (prop->type) {
2102                 case PROP_COLLECTION: {
2103                         CollectionPropertyRNA *cprop = (CollectionPropertyRNA*)prop;
2104
2105                         if (begin) cprop->begin = (PropCollectionBeginFunc)begin;
2106                         if (next) cprop->next = (PropCollectionNextFunc)next;
2107                         if (end) cprop->end = (PropCollectionEndFunc)end;
2108                         if (get) cprop->get = (PropCollectionGetFunc)get;
2109                         if (length) cprop->length = (PropCollectionLengthFunc)length;
2110                         if (lookupint) cprop->lookupint = (PropCollectionLookupIntFunc)lookupint;
2111                         if (lookupstring) cprop->lookupstring = (PropCollectionLookupStringFunc)lookupstring;
2112                         if (assignint) cprop->assignint = (PropCollectionAssignIntFunc)assignint;
2113                         break;
2114                 }
2115                 default:
2116                         fprintf(stderr, "%s: \"%s.%s\", type is not collection.\n", __func__, srna->identifier, prop->identifier);
2117                         DefRNA.error = 1;
2118                         break;
2119         }
2120 }
2121
2122 void RNA_def_property_srna(PropertyRNA *prop, const char *type)
2123 {
2124         prop->srna = (StructRNA*)type;
2125 }
2126
2127 void RNA_def_py_data(PropertyRNA *prop, void *py_data)
2128 {
2129         prop->py_data = py_data;
2130 }
2131
2132 /* Compact definitions */
2133
2134 PropertyRNA *RNA_def_boolean(StructOrFunctionRNA *cont_, const char *identifier, int default_value,
2135                              const char *ui_name, const char *ui_description)
2136 {
2137         ContainerRNA *cont = cont_;
2138         PropertyRNA *prop;
2139         
2140         prop = RNA_def_property(cont, identifier, PROP_BOOLEAN, PROP_NONE);
2141         RNA_def_property_boolean_default(prop, default_value);
2142         RNA_def_property_ui_text(prop, ui_name, ui_description);
2143
2144         return prop;
2145 }
2146
2147 PropertyRNA *RNA_def_boolean_array(StructOrFunctionRNA *cont_, const char *identifier, int len, int *default_value,
2148                                    const char *ui_name, const char *ui_description)
2149 {
2150         ContainerRNA *cont = cont_;
2151         PropertyRNA *prop;
2152         
2153         prop = RNA_def_property(cont, identifier, PROP_BOOLEAN, PROP_NONE);
2154         if (len != 0) RNA_def_property_array(prop, len);
2155         if (default_value) RNA_def_property_boolean_array_default(prop, default_value);
2156         RNA_def_property_ui_text(prop, ui_name, ui_description);
2157
2158         return prop;
2159 }
2160
2161 PropertyRNA *RNA_def_boolean_layer(StructOrFunctionRNA *cont_, const char *identifier, int len, int *default_value,
2162                                    const char *ui_name, const char *ui_description)
2163 {
2164         ContainerRNA *cont = cont_;
2165         PropertyRNA *prop;
2166         
2167         prop = RNA_def_property(cont, identifier, PROP_BOOLEAN, PROP_LAYER);
2168         if (len != 0) RNA_def_property_array(prop, len);
2169         if (default_value) RNA_def_property_boolean_array_default(prop, default_value);
2170         RNA_def_property_ui_text(prop, ui_name, ui_description);
2171
2172         return prop;
2173 }
2174
2175 PropertyRNA *RNA_def_boolean_layer_member(StructOrFunctionRNA *cont_, const char *identifier, int len,
2176                                           int *default_value, const char *ui_name, const char *ui_description)
2177 {
2178         ContainerRNA *cont = cont_;
2179         PropertyRNA *prop;
2180         
2181         prop = RNA_def_property(cont, identifier, PROP_BOOLEAN, PROP_LAYER_MEMBER);
2182         if (len != 0) RNA_def_property_array(prop, len);
2183         if (default_value) RNA_def_property_boolean_array_default(prop, default_value);
2184         RNA_def_property_ui_text(prop, ui_name, ui_description);
2185
2186         return prop;
2187 }
2188
2189 PropertyRNA *RNA_def_boolean_vector(StructOrFunctionRNA *cont_, const char *identifier, int len, int *default_value,
2190                                     const char *ui_name, const char *ui_description)
2191 {
2192         ContainerRNA *cont = cont_;
2193         PropertyRNA *prop;
2194         
2195         prop = RNA_def_property(cont, identifier, PROP_BOOLEAN, PROP_XYZ); /* XXX */
2196         if (len != 0) RNA_def_property_array(prop, len);
2197         if (default_value) RNA_def_property_boolean_array_default(prop, default_value);
2198         RNA_def_property_ui_text(prop, ui_name, ui_description);
2199
2200         return prop;
2201 }
2202
2203 PropertyRNA *RNA_def_int(StructOrFunctionRNA *cont_, const char *identifier, int default_value, int hardmin,
2204                          int hardmax, const char *ui_name, const char *ui_description, int softmin, int softmax)
2205 {
2206         ContainerRNA *cont = cont_;
2207         PropertyRNA *prop;
2208         
2209         prop = RNA_def_property(cont, identifier, PROP_INT, PROP_NONE);
2210         RNA_def_property_int_default(prop, default_value);
2211         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2212         RNA_def_property_ui_text(prop, ui_name, ui_description);
2213         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2214
2215         return prop;
2216 }
2217
2218 PropertyRNA *RNA_def_int_vector(StructOrFunctionRNA *cont_, const char *identifier, int len, const int *default_value,
2219                                 int hardmin, int hardmax, const char *ui_name, const char *ui_description,
2220                                 int softmin, int softmax)
2221 {
2222         ContainerRNA *cont = cont_;
2223         PropertyRNA *prop;
2224         
2225         prop = RNA_def_property(cont, identifier, PROP_INT, PROP_XYZ); /* XXX */
2226         if (len != 0) RNA_def_property_array(prop, len);
2227         if (default_value) RNA_def_property_int_array_default(prop, default_value);
2228         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2229         RNA_def_property_ui_text(prop, ui_name, ui_description);
2230         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2231
2232         return prop;
2233 }
2234
2235 PropertyRNA *RNA_def_int_array(StructOrFunctionRNA *cont_, const char *identifier, int len, const int *default_value,
2236                                int hardmin, int hardmax, const char *ui_name, const char *ui_description,
2237                                int softmin, int softmax)
2238 {
2239         ContainerRNA *cont = cont_;
2240         PropertyRNA *prop;
2241         
2242         prop = RNA_def_property(cont, identifier, PROP_INT, PROP_NONE);
2243         if (len != 0) RNA_def_property_array(prop, len);
2244         if (default_value) RNA_def_property_int_array_default(prop, default_value);
2245         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2246         RNA_def_property_ui_text(prop, ui_name, ui_description);
2247         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2248
2249         return prop;
2250 }
2251
2252 PropertyRNA *RNA_def_string(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value, int maxlen,
2253                             const char *ui_name, const char *ui_description)
2254 {
2255         ContainerRNA *cont = cont_;
2256         PropertyRNA *prop;
2257         
2258         prop = RNA_def_property(cont, identifier, PROP_STRING, PROP_NONE);
2259         if (maxlen != 0) RNA_def_property_string_maxlength(prop, maxlen);
2260         if (default_value) RNA_def_property_string_default(prop, default_value);
2261         RNA_def_property_ui_text(prop, ui_name, ui_description);
2262
2263         return prop;
2264 }
2265
2266 PropertyRNA *RNA_def_string_file_path(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value,
2267                                       int maxlen, const char *ui_name, const char *ui_description)
2268 {
2269         ContainerRNA *cont = cont_;
2270         PropertyRNA *prop;
2271         
2272         prop = RNA_def_property(cont, identifier, PROP_STRING, PROP_FILEPATH);
2273         if (maxlen != 0) RNA_def_property_string_maxlength(prop, maxlen);
2274         if (default_value) RNA_def_property_string_default(prop, default_value);
2275         RNA_def_property_ui_text(prop, ui_name, ui_description);
2276
2277         return prop;
2278 }
2279
2280 PropertyRNA *RNA_def_string_dir_path(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value,
2281                                      int maxlen, const char *ui_name, const char *ui_description)
2282 {
2283         ContainerRNA *cont = cont_;
2284         PropertyRNA *prop;
2285         
2286         prop = RNA_def_property(cont, identifier, PROP_STRING, PROP_DIRPATH);
2287         if (maxlen != 0) RNA_def_property_string_maxlength(prop, maxlen);
2288         if (default_value) RNA_def_property_string_default(prop, default_value);
2289         RNA_def_property_ui_text(prop, ui_name, ui_description);
2290
2291         return prop;
2292 }
2293
2294 PropertyRNA *RNA_def_string_file_name(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value,
2295                                       int maxlen, const char *ui_name, const char *ui_description)
2296 {
2297         ContainerRNA *cont = cont_;
2298         PropertyRNA *prop;
2299         
2300         prop = RNA_def_property(cont, identifier, PROP_STRING, PROP_FILENAME);
2301         if (maxlen != 0) RNA_def_property_string_maxlength(prop, maxlen);
2302         if (default_value) RNA_def_property_string_default(prop, default_value);
2303         RNA_def_property_ui_text(prop, ui_name, ui_description);
2304
2305         return prop;
2306 }
2307
2308 PropertyRNA *RNA_def_string_translate(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value,
2309                                       int maxlen, const char *ui_name, const char *ui_description)
2310 {
2311         ContainerRNA *cont = cont_;
2312         PropertyRNA *prop;
2313
2314         prop = RNA_def_property(cont, identifier, PROP_STRING, PROP_TRANSLATE);
2315         if (maxlen != 0) RNA_def_property_string_maxlength(prop, maxlen);
2316         if (default_value) RNA_def_property_string_default(prop, default_value);
2317         RNA_def_property_ui_text(prop, ui_name, ui_description);
2318
2319         return prop;
2320 }
2321
2322 PropertyRNA *RNA_def_enum(StructOrFunctionRNA *cont_, const char *identifier, const EnumPropertyItem *items,
2323                           int default_value, const char *ui_name, const char *ui_description)
2324 {
2325         ContainerRNA *cont = cont_;
2326         PropertyRNA *prop;
2327
2328         if (!items) {
2329                 printf("%s: items not allowed to be NULL.\n", __func__);
2330                 return NULL;
2331         }
2332         
2333         prop = RNA_def_property(cont, identifier, PROP_ENUM, PROP_NONE);
2334         if (items) RNA_def_property_enum_items(prop, items);
2335         RNA_def_property_enum_default(prop, default_value);
2336         RNA_def_property_ui_text(prop, ui_name, ui_description);
2337
2338         return prop;
2339 }
2340
2341 /* same as above but sets 'PROP_ENUM_FLAG' before setting the default value */
2342 PropertyRNA *RNA_def_enum_flag(StructOrFunctionRNA *cont_, const char *identifier, const EnumPropertyItem *items,
2343                                int default_value, const char *ui_name, const char *ui_description)
2344 {
2345         ContainerRNA *cont = cont_;
2346         PropertyRNA *prop;
2347
2348         if (!items) {
2349                 printf("%s: items not allowed to be NULL.\n", __func__);
2350                 return NULL;
2351         }
2352
2353         prop = RNA_def_property(cont, identifier, PROP_ENUM, PROP_NONE);
2354         RNA_def_property_flag(prop, PROP_ENUM_FLAG); /* important to run before default set */
2355         if (items) RNA_def_property_enum_items(prop, items);
2356         RNA_def_property_enum_default(prop, default_value);
2357         RNA_def_property_ui_text(prop, ui_name, ui_description);
2358
2359         return prop;
2360 }
2361
2362 void RNA_def_enum_funcs(PropertyRNA *prop, EnumPropertyItemFunc itemfunc)
2363 {
2364         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
2365         eprop->itemf = itemfunc;
2366 }
2367
2368 void RNA_def_enum_py_data(PropertyRNA *prop, void *py_data)
2369 {
2370         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
2371         eprop->py_data = py_data;
2372 }
2373
2374 PropertyRNA *RNA_def_float(StructOrFunctionRNA *cont_, const char *identifier, float default_value,
2375                            float hardmin, float hardmax, const char *ui_name, const char *ui_description,
2376                            float softmin, float softmax)
2377 {
2378         ContainerRNA *cont = cont_;
2379         PropertyRNA *prop;
2380         
2381         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_NONE);
2382         RNA_def_property_float_default(prop, default_value);
2383         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2384         RNA_def_property_ui_text(prop, ui_name, ui_description);
2385         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2386
2387         return prop;
2388 }
2389
2390 PropertyRNA *RNA_def_float_vector(StructOrFunctionRNA *cont_, const char *identifier, int len,
2391                                   const float *default_value, float hardmin, float hardmax, const char *ui_name,
2392                                   const char *ui_description, float softmin, float softmax)
2393 {
2394         ContainerRNA *cont = cont_;
2395         PropertyRNA *prop;
2396         
2397         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_XYZ);
2398         if (len != 0) RNA_def_property_array(prop, len);
2399         if (default_value) RNA_def_property_float_array_default(prop, default_value);
2400         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2401         RNA_def_property_ui_text(prop, ui_name, ui_description);
2402         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2403
2404         return prop;
2405 }
2406
2407 PropertyRNA *RNA_def_float_vector_xyz(StructOrFunctionRNA *cont_, const char *identifier, int len,
2408                                       const float *default_value, float hardmin, float hardmax, const char *ui_name,
2409                                       const char *ui_description, float softmin, float softmax)
2410 {
2411         PropertyRNA *prop;
2412         
2413         prop = RNA_def_float_vector(cont_, identifier, len, default_value, hardmin, hardmax, ui_name, ui_description,
2414                                     softmin, softmax);
2415         prop->subtype = PROP_XYZ_LENGTH;
2416
2417         return prop;
2418 }
2419
2420 PropertyRNA *RNA_def_float_color(StructOrFunctionRNA *cont_, const char *identifier, int len,
2421                                  const float *default_value, float hardmin, float hardmax, const char *ui_name,
2422                                  const char *ui_description, float softmin, float softmax)
2423 {
2424         ContainerRNA *cont = cont_;
2425         PropertyRNA *prop;
2426         
2427         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_COLOR);
2428         if (len != 0) RNA_def_property_array(prop, len);
2429         if (default_value) RNA_def_property_float_array_default(prop, default_value);
2430         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2431         RNA_def_property_ui_text(prop, ui_name, ui_description);
2432         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2433
2434         return prop;
2435 }
2436
2437
2438 PropertyRNA *RNA_def_float_matrix(StructOrFunctionRNA *cont_, const char *identifier, int rows, int columns,
2439                                   const float *default_value, float hardmin, float hardmax, const char *ui_name,
2440                                   const char *ui_description, float softmin, float softmax)
2441 {
2442         ContainerRNA *cont = cont_;
2443         PropertyRNA *prop;
2444         int length[2];
2445
2446         length[0] = rows;
2447         length[1] = columns;
2448
2449         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_MATRIX);
2450         RNA_def_property_multi_array(prop, 2, length);
2451         if (default_value) RNA_def_property_float_array_default(prop, default_value);
2452         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2453         RNA_def_property_ui_text(prop, ui_name, ui_description);
2454         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2455
2456         return prop;
2457 }
2458
2459 PropertyRNA *RNA_def_float_rotation(StructOrFunctionRNA *cont_, const char *identifier, int len,
2460                                     const float *default_value, float hardmin, float hardmax, const char *ui_name,
2461                                     const char *ui_description, float softmin, float softmax)
2462 {
2463         ContainerRNA *cont = cont_;
2464         PropertyRNA *prop;
2465         
2466         prop = RNA_def_property(cont, identifier, PROP_FLOAT, (len != 0) ? PROP_EULER : PROP_ANGLE);
2467         if (len != 0) {
2468                 RNA_def_property_array(prop, len);
2469                 if (default_value) RNA_def_property_float_array_default(prop, default_value);
2470         }
2471         else {
2472                 /* RNA_def_property_float_default must be called outside */
2473                 BLI_assert(default_value == NULL);
2474         }
2475         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2476         RNA_def_property_ui_text(prop, ui_name, ui_description);
2477         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2478
2479         return prop;
2480 }
2481
2482 PropertyRNA *RNA_def_float_array(StructOrFunctionRNA *cont_, const char *identifier, int len,
2483                                  const float *default_value, float hardmin, float hardmax, const char *ui_name,
2484                                  const char *ui_description, float softmin, float softmax)
2485 {
2486         ContainerRNA *cont = cont_;
2487         PropertyRNA *prop;
2488         
2489         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_NONE);
2490         if (len != 0) RNA_def_property_array(prop, len);
2491         if (default_value) RNA_def_property_float_array_default(prop, default_value);
2492         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2493         RNA_def_property_ui_text(prop, ui_name, ui_description);
2494         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2495
2496         return prop;
2497 }
2498
2499 PropertyRNA *RNA_def_float_percentage(StructOrFunctionRNA *cont_, const char *identifier, float default_value,
2500                                       float hardmin, float hardmax, const char *ui_name, const char *ui_description,
2501                                       float softmin, float softmax)
2502 {
2503         ContainerRNA *cont = cont_;
2504         PropertyRNA *prop;
2505         
2506         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_PERCENTAGE);
2507         RNA_def_property_float_default(prop, default_value);
2508         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2509         RNA_def_property_ui_text(prop, ui_name, ui_description);
2510         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2511
2512         return prop;
2513 }
2514
2515 PropertyRNA *RNA_def_float_factor(StructOrFunctionRNA *cont_, const char *identifier, float default_value,
2516                                   float hardmin, float hardmax, const char *ui_name, const char *ui_description,
2517                                   float softmin, float softmax)
2518 {
2519         ContainerRNA *cont = cont_;
2520         PropertyRNA *prop;
2521         
2522         prop = RNA_def_property(cont, identifier, PROP_FLOAT, PROP_FACTOR);
2523         RNA_def_property_float_default(prop, default_value);
2524         if (hardmin != hardmax) RNA_def_property_range(prop, hardmin, hardmax);
2525         RNA_def_property_ui_text(prop, ui_name, ui_description);
2526         RNA_def_property_ui_range(prop, softmin, softmax, 1, 3);
2527
2528         return prop;
2529 }
2530
2531 PropertyRNA *RNA_def_pointer(StructOrFunctionRNA *cont_, const char *identifier, const char *type,
2532                              const char *ui_name, const char *ui_description)
2533 {
2534         ContainerRNA *cont = cont_;
2535         PropertyRNA *prop;
2536         
2537         prop = RNA_def_property(cont, identifier, PROP_POINTER, PROP_NONE);
2538         RNA_def_property_struct_type(prop, type);
2539         RNA_def_property_ui_text(prop, ui_name, ui_description);
2540
2541         return prop;
2542 }
2543
2544 PropertyRNA *RNA_def_pointer_runtime(StructOrFunctionRNA *cont_, const char *identifier, StructRNA *type,
2545                                      const char *ui_name, const char *ui_description)
2546 {
2547         ContainerRNA *cont = cont_;
2548         PropertyRNA *prop;
2549         
2550         prop = RNA_def_property(cont, identifier, PROP_POINTER, PROP_NONE);
2551         RNA_def_property_struct_runtime(prop, type);
2552         RNA_def_property_ui_text(prop, ui_name, ui_description);
2553
2554         return prop;
2555 }
2556
2557 PropertyRNA *RNA_def_collection(StructOrFunctionRNA *cont_, const char *identifier, const char *type,
2558                                 const char *ui_name, const char *ui_description)
2559 {
2560         ContainerRNA *cont = cont_;
2561         PropertyRNA *prop;
2562         
2563         prop = RNA_def_property(cont, identifier, PROP_COLLECTION, PROP_NONE);
2564         RNA_def_property_struct_type(prop, type);
2565         RNA_def_property_ui_text(prop, ui_name, ui_description);
2566
2567         return prop;
2568 }
2569
2570 PropertyRNA *RNA_def_collection_runtime(StructOrFunctionRNA *cont_, const char *identifier, StructRNA *type,
2571                                         const char *ui_name, const char *ui_description)
2572 {
2573         ContainerRNA *cont = cont_;
2574         PropertyRNA *prop;
2575         
2576         prop = RNA_def_property(cont, identifier, PROP_COLLECTION, PROP_NONE);
2577         RNA_def_property_struct_runtime(prop, type);
2578         RNA_def_property_ui_text(prop, ui_name, ui_description);
2579
2580         return prop;
2581 }
2582
2583 /* Function */
2584
2585 static FunctionRNA *rna_def_function(StructRNA *srna, const char *identifier)
2586 {
2587         FunctionRNA *func;
2588         StructDefRNA *dsrna;
2589         FunctionDefRNA *dfunc;
2590
2591         if (DefRNA.preprocess) {
2592                 char error[512];
2593
2594                 if (rna_validate_identifier(identifier, error, 0) == 0) {
2595                         fprintf(stderr, "%s: function identifier \"%s\" - %s\n", __func__, identifier, error);
2596                         DefRNA.error = 1;
2597                 }
2598         }
2599
2600         func = MEM_callocN(sizeof(FunctionRNA), "FunctionRNA");
2601         func->identifier = identifier;
2602         func->description = identifier;
2603
2604         rna_addtail(&srna->functions, func);
2605
2606         if (DefRNA.preprocess) {
2607                 dsrna = rna_find_struct_def(srna);
2608                 dfunc = MEM_callocN(sizeof(FunctionDefRNA), "FunctionDefRNA");
2609                 rna_addtail(&dsrna->functions, dfunc);
2610                 dfunc->func = func;
2611         }
2612         else
2613                 func->flag |= FUNC_RUNTIME;
2614
2615         return func;
2616 }
2617
2618 FunctionRNA *RNA_def_function(StructRNA *srna, const char *identifier, const char *call)
2619 {
2620         FunctionRNA *func;
2621         FunctionDefRNA *dfunc;
2622
2623         func = rna_def_function(srna, identifier);
2624
2625         if (!DefRNA.preprocess) {
2626                 fprintf(stderr, "%s: only at preprocess time.\n", __func__);
2627                 return func;
2628         }
2629
2630         dfunc = rna_find_function_def(func);
2631         dfunc->call = call;
2632
2633         return func;
2634 }
2635
2636 FunctionRNA *RNA_def_function_runtime(StructRNA *srna, const char *identifier, CallFunc call)
2637 {
2638         FunctionRNA *func;
2639
2640         func = rna_def_function(srna, identifier);
2641
2642         if (DefRNA.preprocess) {
2643                 fprintf(stderr, "%s: only at runtime.\n", __func__);
2644                 return func;
2645         }
2646
2647         func->call = call;
2648
2649
2650         return func;
2651 }
2652
2653 /* C return value only!, multiple RNA returns can be done with RNA_def_function_output */
2654 void RNA_def_function_return(FunctionRNA *func, PropertyRNA *ret)
2655 {
2656         if (ret->flag & PROP_DYNAMIC) {
2657                 fprintf(stderr, "%s: \"%s.%s\", dynamic values are not allowed as strict returns, "
2658                         "use RNA_def_function_output instead.\n", __func__, func->identifier, ret->identifier);
2659                 return;
2660         }
2661         else if (ret->arraydimension) {
2662                 fprintf(stderr, "%s: \"%s.%s\", arrays are not allowed as strict returns, "
2663                         "use RNA_def_function_output instead.\n", __func__, func->identifier, ret->identifier);
2664                 return;
2665         }
2666
2667         func->c_ret = ret;
2668
2669         RNA_def_function_output(func, ret);
2670 }
2671
2672 void RNA_def_function_output(FunctionRNA *UNUSED(func), PropertyRNA *ret)
2673 {
2674         ret->flag |= PROP_OUTPUT;
2675 }
2676
2677 void RNA_def_function_flag(FunctionRNA *func, int flag)
2678 {
2679         func->flag |= flag;
2680 }
2681
2682 void RNA_def_function_ui_description(FunctionRNA *func, const char *description)
2683 {
2684         func->description = description;
2685 }
2686
2687 int rna_parameter_size(PropertyRNA *parm)
2688 {
2689         PropertyType ptype = parm->type;
2690         int len = parm->totarraylength; /* only supports fixed length at the moment */
2691
2692         if (len > 0) {
2693                 /* XXX in other parts is mentioned that strings can be dynamic as well */
2694                 if (parm->flag & PROP_DYNAMIC)
2695                         return sizeof(void *);
2696
2697                 switch (ptype) {
2698                         case PROP_BOOLEAN:
2699                         case PROP_INT:
2700                                 return sizeof(int)*len;
2701                         case PROP_FLOAT:
2702                                 return sizeof(float)*len;
2703                         default:
2704                                 break;
2705                 }
2706         }
2707         else {
2708                 switch (ptype) {
2709                         case PROP_BOOLEAN:
2710                         case PROP_INT:
2711                         case PROP_ENUM:
2712                                 return sizeof(int);
2713                         case PROP_FLOAT:
2714                                 return sizeof(float);
2715                         case PROP_STRING:
2716                                 /* return values don't store a pointer to the original */
2717                                 if (parm->flag & PROP_THICK_WRAP) {
2718                                         StringPropertyRNA *sparm = (StringPropertyRNA*)parm;
2719                                         return sizeof(char) * sparm->maxlength;
2720                                 } else
2721                                         return sizeof(char *);
2722                         case PROP_POINTER: {
2723 #ifdef RNA_RUNTIME
2724                                 if (parm->flag & PROP_RNAPTR)
2725                                         return sizeof(PointerRNA);
2726                                 else
2727                                         return sizeof(void *);
2728 #else
2729                                 if (parm->flag & PROP_RNAPTR)
2730                                         return sizeof(PointerRNA);
2731                                 else
2732                                         return sizeof(void *);
2733 #endif
2734                         }
2735                         case PROP_COLLECTION:
2736                                 return sizeof(ListBase);
2737                 }
2738         }
2739
2740         return sizeof(void *);
2741 }
2742
2743 /* this function returns the size of the memory allocated for the parameter,
2744  * useful for instance for memory alignment or for storing additional information */
2745 int rna_parameter_size_alloc(PropertyRNA *parm)
2746 {
2747         int size = rna_parameter_size(parm);
2748
2749         if (parm->flag & PROP_DYNAMIC)
2750                 size += sizeof(((ParameterDynAlloc *)NULL)->array_tot);
2751
2752         return size;
2753 }
2754
2755 /* Dynamic Enums */
2756
2757 void RNA_enum_item_add(EnumPropertyItem **items, int *totitem, const EnumPropertyItem *item)
2758 {
2759         EnumPropertyItem *newitems;
2760         int tot = *totitem;
2761
2762         if (tot == 0) {
2763                 *items = MEM_callocN(sizeof(EnumPropertyItem)*8, "RNA_enum_items_add");
2764         }
2765         else if (tot >= 8 && (tot&(tot-1)) == 0){
2766                 /* power of two > 8 */
2767                 newitems = MEM_callocN(sizeof(EnumPropertyItem)*tot*2, "RNA_enum_items_add");
2768                 memcpy(newitems, *items, sizeof(EnumPropertyItem)*tot);
2769                 MEM_freeN(*items);
2770                 *items = newitems;
2771         }
2772
2773         (*items)[tot] = *item;
2774         *totitem = tot+1;
2775 }
2776
2777 void RNA_enum_item_add_separator(EnumPropertyItem **items, int *totitem)
2778 {
2779         static EnumPropertyItem sepr = {0, "", 0, NULL, NULL};
2780         RNA_enum_item_add(items, totitem, &sepr);
2781 }
2782
2783 void RNA_enum_items_add(EnumPropertyItem **items, int *totitem, EnumPropertyItem *item)
2784 {
2785         for (; item->identifier; item++)
2786                 RNA_enum_item_add(items, totitem, item);
2787 }
2788
2789 void RNA_enum_items_add_value(EnumPropertyItem **items, int *totitem, EnumPropertyItem *item, int value)
2790 {
2791         for (; item->identifier; item++) {
2792                 if (item->value == value) {
2793                         RNA_enum_item_add(items, totitem, item);
2794                         /* break on first match - does this break anything?
2795                          * (is quick hack to get object->parent_type working ok for armature/lattice) */
2796                         break;
2797                 }
2798         }
2799 }
2800
2801 void RNA_enum_item_end(EnumPropertyItem **items, int *totitem)
2802 {
2803         static EnumPropertyItem empty = {0, NULL, 0, NULL, NULL};
2804         RNA_enum_item_add(items, totitem, &empty);
2805 }
2806
2807 /* Memory management */
2808
2809 #ifdef RNA_RUNTIME
2810 void RNA_def_struct_duplicate_pointers(StructRNA *srna)
2811 {
2812         if (srna->identifier) srna->identifier = BLI_strdup(srna->identifier);
2813         if (srna->name) srna->name = BLI_strdup(srna->name);
2814         if (srna->description) srna->description = BLI_strdup(srna->description);
2815
2816         srna->flag |= STRUCT_FREE_POINTERS;
2817 }
2818
2819 void RNA_def_struct_free_pointers(StructRNA *srna)
2820 {
2821         if (srna->flag & STRUCT_FREE_POINTERS) {
2822                 if (srna->identifier) MEM_freeN((void*)srna->identifier);
2823                 if (srna->name) MEM_freeN((void*)srna->name);
2824                 if (srna->description) MEM_freeN((void*)srna->description);
2825         }
2826 }
2827
2828 void RNA_def_func_duplicate_pointers(FunctionRNA *func)
2829 {
2830         if (func->identifier) func->identifier = BLI_strdup(func->identifier);
2831         if (func->description) func->description = BLI_strdup(func->description);
2832
2833         func->flag |= FUNC_FREE_POINTERS;
2834 }
2835
2836 void RNA_def_func_free_pointers(FunctionRNA *func)
2837 {
2838         if (func->flag & FUNC_FREE_POINTERS) {
2839                 if (func->identifier) MEM_freeN((void*)func->identifier);
2840                 if (func->description) MEM_freeN((void*)func->description);
2841         }
2842 }
2843
2844 void RNA_def_property_duplicate_pointers(StructOrFunctionRNA *cont_, PropertyRNA *prop)
2845 {
2846         ContainerRNA *cont = cont_;
2847         EnumPropertyItem *earray;
2848         float *farray;
2849         int *iarray;
2850         int a;
2851
2852         /* annoying since we just added this to a hash, could make this add the correct key to the hash
2853          * in the first place */
2854         if (prop->identifier) {
2855                 if (cont->prophash) {
2856                         BLI_ghash_remove(cont->prophash, (void*)prop->identifier, NULL, NULL);
2857                         prop->identifier = BLI_strdup(prop->identifier);
2858                         BLI_ghash_insert(cont->prophash, (void*)prop->identifier, prop);
2859                 }
2860                 else {
2861                         prop->identifier = BLI_strdup(prop->identifier);
2862                 }
2863         }
2864
2865         if (prop->name) prop->name = BLI_strdup(prop->name);
2866         if (prop->description) prop->description = BLI_strdup(prop->description);
2867
2868         switch (prop->type) {
2869                 case PROP_BOOLEAN: {
2870                         BoolPropertyRNA *bprop = (BoolPropertyRNA*)prop;
2871
2872                         if (bprop->defaultarray) {
2873                                 iarray = MEM_callocN(sizeof(int)*prop->totarraylength, "RNA_def_property_store");
2874                                 memcpy(iarray, bprop->defaultarray, sizeof(int)*prop->totarraylength);
2875                                 bprop->defaultarray = iarray;
2876                         }
2877                         break;
2878                 }
2879                 case PROP_INT: {
2880                         IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
2881
2882                         if (iprop->defaultarray) {
2883                                 iarray = MEM_callocN(sizeof(int)*prop->totarraylength, "RNA_def_property_store");
2884                                 memcpy(iarray, iprop->defaultarray, sizeof(int)*prop->totarraylength);
2885                                 iprop->defaultarray = iarray;
2886                         }
2887                         break;
2888                 }
2889                 case PROP_ENUM: {
2890                         EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
2891
2892                         if (eprop->item) {
2893                                 earray = MEM_callocN(sizeof(EnumPropertyItem)*(eprop->totitem+1), "RNA_def_property_store"),
2894                                 memcpy(earray, eprop->item, sizeof(EnumPropertyItem)*(eprop->totitem+1));
2895                                 eprop->item = earray;
2896
2897                                 for (a = 0; a<eprop->totitem; a++) {
2898                                         if (eprop->item[a].identifier)
2899                                                 eprop->item[a].identifier = BLI_strdup(eprop->item[a].identifier);
2900                                         if (eprop->item[a].name)
2901                                                 eprop->item[a].name = BLI_strdup(eprop->item[a].name);
2902                                         if (eprop->item[a].description)
2903                                                 eprop->item[a].description = BLI_strdup(eprop->item[a].description);
2904                                 }
2905                         }
2906                         break;
2907                 }
2908                 case PROP_FLOAT: {
2909                         FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
2910
2911                         if (fprop->defaultarray) {
2912                                 farray = MEM_callocN(sizeof(float)*prop->totarraylength, "RNA_def_property_store");
2913                                 memcpy(farray, fprop->defaultarray, sizeof(float)*prop->totarraylength);
2914                                 fprop->defaultarray = farray;
2915                         }
2916                         break;
2917                 }
2918                 case PROP_STRING: {
2919                         StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
2920                         if (sprop->defaultvalue)
2921                                 sprop->defaultvalue = BLI_strdup(sprop->defaultvalue);
2922                         break;
2923                 }
2924                 default:
2925                         break;
2926         }
2927
2928         prop->flag |= PROP_FREE_POINTERS;
2929 }
2930
2931 void RNA_def_property_free_pointers(PropertyRNA *prop)
2932 {
2933         if (prop->flag & PROP_FREE_POINTERS) {
2934                 int a;
2935
2936                 if (prop->identifier)
2937                         MEM_freeN((void*)prop->identifier);
2938                 if (prop->name)
2939                         MEM_freeN((void*)prop->name);
2940                 if (prop->description)
2941                         MEM_freeN((void*)prop->description);
2942                 if (prop->py_data)
2943                         MEM_freeN(prop->py_data);
2944
2945                 switch (prop->type) {
2946                         case PROP_BOOLEAN: {
2947                                 BoolPropertyRNA *bprop = (BoolPropertyRNA*)prop;
2948                                 if (bprop->defaultarray)
2949                                         MEM_freeN((void*)bprop->defaultarray);
2950                                 break;
2951                         }
2952                         case PROP_INT: {
2953                                 IntPropertyRNA *iprop = (IntPropertyRNA*)prop;
2954                                 if (iprop->defaultarray)
2955                                         MEM_freeN((void*)iprop->defaultarray);
2956                                 break;
2957                         }
2958                         case PROP_FLOAT: {
2959                                 FloatPropertyRNA *fprop = (FloatPropertyRNA*)prop;
2960                                 if (fprop->defaultarray)
2961                                         MEM_freeN((void*)fprop->defaultarray);
2962                                 break;
2963                         }
2964                         case PROP_ENUM: {
2965                                 EnumPropertyRNA *eprop = (EnumPropertyRNA*)prop;
2966
2967                                 for (a = 0; a<eprop->totitem; a++) {
2968                                         if (eprop->item[a].identifier)
2969                                                 MEM_freeN((void*)eprop->item[a].identifier);
2970                                         if (eprop->item[a].name)
2971                                                 MEM_freeN((void*)eprop->item[a].name);
2972                                         if (eprop->item[a].description)
2973                                                 MEM_freeN((void*)eprop->item[a].description);
2974                                 }
2975
2976                                 if (eprop->item) MEM_freeN((void*)eprop->item);
2977                                 break;
2978                         }
2979                         case PROP_STRING: {
2980                                 StringPropertyRNA *sprop = (StringPropertyRNA*)prop;
2981                                 if (sprop->defaultvalue)
2982                                         MEM_freeN((void*)sprop->defaultvalue);
2983                                 break;
2984                         }
2985                         default:
2986                                 break;
2987                 }
2988         }
2989 }
2990
2991 static void rna_def_property_free(StructOrFunctionRNA *cont_, PropertyRNA *prop)
2992 {
2993         ContainerRNA *cont = cont_;
2994         
2995         if (prop->flag & PROP_RUNTIME) {
2996                 if (cont->prophash)
2997                         BLI_ghash_remove(cont->prophash, (void*)prop->identifier, NULL, NULL);
2998
2999                 RNA_def_property_free_pointers(prop);
3000                 rna_freelinkN(&cont->properties, prop);
3001         }
3002         else {
3003                 RNA_def_property_free_pointers(prop);
3004         }
3005 }
3006
3007 /* note: only intended for removing dynamic props */
3008 int RNA_def_property_free_identifier(StructOrFunctionRNA *cont_, const char *identifier)
3009 {
3010         ContainerRNA *cont = cont_;
3011         PropertyRNA *prop;
3012         
3013         for (prop = cont->properties.first; prop; prop = prop->next) {
3014                 if (strcmp(prop->identifier, identifier) == 0) {
3015                         if (prop->flag & PROP_RUNTIME) {
3016                                 rna_def_property_free(cont_, prop);
3017                                 return 1;
3018                         }
3019                         else {
3020                                 return -1;
3021                         }
3022                 }
3023         }
3024         return 0;
3025 }
3026 #endif
3027
3028 const char *RNA_property_typename(PropertyType type)
3029 {
3030         switch (type) {
3031                 case PROP_BOOLEAN: return "PROP_BOOLEAN";
3032                 case PROP_INT: return "PROP_INT";
3033                 case PROP_FLOAT: return "PROP_FLOAT";
3034                 case PROP_STRING: return "PROP_STRING";
3035                 case PROP_ENUM: return "PROP_ENUM";
3036                 case PROP_POINTER: return "PROP_POINTER";
3037                 case PROP_COLLECTION: return "PROP_COLLECTION";
3038         }
3039
3040         return "PROP_UNKNOWN";
3041 }