33 intensity(m_intensity),
34 validRange(m_validRange)
40 uint8_t CObservation2DRangeScan::serializeGetVersion()
const {
return 7; }
41 void CObservation2DRangeScan::serializeTo(
45 out << aperture << rightToLeft << maxRange << sensorPose;
48 ASSERT_(validRange.size() == scan.size());
52 out.
WriteBuffer(&m_validRange[0],
sizeof(m_validRange[0]) * N);
62 out << hasIntensity();
66 void CObservation2DRangeScan::truncateByDistanceAndAngle(
67 float min_distance,
float max_angle,
float min_height,
float max_height,
73 unsigned int nPts = scan.
size();
75 auto itValid = m_validRange.begin();
76 for (
auto itScan = m_scan.begin(); itScan != m_scan.end();
77 itScan++, itValid++, k++)
79 float ang = fabs(k * aperture / nPts - aperture * 0.5);
80 float x = (*itScan) * cos(ang);
82 if (min_height != 0 || max_height != 0)
84 ASSERT_(max_height > min_height);
85 if (*itScan < min_distance || ang > max_angle ||
86 x > h - min_height ||
x < h - max_height)
89 else if (*itScan < min_distance || ang > max_angle)
94 void CObservation2DRangeScan::serializeFrom(
105 in >> aperture >> rightToLeft >> maxRange >> sensorPose >>
112 if (N)
in.ReadBufferFixEndianness(&m_scan[0], N);
118 &m_validRange[0],
sizeof(m_validRange[0]) * N);
123 for (i = 0; i < N; i++) m_validRange[i] = scan[i] < maxRange;
156 in >> aperture >> rightToLeft >> maxRange >> sensorPose;
165 in.ReadBufferFixEndianness(&m_scan[0], N);
166 in.ReadBuffer(&m_validRange[0],
sizeof(m_validRange[0]) * N);
169 in.ReadBufferFixEndianness(×tamp, 1);
186 setScanHasIntensity(hasIntensity);
187 if (hasIntensity && N)
189 in.ReadBufferFixEndianness(&m_intensity[0], N);
209 mxArray* CObservation2DRangeScan::writeToMatlab()
const 212 const char* fields[] = {
"class",
226 mexplus::MxArray obs_struct(
227 mexplus::MxArray::Struct(
sizeof(fields) /
sizeof(fields[0]), fields));
229 obs_struct.set(
"class", this->GetRuntimeClass()->className);
231 obs_struct.set(
"ts", this->timestamp);
232 obs_struct.set(
"sensorLabel", this->sensorLabel);
234 obs_struct.set(
"scan", this->m_scan);
238 obs_struct.set(
"validRange", this->m_validRange);
239 obs_struct.set(
"intensity", this->m_intensity);
240 obs_struct.set(
"aperture", this->aperture);
241 obs_struct.set(
"rightToLeft", this->rightToLeft);
242 obs_struct.set(
"maxRange", this->maxRange);
243 obs_struct.set(
"stdError", this->stdError);
244 obs_struct.set(
"beamAperture", this->beamAperture);
245 obs_struct.set(
"deltaPitch", this->deltaPitch);
246 obs_struct.set(
"pose", this->sensorPose);
248 return obs_struct.release();
257 bool CObservation2DRangeScan::isPlanarScan(
const double tolerance)
const 259 return sensorPose.isHorizontal(tolerance);
262 bool CObservation2DRangeScan::hasIntensity()
const {
return m_has_intensity; }
263 void CObservation2DRangeScan::setScanHasIntensity(
bool setHasIntensityFlag)
265 m_has_intensity = setHasIntensityFlag;
271 void CObservation2DRangeScan::filterByExclusionAreas(
274 if (areas.empty())
return;
279 size_t sizeRangeScan = scan.size();
281 ASSERT_(scan.size() == validRange.size());
283 if (!sizeRangeScan)
return;
287 Ang = -0.5 * aperture;
288 dA = aperture / (sizeRangeScan - 1);
292 Ang = +0.5 * aperture;
293 dA = -aperture / (sizeRangeScan - 1);
296 auto valid_it = m_validRange.begin();
297 for (
auto scan_it = m_scan.begin(); scan_it != m_scan.end();
298 scan_it++, valid_it++)
307 const double Lx = *scan_it * cos(Ang);
308 const double Ly = *scan_it * sin(Ang);
313 this->sensorPose.composePoint(Lx, Ly, 0, Gx, Gy, Gz);
316 for (
const auto& area : areas)
318 if (area.first.PointIntoPolygon(Gx, Gy) &&
319 (Gz >= area.second.first && Gz <= area.second.second))
333 void CObservation2DRangeScan::filterByExclusionAreas(
334 const std::vector<mrpt::math::CPolygon>& areas)
336 if (areas.empty())
return;
339 for (
const auto& area : areas)
341 TListExclusionAreasWithRanges::value_type dat;
343 dat.second.first = -std::numeric_limits<double>::max();
344 dat.second.second = std::numeric_limits<double>::max();
348 filterByExclusionAreas(lst);
354 void CObservation2DRangeScan::filterByExclusionAngles(
355 const std::vector<std::pair<double, double>>& angles)
357 if (angles.empty())
return;
362 const size_t sizeRangeScan = scan.size();
364 ASSERT_(scan.size() == validRange.size());
366 if (!sizeRangeScan)
return;
370 Ang = -0.5 * aperture;
371 dA = aperture / (sizeRangeScan - 1);
375 Ang = +0.5 * aperture;
376 dA = -aperture / (sizeRangeScan - 1);
380 for (
const auto& angle : angles)
386 if (ap_idx_ini < 0) ap_idx_ini = 0;
387 if (ap_idx_end < 0) ap_idx_end = 0;
389 if (ap_idx_ini > (
int)sizeRangeScan) ap_idx_ini = sizeRangeScan - 1;
390 if (ap_idx_end > (
int)sizeRangeScan) ap_idx_end = sizeRangeScan - 1;
392 const size_t idx_ini = ap_idx_ini;
393 const size_t idx_end = ap_idx_end;
395 if (idx_end >= idx_ini)
397 for (
size_t i = idx_ini; i <= idx_end; i++) m_validRange[i] =
false;
401 for (
size_t i = 0; i < idx_end; i++) m_validRange[i] =
false;
403 for (
size_t i = idx_ini; i < sizeRangeScan; i++)
404 m_validRange[i] =
false;
431 void CObservation2DRangeScan::internal_buildAuxPointsMap(
432 const void* options)
const 435 throw std::runtime_error(
436 "[CObservation2DRangeScan::buildAuxPointsMap] ERROR: This function " 437 "needs linking against mrpt-maps.\n");
439 (*ptr_internal_build_points_map_from_scan2D)(*
this, m_cachedMap, options);
445 p.nRays = this->scan.size();
446 p.aperture = this->aperture;
447 p.rightToLeft = this->rightToLeft;
453 if (
a.nRays !=
b.nRays)
return a.nRays <
b.nRays;
454 if (
a.aperture !=
b.aperture)
return a.aperture <
b.aperture;
455 if (
a.rightToLeft !=
b.rightToLeft)
return a.rightToLeft;
459 void CObservation2DRangeScan::getDescriptionAsText(std::ostream& o)
const 461 CObservation::getDescriptionAsText(o);
462 o <<
"Homogeneous matrix for the sensor's 3D pose, relative to robot " 464 o << sensorPose.getHomogeneousMatrixVal<
CMatrixDouble44>() << sensorPose
468 "Samples direction: %s\n",
469 (rightToLeft) ?
"Right->Left" :
"Left->Right");
470 o <<
format(
"Points in the scan: %u\n", (
unsigned)scan.size());
471 o <<
format(
"Estimated sensor 'sigma': %f\n", stdError);
473 "Increment in pitch during the scan: %f deg\n",
RAD2DEG(deltaPitch));
476 for (i = 0; i < scan.size(); i++)
477 if (!validRange[i]) inval++;
478 o <<
format(
"Invalid points in the scan: %u\n", (
unsigned)inval);
480 o <<
format(
"Sensor maximum range: %.02f m\n", maxRange);
482 "Sensor field-of-view (\"aperture\"): %.01f deg\n",
RAD2DEG(aperture));
484 o <<
"Raw scan values: [";
485 for (i = 0; i < scan.size(); i++) o <<
format(
"%.03f ", scan[i]);
488 o <<
"Raw valid-scan values: [";
489 for (i = 0; i < validRange.size(); i++)
490 o <<
format(
"%u ", validRange[i] ? 1 : 0);
495 o <<
"Raw intensity values: [";
496 for (i = 0; i < m_intensity.size(); i++)
497 o <<
format(
"%d ", m_intensity[i]);
502 float CObservation2DRangeScan::getScanRange(
const size_t i)
const 508 void CObservation2DRangeScan::setScanRange(
const size_t i,
const float val)
514 int CObservation2DRangeScan::getScanIntensity(
const size_t i)
const 517 return m_intensity[i];
519 void CObservation2DRangeScan::setScanIntensity(
const size_t i,
const int val)
522 m_intensity[i] =
val;
525 bool CObservation2DRangeScan::getScanRangeValidity(
const size_t i)
const 528 return m_validRange[i] != 0;
530 void CObservation2DRangeScan::setScanRangeValidity(
531 const size_t i,
const bool val)
534 m_validRange[i] =
val ? 1 : 0;
537 void CObservation2DRangeScan::resizeScan(
const size_t len)
540 m_intensity.resize(
len);
541 m_validRange.resize(
len);
544 void CObservation2DRangeScan::resizeScanAndAssign(
545 const size_t len,
const float rangeVal,
const bool rangeValidity,
548 m_scan.assign(
len, rangeVal);
549 m_validRange.assign(
len, rangeValidity);
550 m_intensity.assign(
len, rangeIntensity);
553 size_t CObservation2DRangeScan::getScanSize()
const {
return m_scan.size(); }
554 void CObservation2DRangeScan::loadFromVectors(
555 size_t nRays,
const float* scanRanges,
const char* scanValidity)
560 for (
size_t i = 0; i < nRays; i++)
562 m_scan[i] = scanRanges[i];
563 m_validRange[i] = scanValidity[i];
A compile-time fixed-size numeric matrix container.
#define THROW_EXCEPTION(msg)
scan2pts_functor ptr_internal_build_points_map_from_scan2D
#define ASSERT_BELOW_(__A, __B)
#define IMPLEMENTS_SERIALIZABLE(class_name, base, NameSpace)
To be added to all CSerializable-classes implementation files.
static constexpr size_type size()
void WriteBufferFixEndianness(const T *ptr, size_t ElementCount)
Writes a sequence of elemental datatypes, taking care of reordering their bytes from the running arch...
bool operator<(const T2DScanProperties &a, const T2DScanProperties &b)
Order operator, so T2DScanProperties can appear in associative STL containers.
void internal_set_build_points_map_from_scan2D(scan2pts_functor fn)
void WriteBuffer(const void *Buffer, size_t Count)
Writes a block of bytes to the stream from Buffer.
#define MRPT_THROW_UNKNOWN_SERIALIZATION_VERSION(__V)
For use in CSerializable implementations.
#define ASSERT_(f)
Defines an assertion mechanism.
This base provides a set of functions for maths stuff.
Auxiliary struct that holds all the relevant geometry information about a 2D scan.
T wrapTo2Pi(T a)
Modifies the given angle to translate it into the [0,2pi[ range.
This namespace contains representation of robot actions and observations.
#define IMPLEMENTS_MEXPLUS_FROM(complete_type)
Classes for 2D/3D geometry representation, both of single values and probability density distribution...
struct mxArray_tag mxArray
Forward declaration for mxArray (avoid #including as much as possible to speed up compiling) ...
This class is a "CSerializable" wrapper for "CMatrixFloat".
A "CObservation"-derived class that represents a 2D range scan measurement (typically from a laser sc...
Virtual base class for "archives": classes abstracting I/O streams.
A class used to store a 3D pose (a 3D translation + a rotation in 3D).
Declares a class that represents any robot's observation.
std::vector< std::pair< mrpt::math::CPolygon, std::pair< double, double > >> TListExclusionAreasWithRanges
Used in filterByExclusionAreas.
void(*)(const mrpt::obs::CObservation2DRangeScan &obs, mrpt::maps::CMetricMap::Ptr &out_map, const void *insertOps) scan2pts_functor
typedef void(APIENTRYP PFNGLBLENDCOLORPROC)(GLclampf red
GLenum GLsizei GLenum format
unsigned __int32 uint32_t
GLubyte GLubyte GLubyte a