diff options
author | Kévin Dietrich <kevin.dietrich@mailoo.org> | 2016-01-09 06:37:53 +0300 |
---|---|---|
committer | Kévin Dietrich <kevin.dietrich@mailoo.org> | 2016-01-09 06:37:53 +0300 |
commit | d7da51b7277252d887cd93b1ac26bfe4ee25ad44 (patch) | |
tree | 0bb4c28cf1b42ee5f3ed0a5a478e99bcfb591a13 /source/blender/blenkernel/intern/object.c | |
parent | cc0f5bf7ec4a072994633294b4cbea0cd7472a07 (diff) |
Smoke, Dynamic Paint: de-duplicate object subframe update function.
As in the title. In the smoke version, there was also an extra
'for_render' parameter that wasn't used, and wasn't used by the callers
either, so it was removed altogether.
Reviewers: brecht
Reviewed By: brecht
Subscribers: brecht
Differential Revision: https://developer.blender.org/D1718
Diffstat (limited to 'source/blender/blenkernel/intern/object.c')
-rw-r--r-- | source/blender/blenkernel/intern/object.c | 102 |
1 files changed, 102 insertions, 0 deletions
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c index b448bec84e3..ba7daee9f3f 100644 --- a/source/blender/blenkernel/intern/object.c +++ b/source/blender/blenkernel/intern/object.c @@ -4099,3 +4099,105 @@ bool BKE_object_modifier_use_time(Object *ob, ModifierData *md) return false; } + +/* set "ignore cache" flag for all caches on this object */ +static void object_cacheIgnoreClear(Object *ob, int state) +{ + ListBase pidlist; + PTCacheID *pid; + BKE_ptcache_ids_from_object(&pidlist, ob, NULL, 0); + + for (pid = pidlist.first; pid; pid = pid->next) { + if (pid->cache) { + if (state) + pid->cache->flag |= PTCACHE_IGNORE_CLEAR; + else + pid->cache->flag &= ~PTCACHE_IGNORE_CLEAR; + } + } + + BLI_freelistN(&pidlist); +} + +/* Note: this function should eventually be replaced by depsgraph functionality. + * Avoid calling this in new code unless there is a very good reason for it! + */ +bool BKE_object_modifier_update_subframe(Scene *scene, Object *ob, bool update_mesh, + int parent_recursion, float frame, + ModifierType type) +{ + ModifierData *md = modifiers_findByType(ob, type); + bConstraint *con; + + if (type == eModifierType_DynamicPaint) { + DynamicPaintModifierData *pmd = (DynamicPaintModifierData *)md; + + /* if other is dynamic paint canvas, don't update */ + if (pmd && pmd->canvas) + return true; + } + else if (type == eModifierType_Smoke) { + SmokeModifierData *smd = (SmokeModifierData *)md; + + if (smd && (smd->type & MOD_SMOKE_TYPE_DOMAIN) != 0) + return true; + } + + /* if object has parents, update them too */ + if (parent_recursion) { + int recursion = parent_recursion - 1; + bool no_update = false; + if (ob->parent) no_update |= BKE_object_modifier_update_subframe(scene, ob->parent, 0, recursion, frame, type); + if (ob->track) no_update |= BKE_object_modifier_update_subframe(scene, ob->track, 0, recursion, frame, type); + + /* skip subframe if object is parented + * to vertex of a dynamic paint canvas */ + if (no_update && (ob->partype == PARVERT1 || ob->partype == PARVERT3)) + return false; + + /* also update constraint targets */ + for (con = ob->constraints.first; con; con = con->next) { + const bConstraintTypeInfo *cti = BKE_constraint_typeinfo_get(con); + ListBase targets = {NULL, NULL}; + + if (cti && cti->get_constraint_targets) { + bConstraintTarget *ct; + cti->get_constraint_targets(con, &targets); + for (ct = targets.first; ct; ct = ct->next) { + if (ct->tar) + BKE_object_modifier_update_subframe(scene, ct->tar, 0, recursion, frame, type); + } + /* free temp targets */ + if (cti->flush_constraint_targets) + cti->flush_constraint_targets(con, &targets, 0); + } + } + } + + /* was originally OB_RECALC_ALL - TODO - which flags are really needed??? */ + ob->recalc |= OB_RECALC_OB | OB_RECALC_DATA | OB_RECALC_TIME; + BKE_animsys_evaluate_animdata(scene, &ob->id, ob->adt, frame, ADT_RECALC_ANIM); + if (update_mesh) { + /* ignore cache clear during subframe updates + * to not mess up cache validity */ + object_cacheIgnoreClear(ob, 1); + BKE_object_handle_update(G.main->eval_ctx, scene, ob); + object_cacheIgnoreClear(ob, 0); + } + else + BKE_object_where_is_calc_time(scene, ob, frame); + + /* for curve following objects, parented curve has to be updated too */ + if (ob->type == OB_CURVE) { + Curve *cu = ob->data; + BKE_animsys_evaluate_animdata(scene, &cu->id, cu->adt, frame, ADT_RECALC_ANIM); + } + /* and armatures... */ + if (ob->type == OB_ARMATURE) { + bArmature *arm = ob->data; + BKE_animsys_evaluate_animdata(scene, &arm->id, arm->adt, frame, ADT_RECALC_ANIM); + BKE_pose_where_is(scene, ob); + } + + return false; +} |