Fix T94078: Wrong Bound Box calculated for curves
`DEG_OBJECT_ITER_FOR_RENDER_ENGINE_BEGIN` creates temporary objects that correspond to duplicates or instances. These temporary objects can share same pointers with the original object as in the case of Bounding Box. Bound Box of temporary objects is marked dirty in `BKE_object_replace_data_on_shallow_copy` since `ob->data` is different. This causes the original Bounding Box, calculated for the evaluated geometry, to be lost. The solution in this commit is to change the boundbox reference of the temporary objects, so the boundbox of the non-temporary object (with the data curve) is not marked dirty. Differential Revision: https://developer.blender.org/D13581
This commit is contained in:
parent
5085c622ea
commit
5560f32447
Notes:
blender-bot
2023-02-13 16:47:57 +01:00
Referenced by issue #94733, Geometry nodes. Low performance case with instancing Referenced by issue #94078, Wrong Bound Box calculated for curves
|
@ -76,14 +76,8 @@ void deg_invalidate_iterator_work_data(DEGObjectIterData *data)
|
|||
#endif
|
||||
}
|
||||
|
||||
void verify_id_properties_freed(DEGObjectIterData *data)
|
||||
void ensure_id_properties_freed(const Object *dupli_object, Object *temp_dupli_object)
|
||||
{
|
||||
if (data->dupli_object_current == nullptr) {
|
||||
/* We didn't enter duplication yet, so we can't have any dangling pointers. */
|
||||
return;
|
||||
}
|
||||
const Object *dupli_object = data->dupli_object_current->ob;
|
||||
Object *temp_dupli_object = &data->temp_dupli_object;
|
||||
if (temp_dupli_object->id.properties == nullptr) {
|
||||
/* No ID properties in temp data-block -- no leak is possible. */
|
||||
return;
|
||||
|
@ -97,6 +91,35 @@ void verify_id_properties_freed(DEGObjectIterData *data)
|
|||
temp_dupli_object->id.properties = nullptr;
|
||||
}
|
||||
|
||||
void ensure_boundbox_freed(const Object *dupli_object, Object *temp_dupli_object)
|
||||
{
|
||||
if (temp_dupli_object->runtime.bb == nullptr) {
|
||||
/* No Bounding Box in temp data-block -- no leak is possible. */
|
||||
return;
|
||||
}
|
||||
if (temp_dupli_object->runtime.bb == dupli_object->runtime.bb) {
|
||||
/* Temp copy of object did not modify Bounding Box. */
|
||||
return;
|
||||
}
|
||||
/* Free memory which is owned by temporary storage which is about to get overwritten. */
|
||||
MEM_freeN(temp_dupli_object->runtime.bb);
|
||||
temp_dupli_object->runtime.bb = nullptr;
|
||||
}
|
||||
|
||||
void free_owned_memory(DEGObjectIterData *data)
|
||||
{
|
||||
if (data->dupli_object_current == nullptr) {
|
||||
/* We didn't enter duplication yet, so we can't have any dangling pointers. */
|
||||
return;
|
||||
}
|
||||
|
||||
const Object *dupli_object = data->dupli_object_current->ob;
|
||||
Object *temp_dupli_object = &data->temp_dupli_object;
|
||||
|
||||
ensure_id_properties_freed(dupli_object, temp_dupli_object);
|
||||
ensure_boundbox_freed(dupli_object, temp_dupli_object);
|
||||
}
|
||||
|
||||
bool deg_object_hide_original(eEvaluationMode eval_mode, Object *ob, DupliObject *dob)
|
||||
{
|
||||
/* Automatic hiding if this object is being instanced on verts/faces/frames
|
||||
|
@ -153,7 +176,7 @@ bool deg_iterator_duplis_step(DEGObjectIterData *data)
|
|||
continue;
|
||||
}
|
||||
|
||||
verify_id_properties_freed(data);
|
||||
free_owned_memory(data);
|
||||
|
||||
data->dupli_object_current = dob;
|
||||
|
||||
|
@ -169,6 +192,8 @@ bool deg_iterator_duplis_step(DEGObjectIterData *data)
|
|||
copy_v4_v4(temp_dupli_object->color, dupli_parent->color);
|
||||
temp_dupli_object->runtime.select_id = dupli_parent->runtime.select_id;
|
||||
if (dob->ob->data != dob->ob_data) {
|
||||
/* Do not modify the original boundbox. */
|
||||
temp_dupli_object->runtime.bb = nullptr;
|
||||
BKE_object_replace_data_on_shallow_copy(temp_dupli_object, dob->ob_data);
|
||||
}
|
||||
|
||||
|
@ -192,7 +217,7 @@ bool deg_iterator_duplis_step(DEGObjectIterData *data)
|
|||
return true;
|
||||
}
|
||||
|
||||
verify_id_properties_freed(data);
|
||||
free_owned_memory(data);
|
||||
free_object_duplilist(data->dupli_list);
|
||||
data->dupli_parent = nullptr;
|
||||
data->dupli_list = nullptr;
|
||||
|
|
|
@ -757,8 +757,11 @@ static void duplidata_key_free(void *key)
|
|||
}
|
||||
else {
|
||||
Object temp_object = *dupli_key->ob;
|
||||
/* Do not modify the original boundbox. */
|
||||
temp_object.runtime.bb = NULL;
|
||||
BKE_object_replace_data_on_shallow_copy(&temp_object, dupli_key->ob_data);
|
||||
drw_batch_cache_generate_requested(&temp_object);
|
||||
MEM_SAFE_FREE(temp_object.runtime.bb);
|
||||
}
|
||||
MEM_freeN(key);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue