From c622533fa01a9f478d5116ca68ad299081ae22b4 Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Mon, 18 Sep 2017 15:50:27 +0500 Subject: Fix T52432: Blender crashes while using Ghost (new depsgraph) --- .../depsgraph/intern/eval/deg_eval_flush.cc | 24 +++++++++++++++++++--- 1 file changed, 21 insertions(+), 3 deletions(-) diff --git a/source/blender/depsgraph/intern/eval/deg_eval_flush.cc b/source/blender/depsgraph/intern/eval/deg_eval_flush.cc index c230ab4c8fd..40f6901de33 100644 --- a/source/blender/depsgraph/intern/eval/deg_eval_flush.cc +++ b/source/blender/depsgraph/intern/eval/deg_eval_flush.cc @@ -54,6 +54,12 @@ extern "C" { namespace DEG { +enum { + COMPONENT_STATE_NONE = 0, + COMPONENT_STATE_SCHEDULED = 1, + COMPONENT_STATE_DONE = 2, +}; + namespace { // TODO(sergey): De-duplicate with depsgraph_tag,cc @@ -83,7 +89,7 @@ static void flush_init_func(void *data_v, int i) ComponentDepsNode *comp_node = node->owner; IDDepsNode *id_node = comp_node->owner; id_node->done = 0; - comp_node->done = 0; + comp_node->done = COMPONENT_STATE_NONE; node->scheduled = false; } @@ -146,7 +152,7 @@ void deg_graph_flush_updates(Main *bmain, Depsgraph *graph) lib_id_recalc_data_tag(bmain, id); } - if (comp_node->done == 0) { + if (comp_node->done != COMPONENT_STATE_DONE) { Object *object = NULL; if (GS(id->name) == ID_OB) { object = (Object *)id; @@ -190,9 +196,21 @@ void deg_graph_flush_updates(Main *bmain, Depsgraph *graph) break; } } + /* When some target changes bone, we might need to re-run the + * whole IK solver, otherwise result might be unpredictable. + */ + if (comp_node->type == DEG_NODE_TYPE_BONE) { + ComponentDepsNode *pose_comp = + id_node->find_component(DEG_NODE_TYPE_EVAL_POSE); + BLI_assert(pose_comp != NULL); + if (pose_comp->done == COMPONENT_STATE_NONE) { + queue.push_front(pose_comp->get_entry_operation()); + pose_comp->done = COMPONENT_STATE_SCHEDULED; + } + } } - id_node->done = 1; + id_node->done = COMPONENT_STATE_DONE; comp_node->done = 1; /* Flush to nodes along links... */ -- cgit v1.2.3