Cleanup: RNA boolean names (use prefix conventions)
[blender.git] / source / blender / makesrna / intern / rna_key.c
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 \ingroup RNA
18  */
19
20 #include <stdlib.h>
21
22 #include "DNA_ID.h"
23 #include "DNA_scene_types.h"
24 #include "DNA_curve_types.h"
25 #include "DNA_key_types.h"
26 #include "DNA_lattice_types.h"
27 #include "DNA_mesh_types.h"
28
29 #include "BLI_utildefines.h"
30 #include "BLI_math.h"
31
32 #include "BLT_translation.h"
33
34 #include "RNA_access.h"
35 #include "RNA_define.h"
36 #include "RNA_enum_types.h"
37
38 #include "MEM_guardedalloc.h"
39
40 #include "rna_internal.h"
41
42 #ifdef RNA_RUNTIME
43
44 #include <stddef.h>
45
46 #include "DNA_object_types.h"
47
48 #include "BLI_string_utils.h"
49
50 #include "BKE_animsys.h"
51 #include "BKE_key.h"
52 #include "BKE_main.h"
53
54 #include "DEG_depsgraph.h"
55
56 #include "WM_api.h"
57 #include "WM_types.h"
58
59 static Key *rna_ShapeKey_find_key(ID *id)
60 {
61         switch (GS(id->name)) {
62                 case ID_CU: return ((Curve *)id)->key;
63                 case ID_KE: return (Key *)id;
64                 case ID_LT: return ((Lattice *)id)->key;
65                 case ID_ME: return ((Mesh *)id)->key;
66                 case ID_OB: return BKE_key_from_object((Object *)id);
67                 default: return NULL;
68         }
69 }
70
71 static void rna_ShapeKey_name_set(PointerRNA *ptr, const char *value)
72 {
73         KeyBlock *kb = ptr->data;
74         char oldname[sizeof(kb->name)];
75
76         /* make a copy of the old name first */
77         BLI_strncpy(oldname, kb->name, sizeof(kb->name));
78
79         /* copy the new name into the name slot */
80         BLI_strncpy_utf8(kb->name, value, sizeof(kb->name));
81
82         /* make sure the name is truly unique */
83         if (ptr->id.data) {
84                 Key *key = rna_ShapeKey_find_key(ptr->id.data);
85                 BLI_uniquename(&key->block, kb, CTX_DATA_(BLT_I18NCONTEXT_ID_SHAPEKEY, "Key"), '.',
86                                offsetof(KeyBlock, name), sizeof(kb->name));
87         }
88
89         /* fix all the animation data which may link to this */
90         BKE_animdata_fix_paths_rename_all(NULL, "key_blocks", oldname, kb->name);
91 }
92
93 static float rna_ShapeKey_frame_get(PointerRNA *ptr)
94 {
95         KeyBlock *kb = (KeyBlock *)ptr->data;
96         return kb->pos * 100.0f;  /* Because pos is ctime/100... */
97 }
98
99 static void rna_ShapeKey_value_set(PointerRNA *ptr, float value)
100 {
101         KeyBlock *data = (KeyBlock *)ptr->data;
102         CLAMP(value, data->slidermin, data->slidermax);
103         data->curval = value;
104 }
105
106 static void rna_ShapeKey_value_range(PointerRNA *ptr, float *min, float *max,
107                                      float *UNUSED(softmin), float *UNUSED(softmax))
108 {
109         KeyBlock *data = (KeyBlock *)ptr->data;
110
111         *min = data->slidermin;
112         *max = data->slidermax;
113 }
114
115 /* epsilon for how close one end of shapekey range can get to the other */
116 #define SHAPEKEY_SLIDER_TOL 0.001f
117
118 static void rna_ShapeKey_slider_min_range(PointerRNA *ptr, float *min, float *max,
119                                           float *UNUSED(softmin), float *UNUSED(softmax))
120 {
121         KeyBlock *data = (KeyBlock *)ptr->data;
122
123         *min = -10.0f;
124         *max = data->slidermax - SHAPEKEY_SLIDER_TOL;
125 }
126
127 static void rna_ShapeKey_slider_min_set(PointerRNA *ptr, float value)
128 {
129         KeyBlock *data = (KeyBlock *)ptr->data;
130         float min, max, softmin, softmax;
131
132         rna_ShapeKey_slider_min_range(ptr, &min, &max, &softmin, &softmax);
133         CLAMP(value, min, max);
134         data->slidermin = value;
135 }
136
137 static void rna_ShapeKey_slider_max_range(PointerRNA *ptr, float *min, float *max,
138                                           float *UNUSED(softmin), float *UNUSED(softmax))
139 {
140         KeyBlock *data = (KeyBlock *)ptr->data;
141
142         *min = data->slidermin + SHAPEKEY_SLIDER_TOL;
143         *max = 10.0f;
144 }
145
146 static void rna_ShapeKey_slider_max_set(PointerRNA *ptr, float value)
147 {
148         KeyBlock *data = (KeyBlock *)ptr->data;
149         float min, max, softmin, softmax;
150
151         rna_ShapeKey_slider_max_range(ptr, &min, &max, &softmin, &softmax);
152         CLAMP(value, min, max);
153         data->slidermax = value;
154 }
155
156 #undef SHAPEKEY_SLIDER_TOL
157
158 /* ***** Normals accessors for shapekeys. ***** */
159 /* Note: with this we may recompute several times the same data, should we want to access verts, then polys, then loops
160  *       normals... However, such case looks rather unlikely - and not worth adding some kind of caching in KeyBlocks.
161  */
162
163 static Mesh *rna_KeyBlock_normals_get_mesh(PointerRNA *ptr, ID *id)
164 {
165         Key *key = rna_ShapeKey_find_key((id == NULL && ptr != NULL) ? ptr->id.data : id);
166         id = key ? key->from : NULL;
167
168         if (id != NULL) {
169                 switch (GS(id->name)) {
170                         case ID_ME:
171                                 return (Mesh *)id;
172                         case ID_OB:
173                         {
174                                 Object *ob = (Object *)id;
175                                 if (ob->type == OB_MESH) {
176                                         return ob->data;
177                                 }
178                         }
179                         default:
180                                 break;
181                 }
182         }
183
184         return NULL;
185 }
186
187 static int rna_KeyBlock_normals_vert_len(PointerRNA *ptr, int length[RNA_MAX_ARRAY_DIMENSION])
188 {
189         Mesh *me = rna_KeyBlock_normals_get_mesh(ptr, NULL);
190
191         length[0] = me ? me->totvert : 0;
192         length[1] = 3;
193
194         return (length[0] * length[1]);
195 }
196
197 static void rna_KeyBlock_normals_vert_calc(ID *id, KeyBlock *data, int *normals_len, float **normals)
198 {
199         Mesh *me = rna_KeyBlock_normals_get_mesh(NULL, id);
200
201         *normals_len = (me ? me->totvert : 0) * 3;
202
203         if (ELEM(NULL, me, data) || (me->totvert == 0)) {
204                 *normals = NULL;
205                 return;
206         }
207
208         *normals = MEM_mallocN(sizeof(**normals) * (size_t)(*normals_len), __func__);
209
210         BKE_keyblock_mesh_calc_normals(data, me, (float (*)[3])(*normals), NULL, NULL);
211 }
212
213 static int rna_KeyBlock_normals_poly_len(PointerRNA *ptr, int length[RNA_MAX_ARRAY_DIMENSION])
214 {
215         Mesh *me = rna_KeyBlock_normals_get_mesh(ptr, NULL);
216
217         length[0] = me ? me->totpoly : 0;
218         length[1] = 3;
219
220         return (length[0] * length[1]);
221 }
222
223 static void rna_KeyBlock_normals_poly_calc(ID *id, KeyBlock *data, int *normals_len, float **normals)
224 {
225         Mesh *me = rna_KeyBlock_normals_get_mesh(NULL, id);
226
227         *normals_len = (me ? me->totpoly : 0) * 3;
228
229         if (ELEM(NULL, me, data) || (me->totpoly == 0)) {
230                 *normals = NULL;
231                 return;
232         }
233
234         *normals = MEM_mallocN(sizeof(**normals) * (size_t)(*normals_len), __func__);
235
236         BKE_keyblock_mesh_calc_normals(data, me, NULL, (float (*)[3])(*normals), NULL);
237 }
238
239 static int rna_KeyBlock_normals_loop_len(PointerRNA *ptr, int length[RNA_MAX_ARRAY_DIMENSION])
240 {
241         Mesh *me = rna_KeyBlock_normals_get_mesh(ptr, NULL);
242
243         length[0] = me ? me->totloop : 0;
244         length[1] = 3;
245
246         return (length[0] * length[1]);
247 }
248
249 static void rna_KeyBlock_normals_loop_calc(ID *id, KeyBlock *data, int *normals_len, float **normals)
250 {
251         Mesh *me = rna_KeyBlock_normals_get_mesh(NULL, id);
252
253         *normals_len = (me ? me->totloop : 0) * 3;
254
255         if (ELEM(NULL, me, data) || (me->totloop == 0)) {
256                 *normals = NULL;
257                 return;
258         }
259
260         *normals = MEM_mallocN(sizeof(**normals) * (size_t)(*normals_len), __func__);
261
262         BKE_keyblock_mesh_calc_normals(data, me, NULL, NULL, (float (*)[3])(*normals));
263 }
264
265
266 PointerRNA rna_object_shapekey_index_get(ID *id, int value)
267 {
268         Key *key = rna_ShapeKey_find_key(id);
269         KeyBlock *kb = NULL;
270         PointerRNA ptr;
271
272         if (key && value < key->totkey)
273                 kb = BLI_findlink(&key->block, value);
274
275         RNA_pointer_create(id, &RNA_ShapeKey, kb, &ptr);
276
277         return ptr;
278 }
279
280 int rna_object_shapekey_index_set(ID *id, PointerRNA value, int current)
281 {
282         Key *key = rna_ShapeKey_find_key(id);
283
284         if (key) {
285                 int a = BLI_findindex(&key->block, value.data);
286                 if (a != -1) return a;
287         }
288
289         return current;
290 }
291
292 static PointerRNA rna_ShapeKey_relative_key_get(PointerRNA *ptr)
293 {
294         KeyBlock *kb = (KeyBlock *)ptr->data;
295
296         return rna_object_shapekey_index_get(ptr->id.data, kb->relative);
297 }
298
299 static void rna_ShapeKey_relative_key_set(PointerRNA *ptr, PointerRNA value)
300 {
301         KeyBlock *kb = (KeyBlock *)ptr->data;
302
303         kb->relative = rna_object_shapekey_index_set(ptr->id.data, value, kb->relative);
304 }
305
306 static void rna_ShapeKeyPoint_co_get(PointerRNA *ptr, float *values)
307 {
308         float *vec = (float *)ptr->data;
309
310         values[0] = vec[0];
311         values[1] = vec[1];
312         values[2] = vec[2];
313 }
314
315 static void rna_ShapeKeyPoint_co_set(PointerRNA *ptr, const float *values)
316 {
317         float *vec = (float *)ptr->data;
318
319         vec[0] = values[0];
320         vec[1] = values[1];
321         vec[2] = values[2];
322 }
323
324 static float rna_ShapeKeyCurvePoint_tilt_get(PointerRNA *ptr)
325 {
326         float *vec = (float *)ptr->data;
327         return vec[3];
328 }
329
330 static void rna_ShapeKeyCurvePoint_tilt_set(PointerRNA *ptr, float value)
331 {
332         float *vec = (float *)ptr->data;
333         vec[3] = value;
334 }
335
336 static float rna_ShapeKeyCurvePoint_radius_get(PointerRNA *ptr)
337 {
338         float *vec = (float *)ptr->data;
339         return vec[4];
340 }
341
342 static void rna_ShapeKeyCurvePoint_radius_set(PointerRNA *ptr, float value)
343 {
344         float *vec = (float *)ptr->data;
345         CLAMP_MIN(value, 0.0f);
346         vec[4] = value;
347 }
348
349 static void rna_ShapeKeyBezierPoint_co_get(PointerRNA *ptr, float *values)
350 {
351         float *vec = (float *)ptr->data;
352
353         values[0] = vec[0 + 3];
354         values[1] = vec[1 + 3];
355         values[2] = vec[2 + 3];
356 }
357
358 static void rna_ShapeKeyBezierPoint_co_set(PointerRNA *ptr, const float *values)
359 {
360         float *vec = (float *)ptr->data;
361
362         vec[0 + 3] = values[0];
363         vec[1 + 3] = values[1];
364         vec[2 + 3] = values[2];
365 }
366
367 static void rna_ShapeKeyBezierPoint_handle_1_co_get(PointerRNA *ptr, float *values)
368 {
369         float *vec = (float *)ptr->data;
370
371         values[0] = vec[0];
372         values[1] = vec[1];
373         values[2] = vec[2];
374 }
375
376 static void rna_ShapeKeyBezierPoint_handle_1_co_set(PointerRNA *ptr, const float *values)
377 {
378         float *vec = (float *)ptr->data;
379
380         vec[0] = values[0];
381         vec[1] = values[1];
382         vec[2] = values[2];
383 }
384
385 static void rna_ShapeKeyBezierPoint_handle_2_co_get(PointerRNA *ptr, float *values)
386 {
387         float *vec = (float *)ptr->data;
388
389         values[0] = vec[6 + 0];
390         values[1] = vec[6 + 1];
391         values[2] = vec[6 + 2];
392 }
393
394 static void rna_ShapeKeyBezierPoint_handle_2_co_set(PointerRNA *ptr, const float *values)
395 {
396         float *vec = (float *)ptr->data;
397
398         vec[6 + 0] = values[0];
399         vec[6 + 1] = values[1];
400         vec[6 + 2] = values[2];
401 }
402
403 static float rna_ShapeKeyBezierPoint_tilt_get(PointerRNA *ptr)
404 {
405         float *vec = (float *)ptr->data;
406         return vec[9];
407 }
408
409 static void rna_ShapeKeyBezierPoint_tilt_set(PointerRNA *ptr, float value)
410 {
411         float *vec = (float *)ptr->data;
412         vec[9] = value;
413 }
414
415 static float rna_ShapeKeyBezierPoint_radius_get(PointerRNA *ptr)
416 {
417         float *vec = (float *)ptr->data;
418         return vec[10];
419 }
420
421 static void rna_ShapeKeyBezierPoint_radius_set(PointerRNA *ptr, float value)
422 {
423         float *vec = (float *)ptr->data;
424         CLAMP_MIN(value, 0.0f);
425         vec[10] = value;
426 }
427
428 /* Indexing and iteration of Curve points through sub-curves. */
429 typedef struct NurbInfo {
430         Nurb *nu;
431         int nurb_size, nurb_elem_step;
432
433         /* Current index in the Nurb */
434         int nurb_index;
435
436         /* Total index as item and element. */
437         int item_index, elem_index;
438 } NurbInfo;
439
440 StructRNA *rna_ShapeKey_curve_point_type(Nurb *nu)
441 {
442         if (nu->bezt) {
443                 return &RNA_ShapeKeyBezierPoint;
444         }
445         else {
446                 return &RNA_ShapeKeyCurvePoint;
447         }
448 }
449
450 static void rna_ShapeKey_NurbInfo_init(NurbInfo *r_info, Nurb *nu)
451 {
452         r_info->nu = nu;
453
454         if (nu->bezt) {
455                 r_info->nurb_size = nu->pntsu;
456                 r_info->nurb_elem_step = KEYELEM_ELEM_LEN_BEZTRIPLE;
457         }
458         else {
459                 r_info->nurb_size = nu->pntsu * nu->pntsv;
460                 r_info->nurb_elem_step = KEYELEM_ELEM_LEN_BPOINT;
461         }
462 }
463
464 static void rna_ShapeKey_NurbInfo_step(NurbInfo *r_info, Nurb *nu, int *p_raw_index, bool input_elem)
465 {
466         rna_ShapeKey_NurbInfo_init(r_info, nu);
467
468         if (input_elem) {
469                 r_info->nurb_index = MIN2(r_info->nurb_size, *p_raw_index / r_info->nurb_elem_step);
470                 *p_raw_index -= r_info->nurb_size * r_info->nurb_elem_step;
471         }
472         else {
473                 r_info->nurb_index = MIN2(r_info->nurb_size, *p_raw_index);
474                 *p_raw_index -= r_info->nurb_size;
475         }
476
477         r_info->item_index += r_info->nurb_index;
478         r_info->elem_index += r_info->nurb_index * r_info->nurb_elem_step;
479 }
480
481 static void rna_ShapeKey_NurbInfo_find_index(Key *key, int raw_index, bool input_elem, NurbInfo *r_info)
482 {
483         Curve *cu = (Curve *)key->from;
484
485         memset(r_info, 0, sizeof(*r_info));
486
487         for (Nurb *nu = cu->nurb.first; nu && raw_index >= 0; nu = nu->next) {
488                 rna_ShapeKey_NurbInfo_step(r_info, nu, &raw_index, input_elem);
489         }
490 }
491
492 static int rna_ShapeKey_curve_find_index(Key *key, int elem_index)
493 {
494         NurbInfo info;
495         rna_ShapeKey_NurbInfo_find_index(key, elem_index, true, &info);
496         return info.item_index;
497 }
498
499 typedef struct ShapeKeyCurvePoint {
500         StructRNA *type;
501         void *data;
502 } ShapeKeyCurvePoint;
503
504 /* Build a mapping array for Curve objects with mixed sub-curve types. */
505 static void rna_ShapeKey_data_begin_mixed(CollectionPropertyIterator *iter, Key *key, KeyBlock *kb, Curve *cu)
506 {
507         int point_count = rna_ShapeKey_curve_find_index(key, kb->totelem);
508
509         ShapeKeyCurvePoint *points = MEM_malloc_arrayN(sizeof(ShapeKeyCurvePoint), point_count, __func__);
510
511         char *databuf = kb->data;
512         int items_left = point_count;
513         NurbInfo info = { NULL };
514
515         for (Nurb *nu = cu->nurb.first; nu && items_left > 0; nu = nu->next) {
516                 ShapeKeyCurvePoint *nurb_points = points + info.item_index;
517                 char *nurb_data = databuf + info.elem_index * key->elemsize;
518
519                 rna_ShapeKey_NurbInfo_step(&info, nu, &items_left, false);
520
521                 StructRNA *type = rna_ShapeKey_curve_point_type(nu);
522
523                 for (int i = 0; i < info.nurb_index; i++) {
524                         nurb_points[i].type = type;
525                         nurb_points[i].data = nurb_data + i * info.nurb_elem_step * key->elemsize;
526                 }
527         }
528
529         rna_iterator_array_begin(iter, points, sizeof(*points), point_count, true, NULL);
530 }
531
532 static void rna_ShapeKey_data_begin(CollectionPropertyIterator *iter, PointerRNA *ptr)
533 {
534         Key *key = rna_ShapeKey_find_key(ptr->id.data);
535         KeyBlock *kb = (KeyBlock *)ptr->data;
536         int tot = kb->totelem, size = key->elemsize;
537
538         if (GS(key->from->name) == ID_CU && tot > 0) {
539                 Curve *cu = (Curve *)key->from;
540                 StructRNA *type = NULL;
541                 NurbInfo info = { 0 };
542
543                 /* Check if all sub-curves have the same type. */
544                 for (Nurb *nu = cu->nurb.first; nu; nu = nu->next) {
545                         if (type == NULL) {
546                                 type = rna_ShapeKey_curve_point_type(nu);
547                                 rna_ShapeKey_NurbInfo_init(&info, nu);
548                         }
549                         else if (type != rna_ShapeKey_curve_point_type(nu)) {
550                                 type = NULL;
551                                 break;
552                         }
553                 }
554
555                 /* If types are mixed, build a mapping array. */
556                 if (type == NULL) {
557                         rna_ShapeKey_data_begin_mixed(iter, key, kb, cu);
558                         return;
559                 }
560                 else {
561                         tot /= info.nurb_elem_step;
562                         size *= info.nurb_elem_step;
563                 }
564         }
565
566         rna_iterator_array_begin(iter, (void *)kb->data, size, tot, 0, NULL);
567 }
568
569 static int rna_ShapeKey_data_length(PointerRNA *ptr)
570 {
571         Key *key = rna_ShapeKey_find_key(ptr->id.data);
572         KeyBlock *kb = (KeyBlock *)ptr->data;
573         int tot = kb->totelem;
574
575         if (GS(key->from->name) == ID_CU) {
576                 tot = rna_ShapeKey_curve_find_index(key, tot);
577         }
578
579         return tot;
580 }
581
582 static PointerRNA rna_ShapeKey_data_get(CollectionPropertyIterator *iter)
583 {
584         Key *key = rna_ShapeKey_find_key(iter->parent.id.data);
585         void *ptr = rna_iterator_array_get(iter);
586         StructRNA *type = &RNA_ShapeKeyPoint;
587
588         /* If data_begin allocated a mapping array, access it. */
589         if (iter->internal.array.free_ptr) {
590                 ShapeKeyCurvePoint *point = ptr;
591
592                 return rna_pointer_inherit_refine(&iter->parent, point->type, point->data);
593         }
594
595         if (GS(key->from->name) == ID_CU) {
596                 Curve *cu = (Curve *)key->from;
597
598                 type = rna_ShapeKey_curve_point_type(cu->nurb.first);
599         }
600
601         return rna_pointer_inherit_refine(&iter->parent, type, ptr);
602 }
603
604 int rna_ShapeKey_data_lookup_int(PointerRNA *ptr, int index, PointerRNA *r_ptr)
605 {
606         Key *key = rna_ShapeKey_find_key(ptr->id.data);
607         KeyBlock *kb = (KeyBlock *)ptr->data;
608         int elemsize = key->elemsize;
609         char *databuf = kb->data;
610
611         memset(r_ptr, 0, sizeof(*r_ptr));
612
613         if (index < 0) {
614                 return false;
615         }
616
617         if (GS(key->from->name) == ID_CU) {
618                 NurbInfo info;
619                 rna_ShapeKey_NurbInfo_find_index(key, index, false, &info);
620
621                 if (info.nu && info.nurb_index < info.nurb_size) {
622                         StructRNA *type = rna_ShapeKey_curve_point_type(info.nu);
623
624                         *r_ptr = rna_pointer_inherit_refine(ptr, type, databuf + elemsize * info.elem_index);
625                         return true;
626                 }
627         }
628         else {
629                 if (index < kb->totelem) {
630                         *r_ptr = rna_pointer_inherit_refine(ptr, &RNA_ShapeKeyPoint, databuf + elemsize * index);
631                         return true;
632                 }
633         }
634
635         return false;
636 }
637
638 static char *rna_ShapeKey_path(PointerRNA *ptr)
639 {
640         KeyBlock *kb = (KeyBlock *)ptr->data;
641         ID *id = ptr->id.data;
642         char name_esc[sizeof(kb->name) * 2];
643
644         BLI_strescape(name_esc, kb->name, sizeof(name_esc));
645
646         if ((id) && (GS(id->name) != ID_KE))
647                 return BLI_sprintfN("shape_keys.key_blocks[\"%s\"]", name_esc);
648         else
649                 return BLI_sprintfN("key_blocks[\"%s\"]", name_esc);
650 }
651
652 static void rna_Key_update_data(Main *bmain, Scene *UNUSED(scene), PointerRNA *ptr)
653 {
654         Key *key = ptr->id.data;
655         Object *ob;
656
657         for (ob = bmain->object.first; ob; ob = ob->id.next) {
658                 if (BKE_key_from_object(ob) == key) {
659                         DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
660                         WM_main_add_notifier(NC_OBJECT | ND_MODIFIER, ob);
661                 }
662         }
663 }
664
665 static KeyBlock *rna_ShapeKeyData_find_keyblock(Key *key, float *point)
666 {
667         KeyBlock *kb;
668
669         /* sanity checks */
670         if (ELEM(NULL, key, point))
671                 return NULL;
672
673         /* we'll need to manually search through the keyblocks and check
674          * if the point is somewhere in the middle of each block's data
675          */
676         for (kb = key->block.first; kb; kb = kb->next) {
677                 if (kb->data) {
678                         float *start = (float *)kb->data;
679                         float *end;
680
681                         /* easy cases first */
682                         if ((start == NULL) || (start > point)) {
683                                 /* there's no chance point is in array */
684                                 continue;
685                         }
686                         else if (start == point) {
687                                 /* exact match - point is first in array */
688                                 return kb;
689                         }
690
691                         /* determine where end of array is
692                          * - elemsize is in bytes, so use (char *) cast to get array in terms of bytes
693                          */
694                         end = (float *)((char *)start + (key->elemsize * kb->totelem));
695
696                         /* if point's address is less than the end, then it is somewhere between start and end, so in array */
697                         if (end > point) {
698                                 /* we've found the owner of the point data */
699                                 return kb;
700                         }
701                 }
702         }
703
704         return NULL;
705 }
706
707 static int rna_ShapeKeyPoint_get_index(Key *key, KeyBlock *kb, float *point)
708 {
709         /* if we frame the data array and point pointers as (char *), then the difference between
710          * them will be in bytes. Thus, dividing through by key->elemsize (number of bytes per point)
711          * gives us the offset of point from start of array.
712          */
713         char *start = (char *)kb->data;
714         char *pt = (char *)point;
715
716         return (int)(pt - start) / key->elemsize;
717 }
718
719 static char *rna_ShapeKeyPoint_path(PointerRNA *ptr)
720 {
721         ID *id = (ID *)ptr->id.data;
722         Key *key = rna_ShapeKey_find_key(ptr->id.data);
723         KeyBlock *kb;
724         float *point = (float *)ptr->data;
725
726         /* if we can get a key block, we can construct a path */
727         kb = rna_ShapeKeyData_find_keyblock(key, point);
728
729         if (kb) {
730                 char name_esc_kb[sizeof(kb->name) * 2];
731                 int index;
732
733                 index = rna_ShapeKeyPoint_get_index(key, kb, point);
734
735                 if (ELEM(ptr->type, &RNA_ShapeKeyBezierPoint, &RNA_ShapeKeyCurvePoint)) {
736                         index = rna_ShapeKey_curve_find_index(key, index);
737                 }
738
739                 BLI_strescape(name_esc_kb, kb->name, sizeof(name_esc_kb));
740
741                 if (GS(id->name) == ID_KE)
742                         return BLI_sprintfN("key_blocks[\"%s\"].data[%d]", name_esc_kb, index);
743                 else
744                         return BLI_sprintfN("shape_keys.key_blocks[\"%s\"].data[%d]", name_esc_kb, index);
745         }
746         else
747                 return NULL;  /* XXX: there's really no way to resolve this... */
748 }
749
750 #else
751
752 const EnumPropertyItem rna_enum_keyblock_type_items[] = {
753         {KEY_LINEAR, "KEY_LINEAR", 0, "Linear", ""},
754         {KEY_CARDINAL, "KEY_CARDINAL", 0, "Cardinal", ""},
755         {KEY_CATMULL_ROM, "KEY_CATMULL_ROM", 0, "Catmull-Rom", ""},
756         {KEY_BSPLINE, "KEY_BSPLINE", 0, "BSpline", ""},
757         {0, NULL, 0, NULL, NULL},
758 };
759
760 static const float tilt_limit = DEG2RADF(21600.0f);
761
762 static void rna_def_keydata(BlenderRNA *brna)
763 {
764         StructRNA *srna;
765         PropertyRNA *prop;
766
767         srna = RNA_def_struct(brna, "ShapeKeyPoint", NULL);
768         RNA_def_struct_ui_text(srna, "Shape Key Point", "Point in a shape key");
769         RNA_def_struct_path_func(srna, "rna_ShapeKeyPoint_path");
770
771         prop = RNA_def_property(srna, "co", PROP_FLOAT, PROP_TRANSLATION);
772         RNA_def_property_array(prop, 3);
773         RNA_def_property_float_funcs(prop, "rna_ShapeKeyPoint_co_get", "rna_ShapeKeyPoint_co_set", NULL);
774         RNA_def_property_ui_text(prop, "Location", "");
775         RNA_def_property_update(prop, 0, "rna_Key_update_data");
776
777         srna = RNA_def_struct(brna, "ShapeKeyCurvePoint", NULL);
778         RNA_def_struct_ui_text(srna, "Shape Key Curve Point", "Point in a shape key for curves");
779         /* there's nothing type specific here, so this is fine for now */
780         RNA_def_struct_path_func(srna, "rna_ShapeKeyPoint_path");
781
782         prop = RNA_def_property(srna, "co", PROP_FLOAT, PROP_TRANSLATION);
783         RNA_def_property_array(prop, 3);
784         RNA_def_property_float_funcs(prop, "rna_ShapeKeyPoint_co_get", "rna_ShapeKeyPoint_co_set", NULL);
785         RNA_def_property_ui_text(prop, "Location", "");
786         RNA_def_property_update(prop, 0, "rna_Key_update_data");
787
788         prop = RNA_def_property(srna, "tilt", PROP_FLOAT, PROP_ANGLE);
789         RNA_def_property_float_funcs(prop, "rna_ShapeKeyCurvePoint_tilt_get", "rna_ShapeKeyCurvePoint_tilt_set", NULL);
790         RNA_def_property_range(prop, -tilt_limit, tilt_limit);
791         RNA_def_property_ui_range(prop, -tilt_limit, tilt_limit, 10, 3);
792         RNA_def_property_ui_text(prop, "Tilt", "Tilt in 3D View");
793         RNA_def_property_update(prop, 0, "rna_Key_update_data");
794
795         prop = RNA_def_property(srna, "radius", PROP_FLOAT, PROP_NONE);
796         RNA_def_property_float_funcs(prop, "rna_ShapeKeyCurvePoint_radius_get", "rna_ShapeKeyCurvePoint_radius_set", NULL);
797         RNA_def_property_range(prop, 0.0f, FLT_MAX);
798         RNA_def_property_ui_text(prop, "Radius", "Radius for beveling");
799         RNA_def_property_update(prop, 0, "rna_Key_update_data");
800
801         srna = RNA_def_struct(brna, "ShapeKeyBezierPoint", NULL);
802         RNA_def_struct_ui_text(srna, "Shape Key Bezier Point", "Point in a shape key for Bezier curves");
803         /* there's nothing type specific here, so this is fine for now */
804         RNA_def_struct_path_func(srna, "rna_ShapeKeyPoint_path");
805
806         prop = RNA_def_property(srna, "co", PROP_FLOAT, PROP_TRANSLATION);
807         RNA_def_property_array(prop, 3);
808         RNA_def_property_float_funcs(prop, "rna_ShapeKeyBezierPoint_co_get", "rna_ShapeKeyBezierPoint_co_set", NULL);
809         RNA_def_property_ui_text(prop, "Location", "");
810         RNA_def_property_update(prop, 0, "rna_Key_update_data");
811
812         prop = RNA_def_property(srna, "handle_left", PROP_FLOAT, PROP_TRANSLATION);
813         RNA_def_property_array(prop, 3);
814         RNA_def_property_float_funcs(prop, "rna_ShapeKeyBezierPoint_handle_1_co_get",
815                                      "rna_ShapeKeyBezierPoint_handle_1_co_set", NULL);
816         RNA_def_property_ui_text(prop, "Handle 1 Location", "");
817         RNA_def_property_update(prop, 0, "rna_Key_update_data");
818
819         prop = RNA_def_property(srna, "handle_right", PROP_FLOAT, PROP_TRANSLATION);
820         RNA_def_property_array(prop, 3);
821         RNA_def_property_float_funcs(prop, "rna_ShapeKeyBezierPoint_handle_2_co_get",
822                                      "rna_ShapeKeyBezierPoint_handle_2_co_set", NULL);
823         RNA_def_property_ui_text(prop, "Handle 2 Location", "");
824         RNA_def_property_update(prop, 0, "rna_Key_update_data");
825
826         prop = RNA_def_property(srna, "tilt", PROP_FLOAT, PROP_ANGLE);
827         RNA_def_property_float_funcs(prop, "rna_ShapeKeyBezierPoint_tilt_get", "rna_ShapeKeyBezierPoint_tilt_set", NULL);
828         RNA_def_property_range(prop, -tilt_limit, tilt_limit);
829         RNA_def_property_ui_range(prop, -tilt_limit, tilt_limit, 10, 3);
830         RNA_def_property_ui_text(prop, "Tilt", "Tilt in 3D View");
831         RNA_def_property_update(prop, 0, "rna_Key_update_data");
832
833         prop = RNA_def_property(srna, "radius", PROP_FLOAT, PROP_NONE);
834         RNA_def_property_float_funcs(prop, "rna_ShapeKeyBezierPoint_radius_get", "rna_ShapeKeyBezierPoint_radius_set", NULL);
835         RNA_def_property_range(prop, 0.0f, FLT_MAX);
836         RNA_def_property_ui_text(prop, "Radius", "Radius for beveling");
837         RNA_def_property_update(prop, 0, "rna_Key_update_data");
838 }
839
840 static void rna_def_keyblock(BlenderRNA *brna)
841 {
842         StructRNA *srna;
843         PropertyRNA *prop, *parm;
844         FunctionRNA *func;
845
846         srna = RNA_def_struct(brna, "ShapeKey", NULL);
847         RNA_def_struct_ui_text(srna, "Shape Key", "Shape key in a shape keys data-block");
848         RNA_def_struct_sdna(srna, "KeyBlock");
849         RNA_def_struct_path_func(srna, "rna_ShapeKey_path");
850         RNA_def_struct_ui_icon(srna, ICON_SHAPEKEY_DATA);
851
852         prop = RNA_def_property(srna, "name", PROP_STRING, PROP_NONE);
853         RNA_def_property_ui_text(prop, "Name", "Name of Shape Key");
854         RNA_def_property_string_funcs(prop, NULL, NULL, "rna_ShapeKey_name_set");
855         RNA_def_property_update(prop, 0, "rna_Key_update_data");
856         RNA_def_struct_name_property(srna, prop);
857
858         /* keys need to be sorted to edit this */
859         prop = RNA_def_property(srna, "frame", PROP_FLOAT, PROP_TIME);
860         RNA_def_property_clear_flag(prop, PROP_EDITABLE);
861         RNA_def_property_float_sdna(prop, NULL, "pos");
862         RNA_def_property_float_funcs(prop, "rna_ShapeKey_frame_get", NULL, NULL);
863         RNA_def_property_ui_text(prop, "Frame", "Frame for absolute keys");
864         RNA_def_property_update(prop, 0, "rna_Key_update_data");
865
866         /* for now, this is editable directly, as users can set this even if they're not animating them
867          * (to test results) */
868         prop = RNA_def_property(srna, "value", PROP_FLOAT, PROP_FACTOR);
869         RNA_def_property_float_sdna(prop, NULL, "curval");
870         RNA_def_property_float_funcs(prop, NULL, "rna_ShapeKey_value_set", "rna_ShapeKey_value_range");
871         RNA_def_property_ui_range(prop, -10.0f, 10.0f, 10, 3);
872         RNA_def_property_ui_text(prop, "Value", "Value of shape key at the current frame");
873         RNA_def_property_update(prop, 0, "rna_Key_update_data");
874
875         prop = RNA_def_property(srna, "interpolation", PROP_ENUM, PROP_NONE);
876         RNA_def_property_enum_sdna(prop, NULL, "type");
877         RNA_def_property_enum_items(prop, rna_enum_keyblock_type_items);
878         RNA_def_property_ui_text(prop, "Interpolation", "Interpolation type for absolute shape keys");
879         RNA_def_property_update(prop, 0, "rna_Key_update_data");
880
881         prop = RNA_def_property(srna, "vertex_group", PROP_STRING, PROP_NONE);
882         RNA_def_property_string_sdna(prop, NULL, "vgroup");
883         RNA_def_property_ui_text(prop, "Vertex Group", "Vertex weight group, to blend with basis shape");
884         RNA_def_property_update(prop, 0, "rna_Key_update_data");
885
886         prop = RNA_def_property(srna, "relative_key", PROP_POINTER, PROP_NONE);
887         RNA_def_property_struct_type(prop, "ShapeKey");
888         RNA_def_property_flag(prop, PROP_EDITABLE | PROP_NEVER_NULL | PROP_PTR_NO_OWNERSHIP);
889         RNA_def_property_pointer_funcs(prop, "rna_ShapeKey_relative_key_get",
890                                        "rna_ShapeKey_relative_key_set", NULL, NULL);
891         RNA_def_property_ui_text(prop, "Relative Key", "Shape used as a relative key");
892         RNA_def_property_update(prop, 0, "rna_Key_update_data");
893
894         prop = RNA_def_property(srna, "mute", PROP_BOOLEAN, PROP_NONE);
895         RNA_def_property_boolean_sdna(prop, NULL, "flag", KEYBLOCK_MUTE);
896         RNA_def_property_ui_text(prop, "Mute", "Mute this shape key");
897         RNA_def_property_ui_icon(prop, ICON_HIDE_OFF, -1);
898         RNA_def_property_update(prop, 0, "rna_Key_update_data");
899
900         prop = RNA_def_property(srna, "slider_min", PROP_FLOAT, PROP_NONE);
901         RNA_def_property_float_sdna(prop, NULL, "slidermin");
902         RNA_def_property_range(prop, -10.0f, 10.0f);
903         RNA_def_property_float_funcs(prop, NULL, "rna_ShapeKey_slider_min_set", "rna_ShapeKey_slider_min_range");
904         RNA_def_property_ui_text(prop, "Slider Min", "Minimum for slider");
905
906         prop = RNA_def_property(srna, "slider_max", PROP_FLOAT, PROP_NONE);
907         RNA_def_property_float_sdna(prop, NULL, "slidermax");
908         RNA_def_property_range(prop, -10.0f, 10.0f);
909         RNA_def_property_float_default(prop, 1.0f);
910         RNA_def_property_float_funcs(prop, NULL, "rna_ShapeKey_slider_max_set", "rna_ShapeKey_slider_max_range");
911         RNA_def_property_ui_text(prop, "Slider Max", "Maximum for slider");
912
913         prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
914         RNA_def_property_collection_sdna(prop, NULL, "data", "totelem");
915         RNA_def_property_struct_type(prop, "UnknownType");
916         RNA_def_property_ui_text(prop, "Data", "");
917         RNA_def_property_collection_funcs(prop, "rna_ShapeKey_data_begin", NULL, NULL, "rna_ShapeKey_data_get",
918                                           "rna_ShapeKey_data_length", "rna_ShapeKey_data_lookup_int", NULL, NULL);
919
920         /* XXX multi-dim dynamic arrays are very badly supported by (py)rna currently, those are defined for the day
921          *     it works better, for now user will get a 1D tuple...
922          **/
923         func = RNA_def_function(srna, "normals_vertex_get", "rna_KeyBlock_normals_vert_calc");
924         RNA_def_function_ui_description(func, "Compute local space vertices' normals for this shape key");
925         RNA_def_function_flag(func, FUNC_USE_SELF_ID);
926         parm = RNA_def_property(func, "normals", PROP_FLOAT, /* PROP_DIRECTION */ PROP_NONE);
927         RNA_def_parameter_flags(parm, PROP_DYNAMIC, PARM_OUTPUT);
928         RNA_def_property_multi_array(parm, 2, NULL);
929         RNA_def_property_range(parm, -1.0f, 1.0f);
930         RNA_def_property_dynamic_array_funcs(parm, "rna_KeyBlock_normals_vert_len");
931
932         func = RNA_def_function(srna, "normals_polygon_get", "rna_KeyBlock_normals_poly_calc");
933         RNA_def_function_ui_description(func, "Compute local space faces' normals for this shape key");
934         RNA_def_function_flag(func, FUNC_USE_SELF_ID);
935         parm = RNA_def_property(func, "normals", PROP_FLOAT, /* PROP_DIRECTION */ PROP_NONE);
936         RNA_def_parameter_flags(parm, PROP_DYNAMIC, PARM_OUTPUT);
937         RNA_def_property_multi_array(parm, 2, NULL);
938         RNA_def_property_range(parm, -1.0f, 1.0f);
939         RNA_def_property_dynamic_array_funcs(parm, "rna_KeyBlock_normals_poly_len");
940
941         func = RNA_def_function(srna, "normals_split_get", "rna_KeyBlock_normals_loop_calc");
942         RNA_def_function_ui_description(func, "Compute local space face corners' normals for this shape key");
943         RNA_def_function_flag(func, FUNC_USE_SELF_ID);
944         parm = RNA_def_property(func, "normals", PROP_FLOAT, /* PROP_DIRECTION */ PROP_NONE);
945         RNA_def_parameter_flags(parm, PROP_DYNAMIC, PARM_OUTPUT);
946         RNA_def_property_multi_array(parm, 2, NULL);
947         RNA_def_property_range(parm, -1.0f, 1.0f);
948         RNA_def_property_dynamic_array_funcs(parm, "rna_KeyBlock_normals_loop_len");
949 }
950
951 static void rna_def_key(BlenderRNA *brna)
952 {
953         StructRNA *srna;
954         PropertyRNA *prop;
955
956         srna = RNA_def_struct(brna, "Key", "ID");
957         RNA_def_struct_ui_text(srna, "Key", "Shape keys data-block containing different shapes of geometric data-blocks");
958         RNA_def_struct_ui_icon(srna, ICON_SHAPEKEY_DATA);
959
960         prop = RNA_def_property(srna, "reference_key", PROP_POINTER, PROP_NONE);
961         RNA_def_property_flag(prop, PROP_NEVER_NULL);
962         RNA_def_property_clear_flag(prop, PROP_EDITABLE);
963         RNA_def_property_pointer_sdna(prop, NULL, "refkey");
964         RNA_def_property_ui_text(prop, "Reference Key", "");
965
966         prop = RNA_def_property(srna, "key_blocks", PROP_COLLECTION, PROP_NONE);
967         RNA_def_property_collection_sdna(prop, NULL, "block", NULL);
968         RNA_def_property_struct_type(prop, "ShapeKey");
969         RNA_def_property_ui_text(prop, "Key Blocks", "Shape keys");
970
971         rna_def_animdata_common(srna);
972
973         prop = RNA_def_property(srna, "user", PROP_POINTER, PROP_NONE);
974         RNA_def_property_flag(prop, PROP_NEVER_NULL);
975         RNA_def_property_pointer_sdna(prop, NULL, "from");
976         RNA_def_property_ui_text(prop, "User", "Data-block using these shape keys");
977
978         prop = RNA_def_property(srna, "use_relative", PROP_BOOLEAN, PROP_NONE);
979         RNA_def_property_boolean_sdna(prop, NULL, "type", KEY_RELATIVE);
980         RNA_def_property_ui_text(prop, "Relative",
981                                  "Make shape keys relative, "
982                                  "otherwise play through shapes as a sequence using the evaluation time");
983         RNA_def_property_update(prop, 0, "rna_Key_update_data");
984
985         prop = RNA_def_property(srna, "eval_time", PROP_FLOAT, PROP_NONE);
986         RNA_def_property_float_sdna(prop, NULL, "ctime");
987         RNA_def_property_range(prop, MINFRAME, MAXFRAME);
988         RNA_def_property_ui_text(prop, "Evaluation Time", "Evaluation time for absolute shape keys");
989         RNA_def_property_update(prop, 0, "rna_Key_update_data");
990 }
991
992 void RNA_def_key(BlenderRNA *brna)
993 {
994         rna_def_key(brna);
995         rna_def_keyblock(brna);
996         rna_def_keydata(brna);
997 }
998
999 #endif