ARGoS 3
A parallel, multi-engine simulator for swarm robotics
colored_blob_omnidirectional_camera_rotzonly_sensor.cpp
Go to the documentation of this file.
2#include <argos3/core/simulator/simulator.h>
3#include <argos3/core/simulator/space/positional_indices/positional_index.h>
4#include <argos3/core/simulator/entity/composable_entity.h>
5#include <argos3/core/simulator/entity/embodied_entity.h>
6#include <argos3/plugins/simulator/entities/led_entity.h>
7#include <argos3/plugins/simulator/entities/omnidirectional_camera_equipped_entity.h>
8#include <argos3/plugins/simulator/media/led_medium.h>
9
10namespace argos {
11
12 /****************************************/
13 /****************************************/
14
16
17 public:
18
22 CEmbodiedEntity& c_embodied_entity,
23 CControllableEntity& c_controllable_entity,
24 bool b_show_rays,
25 Real f_noise_std_dev) :
26 m_tBlobs(t_blobs),
27 m_cOmnicamEntity(c_omnicam_entity),
28 m_cEmbodiedEntity(c_embodied_entity),
29 m_cControllableEntity(c_controllable_entity),
30 m_bShowRays(b_show_rays),
31 m_fDistanceNoiseStdDev(f_noise_std_dev),
32 m_pcRNG(nullptr) {
33 m_pcRootSensingEntity = &m_cEmbodiedEntity.GetParent();
34 if(m_fDistanceNoiseStdDev > 0.0f) {
35 m_pcRNG = CRandom::CreateRNG("argos");
36 }
37 }
39 while(! m_tBlobs.empty()) {
40 delete m_tBlobs.back();
41 m_tBlobs.pop_back();
42 }
43 }
44
45 virtual bool operator()(CLEDEntity& c_led) {
46 /* Process this LED only if it's lit */
47 if(c_led.GetColor() != CColor::BLACK) {
48 if(c_led.HasParent()) {
49 /* Filter out the LEDs belonging to the sensing entity by checking if they share the same parent entity */
50 m_pcRootOfLEDEntity = &c_led.GetParent();
51 while(m_pcRootOfLEDEntity->HasParent()) m_pcRootOfLEDEntity = &m_pcRootOfLEDEntity->GetParent();
52 if(m_pcRootSensingEntity == m_pcRootOfLEDEntity) {
53 return true;
54 }
55 }
56 /* If we are here, it's because the LED must be processed */
57 m_cOcclusionCheckRay.SetEnd(c_led.GetPosition());
58 m_cLEDRelativePos = c_led.GetPosition();
59 m_cLEDRelativePos -= m_cCameraPos;
60 m_cLEDRelativePosXY.Set(m_cLEDRelativePos.GetX(),
61 m_cLEDRelativePos.GetY());
62 if(Abs(m_cLEDRelativePos.GetX()) < m_fGroundHalfRange &&
63 Abs(m_cLEDRelativePos.GetY()) < m_fGroundHalfRange &&
64 m_cLEDRelativePos.GetZ() < m_cCameraPos.GetZ() &&
66 m_cOcclusionCheckRay,
67 m_cEmbodiedEntity)) {
68 /* If noise was setup, add it */
69 if(m_fDistanceNoiseStdDev > 0.0f) {
70 m_cLEDRelativePosXY += CVector2(
71 m_cLEDRelativePosXY.Length() * m_pcRNG->Gaussian(m_fDistanceNoiseStdDev),
72 m_pcRNG->Uniform(CRadians::UNSIGNED_RANGE));
73 }
75 c_led.GetColor(),
76 NormalizedDifference(m_cLEDRelativePosXY.Angle(), m_cCameraOrient),
77 m_cLEDRelativePosXY.Length() * 100.0f));
78 if(m_bShowRays) {
79 m_cControllableEntity.AddCheckedRay(false, CRay3(m_cCameraPos, c_led.GetPosition()));
80 }
81 }
82 }
83 return true;
84 }
85
86 void Setup(Real f_ground_half_range) {
87 while(! m_tBlobs.empty()) {
88 delete m_tBlobs.back();
89 m_tBlobs.pop_back();
90 }
91 m_fGroundHalfRange = f_ground_half_range;
92 m_cEmbodiedEntity.GetOriginAnchor().Orientation.ToEulerAngles(m_cCameraOrient, m_cTmp1, m_cTmp2);
93 m_cCameraPos = m_cEmbodiedEntity.GetOriginAnchor().Position;
94 m_cCameraPos += m_cOmnicamEntity.GetOffset();
95 m_cOcclusionCheckRay.SetStart(m_cCameraPos);
96 }
97
98 private:
99
101 COmnidirectionalCameraEquippedEntity& m_cOmnicamEntity;
102 CEmbodiedEntity& m_cEmbodiedEntity;
103 CControllableEntity& m_cControllableEntity;
104 Real m_fGroundHalfRange;
105 bool m_bShowRays;
106 CEntity* m_pcRootSensingEntity;
107 CEntity* m_pcRootOfLEDEntity;
108 CVector3 m_cCameraPos;
109 CRadians m_cCameraOrient;
110 CRadians m_cTmp1, m_cTmp2;
111 CVector3 m_cLEDRelativePos;
112 CVector2 m_cLEDRelativePosXY;
113 SEmbodiedEntityIntersectionItem m_sIntersectionItem;
114 CRay3 m_cOcclusionCheckRay;
115 Real m_fDistanceNoiseStdDev;
116 CRandom::CRNG* m_pcRNG;
117 };
118
119 /****************************************/
120 /****************************************/
121
130
131 /****************************************/
132 /****************************************/
133
136
137 /****************************************/
138 /****************************************/
139
141 /* Get omndirectional camera equipped entity */
142 m_pcOmnicamEntity = &(c_entity.GetComponent<COmnidirectionalCameraEquippedEntity>("omnidirectional_camera"));
143 /* Get controllable entity */
144 m_pcControllableEntity = &(c_entity.GetComponent<CControllableEntity>("controller"));
145 /* Get embodied entity */
146 m_pcEmbodiedEntity = &(c_entity.GetComponent<CEmbodiedEntity>("body"));
147 }
148
149 /****************************************/
150 /****************************************/
151
153 try {
154 /* Parent class init */
156 /* Show rays? */
158 /* Parse noise */
159 Real fDistanceNoiseStdDev = 0;
160 GetNodeAttributeOrDefault(t_tree, "noise_std_dev", fDistanceNoiseStdDev, fDistanceNoiseStdDev);
161 /* Get LED medium from id specified in the XML */
162 std::string strMedium;
163 GetNodeAttribute(t_tree, "medium", strMedium);
164 m_pcLEDIndex = &(CSimulator::GetInstance().GetMedium<CLEDMedium>(strMedium).GetIndex());
165 /* Create check operation */
167 m_sReadings.BlobList,
172 fDistanceNoiseStdDev);
173 }
174 catch(CARGoSException& ex) {
175 THROW_ARGOSEXCEPTION_NESTED("Error initializing the colored blob omnidirectional camera rotzonly sensor", ex);
176 }
177 /* sensor is disabled by default */
178 Disable();
179 }
180
181 /****************************************/
182 /****************************************/
183
185 /* sensor is disabled--nothing to do */
186 if (IsDisabled()) {
187 return;
188 }
189
190 /* Increase data counter */
191 ++m_sReadings.Counter;
192 /* Calculate range on the ground */
193 CVector3 cCameraPos = m_pcOmnicamEntity->GetOffset();
194 cCameraPos += m_pcEmbodiedEntity->GetOriginAnchor().Position;
195 Real fGroundHalfRange = cCameraPos.GetZ() * Tan(m_pcOmnicamEntity->GetAperture());
196 /* Prepare the operation */
197 m_pcOperation->Setup(fGroundHalfRange);
198 /* Go through LED entities in box range */
199 m_pcLEDIndex->ForEntitiesInBoxRange(
200 CVector3(cCameraPos.GetX(),
201 cCameraPos.GetY(),
202 cCameraPos.GetZ() * 0.5f),
203 CVector3(fGroundHalfRange, fGroundHalfRange, cCameraPos.GetZ() * 0.5f),
205 }
206
207 /****************************************/
208 /****************************************/
209
211 m_sReadings.Counter = 0;
212 m_sReadings.BlobList.clear();
213 }
214
215 /****************************************/
216 /****************************************/
217
221
222 /****************************************/
223 /****************************************/
224
229
230 /****************************************/
231 /****************************************/
232
237
238 /****************************************/
239 /****************************************/
240
242 "colored_blob_omnidirectional_camera", "rot_z_only",
243 "Carlo Pinciroli [ilpincy@gmail.com]",
244 "1.0",
245
246 "A generic omnidirectional camera sensor to detect colored blobs.",
247 "This sensor accesses an omnidirectional camera that detects colored blobs. The\n"
248 "sensor returns a list of blobs, each defined by a color and a position with\n"
249 "respect to the robot reference point on the ground. In controllers, you must\n"
250 "include the ci_colored_blob_omnidirectional_camera_sensor.h header.\n\n"
251
252 "This sensor is disabled by default, and must be enabled before it can be\n"
253 "used.\n\n"
254
255 "REQUIRED XML CONFIGURATION\n\n"
256
257 " <controllers>\n"
258 " ...\n"
259 " <my_controller ...>\n"
260 " ...\n"
261 " <sensors>\n"
262 " ...\n"
263 " <colored_blob_omnidirectional_camera implementation=\"rot_z_only\"\n"
264 " medium=\"leds\" />\n"
265 " ...\n"
266 " </sensors>\n"
267 " ...\n"
268 " </my_controller>\n"
269 " ...\n"
270 " </controllers>\n\n"
271
272 "The 'medium' attribute must be set to the id of the leds medium declared in the\n"
273 "<media> section.\n\n"
274
275 "OPTIONAL XML CONFIGURATION\n\n"
276
277 "It is possible to draw the rays shot by the camera sensor in the OpenGL\n"
278 "visualization. This can be useful for sensor debugging but also to understand\n"
279 "what's wrong in your controller. In OpenGL, the rays are drawn in cyan when\n"
280 "they are not obstructed and in purple when they are. In case a ray is\n"
281 "obstructed, a black dot is drawn where the intersection occurred.\n"
282 "To turn this functionality on, add the attribute \"show_rays\" as in this\n"
283 "example:\n\n"
284
285 " <controllers>\n"
286 " ...\n"
287 " <my_controller ...>\n"
288 " ...\n"
289 " <sensors>\n"
290 " ...\n"
291 " <colored_blob_omnidirectional_camera implementation=\"rot_z_only\"\n"
292 " medium=\"leds\" />\n"
293 " show_rays=\"true\" />\n"
294 " ...\n"
295 " </sensors>\n"
296 " ...\n"
297 " </my_controller>\n"
298 " ...\n"
299 " </controllers>\n\n"
300
301 "It is possible to add uniform noise to the blobs, thus matching the\n"
302 "characteristics of a real robot better. This can be done with the attribute\n"
303 "\"noise_std_dev\".\n\n"
304 " <controllers>\n"
305 " ...\n"
306 " <my_controller ...>\n"
307 " ...\n"
308 " <sensors>\n"
309 " ...\n"
310 " <colored_blob_omnidirectional_camera implementation=\"rot_z_only\"\n"
311 " medium=\"leds\" />\n"
312 " noise_std_dev=\"0.1\" />\n"
313 " ...\n"
314 " </sensors>\n"
315 " ...\n"
316 " </my_controller>\n"
317 " ...\n"
318 " </controllers>\n\n"
319
320 "OPTIMIZATION HINTS\n\n"
321
322 "1. For small swarms, enabling the sensor (and therefore causing ARGoS to\n"
323 " update its readings each timestep) unconditionally does not impact performance too\n"
324 " much. For large swarms, it can impact performance, and selectively\n"
325 " enabling/disabling the sensor according to when each individual robot needs it\n"
326 " (e.g., only when it is looking for an LED equipped entity) can increase performance\n"
327 " by only requiring ARGoS to update the readings on timesteps they will be used.\n",
328
329 "Usable"
330 );
331
332}
float Real
Collects all ARGoS code.
Definition datatypes.h:39
#define THROW_ARGOSEXCEPTION_NESTED(message, nested)
This macro throws an ARGoS exception with the passed message and nesting the passed exception.
#define REGISTER_SENSOR(CLASSNAME, LABEL, IMPLEMENTATION, AUTHOR, VERSION, BRIEF_DESCRIPTION, LONG_DESCRIPTION, STATUS)
Registers a new sensor model inside ARGoS.
Definition sensor.h:63
The namespace containing all the ARGoS related code.
Definition ci_actuator.h:12
bool GetClosestEmbodiedEntityIntersectedByRay(SEmbodiedEntityIntersectionItem &s_item, const CRay3 &c_ray)
Returns the closest intersection with an embodied entity to the ray start.
void GetNodeAttributeOrDefault(TConfigurationNode &t_node, const std::string &str_attribute, T &t_buffer, const T &t_default)
Returns the value of a node's attribute, or the passed default value.
CRadians NormalizedDifference(const CRadians &c_angle1, const CRadians &c_angle2)
Calculates the normalized difference between the given angles.
Definition angles.h:510
ticpp::Element TConfigurationNode
The ARGoS configuration XML node.
Real Tan(const CRadians &c_radians)
Computes the tangent of the passed value in radians.
Definition angles.h:604
T Abs(const T &t_v)
Returns the absolute value of the passed argument.
Definition general.h:25
void GetNodeAttribute(TConfigurationNode &t_node, const std::string &str_attribute, T &t_buffer)
Returns the value of a node's attribute.
virtual void Enable()
Enables updating of sensor information in the event loop.
Definition ci_sensor.h:78
virtual void Init(TConfigurationNode &t_node)
Initializes the sensor from the XML configuration tree.
Definition ci_sensor.h:54
bool IsDisabled() const
Definition ci_sensor.h:86
virtual void Disable()
Disables updating of sensor information in the event loop.
Definition ci_sensor.h:83
Basic class for an entity that contains other entities.
CEntity & GetComponent(const std::string &str_component)
Returns the component with the passed string label.
An entity that contains a pointer to the user-defined controller.
This entity is a link to a body in the physics engine.
The basic entity type.
Definition entity.h:90
CComposableEntity & GetParent()
Returns this entity's parent.
Definition entity.cpp:91
bool HasParent() const
Returns true if this entity has a parent.
Definition entity.h:171
const CVector3 & GetPosition() const
static CSimulator & GetInstance()
Returns the instance to the CSimulator class.
Definition simulator.cpp:78
T & GetMedium(const std::string &str_id)
Returns a reference to a medium.
Definition simulator.h:129
A data structure that contains positional entities.
The exception that wraps all errors in ARGoS.
static CColor BLACK
Definition color.h:29
It defines the basic type CRadians, used to store an angle value in radians.
Definition angles.h:42
static const CRange< CRadians > UNSIGNED_RANGE
The unsigned normalization range [0:TWO_PI].
Definition angles.h:274
static CRNG * CreateRNG(const std::string &str_category)
Creates a new RNG inside the given category.
Definition rng.cpp:347
The RNG.
Definition rng.h:90
A 2D vector class.
Definition vector2.h:27
A 3D vector class.
Definition vector3.h:31
Real GetX() const
Returns the x coordinate of this vector.
Definition vector3.h:105
void Set(const Real f_x, const Real f_y, const Real f_z)
Sets the vector contents from Cartesian coordinates.
Definition vector3.h:155
Real GetY() const
Returns the y coordinate of this vector.
Definition vector3.h:121
Real GetZ() const
Returns the z coordinate of this vector.
Definition vector3.h:137
std::vector< SBlob * > TBlobList
Vector of pointers to colored blobs.
An SBlob represents a generic colored 2D segment in the image.
COmnidirectionalCameraLEDCheckOperation(CCI_ColoredBlobOmnidirectionalCameraSensor::TBlobList &t_blobs, COmnidirectionalCameraEquippedEntity &c_omnicam_entity, CEmbodiedEntity &c_embodied_entity, CControllableEntity &c_controllable_entity, bool b_show_rays, Real f_noise_std_dev)
virtual void Disable()
Disables updating of sensor information in the event loop.
virtual void Reset()
Resets the sensor to the state it had just after Init().
virtual void Enable()
Enables updating of sensor information in the event loop.
virtual void Update()
Updates the state of the entity associated to this sensor, if the sensor is currently enabled.
virtual void SetRobot(CComposableEntity &c_entity)
Sets the entity associated to this sensor.
virtual void Init(TConfigurationNode &t_tree)
Initializes the sensor from the XML configuration tree.
const CColor & GetColor() const
Returns the current color of the LED.
Definition led_entity.h:58