31f6e2c606727d8b70cbf1957cf466fffe632999
[blender.git] / source / blender / blenkernel / intern / fcurve.c
1 /**
2  * $Id$
3  *
4  * ***** BEGIN GPL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
19  *
20  * The Original Code is Copyright (C) 2009 Blender Foundation, Joshua Leung
21  * All rights reserved.
22  *
23  * The Original Code is: all of this file.
24  *
25  * Contributor(s): Joshua Leung (full recode)
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  */
29  
30
31 #include <math.h>
32 #include <stdio.h>
33 #include <stddef.h>
34 #include <string.h>
35 #include <float.h>
36
37 #ifdef HAVE_CONFIG_H
38 #include <config.h>
39 #endif
40
41 #include "MEM_guardedalloc.h"
42
43 #include "DNA_anim_types.h"
44
45 #include "BLI_blenlib.h"
46 #include "BLI_arithb.h"
47 #include "BLI_noise.h"
48
49 #include "BKE_fcurve.h"
50 #include "BKE_curve.h" 
51 #include "BKE_global.h"
52 #include "BKE_idprop.h"
53 #include "BKE_utildefines.h"
54
55 #include "RNA_access.h"
56 #include "RNA_types.h"
57
58 #ifndef DISABLE_PYTHON
59 #include "BPY_extern.h" 
60 #endif
61
62 #define SMALL -1.0e-10
63 #define SELECT 1
64
65 /* ************************** Data-Level Functions ************************* */
66
67 /* ---------------------- Freeing --------------------------- */
68
69 /* Frees the F-Curve itself too, so make sure BLI_remlink is called before calling this... */
70 void free_fcurve (FCurve *fcu) 
71 {
72         if (fcu == NULL) 
73                 return;
74         
75         /* free curve data */
76         if (fcu) {
77                 if (fcu->bezt) MEM_freeN(fcu->bezt);
78                 if (fcu->fpt) MEM_freeN(fcu->fpt);
79         }
80         
81         /* free RNA-path, as this were allocated when getting the path string */
82         if (fcu->rna_path)
83                 MEM_freeN(fcu->rna_path);
84         
85         /* free extra data - i.e. modifiers, and driver */
86         fcurve_free_driver(fcu);
87         free_fmodifiers(&fcu->modifiers);
88         
89         /* free f-curve itself */
90         MEM_freeN(fcu);
91 }
92
93 /* Frees a list of F-Curves */
94 void free_fcurves (ListBase *list)
95 {
96         FCurve *fcu, *fcn;
97         
98         /* sanity check */
99         if (list == NULL)
100                 return;
101                 
102         /* free data - no need to call remlink before freeing each curve, 
103          * as we store reference to next, and freeing only touches the curve
104          * it's given
105          */
106         for (fcu= list->first; fcu; fcu= fcn) {
107                 fcn= fcu->next;
108                 free_fcurve(fcu);
109         }
110         
111         /* clear pointers just in case */
112         list->first= list->last= NULL;
113 }       
114
115 /* ---------------------- Copy --------------------------- */
116
117 /* duplicate an F-Curve */
118 FCurve *copy_fcurve (FCurve *fcu)
119 {
120         FCurve *fcu_d;
121         
122         /* sanity check */
123         if (fcu == NULL)
124                 return NULL;
125                 
126         /* make a copy */
127         fcu_d= MEM_dupallocN(fcu);
128         
129         fcu_d->next= fcu_d->prev= NULL;
130         fcu_d->grp= NULL;
131         
132         /* copy curve data */
133         fcu_d->bezt= MEM_dupallocN(fcu_d->bezt);
134         fcu_d->fpt= MEM_dupallocN(fcu_d->fpt);
135         
136         /* copy rna-path */
137         fcu_d->rna_path= MEM_dupallocN(fcu_d->rna_path);
138         
139         /* copy driver */
140         fcu_d->driver= fcurve_copy_driver(fcu_d->driver);
141         
142         /* copy modifiers */
143         copy_fmodifiers(&fcu_d->modifiers, &fcu->modifiers);
144         
145         /* return new data */
146         return fcu_d;
147 }
148
149 /* duplicate a list of F-Curves */
150 void copy_fcurves (ListBase *dst, ListBase *src)
151 {
152         FCurve *dfcu, *sfcu;
153         
154         /* sanity checks */
155         if ELEM(NULL, dst, src)
156                 return;
157         
158         /* clear destination list first */
159         dst->first= dst->last= NULL;
160         
161         /* copy one-by-one */
162         for (sfcu= src->first; sfcu; sfcu= sfcu->next) {
163                 dfcu= copy_fcurve(sfcu);
164                 BLI_addtail(dst, dfcu);
165         }
166 }
167
168 /* ---------------------- Relink --------------------------- */
169
170 #if 0
171 /* uses id->newid to match pointers with other copied data 
172  *      - called after single-user or other such
173  */
174                         if (icu->driver)
175                                 ID_NEW(icu->driver->ob);
176 #endif
177
178 /* --------------------- Finding -------------------------- */
179
180 /* Find the F-Curve affecting the given RNA-access path + index, in the list of F-Curves provided */
181 FCurve *list_find_fcurve (ListBase *list, const char rna_path[], const int array_index)
182 {
183         FCurve *fcu;
184         
185         /* sanity checks */
186         if ( ELEM(NULL, list, rna_path) || (array_index < 0) )
187                 return NULL;
188         
189         /* check paths of curves, then array indices... */
190         for (fcu= list->first; fcu; fcu= fcu->next) {
191                 /* simple string-compare (this assumes that they have the same root...) */
192                 if (fcu->rna_path && !strcmp(fcu->rna_path, rna_path)) {
193                         /* now check indicies */
194                         if (fcu->array_index == array_index)
195                                 return fcu;
196                 }
197         }
198         
199         /* return */
200         return NULL;
201 }
202
203 /* Calculate the extents of F-Curve's data */
204 void calc_fcurve_bounds (FCurve *fcu, float *xmin, float *xmax, float *ymin, float *ymax)
205 {
206         float xminv=999999999.0f, xmaxv=-999999999.0f;
207         float yminv=999999999.0f, ymaxv=-999999999.0f;
208         short foundvert=0;
209         unsigned int i;
210         
211         if (fcu->totvert) {
212                 if (fcu->bezt) {
213                         /* frame range can be directly calculated from end verts */
214                         if (xmin || xmax) {
215                                 xminv= MIN2(xminv, fcu->bezt[0].vec[1][0]);
216                                 xmaxv= MAX2(xmaxv, fcu->bezt[fcu->totvert-1].vec[1][0]);
217                         }
218                         
219                         /* only loop over keyframes to find extents for values if needed */
220                         if (ymin || ymax) {
221                                 BezTriple *bezt;
222                                 
223                                 for (bezt=fcu->bezt, i=0; i < fcu->totvert; bezt++, i++) {
224                                         if (bezt->vec[1][1] < yminv)
225                                                 yminv= bezt->vec[1][1];
226                                         if (bezt->vec[1][1] > ymaxv)
227                                                 ymaxv= bezt->vec[1][1];
228                                 }
229                         }
230                 }
231                 else if (fcu->fpt) {
232                         /* frame range can be directly calculated from end verts */
233                         if (xmin || xmax) {
234                                 xminv= MIN2(xminv, fcu->fpt[0].vec[0]);
235                                 xmaxv= MAX2(xmaxv, fcu->fpt[fcu->totvert-1].vec[0]);
236                         }
237                         
238                         /* only loop over keyframes to find extents for values if needed */
239                         if (ymin || ymax) {
240                                 FPoint *fpt;
241                                 
242                                 for (fpt=fcu->fpt, i=0; i < fcu->totvert; fpt++, i++) {
243                                         if (fpt->vec[1] < yminv)
244                                                 yminv= fpt->vec[1];
245                                         if (fpt->vec[1] > ymaxv)
246                                                 ymaxv= fpt->vec[1];
247                                 }
248                         }
249                 }
250                 
251                 foundvert=1;
252         }
253         
254         /* minimum sizes are 1.0f */
255         if (foundvert) {
256                 if (xminv == xmaxv) xmaxv += 1.0f;
257                 if (yminv == ymaxv) ymaxv += 1.0f;
258                 
259                 if (xmin) *xmin= xminv;
260                 if (xmax) *xmax= xmaxv;
261                 
262                 if (ymin) *ymin= yminv;
263                 if (ymax) *ymax= ymaxv;
264         }
265         else {
266                 if (xmin) *xmin= 0.0f;
267                 if (xmax) *xmax= 0.0f;
268                 
269                 if (ymin) *ymin= 1.0f;
270                 if (ymax) *ymax= 1.0f;
271         }
272 }
273
274 /* Calculate the extents of F-Curve's keyframes */
275 void calc_fcurve_range (FCurve *fcu, float *start, float *end)
276 {
277         float min=999999999.0f, max=-999999999.0f;
278         short foundvert=0;
279
280         if (fcu->totvert) {
281                 if (fcu->bezt) {
282                         min= MIN2(min, fcu->bezt[0].vec[1][0]);
283                         max= MAX2(max, fcu->bezt[fcu->totvert-1].vec[1][0]);
284                 }
285                 else if (fcu->fpt) {
286                         min= MIN2(min, fcu->fpt[0].vec[0]);
287                         max= MAX2(max, fcu->fpt[fcu->totvert-1].vec[0]);
288                 }
289                 
290                 foundvert=1;
291         }
292         
293         /* minimum length is 1 frame */
294         if (foundvert) {
295                 if (min == max) max += 1.0f;
296                 *start= min;
297                 *end= max;
298         }
299         else {
300                 *start= 0.0f;
301                 *end= 1.0f;
302         }
303 }
304
305 /* ***************************** Keyframe Column Tools ********************************* */
306
307 /* add a BezTriple to a column */
308 void bezt_add_to_cfra_elem (ListBase *lb, BezTriple *bezt)
309 {
310         CfraElem *ce, *cen;
311         
312         for (ce= lb->first; ce; ce= ce->next) {
313                 /* double key? */
314                 if (ce->cfra == bezt->vec[1][0]) {
315                         if (bezt->f2 & SELECT) ce->sel= bezt->f2;
316                         return;
317                 }
318                 /* should key be inserted before this column? */
319                 else if (ce->cfra > bezt->vec[1][0]) break;
320         }
321         
322         /* create a new column */
323         cen= MEM_callocN(sizeof(CfraElem), "add_to_cfra_elem"); 
324         if (ce) BLI_insertlinkbefore(lb, ce, cen);
325         else BLI_addtail(lb, cen);
326
327         cen->cfra= bezt->vec[1][0];
328         cen->sel= bezt->f2;
329 }
330
331 /* ***************************** Samples Utilities ******************************* */
332 /* Some utilities for working with FPoints (i.e. 'sampled' animation curve data, such as
333  * data imported from BVH/Mocap files), which are specialised for use with high density datasets,
334  * which BezTriples/Keyframe data are ill equipped to do.
335  */
336  
337  
338 /* Basic sampling callback which acts as a wrapper for evaluate_fcurve() 
339  *      'data' arg here is unneeded here...
340  */
341 float fcurve_samplingcb_evalcurve (FCurve *fcu, void *data, float evaltime)
342 {
343         /* assume any interference from drivers on the curve is intended... */
344         return evaluate_fcurve(fcu, evaltime);
345
346
347  
348 /* Main API function for creating a set of sampled curve data, given some callback function 
349  * used to retrieve the values to store.
350  */
351 void fcurve_store_samples (FCurve *fcu, void *data, int start, int end, FcuSampleFunc sample_cb)
352 {
353         FPoint *fpt, *new_fpt;
354         int cfra;
355         
356         /* sanity checks */
357         // TODO: make these tests report errors using reports not printf's
358         if ELEM(NULL, fcu, sample_cb) {
359                 printf("Error: No F-Curve with F-Curve Modifiers to Bake\n");
360                 return;
361         }
362         if (start >= end) {
363                 printf("Error: Frame range for Sampled F-Curve creation is inappropriate \n");
364                 return;
365         }
366         
367         /* set up sample data */
368         fpt= new_fpt= MEM_callocN(sizeof(FPoint)*(end-start+1), "FPoint Samples");
369         
370         /* use the sampling callback at 1-frame intervals from start to end frames */
371         for (cfra= start; cfra <= end; cfra++, fpt++) {
372                 fpt->vec[0]= (float)cfra;
373                 fpt->vec[1]= sample_cb(fcu, data, (float)cfra);
374         }
375         
376         /* free any existing sample/keyframe data on curve  */
377         if (fcu->bezt) MEM_freeN(fcu->bezt);
378         if (fcu->fpt) MEM_freeN(fcu->fpt);
379         
380         /* store the samples */
381         fcu->bezt= NULL;
382         fcu->fpt= new_fpt;
383         fcu->totvert= end - start + 1;
384 }
385
386 /* ***************************** F-Curve Sanity ********************************* */
387 /* The functions here are used in various parts of Blender, usually after some editing
388  * of keyframe data has occurred. They ensure that keyframe data is properly ordered and
389  * that the handles are correctly 
390  */
391
392 /* This function recalculates the handles of an F-Curve 
393  * If the BezTriples have been rearranged, sort them first before using this.
394  */
395 void calchandles_fcurve (FCurve *fcu)
396 {
397         BezTriple *bezt, *prev, *next;
398         int a= fcu->totvert;
399
400         /* Error checking:
401          *      - need at least two points
402          *      - need bezier keys
403          *      - only bezier-interpolation has handles (for now)
404          */
405         if (ELEM(NULL, fcu, fcu->bezt) || (a < 2) /*|| ELEM(fcu->ipo, BEZT_IPO_CONST, BEZT_IPO_LIN)*/) 
406                 return;
407         
408         /* get initial pointers */
409         bezt= fcu->bezt;
410         prev= NULL;
411         next= (bezt + 1);
412         
413         /* loop over all beztriples, adjusting handles */
414         while (a--) {
415                 /* clamp timing of handles to be on either side of beztriple */
416                 if (bezt->vec[0][0] > bezt->vec[1][0]) bezt->vec[0][0]= bezt->vec[1][0];
417                 if (bezt->vec[2][0] < bezt->vec[1][0]) bezt->vec[2][0]= bezt->vec[1][0];
418                 
419                 /* calculate auto-handles */
420                 if (fcu->flag & FCURVE_AUTO_HANDLES) 
421                         calchandleNurb(bezt, prev, next, 2);    /* 2==special autohandle && keep extrema horizontal */
422                 else
423                         calchandleNurb(bezt, prev, next, 1);    /* 1==special autohandle */
424                 
425                 /* for automatic ease in and out */
426                 if ((bezt->h1==HD_AUTO) && (bezt->h2==HD_AUTO)) {
427                         /* only do this on first or last beztriple */
428                         if ((a == 0) || (a == fcu->totvert-1)) {
429                                 /* set both handles to have same horizontal value as keyframe */
430                                 if (fcu->extend == FCURVE_EXTRAPOLATE_CONSTANT) {
431                                         bezt->vec[0][1]= bezt->vec[2][1]= bezt->vec[1][1];
432                                 }
433                         }
434                 }
435                 
436                 /* advance pointers for next iteration */
437                 prev= bezt;
438                 if (a == 1) next= NULL;
439                 else next++;
440                 bezt++;
441         }
442 }
443
444 /* Use when F-Curve with handles has changed
445  * It treats all BezTriples with the following rules:
446  *  - PHASE 1: do types have to be altered?
447  *              -> Auto handles: become aligned when selection status is NOT(000 || 111)
448  *              -> Vector handles: become 'nothing' when (one half selected AND other not)
449  *  - PHASE 2: recalculate handles
450 */
451 void testhandles_fcurve (FCurve *fcu)
452 {
453         BezTriple *bezt;
454         unsigned int a;
455
456         /* only beztriples have handles (bpoints don't though) */
457         if ELEM(NULL, fcu, fcu->bezt)
458                 return;
459         
460         /* loop over beztriples */
461         for (a=0, bezt=fcu->bezt; a < fcu->totvert; a++, bezt++) {
462                 short flag= 0;
463                 
464                 /* flag is initialised as selection status
465                  * of beztriple control-points (labelled 0,1,2)
466                  */
467                 if (bezt->f1 & SELECT) flag |= (1<<0); // == 1
468                 if (bezt->f2 & SELECT) flag |= (1<<1); // == 2
469                 if (bezt->f3 & SELECT) flag |= (1<<2); // == 4
470                 
471                 /* one or two handles selected only */
472                 if (ELEM(flag, 0, 7)==0) {
473                         /* auto handles become aligned */
474                         if (bezt->h1==HD_AUTO)
475                                 bezt->h1= HD_ALIGN;
476                         if (bezt->h2==HD_AUTO)
477                                 bezt->h2= HD_ALIGN;
478                         
479                         /* vector handles become 'free' when only one half selected */
480                         if (bezt->h1==HD_VECT) {
481                                 /* only left half (1 or 2 or 1+2) */
482                                 if (flag < 4) 
483                                         bezt->h1= 0;
484                         }
485                         if (bezt->h2==HD_VECT) {
486                                 /* only right half (4 or 2+4) */
487                                 if (flag > 3) 
488                                         bezt->h2= 0;
489                         }
490                 }
491         }
492
493         /* recalculate handles */
494         calchandles_fcurve(fcu);
495 }
496
497 /* This function sorts BezTriples so that they are arranged in chronological order,
498  * as tools working on F-Curves expect that the BezTriples are in order.
499  */
500 void sort_time_fcurve (FCurve *fcu)
501 {
502         short ok= 1;
503         
504         /* keep adjusting order of beztriples until nothing moves (bubble-sort) */
505         while (ok) {
506                 ok= 0;
507                 
508                 /* currently, will only be needed when there are beztriples */
509                 if (fcu->bezt) {
510                         BezTriple *bezt;
511                         unsigned int a;
512                         
513                         /* loop over ALL points to adjust position in array and recalculate handles */
514                         for (a=0, bezt=fcu->bezt; a < fcu->totvert; a++, bezt++) {
515                                 /* check if thee's a next beztriple which we could try to swap with current */
516                                 if (a < (fcu->totvert-1)) {
517                                         /* swap if one is after the other (and indicate that order has changed) */
518                                         if (bezt->vec[1][0] > (bezt+1)->vec[1][0]) {
519                                                 SWAP(BezTriple, *bezt, *(bezt+1));
520                                                 ok= 1;
521                                         }
522                                         
523                                         /* if either one of both of the points exceeds crosses over the keyframe time... */
524                                         if ( (bezt->vec[0][0] > bezt->vec[1][0]) && (bezt->vec[2][0] < bezt->vec[1][0]) ) {
525                                                 /* swap handles if they have switched sides for some reason */
526                                                 SWAP(float, bezt->vec[0][0], bezt->vec[2][0]);
527                                                 SWAP(float, bezt->vec[0][1], bezt->vec[2][1]);
528                                         }
529                                         else {
530                                                 /* clamp handles */
531                                                 if (bezt->vec[0][0] > bezt->vec[1][0]) 
532                                                         bezt->vec[0][0]= bezt->vec[1][0];
533                                                 if (bezt->vec[2][0] < bezt->vec[1][0]) 
534                                                         bezt->vec[2][0]= bezt->vec[1][0];
535                                         }
536                                 }
537                         }
538                 }
539         }
540 }
541
542 /* This function tests if any BezTriples are out of order, thus requiring a sort */
543 short test_time_fcurve (FCurve *fcu)
544 {
545         unsigned int a;
546         
547         /* sanity checks */
548         if (fcu == NULL)
549                 return 0;
550         
551         /* currently, only need to test beztriples */
552         if (fcu->bezt) {
553                 BezTriple *bezt;
554                 
555                 /* loop through all BezTriples, stopping when one exceeds the one after it */
556                 for (a=0, bezt= fcu->bezt; a < (fcu->totvert - 1); a++, bezt++) {
557                         if (bezt->vec[1][0] > (bezt+1)->vec[1][0])
558                                 return 1;
559                 }
560         }
561         else if (fcu->fpt) {
562                 FPoint *fpt;
563                 
564                 /* loop through all FPoints, stopping when one exceeds the one after it */
565                 for (a=0, fpt= fcu->fpt; a < (fcu->totvert - 1); a++, fpt++) {
566                         if (fpt->vec[0] > (fpt+1)->vec[0])
567                                 return 1;
568                 }
569         }
570         
571         /* none need any swapping */
572         return 0;
573 }
574
575 /* ***************************** Drivers ********************************* */
576
577 /* Driver API --------------------------------- */
578
579 /* This frees the driver target itself */
580 void driver_free_target (ChannelDriver *driver, DriverTarget *dtar)
581 {
582         /* sanity checks */
583         if (dtar == NULL)
584                 return;
585                 
586         /* free target vars */
587         if (dtar->rna_path)
588                 MEM_freeN(dtar->rna_path);
589         
590         /* remove the target from the driver */
591         if (driver)
592                 BLI_freelinkN(&driver->targets, dtar);
593         else
594                 MEM_freeN(dtar);
595 }
596
597 /* Add a new driver target variable */
598 DriverTarget *driver_add_new_target (ChannelDriver *driver)
599 {
600         DriverTarget *dtar;
601         
602         /* sanity checks */
603         if (driver == NULL)
604                 return NULL;
605                 
606         /* make a new target */
607         dtar= MEM_callocN(sizeof(DriverTarget), "DriverTarget");
608         BLI_addtail(&driver->targets, dtar);
609         
610         /* give the target a 'unique' name */
611         strcpy(dtar->name, "var");
612         BLI_uniquename(&driver->targets, dtar, "var", '_', offsetof(DriverTarget, name), 64);
613         
614         /* return the target */
615         return dtar;
616 }
617
618 /* This frees the driver itself */
619 void fcurve_free_driver(FCurve *fcu)
620 {
621         ChannelDriver *driver;
622         DriverTarget *dtar, *dtarn;
623         
624         /* sanity checks */
625         if ELEM(NULL, fcu, fcu->driver)
626                 return;
627         driver= fcu->driver;
628         
629         /* free driver targets */
630         for (dtar= driver->targets.first; dtar; dtar= dtarn) {
631                 dtarn= dtar->next;
632                 driver_free_target(driver, dtar);
633         }
634         
635         /* free driver itself, then set F-Curve's point to this to NULL (as the curve may still be used) */
636         MEM_freeN(driver);
637         fcu->driver= NULL;
638 }
639
640 /* This makes a copy of the given driver */
641 ChannelDriver *fcurve_copy_driver (ChannelDriver *driver)
642 {
643         ChannelDriver *ndriver;
644         DriverTarget *dtar;
645         
646         /* sanity checks */
647         if (driver == NULL)
648                 return NULL;
649                 
650         /* copy all data */
651         ndriver= MEM_dupallocN(driver);
652         
653         /* copy targets */
654         ndriver->targets.first= ndriver->targets.last= NULL;
655         BLI_duplicatelist(&ndriver->targets, &driver->targets);
656         
657         for (dtar= ndriver->targets.first; dtar; dtar= dtar->next) {
658                 /* make a copy of target's rna path if available */
659                 if (dtar->rna_path)
660                         dtar->rna_path = MEM_dupallocN(dtar->rna_path);
661         }
662         
663         /* return the new driver */
664         return ndriver;
665 }
666
667 /* Driver Evaluation -------------------------- */
668
669 /* Helper function to obtain a value using RNA from the specified source (for evaluating drivers) */
670 float driver_get_target_value (ChannelDriver *driver, DriverTarget *dtar)
671 {
672         PointerRNA id_ptr, ptr;
673         PropertyRNA *prop;
674         ID *id;
675         char *path;
676         int index;
677         float value= 0.0f;
678         
679         /* sanity check */
680         if ELEM(NULL, driver, dtar)
681                 return 0.0f;
682         
683         /* get RNA-pointer for the ID-block given in target */
684         RNA_id_pointer_create(dtar->id, &id_ptr);
685         id= dtar->id;
686         path= dtar->rna_path;
687         index= dtar->array_index;
688         
689         /* error check for missing pointer... */
690         if (id == NULL) {
691                 printf("Error: driver doesn't have any valid target to use \n");
692                 if (G.f & G_DEBUG) printf("\tpath = %s [%d] \n", path, index);
693                 driver->flag |= DRIVER_FLAG_INVALID;
694                 return 0.0f;
695         }
696         
697         /* get property to read from, and get value as appropriate */
698         if (RNA_path_resolve(&id_ptr, path, &ptr, &prop)) {
699                 switch (RNA_property_type(prop)) {
700                         case PROP_BOOLEAN:
701                                 if (RNA_property_array_length(&ptr, prop))
702                                         value= (float)RNA_property_boolean_get_index(&ptr, prop, index);
703                                 else
704                                         value= (float)RNA_property_boolean_get(&ptr, prop);
705                                 break;
706                         case PROP_INT:
707                                 if (RNA_property_array_length(&ptr, prop))
708                                         value= (float)RNA_property_int_get_index(&ptr, prop, index);
709                                 else
710                                         value= (float)RNA_property_int_get(&ptr, prop);
711                                 break;
712                         case PROP_FLOAT:
713                                 if (RNA_property_array_length(&ptr, prop))
714                                         value= RNA_property_float_get_index(&ptr, prop, index);
715                                 else
716                                         value= RNA_property_float_get(&ptr, prop);
717                                 break;
718                         case PROP_ENUM:
719                                 value= (float)RNA_property_enum_get(&ptr, prop);
720                                 break;
721                         default:
722                                 break;
723                 }
724         }
725         else if (G.f & G_DEBUG)
726                 printf("Driver Evaluation Error: cannot resolve target for %s -> %s \n", id->name, path);
727         
728         return value;
729 }
730
731 /* Get two PoseChannels from the targets of the given Driver */
732 static void driver_get_target_pchans2 (ChannelDriver *driver, bPoseChannel **pchan1, bPoseChannel **pchan2)
733 {
734         DriverTarget *dtar;
735         short i = 0;
736         
737         /* before doing anything */
738         *pchan1= NULL;
739         *pchan2= NULL;
740         
741         /* only take the first two targets */
742         for (dtar= driver->targets.first; (dtar) && (i < 2); dtar=dtar->next, i++) {
743                 PointerRNA id_ptr, ptr;
744                 PropertyRNA *prop;
745                 
746                 /* get RNA-pointer for the ID-block given in target */
747                 if (dtar->id)
748                         RNA_id_pointer_create(dtar->id, &id_ptr);
749                 else
750                         continue;
751                 
752                 /* resolve path so that we have pointer to the right posechannel */
753                 if (RNA_path_resolve(&id_ptr, dtar->rna_path, &ptr, &prop)) {
754                         /* is pointer valid (i.e. pointing to an actual posechannel */
755                         if ((ptr.type == &RNA_PoseChannel) && (ptr.data)) {
756                                 /* first or second target? */
757                                 if (i)
758                                         *pchan1= ptr.data;
759                                 else
760                                         *pchan2= ptr.data;
761                         }
762                 }
763         }
764 }
765
766 /* Evaluate an Channel-Driver to get a 'time' value to use instead of "evaltime"
767  *      - "evaltime" is the frame at which F-Curve is being evaluated
768  *      - has to return a float value 
769  */
770 static float evaluate_driver (ChannelDriver *driver, float evaltime)
771 {
772         DriverTarget *dtar;
773         
774         /* check if driver can be evaluated */
775         if (driver->flag & DRIVER_FLAG_INVALID)
776                 return 0.0f;
777         
778         // TODO: the flags for individual targets need to be used too for more fine-grained support...
779         switch (driver->type) {
780                 case DRIVER_TYPE_AVERAGE: /* average values of driver targets */
781                 {
782                         /* check how many targets there are first (i.e. just one?) */
783                         if (driver->targets.first == driver->targets.last) {
784                                 /* just one target, so just use that */
785                                 dtar= driver->targets.first;
786                                 return driver_get_target_value(driver, dtar);
787                         }
788                         else {
789                                 /* more than one target, so average the values of the targets */
790                                 int tot = 0;
791                                 float value = 0.0f;
792                                 
793                                 /* loop through targets, adding (hopefully we don't get any overflow!) */
794                                 for (dtar= driver->targets.first; dtar; dtar=dtar->next) {
795                                         value += driver_get_target_value(driver, dtar); 
796                                         tot++;
797                                 }
798                                 
799                                 /* return the average of these */
800                                 return (value / (float)tot);
801                         }
802                 }
803                         break;
804                 
805                 case DRIVER_TYPE_PYTHON: /* expression */
806                 {
807 #ifndef DISABLE_PYTHON
808                         /* check for empty or invalid expression */
809                         if ( (driver->expression[0] == '\0') ||
810                                  (driver->flag & DRIVER_FLAG_INVALID) )
811                         {
812                                 return 0.0f;
813                         }
814                         
815                         /* this evaluates the expression using Python,and returns its result:
816                          *      - on errors it reports, then returns 0.0f
817                          */
818                         return BPY_pydriver_eval(driver);
819 #endif /* DISABLE_PYTHON*/
820                 }
821                         break;
822
823                 
824                 case DRIVER_TYPE_ROTDIFF: /* difference of rotations of 2 bones (should ideally be in same armature) */
825                 {
826                         bPoseChannel *pchan, *pchan2;
827                         float q1[4], q2[4], quat[4], angle;
828                         
829                         /* get pose channels, and check if we've got two */
830                         driver_get_target_pchans2(driver, &pchan, &pchan2);
831                         if (ELEM(NULL, pchan, pchan2)) {
832                                 /* disable this driver, since it doesn't work correctly... */
833                                 driver->flag |= DRIVER_FLAG_INVALID;
834                                 
835                                 /* check what the error was */
836                                 if ((pchan == NULL) && (pchan2 == NULL))
837                                         printf("Driver Evaluation Error: Rotational difference failed - first 2 targets invalid \n");
838                                 else if (pchan == NULL)
839                                         printf("Driver Evaluation Error: Rotational difference failed - first target not valid PoseChannel \n");
840                                 else if (pchan2 == NULL)
841                                         printf("Driver Evaluation Error: Rotational difference failed - second target not valid PoseChannel \n");
842                                         
843                                 /* stop here... */
844                                 return 0.0f;
845                         }                       
846                         
847                         /* use the final posed locations */
848                         Mat4ToQuat(pchan->pose_mat, q1);
849                         Mat4ToQuat(pchan2->pose_mat, q2);
850                         
851                         QuatInv(q1);
852                         QuatMul(quat, q1, q2);
853                         angle = 2.0f * (saacos(quat[0]));
854                         angle= ABS(angle);
855                         
856                         return (angle > M_PI) ? (float)((2.0f * M_PI) - angle) : (float)(angle);
857                 }
858                         break;
859                 
860                 default:
861                 {
862                         /* special 'hack' - just use stored value 
863                          *      This is currently used as the mechanism which allows animated settings to be able
864                          *      to be changed via the UI.
865                          */
866                         return driver->curval;
867                 }
868         }
869         
870         /* return 0.0f, as couldn't find relevant data to use */
871         return 0.0f;
872 }
873
874 /* ***************************** Curve Calculations ********************************* */
875
876 /* The total length of the handles is not allowed to be more
877  * than the horizontal distance between (v1-v4).
878  * This is to prevent curve loops.
879 */
880 void correct_bezpart (float *v1, float *v2, float *v3, float *v4)
881 {
882         float h1[2], h2[2], len1, len2, len, fac;
883         
884         /* calculate handle deltas */
885         h1[0]= v1[0] - v2[0];
886         h1[1]= v1[1] - v2[1];
887         
888         h2[0]= v4[0] - v3[0];
889         h2[1]= v4[1] - v3[1];
890         
891         /* calculate distances: 
892          *      - len   = span of time between keyframes 
893          *      - len1  = length of handle of start key
894          *      - len2  = length of handle of end key
895          */
896         len= v4[0]- v1[0];
897         len1= (float)fabs(h1[0]);
898         len2= (float)fabs(h2[0]);
899         
900         /* if the handles have no length, no need to do any corrections */
901         if ((len1+len2) == 0.0f) 
902                 return;
903                 
904         /* the two handles cross over each other, so force them
905          * apart using the proportion they overlap 
906          */
907         if ((len1+len2) > len) {
908                 fac= len / (len1+len2);
909                 
910                 v2[0]= (v1[0] - fac*h1[0]);
911                 v2[1]= (v1[1] - fac*h1[1]);
912                 
913                 v3[0]= (v4[0] - fac*h2[0]);
914                 v3[1]= (v4[1] - fac*h2[1]);
915         }
916 }
917
918 /* find root ('zero') */
919 int findzero (float x, float q0, float q1, float q2, float q3, float *o)
920 {
921         double c0, c1, c2, c3, a, b, c, p, q, d, t, phi;
922         int nr= 0;
923
924         c0= q0 - x;
925         c1= 3.0 * (q1 - q0);
926         c2= 3.0 * (q0 - 2.0*q1 + q2);
927         c3= q3 - q0 + 3.0 * (q1 - q2);
928         
929         if (c3 != 0.0) {
930                 a= c2/c3;
931                 b= c1/c3;
932                 c= c0/c3;
933                 a= a/3;
934                 
935                 p= b/3 - a*a;
936                 q= (2*a*a*a - a*b + c) / 2;
937                 d= q*q + p*p*p;
938                 
939                 if (d > 0.0) {
940                         t= sqrt(d);
941                         o[0]= (float)(Sqrt3d(-q+t) + Sqrt3d(-q-t) - a);
942                         
943                         if ((o[0] >= SMALL) && (o[0] <= 1.000001)) return 1;
944                         else return 0;
945                 }
946                 else if (d == 0.0) {
947                         t= Sqrt3d(-q);
948                         o[0]= (float)(2*t - a);
949                         
950                         if ((o[0] >= SMALL) && (o[0] <= 1.000001)) nr++;
951                         o[nr]= (float)(-t-a);
952                         
953                         if ((o[nr] >= SMALL) && (o[nr] <= 1.000001)) return nr+1;
954                         else return nr;
955                 }
956                 else {
957                         phi= acos(-q / sqrt(-(p*p*p)));
958                         t= sqrt(-p);
959                         p= cos(phi/3);
960                         q= sqrt(3 - 3*p*p);
961                         o[0]= (float)(2*t*p - a);
962                         
963                         if ((o[0] >= SMALL) && (o[0] <= 1.000001)) nr++;
964                         o[nr]= (float)(-t * (p + q) - a);
965                         
966                         if ((o[nr] >= SMALL) && (o[nr] <= 1.000001)) nr++;
967                         o[nr]= (float)(-t * (p - q) - a);
968                         
969                         if ((o[nr] >= SMALL) && (o[nr] <= 1.000001)) return nr+1;
970                         else return nr;
971                 }
972         }
973         else {
974                 a=c2;
975                 b=c1;
976                 c=c0;
977                 
978                 if (a != 0.0) {
979                         // discriminant
980                         p= b*b - 4*a*c;
981                         
982                         if (p > 0) {
983                                 p= sqrt(p);
984                                 o[0]= (float)((-b-p) / (2 * a));
985                                 
986                                 if ((o[0] >= SMALL) && (o[0] <= 1.000001)) nr++;
987                                 o[nr]= (float)((-b+p)/(2*a));
988                                 
989                                 if ((o[nr] >= SMALL) && (o[nr] <= 1.000001)) return nr+1;
990                                 else return nr;
991                         }
992                         else if (p == 0) {
993                                 o[0]= (float)(-b / (2 * a));
994                                 if ((o[0] >= SMALL) && (o[0] <= 1.000001)) return 1;
995                                 else return 0;
996                         }
997                 }
998                 else if (b != 0.0) {
999                         o[0]= (float)(-c/b);
1000                         
1001                         if ((o[0] >= SMALL) && (o[0] <= 1.000001)) return 1;
1002                         else return 0;
1003                 }
1004                 else if (c == 0.0) {
1005                         o[0]= 0.0;
1006                         return 1;
1007                 }
1008                 
1009                 return 0;       
1010         }
1011 }
1012
1013 void berekeny (float f1, float f2, float f3, float f4, float *o, int b)
1014 {
1015         float t, c0, c1, c2, c3;
1016         int a;
1017
1018         c0= f1;
1019         c1= 3.0f * (f2 - f1);
1020         c2= 3.0f * (f1 - 2.0f*f2 + f3);
1021         c3= f4 - f1 + 3.0f * (f2 - f3);
1022         
1023         for (a=0; a < b; a++) {
1024                 t= o[a];
1025                 o[a]= c0 + t*c1 + t*t*c2 + t*t*t*c3;
1026         }
1027 }
1028
1029 void berekenx (float *f, float *o, int b)
1030 {
1031         float t, c0, c1, c2, c3;
1032         int a;
1033
1034         c0= f[0];
1035         c1= 3.0f * (f[3] - f[0]);
1036         c2= 3.0f * (f[0] - 2.0f*f[3] + f[6]);
1037         c3= f[9] - f[0] + 3.0f * (f[3] - f[6]);
1038         
1039         for (a=0; a < b; a++) {
1040                 t= o[a];
1041                 o[a]= c0 + t*c1 + t*t*c2 + t*t*t*c3;
1042         }
1043 }
1044
1045
1046 /* -------------------------- */
1047
1048 /* Calculate F-Curve value for 'evaltime' using BezTriple keyframes */
1049 static float fcurve_eval_keyframes (FCurve *fcu, BezTriple *bezts, float evaltime)
1050 {
1051         BezTriple *bezt, *prevbezt, *lastbezt;
1052         float v1[2], v2[2], v3[2], v4[2], opl[32], dx, fac;
1053         unsigned int a;
1054         int b;
1055         float cvalue = 0.0f;
1056         
1057         /* get pointers */
1058         a= fcu->totvert-1;
1059         prevbezt= bezts;
1060         bezt= prevbezt+1;
1061         lastbezt= prevbezt + a;
1062         
1063         /* evaluation time at or past endpoints? */
1064         if (prevbezt->vec[1][0] >= evaltime) 
1065         {
1066                 /* before or on first keyframe */
1067                 if ( (fcu->extend == FCURVE_EXTRAPOLATE_LINEAR) && (prevbezt->ipo != BEZT_IPO_CONST) &&
1068                         !(fcu->flag & FCURVE_DISCRETE_VALUES) ) 
1069                 {
1070                         /* linear or bezier interpolation */
1071                         if (prevbezt->ipo==BEZT_IPO_LIN) 
1072                         {
1073                                 /* Use the next center point instead of our own handle for
1074                                  * linear interpolated extrapolate 
1075                                  */
1076                                 if (fcu->totvert == 1) 
1077                                         cvalue= prevbezt->vec[1][1];
1078                                 else 
1079                                 {
1080                                         bezt = prevbezt+1;
1081                                         dx= prevbezt->vec[1][0] - evaltime;
1082                                         fac= bezt->vec[1][0] - prevbezt->vec[1][0];
1083                                         
1084                                         /* prevent division by zero */
1085                                         if (fac) {
1086                                                 fac= (bezt->vec[1][1] - prevbezt->vec[1][1]) / fac;
1087                                                 cvalue= prevbezt->vec[1][1] - (fac * dx);
1088                                         }
1089                                         else 
1090                                                 cvalue= prevbezt->vec[1][1];
1091                                 }
1092                         } 
1093                         else 
1094                         {
1095                                 /* Use the first handle (earlier) of first BezTriple to calculate the
1096                                  * gradient and thus the value of the curve at evaltime
1097                                  */
1098                                 dx= prevbezt->vec[1][0] - evaltime;
1099                                 fac= prevbezt->vec[1][0] - prevbezt->vec[0][0];
1100                                 
1101                                 /* prevent division by zero */
1102                                 if (fac) {
1103                                         fac= (prevbezt->vec[1][1] - prevbezt->vec[0][1]) / fac;
1104                                         cvalue= prevbezt->vec[1][1] - (fac * dx);
1105                                 }
1106                                 else 
1107                                         cvalue= prevbezt->vec[1][1];
1108                         }
1109                 }
1110                 else 
1111                 {
1112                         /* constant (BEZT_IPO_HORIZ) extrapolation or constant interpolation, 
1113                          * so just extend first keyframe's value 
1114                          */
1115                         cvalue= prevbezt->vec[1][1];
1116                 }
1117         }
1118         else if (lastbezt->vec[1][0] <= evaltime) 
1119         {
1120                 /* after or on last keyframe */
1121                 if ( (fcu->extend == FCURVE_EXTRAPOLATE_LINEAR) && (lastbezt->ipo != BEZT_IPO_CONST) &&
1122                         !(fcu->flag & FCURVE_DISCRETE_VALUES) ) 
1123                 {
1124                         /* linear or bezier interpolation */
1125                         if (lastbezt->ipo==BEZT_IPO_LIN) 
1126                         {
1127                                 /* Use the next center point instead of our own handle for
1128                                  * linear interpolated extrapolate 
1129                                  */
1130                                 if (fcu->totvert == 1) 
1131                                         cvalue= lastbezt->vec[1][1];
1132                                 else 
1133                                 {
1134                                         prevbezt = lastbezt - 1;
1135                                         dx= evaltime - lastbezt->vec[1][0];
1136                                         fac= lastbezt->vec[1][0] - prevbezt->vec[1][0];
1137                                         
1138                                         /* prevent division by zero */
1139                                         if (fac) {
1140                                                 fac= (lastbezt->vec[1][1] - prevbezt->vec[1][1]) / fac;
1141                                                 cvalue= lastbezt->vec[1][1] + (fac * dx);
1142                                         }
1143                                         else 
1144                                                 cvalue= lastbezt->vec[1][1];
1145                                 }
1146                         } 
1147                         else 
1148                         {
1149                                 /* Use the gradient of the second handle (later) of last BezTriple to calculate the
1150                                  * gradient and thus the value of the curve at evaltime
1151                                  */
1152                                 dx= evaltime - lastbezt->vec[1][0];
1153                                 fac= lastbezt->vec[2][0] - lastbezt->vec[1][0];
1154                                 
1155                                 /* prevent division by zero */
1156                                 if (fac) {
1157                                         fac= (lastbezt->vec[2][1] - lastbezt->vec[1][1]) / fac;
1158                                         cvalue= lastbezt->vec[1][1] + (fac * dx);
1159                                 }
1160                                 else 
1161                                         cvalue= lastbezt->vec[1][1];
1162                         }
1163                 }
1164                 else 
1165                 {
1166                         /* constant (BEZT_IPO_HORIZ) extrapolation or constant interpolation, 
1167                          * so just extend last keyframe's value 
1168                          */
1169                         cvalue= lastbezt->vec[1][1];
1170                 }
1171         }
1172         else 
1173         {
1174                 /* evaltime occurs somewhere in the middle of the curve */
1175                 for (a=0; prevbezt && bezt && (a < fcu->totvert-1); a++, prevbezt=bezt, bezt++) 
1176                 {  
1177                         /* evaltime occurs within the interval defined by these two keyframes */
1178                         if ((prevbezt->vec[1][0] <= evaltime) && (bezt->vec[1][0] >= evaltime)) 
1179                         {
1180                                 /* value depends on interpolation mode */
1181                                 if ((prevbezt->ipo == BEZT_IPO_CONST) || (fcu->flag & FCURVE_DISCRETE_VALUES))
1182                                 {
1183                                         /* constant (evaltime not relevant, so no interpolation needed) */
1184                                         cvalue= prevbezt->vec[1][1];
1185                                 }
1186                                 else if (prevbezt->ipo == BEZT_IPO_LIN) 
1187                                 {
1188                                         /* linear - interpolate between values of the two keyframes */
1189                                         fac= bezt->vec[1][0] - prevbezt->vec[1][0];
1190                                         
1191                                         /* prevent division by zero */
1192                                         if (fac) {
1193                                                 fac= (evaltime - prevbezt->vec[1][0]) / fac;
1194                                                 cvalue= prevbezt->vec[1][1] + (fac * (bezt->vec[1][1] - prevbezt->vec[1][1]));
1195                                         }
1196                                         else
1197                                                 cvalue= prevbezt->vec[1][1];
1198                                 }
1199                                 else 
1200                                 {
1201                                         /* bezier interpolation */
1202                                                 /* v1,v2 are the first keyframe and its 2nd handle */
1203                                         v1[0]= prevbezt->vec[1][0];
1204                                         v1[1]= prevbezt->vec[1][1];
1205                                         v2[0]= prevbezt->vec[2][0];
1206                                         v2[1]= prevbezt->vec[2][1];
1207                                                 /* v3,v4 are the last keyframe's 1st handle + the last keyframe */
1208                                         v3[0]= bezt->vec[0][0];
1209                                         v3[1]= bezt->vec[0][1];
1210                                         v4[0]= bezt->vec[1][0];
1211                                         v4[1]= bezt->vec[1][1];
1212                                         
1213                                         /* adjust handles so that they don't overlap (forming a loop) */
1214                                         correct_bezpart(v1, v2, v3, v4);
1215                                         
1216                                         /* try to get a value for this position - if failure, try another set of points */
1217                                         b= findzero(evaltime, v1[0], v2[0], v3[0], v4[0], opl);
1218                                         if (b) {
1219                                                 berekeny(v1[1], v2[1], v3[1], v4[1], opl, 1);
1220                                                 cvalue= opl[0];
1221                                                 break;
1222                                         }
1223                                 }
1224                         }
1225                 }
1226         }
1227         
1228         /* return value */
1229         return cvalue;
1230 }
1231
1232 /* Calculate F-Curve value for 'evaltime' using FPoint samples */
1233 static float fcurve_eval_samples (FCurve *fcu, FPoint *fpts, float evaltime)
1234 {
1235         FPoint *prevfpt, *lastfpt, *fpt;
1236         float cvalue= 0.0f;
1237         
1238         /* get pointers */
1239         prevfpt= fpts;
1240         lastfpt= prevfpt + fcu->totvert-1;
1241         
1242         /* evaluation time at or past endpoints? */
1243         if (prevfpt->vec[0] >= evaltime) {
1244                 /* before or on first sample, so just extend value */
1245                 cvalue= prevfpt->vec[1];
1246         }
1247         else if (lastfpt->vec[0] <= evaltime) {
1248                 /* after or on last sample, so just extend value */
1249                 cvalue= lastfpt->vec[1];
1250         }
1251         else {
1252                 /* find the one on the right frame (assume that these are spaced on 1-frame intervals) */
1253                 fpt= prevfpt + (int)(evaltime - prevfpt->vec[0]);
1254                 cvalue= fpt->vec[1];
1255         }
1256         
1257         /* return value */
1258         return cvalue;
1259 }
1260
1261 /* ***************************** F-Curve - Evaluation ********************************* */
1262
1263 /* Evaluate and return the value of the given F-Curve at the specified frame ("evaltime") 
1264  * Note: this is also used for drivers
1265  */
1266 float evaluate_fcurve (FCurve *fcu, float evaltime) 
1267 {
1268         float cvalue= 0.0f;
1269         float devaltime;
1270         
1271         /* if there is a driver (only if this F-Curve is acting as 'driver'), evaluate it to find value to use as "evaltime" 
1272          * since drivers essentially act as alternative input (i.e. in place of 'time') for F-Curves
1273          *      - this value will also be returned as the value of the 'curve', if there are no keyframes
1274          */
1275         if (fcu->driver) {
1276                 /* evaltime now serves as input for the curve */
1277                 evaltime= cvalue= evaluate_driver(fcu->driver, evaltime);
1278         }
1279         
1280         /* evaluate modifiers which modify time to evaluate the base curve at */
1281         devaltime= evaluate_time_fmodifiers(&fcu->modifiers, fcu, cvalue, evaltime);
1282         
1283         /* evaluate curve-data 
1284          *      - 'devaltime' instead of 'evaltime', as this is the time that the last time-modifying 
1285          *        F-Curve modifier on the stack requested the curve to be evaluated at
1286          */
1287         if (fcu->bezt)
1288                 cvalue= fcurve_eval_keyframes(fcu, fcu->bezt, devaltime);
1289         else if (fcu->fpt)
1290                 cvalue= fcurve_eval_samples(fcu, fcu->fpt, devaltime);
1291         
1292         /* evaluate modifiers */
1293         evaluate_value_fmodifiers(&fcu->modifiers, fcu, &cvalue, evaltime);
1294         
1295         /* if curve can only have integral values, perform truncation (i.e. drop the decimal part)
1296          * here so that the curve can be sampled correctly
1297          */
1298         if (fcu->flag & FCURVE_INT_VALUES)
1299                 cvalue= (float)((int)cvalue);
1300         
1301         /* return evaluated value */
1302         return cvalue;
1303 }
1304
1305 /* Calculate the value of the given F-Curve at the given frame, and set its curval */
1306 void calculate_fcurve (FCurve *fcu, float ctime)
1307 {
1308         /* only calculate + set curval (overriding the existing value) if curve has 
1309          * any data which warrants this...
1310          */
1311         if ( (fcu->totvert) || (fcu->driver && !(fcu->driver->flag & DRIVER_FLAG_INVALID)) ||
1312                  list_has_suitable_fmodifier(&fcu->modifiers, 0, FMI_TYPE_GENERATE_CURVE) )
1313         {
1314                 /* calculate and set curval (evaluates driver too if necessary) */
1315                 fcu->curval= evaluate_fcurve(fcu, ctime);
1316         }
1317 }
1318