Skip to content

Commit

Permalink
Particle system - Part2 (#562)
Browse files Browse the repository at this point in the history
Signed-off-by: Carlos Agüero <[email protected]>

Co-authored-by: Ashton Larkin <[email protected]>
Co-authored-by: Ian Chen <[email protected]>
  • Loading branch information
3 people committed Feb 18, 2021
1 parent 8c13dce commit e77e376
Show file tree
Hide file tree
Showing 14 changed files with 1,201 additions and 15 deletions.
90 changes: 90 additions & 0 deletions examples/worlds/particle_emitter.sdf
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
<?xml version="1.0" ?>

<!--
Launch this example with:
ign gazebo -r particle_emitter.sdf
Try modifying some parameters of the emitter:
To disable the particle emitter:
ign topic -t /model/smoke_generator/particle_emitter/smoke_generator -m ignition.msgs.ParticleEmitter -p 'name: "smoke_generator" pose { position { } orientation { w: 1 } } size { x: 1 y: 1 z: 1 } rate: 10 emitting: false particle_size { x: 1 y: 1 z: 1 } lifetime: 2 material { header { data { key: "double_sided" value: "0" } } ambient { a: 1 } diffuse { r: 0.7 g: 0.7 b: 0.7 a: 1 } specular { a: 1 } emissive { a: 1 } lighting: true pbr { type: METAL albedo_map: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smoke.png" metalness: 0.5 roughness: 0.5 } } min_velocity: 10 max_velocity: 20 color_start { r: 1 g: 1 b: 1 a: 1 } color_end { r: 1 g: 1 b: 1 a: 1 } scale_rate: 10 color_range_image: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smokecolors.png"'
Enable back the particle emitter:
ign topic -t /model/smoke_generator/particle_emitter/smoke_generator -m ignition.msgs.ParticleEmitter -p 'name: "smoke_generator" pose { position { } orientation { w: 1 } } size { x: 1 y: 1 z: 1 } rate: 10 emitting: true particle_size { x: 1 y: 1 z: 1 } lifetime: 2 material { header { data { key: "double_sided" value: "0" } } ambient { a: 1 } diffuse { r: 0.7 g: 0.7 b: 0.7 a: 1 } specular { a: 1 } emissive { a: 1 } lighting: true pbr { type: METAL albedo_map: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smoke.png" metalness: 0.5 roughness: 0.5 } } min_velocity: 10 max_velocity: 20 color_start { r: 1 g: 1 b: 1 a: 1 } color_end { r: 1 g: 1 b: 1 a: 1 } scale_rate: 10 color_range_image: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smokecolors.png"'
Then, change the particle rate:
ign topic -t /model/smoke_generator/particle_emitter/smoke_generator -m ignition.msgs.ParticleEmitter -p 'name: "smoke_generator" pose { position { } orientation { w: 1 } } size { x: 1 y: 1 z: 1 } rate: 100 emitting: true particle_size { x: 1 y: 1 z: 1 } lifetime: 2 material { header { data { key: "double_sided" value: "0" } } ambient { a: 1 } diffuse { r: 0.7 g: 0.7 b: 0.7 a: 1 } specular { a: 1 } emissive { a: 1 } lighting: true pbr { type: METAL albedo_map: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smoke.png" metalness: 0.5 roughness: 0.5 } } min_velocity: 10 max_velocity: 20 color_start { r: 1 g: 1 b: 1 a: 1 } color_end { r: 1 g: 1 b: 1 a: 1 } scale_rate: 10 color_range_image: "/home/caguero/.ignition/fuel/fuel.ignitionrobotics.org/caguero/models/smoke_generator/2/materials/textures/smokecolors.png"'
-->

<sdf version="1.6">
<world name="particle_emitters">

<physics name="1ms" type="ode">
<max_step_size>0.001</max_step_size>
<real_time_factor>1.0</real_time_factor>
</physics>
<plugin
filename="ignition-gazebo-physics-system"
name="ignition::gazebo::systems::Physics">
</plugin>
<plugin
filename="ignition-gazebo-user-commands-system"
name="ignition::gazebo::systems::UserCommands">
</plugin>
<plugin
filename="ignition-gazebo-scene-broadcaster-system"
name="ignition::gazebo::systems::SceneBroadcaster">
</plugin>

<light type="directional" name="sun">
<cast_shadows>true</cast_shadows>
<pose>0 0 10 0 0 0</pose>
<diffuse>1 1 1 1</diffuse>
<specular>0.5 0.5 0.5 1</specular>
<attenuation>
<range>1000</range>
<constant>0.9</constant>
<linear>0.01</linear>
<quadratic>0.001</quadratic>
</attenuation>
<direction>-0.5 0.1 -0.9</direction>
</light>

<model name="ground_plane">
<static>true</static>
<link name="link">
<collision name="collision">
<geometry>
<plane>
<normal>0 0 1</normal>
</plane>
</geometry>
</collision>
<visual name="visual">
<geometry>
<plane>
<normal>0 0 1</normal>
<size>100 100</size>
</plane>
</geometry>
<material>
<ambient>0.8 0.8 0.8 1</ambient>
<diffuse>0.8 0.8 0.8 1</diffuse>
<specular>0.8 0.8 0.8 1</specular>
</material>
</visual>
</link>
</model>

<include>
<uri>https://fuel.ignitionrobotics.org/1.0/caguero/models/smoke_generator</uri>
</include>

</world>
</sdf>


7 changes: 7 additions & 0 deletions include/ignition/gazebo/components/ParticleEmitter.hh
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,13 @@ namespace components
serializers::MsgSerializer>;
IGN_GAZEBO_REGISTER_COMPONENT("ign_gazebo_components.ParticleEmitter",
ParticleEmitter)

/// \brief A component that contains a particle emitter command.
using ParticleEmitterCmd = Component<msgs::ParticleEmitter,
class ParticleEmitterCmdTag,
serializers::MsgSerializer>;
IGN_GAZEBO_REGISTER_COMPONENT("ign_gazebo_components.ParticleEmitterCmd",
ParticleEmitterCmd)
}
}
}
Expand Down
17 changes: 17 additions & 0 deletions include/ignition/gazebo/rendering/SceneManager.hh
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@
#include <ignition/common/Animation.hh>
#include <ignition/common/graphics/Types.hh>

