Object: improve on fix for Object.to_mesh() crash T86871
While fa7ddd0f43
fixed the reported issue,
the possibility of reusing runtime data during curve-to-mesh conversion
remained. Instead of treating the bounding-box as a special case,
clear all run-time data for temporary objects.
Ref D11026
Reviewed By: sergey
This commit is contained in:
parent
ea17a92cd7
commit
2b723abea0
Notes:
blender-bot
2023-02-14 06:45:14 +01:00
Referenced by commit d18be66a54
, Fix T86871: Mesh.mesh_from_object creates empty mesh from curve
Referenced by issue #87944, Python API Function `bpy.data.meshes.mesh_from_object()` No Longer Works
|
@ -374,6 +374,7 @@ struct MovieClip *BKE_object_movieclip_get(struct Scene *scene,
|
|||
|
||||
void BKE_object_runtime_reset(struct Object *object);
|
||||
void BKE_object_runtime_reset_on_copy(struct Object *object, const int flag);
|
||||
void BKE_object_runtime_free(struct Object *object);
|
||||
|
||||
void BKE_object_batch_cache_dirty_tag(struct Object *ob);
|
||||
|
||||
|
|
|
@ -1027,11 +1027,15 @@ static Object *object_for_curve_to_mesh_create(Object *object)
|
|||
*
|
||||
* Note that there are extra fields in there like bevel and path, but those are not needed during
|
||||
* conversion, so they are not copied to save unnecessary allocations. */
|
||||
if (object->runtime.curve_cache != NULL) {
|
||||
if (temp_object->runtime.curve_cache == NULL) {
|
||||
temp_object->runtime.curve_cache = MEM_callocN(sizeof(CurveCache),
|
||||
"CurveCache for curve types");
|
||||
}
|
||||
|
||||
if (object->runtime.curve_cache != NULL) {
|
||||
BKE_displist_copy(&temp_object->runtime.curve_cache->disp, &object->runtime.curve_cache->disp);
|
||||
}
|
||||
|
||||
/* Constructive modifiers will use mesh to store result. */
|
||||
if (object->runtime.data_eval != NULL) {
|
||||
BKE_id_copy_ex(
|
||||
|
@ -1059,15 +1063,17 @@ static Object *object_for_curve_to_mesh_create(Object *object)
|
|||
|
||||
static void curve_to_mesh_eval_ensure(Object *object)
|
||||
{
|
||||
if (object->runtime.curve_cache == NULL) {
|
||||
object->runtime.curve_cache = MEM_callocN(sizeof(CurveCache), "CurveCache for Curve");
|
||||
}
|
||||
Curve *curve = (Curve *)object->data;
|
||||
Curve remapped_curve = *curve;
|
||||
Object remapped_object = *object;
|
||||
remapped_object.runtime.bb = NULL;
|
||||
BKE_object_runtime_reset(&remapped_object);
|
||||
|
||||
remapped_object.data = &remapped_curve;
|
||||
|
||||
if (remapped_object.runtime.curve_cache == NULL) {
|
||||
remapped_object.runtime.curve_cache = MEM_callocN(sizeof(CurveCache), "CurveCache for Curve");
|
||||
}
|
||||
|
||||
/* Clear all modifiers for the bevel object.
|
||||
*
|
||||
* This is because they can not be reliably evaluated for an original object (at least because
|
||||
|
@ -1078,8 +1084,8 @@ static void curve_to_mesh_eval_ensure(Object *object)
|
|||
Object bevel_object = {{NULL}};
|
||||
if (remapped_curve.bevobj != NULL) {
|
||||
bevel_object = *remapped_curve.bevobj;
|
||||
bevel_object.runtime.bb = NULL;
|
||||
BLI_listbase_clear(&bevel_object.modifiers);
|
||||
BKE_object_runtime_reset(&bevel_object);
|
||||
remapped_curve.bevobj = &bevel_object;
|
||||
}
|
||||
|
||||
|
@ -1087,8 +1093,8 @@ static void curve_to_mesh_eval_ensure(Object *object)
|
|||
Object taper_object = {{NULL}};
|
||||
if (remapped_curve.taperobj != NULL) {
|
||||
taper_object = *remapped_curve.taperobj;
|
||||
taper_object.runtime.bb = NULL;
|
||||
BLI_listbase_clear(&taper_object.modifiers);
|
||||
BKE_object_runtime_reset(&taper_object);
|
||||
remapped_curve.taperobj = &taper_object;
|
||||
}
|
||||
|
||||
|
@ -1110,12 +1116,9 @@ static void curve_to_mesh_eval_ensure(Object *object)
|
|||
BKE_object_eval_assign_data(&remapped_object, &mesh_eval->id, true);
|
||||
}
|
||||
|
||||
MEM_SAFE_FREE(remapped_object.runtime.bb);
|
||||
MEM_SAFE_FREE(taper_object.runtime.bb);
|
||||
MEM_SAFE_FREE(bevel_object.runtime.bb);
|
||||
|
||||
BKE_object_free_curve_cache(&bevel_object);
|
||||
BKE_object_free_curve_cache(&taper_object);
|
||||
BKE_object_runtime_free(&remapped_object);
|
||||
BKE_object_runtime_free(&taper_object);
|
||||
BKE_object_runtime_free(&taper_object);
|
||||
}
|
||||
|
||||
static Mesh *mesh_new_from_curve_type_object(Object *object)
|
||||
|
|
|
@ -5113,6 +5113,17 @@ void BKE_object_runtime_reset_on_copy(Object *object, const int UNUSED(flag))
|
|||
runtime->geometry_set_eval = NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* The function frees memory used by the runtime data, but not the runtime field itself.
|
||||
*
|
||||
* The caller is expected to run #BKE_object_runtime_reset if the struct will be used again.
|
||||
*/
|
||||
void BKE_object_runtime_free(Object *object)
|
||||
{
|
||||
/* Currently this is all that's needed. */
|
||||
BKE_object_free_derived_caches(object);
|
||||
}
|
||||
|
||||
/**
|
||||
* Find an associated armature object.
|
||||
*/
|
||||
|
|
Loading…
Reference in New Issue