forked from blender/blender
Implement instancing for light objects #35
@ -8,6 +8,11 @@
|
||||
|
||||
namespace blender::render::hydra {
|
||||
|
||||
void InstancerData::LightInstance::update()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
InstancerData::InstancerData(BlenderSceneDelegate *scene_delegate,
|
||||
Object *object,
|
||||
pxr::SdfPath const &prim_id)
|
||||
@ -212,34 +217,35 @@ void InstancerData::set_instances()
|
||||
for (auto &it : mesh_instances_) {
|
||||
it.second.indices.clear();
|
||||
}
|
||||
int mesh_index = 0, light_index = 0;
|
||||
Instance *inst;
|
||||
pxr::SdfPath p_id;
|
||||
Object *ob;
|
||||
for (auto &it : light_instances_) {
|
||||
it.second.transforms.clear();
|
||||
}
|
||||
|
||||
ListBase *lb = object_duplilist(
|
||||
scene_delegate_->depsgraph, scene_delegate_->scene, (Object *)id);
|
||||
LISTBASE_FOREACH (DupliObject *, dupli, lb) {
|
||||
ob = dupli->ob;
|
||||
Object *ob = dupli->ob;
|
||||
if (!is_supported(ob)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
p_id = object_prim_id(dupli->ob);
|
||||
pxr::SdfPath p_id = object_prim_id(ob);
|
||||
if (ob->type == OB_LAMP) {
|
||||
LightInstance *inst;
|
||||
auto it = light_instances_.find(p_id);
|
||||
if (it == light_instances_.end()) {
|
||||
inst = &light_instances_[p_id];
|
||||
inst->obj_data = std::make_unique<LightData>(scene_delegate_, ob, p_id);
|
||||
inst->obj_data->init();
|
||||
inst->data = std::make_unique<LightData>(scene_delegate_, ob, p_id);
|
||||
inst->data->init();
|
||||
}
|
||||
else {
|
||||
inst = &it->second;
|
||||
}
|
||||
mesh_transforms_.push_back(gf_matrix_from_transform(dupli->mat));
|
||||
inst->indices.push_back(mesh_index);
|
||||
ID_LOG(2, "%s %d", inst->data->id->name, inst->transforms.size());
|
||||
inst->transforms.push_back(gf_matrix_from_transform(dupli->mat));
|
||||
}
|
||||
else {
|
||||
MeshInstance *inst;
|
||||
auto it = mesh_instances_.find(p_id);
|
||||
if (it == mesh_instances_.end()) {
|
||||
inst = &mesh_instances_[p_id];
|
||||
@ -248,15 +254,14 @@ void InstancerData::set_instances()
|
||||
else {
|
||||
inst = &it->second;
|
||||
}
|
||||
ID_LOG(2, "%s %d", inst->obj_data->id->name, mesh_transforms_.size());
|
||||
inst->indices.push_back(mesh_transforms_.size());
|
||||
mesh_transforms_.push_back(gf_matrix_from_transform(dupli->mat));
|
||||
inst->indices.push_back(mesh_index);
|
||||
ID_LOG(2, "%s %d", inst->obj_data->id->name, mesh_index);
|
||||
++mesh_index;
|
||||
}
|
||||
}
|
||||
free_object_duplilist(lb);
|
||||
|
||||
/* Remove intances without indices */
|
||||
/* Remove mesh intances without indices */
|
||||
for (auto it = mesh_instances_.begin(); it != mesh_instances_.end(); ++it) {
|
||||
if (!it->second.indices.empty()) {
|
||||
continue;
|
||||
@ -265,6 +270,15 @@ void InstancerData::set_instances()
|
||||
mesh_instances_.erase(it);
|
||||
it = mesh_instances_.begin();
|
||||
}
|
||||
|
||||
/* Update light intances and remove instances without transforms */
|
||||
for (auto it = light_instances_.begin(); it != light_instances_.end(); ++it) {
|
||||
it->second.update();
|
||||
if (it->second.transforms.empty()) {
|
||||
light_instances_.erase(it);
|
||||
it = light_instances_.begin();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace blender::render::hydra
|
||||
|
@ -6,15 +6,26 @@
|
||||
#include "BKE_duplilist.h"
|
||||
|
||||
#include "mesh.h"
|
||||
#include "light.h"
|
||||
|
||||
namespace blender::render::hydra {
|
||||
|
||||
class InstancerData : public ObjectData {
|
||||
struct Instance {
|
||||
struct MeshInstance {
|
||||
std::unique_ptr<ObjectData> obj_data;
|
||||
pxr::VtIntArray indices;
|
||||
};
|
||||
|
||||
struct LightInstance {
|
||||
std::unique_ptr<LightData> data;
|
||||
pxr::VtMatrix4dArray transforms;
|
||||
|
||||
void update();
|
||||
|
||||
private:
|
||||
int count_ = 0;
|
||||
};
|
||||
|
||||
public:
|
||||
InstancerData(BlenderSceneDelegate *scene_delegate, Object *object, pxr::SdfPath const &prim_id);
|
||||
|
||||
@ -45,10 +56,9 @@ class InstancerData : public ObjectData {
|
||||
pxr::SdfPath object_prim_id(Object *object) const;
|
||||
void set_instances();
|
||||
|
||||
pxr::TfHashMap<pxr::SdfPath, Instance, pxr::SdfPath::Hash> mesh_instances_;
|
||||
pxr::TfHashMap<pxr::SdfPath, Instance, pxr::SdfPath::Hash> light_instances_;
|
||||
pxr::TfHashMap<pxr::SdfPath, MeshInstance, pxr::SdfPath::Hash> mesh_instances_;
|
||||
pxr::TfHashMap<pxr::SdfPath, LightInstance, pxr::SdfPath::Hash> light_instances_;
|
||||
pxr::VtMatrix4dArray mesh_transforms_;
|
||||
pxr::VtMatrix4dArray light_transforms_;
|
||||
};
|
||||
|
||||
using InstancerDataMap =
|
||||
|
Loading…
Reference in New Issue
Block a user