Nla Refactor: Split animsys_evaluate_nla()
No intended functional changes. Refactors animsys_evaluate_nla() into 2 versions: animsys_evaluate_nla_for_keyframing(), animsys_evaluate_nla_for_flush() to make it clear what data is being calculated and why. Dummy strip creation has been refactored to two separate functions, animsys_create_tweak_strip() and animsys_create_action_track_strip(). Both are evaluated differently from other strips and eachother. There's no need to interweave them. A future patch D8296, generally requires both strips. ___ XXX anim_sys.c) nlatrack_find_tweaked() is a temporary work around. If anyone has any insight into this problem, help is appreciated. Reviewed by: sybren Differential Revision: http://developer.blender.org/D9696
This commit is contained in:
parent
b75552ebbb
commit
09709a7e64
Notes:
blender-bot
2023-02-14 02:43:21 +01:00
Referenced by commit abfb9dbf59
, Fix: Disabled NLA Interferes with Action Eval
|
@ -212,8 +212,7 @@ struct NlaKeyframingContext *BKE_animsys_get_nla_keyframing_context(
|
|||
struct ListBase *cache,
|
||||
struct PointerRNA *ptr,
|
||||
struct AnimData *adt,
|
||||
const struct AnimationEvalContext *anim_eval_context,
|
||||
const bool flush_to_original);
|
||||
const struct AnimationEvalContext *anim_eval_context);
|
||||
bool BKE_animsys_nla_remap_keyframe_values(struct NlaKeyframingContext *context,
|
||||
struct PointerRNA *prop_ptr,
|
||||
struct PropertyRNA *prop,
|
||||
|
|
|
@ -979,6 +979,19 @@ NlaEvalStrip *nlastrips_ctime_get_strip(ListBase *list,
|
|||
return nes;
|
||||
}
|
||||
|
||||
static NlaEvalStrip *nlastrips_ctime_get_strip_single(
|
||||
ListBase *dst_list,
|
||||
NlaStrip *single_strip,
|
||||
const AnimationEvalContext *anim_eval_context,
|
||||
const bool flush_to_original)
|
||||
{
|
||||
ListBase single_tracks_list;
|
||||
single_tracks_list.first = single_tracks_list.last = single_strip;
|
||||
|
||||
return nlastrips_ctime_get_strip(
|
||||
dst_list, &single_tracks_list, -1, anim_eval_context, flush_to_original);
|
||||
}
|
||||
|
||||
/* ---------------------- */
|
||||
|
||||
/* Initialize a valid mask, allocating memory if necessary. */
|
||||
|
@ -2212,177 +2225,226 @@ static void animsys_evaluate_nla_domain(PointerRNA *ptr, NlaEvalData *channels,
|
|||
|
||||
/* ---------------------- */
|
||||
|
||||
/** Tweaked strip is evaluated differently from other strips. Adjacent strips are ignored
|
||||
* and includes a workaround for when user is not editing in place. */
|
||||
static void animsys_create_tweak_strip(const AnimData *adt,
|
||||
const bool keyframing_to_strip,
|
||||
NlaStrip *r_tweak_strip)
|
||||
|
||||
{
|
||||
/* Copy active strip so we can modify how it evaluates without affecting user data. */
|
||||
memcpy(r_tweak_strip, adt->actstrip, sizeof(NlaStrip));
|
||||
r_tweak_strip->next = r_tweak_strip->prev = NULL;
|
||||
|
||||
/* If tweaked strip is syncing action length, then evaluate using action length. */
|
||||
if (r_tweak_strip->flag & NLASTRIP_FLAG_SYNC_LENGTH) {
|
||||
BKE_nlastrip_recalculate_bounds_sync_action(r_tweak_strip);
|
||||
}
|
||||
|
||||
/* Strips with a user-defined time curve don't get properly remapped for editing
|
||||
* at the moment, so mapping them just for display may be confusing. */
|
||||
const bool is_inplace_tweak = !(adt->flag & ADT_NLA_EDIT_NOMAP) &&
|
||||
!(adt->actstrip->flag & NLASTRIP_FLAG_USR_TIME);
|
||||
|
||||
if (!is_inplace_tweak) {
|
||||
/* Use Hold due to no proper remapping yet (the note above). */
|
||||
r_tweak_strip->extendmode = NLASTRIP_EXTEND_HOLD;
|
||||
|
||||
/* Disable range. */
|
||||
r_tweak_strip->flag |= NLASTRIP_FLAG_NO_TIME_MAP;
|
||||
}
|
||||
|
||||
/** Controls whether able to keyframe outside range of tweaked strip. */
|
||||
if (keyframing_to_strip) {
|
||||
r_tweak_strip->extendmode = (is_inplace_tweak &&
|
||||
!(r_tweak_strip->flag & NLASTRIP_FLAG_SYNC_LENGTH)) ?
|
||||
NLASTRIP_EXTEND_NOTHING :
|
||||
NLASTRIP_EXTEND_HOLD;
|
||||
}
|
||||
}
|
||||
|
||||
/** Action track and strip are associated with the non-pushed action. */
|
||||
static void animsys_create_action_track_strip(const AnimData *adt,
|
||||
const bool keyframing_to_strip,
|
||||
NlaStrip *r_action_strip)
|
||||
{
|
||||
memset(r_action_strip, 0, sizeof(NlaStrip));
|
||||
|
||||
bAction *action = adt->action;
|
||||
|
||||
if ((adt->flag & ADT_NLA_EDIT_ON)) {
|
||||
action = adt->tmpact;
|
||||
}
|
||||
|
||||
/* Set settings of dummy NLA strip from AnimData settings. */
|
||||
r_action_strip->act = action;
|
||||
|
||||
/* Action range is calculated taking F-Modifiers into account
|
||||
* (which making new strips doesn't do due to the troublesome nature of that). */
|
||||
calc_action_range(r_action_strip->act, &r_action_strip->actstart, &r_action_strip->actend, 1);
|
||||
r_action_strip->start = r_action_strip->actstart;
|
||||
r_action_strip->end = (IS_EQF(r_action_strip->actstart, r_action_strip->actend)) ?
|
||||
(r_action_strip->actstart + 1.0f) :
|
||||
(r_action_strip->actend);
|
||||
|
||||
r_action_strip->blendmode = adt->act_blendmode;
|
||||
r_action_strip->extendmode = adt->act_extendmode;
|
||||
r_action_strip->influence = adt->act_influence;
|
||||
|
||||
/* NOTE: must set this, or else the default setting overrides,
|
||||
* and this setting doesn't work. */
|
||||
r_action_strip->flag |= NLASTRIP_FLAG_USR_INFLUENCE;
|
||||
|
||||
/* Unless extendmode is Nothing (might be useful for flattening NLA evaluation), disable range.
|
||||
* Extendmode Nothing and Hold will behave as normal. Hold Forward will behave just like Hold.
|
||||
*/
|
||||
if (r_action_strip->extendmode != NLASTRIP_EXTEND_NOTHING) {
|
||||
r_action_strip->flag |= NLASTRIP_FLAG_NO_TIME_MAP;
|
||||
}
|
||||
|
||||
const bool tweaking = (adt->flag & ADT_NLA_EDIT_ON) != 0;
|
||||
const bool soloing = (adt->flag & ADT_NLA_SOLO_TRACK) != 0;
|
||||
const bool actionstrip_evaluated = r_action_strip->act && !soloing && !tweaking;
|
||||
if (!actionstrip_evaluated) {
|
||||
r_action_strip->flag |= NLASTRIP_FLAG_MUTED;
|
||||
}
|
||||
|
||||
/** If we're keyframing, then we must allow keyframing outside fcurve bounds. */
|
||||
if (keyframing_to_strip) {
|
||||
r_action_strip->extendmode = NLASTRIP_EXTEND_HOLD;
|
||||
}
|
||||
}
|
||||
|
||||
static bool is_nlatrack_evaluatable(const AnimData *adt, const NlaTrack *nlt)
|
||||
{
|
||||
/* Skip disabled tracks unless it contains the tweaked strip. */
|
||||
const bool contains_tweak_strip = (adt->flag & ADT_NLA_EDIT_ON) &&
|
||||
(nlt->index == adt->act_track->index);
|
||||
if ((nlt->flag & NLATRACK_DISABLED) && !contains_tweak_strip) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Solo and muting are mutually exclusive. */
|
||||
if (adt->flag & ADT_NLA_SOLO_TRACK) {
|
||||
/* Skip if there is a solo track, but this isn't it. */
|
||||
if ((nlt->flag & NLATRACK_SOLO) == 0) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* Skip track if muted. */
|
||||
if (nlt->flag & NLATRACK_MUTED) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Check for special case of non-pushed action being evaluated with no NLA influence (off and no
|
||||
* strips evaluated) nor NLA interference (ensure NLA not soloing). */
|
||||
static bool is_action_track_evaluated_without_nla(const AnimData *adt,
|
||||
const bool any_strip_evaluated)
|
||||
{
|
||||
if (adt->action == NULL) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (any_strip_evaluated) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/** NLA settings interference. */
|
||||
if ((adt->flag & (ADT_NLA_SOLO_TRACK | ADT_NLA_EDIT_ON)) == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
/** Allow action track to evaluate as if there isn't any NLA data. */
|
||||
return true;
|
||||
}
|
||||
|
||||
/** XXX Wayde Moss: BKE_nlatrack_find_tweaked() exists within nla.c, but it doesn't appear to
|
||||
* work as expected. From animsys_evaluate_nla_for_flush(), it returns NULL in tweak mode. I'm not
|
||||
* sure why. Preferably, it would be as simple as checking for (adt->act_Track == nlt) but that
|
||||
* doesn't work either, neither does comparing indices.
|
||||
*
|
||||
* This function is a temporary work around. The first disabled track is always the tweaked track.
|
||||
*/
|
||||
static NlaTrack *nlatrack_find_tweaked(const AnimData *adt)
|
||||
{
|
||||
NlaTrack *nlt;
|
||||
|
||||
if (adt == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Since the track itself gets disabled, we want the first disabled. */
|
||||
for (nlt = adt->nla_tracks.first; nlt; nlt = nlt->next) {
|
||||
if (nlt->flag & NLATRACK_DISABLED) {
|
||||
return nlt;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* NLA Evaluation function - values are calculated and stored in temporary "NlaEvalChannels"
|
||||
*
|
||||
* \param[out] echannels: Evaluation channels with calculated values
|
||||
* \param[out] r_context: If not NULL,
|
||||
* data about the currently edited strip is stored here and excluded from value calculation.
|
||||
* \return false if NLA evaluation isn't actually applicable.
|
||||
*/
|
||||
static bool animsys_evaluate_nla(NlaEvalData *echannels,
|
||||
PointerRNA *ptr,
|
||||
AnimData *adt,
|
||||
const AnimationEvalContext *anim_eval_context,
|
||||
const bool flush_to_original,
|
||||
NlaKeyframingContext *r_context)
|
||||
static bool animsys_evaluate_nla_for_flush(NlaEvalData *echannels,
|
||||
PointerRNA *ptr,
|
||||
const AnimData *adt,
|
||||
const AnimationEvalContext *anim_eval_context,
|
||||
const bool flush_to_original)
|
||||
{
|
||||
NlaTrack *nlt;
|
||||
short track_index = 0;
|
||||
bool has_strips = false;
|
||||
|
||||
ListBase estrips = {NULL, NULL};
|
||||
NlaEvalStrip *nes;
|
||||
NlaStrip dummy_strip_buf;
|
||||
|
||||
/* dummy strip for active action */
|
||||
NlaStrip *dummy_strip = r_context ? &r_context->strip : &dummy_strip_buf;
|
||||
NlaStrip tweak_strip;
|
||||
|
||||
memset(dummy_strip, 0, sizeof(*dummy_strip));
|
||||
NlaTrack *tweaked_track = nlatrack_find_tweaked(adt);
|
||||
|
||||
/* 1. get the stack of strips to evaluate at current time (influence calculated here) */
|
||||
/* Get the stack of strips to evaluate at current time (influence calculated here). */
|
||||
for (nlt = adt->nla_tracks.first; nlt; nlt = nlt->next, track_index++) {
|
||||
/* stop here if tweaking is on and this strip is the tweaking track
|
||||
* (it will be the first one that's 'disabled')... */
|
||||
if ((adt->flag & ADT_NLA_EDIT_ON) && (nlt->flag & NLATRACK_DISABLED)) {
|
||||
break;
|
||||
|
||||
if (!is_nlatrack_evaluatable(adt, nlt)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* solo and muting are mutually exclusive... */
|
||||
if (adt->flag & ADT_NLA_SOLO_TRACK) {
|
||||
/* skip if there is a solo track, but this isn't it */
|
||||
if ((nlt->flag & NLATRACK_SOLO) == 0) {
|
||||
continue;
|
||||
}
|
||||
/* else - mute doesn't matter */
|
||||
}
|
||||
else {
|
||||
/* no solo tracks - skip track if muted */
|
||||
if (nlt->flag & NLATRACK_MUTED) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
/* if this track has strips (but maybe they won't be suitable), set has_strips
|
||||
* - used for mainly for still allowing normal action evaluation...
|
||||
*/
|
||||
if (nlt->strips.first) {
|
||||
has_strips = true;
|
||||
}
|
||||
|
||||
/* otherwise, get strip to evaluate for this channel */
|
||||
nes = nlastrips_ctime_get_strip(
|
||||
&estrips, &nlt->strips, track_index, anim_eval_context, flush_to_original);
|
||||
/** Append strip to evaluate for this track. */
|
||||
if (nlt == tweaked_track) {
|
||||
/** Tweaked strip is evaluated differently. */
|
||||
animsys_create_tweak_strip(adt, false, &tweak_strip);
|
||||
nes = nlastrips_ctime_get_strip_single(
|
||||
&estrips, &tweak_strip, anim_eval_context, flush_to_original);
|
||||
}
|
||||
else {
|
||||
nes = nlastrips_ctime_get_strip(
|
||||
&estrips, &nlt->strips, track_index, anim_eval_context, flush_to_original);
|
||||
}
|
||||
if (nes) {
|
||||
nes->track = nlt;
|
||||
}
|
||||
}
|
||||
|
||||
/* add 'active' Action (may be tweaking track) as last strip to evaluate in NLA stack
|
||||
* - only do this if we're not exclusively evaluating the 'solo' NLA-track
|
||||
* - however, if the 'solo' track houses the current 'tweaking' strip,
|
||||
* then we should allow this to play, otherwise nothing happens
|
||||
*/
|
||||
if ((adt->action) && ((adt->flag & ADT_NLA_SOLO_TRACK) == 0 || (adt->flag & ADT_NLA_EDIT_ON))) {
|
||||
/* if there are strips, evaluate action as per NLA rules */
|
||||
if ((has_strips) || (adt->actstrip)) {
|
||||
/* make dummy NLA strip, and add that to the stack */
|
||||
ListBase dummy_trackslist;
|
||||
|
||||
dummy_trackslist.first = dummy_trackslist.last = dummy_strip;
|
||||
|
||||
/* Strips with a user-defined time curve don't get properly remapped for editing
|
||||
* at the moment, so mapping them just for display may be confusing. */
|
||||
bool is_inplace_tweak = (nlt) && !(adt->flag & ADT_NLA_EDIT_NOMAP) &&
|
||||
!(adt->actstrip->flag & NLASTRIP_FLAG_USR_TIME);
|
||||
|
||||
if (is_inplace_tweak) {
|
||||
/* edit active action in-place according to its active strip, so copy the data */
|
||||
memcpy(dummy_strip, adt->actstrip, sizeof(NlaStrip));
|
||||
/* Prevents nla eval from considering active strip's adj strips.
|
||||
* For user, this means entering tweak mode on a strip ignores evaluating adjacent strips
|
||||
* in the same track. */
|
||||
dummy_strip->next = dummy_strip->prev = NULL;
|
||||
|
||||
/* If tweaked strip is syncing action length, then evaluate using action length. */
|
||||
if (dummy_strip->flag & NLASTRIP_FLAG_SYNC_LENGTH) {
|
||||
BKE_nlastrip_recalculate_bounds_sync_action(dummy_strip);
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* set settings of dummy NLA strip from AnimData settings */
|
||||
dummy_strip->act = adt->action;
|
||||
|
||||
/* action range is calculated taking F-Modifiers into account
|
||||
* (which making new strips doesn't do due to the troublesome nature of that) */
|
||||
calc_action_range(dummy_strip->act, &dummy_strip->actstart, &dummy_strip->actend, 1);
|
||||
dummy_strip->start = dummy_strip->actstart;
|
||||
dummy_strip->end = (IS_EQF(dummy_strip->actstart, dummy_strip->actend)) ?
|
||||
(dummy_strip->actstart + 1.0f) :
|
||||
(dummy_strip->actend);
|
||||
|
||||
/* Always use the blend mode of the strip in tweak mode, even if not in-place. */
|
||||
if (nlt && adt->actstrip) {
|
||||
dummy_strip->blendmode = adt->actstrip->blendmode;
|
||||
dummy_strip->extendmode = NLASTRIP_EXTEND_HOLD;
|
||||
}
|
||||
else {
|
||||
dummy_strip->blendmode = adt->act_blendmode;
|
||||
dummy_strip->extendmode = adt->act_extendmode;
|
||||
}
|
||||
|
||||
/* Unless extend-mode is Nothing (might be useful for flattening NLA evaluation),
|
||||
* disable range. */
|
||||
if (dummy_strip->extendmode != NLASTRIP_EXTEND_NOTHING) {
|
||||
dummy_strip->flag |= NLASTRIP_FLAG_NO_TIME_MAP;
|
||||
}
|
||||
|
||||
dummy_strip->influence = adt->act_influence;
|
||||
|
||||
/* NOTE: must set this, or else the default setting overrides,
|
||||
* and this setting doesn't work. */
|
||||
dummy_strip->flag |= NLASTRIP_FLAG_USR_INFLUENCE;
|
||||
}
|
||||
|
||||
/* add this to our list of evaluation strips */
|
||||
if (r_context == NULL) {
|
||||
nlastrips_ctime_get_strip(
|
||||
&estrips, &dummy_trackslist, -1, anim_eval_context, flush_to_original);
|
||||
}
|
||||
/* If computing the context for keyframing, store data there instead of the list. */
|
||||
else {
|
||||
/* The extend mode here effectively controls
|
||||
* whether it is possible to key-frame beyond the ends.*/
|
||||
dummy_strip->extendmode = (is_inplace_tweak &&
|
||||
!(dummy_strip->flag & NLASTRIP_FLAG_SYNC_LENGTH)) ?
|
||||
NLASTRIP_EXTEND_NOTHING :
|
||||
NLASTRIP_EXTEND_HOLD;
|
||||
|
||||
r_context->eval_strip = nes = nlastrips_ctime_get_strip(
|
||||
NULL, &dummy_trackslist, -1, anim_eval_context, flush_to_original);
|
||||
|
||||
/* These setting combinations require no data from strips below, so exit immediately. */
|
||||
if ((nes == NULL) ||
|
||||
(dummy_strip->blendmode == NLASTRIP_MODE_REPLACE && dummy_strip->influence == 1.0f)) {
|
||||
BLI_freelistN(&estrips);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* special case - evaluate as if there isn't any NLA data */
|
||||
BLI_freelistN(&estrips);
|
||||
return false;
|
||||
}
|
||||
if (is_action_track_evaluated_without_nla(adt, has_strips)) {
|
||||
BLI_freelistN(&estrips);
|
||||
return false;
|
||||
}
|
||||
|
||||
/* only continue if there are strips to evaluate */
|
||||
if (BLI_listbase_is_empty(&estrips)) {
|
||||
return true;
|
||||
}
|
||||
NlaStrip action_strip = {0};
|
||||
animsys_create_action_track_strip(adt, false, &action_strip);
|
||||
nlastrips_ctime_get_strip_single(&estrips, &action_strip, anim_eval_context, flush_to_original);
|
||||
|
||||
/* 2. for each strip, evaluate then accumulate on top of existing channels,
|
||||
* but don't set values yet. */
|
||||
/* Per strip, evaluate and accumulate on top of existing channels. */
|
||||
for (nes = estrips.first; nes; nes = nes->next) {
|
||||
nlastrip_evaluate(ptr,
|
||||
echannels,
|
||||
|
@ -2393,11 +2455,116 @@ static bool animsys_evaluate_nla(NlaEvalData *echannels,
|
|||
flush_to_original);
|
||||
}
|
||||
|
||||
/* 3. free temporary evaluation data that's not used elsewhere */
|
||||
/* Free temporary evaluation data that's not used elsewhere. */
|
||||
BLI_freelistN(&estrips);
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Lower blended values are calculated and accumulated into r_context->lower_eval_data. */
|
||||
static void animsys_evaluate_nla_for_keyframing(PointerRNA *ptr,
|
||||
const AnimData *adt,
|
||||
const AnimationEvalContext *anim_eval_context,
|
||||
NlaKeyframingContext *r_context)
|
||||
{
|
||||
if (!r_context) {
|
||||
return;
|
||||
}
|
||||
|
||||
/* Early out. If NLA track is soloing and tweaked action isn't it, then don't allow keyframe
|
||||
* insertion. */
|
||||
if (adt->flag & ADT_NLA_SOLO_TRACK) {
|
||||
if (!(adt->act_track && (adt->act_track->flag & NLATRACK_SOLO))) {
|
||||
r_context->eval_strip = NULL;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
NlaTrack *nlt;
|
||||
short track_index = 0;
|
||||
bool has_strips = false;
|
||||
|
||||
ListBase lower_estrips = {NULL, NULL};
|
||||
NlaEvalStrip *nes;
|
||||
|
||||
NlaTrack *tweaked_track = nlatrack_find_tweaked(adt);
|
||||
|
||||
/* Get the lower stack of strips to evaluate at current time (influence calculated here). */
|
||||
for (nlt = adt->nla_tracks.first; nlt; nlt = nlt->next, track_index++) {
|
||||
|
||||
if (!is_nlatrack_evaluatable(adt, nlt)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Tweaked strip effect should not be stored in any snapshot. */
|
||||
if (nlt == tweaked_track) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (nlt->strips.first) {
|
||||
has_strips = true;
|
||||
}
|
||||
|
||||
/* Get strip to evaluate for this channel. */
|
||||
nes = nlastrips_ctime_get_strip(
|
||||
&lower_estrips, &nlt->strips, track_index, anim_eval_context, false);
|
||||
if (nes) {
|
||||
nes->track = nlt;
|
||||
}
|
||||
}
|
||||
|
||||
/** Note: Although we early out, we can still keyframe to the non-pushed action since the
|
||||
* keyframe remap function detects (r_context->strip.act == NULL) and will keyframe without
|
||||
* remapping.
|
||||
*/
|
||||
if (is_action_track_evaluated_without_nla(adt, has_strips)) {
|
||||
BLI_freelistN(&lower_estrips);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Write r_context->eval_strip. */
|
||||
if (adt->flag & ADT_NLA_EDIT_ON) {
|
||||
|
||||
NlaStrip *tweak_strip = &r_context->strip;
|
||||
animsys_create_tweak_strip(adt, true, tweak_strip);
|
||||
r_context->eval_strip = nlastrips_ctime_get_strip_single(
|
||||
NULL, tweak_strip, anim_eval_context, false);
|
||||
}
|
||||
else {
|
||||
|
||||
NlaStrip *action_strip = &r_context->strip;
|
||||
animsys_create_action_track_strip(adt, true, action_strip);
|
||||
r_context->eval_strip = nlastrips_ctime_get_strip_single(
|
||||
NULL, action_strip, anim_eval_context, false);
|
||||
}
|
||||
|
||||
/* If NULL, then keyframing will fail. No need to do any more processing. */
|
||||
if (!r_context->eval_strip) {
|
||||
BLI_freelistN(&lower_estrips);
|
||||
return;
|
||||
}
|
||||
|
||||
/* If tweak strip is full REPLACE, then lower strips not needed. */
|
||||
if (r_context->strip.blendmode == NLASTRIP_MODE_REPLACE &&
|
||||
IS_EQF(r_context->strip.influence, 1.0f)) {
|
||||
BLI_freelistN(&lower_estrips);
|
||||
return;
|
||||
}
|
||||
|
||||
/* For each strip, evaluate then accumulate on top of existing channels. */
|
||||
for (nes = lower_estrips.first; nes; nes = nes->next) {
|
||||
nlastrip_evaluate(ptr,
|
||||
&r_context->lower_eval_data,
|
||||
NULL,
|
||||
nes,
|
||||
&r_context->lower_eval_data.eval_snapshot,
|
||||
anim_eval_context,
|
||||
false);
|
||||
}
|
||||
|
||||
/* Free temporary evaluation data that's not used elsewhere. */
|
||||
BLI_freelistN(&lower_estrips);
|
||||
}
|
||||
|
||||
/* NLA Evaluation function (mostly for use through do_animdata)
|
||||
* - All channels that will be affected are not cleared anymore. Instead, we just evaluate into
|
||||
* some temp channels, where values can be accumulated in one go.
|
||||
|
@ -2412,7 +2579,7 @@ static void animsys_calculate_nla(PointerRNA *ptr,
|
|||
nlaeval_init(&echannels);
|
||||
|
||||
/* evaluate the NLA stack, obtaining a set of values to flush */
|
||||
if (animsys_evaluate_nla(&echannels, ptr, adt, anim_eval_context, flush_to_original, NULL)) {
|
||||
if (animsys_evaluate_nla_for_flush(&echannels, ptr, adt, anim_eval_context, flush_to_original)) {
|
||||
/* reset any channels touched by currently inactive actions to default value */
|
||||
animsys_evaluate_nla_domain(ptr, &echannels, adt);
|
||||
|
||||
|
@ -2448,8 +2615,7 @@ NlaKeyframingContext *BKE_animsys_get_nla_keyframing_context(
|
|||
struct ListBase *cache,
|
||||
struct PointerRNA *ptr,
|
||||
struct AnimData *adt,
|
||||
const AnimationEvalContext *anim_eval_context,
|
||||
const bool flush_to_original)
|
||||
const AnimationEvalContext *anim_eval_context)
|
||||
{
|
||||
/* No remapping needed if NLA is off or no action. */
|
||||
if ((adt == NULL) || (adt->action == NULL) || (adt->nla_tracks.first == NULL) ||
|
||||
|
@ -2472,8 +2638,7 @@ NlaKeyframingContext *BKE_animsys_get_nla_keyframing_context(
|
|||
ctx->adt = adt;
|
||||
|
||||
nlaeval_init(&ctx->lower_eval_data);
|
||||
animsys_evaluate_nla(
|
||||
&ctx->lower_eval_data, ptr, adt, anim_eval_context, flush_to_original, ctx);
|
||||
animsys_evaluate_nla_for_keyframing(ptr, adt, anim_eval_context, ctx);
|
||||
|
||||
BLI_assert(ELEM(ctx->strip.act, NULL, adt->action));
|
||||
BLI_addtail(cache, ctx);
|
||||
|
|
|
@ -4710,7 +4710,7 @@ static void achannel_setting_slider_cb(bContext *C, void *id_poin, void *fcu_poi
|
|||
const AnimationEvalContext anim_eval_context = BKE_animsys_eval_context_construct(depsgraph,
|
||||
(float)CFRA);
|
||||
NlaKeyframingContext *nla_context = BKE_animsys_get_nla_keyframing_context(
|
||||
&nla_cache, &id_ptr, adt, &anim_eval_context, false);
|
||||
&nla_cache, &id_ptr, adt, &anim_eval_context);
|
||||
|
||||
/* get current frame and apply NLA-mapping to it (if applicable) */
|
||||
cfra = BKE_nla_tweakedit_remap(adt, (float)CFRA, NLATIME_CONVERT_UNMAP);
|
||||
|
@ -4766,7 +4766,7 @@ static void achannel_setting_slider_shapekey_cb(bContext *C, void *key_poin, voi
|
|||
const AnimationEvalContext anim_eval_context = BKE_animsys_eval_context_construct(depsgraph,
|
||||
(float)CFRA);
|
||||
NlaKeyframingContext *nla_context = BKE_animsys_get_nla_keyframing_context(
|
||||
&nla_cache, &id_ptr, key->adt, &anim_eval_context, false);
|
||||
&nla_cache, &id_ptr, key->adt, &anim_eval_context);
|
||||
|
||||
/* get current frame and apply NLA-mapping to it (if applicable) */
|
||||
const float remapped_frame = BKE_nla_tweakedit_remap(
|
||||
|
|
|
@ -1384,7 +1384,7 @@ static AnimationEvalContext nla_time_remap(const AnimationEvalContext *anim_eval
|
|||
if (adt && adt->action == act) {
|
||||
/* Get NLA context for value remapping. */
|
||||
*r_nla_context = BKE_animsys_get_nla_keyframing_context(
|
||||
nla_cache, id_ptr, adt, anim_eval_context, false);
|
||||
nla_cache, id_ptr, adt, anim_eval_context);
|
||||
|
||||
/* Apply NLA-mapping to frame. */
|
||||
const float remapped_frame = BKE_nla_tweakedit_remap(
|
||||
|
|
Loading…
Reference in New Issue