Camera tracking: animation datablock for MovieClip
[blender-staging.git] / source / blender / blenkernel / intern / anim_sys.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * The Original Code is Copyright (C) 2009 Blender Foundation, Joshua Leung
19  * All rights reserved.
20  *
21  * The Original Code is: all of this file.
22  *
23  * Contributor(s): Joshua Leung (full recode)
24  *
25  * ***** END GPL LICENSE BLOCK *****
26  */
27
28 /** \file blender/blenkernel/intern/anim_sys.c
29  *  \ingroup bke
30  */
31
32
33 #include <stdio.h>
34 #include <string.h>
35 #include <stddef.h>
36 #include <float.h>
37 #include <math.h>
38
39 #include "MEM_guardedalloc.h"
40
41 #include "BLI_blenlib.h"
42 #include "BLI_dynstr.h"
43 #include "BLI_utildefines.h"
44
45 #include "DNA_anim_types.h"
46 #include "DNA_lamp_types.h"
47 #include "DNA_material_types.h"
48 #include "DNA_scene_types.h"
49 #include "DNA_texture_types.h"
50 #include "DNA_world_types.h"
51
52 #include "BKE_animsys.h"
53 #include "BKE_action.h"
54 #include "BKE_depsgraph.h"
55 #include "BKE_fcurve.h"
56 #include "BKE_nla.h"
57 #include "BKE_global.h"
58 #include "BKE_main.h"
59 #include "BKE_library.h"
60 #include "BKE_report.h"
61 #include "BKE_utildefines.h"
62
63 #include "RNA_access.h"
64
65 #include "nla_private.h"
66
67 /* ***************************************** */
68 /* AnimData API */
69
70 /* Getter/Setter -------------------------------------------- */
71
72 /* Check if ID can have AnimData */
73 short id_type_can_have_animdata (ID *id)
74 {
75         /* sanity check */
76         if (id == NULL)
77                 return 0;
78                 
79         /* Only some ID-blocks have this info for now */
80         // TODO: finish adding this for the other blocktypes
81         switch (GS(id->name)) {
82                         /* has AnimData */
83                 case ID_OB:
84                 case ID_ME: case ID_MB: case ID_CU: case ID_AR: case ID_LT:
85                 case ID_KE:
86                 case ID_PA:
87                 case ID_MA: case ID_TE: case ID_NT:
88                 case ID_LA: case ID_CA: case ID_WO:
89                 case ID_SPK:
90                 case ID_SCE:
91                 case ID_MC:
92                 {
93                         return 1;
94                 }
95                 
96                         /* no AnimData */
97                 default:
98                         return 0;
99         }
100 }
101
102
103 /* Get AnimData from the given ID-block. In order for this to work, we assume that 
104  * the AnimData pointer is stored immediately after the given ID-block in the struct,
105  * as per IdAdtTemplate.
106  */
107 AnimData *BKE_animdata_from_id (ID *id)
108 {
109         /* only some ID-blocks have this info for now, so we cast the 
110          * types that do to be of type IdAdtTemplate, and extract the
111          * AnimData that way
112          */
113         if (id_type_can_have_animdata(id)) {
114                 IdAdtTemplate *iat= (IdAdtTemplate *)id;
115                 return iat->adt;
116         }
117         else
118                 return NULL;
119 }
120
121 /* Add AnimData to the given ID-block. In order for this to work, we assume that 
122  * the AnimData pointer is stored immediately after the given ID-block in the struct,
123  * as per IdAdtTemplate. Also note that 
124  */
125 AnimData *BKE_id_add_animdata (ID *id)
126 {
127         /* Only some ID-blocks have this info for now, so we cast the 
128          * types that do to be of type IdAdtTemplate, and add the AnimData
129          * to it using the template
130          */
131         if (id_type_can_have_animdata(id)) {
132                 IdAdtTemplate *iat= (IdAdtTemplate *)id;
133                 
134                 /* check if there's already AnimData, in which case, don't add */
135                 if (iat->adt == NULL) {
136                         AnimData *adt;
137                         
138                         /* add animdata */
139                         adt= iat->adt= MEM_callocN(sizeof(AnimData), "AnimData");
140                         
141                         /* set default settings */
142                         adt->act_influence= 1.0f;
143                 }
144                 
145                 return iat->adt;
146         }
147         else 
148                 return NULL;
149 }
150
151 /* Action Setter --------------------------------------- */
152
153 /* Called when user tries to change the active action of an AnimData block (via RNA, Outliner, etc.) */
154 short BKE_animdata_set_action (ReportList *reports, ID *id, bAction *act)
155 {
156         AnimData *adt = BKE_animdata_from_id(id);
157         short ok = 0;
158         
159         /* animdata validity check */
160         if (adt == NULL) {
161                 BKE_report(reports, RPT_WARNING, "No AnimData to set action on");
162                 return ok;
163         }
164         
165         /* active action is only editable when it is not a tweaking strip 
166          * see rna_AnimData_action_editable() in rna_animation.c
167          */
168         if ((adt->flag & ADT_NLA_EDIT_ON) || (adt->actstrip) || (adt->tmpact)) {
169                 /* cannot remove, otherwise things turn to custard */
170                 BKE_report(reports, RPT_ERROR, "Cannot change action, as it is still being edited in NLA");
171                 return ok;
172         }
173         
174         /* manage usercount for current action */
175         if (adt->action)
176                 id_us_min((ID*)adt->action);
177         
178         /* assume that AnimData's action can in fact be edited... */
179         if (act) {
180                 /* action must have same type as owner */
181                 if (ELEM(act->idroot, 0, GS(id->name))) {
182                         /* can set */
183                         adt->action = act;
184                         id_us_plus((ID*)adt->action);
185                         ok = 1;
186                 }
187                 else {
188                         /* cannot set */
189                         BKE_reportf(reports, RPT_ERROR,
190                                         "Couldn't set Action '%s' onto ID '%s', as it doesn't have suitably rooted paths for this purpose", 
191                                         act->id.name+2, id->name);
192                         //ok = 0;
193                 }
194         }
195         else {
196                 /* just clearing the action... */
197                 adt->action = NULL;
198                 ok = 1;
199         }
200         
201         return ok;
202 }
203
204 /* Freeing -------------------------------------------- */
205
206 /* Free AnimData used by the nominated ID-block, and clear ID-block's AnimData pointer */
207 void BKE_free_animdata (ID *id)
208 {
209         /* Only some ID-blocks have this info for now, so we cast the 
210          * types that do to be of type IdAdtTemplate
211          */
212         if (id_type_can_have_animdata(id)) {
213                 IdAdtTemplate *iat= (IdAdtTemplate *)id;
214                 AnimData *adt= iat->adt;
215                 
216                 /* check if there's any AnimData to start with */
217                 if (adt) {
218                         /* unlink action (don't free, as it's in its own list) */
219                         if (adt->action)
220                                 adt->action->id.us--;
221                         /* same goes for the temporarily displaced action */
222                         if (adt->tmpact)
223                                 adt->tmpact->id.us--;
224                                 
225                         /* free nla data */
226                         free_nladata(&adt->nla_tracks);
227                         
228                         /* free drivers - stored as a list of F-Curves */
229                         free_fcurves(&adt->drivers);
230                         
231                         /* free overrides */
232                         // TODO...
233                         
234                         /* free animdata now */
235                         MEM_freeN(adt);
236                         iat->adt= NULL;
237                 }
238         }
239 }
240
241 /* Freeing -------------------------------------------- */
242
243 /* Make a copy of the given AnimData - to be used when copying datablocks */
244 AnimData *BKE_copy_animdata (AnimData *adt, const short do_action)
245 {
246         AnimData *dadt;
247         
248         /* sanity check before duplicating struct */
249         if (adt == NULL)
250                 return NULL;
251         dadt= MEM_dupallocN(adt);
252         
253         /* make a copy of action - at worst, user has to delete copies... */
254         if (do_action) {
255                 dadt->action= copy_action(adt->action);
256                 dadt->tmpact= copy_action(adt->tmpact);
257         }
258         else {
259                 id_us_plus((ID *)dadt->action);
260                 id_us_plus((ID *)dadt->tmpact);
261         }
262
263         /* duplicate NLA data */
264         copy_nladata(&dadt->nla_tracks, &adt->nla_tracks);
265         
266         /* duplicate drivers (F-Curves) */
267         copy_fcurves(&dadt->drivers, &adt->drivers);
268         
269         /* don't copy overrides */
270         dadt->overrides.first= dadt->overrides.last= NULL;
271         
272         /* return */
273         return dadt;
274 }
275
276 int BKE_copy_animdata_id (ID *id_to, ID *id_from, const short do_action)
277 {
278         AnimData *adt;
279
280         if ((id_to && id_from) && (GS(id_to->name) != GS(id_from->name)))
281                 return 0;
282
283         BKE_free_animdata(id_to);
284
285         adt = BKE_animdata_from_id(id_from);
286         if (adt) {
287                 IdAdtTemplate *iat = (IdAdtTemplate *)id_to;
288                 iat->adt= BKE_copy_animdata(adt, do_action);
289         }
290
291         return 1;
292 }
293
294 void BKE_copy_animdata_id_action(ID *id)
295 {
296         AnimData *adt= BKE_animdata_from_id(id);
297         if (adt) {
298                 if (adt->action) {
299                         id_us_min((ID *)adt->action);
300                         adt->action= copy_action(adt->action);
301                 }
302                 if (adt->tmpact) {
303                         id_us_min((ID *)adt->tmpact);
304                         adt->tmpact= copy_action(adt->tmpact);
305                 }
306         }
307 }
308
309 /* Make Local -------------------------------------------- */
310
311 static void make_local_strips(ListBase *strips)
312 {
313         NlaStrip *strip;
314
315         for (strip=strips->first; strip; strip=strip->next) {
316                 if (strip->act) make_local_action(strip->act);
317                 if (strip->remap && strip->remap->target) make_local_action(strip->remap->target);
318                 
319                 make_local_strips(&strip->strips);
320         }
321 }
322
323 /* Use local copy instead of linked copy of various ID-blocks */
324 void BKE_animdata_make_local(AnimData *adt)
325 {
326         NlaTrack *nlt;
327         
328         /* Actions - Active and Temp */
329         if (adt->action) make_local_action(adt->action);
330         if (adt->tmpact) make_local_action(adt->tmpact);
331         /* Remaps */
332         if (adt->remap && adt->remap->target) make_local_action(adt->remap->target);
333         
334         /* Drivers */
335         // TODO: need to remap the ID-targets too?
336         
337         /* NLA Data */
338         for (nlt=adt->nla_tracks.first; nlt; nlt=nlt->next) 
339                 make_local_strips(&nlt->strips);
340 }
341
342
343 /* When duplicating data (i.e. objects), drivers referring to the original data will 
344  * get updated to point to the duplicated data (if drivers belong to the new data)
345  */
346 void BKE_relink_animdata (AnimData *adt)
347 {
348         /* sanity check */
349         if (adt == NULL)
350                 return;
351         
352         /* drivers */
353         if (adt->drivers.first) {
354                 FCurve *fcu;
355                 
356                 /* check each driver against all the base paths to see if any should go */
357                 for (fcu= adt->drivers.first; fcu; fcu=fcu->next) {
358                         ChannelDriver *driver= fcu->driver;
359                         DriverVar *dvar;
360                         
361                         /* driver variables */
362                         for (dvar= driver->variables.first; dvar; dvar=dvar->next) {
363                                 /* only change the used targets, since the others will need fixing manually anyway */
364                                 DRIVER_TARGETS_USED_LOOPER(dvar)
365                                 {
366                                         if (dtar->id && dtar->id->newid) {
367                                                 dtar->id= dtar->id->newid;
368                                         }
369                                 }
370                                 DRIVER_TARGETS_LOOPER_END
371                         }
372                 }
373         }
374 }
375
376 /* Sub-ID Regrouping ------------------------------------------- */
377
378 /* helper heuristic for determining if a path is compatible with the basepath 
379  * < path: (str) full RNA-path from some data (usually an F-Curve) to compare
380  * < basepath: (str) shorter path fragment to look for
381  * > returns (bool) whether there is a match
382  */
383 static short animpath_matches_basepath (const char path[], const char basepath[])
384 {
385         /* we need start of path to be basepath */
386         return (path && basepath) && (strstr(path, basepath) == path);
387 }
388
389 /* Move F-Curves in src action to dst action, setting up all the necessary groups 
390  * for this to happen, but only if the F-Curves being moved have the appropriate 
391  * "base path". 
392  *      - This is used when data moves from one datablock to another, causing the
393  *        F-Curves to need to be moved over too
394  */
395 void action_move_fcurves_by_basepath (bAction *srcAct, bAction *dstAct, const char basepath[])
396 {
397         FCurve *fcu, *fcn=NULL;
398         
399         /* sanity checks */
400         if ELEM3(NULL, srcAct, dstAct, basepath) {
401                 if (G.f & G_DEBUG) {
402                         printf("ERROR: action_partition_fcurves_by_basepath(%p, %p, %p) has insufficient info to work with\n",
403                                         (void *)srcAct, (void *)dstAct, (void *)basepath);
404                 }
405                 return;
406         }
407                 
408         /* clear 'temp' flags on all groups in src, as we'll be needing them later 
409          * to identify groups that we've managed to empty out here
410          */
411         action_groups_clear_tempflags(srcAct);
412         
413         /* iterate over all src F-Curves, moving over the ones that need to be moved */
414         for (fcu = srcAct->curves.first; fcu; fcu = fcn) {
415                 /* store next pointer in case we move stuff */
416                 fcn = fcu->next;
417                 
418                 /* should F-Curve be moved over?
419                  *      - we only need the start of the path to match basepath
420                  */
421                 if (animpath_matches_basepath(fcu->rna_path, basepath)) {                       
422                         bActionGroup *agrp = NULL;
423                         
424                         /* if grouped... */
425                         if (fcu->grp) {
426                                 /* make sure there will be a matching group on the other side for the migrants */
427                                 agrp = action_groups_find_named(dstAct, fcu->grp->name);
428                                 
429                                 if (agrp == NULL) {
430                                         /* add a new one with a similar name (usually will be the same though) */
431                                         agrp = action_groups_add_new(dstAct, fcu->grp->name);
432                                 }
433                                 
434                                 /* old groups should be tagged with 'temp' flags so they can be removed later
435                                  * if we remove everything from them
436                                  */
437                                 fcu->grp->flag |= AGRP_TEMP;
438                         }
439                         
440                         /* perform the migration now */
441                         action_groups_remove_channel(srcAct, fcu);
442                         
443                         if (agrp)
444                                 action_groups_add_channel(dstAct, agrp, fcu);
445                         else
446                                 BLI_addtail(&dstAct->curves, fcu);
447                 }
448         }
449         
450         /* cleanup groups (if present) */
451         if (srcAct->groups.first) {
452                 bActionGroup *agrp, *grp=NULL;
453                 
454                 for (agrp = srcAct->groups.first; agrp; agrp = grp) {
455                         grp = agrp->next;
456                         
457                         /* only tagged groups need to be considered - clearing these tags or removing them */
458                         if (agrp->flag & AGRP_TEMP) {
459                                 /* if group is empty and tagged, then we can remove as this operation
460                                  * moved out all the channels that were formerly here
461                                  */
462                                 if (agrp->channels.first == NULL)
463                                         BLI_freelinkN(&srcAct->groups, agrp);
464                                 else
465                                         agrp->flag &= ~AGRP_TEMP;
466                         }
467                 }
468         }
469 }
470
471 /* Transfer the animation data from srcID to dstID where the srcID
472  * animation data is based off "basepath", creating new AnimData and
473  * associated data as necessary
474  */
475 void BKE_animdata_separate_by_basepath (ID *srcID, ID *dstID, ListBase *basepaths)
476 {
477         AnimData *srcAdt=NULL, *dstAdt=NULL;
478         LinkData *ld;
479         
480         /* sanity checks */
481         if ELEM(NULL, srcID, dstID) {
482                 if (G.f & G_DEBUG)
483                         printf("ERROR: no source or destination ID to separate AnimData with\n");
484                 return;
485         }
486         
487         /* get animdata from src, and create for destination (if needed) */
488         srcAdt = BKE_animdata_from_id(srcID);
489         dstAdt = BKE_id_add_animdata(dstID);
490         
491         if ELEM(NULL, srcAdt, dstAdt) {
492                 if (G.f & G_DEBUG)
493                         printf("ERROR: no AnimData for this pair of ID's\n");
494                 return;
495         }
496         
497         /* active action */
498         if (srcAdt->action) {
499                 /* set up an action if necessary, and name it in a similar way so that it can be easily found again */
500                 if (dstAdt->action == NULL) {
501                         dstAdt->action = add_empty_action(srcAdt->action->id.name+2);
502                 }
503                 else if (dstAdt->action == srcAdt->action) {
504                         printf("Argh! Source and Destination share animation! ('%s' and '%s' both use '%s') Making new empty action\n",
505                                 srcID->name, dstID->name, srcAdt->action->id.name);
506                         
507                         // TODO: review this...
508                         id_us_min(&dstAdt->action->id);
509                         dstAdt->action = add_empty_action(dstAdt->action->id.name+2);
510                 }
511                         
512                 /* loop over base paths, trying to fix for each one... */
513                 for (ld = basepaths->first; ld; ld = ld->next) {
514                         const char *basepath = (const char *)ld->data;
515                         action_move_fcurves_by_basepath(srcAdt->action, dstAdt->action, basepath);
516                 }
517         }
518         
519         /* drivers */
520         if (srcAdt->drivers.first) {
521                 FCurve *fcu, *fcn=NULL;
522                 
523                 /* check each driver against all the base paths to see if any should go */
524                 for (fcu = srcAdt->drivers.first; fcu; fcu = fcn) {
525                         fcn = fcu->next;
526                         
527                         /* try each basepath in turn, but stop on the first one which works */
528                         for (ld = basepaths->first; ld; ld = ld->next) {
529                                 const char *basepath = (const char *)ld->data;
530                                 
531                                 if (animpath_matches_basepath(fcu->rna_path, basepath)) {
532                                         /* just need to change lists */
533                                         BLI_remlink(&srcAdt->drivers, fcu);
534                                         BLI_addtail(&dstAdt->drivers, fcu);
535                                         
536                                         // TODO: add depsgraph flushing calls?
537                                         
538                                         /* can stop now, as moved already */
539                                         break;
540                                 }
541                         }
542                 }
543         }
544 }
545
546 /* Path Validation -------------------------------------------- */
547
548 /* Check if a given RNA Path is valid, by tracing it from the given ID, and seeing if we can resolve it */
549 static short check_rna_path_is_valid (ID *owner_id, const char *path)
550 {
551         PointerRNA id_ptr, ptr;
552         PropertyRNA *prop=NULL;
553         
554         /* make initial RNA pointer to start resolving from */
555         RNA_id_pointer_create(owner_id, &id_ptr);
556         
557         /* try to resolve */
558         return RNA_path_resolve(&id_ptr, path, &ptr, &prop); 
559 }
560
561 /* Check if some given RNA Path needs fixing - free the given path and set a new one as appropriate 
562  * NOTE: we assume that oldName and newName have [" "] padding around them
563  */
564 static char *rna_path_rename_fix (ID *owner_id, const char *prefix, const char *oldName, const char *newName, char *oldpath, int verify_paths)
565 {
566         char *prefixPtr= strstr(oldpath, prefix);
567         char *oldNamePtr= strstr(oldpath, oldName);
568         int prefixLen= strlen(prefix);
569         int oldNameLen= strlen(oldName);
570         
571         /* only start fixing the path if the prefix and oldName feature in the path,
572          * and prefix occurs immediately before oldName
573          */
574         if ( (prefixPtr && oldNamePtr) && (prefixPtr+prefixLen == oldNamePtr) ) {
575                 /* if we haven't aren't able to resolve the path now, try again after fixing it */
576                 if (!verify_paths || check_rna_path_is_valid(owner_id, oldpath) == 0) {         
577                         DynStr *ds= BLI_dynstr_new();
578                         char *postfixPtr= oldNamePtr+oldNameLen;
579                         char *newPath = NULL;
580                         char oldChar;
581                         
582                         /* add the part of the string that goes up to the start of the prefix */
583                         if (prefixPtr > oldpath) {
584                                 oldChar= prefixPtr[0]; 
585                                 prefixPtr[0]= 0;
586                                 BLI_dynstr_append(ds, oldpath);
587                                 prefixPtr[0]= oldChar;
588                         }
589                         
590                         /* add the prefix */
591                         BLI_dynstr_append(ds, prefix);
592                         
593                         /* add the new name (complete with brackets) */
594                         BLI_dynstr_append(ds, newName);
595                         
596                         /* add the postfix */
597                         BLI_dynstr_append(ds, postfixPtr);
598                         
599                         /* create new path, and cleanup old data */
600                         newPath= BLI_dynstr_get_cstring(ds);
601                         BLI_dynstr_free(ds);
602                         
603                         /* check if the new path will solve our problems */
604                         // TODO: will need to check whether this step really helps in practice
605                         if (!verify_paths || check_rna_path_is_valid(owner_id, newPath)) {
606                                 /* free the old path, and return the new one, since we've solved the issues */
607                                 MEM_freeN(oldpath);
608                                 return newPath;
609                         }
610                         else {
611                                 /* still couldn't resolve the path... so, might as well just leave it alone */
612                                 MEM_freeN(newPath);
613                         }
614                 }
615         }
616         
617         /* the old path doesn't need to be changed */
618         return oldpath;
619 }
620
621 /* Check RNA-Paths for a list of F-Curves */
622 static void fcurves_path_rename_fix (ID *owner_id, const char *prefix, char *oldName, char *newName, ListBase *curves, int verify_paths)
623 {
624         FCurve *fcu;
625         
626         /* we need to check every curve... */
627         for (fcu= curves->first; fcu; fcu= fcu->next) {
628                 /* firstly, handle the F-Curve's own path */
629                 if (fcu->rna_path)
630                         fcu->rna_path= rna_path_rename_fix(owner_id, prefix, oldName, newName, fcu->rna_path, verify_paths);
631         }
632 }
633
634 /* Check RNA-Paths for a list of Drivers */
635 static void drivers_path_rename_fix (ID *owner_id, const char *prefix, const char *oldName, const char *newName, const char *oldKey, const char *newKey, ListBase *curves, int verify_paths)
636 {
637         FCurve *fcu;
638         
639         /* we need to check every curve - drivers are F-Curves too! */
640         for (fcu= curves->first; fcu; fcu= fcu->next) {
641                 /* firstly, handle the F-Curve's own path */
642                 if (fcu->rna_path)
643                         fcu->rna_path= rna_path_rename_fix(owner_id, prefix, oldKey, newKey, fcu->rna_path, verify_paths);
644                 
645                 /* driver? */
646                 if (fcu->driver) {
647                         ChannelDriver *driver= fcu->driver;
648                         DriverVar *dvar;
649                         
650                         /* driver variables */
651                         for (dvar= driver->variables.first; dvar; dvar=dvar->next) {
652                                 /* only change the used targets, since the others will need fixing manually anyway */
653                                 DRIVER_TARGETS_USED_LOOPER(dvar) 
654                                 {
655                                         /* rename RNA path */
656                                         if (dtar->rna_path && dtar->id)
657                                                 dtar->rna_path= rna_path_rename_fix(dtar->id, prefix, oldKey, newKey, dtar->rna_path, verify_paths);
658                                         
659                                         /* also fix the bone-name (if applicable) */
660                                         if (strstr(prefix, "bones")) {
661                                                 if ( ((dtar->id) && (GS(dtar->id->name) == ID_OB)) &&
662                                                          (dtar->pchan_name[0]) && (strcmp(oldName, dtar->pchan_name)==0) )
663                                                 {
664                                                         BLI_strncpy(dtar->pchan_name, newName, sizeof(dtar->pchan_name));
665                                                 }
666                                         }
667                                 }
668                                 DRIVER_TARGETS_LOOPER_END
669                         }
670                 }
671         }
672 }
673
674 /* Fix all RNA-Paths for Actions linked to NLA Strips */
675 static void nlastrips_path_rename_fix (ID *owner_id, const char *prefix, char *oldName, char *newName, ListBase *strips, int verify_paths)
676 {
677         NlaStrip *strip;
678         
679         /* recursively check strips, fixing only actions... */
680         for (strip= strips->first; strip; strip= strip->next) {
681                 /* fix strip's action */
682                 if (strip->act)
683                         fcurves_path_rename_fix(owner_id, prefix, oldName, newName, &strip->act->curves, verify_paths);
684                 /* ignore own F-Curves, since those are local...  */
685                 
686                 /* check sub-strips (if metas) */
687                 nlastrips_path_rename_fix(owner_id, prefix, oldName, newName, &strip->strips, verify_paths);
688         }
689 }
690
691 /* Fix all RNA-Paths in the AnimData block used by the given ID block
692  * NOTE: it is assumed that the structure we're replacing is <prefix><["><name><"]>
693  *              i.e. pose.bones["Bone"]
694  */
695 void BKE_animdata_fix_paths_rename (ID *owner_id, AnimData *adt, const char *prefix, const char *oldName, const char *newName, int oldSubscript, int newSubscript, int verify_paths)
696 {
697         NlaTrack *nlt;
698         char *oldN, *newN;
699         
700         /* if no AnimData, no need to proceed */
701         if (ELEM(NULL, owner_id, adt))
702                 return;
703         
704         if ((oldName != NULL) && (newName != NULL)) {
705                 /* pad the names with [" "] so that only exact matches are made */
706                 oldN= BLI_sprintfN("[\"%s\"]", oldName);
707                 newN= BLI_sprintfN("[\"%s\"]", newName);
708         } 
709         else {
710                 oldN= BLI_sprintfN("[%d]", oldSubscript);
711                 newN= BLI_sprintfN("[%d]", newSubscript);
712         }
713         
714         /* Active action and temp action */
715         if (adt->action)
716                 fcurves_path_rename_fix(owner_id, prefix, oldN, newN, &adt->action->curves, verify_paths);
717         if (adt->tmpact)
718                 fcurves_path_rename_fix(owner_id, prefix, oldN, newN, &adt->tmpact->curves, verify_paths);
719                 
720         /* Drivers - Drivers are really F-Curves */
721         drivers_path_rename_fix(owner_id, prefix, oldName, newName, oldN, newN, &adt->drivers, verify_paths);
722         
723         /* NLA Data - Animation Data for Strips */
724         for (nlt= adt->nla_tracks.first; nlt; nlt= nlt->next)
725                 nlastrips_path_rename_fix(owner_id, prefix, oldN, newN, &nlt->strips, verify_paths);
726                 
727         /* free the temp names */
728         MEM_freeN(oldN);
729         MEM_freeN(newN);
730 }
731
732 /* Whole Database Ops -------------------------------------------- */
733
734 /* apply the given callback function on all data in main database */
735 void BKE_animdata_main_cb (Main *mainptr, ID_AnimData_Edit_Callback func, void *user_data)
736 {
737         ID *id;
738
739         /* standard data version */
740 #define ANIMDATA_IDS_CB(first) \
741         for (id= first; id; id= id->next) { \
742                 AnimData *adt= BKE_animdata_from_id(id); \
743                 if (adt) func(id, adt, user_data); \
744         }
745         
746         /* "embedded" nodetree cases (i.e. scene/material/texture->nodetree) */
747 #define ANIMDATA_NODETREE_IDS_CB(first, NtId_Type) \
748         for (id= first; id; id= id->next) { \
749                 AnimData *adt= BKE_animdata_from_id(id); \
750                 NtId_Type *ntp= (NtId_Type *)id; \
751                 if (ntp->nodetree) { \
752                         AnimData *adt2= BKE_animdata_from_id((ID *)ntp); \
753                         if (adt2) func(id, adt2, user_data); \
754                 } \
755                 if (adt) func(id, adt, user_data); \
756         }
757         
758         /* nodes */
759         ANIMDATA_IDS_CB(mainptr->nodetree.first);
760         
761         /* textures */
762         ANIMDATA_NODETREE_IDS_CB(mainptr->tex.first, Tex);
763         
764         /* lamps */
765         ANIMDATA_IDS_CB(mainptr->lamp.first);
766         
767         /* materials */
768         ANIMDATA_NODETREE_IDS_CB(mainptr->mat.first, Material);
769         
770         /* cameras */
771         ANIMDATA_IDS_CB(mainptr->camera.first);
772         
773         /* shapekeys */
774         ANIMDATA_IDS_CB(mainptr->key.first);
775         
776         /* metaballs */
777         ANIMDATA_IDS_CB(mainptr->mball.first);
778         
779         /* curves */
780         ANIMDATA_IDS_CB(mainptr->curve.first);
781         
782         /* armatures */
783         ANIMDATA_IDS_CB(mainptr->armature.first);
784         
785         /* lattices */
786         ANIMDATA_IDS_CB(mainptr->latt.first);
787         
788         /* meshes */
789         ANIMDATA_IDS_CB(mainptr->mesh.first);
790         
791         /* particles */
792         ANIMDATA_IDS_CB(mainptr->particle.first);
793
794         /* speakers */
795         ANIMDATA_IDS_CB(mainptr->speaker.first);
796
797         /* objects */
798         ANIMDATA_IDS_CB(mainptr->object.first);
799         
800         /* worlds */
801         ANIMDATA_IDS_CB(mainptr->world.first);
802         
803         /* scenes */
804         ANIMDATA_NODETREE_IDS_CB(mainptr->scene.first, Scene);
805 }
806
807 /* Fix all RNA-Paths throughout the database (directly access the Global.main version)
808  * NOTE: it is assumed that the structure we're replacing is <prefix><["><name><"]>
809  *              i.e. pose.bones["Bone"]
810  */
811 /* TODO: use BKE_animdata_main_cb for looping over all data  */
812 void BKE_all_animdata_fix_paths_rename (const char *prefix, const char *oldName, const char *newName)
813 {
814         Main *mainptr= G.main;
815         ID *id;
816         
817         /* macro for less typing 
818          *      - whether animdata exists is checked for by the main renaming callback, though taking 
819          *        this outside of the function may make things slightly faster?
820          */
821 #define RENAMEFIX_ANIM_IDS(first) \
822         for (id= first; id; id= id->next) { \
823                 AnimData *adt= BKE_animdata_from_id(id); \
824                 BKE_animdata_fix_paths_rename(id, adt, prefix, oldName, newName, 0, 0, 1);\
825         }
826         
827         /* another version of this macro for nodetrees */
828 #define RENAMEFIX_ANIM_NODETREE_IDS(first, NtId_Type) \
829         for (id= first; id; id= id->next) { \
830                 AnimData *adt= BKE_animdata_from_id(id); \
831                 NtId_Type *ntp= (NtId_Type *)id; \
832                 if (ntp->nodetree) { \
833                         AnimData *adt2= BKE_animdata_from_id((ID *)ntp); \
834                         BKE_animdata_fix_paths_rename((ID *)ntp, adt2, prefix, oldName, newName, 0, 0, 1);\
835                 } \
836                 BKE_animdata_fix_paths_rename(id, adt, prefix, oldName, newName, 0, 0, 1);\
837         }
838         
839         /* nodes */
840         RENAMEFIX_ANIM_IDS(mainptr->nodetree.first);
841         
842         /* textures */
843         RENAMEFIX_ANIM_NODETREE_IDS(mainptr->tex.first, Tex);
844         
845         /* lamps */
846         RENAMEFIX_ANIM_IDS(mainptr->lamp.first);
847         
848         /* materials */
849         RENAMEFIX_ANIM_NODETREE_IDS(mainptr->mat.first, Material);
850         
851         /* cameras */
852         RENAMEFIX_ANIM_IDS(mainptr->camera.first);
853         
854         /* shapekeys */
855         RENAMEFIX_ANIM_IDS(mainptr->key.first);
856         
857         /* metaballs */
858         RENAMEFIX_ANIM_IDS(mainptr->mball.first);
859         
860         /* curves */
861         RENAMEFIX_ANIM_IDS(mainptr->curve.first);
862         
863         /* armatures */
864         RENAMEFIX_ANIM_IDS(mainptr->armature.first);
865         
866         /* lattices */
867         RENAMEFIX_ANIM_IDS(mainptr->latt.first);
868         
869         /* meshes */
870         RENAMEFIX_ANIM_IDS(mainptr->mesh.first);
871         
872         /* particles */
873         RENAMEFIX_ANIM_IDS(mainptr->particle.first);
874
875         /* speakers */
876         RENAMEFIX_ANIM_IDS(mainptr->speaker.first);
877
878         /* objects */
879         RENAMEFIX_ANIM_IDS(mainptr->object.first); 
880         
881         /* worlds */
882         RENAMEFIX_ANIM_IDS(mainptr->world.first);
883         
884         /* scenes */
885         RENAMEFIX_ANIM_NODETREE_IDS(mainptr->scene.first, Scene);
886 }
887
888 /* *********************************** */ 
889 /* KeyingSet API */
890
891 /* Finding Tools --------------------------- */
892
893 /* Find the first path that matches the given criteria */
894 // TODO: do we want some method to perform partial matches too?
895 KS_Path *BKE_keyingset_find_path (KeyingSet *ks, ID *id, const char group_name[], const char rna_path[], int array_index, int UNUSED(group_mode))
896 {
897         KS_Path *ksp;
898         
899         /* sanity checks */
900         if ELEM3(NULL, ks, rna_path, id)
901                 return NULL;
902         
903         /* loop over paths in the current KeyingSet, finding the first one where all settings match 
904          * (i.e. the first one where none of the checks fail and equal 0)
905          */
906         for (ksp= ks->paths.first; ksp; ksp= ksp->next) {
907                 short eq_id=1, eq_path=1, eq_index=1, eq_group=1;
908                 
909                 /* id */
910                 if (id != ksp->id)
911                         eq_id= 0;
912                 
913                 /* path */
914                 if ((ksp->rna_path==NULL) || strcmp(rna_path, ksp->rna_path))
915                         eq_path= 0;
916                         
917                 /* index - need to compare whole-array setting too... */
918                 if (ksp->array_index != array_index)
919                         eq_index= 0;
920                         
921                 /* group */
922                 if (group_name) {
923                         // FIXME: these checks need to be coded... for now, it's not too important though
924                 }
925                         
926                 /* if all aspects are ok, return */
927                 if (eq_id && eq_path && eq_index && eq_group)
928                         return ksp;
929         }
930         
931         /* none found */
932         return NULL;
933 }
934  
935 /* Defining Tools --------------------------- */
936
937 /* Used to create a new 'custom' KeyingSet for the user, that will be automatically added to the stack */
938 KeyingSet *BKE_keyingset_add (ListBase *list, const char name[], short flag, short keyingflag)
939 {
940         KeyingSet *ks;
941         
942         /* allocate new KeyingSet */
943         ks= MEM_callocN(sizeof(KeyingSet), "KeyingSet");
944
945         BLI_strncpy(ks->name, name ? name : "KeyingSet", sizeof(ks->name));
946
947         ks->flag= flag;
948         ks->keyingflag= keyingflag;
949         
950         /* add KeyingSet to list */
951         BLI_addtail(list, ks);
952         
953         /* make sure KeyingSet has a unique name (this helps with identification) */
954         BLI_uniquename(list, ks, "KeyingSet", '.', offsetof(KeyingSet, name), sizeof(ks->name));
955         
956         /* return new KeyingSet for further editing */
957         return ks;
958 }
959
960 /* Add a path to a KeyingSet. Nothing is returned for now...
961  * Checks are performed to ensure that destination is appropriate for the KeyingSet in question
962  */
963 KS_Path *BKE_keyingset_add_path (KeyingSet *ks, ID *id, const char group_name[], const char rna_path[], int array_index, short flag, short groupmode)
964 {
965         KS_Path *ksp;
966         
967         /* sanity checks */
968         if ELEM(NULL, ks, rna_path) {
969                 printf("ERROR: no Keying Set and/or RNA Path to add path with \n");
970                 return NULL;
971         }
972         
973         /* ID is required for all types of KeyingSets */
974         if (id == NULL) {
975                 printf("ERROR: No ID provided for Keying Set Path. \n");
976                 return NULL;
977         }
978         
979         /* don't add if there is already a matching KS_Path in the KeyingSet */
980         if (BKE_keyingset_find_path(ks, id, group_name, rna_path, array_index, groupmode)) {
981                 if (G.f & G_DEBUG)
982                         printf("ERROR: destination already exists in Keying Set \n");
983                 return NULL;
984         }
985         
986         /* allocate a new KeyingSet Path */
987         ksp= MEM_callocN(sizeof(KS_Path), "KeyingSet Path");
988         
989         /* just store absolute info */
990         ksp->id= id;
991         if (group_name)
992                 BLI_strncpy(ksp->group, group_name, sizeof(ksp->group));
993         else
994                 ksp->group[0]= '\0';
995         
996         /* store additional info for relative paths (just in case user makes the set relative) */
997         if (id)
998                 ksp->idtype= GS(id->name);
999         
1000         /* just copy path info */
1001         // TODO: should array index be checked too?
1002         ksp->rna_path= BLI_strdupn(rna_path, strlen(rna_path));
1003         ksp->array_index= array_index;
1004         
1005         /* store flags */
1006         ksp->flag= flag;
1007         ksp->groupmode= groupmode;
1008         
1009         /* add KeyingSet path to KeyingSet */
1010         BLI_addtail(&ks->paths, ksp);
1011         
1012         /* return this path */
1013         return ksp;
1014 }       
1015
1016 /* Free the given Keying Set path */
1017 void BKE_keyingset_free_path (KeyingSet *ks, KS_Path *ksp)
1018 {
1019         /* sanity check */
1020         if ELEM(NULL, ks, ksp)
1021                 return;
1022
1023         /* free RNA-path info */
1024         if(ksp->rna_path)
1025                 MEM_freeN(ksp->rna_path);
1026
1027         /* free path itself */
1028         BLI_freelinkN(&ks->paths, ksp);
1029 }
1030
1031 /* Copy all KeyingSets in the given list */
1032 void BKE_keyingsets_copy (ListBase *newlist, ListBase *list)
1033 {
1034         KeyingSet *ksn;
1035         KS_Path *kspn;
1036         
1037         BLI_duplicatelist(newlist, list);
1038
1039         for (ksn=newlist->first; ksn; ksn=ksn->next) {
1040                 BLI_duplicatelist(&ksn->paths, &ksn->paths);
1041                 
1042                 for (kspn=ksn->paths.first; kspn; kspn=kspn->next)
1043                         kspn->rna_path= MEM_dupallocN(kspn->rna_path);
1044         }
1045 }
1046
1047 /* Freeing Tools --------------------------- */
1048
1049 /* Free data for KeyingSet but not set itself */
1050 void BKE_keyingset_free (KeyingSet *ks)
1051 {
1052         KS_Path *ksp, *kspn;
1053         
1054         /* sanity check */
1055         if (ks == NULL)
1056                 return;
1057         
1058         /* free each path as we go to avoid looping twice */
1059         for (ksp= ks->paths.first; ksp; ksp= kspn) {
1060                 kspn= ksp->next;
1061                 BKE_keyingset_free_path(ks, ksp);
1062         }
1063 }
1064
1065 /* Free all the KeyingSets in the given list */
1066 void BKE_keyingsets_free (ListBase *list)
1067 {
1068         KeyingSet *ks, *ksn;
1069         
1070         /* sanity check */
1071         if (list == NULL)
1072                 return;
1073         
1074         /* loop over KeyingSets freeing them 
1075          *      - BKE_keyingset_free() doesn't free the set itself, but it frees its sub-data
1076          */
1077         for (ks= list->first; ks; ks= ksn) {
1078                 ksn= ks->next;
1079                 BKE_keyingset_free(ks);
1080                 BLI_freelinkN(list, ks);
1081         }
1082 }
1083
1084 /* ***************************************** */
1085 /* Evaluation Data-Setting Backend */
1086
1087 /* Retrieve string to act as RNA-path, adjusted using mapping-table if provided 
1088  * It returns whether the string needs to be freed (i.e. if it was a temp remapped one)
1089  * // FIXME: maybe it would be faster if we didn't have to alloc/free strings like this all the time, but for now it's safer
1090  *
1091  *      - remap: remapping table to use
1092  *      - path: original path string (as stored in F-Curve data)
1093  *      - dst: destination string to write data to
1094  */
1095 static short animsys_remap_path (AnimMapper *UNUSED(remap), char *path, char **dst)
1096 {
1097         /* is there a valid remapping table to use? */
1098         //if (remap) {
1099                 /* find a matching entry... to use to remap */
1100                 // ...TODO...
1101         //}
1102         
1103         /* nothing suitable found, so just set dst to look at path (i.e. no alloc/free needed) */
1104         *dst= path;
1105         return 0;
1106 }
1107
1108
1109 /* less then 1.0 evaluates to false, use epsilon to avoid float error */
1110 #define ANIMSYS_FLOAT_AS_BOOL(value) ((value) > ((1.0f-FLT_EPSILON)))
1111
1112 /* Write the given value to a setting using RNA, and return success */
1113 static short animsys_write_rna_setting (PointerRNA *ptr, char *path, int array_index, float value)
1114 {
1115         PropertyRNA *prop;
1116         PointerRNA new_ptr;
1117         
1118         //printf("%p %s %i %f\n", ptr, path, array_index, value);
1119         
1120         /* get property to write to */
1121         if (RNA_path_resolve(ptr, path, &new_ptr, &prop)) 
1122         {
1123                 /* set value - only for animatable numerical values */
1124                 if (RNA_property_animateable(&new_ptr, prop)) 
1125                 {
1126                         int array_len= RNA_property_array_length(&new_ptr, prop);
1127                         
1128                         if (array_len && array_index >= array_len)
1129                         {
1130                                 if (G.f & G_DEBUG) {
1131                                         printf("Animato: Invalid array index. ID = '%s',  '%s[%d]', array length is %d \n",
1132                                                 (ptr && ptr->id.data) ? (((ID *)ptr->id.data)->name+2) : "<No ID>",
1133                                                 path, array_index, array_len-1);
1134                                 }
1135                                 
1136                                 return 0;
1137                         }
1138                         
1139                         switch (RNA_property_type(prop)) 
1140                         {
1141                                 case PROP_BOOLEAN:
1142                                         if (array_len)
1143                                                 RNA_property_boolean_set_index(&new_ptr, prop, array_index, ANIMSYS_FLOAT_AS_BOOL(value));
1144                                         else
1145                                                 RNA_property_boolean_set(&new_ptr, prop, ANIMSYS_FLOAT_AS_BOOL(value));
1146                                         break;
1147                                 case PROP_INT:
1148                                         if (array_len)
1149                                                 RNA_property_int_set_index(&new_ptr, prop, array_index, (int)value);
1150                                         else
1151                                                 RNA_property_int_set(&new_ptr, prop, (int)value);
1152                                         break;
1153                                 case PROP_FLOAT:
1154                                         if (array_len)
1155                                                 RNA_property_float_set_index(&new_ptr, prop, array_index, value);
1156                                         else
1157                                                 RNA_property_float_set(&new_ptr, prop, value);
1158                                         break;
1159                                 case PROP_ENUM:
1160                                         RNA_property_enum_set(&new_ptr, prop, (int)value);
1161                                         break;
1162                                 default:
1163                                         /* nothing can be done here... so it is unsuccessful? */
1164                                         return 0;
1165                         }
1166                         
1167                         /* RNA property update disabled for now - [#28525] [#28690] [#28774] [#28777] */
1168 #if 0
1169                         /* buffer property update for later flushing */
1170                         if (RNA_property_update_check(prop)) {
1171                                 short skip_updates_hack = 0;
1172                                 
1173                                 /* optimisation hacks: skip property updates for those properties
1174                                  * for we know that which the updates in RNA were really just for
1175                                  * flushing property editing via UI/Py
1176                                  */
1177                                 if (new_ptr.type == &RNA_PoseBone) {
1178                                         /* bone transforms - update pose (i.e. tag depsgraph) */
1179                                         skip_updates_hack = 1;
1180                                 }                               
1181                                 
1182                                 if (skip_updates_hack == 0)
1183                                         RNA_property_update_cache_add(&new_ptr, prop);
1184                         }
1185 #endif
1186
1187                         /* as long as we don't do property update, we still tag datablock
1188                            as having been updated. this flag does not cause any updates to
1189                            be run, it's for e.g. render engines to synchronize data */
1190                         if(new_ptr.id.data) {
1191                                 ID *id= new_ptr.id.data;
1192                                 id->flag |= LIB_ID_RECALC;
1193                                 DAG_id_type_tag(G.main, GS(id->name));
1194                         }
1195                 }
1196                 
1197                 /* successful */
1198                 return 1;
1199         }
1200         else {
1201                 /* failed to get path */
1202                 // XXX don't tag as failed yet though, as there are some legit situations (Action Constraint) 
1203                 // where some channels will not exist, but shouldn't lock up Action
1204                 if (G.f & G_DEBUG) {
1205                         printf("Animato: Invalid path. ID = '%s',  '%s[%d]' \n",
1206                                 (ptr && ptr->id.data) ? (((ID *)ptr->id.data)->name+2) : "<No ID>", 
1207                                 path, array_index);
1208                 }
1209                 return 0;
1210         }
1211 }
1212
1213 /* Simple replacement based data-setting of the FCurve using RNA */
1214 static short animsys_execute_fcurve (PointerRNA *ptr, AnimMapper *remap, FCurve *fcu)
1215 {
1216         char *path = NULL;
1217         short free_path=0;
1218         short ok= 0;
1219         
1220         /* get path, remapped as appropriate to work in its new environment */
1221         free_path= animsys_remap_path(remap, fcu->rna_path, &path);
1222         
1223         /* write value to setting */
1224         if (path)
1225                 ok= animsys_write_rna_setting(ptr, path, fcu->array_index, fcu->curval);
1226         
1227         /* free temp path-info */
1228         if (free_path)
1229                 MEM_freeN(path);
1230                 
1231         /* return whether we were successful */
1232         return ok;
1233 }
1234
1235 /* Evaluate all the F-Curves in the given list 
1236  * This performs a set of standard checks. If extra checks are required, separate code should be used
1237  */
1238 static void animsys_evaluate_fcurves (PointerRNA *ptr, ListBase *list, AnimMapper *remap, float ctime)
1239 {
1240         FCurve *fcu;
1241         
1242         /* calculate then execute each curve */
1243         for (fcu= list->first; fcu; fcu= fcu->next) 
1244         {
1245                 /* check if this F-Curve doesn't belong to a muted group */
1246                 if ((fcu->grp == NULL) || (fcu->grp->flag & AGRP_MUTED)==0) {
1247                         /* check if this curve should be skipped */
1248                         if ((fcu->flag & (FCURVE_MUTED|FCURVE_DISABLED)) == 0) 
1249                         {
1250                                 calculate_fcurve(fcu, ctime);
1251                                 animsys_execute_fcurve(ptr, remap, fcu); 
1252                         }
1253                 }
1254         }
1255 }
1256
1257 /* ***************************************** */
1258 /* Driver Evaluation */
1259
1260 /* Evaluate Drivers */
1261 static void animsys_evaluate_drivers (PointerRNA *ptr, AnimData *adt, float ctime)
1262 {
1263         FCurve *fcu;
1264         
1265         /* drivers are stored as F-Curves, but we cannot use the standard code, as we need to check if
1266          * the depsgraph requested that this driver be evaluated...
1267          */
1268         for (fcu= adt->drivers.first; fcu; fcu= fcu->next) 
1269         {
1270                 ChannelDriver *driver= fcu->driver;
1271                 short ok= 0;
1272                 
1273                 /* check if this driver's curve should be skipped */
1274                 if ((fcu->flag & (FCURVE_MUTED|FCURVE_DISABLED)) == 0) 
1275                 {
1276                         /* check if driver itself is tagged for recalculation */
1277                         if ((driver) && !(driver->flag & DRIVER_FLAG_INVALID)/*&& (driver->flag & DRIVER_FLAG_RECALC)*/) {      // XXX driver recalc flag is not set yet by depsgraph!
1278                                 /* evaluate this using values set already in other places */
1279                                 // NOTE: for 'layering' option later on, we should check if we should remove old value before adding new to only be done when drivers only changed
1280                                 calculate_fcurve(fcu, ctime);
1281                                 ok= animsys_execute_fcurve(ptr, NULL, fcu);
1282                                 
1283                                 /* clear recalc flag */
1284                                 driver->flag &= ~DRIVER_FLAG_RECALC;
1285                                 
1286                                 /* set error-flag if evaluation failed */
1287                                 if (ok == 0)
1288                                         driver->flag |= DRIVER_FLAG_INVALID; 
1289                         }
1290                 }
1291         }
1292 }
1293
1294 /* ***************************************** */
1295 /* Actions Evaluation */
1296
1297 /* strictly not necessary for actual "evaluation", but it is a useful safety check
1298  * to reduce the amount of times that users end up having to "revive" wrongly-assigned
1299  * actions
1300  */
1301 static void action_idcode_patch_check (ID *id, bAction *act)
1302 {
1303         int idcode = 0;
1304         
1305         /* just in case */
1306         if (ELEM(NULL, id, act))
1307                 return;
1308         else
1309                 idcode = GS(id->name);
1310         
1311         /* the actual checks... hopefully not too much of a performance hit in the long run... */
1312         if (act->idroot == 0) {
1313                 /* use the current root if not set already (i.e. newly created actions and actions from 2.50-2.57 builds)
1314                  *      - this has problems if there are 2 users, and the first one encountered is the invalid one
1315                  *        in which case, the user will need to manually fix this (?)
1316                  */
1317                 act->idroot = idcode;
1318         }
1319         else if (act->idroot != idcode) {
1320                 /* only report this error if debug mode is enabled (to save performance everywhere else) */
1321                 if (G.f & G_DEBUG) {
1322                         printf("AnimSys Safety Check Failed: Action '%s' is not meant to be used from ID-Blocks of type %d such as '%s'\n",
1323                                 act->id.name+2, idcode, id->name);
1324                 }
1325         }
1326 }
1327
1328 /* ----------------------------------------- */
1329
1330 /* Evaluate Action Group */
1331 void animsys_evaluate_action_group (PointerRNA *ptr, bAction *act, bActionGroup *agrp, AnimMapper *remap, float ctime)
1332 {
1333         FCurve *fcu;
1334         
1335         /* check if mapper is appropriate for use here (we set to NULL if it's inappropriate) */
1336         if ELEM(NULL, act, agrp) return;
1337         if ((remap) && (remap->target != act)) remap= NULL;
1338         
1339         action_idcode_patch_check(ptr->id.data, act);
1340         
1341         /* if group is muted, don't evaluated any of the F-Curve */
1342         if (agrp->flag & AGRP_MUTED)
1343                 return;
1344         
1345         /* calculate then execute each curve */
1346         for (fcu= agrp->channels.first; (fcu) && (fcu->grp == agrp); fcu= fcu->next) 
1347         {
1348                 /* check if this curve should be skipped */
1349                 if ((fcu->flag & (FCURVE_MUTED|FCURVE_DISABLED)) == 0) 
1350                 {
1351                         calculate_fcurve(fcu, ctime);
1352                         animsys_execute_fcurve(ptr, remap, fcu); 
1353                 }
1354         }
1355 }
1356
1357 /* Evaluate Action (F-Curve Bag) */
1358 void animsys_evaluate_action (PointerRNA *ptr, bAction *act, AnimMapper *remap, float ctime)
1359 {
1360         /* check if mapper is appropriate for use here (we set to NULL if it's inappropriate) */
1361         if (act == NULL) return;
1362         if ((remap) && (remap->target != act)) remap= NULL;
1363         
1364         action_idcode_patch_check(ptr->id.data, act);
1365         
1366         /* calculate then execute each curve */
1367         animsys_evaluate_fcurves(ptr, &act->curves, remap, ctime);
1368 }
1369
1370 /* ***************************************** */
1371 /* NLA System - Evaluation */
1372
1373 /* calculate influence of strip based for given frame based on blendin/out values */
1374 static float nlastrip_get_influence (NlaStrip *strip, float cframe)
1375 {
1376         /* sanity checks - normalise the blendin/out values? */
1377         strip->blendin= fabsf(strip->blendin);
1378         strip->blendout= fabsf(strip->blendout);
1379         
1380         /* result depends on where frame is in respect to blendin/out values */
1381         if (IS_EQ(strip->blendin, 0)==0 && (cframe <= (strip->start + strip->blendin))) {
1382                 /* there is some blend-in */
1383                 return fabsf(cframe - strip->start) / (strip->blendin);
1384         }
1385         else if (IS_EQ(strip->blendout, 0)==0 && (cframe >= (strip->end - strip->blendout))) {
1386                 /* there is some blend-out */
1387                 return fabsf(strip->end - cframe) / (strip->blendout);
1388         }
1389         else {
1390                 /* in the middle of the strip, we should be full strength */
1391                 return 1.0f;
1392         }
1393 }
1394
1395 /* evaluate the evaluation time and influence for the strip, storing the results in the strip */
1396 static void nlastrip_evaluate_controls (NlaStrip *strip, float ctime)
1397 {
1398         /* firstly, analytically generate values for influence and time (if applicable) */
1399         if ((strip->flag & NLASTRIP_FLAG_USR_TIME) == 0)
1400                 strip->strip_time= nlastrip_get_frame(strip, ctime, NLATIME_CONVERT_EVAL);
1401         if ((strip->flag & NLASTRIP_FLAG_USR_INFLUENCE) == 0)
1402                 strip->influence= nlastrip_get_influence(strip, ctime);
1403         
1404         /* now strip's evaluate F-Curves for these settings (if applicable) */
1405         if (strip->fcurves.first) {
1406                 PointerRNA strip_ptr;
1407                 
1408                 /* create RNA-pointer needed to set values */
1409                 RNA_pointer_create(NULL, &RNA_NlaStrip, strip, &strip_ptr);
1410                 
1411                 /* execute these settings as per normal */
1412                 animsys_evaluate_fcurves(&strip_ptr, &strip->fcurves, NULL, ctime);
1413         }
1414
1415         /* if user can control the evaluation time (using F-Curves), consider the option which allows this time to be clamped 
1416          * to lie within extents of the action-clip, so that a steady changing rate of progress through several cycles of the clip
1417          * can be achieved easily
1418          */
1419         // NOTE: if we add any more of these special cases, we better group them up nicely...
1420         if ((strip->flag & NLASTRIP_FLAG_USR_TIME) && (strip->flag & NLASTRIP_FLAG_USR_TIME_CYCLIC))
1421                 strip->strip_time= fmod(strip->strip_time - strip->actstart, strip->actend - strip->actstart);
1422 }
1423
1424 /* gets the strip active at the current time for a list of strips for evaluation purposes */
1425 NlaEvalStrip *nlastrips_ctime_get_strip (ListBase *list, ListBase *strips, short index, float ctime)
1426 {
1427         NlaStrip *strip, *estrip=NULL;
1428         NlaEvalStrip *nes;
1429         short side= 0;
1430         
1431         /* loop over strips, checking if they fall within the range */
1432         for (strip= strips->first; strip; strip= strip->next) {
1433                 /* check if current time occurs within this strip  */
1434                 if (IN_RANGE_INCL(ctime, strip->start, strip->end)) {
1435                         /* this strip is active, so try to use it */
1436                         estrip= strip;
1437                         side= NES_TIME_WITHIN;
1438                         break;
1439                 }
1440                 
1441                 /* if time occurred before current strip... */
1442                 if (ctime < strip->start) {
1443                         if (strip == strips->first) {
1444                                 /* before first strip - only try to use it if it extends backwards in time too */
1445                                 if (strip->extendmode == NLASTRIP_EXTEND_HOLD)
1446                                         estrip= strip;
1447                                         
1448                                 /* side is 'before' regardless of whether there's a useful strip */
1449                                 side= NES_TIME_BEFORE;
1450                         }
1451                         else {
1452                                 /* before next strip - previous strip has ended, but next hasn't begun, 
1453                                  * so blending mode depends on whether strip is being held or not...
1454                                  *      - only occurs when no transition strip added, otherwise the transition would have
1455                                  *        been picked up above...
1456                                  */
1457                                 strip= strip->prev;
1458                                 
1459                                 if (strip->extendmode != NLASTRIP_EXTEND_NOTHING)
1460                                         estrip= strip;
1461                                 side= NES_TIME_AFTER;
1462                         }
1463                         break;
1464                 }
1465                 
1466                 /* if time occurred after current strip... */
1467                 if (ctime > strip->end) {
1468                         /* only if this is the last strip should we do anything, and only if that is being held */
1469                         if (strip == strips->last) {
1470                                 if (strip->extendmode != NLASTRIP_EXTEND_NOTHING)
1471                                         estrip= strip;
1472                                         
1473                                 side= NES_TIME_AFTER;
1474                                 break;
1475                         }
1476                         
1477                         /* otherwise, skip... as the 'before' case will catch it more elegantly! */
1478                 }
1479         }
1480         
1481         /* check if a valid strip was found
1482          *      - must not be muted (i.e. will have contribution
1483          */
1484         if ((estrip == NULL) || (estrip->flag & NLASTRIP_FLAG_MUTED)) 
1485                 return NULL;
1486                 
1487         /* if ctime was not within the boundaries of the strip, clamp! */
1488         switch (side) {
1489                 case NES_TIME_BEFORE: /* extend first frame only */
1490                         ctime= estrip->start;
1491                         break;
1492                 case NES_TIME_AFTER: /* extend last frame only */
1493                         ctime= estrip->end;
1494                         break;
1495         }
1496         
1497         /* evaluate strip's evaluation controls  
1498          *      - skip if no influence (i.e. same effect as muting the strip)
1499          *      - negative influence is not supported yet... how would that be defined?
1500          */
1501         // TODO: this sounds a bit hacky having a few isolated F-Curves stuck on some data it operates on...
1502         nlastrip_evaluate_controls(estrip, ctime);
1503         if (estrip->influence <= 0.0f)
1504                 return NULL;
1505                 
1506         /* check if strip has valid data to evaluate,
1507          * and/or perform any additional type-specific actions
1508          */
1509         switch (estrip->type) {
1510                 case NLASTRIP_TYPE_CLIP: 
1511                         /* clip must have some action to evaluate */
1512                         if (estrip->act == NULL)
1513                                 return NULL;
1514                         break;
1515                 case NLASTRIP_TYPE_TRANSITION:
1516                         /* there must be strips to transition from and to (i.e. prev and next required) */
1517                         if (ELEM(NULL, estrip->prev, estrip->next))
1518                                 return NULL;
1519                                 
1520                         /* evaluate controls for the relevant extents of the bordering strips... */
1521                         nlastrip_evaluate_controls(estrip->prev, estrip->start);
1522                         nlastrip_evaluate_controls(estrip->next, estrip->end);
1523                         break;
1524         }
1525         
1526         /* add to list of strips we need to evaluate */
1527         nes= MEM_callocN(sizeof(NlaEvalStrip), "NlaEvalStrip");
1528         
1529         nes->strip= estrip;
1530         nes->strip_mode= side;
1531         nes->track_index= index;
1532         nes->strip_time= estrip->strip_time;
1533         
1534         if (list)
1535                 BLI_addtail(list, nes);
1536         
1537         return nes;
1538 }
1539
1540 /* ---------------------- */
1541
1542 /* find an NlaEvalChannel that matches the given criteria 
1543  *      - ptr and prop are the RNA data to find a match for
1544  */
1545 static NlaEvalChannel *nlaevalchan_find_match (ListBase *channels, PointerRNA *ptr, PropertyRNA *prop, int array_index)
1546 {
1547         NlaEvalChannel *nec;
1548         
1549         /* sanity check */
1550         if (channels == NULL)
1551                 return NULL;
1552         
1553         /* loop through existing channels, checking for a channel which affects the same property */
1554         for (nec= channels->first; nec; nec= nec->next) {
1555                 /* - comparing the PointerRNA's is done by comparing the pointers
1556                  *   to the actual struct the property resides in, since that all the
1557                  *   other data stored in PointerRNA cannot allow us to definitively 
1558                  *      identify the data 
1559                  */
1560                 if ((nec->ptr.data == ptr->data) && (nec->prop == prop) && (nec->index == array_index))
1561                         return nec;
1562         }
1563         
1564         /* not found */
1565         return NULL;
1566 }
1567
1568 /* verify that an appropriate NlaEvalChannel for this F-Curve exists */
1569 static NlaEvalChannel *nlaevalchan_verify (PointerRNA *ptr, ListBase *channels, NlaEvalStrip *nes, FCurve *fcu, short *newChan)
1570 {
1571         NlaEvalChannel *nec;
1572         NlaStrip *strip= nes->strip;
1573         PropertyRNA *prop;
1574         PointerRNA new_ptr;
1575         char *path = NULL;
1576         /* short free_path=0; */
1577         
1578         /* sanity checks */
1579         if (channels == NULL)
1580                 return NULL;
1581         
1582         /* get RNA pointer+property info from F-Curve for more convenient handling */
1583                 /* get path, remapped as appropriate to work in its new environment */
1584         /* free_path= */ /* UNUSED */ animsys_remap_path(strip->remap, fcu->rna_path, &path);
1585         
1586                 /* a valid property must be available, and it must be animateable */
1587         if (RNA_path_resolve(ptr, path, &new_ptr, &prop) == 0) {
1588                 if (G.f & G_DEBUG) printf("NLA Strip Eval: Cannot resolve path \n");
1589                 return NULL;
1590         }
1591                 /* only ok if animateable */
1592         else if (RNA_property_animateable(&new_ptr, prop) == 0) {
1593                 if (G.f & G_DEBUG) printf("NLA Strip Eval: Property not animateable \n");
1594                 return NULL;
1595         }
1596         
1597         /* try to find a match */
1598         nec= nlaevalchan_find_match(channels, &new_ptr, prop, fcu->array_index);
1599         
1600         /* allocate a new struct for this if none found */
1601         if (nec == NULL) {
1602                 nec= MEM_callocN(sizeof(NlaEvalChannel), "NlaEvalChannel");
1603                 *newChan= 1;
1604                 BLI_addtail(channels, nec);
1605                 
1606                 nec->ptr= new_ptr; 
1607                 nec->prop= prop;
1608                 nec->index= fcu->array_index;
1609         }
1610         else
1611                 *newChan= 0;
1612         
1613         /* we can now return */
1614         return nec;
1615 }
1616
1617 /* accumulate (i.e. blend) the given value on to the channel it affects */
1618 static void nlaevalchan_accumulate (NlaEvalChannel *nec, NlaEvalStrip *nes, short newChan, float value)
1619 {
1620         NlaStrip *strip= nes->strip;
1621         short blendmode= strip->blendmode;
1622         float inf= strip->influence;
1623         
1624         /* if channel is new, just store value regardless of blending factors, etc. */
1625         if (newChan) {
1626                 nec->value= value;
1627                 return;
1628         }
1629                 
1630         /* if this is being performed as part of transition evaluation, incorporate
1631          * an additional weighting factor for the influence
1632          */
1633         if (nes->strip_mode == NES_TIME_TRANSITION_END) 
1634                 inf *= nes->strip_time;
1635         
1636         /* premultiply the value by the weighting factor */
1637         if (IS_EQ(inf, 0)) return;
1638         value *= inf;
1639         
1640         /* perform blending */
1641         switch (blendmode) {
1642                 case NLASTRIP_MODE_ADD:
1643                         /* simply add the scaled value on to the stack */
1644                         nec->value += value;
1645                         break;
1646                         
1647                 case NLASTRIP_MODE_SUBTRACT:
1648                         /* simply subtract the scaled value from the stack */
1649                         nec->value -= value;
1650                         break;
1651                         
1652                 case NLASTRIP_MODE_MULTIPLY:
1653                         /* multiply the scaled value with the stack */
1654                         nec->value *= value;
1655                         break;
1656                 
1657                 case NLASTRIP_MODE_REPLACE:
1658                 default: // TODO: do we really want to blend by default? it seems more uses might prefer add...
1659                         /* do linear interpolation 
1660                          *      - the influence of the accumulated data (elsewhere, that is called dstweight) 
1661                          *        is 1 - influence, since the strip's influence is srcweight
1662                          */
1663                         nec->value= nec->value * (1.0f - inf)   +   value;
1664                         break;
1665         }
1666 }
1667
1668 /* accumulate the results of a temporary buffer with the results of the full-buffer */
1669 static void nlaevalchan_buffers_accumulate (ListBase *channels, ListBase *tmp_buffer, NlaEvalStrip *nes)
1670 {
1671         NlaEvalChannel *nec, *necn, *necd;
1672         
1673         /* optimise - abort if no channels */
1674         if (tmp_buffer->first == NULL)
1675                 return;
1676         
1677         /* accumulate results in tmp_channels buffer to the accumulation buffer */
1678         for (nec= tmp_buffer->first; nec; nec= necn) {
1679                 /* get pointer to next channel in case we remove the current channel from the temp-buffer */
1680                 necn= nec->next;
1681                 
1682                 /* try to find an existing matching channel for this setting in the accumulation buffer */
1683                 necd= nlaevalchan_find_match(channels, &nec->ptr, nec->prop, nec->index);
1684                 
1685                 /* if there was a matching channel already in the buffer, accumulate to it,
1686                  * otherwise, add the current channel to the buffer for efficiency
1687                  */
1688                 if (necd)
1689                         nlaevalchan_accumulate(necd, nes, 0, nec->value);
1690                 else {
1691                         BLI_remlink(tmp_buffer, nec);
1692                         BLI_addtail(channels, nec);
1693                 }
1694         }
1695         
1696         /* free temp-channels that haven't been assimilated into the buffer */
1697         BLI_freelistN(tmp_buffer);
1698 }
1699
1700 /* ---------------------- */
1701 /* F-Modifier stack joining/separation utilities - should we generalise these for BLI_listbase.h interface? */
1702
1703 /* Temporarily join two lists of modifiers together, storing the result in a third list */
1704 static void nlaeval_fmodifiers_join_stacks (ListBase *result, ListBase *list1, ListBase *list2)
1705 {
1706         FModifier *fcm1, *fcm2;
1707         
1708         /* if list1 is invalid...  */
1709         if ELEM(NULL, list1, list1->first) {
1710                 if (list2 && list2->first) {
1711                         result->first= list2->first;
1712                         result->last= list2->last;
1713                 }
1714         }
1715         /* if list 2 is invalid... */
1716         else if ELEM(NULL, list2, list2->first) {
1717                 result->first= list1->first;
1718                 result->last= list1->last;
1719         }
1720         else {
1721                 /* list1 should be added first, and list2 second, with the endpoints of these being the endpoints for result 
1722                  *      - the original lists must be left unchanged though, as we need that fact for restoring
1723                  */
1724                 result->first= list1->first;
1725                 result->last= list2->last;
1726                 
1727                 fcm1= list1->last;
1728                 fcm2= list2->first;
1729                 
1730                 fcm1->next= fcm2;
1731                 fcm2->prev= fcm1;
1732         }
1733 }
1734
1735 /* Split two temporary lists of modifiers */
1736 static void nlaeval_fmodifiers_split_stacks (ListBase *list1, ListBase *list2)
1737 {
1738         FModifier *fcm1, *fcm2;
1739         
1740         /* if list1/2 is invalid... just skip */
1741         if ELEM(NULL, list1, list2)
1742                 return;
1743         if ELEM(NULL, list1->first, list2->first)
1744                 return;
1745                 
1746         /* get endpoints */
1747         fcm1= list1->last;
1748         fcm2= list2->first;
1749         
1750         /* clear their links */
1751         fcm1->next= NULL;
1752         fcm2->prev= NULL;
1753 }
1754
1755 /* ---------------------- */
1756
1757 /* evaluate action-clip strip */
1758 static void nlastrip_evaluate_actionclip (PointerRNA *ptr, ListBase *channels, ListBase *modifiers, NlaEvalStrip *nes)
1759 {
1760         ListBase tmp_modifiers = {NULL, NULL};
1761         NlaStrip *strip= nes->strip;
1762         FCurve *fcu;
1763         float evaltime;
1764         
1765         /* sanity checks for action */
1766         if (strip == NULL)
1767                 return;
1768                 
1769         if (strip->act == NULL) {
1770                 printf("NLA-Strip Eval Error: Strip '%s' has no Action\n", strip->name);
1771                 return;
1772         }
1773         
1774         action_idcode_patch_check(ptr->id.data, strip->act);
1775         
1776         /* join this strip's modifiers to the parent's modifiers (own modifiers first) */
1777         nlaeval_fmodifiers_join_stacks(&tmp_modifiers, &strip->modifiers, modifiers);
1778         
1779         /* evaluate strip's modifiers which modify time to evaluate the base curves at */
1780         evaltime= evaluate_time_fmodifiers(&tmp_modifiers, NULL, 0.0f, strip->strip_time);
1781         
1782         /* evaluate all the F-Curves in the action, saving the relevant pointers to data that will need to be used */
1783         for (fcu= strip->act->curves.first; fcu; fcu= fcu->next) {
1784                 NlaEvalChannel *nec;
1785                 float value = 0.0f;
1786                 short newChan = -1;
1787                 
1788                 /* check if this curve should be skipped */
1789                 if (fcu->flag & (FCURVE_MUTED|FCURVE_DISABLED)) 
1790                         continue;
1791                 if ((fcu->grp) && (fcu->grp->flag & AGRP_MUTED))
1792                         continue;
1793                         
1794                 /* evaluate the F-Curve's value for the time given in the strip 
1795                  * NOTE: we use the modified time here, since strip's F-Curve Modifiers are applied on top of this 
1796                  */
1797                 value= evaluate_fcurve(fcu, evaltime);
1798                 
1799                 /* apply strip's F-Curve Modifiers on this value 
1800                  * NOTE: we apply the strip's original evaluation time not the modified one (as per standard F-Curve eval)
1801                  */
1802                 evaluate_value_fmodifiers(&tmp_modifiers, fcu, &value, strip->strip_time);
1803                 
1804                 
1805                 /* get an NLA evaluation channel to work with, and accumulate the evaluated value with the value(s)
1806                  * stored in this channel if it has been used already
1807                  */
1808                 nec= nlaevalchan_verify(ptr, channels, nes, fcu, &newChan);
1809                 if (nec)
1810                         nlaevalchan_accumulate(nec, nes, newChan, value);
1811         }
1812         
1813         /* unlink this strip's modifiers from the parent's modifiers again */
1814         nlaeval_fmodifiers_split_stacks(&strip->modifiers, modifiers);
1815 }
1816
1817 /* evaluate transition strip */
1818 static void nlastrip_evaluate_transition (PointerRNA *ptr, ListBase *channels, ListBase *modifiers, NlaEvalStrip *nes)
1819 {
1820         ListBase tmp_channels = {NULL, NULL};
1821         ListBase tmp_modifiers = {NULL, NULL};
1822         NlaEvalStrip tmp_nes;
1823         NlaStrip *s1, *s2;
1824         
1825         /* join this strip's modifiers to the parent's modifiers (own modifiers first) */
1826         nlaeval_fmodifiers_join_stacks(&tmp_modifiers, &nes->strip->modifiers, modifiers);
1827         
1828         /* get the two strips to operate on 
1829          *      - we use the endpoints of the strips directly flanking our strip
1830          *        using these as the endpoints of the transition (destination and source)
1831          *      - these should have already been determined to be valid...
1832          *      - if this strip is being played in reverse, we need to swap these endpoints
1833          *        otherwise they will be interpolated wrong
1834          */
1835         if (nes->strip->flag & NLASTRIP_FLAG_REVERSE) {
1836                 s1= nes->strip->next;
1837                 s2= nes->strip->prev;
1838         }
1839         else {
1840                 s1= nes->strip->prev;
1841                 s2= nes->strip->next;
1842         }
1843         
1844         /* prepare template for 'evaluation strip' 
1845          *      - based on the transition strip's evaluation strip data
1846          *      - strip_mode is NES_TIME_TRANSITION_* based on which endpoint
1847          *      - strip_time is the 'normalised' (i.e. in-strip) time for evaluation,
1848          *        which doubles up as an additional weighting factor for the strip influences
1849          *        which allows us to appear to be 'interpolating' between the two extremes
1850          */
1851         tmp_nes= *nes;
1852         
1853         /* evaluate these strips into a temp-buffer (tmp_channels) */
1854         // FIXME: modifier evalation here needs some work...
1855                 /* first strip */
1856         tmp_nes.strip_mode= NES_TIME_TRANSITION_START;
1857         tmp_nes.strip= s1;
1858         nlastrip_evaluate(ptr, &tmp_channels, &tmp_modifiers, &tmp_nes);
1859         
1860                 /* second strip */
1861         tmp_nes.strip_mode= NES_TIME_TRANSITION_END;
1862         tmp_nes.strip= s2;
1863         nlastrip_evaluate(ptr, &tmp_channels, &tmp_modifiers, &tmp_nes);
1864         
1865         
1866         /* assumulate temp-buffer and full-buffer, using the 'real' strip */
1867         nlaevalchan_buffers_accumulate(channels, &tmp_channels, nes);
1868         
1869         /* unlink this strip's modifiers from the parent's modifiers again */
1870         nlaeval_fmodifiers_split_stacks(&nes->strip->modifiers, modifiers);
1871 }
1872
1873 /* evaluate meta-strip */
1874 static void nlastrip_evaluate_meta (PointerRNA *ptr, ListBase *channels, ListBase *modifiers, NlaEvalStrip *nes)
1875 {
1876         ListBase tmp_channels = {NULL, NULL};
1877         ListBase tmp_modifiers = {NULL, NULL};
1878         NlaStrip *strip= nes->strip;
1879         NlaEvalStrip *tmp_nes;
1880         float evaltime;
1881         
1882         /* meta-strip was calculated normally to have some time to be evaluated at
1883          * and here we 'look inside' the meta strip, treating it as a decorated window to
1884          * it's child strips, which get evaluated as if they were some tracks on a strip 
1885          * (but with some extra modifiers to apply).
1886          *
1887          * NOTE: keep this in sync with animsys_evaluate_nla()
1888          */
1889          
1890         /* join this strip's modifiers to the parent's modifiers (own modifiers first) */
1891         nlaeval_fmodifiers_join_stacks(&tmp_modifiers, &strip->modifiers, modifiers); 
1892         
1893         /* find the child-strip to evaluate */
1894         evaltime= (nes->strip_time * (strip->end - strip->start)) + strip->start;
1895         tmp_nes= nlastrips_ctime_get_strip(NULL, &strip->strips, -1, evaltime);
1896         if (tmp_nes == NULL)
1897                 return;
1898                 
1899         /* evaluate child-strip into tmp_channels buffer before accumulating 
1900          * in the accumulation buffer
1901          */
1902         nlastrip_evaluate(ptr, &tmp_channels, &tmp_modifiers, tmp_nes);
1903         
1904         /* assumulate temp-buffer and full-buffer, using the 'real' strip */
1905         nlaevalchan_buffers_accumulate(channels, &tmp_channels, nes);
1906         
1907         /* free temp eval-strip */
1908         MEM_freeN(tmp_nes);
1909         
1910         /* unlink this strip's modifiers from the parent's modifiers again */
1911         nlaeval_fmodifiers_split_stacks(&strip->modifiers, modifiers);
1912 }
1913
1914 /* evaluates the given evaluation strip */
1915 void nlastrip_evaluate (PointerRNA *ptr, ListBase *channels, ListBase *modifiers, NlaEvalStrip *nes)
1916 {
1917         NlaStrip *strip= nes->strip;
1918         
1919         /* to prevent potential infinite recursion problems (i.e. transition strip, beside meta strip containing a transition
1920          * several levels deep inside it), we tag the current strip as being evaluated, and clear this when we leave
1921          */
1922         // TODO: be careful with this flag, since some edit tools may be running and have set this while animplayback was running
1923         if (strip->flag & NLASTRIP_FLAG_EDIT_TOUCHED)
1924                 return;
1925         strip->flag |= NLASTRIP_FLAG_EDIT_TOUCHED;
1926         
1927         /* actions to take depend on the type of strip */
1928         switch (strip->type) {
1929                 case NLASTRIP_TYPE_CLIP: /* action-clip */
1930                         nlastrip_evaluate_actionclip(ptr, channels, modifiers, nes);
1931                         break;
1932                 case NLASTRIP_TYPE_TRANSITION: /* transition */
1933                         nlastrip_evaluate_transition(ptr, channels, modifiers, nes);
1934                         break;
1935                 case NLASTRIP_TYPE_META: /* meta */
1936                         nlastrip_evaluate_meta(ptr, channels, modifiers, nes);
1937                         break;
1938                         
1939                 default: /* do nothing */
1940                         break;
1941         }
1942         
1943         /* clear temp recursion safe-check */
1944         strip->flag &= ~NLASTRIP_FLAG_EDIT_TOUCHED;
1945 }
1946
1947 /* write the accumulated settings to */
1948 void nladata_flush_channels (ListBase *channels)
1949 {
1950         NlaEvalChannel *nec;
1951         
1952         /* sanity checks */
1953         if (channels == NULL)
1954                 return;
1955         
1956         /* for each channel with accumulated values, write its value on the property it affects */
1957         for (nec= channels->first; nec; nec= nec->next) {
1958                 PointerRNA *ptr= &nec->ptr;
1959                 PropertyRNA *prop= nec->prop;
1960                 int array_index= nec->index;
1961                 float value= nec->value;
1962                 
1963                 /* write values - see animsys_write_rna_setting() to sync the code */
1964                 switch (RNA_property_type(prop)) 
1965                 {
1966                         case PROP_BOOLEAN:
1967                                 if (RNA_property_array_length(ptr, prop))
1968                                         RNA_property_boolean_set_index(ptr, prop, array_index, ANIMSYS_FLOAT_AS_BOOL(value));
1969                                 else
1970                                         RNA_property_boolean_set(ptr, prop, ANIMSYS_FLOAT_AS_BOOL(value));
1971                                 break;
1972                         case PROP_INT:
1973                                 if (RNA_property_array_length(ptr, prop))
1974                                         RNA_property_int_set_index(ptr, prop, array_index, (int)value);
1975                                 else
1976                                         RNA_property_int_set(ptr, prop, (int)value);
1977                                 break;
1978                         case PROP_FLOAT:
1979                                 if (RNA_property_array_length(ptr, prop))
1980                                         RNA_property_float_set_index(ptr, prop, array_index, value);
1981                                 else
1982                                         RNA_property_float_set(ptr, prop, value);
1983                                 break;
1984                         case PROP_ENUM:
1985                                 RNA_property_enum_set(ptr, prop, (int)value);
1986                                 break;
1987                         default:
1988                                 // can't do anything with other types of property....
1989                                 break;
1990                 }
1991         }
1992 }
1993
1994 /* ---------------------- */
1995
1996 /* NLA Evaluation function - values are calculated and stored in temporary "NlaEvalChannels" 
1997  * ! This is exported so that keyframing code can use this for make use of it for anim layers support
1998  * > echannels: (list<NlaEvalChannels>) evaluation channels with calculated values
1999  */
2000 static void animsys_evaluate_nla (ListBase *echannels, PointerRNA *ptr, AnimData *adt, float ctime)
2001 {
2002         NlaTrack *nlt;
2003         short track_index=0;
2004         short has_strips = 0;
2005         
2006         ListBase estrips= {NULL, NULL};
2007         NlaEvalStrip *nes;
2008         
2009         /* 1. get the stack of strips to evaluate at current time (influence calculated here) */
2010         for (nlt=adt->nla_tracks.first; nlt; nlt=nlt->next, track_index++) { 
2011                 /* stop here if tweaking is on and this strip is the tweaking track (it will be the first one that's 'disabled')... */
2012                 if ((adt->flag & ADT_NLA_EDIT_ON) && (nlt->flag & NLATRACK_DISABLED))
2013                         break;
2014                         
2015                 /* skip if we're only considering a track tagged 'solo' */
2016                 if ((adt->flag & ADT_NLA_SOLO_TRACK) && (nlt->flag & NLATRACK_SOLO)==0)
2017                         continue;
2018                 /* skip if track is muted */
2019                 if (nlt->flag & NLATRACK_MUTED) 
2020                         continue;
2021                         
2022                 /* if this track has strips (but maybe they won't be suitable), set has_strips 
2023                  *      - used for mainly for still allowing normal action evaluation...
2024                  */
2025                 if (nlt->strips.first)
2026                         has_strips= 1;
2027                         
2028                 /* otherwise, get strip to evaluate for this channel */
2029                 nes= nlastrips_ctime_get_strip(&estrips, &nlt->strips, track_index, ctime);
2030                 if (nes) nes->track= nlt;
2031         }
2032         
2033         /* add 'active' Action (may be tweaking track) as last strip to evaluate in NLA stack
2034          *      - only do this if we're not exclusively evaluating the 'solo' NLA-track
2035          */
2036         if ((adt->action) && !(adt->flag & ADT_NLA_SOLO_TRACK)) {
2037                 /* if there are strips, evaluate action as per NLA rules */
2038                 if ((has_strips) || (adt->actstrip)) {
2039                         /* make dummy NLA strip, and add that to the stack */
2040                         NlaStrip dummy_strip= {NULL};
2041                         ListBase dummy_trackslist;
2042                         
2043                         dummy_trackslist.first= dummy_trackslist.last= &dummy_strip;
2044                         
2045                         if ((nlt) && !(adt->flag & ADT_NLA_EDIT_NOMAP)) {
2046                                 /* edit active action in-place according to its active strip, so copy the data  */
2047                                 memcpy(&dummy_strip, adt->actstrip, sizeof(NlaStrip));
2048                                 dummy_strip.next = dummy_strip.prev = NULL;
2049                         }
2050                         else {
2051                                 /* set settings of dummy NLA strip from AnimData settings */
2052                                 dummy_strip.act= adt->action;
2053                                 dummy_strip.remap= adt->remap;
2054                                 
2055                                 /* action range is calculated taking F-Modifiers into account (which making new strips doesn't do due to the troublesome nature of that) */
2056                                 calc_action_range(dummy_strip.act, &dummy_strip.actstart, &dummy_strip.actend, 1);
2057                                 dummy_strip.start = dummy_strip.actstart;
2058                                 dummy_strip.end = (IS_EQF(dummy_strip.actstart, dummy_strip.actend)) ?  (dummy_strip.actstart + 1.0f): (dummy_strip.actend);
2059                                 
2060                                 dummy_strip.blendmode= adt->act_blendmode;
2061                                 dummy_strip.extendmode= adt->act_extendmode;
2062                                 dummy_strip.influence= adt->act_influence;
2063                         }
2064                         
2065                         /* add this to our list of evaluation strips */
2066                         nlastrips_ctime_get_strip(&estrips, &dummy_trackslist, -1, ctime);
2067                 }
2068                 else {
2069                         /* special case - evaluate as if there isn't any NLA data */
2070                         // TODO: this is really just a stop-gap measure...
2071                         animsys_evaluate_action(ptr, adt->action, adt->remap, ctime);
2072                         return;
2073                 }
2074         }
2075         
2076         /* only continue if there are strips to evaluate */
2077         if (estrips.first == NULL)
2078                 return;
2079         
2080         
2081         /* 2. for each strip, evaluate then accumulate on top of existing channels, but don't set values yet */
2082         for (nes= estrips.first; nes; nes= nes->next) 
2083                 nlastrip_evaluate(ptr, echannels, NULL, nes);
2084                 
2085         /* 3. free temporary evaluation data that's not used elsewhere */
2086         BLI_freelistN(&estrips);
2087 }
2088
2089 /* NLA Evaluation function (mostly for use through do_animdata) 
2090  *      - All channels that will be affected are not cleared anymore. Instead, we just evaluate into 
2091  *              some temp channels, where values can be accumulated in one go.
2092  */
2093 static void animsys_calculate_nla (PointerRNA *ptr, AnimData *adt, float ctime)
2094 {
2095         ListBase echannels= {NULL, NULL};
2096         
2097         // TODO: need to zero out all channels used, otherwise we have problems with threadsafety
2098         // and also when the user jumps between different times instead of moving sequentially...
2099         
2100         /* evaluate the NLA stack, obtaining a set of values to flush */
2101         animsys_evaluate_nla(&echannels, ptr, adt, ctime);
2102         
2103         /* flush effects of accumulating channels in NLA to the actual data they affect */
2104         nladata_flush_channels(&echannels);
2105         
2106         /* free temp data */
2107         BLI_freelistN(&echannels);
2108 }
2109
2110 /* ***************************************** */ 
2111 /* Overrides System - Public API */
2112
2113 /* Clear all overides */
2114
2115 /* Add or get existing Override for given setting */
2116 #if 0
2117 AnimOverride *BKE_animsys_validate_override (PointerRNA *UNUSED(ptr), char *UNUSED(path), int UNUSED(array_index))
2118 {
2119         // FIXME: need to define how to get overrides
2120         return NULL;
2121
2122 #endif
2123
2124 /* -------------------- */
2125
2126 /* Evaluate Overrides */
2127 static void animsys_evaluate_overrides (PointerRNA *ptr, AnimData *adt)
2128 {
2129         AnimOverride *aor;
2130         
2131         /* for each override, simply execute... */
2132         for (aor= adt->overrides.first; aor; aor= aor->next)
2133                 animsys_write_rna_setting(ptr, aor->rna_path, aor->array_index, aor->value);
2134 }
2135
2136 /* ***************************************** */
2137 /* Evaluation System - Public API */
2138
2139 /* Overview of how this system works:
2140  *      1) Depsgraph sorts data as necessary, so that data is in an order that means 
2141  *              that all dependences are resolved before dependants.
2142  *      2) All normal animation is evaluated, so that drivers have some basis values to
2143  *              work with
2144  *              a.      NLA stacks are done first, as the Active Actions act as 'tweaking' tracks
2145  *                      which modify the effects of the NLA-stacks
2146  *              b.      Active Action is evaluated as per normal, on top of the results of the NLA tracks
2147  *
2148  * --------------< often in a separate phase... >------------------ 
2149  *
2150  *      3) Drivers/expressions are evaluated on top of this, in an order where dependences are
2151  *              resolved nicely. 
2152  *         Note: it may be necessary to have some tools to handle the cases where some higher-level
2153  *              drivers are added and cause some problematic dependencies that didn't exist in the local levels...
2154  *
2155  * --------------< always executed >------------------ 
2156  *
2157  * Maintainance of editability of settings (XXX):
2158  *      In order to ensure that settings that are animated can still be manipulated in the UI without requiring
2159  *      that keyframes are added to prevent these values from being overwritten, we use 'overrides'. 
2160  *
2161  * Unresolved things:
2162  *      - Handling of multi-user settings (i.e. time-offset, group-instancing) -> big cache grids or nodal system? but stored where?
2163  *      - Multiple-block dependencies (i.e. drivers for settings are in both local and higher levels) -> split into separate lists? 
2164  *
2165  * Current Status:
2166  *      - Currently (as of September 2009), overrides we haven't needed to (fully) implement overrides. 
2167  *        However, the code fo this is relatively harmless, so is left in the code for now.
2168  */
2169
2170 /* Evaluation loop for evaluation animation data 
2171  *
2172  * This assumes that the animation-data provided belongs to the ID block in question,
2173  * and that the flags for which parts of the anim-data settings need to be recalculated 
2174  * have been set already by the depsgraph. Now, we use the recalc 
2175  */
2176 void BKE_animsys_evaluate_animdata (Scene *scene, ID *id, AnimData *adt, float ctime, short recalc)
2177 {
2178         PointerRNA id_ptr;
2179         
2180         /* sanity checks */
2181         if ELEM(NULL, id, adt)
2182                 return;
2183         
2184         /* get pointer to ID-block for RNA to use */
2185         RNA_id_pointer_create(id, &id_ptr);
2186         
2187         /* recalculate keyframe data:
2188          *      - NLA before Active Action, as Active Action behaves as 'tweaking track'
2189          *        that overrides 'rough' work in NLA
2190          */
2191         // TODO: need to double check that this all works correctly
2192         if ((recalc & ADT_RECALC_ANIM) || (adt->recalc & ADT_RECALC_ANIM))
2193         {
2194                 /* evaluate NLA data */
2195                 if ((adt->nla_tracks.first) && !(adt->flag & ADT_NLA_EVAL_OFF))
2196                 {
2197                         /* evaluate NLA-stack 
2198                          *      - active action is evaluated as part of the NLA stack as the last item
2199                          */
2200                         animsys_calculate_nla(&id_ptr, adt, ctime);
2201                 }
2202                 /* evaluate Active Action only */
2203                 else if (adt->action)
2204                         animsys_evaluate_action(&id_ptr, adt->action, adt->remap, ctime);
2205                 
2206                 /* reset tag */
2207                 adt->recalc &= ~ADT_RECALC_ANIM;
2208         }
2209         
2210         /* recalculate drivers 
2211          *      - Drivers need to be evaluated afterwards, as they can either override 
2212          *        or be layered on top of existing animation data.
2213          *      - Drivers should be in the appropriate order to be evaluated without problems...
2214          */
2215         if ((recalc & ADT_RECALC_DRIVERS) /*&& (adt->recalc & ADT_RECALC_DRIVERS)*/) // XXX for now, don't check yet, as depsgraph hasn't been updated
2216         {
2217                 animsys_evaluate_drivers(&id_ptr, adt, ctime);
2218         }
2219         
2220         /* always execute 'overrides' 
2221          *      - Overrides allow editing, by overwriting the value(s) set from animation-data, with the
2222          *        value last set by the user (and not keyframed yet). 
2223          *      - Overrides are cleared upon frame change and/or keyframing
2224          *      - It is best that we execute this everytime, so that no errors are likely to occur.
2225          */
2226         animsys_evaluate_overrides(&id_ptr, adt);
2227         
2228         /* execute and clear all cached property update functions */
2229         if (scene)
2230         {
2231                 Main *bmain = G.main; // xxx - to get passed in!
2232                 RNA_property_update_cache_flush(bmain, scene);
2233                 RNA_property_update_cache_free();
2234         }
2235         
2236         /* clear recalc flag now */
2237         adt->recalc= 0;
2238 }
2239
2240 /* Evaluation of all ID-blocks with Animation Data blocks - Animation Data Only
2241  *
2242  * This will evaluate only the animation info available in the animation data-blocks
2243  * encountered. In order to enforce the system by which some settings controlled by a
2244  * 'local' (i.e. belonging in the nearest ID-block that setting is related to, not a
2245  * standard 'root') block are overridden by a larger 'user'
2246  */
2247 void BKE_animsys_evaluate_all_animation (Main *main, Scene *scene, float ctime)
2248 {
2249         ID *id;
2250
2251         if (G.f & G_DEBUG)
2252                 printf("Evaluate all animation - %f \n", ctime);
2253         
2254         /* macros for less typing 
2255          *      - only evaluate animation data for id if it has users (and not just fake ones)
2256          *      - whether animdata exists is checked for by the evaluation function, though taking 
2257          *        this outside of the function may make things slightly faster?
2258          */
2259 #define EVAL_ANIM_IDS(first, aflag) \
2260         for (id= first; id; id= id->next) { \
2261                 if (ID_REAL_USERS(id) > 0) { \
2262                         AnimData *adt= BKE_animdata_from_id(id); \
2263                         BKE_animsys_evaluate_animdata(scene, id, adt, ctime, aflag); \
2264                 } \
2265         }
2266         /* another macro for the "embedded" nodetree cases 
2267          *      - this is like EVAL_ANIM_IDS, but this handles the case "embedded nodetrees" 
2268          *        (i.e. scene/material/texture->nodetree) which we need a special exception
2269          *        for, otherwise they'd get skipped
2270          *      - ntp = "node tree parent" = datablock where node tree stuff resides
2271          */
2272 #define EVAL_ANIM_NODETREE_IDS(first, NtId_Type, aflag) \
2273         for (id= first; id; id= id->next) { \
2274                 if (ID_REAL_USERS(id) > 0) { \
2275                         AnimData *adt= BKE_animdata_from_id(id); \
2276                         NtId_Type *ntp= (NtId_Type *)id; \
2277                         if (ntp->nodetree) { \
2278                                 AnimData *adt2= BKE_animdata_from_id((ID *)ntp->nodetree); \
2279                                 BKE_animsys_evaluate_animdata(scene, (ID *)ntp->nodetree, adt2, ctime, ADT_RECALC_ANIM); \
2280                         } \
2281                         BKE_animsys_evaluate_animdata(scene, id, adt, ctime, aflag); \
2282                 } \
2283         }
2284         
2285         /* optimisation: 
2286          * when there are no actions, don't go over database and loop over heaps of datablocks, 
2287          * which should ultimately be empty, since it is not possible for now to have any animation 
2288          * without some actions, and drivers wouldn't get affected by any state changes
2289          *
2290          * however, if there are some curves, we will need to make sure that their 'ctime' property gets
2291          * set correctly, so this optimisation must be skipped in that case...
2292          */
2293         if ((main->action.first == NULL) && (main->curve.first == NULL)) {
2294                 if (G.f & G_DEBUG)
2295                         printf("\tNo Actions, so no animation needs to be evaluated...\n");
2296                         
2297                 return;
2298         }
2299         
2300         /* nodes */
2301         EVAL_ANIM_IDS(main->nodetree.first, ADT_RECALC_ANIM);
2302         
2303         /* textures */
2304         EVAL_ANIM_NODETREE_IDS(main->tex.first, Tex, ADT_RECALC_ANIM);
2305         
2306         /* lamps */
2307         EVAL_ANIM_NODETREE_IDS(main->lamp.first, Lamp, ADT_RECALC_ANIM);
2308         
2309         /* materials */
2310         EVAL_ANIM_NODETREE_IDS(main->mat.first, Material, ADT_RECALC_ANIM);
2311         
2312         /* cameras */
2313         EVAL_ANIM_IDS(main->camera.first, ADT_RECALC_ANIM);
2314         
2315         /* shapekeys */
2316         EVAL_ANIM_IDS(main->key.first, ADT_RECALC_ANIM);
2317         
2318         /* metaballs */
2319         EVAL_ANIM_IDS(main->mball.first, ADT_RECALC_ANIM);
2320         
2321         /* curves */
2322         EVAL_ANIM_IDS(main->curve.first, ADT_RECALC_ANIM);
2323         
2324         /* armatures */
2325         EVAL_ANIM_IDS(main->armature.first, ADT_RECALC_ANIM);
2326         
2327         /* lattices */
2328         EVAL_ANIM_IDS(main->latt.first, ADT_RECALC_ANIM);
2329         
2330         /* meshes */
2331         EVAL_ANIM_IDS(main->mesh.first, ADT_RECALC_ANIM);
2332         
2333         /* particles */
2334         EVAL_ANIM_IDS(main->particle.first, ADT_RECALC_ANIM);
2335         
2336         /* speakers */
2337         EVAL_ANIM_IDS(main->speaker.first, ADT_RECALC_ANIM);
2338
2339         /* movie clips */
2340         EVAL_ANIM_IDS(main->movieclip.first, ADT_RECALC_ANIM);
2341
2342         /* objects */
2343                 /* ADT_RECALC_ANIM doesn't need to be supplied here, since object AnimData gets 
2344                  * this tagged by Depsgraph on framechange. This optimisation means that objects
2345                  * linked from other (not-visible) scenes will not need their data calculated.
2346                  */
2347         EVAL_ANIM_IDS(main->object.first, 0); 
2348         
2349         /* worlds */
2350         EVAL_ANIM_NODETREE_IDS(main->world.first, World, ADT_RECALC_ANIM);
2351         
2352         /* scenes */
2353         EVAL_ANIM_NODETREE_IDS(main->scene.first, Scene, ADT_RECALC_ANIM);
2354 }
2355
2356 /* ***************************************** */