19#ifndef _USE_MATH_DEFINES
20#define _USE_MATH_DEFINES
25#define DEG2RAD M_PI/180.0
31using namespace rp::standalone::rplidar;
43 m_device_status = DEVICE_OK_STANBY;
49 if (this->parseConfiguration(config) ==
false)
55 bool br = config.check(
"GENERAL");
59 if (general_config.
check(
"serial_port") ==
false) {
yCError(
RP2_LIDAR) <<
"Missing serial_port param in GENERAL group";
return false; }
60 if (general_config.
check(
"serial_baudrate") ==
false) {
yCError(
RP2_LIDAR) <<
"Missing serial_baudrate param in GENERAL group";
return false; }
61 if (general_config.
check(
"sample_buffer_life") ==
false) {
yCError(
RP2_LIDAR) <<
"Missing sample_buffer_life param in GENERAL group";
return false; }
63 baudrate = general_config.
find(
"serial_baudrate").
asInt32();
64 m_serialPort = general_config.
find(
"serial_port").
asString();
65 m_buffer_life = general_config.
find(
"sample_buffer_life").
asInt32();
66 if (general_config.
check(
"motor_pwm"))
68 m_pwm_val = general_config.
find(
"motor_pwm").
asInt32();
70 if (general_config.
check(
"thread_period"))
72 double thread_period = general_config.
find(
"thread_period").
asInt32() / 1000.0;
73 this->setPeriod(thread_period);
82 m_drv = RPlidarDriver::CreateDriver(rp::standalone::rplidar::DRIVER_TYPE_SERIALPORT);
89 if (IS_FAIL(m_drv->connect(m_serialPort.c_str(), (_u32)baudrate)))
91 yCError(
RP2_LIDAR) <<
"Error, cannot bind to the specified serial port:", m_serialPort.c_str();
92 RPlidarDriver::DisposeDriver(m_drv);
96 m_info = deviceinfo();
97 yCInfo(
RP2_LIDAR,
"max_dist %f, min_dist %f", m_max_distance, m_min_distance);
99 bool m_inExpressMode=
false;
100 result = m_drv->checkExpressScanSupported(m_inExpressMode);
101 if (result == RESULT_OK && m_inExpressMode==
true)
110 result = m_drv->startMotor();
111 if (result != RESULT_OK)
120 if (m_pwm_val>0 && m_pwm_val<1023)
122 result = m_drv->setMotorPWM(m_pwm_val);
123 if (result != RESULT_OK)
132 yCError(
RP2_LIDAR) <<
"Invalid motor pwm request " << m_pwm_val <<
". It should be a value between 0 and 1023.";
141 bool forceScan =
false;
142 result = m_drv->startScan(forceScan,m_inExpressMode);
144 if (result != RESULT_OK)
152 yCInfo(
RP2_LIDAR,
"max_angle %f, min_angle %f", m_max_angle, m_min_angle);
155 PeriodicThread::start();
161 PeriodicThread::stop();
164 RPlidarDriver::DisposeDriver(
m_drv);
171 std::lock_guard<std::mutex> guard(
m_mutex);
179 std::lock_guard<std::mutex> guard(
m_mutex);
187 std::lock_guard<std::mutex> guard(
m_mutex);
194 std::lock_guard<std::mutex> guard(
m_mutex);
206#define _countof(_Array) (int)(sizeof(_Array) / sizeof (_Array[0]))
219 rplidar_response_measurement_node_t nodes[2048];
222 op_result =
m_drv->grabScanData(nodes, count);
223 if (op_result != RESULT_OK)
226 handleError(op_result);
231 bool is4kmode =
false;
233 if (op_result != RESULT_OK)
239 m_drv->ascendScanData(nodes, count);
241 if (op_result != RESULT_OK)
244 handleError(op_result);
253 m_laser_data[i] = std::numeric_limits<double>::infinity();
261 for (
size_t i = 0; i < count; ++i)
264 double distance = nodes[i].distance_q2 / 4.0f / 1000.0;
265 double angle = (float)((nodes[i].angle_q6_checkbit >> RPLIDAR_RESP_MEASUREMENT_ANGLE_SHIFT) / 64.0f);
266 double quality = nodes[i].sync_quality >> RPLIDAR_RESP_MEASUREMENT_QUALITY_SHIFT;
267 angle = (360 - angle);
280 if (quality == 0 || distance == 0)
282 distance = std::numeric_limits<double>::infinity();
310void RpLidar2::handleError(u_result error)
314 case RESULT_FAIL_BIT:
317 case RESULT_ALREADY_DONE:
320 case RESULT_INVALID_DATA:
323 case RESULT_OPERATION_FAIL:
326 case RESULT_OPERATION_TIMEOUT:
329 case RESULT_OPERATION_STOP:
332 case RESULT_OPERATION_NOT_SUPPORT:
335 case RESULT_FORMAT_NOT_SUPPORT:
338 case RESULT_INSUFFICIENT_MEMORY:
344std::string RpLidar2::deviceinfo()
349 rplidar_response_device_info_t info;
350 std::string serialNumber;
352 result =
m_drv->getDeviceInfo(info);
353 if (result != RESULT_OK)
359 for (
unsigned char i : info.serialnum)
364 return "Firmware Version: " +
std::to_string(info.firmware_version) +
367 "\nSerial Number:" + serialNumber;
rpLidar2: The device driver for the RP2 lidar
bool setScanRate(double rate) override
set the scan rate (scans per seconds)
bool setScanLimits(double min, double max) override
set the scan angular range.
bool close() override
Close the DeviceDriver.
bool threadInit() override
Initialization method.
bool acquireDataFromHW() override final
This method should be implemented by the user, and contain the logic to grab data from the hardware.
bool setDistanceRange(double min, double max) override
set the device detection range.
bool setHorizontalResolution(double step) override
get the angular step between two measurements (if available)
void threadRelease() override
Release method.
void run() override
Loop function.
virtual bool updateLidarData()
This utility method calls in sequence: grabDataFromHW(), updateTimestamp and applyLimitsOnLaserData()...
yarp::sig::Vector m_laser_data
void step()
Call this to "step" the thread rather than starting it.
A base class for nested structures that can be searched.
virtual bool check(const std::string &key) const =0
Check if there exists a property of the given name.
virtual Value & find(const std::string &key) const =0
Gets a value corresponding to a given keyword.
virtual Bottle & findGroup(const std::string &key) const =0
Gets a list corresponding to a given keyword.
virtual std::int32_t asInt32() const
Get 32-bit integer value.
virtual std::string asString() const
Get string value.
#define yCInfo(component,...)
#define yCError(component,...)
#define yCWarning(component,...)
#define yCDebug(component,...)
#define YARP_LOG_COMPONENT(name,...)
std::string to_string(IntegerType x)
The main, catch-all namespace for YARP.
const yarp::os::LogComponent & RP2_LIDAR()