BLEN-359: Implement updates for instances in viewport #20

Merged
Bogdan Nagirniak merged 20 commits from BLEN-359_1 into hydra-render 2023-04-05 11:47:37 +02:00
3 changed files with 40 additions and 8 deletions
Showing only changes of commit 5bc6d011bb - Show all commits

View File

@ -119,9 +119,6 @@ void BlenderSceneDelegate::update_collection(bool remove, bool visibility)
if (!ObjectData::supported(object)) { if (!ObjectData::supported(object)) {
continue; continue;
} }
if ((object->transflag & OB_DUPLI) && InstancerData::supported(object)) {
add_update_instancer(object);
}
id = ObjectData::prim_id(this, object); id = ObjectData::prim_id(this, object);
if (remove) { if (remove) {
@ -170,10 +167,17 @@ void BlenderSceneDelegate::update_collection(bool remove, bool visibility)
void BlenderSceneDelegate::add_update_object(Object *object) void BlenderSceneDelegate::add_update_object(Object *object)
{ {
if ((object->transflag & OB_DUPLI) && InstancerData::supported(object)) {
add_update_instancer(object);
}
pxr::SdfPath id = ObjectData::prim_id(this, object); pxr::SdfPath id = ObjectData::prim_id(this, object);
ObjectData *obj_data = object_data(id); ObjectData *obj_data = object_data(id);
if (obj_data) { if (obj_data) {
obj_data->update(); obj_data->update();
return;
}
if (view3d && !BKE_object_is_visible_in_viewport(view3d, object)) {
return;
} }
objects[id] = ObjectData::create(this, object); objects[id] = ObjectData::create(this, object);
obj_data = object_data(id); obj_data = object_data(id);
@ -186,6 +190,7 @@ void BlenderSceneDelegate::add_update_instancer(Object *object)
InstancerData *i_data = instancer_data(id, true); InstancerData *i_data = instancer_data(id, true);
if (i_data) { if (i_data) {
i_data->update(); i_data->update();
return;
} }
objects[id] = InstancerData::create(this, object); objects[id] = InstancerData::create(this, object);
i_data = instancer_data(id, true); i_data = instancer_data(id, true);

View File

@ -63,10 +63,12 @@ void InstancerData::init()
ListBase *lb = object_duplilist(scene_delegate->depsgraph, scene_delegate->scene, parent_obj); ListBase *lb = object_duplilist(scene_delegate->depsgraph, scene_delegate->scene, parent_obj);
LISTBASE_FOREACH (DupliObject *, dupli, lb) { LISTBASE_FOREACH (DupliObject *, dupli, lb) {
if (!id) { if (!id) {
/* TODO: We create instances only for object in first dupli.
Instances should be created for all objects */
id = (ID *)dupli->ob; id = (ID *)dupli->ob;
} }
transforms.push_back(gf_matrix_from_transform(dupli->mat)); transforms.push_back(gf_matrix_from_transform(dupli->mat));
CLOG_INFO(LOG_BSD, 2, "Instance %s %d", id->name, dupli->random_id); CLOG_INFO(LOG_BSD, 2, "Instance %s (%s) %d", id->name, ((ID *)dupli->ob)->name, dupli->random_id);
} }
free_object_duplilist(lb); free_object_duplilist(lb);
@ -121,7 +123,7 @@ VtIntArray InstancerData::instance_indices()
void InstancerData::insert() void InstancerData::insert()
{ {
CLOG_INFO(LOG_BSD, 2, "%s", id->name); CLOG_INFO(LOG_BSD, 2, "%s", ((ID *)parent_obj)->name);
MeshData::insert(); MeshData::insert();
if (face_vertex_counts.empty()) { if (face_vertex_counts.empty()) {
@ -132,7 +134,7 @@ void InstancerData::insert()
void InstancerData::remove() void InstancerData::remove()
{ {
CLOG_INFO(LOG_BSD, 2, "%s", id->name); CLOG_INFO(LOG_BSD, 2, "%s", ((ID *)parent_obj)->name);
if (!scene_delegate->GetRenderIndex().HasInstancer(instancer_id)) { if (!scene_delegate->GetRenderIndex().HasInstancer(instancer_id)) {
return; return;
@ -144,8 +146,29 @@ void InstancerData::remove()
void InstancerData::update() void InstancerData::update()
{ {
CLOG_INFO(LOG_BSD, 2, "%s", id->name); CLOG_INFO(LOG_BSD, 2, "%s", ((ID *)parent_obj)->name);
MeshData::update();
pxr::HdDirtyBits bits = pxr::HdChangeTracker::Clean;
unsigned int recalc = ((ID *)parent_obj)->recalc;
if ((recalc & ID_RECALC_GEOMETRY) || (((ID *)parent_obj->data)->recalc & ID_RECALC_GEOMETRY)) {
init();
bits = pxr::HdChangeTracker::AllDirty;
}
else if (recalc & ID_RECALC_TRANSFORM) {
transforms.clear();
ListBase *lb = object_duplilist(scene_delegate->depsgraph, scene_delegate->scene, parent_obj);
LISTBASE_FOREACH (DupliObject *, dupli, lb) {
transforms.push_back(gf_matrix_from_transform(dupli->mat));
}
free_object_duplilist(lb);
bits |= pxr::HdChangeTracker::DirtyTransform;
}
if (bits != pxr::HdChangeTracker::Clean) {
scene_delegate->GetRenderIndex().GetChangeTracker().MarkInstancerDirty(instancer_id, bits);
}
//scene_delegate->GetRenderIndex().GetChangeTracker().MarkRprimDirty(p_id, bits);
} }
} // namespace blender::render::hydra } // namespace blender::render::hydra

View File

@ -223,6 +223,10 @@ void MeshData::update()
} }
} }
if (bits == pxr::HdChangeTracker::Clean) {
return;
}
if (!scene_delegate->GetRenderIndex().HasRprim(p_id)) { if (!scene_delegate->GetRenderIndex().HasRprim(p_id)) {
insert(); insert();
return; return;