Fix #133731: Performance issue with many stashed actions

When duplicating an action, it is stashed in the NLA on a muted track.
Over time this can slow down blender, because certain code will look at every
FCurve in every action in the NLA.
To fix the performance issue, we can take advantage of the fact that
stashed actions are put onto a muted NLA track.

With this patch any strip on a muted NLA track is ignored in the
Depsgraph evaluation.

Measurements of `DEG_graph_relations_update`

| - | Before | After |
| - | - | - |
| 50 actions | ~140 ms | ~10.0 ms |
| 100 actions | ~250 ms | ~10.7 ms |

Pull Request: https://projects.blender.org/blender/blender/pulls/133864
This commit is contained in:
Christoph Lendenfeld 2025-01-31 16:38:30 +01:00 committed by Christoph Lendenfeld
parent 651ae0e47c
commit de31cecfaf
3 changed files with 11 additions and 1 deletions

View File

@ -1254,7 +1254,8 @@ static void nlastrips_apply_all_curves_cb(ID *id,
}
}
/* Helper for BKE_fcurves_main_cb() - Dispatch wrapped operator to all F-Curves */
/* Helper for BKE_fcurves_main_cb() - Dispatch wrapped operator to all F-Curves. Muted NLA Tracks
* are ignored. */
static void adt_apply_all_fcurves_cb(ID *id,
AnimData *adt,
const FunctionRef<void(ID *, FCurve *)> func)
@ -1272,6 +1273,9 @@ static void adt_apply_all_fcurves_cb(ID *id,
/* NLA Data - Animation Data for Strips */
LISTBASE_FOREACH (NlaTrack *, nlt, &adt->nla_tracks) {
if (nlt->flag & NLATRACK_MUTED) {
continue;
}
nlastrips_apply_all_curves_cb(id, &nlt->strips, func);
}
}

View File

@ -1257,6 +1257,9 @@ void DepsgraphNodeBuilder::build_animdata(ID *id)
}
/* NLA strips contain actions. */
LISTBASE_FOREACH (NlaTrack *, nlt, &adt->nla_tracks) {
if (nlt->flag & NLATRACK_MUTED) {
continue;
}
build_animdata_nlastrip_targets(&nlt->strips);
}
/* Drivers. */

View File

@ -1617,6 +1617,9 @@ void DepsgraphRelationBuilder::build_animdata_curves(ID *id)
build_animdata_action_targets(id, adt->slot_handle, adt_key, operation_from, adt->action);
}
LISTBASE_FOREACH (NlaTrack *, nlt, &adt->nla_tracks) {
if (nlt->flag & NLATRACK_MUTED) {
continue;
}
build_animdata_nlastrip_targets(id, adt_key, operation_from, &nlt->strips);
}
}