#include <ignition/msgs/particle_emitter.pb.h>

#include <ignition/rendering/RenderTypes.hh>

#include <ignition/gazebo/config.hh>
Expand Down Expand Up @@ -161,6 +163,21 @@ inline namespace IGNITION_GAZEBO_VERSION_NAMESPACE {
public: rendering::LightPtr CreateLight(Entity _id,
const sdf::Light &_light, Entity _parentId);

/// \brief Create a particle emitter.
/// \param[in] _id Unique particle emitter id
/// \param[in] _emitter Particle emitter data
/// \param[in] _parentId Parent id
/// \return Default particle emitter object created
public: rendering::ParticleEmitterPtr CreateParticleEmitter(
Entity _id, const msgs::ParticleEmitter &_emitter, Entity _parentId);

/// \brief Update an existing particle emitter
/// \brief _id Emitter id to update
/// \brief _emitter Data to update the particle emitter
/// \return Particle emitter updated
public: rendering::ParticleEmitterPtr UpdateParticleEmitter(Entity _id,
const msgs::ParticleEmitter &_emitter);

/// \brief Ignition sensors is the one responsible for adding sensors
/// to the scene. Here we just keep track of it and make sure it has
/// the correct parent.
Expand Down
1 change: 1 addition & 0 deletions src/gui/plugins/scene3d/Scene3D.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2752,6 +2752,7 @@ void Scene3D::Update(const UpdateInfo &_info,
msgs::Pose poseMsg = msgs::Convert(renderWindow->CameraPose());
this->dataPtr->cameraPosePub.Publish(poseMsg);
}
this->dataPtr->renderUtil->UpdateECM(_info, _ecm);
this->dataPtr->renderUtil->UpdateFromECM(_info, _ecm);

// check if video recording is enabled and if we need to lock step
Expand Down
83 changes: 83 additions & 0 deletions src/rendering/RenderUtil.cc
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@
#include <ignition/math/Matrix4.hh>
#include <ignition/math/Pose3.hh>

#include <ignition/msgs/Utility.hh>

#include <ignition/rendering.hh>
#include <ignition/rendering/RenderEngine.hh>
#include <ignition/rendering/RenderingIface.hh>
Expand All @@ -60,6 +62,7 @@
#include "ignition/gazebo/components/Model.hh"
#include "ignition/gazebo/components/Name.hh"
#include "ignition/gazebo/components/ParentEntity.hh"
#include "ignition/gazebo/components/ParticleEmitter.hh"
#include "ignition/gazebo/components/Pose.hh"
#include "ignition/gazebo/components/RgbdCamera.hh"
#include "ignition/gazebo/components/Scene.hh"
Expand Down Expand Up @@ -163,6 +166,17 @@ class ignition::gazebo::RenderUtilPrivate
public: std::vector<std::tuple<Entity, sdf::Sensor, Entity>>
newSensors;

/// \brief New particle emitter to be created. The elements in the tuple are:
/// [0] entity id, [1], particle emitter, [2] parent entity id
public: std::vector<std::tuple<Entity, msgs::ParticleEmitter, Entity>>
newParticleEmitters;

/// \brief New particle emitter commands to be requested.
/// The map key and value are: entity id of the particle emitter to
/// update, and particle emitter msg
public: std::unordered_map<Entity, msgs::ParticleEmitter>
newParticleEmittersCmds;

/// \brief Map of ids of entites to be removed and sim iteration when the
/// remove request is received
public: std::unordered_map<Entity, uint64_t> removeEntities;
Expand Down Expand Up @@ -289,6 +303,28 @@ void RenderUtil::UpdateECM(const UpdateInfo &/*_info*/,
EntityComponentManager &_ecm)
{
std::lock_guard<std::mutex> lock(this->dataPtr->updateMutex);

// particle emitters commands
_ecm.Each<components::ParticleEmitterCmd>(
[&](const Entity &_entity,
const components::ParticleEmitterCmd *_emitterCmd) -> bool
{
// store emitter properties and update them in rendering thread
this->dataPtr->newParticleEmittersCmds[_entity] =
_emitterCmd->Data();

// update pose comp here
if (_emitterCmd->Data().has_pose())
{
auto poseComp = _ecm.Component<components::Pose>(_entity);
if (poseComp)
poseComp->Data() = msgs::Convert(_emitterCmd->Data().pose());
}
_ecm.RemoveComponent<components::ParticleEmitterCmd>(_entity);

return true;
});

// Update thermal cameras
_ecm.Each<components::ThermalCamera>(
[&](const Entity &_entity,
Expand Down Expand Up @@ -413,6 +449,9 @@ void RenderUtil::Update()
auto newVisuals = std::move(this->dataPtr->newVisuals);
auto newActors = std::move(this->dataPtr->newActors);
auto newLights = std::move(this->dataPtr->newLights);
auto newParticleEmitters = std::move(this->dataPtr->newParticleEmitters);
auto newParticleEmittersCmds =
std::move(this->dataPtr->newParticleEmittersCmds);
auto removeEntities = std::move(this->dataPtr->removeEntities);
auto entityPoses = std::move(this->dataPtr->entityPoses);
auto trajectoryPoses = std::move(this->dataPtr->trajectoryPoses);
Expand All @@ -428,6 +467,8 @@ void RenderUtil::Update()
this->dataPtr->newVisuals.clear();
this->dataPtr->newActors.clear();
this->dataPtr->newLights.clear();
this->dataPtr->newParticleEmitters.clear();
this->dataPtr->newParticleEmittersCmds.clear();
this->dataPtr->removeEntities.clear();
this->dataPtr->entityPoses.clear();
this->dataPtr->trajectoryPoses.clear();
Expand Down Expand Up @@ -529,6 +570,18 @@ void RenderUtil::Update()
std::get<0>(light), std::get<1>(light), std::get<2>(light));
}

for (const auto &emitter : newParticleEmitters)
{
this->dataPtr->sceneManager.CreateParticleEmitter(
std::get<0>(emitter), std::get<1>(emitter), std::get<2>(emitter));
}

for (const auto &emitterCmd : newParticleEmittersCmds)
{
this->dataPtr->sceneManager.UpdateParticleEmitter(
emitterCmd.first, emitterCmd.second);
}

if (this->dataPtr->enableSensors && this->dataPtr->createSensorCb)
{
for (const auto &sensor : newSensors)
Expand Down Expand Up @@ -1013,6 +1066,17 @@ void RenderUtilPrivate::CreateRenderingEntities(
return true;
});

// particle emitters
_ecm.Each<components::ParticleEmitter, components::ParentEntity>(
[&](const Entity &_entity,
const components::ParticleEmitter *_emitter,
const components::ParentEntity *_parent) -> bool
{
this->newParticleEmitters.push_back(
std::make_tuple(_entity, _emitter->Data(), _parent->Data()));
return true;
});

if (this->enableSensors)
{
// Create cameras
Expand Down Expand Up @@ -1224,6 +1288,17 @@ void RenderUtilPrivate::CreateRenderingEntities(
return true;
});

// particle emitters
_ecm.EachNew<components::ParticleEmitter, components::ParentEntity>(
[&](const Entity &_entity,
const components::ParticleEmitter *_emitter,
const components::ParentEntity *_parent) -> bool
{
this->newParticleEmitters.push_back(
std::make_tuple(_entity, _emitter->Data(), _parent->Data()));
return true;
});

if (this->enableSensors)
{
// Create cameras
Expand Down Expand Up @@ -1465,6 +1540,14 @@ void RenderUtilPrivate::RemoveRenderingEntities(
return true;
});

// particle emitters
_ecm.EachRemoved<components::ParticleEmitter>(
[&](const Entity &_entity, const components::ParticleEmitter *)->bool
{
this->removeEntities[_entity] = _info.iterations;
return true;
});

// cameras
_ecm.EachRemoved<components::Camera>(
[&](const Entity &_entity, const components::Camera *)->bool
Expand Down
Loading

0 comments on commit e77e376

Please sign in to comment.