1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  */
16 
17 /** \file
18  * \ingroup RNA
19  */
20 
21 #include <stdlib.h>
22 
23 #include "RNA_access.h"
24 #include "RNA_define.h"
25 #include "RNA_enum_types.h"
26 
27 #include "rna_internal.h"
28 
29 #include "DNA_customdata_types.h"
30 #include "DNA_hair_types.h"
31 #include "DNA_mesh_types.h"
32 #include "DNA_meshdata_types.h"
33 #include "DNA_pointcloud_types.h"
34 
35 #include "BKE_attribute.h"
36 #include "BKE_customdata.h"
37 
38 #include "WM_types.h"
39 
40 const EnumPropertyItem rna_enum_attribute_type_items[] = {
41     {CD_PROP_FLOAT, "FLOAT", 0, "Float", "Floating point value"},
42     {CD_PROP_INT32, "INT", 0, "Integer", "32 bit integer"},
43     {CD_PROP_FLOAT3, "FLOAT_VECTOR", 0, "Vector", "3D vector with floating point values"},
44     {CD_PROP_COLOR, "FLOAT_COLOR", 0, "Float Color", "RGBA color with floating point precisions"},
45     {CD_MLOOPCOL, "BYTE_COLOR", 0, "Byte Color", "RGBA color with 8-bit precision"},
46     {CD_PROP_STRING, "STRING", 0, "String", "Text string"},
47     {0, NULL, 0, NULL, NULL},
48 };
49 
50 const EnumPropertyItem rna_enum_attribute_domain_items[] = {
51     /* Not implement yet */
52     // {ATTR_DOMAIN_GEOMETRY, "GEOMETRY", 0, "Geometry", "Attribute on (whole) geometry"},
53     {ATTR_DOMAIN_VERTEX, "VERTEX", 0, "Vertex", "Attribute on mesh vertex"},
54     {ATTR_DOMAIN_EDGE, "EDGE", 0, "Edge", "Attribute on mesh edge"},
55     {ATTR_DOMAIN_CORNER, "CORNER", 0, "Corner", "Attribute on mesh polygon corner"},
56     {ATTR_DOMAIN_POLYGON, "POLYGON", 0, "Polygon", "Attribute on mesh polygons"},
57     /* Not implement yet */
58     // {ATTR_DOMAIN_GRIDS, "GRIDS", 0, "Grids", "Attribute on mesh multires grids"},
59     {ATTR_DOMAIN_POINT, "POINT", 0, "Point", "Attribute on point"},
60     {ATTR_DOMAIN_CURVE, "CURVE", 0, "Curve", "Attribute on hair curve"},
61     {0, NULL, 0, NULL, NULL},
62 };
63 
64 #ifdef RNA_RUNTIME
65 
66 #  include "BLI_math.h"
67 
68 #  include "DEG_depsgraph.h"
69 
70 #  include "BLT_translation.h"
71 
72 #  include "WM_api.h"
73 
74 /* Attribute */
75 
rna_Attribute_path(PointerRNA * ptr)76 static char *rna_Attribute_path(PointerRNA *ptr)
77 {
78   CustomDataLayer *layer = ptr->data;
79   return BLI_sprintfN("attributes['%s']", layer->name);
80 }
81 
rna_Attribute_name_set(PointerRNA * ptr,const char * value)82 static void rna_Attribute_name_set(PointerRNA *ptr, const char *value)
83 {
84   BKE_id_attribute_rename(ptr->owner_id, ptr->data, value, NULL);
85 }
86 
rna_Attribute_name_editable(PointerRNA * ptr,const char ** r_info)87 static int rna_Attribute_name_editable(PointerRNA *ptr, const char **r_info)
88 {
89   CustomDataLayer *layer = ptr->data;
90   if (BKE_id_attribute_required(ptr->owner_id, layer)) {
91     *r_info = N_("Can't modify name of required geometry attribute");
92     return false;
93   }
94 
95   return true;
96 }
97 
rna_Attribute_type_get(PointerRNA * ptr)98 static int rna_Attribute_type_get(PointerRNA *ptr)
99 {
100   CustomDataLayer *layer = ptr->data;
101   return layer->type;
102 }
103 
rna_enum_attribute_domain_itemf(ID * id,bool * r_free)104 const EnumPropertyItem *rna_enum_attribute_domain_itemf(ID *id, bool *r_free)
105 {
106   EnumPropertyItem *item = NULL;
107   const EnumPropertyItem *domain_item = NULL;
108   const ID_Type id_type = GS(id->name);
109   int totitem = 0, a;
110 
111   for (a = 0; rna_enum_attribute_domain_items[a].identifier; a++) {
112     domain_item = &rna_enum_attribute_domain_items[a];
113 
114     if (id_type == ID_PT && !ELEM(domain_item->value, ATTR_DOMAIN_POINT)) {
115       continue;
116     }
117     if (id_type == ID_HA && !ELEM(domain_item->value, ATTR_DOMAIN_POINT, ATTR_DOMAIN_CURVE)) {
118       continue;
119     }
120     if (id_type == ID_ME && ELEM(domain_item->value, ATTR_DOMAIN_POINT, ATTR_DOMAIN_CURVE)) {
121       continue;
122     }
123 
124     RNA_enum_item_add(&item, &totitem, domain_item);
125   }
126   RNA_enum_item_end(&item, &totitem);
127 
128   *r_free = true;
129   return item;
130 }
131 
rna_Attribute_domain_itemf(bContext * UNUSED (C),PointerRNA * ptr,PropertyRNA * UNUSED (prop),bool * r_free)132 static const EnumPropertyItem *rna_Attribute_domain_itemf(bContext *UNUSED(C),
133                                                           PointerRNA *ptr,
134                                                           PropertyRNA *UNUSED(prop),
135                                                           bool *r_free)
136 {
137   return rna_enum_attribute_domain_itemf(ptr->owner_id, r_free);
138 }
139 
rna_Attribute_domain_get(PointerRNA * ptr)140 static int rna_Attribute_domain_get(PointerRNA *ptr)
141 {
142   return BKE_id_attribute_domain(ptr->owner_id, ptr->data);
143 }
144 
rna_Attribute_data_begin(CollectionPropertyIterator * iter,PointerRNA * ptr)145 static void rna_Attribute_data_begin(CollectionPropertyIterator *iter, PointerRNA *ptr)
146 {
147   ID *id = ptr->owner_id;
148   CustomDataLayer *layer = (CustomDataLayer *)ptr->data;
149 
150   int length = BKE_id_attribute_data_length(id, layer);
151   size_t struct_size;
152 
153   switch (layer->type) {
154     case CD_PROP_FLOAT:
155       struct_size = sizeof(MFloatProperty);
156       break;
157     case CD_PROP_INT32:
158       struct_size = sizeof(MIntProperty);
159       break;
160     case CD_PROP_FLOAT3:
161       struct_size = sizeof(float[3]);
162       break;
163     case CD_PROP_COLOR:
164       struct_size = sizeof(MPropCol);
165       break;
166     case CD_MLOOPCOL:
167       struct_size = sizeof(MLoopCol);
168       break;
169     case CD_PROP_STRING:
170       struct_size = sizeof(MStringProperty);
171       break;
172     default:
173       struct_size = 0;
174       length = 0;
175       break;
176   }
177 
178   rna_iterator_array_begin(iter, layer->data, struct_size, length, 0, NULL);
179 }
180 
rna_Attribute_data_length(PointerRNA * ptr)181 static int rna_Attribute_data_length(PointerRNA *ptr)
182 {
183   ID *id = ptr->owner_id;
184   CustomDataLayer *layer = (CustomDataLayer *)ptr->data;
185   return BKE_id_attribute_data_length(id, layer);
186 }
187 
rna_Attribute_update_data(Main * UNUSED (bmain),Scene * UNUSED (scene),PointerRNA * ptr)188 static void rna_Attribute_update_data(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr)
189 {
190   ID *id = ptr->owner_id;
191 
192   /* cheating way for importers to avoid slow updates */
193   if (id->us > 0) {
194     DEG_id_tag_update(id, 0);
195     WM_main_add_notifier(NC_GEOM | ND_DATA, id);
196   }
197 }
198 
199 /* Color Attribute */
200 
rna_ByteColorAttributeValue_color_get(PointerRNA * ptr,float * values)201 static void rna_ByteColorAttributeValue_color_get(PointerRNA *ptr, float *values)
202 {
203   MLoopCol *mlcol = (MLoopCol *)ptr->data;
204   srgb_to_linearrgb_uchar4(values, &mlcol->r);
205 }
206 
rna_ByteColorAttributeValue_color_set(PointerRNA * ptr,const float * values)207 static void rna_ByteColorAttributeValue_color_set(PointerRNA *ptr, const float *values)
208 {
209   MLoopCol *mlcol = (MLoopCol *)ptr->data;
210   linearrgb_to_srgb_uchar4(&mlcol->r, values);
211 }
212 
213 /* Attribute Group */
214 
rna_AttributeGroup_new(ID * id,ReportList * reports,const char * name,const int type,const int domain)215 static PointerRNA rna_AttributeGroup_new(
216     ID *id, ReportList *reports, const char *name, const int type, const int domain)
217 {
218   CustomDataLayer *layer = BKE_id_attribute_new(id, name, type, domain, reports);
219   DEG_id_tag_update(id, ID_RECALC_GEOMETRY);
220   WM_main_add_notifier(NC_GEOM | ND_DATA, id);
221 
222   PointerRNA ptr;
223   RNA_pointer_create(id, &RNA_Attribute, layer, &ptr);
224   return ptr;
225 }
226 
rna_AttributeGroup_remove(ID * id,ReportList * reports,PointerRNA * attribute_ptr)227 static void rna_AttributeGroup_remove(ID *id, ReportList *reports, PointerRNA *attribute_ptr)
228 {
229   CustomDataLayer *layer = (CustomDataLayer *)attribute_ptr->data;
230   BKE_id_attribute_remove(id, layer, reports);
231   RNA_POINTER_INVALIDATE(attribute_ptr);
232 
233   DEG_id_tag_update(id, ID_RECALC_GEOMETRY);
234   WM_main_add_notifier(NC_GEOM | ND_DATA, id);
235 }
236 
rna_Attributes_layer_skip(CollectionPropertyIterator * UNUSED (iter),void * data)237 static int rna_Attributes_layer_skip(CollectionPropertyIterator *UNUSED(iter), void *data)
238 {
239   CustomDataLayer *layer = (CustomDataLayer *)data;
240   return !(CD_TYPE_AS_MASK(layer->type) & CD_MASK_PROP_ALL);
241 }
242 
243 /* Attributes are spread over multiple domains in separate CustomData, we use repeated
244  * array iterators to loop over all. */
rna_AttributeGroup_next_domain(ID * id,CollectionPropertyIterator * iter,int (skip)(CollectionPropertyIterator * iter,void * data))245 static void rna_AttributeGroup_next_domain(ID *id,
246                                            CollectionPropertyIterator *iter,
247                                            int(skip)(CollectionPropertyIterator *iter, void *data))
248 {
249   do {
250     CustomDataLayer *prev_layers = (CustomDataLayer *)iter->internal.array.endptr -
251                                    iter->internal.array.length;
252     CustomData *customdata = BKE_id_attributes_iterator_next_domain(id, prev_layers);
253     if (customdata == NULL) {
254       return;
255     }
256     rna_iterator_array_begin(
257         iter, customdata->layers, sizeof(CustomDataLayer), customdata->totlayer, false, skip);
258   } while (!iter->valid);
259 }
260 
rna_AttributeGroup_iterator_begin(CollectionPropertyIterator * iter,PointerRNA * ptr)261 void rna_AttributeGroup_iterator_begin(CollectionPropertyIterator *iter, PointerRNA *ptr)
262 {
263   memset(&iter->internal.array, 0, sizeof(iter->internal.array));
264   rna_AttributeGroup_next_domain(ptr->owner_id, iter, rna_Attributes_layer_skip);
265 }
266 
rna_AttributeGroup_iterator_next(CollectionPropertyIterator * iter)267 void rna_AttributeGroup_iterator_next(CollectionPropertyIterator *iter)
268 {
269   rna_iterator_array_next(iter);
270 
271   if (!iter->valid) {
272     ID *id = iter->parent.owner_id;
273     rna_AttributeGroup_next_domain(id, iter, rna_Attributes_layer_skip);
274   }
275 }
276 
rna_AttributeGroup_iterator_get(CollectionPropertyIterator * iter)277 PointerRNA rna_AttributeGroup_iterator_get(CollectionPropertyIterator *iter)
278 {
279   /* refine to the proper type */
280   StructRNA *type;
281   CustomDataLayer *layer = rna_iterator_array_get(iter);
282 
283   switch (layer->type) {
284     case CD_PROP_FLOAT:
285       type = &RNA_FloatAttribute;
286       break;
287     case CD_PROP_INT32:
288       type = &RNA_IntAttribute;
289       break;
290     case CD_PROP_FLOAT3:
291       type = &RNA_FloatVectorAttribute;
292       break;
293     case CD_PROP_COLOR:
294       type = &RNA_FloatColorAttribute;
295       break;
296     case CD_MLOOPCOL:
297       type = &RNA_ByteColorAttribute;
298       break;
299     case CD_PROP_STRING:
300       type = &RNA_StringAttribute;
301       break;
302     default:
303       return PointerRNA_NULL;
304   }
305 
306   return rna_pointer_inherit_refine(&iter->parent, type, layer);
307 }
308 
rna_AttributeGroup_length(PointerRNA * ptr)309 int rna_AttributeGroup_length(PointerRNA *ptr)
310 {
311   return BKE_id_attributes_length(ptr->owner_id, CD_MASK_PROP_ALL);
312 }
313 
rna_AttributeGroup_active_index_get(PointerRNA * ptr)314 static int rna_AttributeGroup_active_index_get(PointerRNA *ptr)
315 {
316   return *BKE_id_attributes_active_index_p(ptr->owner_id);
317 }
318 
rna_AttributeGroup_active_get(PointerRNA * ptr)319 static PointerRNA rna_AttributeGroup_active_get(PointerRNA *ptr)
320 {
321   ID *id = ptr->owner_id;
322   CustomDataLayer *layer = BKE_id_attributes_active_get(id);
323 
324   PointerRNA attribute_ptr;
325   RNA_pointer_create(id, &RNA_Attribute, layer, &attribute_ptr);
326   return attribute_ptr;
327 }
328 
rna_AttributeGroup_active_set(PointerRNA * ptr,PointerRNA attribute_ptr,ReportList * UNUSED (reports))329 static void rna_AttributeGroup_active_set(PointerRNA *ptr,
330                                           PointerRNA attribute_ptr,
331                                           ReportList *UNUSED(reports))
332 {
333   ID *id = ptr->owner_id;
334   CustomDataLayer *layer = attribute_ptr.data;
335   BKE_id_attributes_active_set(id, layer);
336 }
337 
rna_AttributeGroup_active_index_set(PointerRNA * ptr,int value)338 static void rna_AttributeGroup_active_index_set(PointerRNA *ptr, int value)
339 {
340   *BKE_id_attributes_active_index_p(ptr->owner_id) = value;
341 }
342 
rna_AttributeGroup_active_index_range(PointerRNA * ptr,int * min,int * max,int * softmin,int * softmax)343 static void rna_AttributeGroup_active_index_range(
344     PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax)
345 {
346   *min = 0;
347   *max = BKE_id_attributes_length(ptr->owner_id, CD_MASK_PROP_ALL);
348 
349   *softmin = *min;
350   *softmax = *max;
351 }
352 
rna_AttributeGroup_update_active(Main * bmain,Scene * scene,PointerRNA * ptr)353 static void rna_AttributeGroup_update_active(Main *bmain, Scene *scene, PointerRNA *ptr)
354 {
355   rna_Attribute_update_data(bmain, scene, ptr);
356 }
357 
358 #else
359 
rna_def_attribute_float(BlenderRNA * brna)360 static void rna_def_attribute_float(BlenderRNA *brna)
361 {
362   StructRNA *srna;
363   PropertyRNA *prop;
364 
365   srna = RNA_def_struct(brna, "FloatAttribute", "Attribute");
366   RNA_def_struct_sdna(srna, "CustomDataLayer");
367   RNA_def_struct_ui_text(srna, "Float Attribute", "Geometry attribute with floating point values");
368 
369   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
370   RNA_def_property_struct_type(prop, "FloatAttributeValue");
371   RNA_def_property_collection_funcs(prop,
372                                     "rna_Attribute_data_begin",
373                                     "rna_iterator_array_next",
374                                     "rna_iterator_array_end",
375                                     "rna_iterator_array_get",
376                                     "rna_Attribute_data_length",
377                                     NULL,
378                                     NULL,
379                                     NULL);
380 
381   srna = RNA_def_struct(brna, "FloatAttributeValue", NULL);
382   RNA_def_struct_sdna(srna, "MFloatProperty");
383   RNA_def_struct_ui_text(
384       srna, "Float Attribute Value", "Floating point value in geometry attribute");
385   prop = RNA_def_property(srna, "value", PROP_FLOAT, PROP_NONE);
386   RNA_def_property_float_sdna(prop, NULL, "f");
387   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
388 }
389 
rna_def_attribute_float_vector(BlenderRNA * brna)390 static void rna_def_attribute_float_vector(BlenderRNA *brna)
391 {
392   StructRNA *srna;
393   PropertyRNA *prop;
394 
395   /* Float Vector Attribute */
396   srna = RNA_def_struct(brna, "FloatVectorAttribute", "Attribute");
397   RNA_def_struct_sdna(srna, "CustomDataLayer");
398   RNA_def_struct_ui_text(
399       srna, "Float Vector Attribute", "Vector geometry attribute, with floating point precision");
400 
401   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
402   RNA_def_property_struct_type(prop, "FloatVectorAttributeValue");
403   RNA_def_property_collection_funcs(prop,
404                                     "rna_Attribute_data_begin",
405                                     "rna_iterator_array_next",
406                                     "rna_iterator_array_end",
407                                     "rna_iterator_array_get",
408                                     "rna_Attribute_data_length",
409                                     NULL,
410                                     NULL,
411                                     NULL);
412 
413   /* Float Vector Attribute Value */
414   srna = RNA_def_struct(brna, "FloatVectorAttributeValue", NULL);
415   RNA_def_struct_sdna(srna, "vec3f");
416   RNA_def_struct_ui_text(
417       srna, "Float Vector Attribute Value", "Vector value in geometry attribute");
418 
419   prop = RNA_def_property(srna, "vector", PROP_FLOAT, PROP_DIRECTION);
420   RNA_def_property_ui_text(prop, "Vector", "3D vector");
421   RNA_def_property_float_sdna(prop, NULL, "x");
422   RNA_def_property_array(prop, 3);
423   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
424 }
425 
rna_def_attribute_float_color(BlenderRNA * brna)426 static void rna_def_attribute_float_color(BlenderRNA *brna)
427 {
428   StructRNA *srna;
429   PropertyRNA *prop;
430 
431   /* Float Color Attribute */
432   srna = RNA_def_struct(brna, "FloatColorAttribute", "Attribute");
433   RNA_def_struct_sdna(srna, "CustomDataLayer");
434   RNA_def_struct_ui_text(
435       srna, "Float Color Attribute", "Color geometry attribute, with floating point precision");
436 
437   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
438   RNA_def_property_struct_type(prop, "FloatColorAttributeValue");
439   RNA_def_property_collection_funcs(prop,
440                                     "rna_Attribute_data_begin",
441                                     "rna_iterator_array_next",
442                                     "rna_iterator_array_end",
443                                     "rna_iterator_array_get",
444                                     "rna_Attribute_data_length",
445                                     NULL,
446                                     NULL,
447                                     NULL);
448 
449   /* Float Color Attribute Value */
450   srna = RNA_def_struct(brna, "FloatColorAttributeValue", NULL);
451   RNA_def_struct_sdna(srna, "MPropCol");
452   RNA_def_struct_ui_text(srna, "Float Color Attribute Value", "Color value in geometry attribute");
453 
454   prop = RNA_def_property(srna, "color", PROP_FLOAT, PROP_COLOR);
455   RNA_def_property_ui_text(prop, "Color", "RGBA color in scene linear color space");
456   RNA_def_property_float_sdna(prop, NULL, "color");
457   RNA_def_property_array(prop, 4);
458   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
459 }
460 
rna_def_attribute_byte_color(BlenderRNA * brna)461 static void rna_def_attribute_byte_color(BlenderRNA *brna)
462 {
463   StructRNA *srna;
464   PropertyRNA *prop;
465 
466   /* Byte Color Attribute */
467   srna = RNA_def_struct(brna, "ByteColorAttribute", "Attribute");
468   RNA_def_struct_sdna(srna, "CustomDataLayer");
469   RNA_def_struct_ui_text(
470       srna, "Byte Color Attribute", "Color geometry attribute, with 8-bit precision");
471 
472   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
473   RNA_def_property_struct_type(prop, "ByteColorAttributeValue");
474   RNA_def_property_collection_funcs(prop,
475                                     "rna_Attribute_data_begin",
476                                     "rna_iterator_array_next",
477                                     "rna_iterator_array_end",
478                                     "rna_iterator_array_get",
479                                     "rna_Attribute_data_length",
480                                     NULL,
481                                     NULL,
482                                     NULL);
483 
484   /* Byte Color Attribute Value */
485   srna = RNA_def_struct(brna, "ByteColorAttributeValue", NULL);
486   RNA_def_struct_sdna(srna, "MLoopCol");
487   RNA_def_struct_ui_text(srna, "Byte Color Attribute Value", "Color value in geometry attribute");
488 
489   prop = RNA_def_property(srna, "color", PROP_FLOAT, PROP_COLOR);
490   RNA_def_property_array(prop, 4);
491   RNA_def_property_range(prop, 0.0f, 1.0f);
492   RNA_def_property_float_funcs(prop,
493                                "rna_ByteColorAttributeValue_color_get",
494                                "rna_ByteColorAttributeValue_color_set",
495                                NULL);
496   RNA_def_property_ui_text(prop, "Color", "RGBA color in scene linear color space");
497   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
498 }
499 
rna_def_attribute_int(BlenderRNA * brna)500 static void rna_def_attribute_int(BlenderRNA *brna)
501 {
502   StructRNA *srna;
503   PropertyRNA *prop;
504 
505   srna = RNA_def_struct(brna, "IntAttribute", "Attribute");
506   RNA_def_struct_sdna(srna, "CustomDataLayer");
507   RNA_def_struct_ui_text(srna, "Int Attribute", "Integer geometry attribute");
508 
509   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
510   RNA_def_property_struct_type(prop, "IntAttributeValue");
511   RNA_def_property_collection_funcs(prop,
512                                     "rna_Attribute_data_begin",
513                                     "rna_iterator_array_next",
514                                     "rna_iterator_array_end",
515                                     "rna_iterator_array_get",
516                                     "rna_Attribute_data_length",
517                                     NULL,
518                                     NULL,
519                                     NULL);
520 
521   srna = RNA_def_struct(brna, "IntAttributeValue", NULL);
522   RNA_def_struct_sdna(srna, "MIntProperty");
523   RNA_def_struct_ui_text(srna, "Integer Attribute Value", "Integer value in geometry attribute");
524   prop = RNA_def_property(srna, "value", PROP_INT, PROP_NONE);
525   RNA_def_property_int_sdna(prop, NULL, "i");
526   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
527 }
528 
rna_def_attribute_string(BlenderRNA * brna)529 static void rna_def_attribute_string(BlenderRNA *brna)
530 {
531   StructRNA *srna;
532   PropertyRNA *prop;
533 
534   srna = RNA_def_struct(brna, "StringAttribute", "Attribute");
535   RNA_def_struct_sdna(srna, "CustomDataLayer");
536   RNA_def_struct_ui_text(srna, "String Attribute", "String geometry attribute");
537 
538   prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
539   RNA_def_property_struct_type(prop, "StringAttributeValue");
540   RNA_def_property_collection_funcs(prop,
541                                     "rna_Attribute_data_begin",
542                                     "rna_iterator_array_next",
543                                     "rna_iterator_array_end",
544                                     "rna_iterator_array_get",
545                                     "rna_Attribute_data_length",
546                                     NULL,
547                                     NULL,
548                                     NULL);
549 
550   srna = RNA_def_struct(brna, "StringAttributeValue", NULL);
551   RNA_def_struct_sdna(srna, "MStringProperty");
552   RNA_def_struct_ui_text(srna, "String Attribute Value", "String value in geometry attribute");
553   prop = RNA_def_property(srna, "value", PROP_STRING, PROP_NONE);
554   RNA_def_property_string_sdna(prop, NULL, "s");
555   RNA_def_property_update(prop, 0, "rna_Attribute_update_data");
556 }
557 
rna_def_attribute(BlenderRNA * brna)558 static void rna_def_attribute(BlenderRNA *brna)
559 {
560   PropertyRNA *prop;
561   StructRNA *srna;
562 
563   srna = RNA_def_struct(brna, "Attribute", NULL);
564   RNA_def_struct_sdna(srna, "CustomDataLayer");
565   RNA_def_struct_ui_text(srna, "Attribute", "Geometry attribute");
566   RNA_def_struct_path_func(srna, "rna_Attribute_path");
567 
568   prop = RNA_def_property(srna, "name", PROP_STRING, PROP_NONE);
569   RNA_def_struct_name_property(srna, prop);
570   RNA_def_property_string_funcs(prop, NULL, NULL, "rna_Attribute_name_set");
571   RNA_def_property_editable_func(prop, "rna_Attribute_name_editable");
572   RNA_def_property_ui_text(prop, "Name", "Name of the Attribute");
573   RNA_def_struct_name_property(srna, prop);
574 
575   prop = RNA_def_property(srna, "data_type", PROP_ENUM, PROP_NONE);
576   RNA_def_property_enum_sdna(prop, NULL, "type");
577   RNA_def_property_enum_items(prop, rna_enum_attribute_type_items);
578   RNA_def_property_enum_funcs(prop, "rna_Attribute_type_get", NULL, NULL);
579   RNA_def_property_ui_text(prop, "Data Type", "Type of data stored in attribute");
580   RNA_def_property_clear_flag(prop, PROP_EDITABLE);
581 
582   prop = RNA_def_property(srna, "domain", PROP_ENUM, PROP_NONE);
583   RNA_def_property_enum_items(prop, rna_enum_attribute_domain_items);
584   RNA_def_property_enum_funcs(
585       prop, "rna_Attribute_domain_get", NULL, "rna_Attribute_domain_itemf");
586   RNA_def_property_ui_text(prop, "Domain", "Domain of the Attribute");
587   RNA_def_property_clear_flag(prop, PROP_EDITABLE);
588 
589   /* types */
590   rna_def_attribute_float(brna);
591   rna_def_attribute_float_vector(brna);
592   rna_def_attribute_float_color(brna);
593   rna_def_attribute_byte_color(brna);
594   rna_def_attribute_int(brna);
595   rna_def_attribute_string(brna);
596 }
597 
598 /* Mesh/PointCloud/Hair.attributes */
rna_def_attribute_group(BlenderRNA * brna)599 static void rna_def_attribute_group(BlenderRNA *brna)
600 {
601   StructRNA *srna;
602   PropertyRNA *prop;
603   FunctionRNA *func;
604   PropertyRNA *parm;
605 
606   srna = RNA_def_struct(brna, "AttributeGroup", NULL);
607   RNA_def_struct_ui_text(srna, "Attribute Group", "Group of geometry attributes");
608   RNA_def_struct_sdna(srna, "ID");
609 
610   /* API */
611   func = RNA_def_function(srna, "new", "rna_AttributeGroup_new");
612   RNA_def_function_ui_description(func, "Add an attribute");
613   RNA_def_function_flag(func, FUNC_USE_REPORTS);
614   parm = RNA_def_string(func, "name", "Attribute", 0, "", "Attribute name");
615   RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
616   parm = RNA_def_enum(
617       func, "type", rna_enum_attribute_type_items, CD_PROP_FLOAT, "Type", "Attribute type");
618   RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
619   parm = RNA_def_enum(func,
620                       "domain",
621                       rna_enum_attribute_domain_items,
622                       ATTR_DOMAIN_VERTEX,
623                       "Domain",
624                       "Type of element that attribute is stored on");
625   RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
626   parm = RNA_def_pointer(func, "attribute", "Attribute", "", "New geometry attribute");
627   RNA_def_parameter_flags(parm, 0, PARM_RNAPTR);
628   RNA_def_function_return(func, parm);
629 
630   func = RNA_def_function(srna, "remove", "rna_AttributeGroup_remove");
631   RNA_def_function_ui_description(func, "Remove an attribute");
632   RNA_def_function_flag(func, FUNC_USE_REPORTS);
633   parm = RNA_def_pointer(func, "attribute", "Attribute", "", "Geometry Attribute");
634   RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR);
635   RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, 0);
636 
637   /* Active */
638   prop = RNA_def_property(srna, "active", PROP_POINTER, PROP_NONE);
639   RNA_def_property_struct_type(prop, "Attribute");
640   RNA_def_property_pointer_funcs(
641       prop, "rna_AttributeGroup_active_get", "rna_AttributeGroup_active_set", NULL, NULL);
642   RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_UNLINK);
643   RNA_def_property_ui_text(prop, "Active Attribute", "Active attribute");
644   RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active");
645 
646   prop = RNA_def_property(srna, "active_index", PROP_INT, PROP_NONE);
647   RNA_def_property_clear_flag(prop, PROP_ANIMATABLE);
648   RNA_def_property_int_funcs(prop,
649                              "rna_AttributeGroup_active_index_get",
650                              "rna_AttributeGroup_active_index_set",
651                              "rna_AttributeGroup_active_index_range");
652   RNA_def_property_update(prop, 0, "rna_AttributeGroup_update_active");
653 }
654 
rna_def_attributes_common(StructRNA * srna)655 void rna_def_attributes_common(StructRNA *srna)
656 {
657   PropertyRNA *prop;
658 
659   /* Attributes */
660   prop = RNA_def_property(srna, "attributes", PROP_COLLECTION, PROP_NONE);
661   RNA_def_property_collection_funcs(prop,
662                                     "rna_AttributeGroup_iterator_begin",
663                                     "rna_AttributeGroup_iterator_next",
664                                     "rna_iterator_array_end",
665                                     "rna_AttributeGroup_iterator_get",
666                                     "rna_AttributeGroup_length",
667                                     NULL,
668                                     NULL,
669                                     NULL);
670   RNA_def_property_struct_type(prop, "Attribute");
671   RNA_def_property_ui_text(prop, "Attributes", "Geometry attributes");
672   RNA_def_property_srna(prop, "AttributeGroup");
673 }
674 
RNA_def_attribute(BlenderRNA * brna)675 void RNA_def_attribute(BlenderRNA *brna)
676 {
677   rna_def_attribute(brna);
678   rna_def_attribute_group(brna);
679 }
680 #endif
681