|
33 | 33 | namespace dynamixel_hardware_interface |
34 | 34 | { |
35 | 35 |
|
| 36 | +// Telemetry interface name constants |
| 37 | +namespace TelemetryInterfaces { |
| 38 | + constexpr const char* TEMPERATURE = "Present Temperature"; |
| 39 | + constexpr const char* VOLTAGE = "Present Input Voltage"; |
| 40 | + constexpr const char* CURRENT = "Present Current"; |
| 41 | + constexpr const char* LOAD = "Present Load"; |
| 42 | +} |
| 43 | + |
36 | 44 | DynamixelHardware::DynamixelHardware() |
37 | 45 | : rclcpp::Node("dynamixel_hardware_interface"), |
38 | 46 | logger_(rclcpp::get_logger("dynamixel_hardware_interface")) |
@@ -364,8 +372,8 @@ hardware_interface::CallbackReturn DynamixelHardware::on_init( |
364 | 372 | dxl_state_pub_uni_ptr_->msg_.dxl_hw_state.resize(num_of_pub_data); |
365 | 373 | dxl_state_pub_uni_ptr_->msg_.torque_state.resize(num_of_pub_data); |
366 | 374 | // Add telemetry arrays |
367 | | - dxl_state_pub_uni_ptr_->msg_.temperature.resize(num_of_pub_data); |
368 | | - dxl_state_pub_uni_ptr_->msg_.voltage.resize(num_of_pub_data); |
| 375 | + dxl_state_pub_uni_ptr_->msg_.present_temperature.resize(num_of_pub_data); |
| 376 | + dxl_state_pub_uni_ptr_->msg_.present_input_voltage.resize(num_of_pub_data); |
369 | 377 | dxl_state_pub_uni_ptr_->msg_.present_current.resize(num_of_pub_data); |
370 | 378 | dxl_state_pub_uni_ptr_->msg_.present_load.resize(num_of_pub_data); |
371 | 379 | dxl_state_pub_uni_ptr_->unlock(); |
@@ -612,6 +620,46 @@ hardware_interface::CallbackReturn DynamixelHardware::stop() |
612 | 620 | return hardware_interface::CallbackReturn::SUCCESS; |
613 | 621 | } |
614 | 622 |
|
| 623 | +struct TelemetryHandler { |
| 624 | + double scale_factor; |
| 625 | + std::function<void(DynamixelHardware*, int16_t, size_t)> setter; |
| 626 | +}; |
| 627 | + |
| 628 | +void DynamixelHardware::processTelemetryInterface( |
| 629 | + const std::string& interface_name, |
| 630 | + double value, |
| 631 | + size_t index) |
| 632 | +{ |
| 633 | + // Static map for constant time lookup - initialized once |
| 634 | + static const std::unordered_map<std::string, TelemetryHandler> telemetry_map = { |
| 635 | + {TelemetryInterfaces::TEMPERATURE, |
| 636 | + {1.0, [](DynamixelHardware* hw, int16_t val, size_t idx) { |
| 637 | + hw->dxl_state_pub_uni_ptr_->msg_.present_temperature.at(idx) = val; |
| 638 | + }}}, |
| 639 | + {TelemetryInterfaces::VOLTAGE, |
| 640 | + {10.0, [](DynamixelHardware* hw, int16_t val, size_t idx) { |
| 641 | + hw->dxl_state_pub_uni_ptr_->msg_.present_input_voltage.at(idx) = val; |
| 642 | + }}}, |
| 643 | + {TelemetryInterfaces::CURRENT, |
| 644 | + {1.0, [](DynamixelHardware* hw, int16_t val, size_t idx) { |
| 645 | + hw->dxl_state_pub_uni_ptr_->msg_.present_current.at(idx) = val; |
| 646 | + }}}, |
| 647 | + {TelemetryInterfaces::LOAD, |
| 648 | + {1.0, [](DynamixelHardware* hw, int16_t val, size_t idx) { |
| 649 | + hw->dxl_state_pub_uni_ptr_->msg_.present_load.at(idx) = val; |
| 650 | + }}} |
| 651 | + }; |
| 652 | + |
| 653 | + auto it = telemetry_map.find(interface_name); |
| 654 | + if (it != telemetry_map.end()) { |
| 655 | + const auto& handler = it->second; |
| 656 | + double scale = handler.scale_factor; |
| 657 | + auto setter = handler.setter; |
| 658 | + int16_t converted_value = static_cast<int16_t>(value * scale); |
| 659 | + setter(this, converted_value, index); |
| 660 | + } |
| 661 | +} |
| 662 | + |
615 | 663 | hardware_interface::return_type DynamixelHardware::read( |
616 | 664 | [[maybe_unused]] const rclcpp::Time & time, const rclcpp::Duration & period) |
617 | 665 | { |
@@ -663,35 +711,17 @@ hardware_interface::return_type DynamixelHardware::read( |
663 | 711 | dxl_state_pub_uni_ptr_->msg_.torque_state.at(index) = ts; |
664 | 712 |
|
665 | 713 | // Initialize telemetry values to 0 |
666 | | - dxl_state_pub_uni_ptr_->msg_.temperature.at(index) = 0; |
667 | | - dxl_state_pub_uni_ptr_->msg_.voltage.at(index) = 0; |
| 714 | + dxl_state_pub_uni_ptr_->msg_.present_temperature.at(index) = 0; |
| 715 | + dxl_state_pub_uni_ptr_->msg_.present_input_voltage.at(index) = 0; |
668 | 716 | dxl_state_pub_uni_ptr_->msg_.present_current.at(index) = 0; |
669 | 717 | dxl_state_pub_uni_ptr_->msg_.present_load.at(index) = 0; |
670 | 718 |
|
671 | 719 | // Extract telemetry values from state interfaces |
672 | 720 | for (size_t i = 0; i < it.interface_name_vec.size(); i++) { |
673 | 721 | const std::string& interface_name = it.interface_name_vec.at(i); |
674 | 722 | double value = *it.value_ptr_vec.at(i); |
675 | | - |
676 | | - if (interface_name == "Present Temperature") { |
677 | | - dxl_state_pub_uni_ptr_->msg_.temperature.at(index) = |
678 | | - static_cast<int16_t>(value); |
679 | | - } |
680 | | - else if (interface_name == "Present Input Voltage") { |
681 | | - dxl_state_pub_uni_ptr_->msg_.voltage.at(index) = |
682 | | - static_cast<int16_t>(value * 10.0); |
683 | | - } |
684 | | - else if (interface_name == "Present Current") { |
685 | | - // Value is already in mA (raw units) from model file |
686 | | - dxl_state_pub_uni_ptr_->msg_.present_current.at(index) = |
687 | | - static_cast<int16_t>(value); |
688 | | - } |
689 | | - else if (interface_name == "Present Load") { |
690 | | - dxl_state_pub_uni_ptr_->msg_.present_load.at(index) = |
691 | | - static_cast<int16_t>(value); |
692 | | - } |
| 723 | + processTelemetryInterface(interface_name, value, index); |
693 | 724 | } |
694 | | - |
695 | 725 | index++; |
696 | 726 | } |
697 | 727 | dxl_state_pub_uni_ptr_->unlockAndPublish(); |
|
0 commit comments