diff --git a/src/experimental/filament/compat/imgui_bridge.cc b/src/experimental/filament/compat/imgui_bridge.cc index 26ca06c2..461ef955 100644 --- a/src/experimental/filament/compat/imgui_bridge.cc +++ b/src/experimental/filament/compat/imgui_bridge.cc @@ -18,31 +18,28 @@ #include #include #include +#include #include #include #include #include #include -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/mesh.h" -#include "experimental/filament/filament/renderable.h" -#include "experimental/filament/filament/scene_view.h" -#include "experimental/filament/filament/texture.h" #include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { using filament::math::float3; using filament::math::mat3f; -ImguiBridge::ImguiBridge(FilamentContext* ctx) : ctx_(ctx) { +ImguiBridge::ImguiBridge(mjrfContext* ctx) : ctx_(ctx) { mjrSceneParams params; mjr_defaultSceneParams(¶ms); params.enable_post_processing = false; params.enable_reflections = false; params.enable_shadows = false; - scene_view_ = std::make_unique(ctx_, params); + scene_ = CreateScene(ctx_, params); } ImguiBridge::~ImguiBridge() { @@ -77,12 +74,12 @@ uintptr_t ImguiBridge::UploadImage(uintptr_t tex_id, const uint8_t* pixels, tex_id = next_tex_id_++; } - std::unique_ptr& texture = textures_[tex_id]; + mjrTexture* texture = GetTexture(tex_id); // If the texture does not exist or the dimensions have changed, we create a // new texture. - if (texture == nullptr || texture->GetWidth() != width || - texture->GetHeight() != height) { + if (texture == nullptr || mjrf_getTextureWidth(texture) != width || + mjrf_getTextureHeight(texture) != height) { mjrTextureConfig config; mjr_defaultTextureConfig(&config); config.width = width; @@ -90,7 +87,9 @@ uintptr_t ImguiBridge::UploadImage(uintptr_t tex_id, const uint8_t* pixels, config.target = mjTEXTURE_2D; config.format = bpp == 4 ? mjPIXEL_FORMAT_RGBA8 : mjPIXEL_FORMAT_RGB8; config.color_space = mjCOLORSPACE_LINEAR; - texture = std::make_unique(ctx_, config); + UniquePtr new_texture = ::mujoco::CreateTexture(ctx_, config); + texture = new_texture.get(); + textures_.insert_or_assign(tex_id, std::move(new_texture)); } // Create a copy of the image to pass it to filament as we don't know the @@ -108,7 +107,7 @@ uintptr_t ImguiBridge::UploadImage(uintptr_t tex_id, const uint8_t* pixels, texture_data.release_callback = callback; std::memcpy(bytes, pixels, num_bytes); - texture->Upload(texture_data); + mjrf_setTextureData(texture, &texture_data); return tex_id; } @@ -126,7 +125,7 @@ void ImguiBridge::CreateTexture(ImTextureData* data) { config.color_space = mjCOLORSPACE_LINEAR; const uintptr_t tex_id = next_tex_id_++; - textures_[tex_id] = std::make_unique(ctx_, config); + textures_.insert_or_assign(tex_id, ::mujoco::CreateTexture(ctx_, config)); data->SetTexID((ImTextureID)tex_id); UpdateTexture(data); } @@ -143,7 +142,7 @@ void ImguiBridge::UpdateTexture(ImTextureData* data) { texture_data.nbytes = data->Width * data->Height * 4; texture_data.user_data = nullptr; texture_data.release_callback = nullptr; - iter->second->Upload(texture_data); + mjrf_setTextureData(iter->second.get(), &texture_data); data->SetStatus(ImTextureStatus_OK); } @@ -156,6 +155,14 @@ void ImguiBridge::DestroyTexture(ImTextureData* data) { } } +mjrTexture* ImguiBridge::GetTexture(uintptr_t tex_id) const { + auto iter = textures_.find(tex_id); + if (iter == textures_.end()) { + return nullptr; + } + return iter->second.get(); +} + void ImguiBridge::Update() { if (!ImGui::GetCurrentContext()) { PrepareRenderables(0); @@ -233,21 +240,22 @@ void ImguiBridge::Update() { data.indices = cmds->IdxBuffer.Data; data.index_type = mjINDEX_TYPE_U16; data.primitive_type = mjMESH_PRIMITIVE_TYPE_TRIANGLES; - meshes_.push_back(std::make_unique(ctx_, data)); + meshes_.push_back(CreateMesh(ctx_, data)); - const Mesh* mesh = meshes_.back().get(); + const mjrMesh* mesh = meshes_.back().get(); int index_offset = 0; for (const ImDrawCmd& command : cmds->CmdBuffer) { const int width = size.x * scale.x; const int height = size.y * scale.y; - auto& renderable = renderables_[renderable_index]; - renderable->SetMesh(mesh, index_offset, command.ElemCount); + UniquePtr& renderable = renderables_[renderable_index]; + mjrf_setRenderableMesh(renderable.get(), mesh, index_offset, + command.ElemCount); mjrMaterialTextures textures; mjr_defaultMaterialTextures(&textures); - textures.color = textures_[command.GetTexID()].get(); + textures.color = GetTexture(command.GetTexID()); mjrMaterialParams properties; mjr_defaultMaterialParams(&properties); @@ -264,9 +272,12 @@ void ImguiBridge::Update() { properties.scissor[2] = width; properties.scissor[3] = height; } - renderable->UpdateMaterial(properties, textures); - renderable->SetTransform( - {float3{0, 0, 0}, mat3f(), float3(scale.x, scale.y, 1.0f)}); + mjrf_setRenderableMaterial(renderable.get(), &properties, &textures); + + const float position[] = {0, 0, 0}; + const float rotation[] = {1, 0, 0, 0, 1, 0, 0, 0, 1}; + const float size[] = {scale.x, scale.y, 1.0f}; + mjrf_setRenderableTransform(renderable.get(), position, rotation, size); index_offset += command.ElemCount; ++renderable_index; @@ -279,15 +290,14 @@ void ImguiBridge::PrepareRenderables(int count) { mjrRenderableParams params; mjr_defaultRenderableParams(¶ms); params.shading_model = mjSHADING_MODEL_UX; - auto& r = - renderables_.emplace_back(std::make_unique(ctx_, params)); - r->SetCastShadows(false); - r->SetReceiveShadows(false); - r->SetBlendOrder(static_cast(renderables_.size())); - scene_view_->AddToScene(r.get()); + params.cast_shadows = false; + params.receive_shadows = false; + params.blend_order = static_cast(renderables_.size() + 1); + auto& renderable = renderables_.emplace_back(CreateRenderable(ctx_, params)); + mjrf_addRenderableToScene(scene_.get(), renderable.get()); } while (renderables_.size() > count) { - scene_view_->RemoveFromScene(renderables_.back().get()); + mjrf_removeRenderableFromScene(scene_.get(), renderables_.back().get()); renderables_.pop_back(); } } diff --git a/src/experimental/filament/compat/imgui_bridge.h b/src/experimental/filament/compat/imgui_bridge.h index 756456fc..ac479292 100644 --- a/src/experimental/filament/compat/imgui_bridge.h +++ b/src/experimental/filament/compat/imgui_bridge.h @@ -16,23 +16,19 @@ #define MUJOCO_SRC_EXPERIMENTAL_FILAMENT_COMPAT_IMGUI_BRIDGE_H_ #include -#include #include #include #include -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/mesh.h" -#include "experimental/filament/filament/renderable.h" -#include "experimental/filament/filament/scene_view.h" -#include "experimental/filament/filament/texture.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { // Creates and manages a SceneView using data read from ImGui. class ImguiBridge { public: - explicit ImguiBridge(FilamentContext* ctx); + explicit ImguiBridge(mjrfContext* ctx); ~ImguiBridge(); // Prepares the Renderables using data from the current ImGui state. This @@ -41,7 +37,7 @@ class ImguiBridge { void Update(); // Returns the managed UX scene. - SceneView* GetSceneView() const { return scene_view_.get(); } + mjrScene* GetScene() const { return scene_.get(); } // Uploads texture to be used with ImGui's Image and ImageButton functions. uintptr_t UploadImage(uintptr_t tex_id, const uint8_t* pixels, int width, @@ -58,12 +54,13 @@ class ImguiBridge { void CreateTexture(ImTextureData* data); void UpdateTexture(ImTextureData* data); void DestroyTexture(ImTextureData* data); + mjrTexture* GetTexture(uintptr_t tex_id) const; - FilamentContext* ctx_ = nullptr; - std::unique_ptr scene_view_; - std::vector> renderables_; - std::vector> meshes_; - std::unordered_map> textures_; + mjrfContext* ctx_ = nullptr; + UniquePtr scene_{nullptr, nullptr}; + std::vector> renderables_; + std::vector> meshes_; + std::unordered_map> textures_; uintptr_t next_tex_id_ = 1; }; diff --git a/src/experimental/filament/compat/imgui_editor.cc b/src/experimental/filament/compat/imgui_editor.cc index dd707914..54105aac 100644 --- a/src/experimental/filament/compat/imgui_editor.cc +++ b/src/experimental/filament/compat/imgui_editor.cc @@ -651,7 +651,7 @@ void DrawLightGui(filament::LightManager& lm, } void DrawGui(SceneBridge* scene_bridge) { - SceneView* scene_view = scene_bridge->GetSceneView(); + SceneView* scene_view = SceneView::downcast(scene_bridge->GetScene()); filament::View* view = scene_view->GetDefaultRenderView(); filament::Engine* engine = scene_view->GetEngine(); filament::LightManager& lm = engine->getLightManager(); diff --git a/src/experimental/filament/compat/mjr_filament_renderer.cc b/src/experimental/filament/compat/mjr_filament_renderer.cc index 831b6636..3046c9f3 100644 --- a/src/experimental/filament/compat/mjr_filament_renderer.cc +++ b/src/experimental/filament/compat/mjr_filament_renderer.cc @@ -27,8 +27,8 @@ #include "experimental/filament/compat/scene_bridge.h" #include "experimental/filament/filament/filament_context.h" #include "experimental/filament/filament/model_util.h" -#include "experimental/filament/filament/render_target.h" #include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { @@ -43,10 +43,10 @@ void MjrFilamentRenderer::Init(const mjModel* model) { mjr_defaultRenderRequest(&render_requests_[0]); mjr_defaultRenderRequest(&render_requests_[1]); - render_requests_[0].scene = scene_bridge_->GetSceneView(); + render_requests_[0].scene = scene_bridge_->GetScene(); render_requests_[0].draw_mode = mjDRAW_MODE_COLOR; - render_requests_[1].scene = imgui_bridge_->GetSceneView(); + render_requests_[1].scene = imgui_bridge_->GetScene(); render_requests_[1].draw_mode = mjDRAW_MODE_COLOR; // The UX camera is a fixed orthographic camera. We only need to change the @@ -135,8 +135,7 @@ void MjrFilamentRenderer::ReadPixels(mjrRect viewport, unsigned char* rgb, config.height = viewport.height; config.color_format = mjPIXEL_FORMAT_RGB8; config.depth_format = mjPIXEL_FORMAT_DEPTH32F; - auto target = - std::make_unique(filament_context_.get(), config); + auto target = CreateRenderTarget(filament_context_.get(), config); render_requests_[0].target = target.get(); render_requests_[1].target = target.get(); @@ -158,11 +157,11 @@ void MjrFilamentRenderer::ReadPixels(mjrRect viewport, unsigned char* rgb, if (depth) { mjrRenderTargetConfig config; mjr_defaultRenderTargetConfig(&config); + config.width = viewport.width; + config.height = viewport.height; config.color_format = mjPIXEL_FORMAT_R32F; config.depth_format = mjPIXEL_FORMAT_DEPTH32F; - auto target = - std::make_unique(filament_context_.get(), config); - target->Prepare(viewport.width, viewport.height); + auto target = CreateRenderTarget(filament_context_.get(), config); render_requests_[0].target = target.get(); render_requests_[1].target = target.get(); diff --git a/src/experimental/filament/compat/model_objects.cc b/src/experimental/filament/compat/model_objects.cc index d87dd4c0..23ced1e0 100644 --- a/src/experimental/filament/compat/model_objects.cc +++ b/src/experimental/filament/compat/model_objects.cc @@ -14,7 +14,6 @@ #include "experimental/filament/compat/model_objects.h" -#include #include #include #include @@ -25,18 +24,16 @@ #include #include -#include #include #include #include #include #include #include "experimental/filament/filament/builtins.h" -#include "experimental/filament/filament/filament_context.h" #include "experimental/filament/filament/math_util.h" -#include "experimental/filament/filament/mesh.h" #include "experimental/filament/filament/model_util.h" -#include "experimental/filament/filament/texture.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { @@ -407,7 +404,7 @@ static std::span GetIndices(const mjModel* model, } } -static void UpdatemjrMeshData(mjrMeshData* data, const mjModel* model, int id, +static void UpdateMeshData(mjrMeshData* data, const mjModel* model, int id, MeshType mesh_type) { if (!IsValidIndex(model, id, mesh_type)) { mju_error("Invalid index %d for type %d", id, mesh_type); @@ -462,7 +459,7 @@ static void UpdatemjrMeshData(mjrMeshData* data, const mjModel* model, int id, data->bounds_max[2] = builder->bounds_max.z; } -void UpdateSkinFlexmjrMeshData(mjrMeshData* data, const mjModel* model, +void UpdateSkinFlexMeshData(mjrMeshData* data, const mjModel* model, const mjvScene* scene, const mjvGeom& geom) { auto positions = GetPositions(model, scene, geom); auto normals = GetNormals(model, scene, geom); @@ -494,21 +491,21 @@ void UpdateSkinFlexmjrMeshData(mjrMeshData* data, const mjModel* model, data->user_data = nullptr; } -ModelObjects::ModelObjects(const mjModel* model, FilamentContext* ctx) +ModelObjects::ModelObjects(const mjModel* model, mjrfContext* ctx) : model_(model), ctx_(ctx) { const int nstack = model->vis.quality.numstacks; const int nslice = model->vis.quality.numslices; const int nquad = model->vis.quality.numquads; - shapes_[kLine] = CreateLine(ctx_); - shapes_[kBox] = CreateBox(ctx_, nquad); - shapes_[kLineBox] = CreateLineBox(ctx_); - shapes_[kCone] = CreateCone(ctx_, nstack, nslice); - shapes_[kDisk] = CreateDisk(ctx_, nslice); - shapes_[kDome] = CreateDome(ctx_, nstack / 2, nslice); - shapes_[kTube] = CreateTube(ctx_, nstack, nslice); - shapes_[kPlane] = CreatePlane(ctx_, nquad); - shapes_[kSphere] = CreateSphere(ctx_, nstack, nslice); - shapes_[kTriangle] = CreateTriangle(ctx_); + shapes_.insert({kLine, CreateLine(ctx_)}); + shapes_.insert({kBox, CreateBox(ctx_, nquad)}); + shapes_.insert({kLineBox, CreateLineBox(ctx_)}); + shapes_.insert({kCone, CreateCone(ctx_, nstack, nslice)}); + shapes_.insert({kDisk, CreateDisk(ctx_, nslice)}); + shapes_.insert({kDome, CreateDome(ctx_, nstack / 2, nslice)}); + shapes_.insert({kTube, CreateTube(ctx_, nstack, nslice)}); + shapes_.insert({kPlane, CreatePlane(ctx_, nquad)}); + shapes_.insert({kSphere, CreateSphere(ctx_, nstack, nslice)}); + shapes_.insert({kTriangle, CreateTriangle(ctx_)}); for (int i = 0; i < model_->ntex; ++i) { UploadTexture(model_, i); @@ -545,14 +542,14 @@ void ModelObjects::UploadMesh(const mjModel* model, int id) { mjrMeshData data; mjr_defaultMeshData(&data); - UpdatemjrMeshData(&data, model, id, MeshType::kNormal); - meshes_[id] = std::make_unique(ctx_, data); + UpdateMeshData(&data, model, id, MeshType::kNormal); + meshes_.insert_or_assign(id, CreateMesh(ctx_, data)); if (model->mesh_graphadr[id] >= 0) { mjrMeshData convex_hull_data; mjr_defaultMeshData(&convex_hull_data); - UpdatemjrMeshData(&convex_hull_data, model, id, MeshType::kConvexHull); - convex_hulls_[id] = std::make_unique(ctx_, convex_hull_data); + UpdateMeshData(&convex_hull_data, model, id, MeshType::kConvexHull); + convex_hulls_.insert_or_assign(id, CreateMesh(ctx_, convex_hull_data)); } } @@ -597,9 +594,9 @@ void ModelObjects::UploadTexture(const mjModel* model, int id) { payload.user_data = nullptr; payload.release_callback = nullptr; - auto texture = std::make_unique(ctx_, config); - texture->Upload(payload); - textures_[id] = std::move(texture); + auto texture = CreateTexture(ctx_, config); + mjrf_setTextureData(texture.get(), &payload); + textures_.insert_or_assign(id, std::move(texture)); } void ModelObjects::UploadHeightField(const mjModel* model, int id) { @@ -614,18 +611,18 @@ void ModelObjects::UploadHeightField(const mjModel* model, int id) { mjrMeshData data; mjr_defaultMeshData(&data); - UpdatemjrMeshData(&data, model, id, MeshType::kHeightField); - height_fields_[id] = std::make_unique(ctx_, data); + UpdateMeshData(&data, model, id, MeshType::kHeightField); + height_fields_.insert_or_assign(id, CreateMesh(ctx_, data)); } void ModelObjects::CreateSkinFlexMesh(const mjvScene* scene, const mjvGeom& geom) { mjrMeshData data; mjr_defaultMeshData(&data); - UpdateSkinFlexmjrMeshData(&data, model_, scene, geom); - dynamic_meshes_[geom.objid] = std::make_unique(ctx_, data); + UpdateSkinFlexMeshData(&data, model_, scene, geom); + dynamic_meshes_.insert_or_assign(geom.objid, CreateMesh(ctx_, data)); } -const Mesh* ModelObjects::GetMeshBuffer(int data_id) const { +const mjrMesh* ModelObjects::GetMeshBuffer(int data_id) const { // As defined by mjv_updateScene: // original mesh: mesh_id * 2 // convex hull: (mesh_id * 2) + 1 @@ -639,29 +636,27 @@ const Mesh* ModelObjects::GetMeshBuffer(int data_id) const { } } -const Mesh* ModelObjects::GetHeightFieldBuffer(int hfield_id) const { +const mjrMesh* ModelObjects::GetHeightFieldBuffer(int hfield_id) const { auto it = height_fields_.find(hfield_id); return it != height_fields_.end() ? it->second.get() : nullptr; } -const Mesh* ModelObjects::GetShapeBuffer(ShapeType shape) const { - if (shape < 0 || shape >= kNumShapes) { - mju_error("Invalid shape type: %d", shape); - } - return shapes_[shape].get(); +const mjrMesh* ModelObjects::GetShapeBuffer(ShapeType shape) const { + auto it = shapes_.find(shape); + return it != shapes_.end() ? it->second.get() : nullptr; } -const Mesh* ModelObjects::GetFlexSkinGeomMesh(int geom_id) const { +const mjrMesh* ModelObjects::GetFlexSkinGeomMesh(int geom_id) const { auto it = dynamic_meshes_.find(geom_id); return it != dynamic_meshes_.end() ? it->second.get() : nullptr; } -const Texture* ModelObjects::GetTexture(int tex_id) const { +const mjrTexture* ModelObjects::GetTexture(int tex_id) const { auto it = textures_.find(tex_id); return it != textures_.end() ? it->second.get() : nullptr; } -const Texture* ModelObjects::GetTexture(int mat_id, int role) const { +const mjrTexture* ModelObjects::GetTexture(int mat_id, int role) const { if (mat_id < 0 || mat_id >= model_->nmat || role < 0 || role >= mjNTEXROLE) { return nullptr; } @@ -669,7 +664,7 @@ const Texture* ModelObjects::GetTexture(int mat_id, int role) const { return GetTexture(tex_id); } -const Texture* ModelObjects::GetSkyboxTexture() const { +const mjrTexture* ModelObjects::GetSkyboxTexture() const { for (auto& iter : textures_) { if (model_->tex_type[iter.first] == mjTEXTURE_SKYBOX) { return iter.second.get(); diff --git a/src/experimental/filament/compat/model_objects.h b/src/experimental/filament/compat/model_objects.h index 2db285f7..0a7f980f 100644 --- a/src/experimental/filament/compat/model_objects.h +++ b/src/experimental/filament/compat/model_objects.h @@ -15,22 +15,19 @@ #ifndef MUJOCO_SRC_EXPERIMENTAL_FILAMENT_COMPAT_MODEL_OBJECTS_H_ #define MUJOCO_SRC_EXPERIMENTAL_FILAMENT_COMPAT_MODEL_OBJECTS_H_ -#include -#include #include #include #include -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/mesh.h" -#include "experimental/filament/filament/texture.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { // Creates and owns various filament objects based on the mjModel. class ModelObjects { public: - ModelObjects(const mjModel* model, FilamentContext* ctx); + ModelObjects(const mjModel* model, mjrfContext* ctx); ~ModelObjects(); enum ShapeType { @@ -56,13 +53,13 @@ class ModelObjects { void CreateSkinFlexMesh(const mjvScene* scene, const mjvGeom& geom); // Returns the cached instance of a filament object created from the mjModel. - const Mesh* GetShapeBuffer(ShapeType shape) const; - const Mesh* GetMeshBuffer(int data_id) const; - const Mesh* GetHeightFieldBuffer(int hfield_id) const; - const Mesh* GetFlexSkinGeomMesh(int geom_id) const; - const Texture* GetTexture(int tex_id) const; - const Texture* GetTexture(int mat_id, int role) const; - const Texture* GetSkyboxTexture() const; + const mjrMesh* GetShapeBuffer(ShapeType shape) const; + const mjrMesh* GetMeshBuffer(int data_id) const; + const mjrMesh* GetHeightFieldBuffer(int hfield_id) const; + const mjrMesh* GetFlexSkinGeomMesh(int geom_id) const; + const mjrTexture* GetTexture(int tex_id) const; + const mjrTexture* GetTexture(int mat_id, int role) const; + const mjrTexture* GetSkyboxTexture() const; float GetSpecularMultiplier() const { return specular_multiplier_; } float GetShininessMultiplier() const { return shininess_multiplier_; } @@ -75,13 +72,13 @@ class ModelObjects { private: const mjModel* model_ = nullptr; - FilamentContext* ctx_ = nullptr; - std::array, kNumShapes> shapes_; - std::unordered_map> meshes_; - std::unordered_map> convex_hulls_; - std::unordered_map> height_fields_; - std::unordered_map> dynamic_meshes_; - std::unordered_map> textures_; + mjrfContext* ctx_ = nullptr; + std::unordered_map> shapes_; + std::unordered_map> meshes_; + std::unordered_map> convex_hulls_; + std::unordered_map> height_fields_; + std::unordered_map> dynamic_meshes_; + std::unordered_map> textures_; float specular_multiplier_ = 0.2f; float shininess_multiplier_ = 0.1f; float emissive_multiplier_ = 0.3f; diff --git a/src/experimental/filament/compat/scene_bridge.cc b/src/experimental/filament/compat/scene_bridge.cc index f47b9316..616cc726 100644 --- a/src/experimental/filament/compat/scene_bridge.cc +++ b/src/experimental/filament/compat/scene_bridge.cc @@ -19,8 +19,6 @@ #include #include -#include -#include #include #include #include @@ -31,16 +29,13 @@ #include "experimental/filament/compat/imgui_bridge.h" #include "experimental/filament/compat/model_objects.h" #include "experimental/filament/compat/scene_geom_util.h" -#include "experimental/filament/filament/color_grading_options.h" #include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/light.h" +#include "experimental/filament/filament/object_manager.h" #include "experimental/filament/filament/math_util.h" #include "experimental/filament/filament/model_util.h" -#include "experimental/filament/filament/object_manager.h" -#include "experimental/filament/filament/renderable.h" #include "experimental/filament/filament/scene_view.h" -#include "experimental/filament/filament/texture.h" #include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { @@ -49,14 +44,14 @@ using filament::math::float4; using filament::math::mat3; using filament::math::mat4; -static std::unique_ptr CreateFallbackIndirectLightTexture( - FilamentContext* ctx, std::string_view filename = "") { +static UniquePtr CreateFallbackIndirectLightTexture( + mjrfContext* ctx, std::string_view filename = "") { if (filename.empty()) { filename = ObjectManager::kDefaultEnvironmentLight; } std::unique_ptr asset = - ctx->GetObjectManager()->LoadAsset(filename); + FilamentContext::downcast(ctx)->GetObjectManager()->LoadAsset(filename); mjrTextureConfig config; mjr_defaultTextureConfig(&config); @@ -66,7 +61,7 @@ static std::unique_ptr CreateFallbackIndirectLightTexture( config.format = mjPIXEL_FORMAT_KTX; config.color_space = mjCOLORSPACE_AUTO; - auto texture = std::make_unique(ctx, config); + auto texture = CreateTexture(ctx, config); mjrTextureData payload; mjr_defaultTextureData(&payload); @@ -77,20 +72,20 @@ static std::unique_ptr CreateFallbackIndirectLightTexture( }; payload.user_data = asset.release(); - texture->Upload(payload); + mjrf_setTextureData(texture.get(), &payload); return texture; } -SceneBridge::SceneBridge(FilamentContext* ctx, const mjModel* model) +SceneBridge::SceneBridge(mjrfContext* ctx, const mjModel* model) : ctx_(ctx) { mjrSceneParams params; mjr_defaultSceneParams(¶ms); params.layer_mask = mjCAT_ALL; params.reflection_layer_mask = mjCAT_DYNAMIC | mjCAT_STATIC; - scene_view_ = std::make_unique(ctx_, params); + scene_ = CreateScene(ctx_, params); model_objects_ = std::make_unique(model, ctx_); - scene_view_->Configure(model); + mjrf_configureSceneFromModel(scene_.get(), model); default_shadow_map_size_ = ReadElement( model, "filament.shadows.map_size", default_shadow_map_size_); @@ -111,15 +106,15 @@ SceneBridge::SceneBridge(FilamentContext* ctx, const mjModel* model) SceneBridge::~SceneBridge() { for (auto& iter : lights_) { - scene_view_->RemoveFromScene(iter.get()); + mjrf_removeLightFromScene(scene_.get(), iter.get()); } lights_.clear(); if (fallback_ibl_) { - scene_view_->RemoveFromScene(fallback_ibl_.get()); + mjrf_removeLightFromScene(scene_.get(), fallback_ibl_.get()); } fallback_ibl_.reset(); for (auto& iter : renderables_) { - scene_view_->RemoveFromScene(iter.get()); + mjrf_removeRenderableFromScene(scene_.get(), iter.get()); } renderables_.clear(); } @@ -127,14 +122,14 @@ SceneBridge::~SceneBridge() { void SceneBridge::SetEnvironmentLight(std::string_view filename, float intensity) { for (auto& light : lights_) { - if (light->GetType() == mjLIGHT_IMAGE) { - scene_view_->RemoveFromScene(light.get()); + if (mjrf_getLightType(light.get()) == mjLIGHT_IMAGE) { + mjrf_removeLightFromScene(scene_.get(), light.get()); light.reset(); break; } } if (fallback_ibl_) { - scene_view_->RemoveFromScene(fallback_ibl_.get()); + mjrf_removeLightFromScene(scene_.get(), fallback_ibl_.get()); fallback_ibl_.reset(); } @@ -145,8 +140,8 @@ void SceneBridge::SetEnvironmentLight(std::string_view filename, params.type = mjLIGHT_IMAGE; params.texture = fallback_ibl_texture_.get(); params.intensity = intensity; - fallback_ibl_ = std::make_unique(ctx_, params); - scene_view_->AddToScene(fallback_ibl_.get()); + fallback_ibl_ = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), fallback_ibl_.get()); } std::optional SceneBridge::ClipFromWorld(const float3& pos) const{ @@ -171,8 +166,8 @@ void SceneBridge::PrepareLights() { params.type = mjLIGHT_IMAGE; params.texture = model_objects_->GetTexture(model->light_texid[i]); params.intensity = model->light_intensity[i]; - auto light_obj = std::make_unique(ctx_, params); - scene_view_->AddToScene(light_obj.get()); + auto light_obj = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), light_obj.get()); lights_.emplace_back(std::move(light_obj)); has_image_based_light = true; } else { @@ -192,8 +187,8 @@ void SceneBridge::PrepareLights() { params.spot_cone_angle = model->light_cutoff[i]; } - auto light_obj = std::make_unique(ctx_, params); - scene_view_->AddToScene(light_obj.get()); + auto light_obj = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), light_obj.get()); lights_.emplace_back(std::move(light_obj)); } } @@ -212,8 +207,8 @@ void SceneBridge::PrepareLights() { params.cast_shadows = 0; params.intensity = 0.0f; params.spot_cone_angle = 90.0f; - auto light_obj = std::make_unique(ctx_, params); - scene_view_->AddToScene(light_obj.get()); + auto light_obj = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), light_obj.get()); lights_.emplace_back(std::move(light_obj)); } @@ -224,8 +219,8 @@ void SceneBridge::PrepareLights() { mjr_defaultLightParams(¶ms); params.type = mjLIGHT_IMAGE; params.intensity = 10.0f; - fallback_ibl_ = std::make_unique(ctx_, params); - scene_view_->AddToScene(fallback_ibl_.get()); + fallback_ibl_ = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), fallback_ibl_.get()); } // There are no "physical" lights in the scene which means we're likely @@ -240,21 +235,22 @@ void SceneBridge::PrepareLights() { params.type = mjLIGHT_IMAGE; params.texture = fallback_ibl_texture_.get(); params.intensity = fallback_environment_light_intensity_; - fallback_ibl_ = std::make_unique(ctx_, params); - scene_view_->AddToScene(fallback_ibl_.get()); + fallback_ibl_ = CreateLight(ctx_, params); + mjrf_addLightToScene(scene_.get(), fallback_ibl_.get()); // Distribute the fallback scene light intensity among the lights. const float intensity = fallback_scene_light_intensity_ / lights_.size(); for (auto& light : lights_) { if (light) { const bool is_headlight = (light == lights_.back()); - light->SetIntensity(is_headlight ? fallback_head_light_intensity_ - : intensity); + mjrf_setLightIntensity(light.get(), + is_headlight ? fallback_head_light_intensity_ + : intensity); } } } - scene_view_->SetSkybox(model_objects_->GetSkyboxTexture()); + mjrf_setSceneSkybox(scene_.get(), model_objects_->GetSkyboxTexture()); } mat4 CalculateClipFromWorld(const mjrRect& viewport, const mjvGLCamera& cam) { @@ -285,16 +281,8 @@ mat4 CalculateClipFromWorld(const mjrRect& viewport, const mjvGLCamera& cam) { } void SceneBridge::Update(const mjrRect& viewport, const mjvScene* scene) { - if (scene->flags[mjRND_SHADOW]) { - scene_view_->EnableShadows(); - } else { - scene_view_->DisableShadows(); - } - if (scene->flags[mjRND_REFLECTION]) { - scene_view_->EnableReflections(); - } else { - scene_view_->DisableReflections(); - } + mjrf_setSceneShadowsEnabled(scene_.get(), scene->flags[mjRND_SHADOW]); + mjrf_setSceneReflectionsEnabled(scene_.get(), scene->flags[mjRND_REFLECTION]); mjtNum hpos[3], hfwd[3]; float headpos[3], gazedir[3]; @@ -308,7 +296,7 @@ void SceneBridge::Update(const mjrRect& viewport, const mjvScene* scene) { // Remove all drawables from previous render and prepare new ones. for (auto& iter : renderables_) { - scene_view_->RemoveFromScene(iter.get()); + mjrf_removeRenderableFromScene(scene_.get(), iter.get()); } renderables_.clear(); for (int i = 0; i < scene->ngeom; ++i) { @@ -324,10 +312,10 @@ void SceneBridge::Update(const mjrRect& viewport, const mjvScene* scene) { model_objects_->CreateSkinFlexMesh(scene, *geom); } - std::unique_ptr renderable = CreateGeomRenderable( + UniquePtr renderable = CreateGeomRenderable( *geom, scene, ctx_, model_objects_.get(), headpos); - scene_view_->AddToScene(renderable.get()); + mjrf_addRenderableToScene(scene_.get(), renderable.get()); renderables_.push_back(std::move(renderable)); } @@ -343,16 +331,15 @@ void SceneBridge::Update(const mjrRect& viewport, const mjvScene* scene) { headpos[2] -= gazedir[2] * 0.05f; // The headlight is always the "back" light. - std::unique_ptr& light = lights_.back(); - light->SetColor(ReadFloat3(scene_light.diffuse)); - light->SetTransform(ReadFloat3(headpos), ReadFloat3(gazedir)); + UniquePtr& light = lights_.back(); + mjrf_setLightColor(light.get(), scene_light.diffuse); + mjrf_setLightTransform(light.get(), headpos, gazedir); continue; } else if (scene_light.id < lights_.size() - 1) { - std::unique_ptr& light = lights_[scene_light.id]; + UniquePtr& light = lights_[scene_light.id]; if (light) { - light->SetColor(ReadFloat3(scene_light.diffuse)); - light->SetTransform(ReadFloat3(scene_light.pos), - ReadFloat3(scene_light.dir)); + mjrf_setLightColor(light.get(), scene_light.diffuse); + mjrf_setLightTransform(light.get(), scene_light.pos, scene_light.dir); } } else { mju_error("Unexpected light id: %d", scene_light.id); @@ -360,11 +347,7 @@ void SceneBridge::Update(const mjrRect& viewport, const mjvScene* scene) { } // Enable/disable the headlight based on whether or not it's in the scene. - if (headlight_enabled) { - lights_.back()->Enable(); - } else { - lights_.back()->Disable(); - } + mjrf_setLightEnabled(lights_.back().get(), headlight_enabled); } void SceneBridge::UploadMesh(const mjModel* model, int id) { diff --git a/src/experimental/filament/compat/scene_bridge.h b/src/experimental/filament/compat/scene_bridge.h index d2d1dfdb..ce6911b6 100644 --- a/src/experimental/filament/compat/scene_bridge.h +++ b/src/experimental/filament/compat/scene_bridge.h @@ -25,18 +25,15 @@ #include #include #include "experimental/filament/compat/model_objects.h" -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/light.h" -#include "experimental/filament/filament/renderable.h" -#include "experimental/filament/filament/scene_view.h" -#include "experimental/filament/filament/texture.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { // Manages all mjModel data and updates a SceneView using an mjvScene. class SceneBridge { public: - SceneBridge(FilamentContext* ctx, const mjModel* model); + SceneBridge(mjrfContext* ctx, const mjModel* model); ~SceneBridge(); // Updates the environment light using the KTX image at the given path. @@ -55,7 +52,7 @@ class SceneBridge { void UploadHeightField(const mjModel* model, int id); // Returns the managed scene. - SceneView* GetSceneView() const { return scene_view_.get(); } + mjrScene* GetScene() const { return scene_.get(); } SceneBridge(const SceneBridge&) = delete; SceneBridge& operator=(const SceneBridge&) = delete; @@ -68,13 +65,13 @@ class SceneBridge { std::optional ClipFromWorld( const filament::math::float3& pos) const; - FilamentContext* ctx_ = nullptr; - std::unique_ptr scene_view_; + mjrfContext* ctx_ = nullptr; std::unique_ptr model_objects_; - std::unique_ptr fallback_ibl_; - std::unique_ptr fallback_ibl_texture_; - std::vector> lights_; - std::vector> renderables_; + UniquePtr scene_{nullptr, nullptr}; + UniquePtr fallback_ibl_{nullptr, nullptr}; + UniquePtr fallback_ibl_texture_{nullptr, nullptr}; + std::vector> lights_; + std::vector> renderables_; filament::math::mat4 clip_from_world_; int default_shadow_map_size_ = 2048; float default_vsm_blur_width_ = 0.0f; diff --git a/src/experimental/filament/compat/scene_geom_util.cc b/src/experimental/filament/compat/scene_geom_util.cc index 6e9939b3..2a131781 100644 --- a/src/experimental/filament/compat/scene_geom_util.cc +++ b/src/experimental/filament/compat/scene_geom_util.cc @@ -16,6 +16,7 @@ #include #include +#include #include #include #include @@ -27,12 +28,10 @@ #include #include #include "experimental/filament/compat/model_objects.h" -#include "experimental/filament/filament/filament_context.h" #include "experimental/filament/filament/math_util.h" -#include "experimental/filament/filament/mesh.h" #include "experimental/filament/filament/renderable.h" -#include "experimental/filament/filament/texture.h" #include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { @@ -64,39 +63,39 @@ static bool IsBehind(const float* headpos, const float* pos, const float* mat) { 0.0f); } -static const Mesh* GetMesh(ModelObjects* model_objs, int data_id) { - const Mesh* mesh = model_objs->GetMeshBuffer(data_id); +static const mjrMesh* GetMesh(ModelObjects* model_objs, int data_id) { + const mjrMesh* mesh = model_objs->GetMeshBuffer(data_id); if (mesh == nullptr) { mju_error("Unknown mesh %d", data_id); } return mesh; } -static const Mesh* GetSkinFlexMesh(ModelObjects* model_objs, int objid) { +static const mjrMesh* GetSkinFlexMesh(ModelObjects* model_objs, int objid) { return model_objs->GetFlexSkinGeomMesh(objid); } -static const Mesh* GetHeightField(ModelObjects* model_objs, int hfield_id) { - const Mesh* mesh = model_objs->GetHeightFieldBuffer(hfield_id); +static const mjrMesh* GetHeightField(ModelObjects* model_objs, int hfield_id) { + const mjrMesh* mesh = model_objs->GetHeightFieldBuffer(hfield_id); if (mesh == nullptr) { mju_error("Unknown height field %d", hfield_id); } return mesh; } -static const Mesh* GetShape(ModelObjects* model_objs, +static const mjrMesh* GetShape(ModelObjects* model_objs, ModelObjects::ShapeType shape_type) { - const Mesh* mesh = model_objs->GetShapeBuffer(shape_type); + const mjrMesh* mesh = model_objs->GetShapeBuffer(shape_type); if (mesh == nullptr) { mju_error("Unknown shape %d", shape_type); } return mesh; } -static void PrepareGeomMeshes(Renderable& renderable, const mjvGeom& geom, +static void PrepareGeomMeshes(mjrRenderable* renderable, const mjvGeom& geom, const mjvScene* scene, ModelObjects* model_objects) { - std::vector meshes; + std::vector meshes; Renderable::GetTransformFn get_transforms; Trs trs = { @@ -334,11 +333,18 @@ static void PrepareGeomMeshes(Renderable& renderable, const mjvGeom& geom, break; } - renderable.SetMeshes(meshes, get_transforms); - renderable.SetTransform(trs); + Renderable::downcast(renderable)->SetMeshes(meshes, get_transforms); + + float position[3]; + std::memcpy(position, &trs.translation[0], 3 * sizeof(float)); + float rotation[9]; + std::memcpy(rotation, &trs.rotation[0], 9 * sizeof(float)); + float size[3]; + std::memcpy(size, &trs.size[0], 3 * sizeof(float)); + mjrf_setRenderableTransform(renderable, position, rotation, size); } -static void UpdateGeomMaterial(Renderable& renderable, const mjvGeom& geom, +static void UpdateGeomMaterial(mjrRenderable* renderable, const mjvGeom& geom, const mjvScene* scene, ModelObjects* model_objs, const float headpos[3]) { const mjModel* model = model_objs->GetModel(); @@ -353,19 +359,19 @@ static void UpdateGeomMaterial(Renderable& renderable, const mjvGeom& geom, if (geom.type == mjGEOM_PLANE) { if (IsBehind(headpos, geom.pos, geom.mat)) { params.color[3] *= 0.3; - renderable.SetReceiveShadows(false); + mjrf_setRenderableReceiveShadows(renderable, false); params.reflective = false; } else { - renderable.SetReceiveShadows(true); + mjrf_setRenderableReceiveShadows(renderable, true); params.reflective = geom.reflectance > 0 && params.color[3] == 1.0f; } } - renderable.SetLayerMask(geom.category); + mjrf_setRenderableLayerMask(renderable, geom.category); if (geom.category == mjCAT_DECOR) { - renderable.SetCastShadows(false); - renderable.SetReceiveShadows(false); + mjrf_setRenderableCastShadows(renderable, false); + mjrf_setRenderableReceiveShadows(renderable, false); } else { - renderable.SetWireframe(scene->flags[mjRND_WIREFRAME]); + mjrf_setRenderableWireframe(renderable, scene->flags[mjRND_WIREFRAME]); } mjrMaterialTextures textures; @@ -420,7 +426,7 @@ static void UpdateGeomMaterial(Renderable& renderable, const mjvGeom& geom, // the programmatic UVs. if (textures.color) { - if (Texture::downcast(textures.color)->GetTarget() == mjTEXTURE_2D) { + if (mjrf_getTextureTarget(textures.color) == mjTEXTURE_2D) { // For 2D textures, `tex_repeat` specifies how many times the texture // image is repeated. The `tex_uniform` flag determines if the repetition // is applied at in object space (false) or in world space (true). @@ -482,11 +488,11 @@ static void UpdateGeomMaterial(Renderable& renderable, const mjvGeom& geom, params.specular *= model_objs->GetSpecularMultiplier(); params.glossiness *= model_objs->GetShininessMultiplier(); - renderable.UpdateMaterial(params, textures); + mjrf_setRenderableMaterial(renderable, ¶ms, &textures); } -std::unique_ptr CreateGeomRenderable( - const mjvGeom& geom, const mjvScene* scene, FilamentContext* ctx, +UniquePtr CreateGeomRenderable( + const mjvGeom& geom, const mjvScene* scene, mjrfContext* ctx, ModelObjects* model_objs, const float headpos[3]) { mjrShadingModel shading_model = mjSHADING_MODEL_SCENE_OBJECT; if (geom.type == mjGEOM_LINE || geom.type == mjGEOM_LINEBOX) { @@ -498,9 +504,9 @@ std::unique_ptr CreateGeomRenderable( mjrRenderableParams params; mjr_defaultRenderableParams(¶ms); params.shading_model = shading_model; - auto renderable = std::make_unique(ctx, params); - PrepareGeomMeshes(*renderable, geom, scene, model_objs); - UpdateGeomMaterial(*renderable, geom, scene, model_objs, headpos); + auto renderable = CreateRenderable(ctx, params); + PrepareGeomMeshes(renderable.get(), geom, scene, model_objs); + UpdateGeomMaterial(renderable.get(), geom, scene, model_objs, headpos); return renderable; } } // namespace mujoco diff --git a/src/experimental/filament/compat/scene_geom_util.h b/src/experimental/filament/compat/scene_geom_util.h index 2a0ee2f5..7823dca3 100644 --- a/src/experimental/filament/compat/scene_geom_util.h +++ b/src/experimental/filament/compat/scene_geom_util.h @@ -15,18 +15,16 @@ #ifndef MUJOCO_SRC_EXPERIMENTAL_FILAMENT_COMPAT_SCENE_GEOM_UTIL_H_ #define MUJOCO_SRC_EXPERIMENTAL_FILAMENT_COMPAT_SCENE_GEOM_UTIL_H_ -#include - #include #include "experimental/filament/compat/model_objects.h" -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/renderable.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { // Creates a Renderable from the given mjvGeom. -std::unique_ptr CreateGeomRenderable( - const mjvGeom& geom, const mjvScene* scene, FilamentContext* ctx, +UniquePtr CreateGeomRenderable( + const mjvGeom& geom, const mjvScene* scene, mjrfContext* ctx, ModelObjects* model_objs, const float headpos[3]); } // namespace mujoco diff --git a/src/experimental/filament/filament/builtins.cc b/src/experimental/filament/filament/builtins.cc index abde82df..90b96baf 100644 --- a/src/experimental/filament/filament/builtins.cc +++ b/src/experimental/filament/filament/builtins.cc @@ -28,6 +28,7 @@ #include "experimental/filament/filament/math_util.h" #include "experimental/filament/filament/mesh.h" #include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" namespace mujoco { @@ -64,15 +65,14 @@ class BuiltinBuilder : public mjrMeshData { virtual ~BuiltinBuilder() = default; template - static std::unique_ptr Create(FilamentContext* ctx, - Args&&... args) { + static UniquePtr Create(mjrfContext* ctx, Args&&... args) { auto builder = new T(std::forward(args)...); mjrMeshData* mesh_data = builder->PrepareMeshData(); mesh_data->release_callback = +[](void* user_data) { delete static_cast(user_data); }; mesh_data->user_data = builder; - return std::make_unique(ctx, *mesh_data); + return CreateMesh(ctx, *mesh_data); } mjrMeshData* PrepareMeshData() { @@ -617,43 +617,43 @@ class DomeBuilder : public BuiltinBuilder { } }; -std::unique_ptr CreateLine(FilamentContext* ctx) { +UniquePtr CreateLine(mjrfContext* ctx) { return BuiltinBuilder::Create(ctx); } -std::unique_ptr CreatePlane(FilamentContext* ctx, int nquad) { +UniquePtr CreatePlane(mjrfContext* ctx, int nquad) { return BuiltinBuilder::Create(ctx, nquad); } -std::unique_ptr CreateTriangle(FilamentContext* ctx) { +UniquePtr CreateTriangle(mjrfContext* ctx) { return BuiltinBuilder::Create(ctx); } -std::unique_ptr CreateBox(FilamentContext* ctx, int nquad) { +UniquePtr CreateBox(mjrfContext* ctx, int nquad) { return BuiltinBuilder::Create(ctx, nquad); } -std::unique_ptr CreateLineBox(FilamentContext* ctx) { +UniquePtr CreateLineBox(mjrfContext* ctx) { return BuiltinBuilder::Create(ctx); } -std::unique_ptr CreateSphere(FilamentContext* ctx, int nstack, int nslice) { +UniquePtr CreateSphere(mjrfContext* ctx, int nstack, int nslice) { return BuiltinBuilder::Create(ctx, nstack, nslice); } -std::unique_ptr CreateTube(FilamentContext* ctx, int nstack, int nslice) { +UniquePtr CreateTube(mjrfContext* ctx, int nstack, int nslice) { return BuiltinBuilder::Create(ctx, nstack, nslice); } -std::unique_ptr CreateDisk(FilamentContext* ctx, int nslice) { +UniquePtr CreateDisk(mjrfContext* ctx, int nslice) { return BuiltinBuilder::Create(ctx, nslice); } -std::unique_ptr CreateDome(FilamentContext* ctx, int nstack, int nslice) { +UniquePtr CreateDome(mjrfContext* ctx, int nstack, int nslice) { return BuiltinBuilder::Create(ctx, nstack, nslice); } -std::unique_ptr CreateCone(FilamentContext* ctx, int nstack, int nslice) { +UniquePtr CreateCone(mjrfContext* ctx, int nstack, int nslice) { return BuiltinBuilder::Create(ctx, nstack, nslice); } diff --git a/src/experimental/filament/filament/builtins.h b/src/experimental/filament/filament/builtins.h index 1727f378..2cf2c591 100644 --- a/src/experimental/filament/filament/builtins.h +++ b/src/experimental/filament/filament/builtins.h @@ -15,24 +15,22 @@ #ifndef MUJOCO_SRC_EXPERIMENTAL_FILAMENT_FILAMENT_BUILTINS_H_ #define MUJOCO_SRC_EXPERIMENTAL_FILAMENT_FILAMENT_BUILTINS_H_ -#include - -#include "experimental/filament/filament/filament_context.h" -#include "experimental/filament/filament/mesh.h" +#include "experimental/filament/render_context_filament.h" +#include "experimental/filament/render_context_filament_cpp.h" // Generates buffers for built-in shapes. namespace mujoco { -std::unique_ptr CreateLine(FilamentContext* ctx); -std::unique_ptr CreatePlane(FilamentContext* ctx, int nquad); -std::unique_ptr CreateTriangle(FilamentContext* ctx); -std::unique_ptr CreateBox(FilamentContext* ctx, int nquad); -std::unique_ptr CreateLineBox(FilamentContext* ctx); -std::unique_ptr CreateSphere(FilamentContext* ctx, int nstack, int nslice); -std::unique_ptr CreateTube(FilamentContext* ctx, int nstack, int nslice); -std::unique_ptr CreateDisk(FilamentContext* ctx, int nslice); -std::unique_ptr CreateDome(FilamentContext* ctx, int nstack, int nslice); -std::unique_ptr CreateCone(FilamentContext* ctx, int nstack, int nslice); +UniquePtr CreateLine(mjrfContext* ctx); +UniquePtr CreatePlane(mjrfContext* ctx, int nquad); +UniquePtr CreateTriangle(mjrfContext* ctx); +UniquePtr CreateBox(mjrfContext* ctx, int nquad); +UniquePtr CreateLineBox(mjrfContext* ctx); +UniquePtr CreateSphere(mjrfContext* ctx, int nstack, int nslice); +UniquePtr CreateTube(mjrfContext* ctx, int nstack, int nslice); +UniquePtr CreateDisk(mjrfContext* ctx, int nslice); +UniquePtr CreateDome(mjrfContext* ctx, int nstack, int nslice); +UniquePtr CreateCone(mjrfContext* ctx, int nstack, int nslice); } // namespace mujoco diff --git a/src/experimental/filament/filament/renderable.cc b/src/experimental/filament/filament/renderable.cc index a620be37..636473f7 100644 --- a/src/experimental/filament/filament/renderable.cc +++ b/src/experimental/filament/filament/renderable.cc @@ -159,7 +159,7 @@ const mat4f& Renderable::GetTransform() const { return transform_; } -void Renderable::SetMeshes(std::span meshes, +void Renderable::SetMeshes(std::span meshes, GetTransformFn get_transform_fn) { if (!parts_.empty()) { mju_error("Cannot set meshes for renderable with multiple parts."); @@ -168,7 +168,7 @@ void Renderable::SetMeshes(std::span meshes, get_transform_fn_ = get_transform_fn; for (int i = 0; i < meshes.size(); ++i) { Part& part = parts_.emplace_back(); - part.mesh = meshes[i]; + part.mesh = Mesh::downcast(meshes[i]); part.elem_offset = 0; part.elem_count = part.mesh->GetFilamentIndexBuffer()->getIndexCount(); InitPartEntity(part); diff --git a/src/experimental/filament/filament/renderable.h b/src/experimental/filament/filament/renderable.h index 6d284e92..e7a405f4 100644 --- a/src/experimental/filament/filament/renderable.h +++ b/src/experimental/filament/filament/renderable.h @@ -70,7 +70,7 @@ class Renderable : public mjrRenderable { // relative to the transform of the renderable itself. This allows users to // construct compound (but rigid) objects from multiple meshes. using GetTransformFn = std::function; - void SetMeshes(std::span meshes, + void SetMeshes(std::span meshes, GetTransformFn get_transform = nullptr); // Sets the layer mask for the managed filament Entities. Layer masks can be