forked from bartvdbraak/blender
fix [#26920] working with bones causes segmetation fault.
ITASC IK solver data wasn't being cleared when constraints were removed, would access freed memory and crash.
This commit is contained in:
parent
b5c2598a6b
commit
ea5b43d862
@ -4019,7 +4019,9 @@ bConstraintTypeInfo *constraint_get_typeinfo (bConstraint *con)
|
||||
|
||||
/* ---------- Data Management ------- */
|
||||
|
||||
/* Free data of a specific constraint if it has any info */
|
||||
/* Free data of a specific constraint if it has any info.
|
||||
* be sure to run BIK_clear_data() when freeing an IK constraint,
|
||||
* unless DAG_scene_sort is called. */
|
||||
void free_constraint_data (bConstraint *con)
|
||||
{
|
||||
if (con->data) {
|
||||
|
@ -844,7 +844,8 @@ static int constraint_delete_exec (bContext *C, wmOperator *UNUSED(op))
|
||||
Object *ob= ptr.id.data;
|
||||
bConstraint *con= ptr.data;
|
||||
ListBase *lb = get_constraint_lb(ob, con, NULL);
|
||||
|
||||
const short is_ik= ELEM(con->type, CONSTRAINT_TYPE_KINEMATIC, CONSTRAINT_TYPE_SPLINEIK);
|
||||
|
||||
/* free the constraint */
|
||||
if (remove_constraint(lb, con)) {
|
||||
/* there's no active constraint now, so make sure this is the case */
|
||||
@ -852,6 +853,11 @@ static int constraint_delete_exec (bContext *C, wmOperator *UNUSED(op))
|
||||
|
||||
ED_object_constraint_update(ob); /* needed to set the flags on posebones correctly */
|
||||
|
||||
/* ITASC needs to be rebuilt once a constraint is removed [#26920] */
|
||||
if(is_ik) {
|
||||
BIK_clear_data(ob->pose);
|
||||
}
|
||||
|
||||
/* notifiers */
|
||||
WM_event_add_notifier(C, NC_OBJECT|ND_CONSTRAINT|NA_REMOVED, ob);
|
||||
|
||||
@ -993,6 +999,8 @@ static int pose_constraints_clear_exec(bContext *C, wmOperator *UNUSED(op))
|
||||
/* force depsgraph to get recalculated since relationships removed */
|
||||
DAG_scene_sort(bmain, scene); /* sort order of objects */
|
||||
|
||||
/* note, calling BIK_clear_data() isnt needed here */
|
||||
|
||||
/* do updates */
|
||||
DAG_id_tag_update(&ob->id, OB_RECALC_DATA);
|
||||
WM_event_add_notifier(C, NC_OBJECT|ND_CONSTRAINT, ob);
|
||||
@ -1003,7 +1011,7 @@ static int pose_constraints_clear_exec(bContext *C, wmOperator *UNUSED(op))
|
||||
void POSE_OT_constraints_clear(wmOperatorType *ot)
|
||||
{
|
||||
/* identifiers */
|
||||
ot->name = "Clear Constraints";
|
||||
ot->name = "Clear Pose Constraints";
|
||||
ot->idname= "POSE_OT_constraints_clear";
|
||||
ot->description= "Clear all the constraints for the selected bones";
|
||||
|
||||
@ -1038,7 +1046,7 @@ static int object_constraints_clear_exec(bContext *C, wmOperator *UNUSED(op))
|
||||
void OBJECT_OT_constraints_clear(wmOperatorType *ot)
|
||||
{
|
||||
/* identifiers */
|
||||
ot->name = "Clear Constraints";
|
||||
ot->name = "Clear Object Constraints";
|
||||
ot->idname= "OBJECT_OT_constraints_clear";
|
||||
ot->description= "Clear all the constraints for the active Object only";
|
||||
|
||||
|
@ -470,11 +470,22 @@ static void rna_PoseChannel_constraints_remove(ID *id, bPoseChannel *pchan, Repo
|
||||
BKE_reportf(reports, RPT_ERROR, "Constraint '%s' not found in pose bone '%s'.", con->name, pchan->name);
|
||||
return;
|
||||
}
|
||||
else {
|
||||
Object *ob= (Object *)id;
|
||||
const short is_ik= ELEM(con->type, CONSTRAINT_TYPE_KINEMATIC, CONSTRAINT_TYPE_SPLINEIK);
|
||||
|
||||
// TODO
|
||||
//ED_object_constraint_set_active(id, NULL);
|
||||
WM_main_add_notifier(NC_OBJECT|ND_CONSTRAINT, id);
|
||||
remove_constraint(&pchan->constraints, con);
|
||||
remove_constraint(&pchan->constraints, con);
|
||||
|
||||
ED_object_constraint_update(ob);
|
||||
|
||||
constraints_set_active(&pchan->constraints, NULL);
|
||||
|
||||
if (is_ik) {
|
||||
BIK_clear_data(ob->pose);
|
||||
}
|
||||
|
||||
WM_main_add_notifier(NC_OBJECT|ND_CONSTRAINT|NA_REMOVED, id);
|
||||
}
|
||||
}
|
||||
|
||||
static int rna_PoseChannel_proxy_editable(PointerRNA *ptr)
|
||||
|
Loading…
Reference in New Issue
Block a user