From 32210bc3b32ee00475d707ae536f09869ab09cd7 Mon Sep 17 00:00:00 2001 From: Lars Ivar Hatledal Date: Wed, 20 Mar 2024 12:59:02 +0100 Subject: [PATCH] make it possible change the amount of instances to render (#247) --- examples/objects/instancing.cpp | 21 +++++++++++---------- include/threepp/objects/InstancedMesh.hpp | 9 +++++---- src/threepp/objects/InstancedMesh.cpp | 9 +++++++-- 3 files changed, 23 insertions(+), 16 deletions(-) diff --git a/examples/objects/instancing.cpp b/examples/objects/instancing.cpp index 0d7734a27..f48ff14ff 100644 --- a/examples/objects/instancing.cpp +++ b/examples/objects/instancing.cpp @@ -29,6 +29,8 @@ namespace { } } } + mesh.instanceMatrix()->needsUpdate(); + mesh.instanceColor()->needsUpdate(); } }// namespace @@ -36,6 +38,7 @@ namespace { int main() { int amount = 10; + const int maxAmount = 25; Canvas canvas("Instancing", {{"aa", 4}, {"vsync", false}}); GLRenderer renderer(canvas.size()); @@ -44,7 +47,7 @@ int main() { auto scene = Scene::create(); auto camera = PerspectiveCamera::create(60, canvas.aspect(), 0.1f, 10000); - camera->position.set(float(amount), float(amount), float(amount)); + camera->position.set(float(maxAmount), float(maxAmount), float(maxAmount)); OrbitControls controls{*camera, canvas}; @@ -54,8 +57,9 @@ int main() { auto material = MeshPhongMaterial::create(); auto geometry = IcosahedronGeometry::create(0.5f, 2); - auto mesh = InstancedMesh::create(geometry, material, static_cast(std::pow(amount, 3))); - + auto mesh = InstancedMesh::create(geometry, material, static_cast(std::pow(maxAmount, 3))); + mesh->instanceMatrix()->setUsage(DrawUsage::Dynamic); + mesh->setCount(static_cast(std::pow(amount, 3))); setupInstancedMesh(*mesh, amount); scene->add(mesh); @@ -68,14 +72,11 @@ int main() { ImGui::SetNextWindowSize({width, 0}, 0); ImGui::Begin("Settings"); - ImGui::SliderInt("Amount", &amount, 2, 25); + ImGui::SliderInt("Amount", &amount, 2, maxAmount); if (ImGui::IsItemEdited()) { colorMap.clear(); - mesh->removeFromParent(); - mesh = InstancedMesh::create(geometry, material, static_cast(std::pow(amount, 3))); + mesh->setCount(static_cast(std::pow(amount, 3))); setupInstancedMesh(*mesh, amount); - scene->add(mesh); - camera->position.set(float(amount), float(amount), float(amount)); } ImGui::End(); @@ -93,7 +94,7 @@ int main() { const auto font = *fontLoader.load("data/fonts/helvetiker_regular.typeface.json"); TextGeometry::Options opts(font, 20, 2); - auto handle = Text2D(opts, ""); + auto handle = Text2D(opts); handle.setColor(Color::black); hud.add(handle, HUD::Options() .setNormalizedPosition({0, 1}) @@ -135,7 +136,7 @@ int main() { counter.update(clock.getElapsedTime()); if (it++ % 60 == 0) { - handle.setText("FPS: " + std::to_string(counter.fps), opts); + handle.setText("FPS: " + std::to_string(counter.fps)); hud.needsUpdate(handle); } diff --git a/include/threepp/objects/InstancedMesh.hpp b/include/threepp/objects/InstancedMesh.hpp index 83a075bf4..3882fdf5d 100644 --- a/include/threepp/objects/InstancedMesh.hpp +++ b/include/threepp/objects/InstancedMesh.hpp @@ -12,7 +12,6 @@ namespace threepp { class InstancedMesh: public Mesh { public: - InstancedMesh( std::shared_ptr geometry, std::shared_ptr material, @@ -20,9 +19,11 @@ namespace threepp { [[nodiscard]] size_t count() const; - FloatBufferAttribute* instanceMatrix() const; + void setCount(size_t count); + + [[nodiscard]] FloatBufferAttribute* instanceMatrix() const; - FloatBufferAttribute* instanceColor() const; + [[nodiscard]] FloatBufferAttribute* instanceColor() const; [[nodiscard]] std::string type() const override; @@ -50,9 +51,9 @@ namespace threepp { bool disposed{false}; size_t count_; + size_t maxCount_; std::unique_ptr instanceMatrix_; std::unique_ptr instanceColor_ = nullptr; - }; }// namespace threepp diff --git a/src/threepp/objects/InstancedMesh.cpp b/src/threepp/objects/InstancedMesh.cpp index 96aa7ee43..5fba70d4d 100644 --- a/src/threepp/objects/InstancedMesh.cpp +++ b/src/threepp/objects/InstancedMesh.cpp @@ -22,7 +22,7 @@ InstancedMesh::InstancedMesh( std::shared_ptr material, size_t count) : Mesh(std::move(geometry), std::move(material)), - count_(count), instanceMatrix_(FloatBufferAttribute::create(std::vector(count * 16), 16)) { + count_(count), maxCount_(count), instanceMatrix_(FloatBufferAttribute::create(std::vector(count * 16), 16)) { this->frustumCulled = false; } @@ -32,6 +32,11 @@ size_t InstancedMesh::count() const { return count_; } +void InstancedMesh::setCount(size_t count) { + + count_ = std::min(maxCount_, count); +} + FloatBufferAttribute* InstancedMesh::instanceMatrix() const { return instanceMatrix_.get(); @@ -62,7 +67,7 @@ void InstancedMesh::setColorAt(size_t index, const Color& color) { if (!this->instanceColor_) { - this->instanceColor_ = FloatBufferAttribute ::create(std::vector(count_ * 3), 3); + this->instanceColor_ = FloatBufferAttribute ::create(std::vector(maxCount_ * 3), 3); } color.toArray(this->instanceColor_->array(), index * 3);