diff --git a/rmcs_ws/src/rmcs_auto_aim_v2 b/rmcs_ws/src/rmcs_auto_aim_v2
index 27ec7806..49f0fa7a 160000
--- a/rmcs_ws/src/rmcs_auto_aim_v2
+++ b/rmcs_ws/src/rmcs_auto_aim_v2
@@ -1 +1 @@
-Subproject commit 27ec780607ab84a3dd7c8a0ca7ecd974bda0bc6f
+Subproject commit 49f0fa7aa3d016dc9e58c5c5a6fb9ed7f6ea7c6f
diff --git a/rmcs_ws/src/rmcs_bringup/config/auto_aim_test.yaml b/rmcs_ws/src/rmcs_bringup/config/auto_aim_test.yaml
index b110fcfd..566d2d90 100644
--- a/rmcs_ws/src/rmcs_bringup/config/auto_aim_test.yaml
+++ b/rmcs_ws/src/rmcs_bringup/config/auto_aim_test.yaml
@@ -2,14 +2,14 @@ rmcs_executor:
ros__parameters:
update_rate: 1000.0
components:
- # - rmcs::AutoAimPlayerComponent -> auto_aim_player
- - rmcs::AutoAimVideoPlayerComponent -> auto_aim_video_player
+ - rmcs::AutoAimPlayerComponent -> auto_aim_player
+ # - rmcs::AutoAimVideoPlayerComponent -> auto_aim_video_player
# - rmcs::AutoAimRecorderComponent -> auto_aim_recorder
- rmcs::AutoAimComponent -> auto_aim_component
auto_aim_player:
ros__parameters:
- input_path: "/workspaces/data/autoaim/自家大符/"
+ input_path: "/workspaces/data/autoaim/robot/blue_fast_track/"
loop_play: true
auto_aim_video_player:
@@ -25,11 +25,13 @@ auto_aim_recorder:
flush_every_n_frames: 64
max_duration_seconds: 0
max_videos_size_gb: 0.0
+ auto_record: false
auto_aim_component:
ros__parameters:
dangerous_fallback: "red"
manual_shoot: false
+ enable_rune: true
camera_translation: [0., 0., 0.]
fire_control:
diff --git a/rmcs_ws/src/rmcs_bringup/config/navigation_test.yaml b/rmcs_ws/src/rmcs_bringup/config/navigation_test.yaml
index 240f88c0..3b250cdd 100644
--- a/rmcs_ws/src/rmcs_bringup/config/navigation_test.yaml
+++ b/rmcs_ws/src/rmcs_bringup/config/navigation_test.yaml
@@ -7,5 +7,5 @@ rmcs_executor:
rmcs_navigation:
ros__parameters:
command_vel_name: "/cmd_vel"
- endpoint: "train"
+ endpoint: "mock"
enable_goal_topic_forward: true
diff --git a/rmcs_ws/src/rmcs_bringup/config/sentry.yaml b/rmcs_ws/src/rmcs_bringup/config/sentry.yaml
index de6f840c..a4b85a3a 100644
--- a/rmcs_ws/src/rmcs_bringup/config/sentry.yaml
+++ b/rmcs_ws/src/rmcs_bringup/config/sentry.yaml
@@ -7,7 +7,7 @@ rmcs_executor:
- rmcs_core::referee::Status -> referee_status
- rmcs_core::referee::Command -> referee_command
- rmcs_core::referee::command::Interaction -> referee_interaction
- # - rmcs_core::referee::command::interaction::SentryDecision -> referee_sentry_decision
+ - rmcs_core::referee::command::interaction::SentryDecision -> referee_sentry_decision
- rmcs_core::referee::command::interaction::Ui -> referee_ui
- rmcs_core::controller::gimbal::EccentricDualYaw -> gimbal_controller
@@ -24,9 +24,9 @@ rmcs_executor:
# - rmcs::navigation::Navigation -> rmcs_navigation
- # - rmcs::AutoAimRecorderComponent -> auto_aim_recorder
- # - rmcs::AutoAimCapturerComponent -> auto_aim_capturer
- # - rmcs::AutoAimComponent -> auto_aim_component
+ - rmcs::AutoAimRecorderComponent -> auto_aim_recorder
+ - rmcs::AutoAimCapturerComponent -> auto_aim_capturer
+ - rmcs::AutoAimComponent -> auto_aim_component
# - rmcs_core::broadcaster::ValueBroadcaster -> value_broadcaster
# - rmcs_core::broadcaster::TfBroadcaster -> tf_broadcaster
@@ -34,7 +34,7 @@ rmcs_executor:
rmcs_navigation:
ros__parameters:
command_vel_name: "/cmd_vel"
- endpoint: "otaku"
+ endpoint: "train"
enable_goal_topic_forward: true
auto_aim_capturer:
@@ -53,8 +53,9 @@ auto_aim_recorder:
output_path: "/tmp/autoaim/records"
queue_depth: 16
flush_every_n_frames: 64
- max_duration_seconds: 0
- max_videos_size_gb: 0.0
+ max_duration_seconds: 300
+ max_videos_size_gb: 100.0
+ auto_record: false
auto_aim_component:
ros__parameters:
@@ -63,10 +64,10 @@ auto_aim_component:
camera_translation: [0.07128, 0.0, 0.0481]
fire_control:
bullet_speed: 22.5
- shoot_delay: 0.1
- offset_yaw: -0.5
- offset_pitch: +1.0
- attack_window: 120.0
+ shoot_delay: 0.02
+ offset_yaw: -0.3
+ offset_pitch: +0.9
+ attack_window: 80.0
degraded_angle_speed: 12.0
window_hysteresis: 0.2
attack_preaim: false
diff --git a/rmcs_ws/src/rmcs_core/plugins.xml b/rmcs_ws/src/rmcs_core/plugins.xml
index a9845583..a066759a 100644
--- a/rmcs_ws/src/rmcs_core/plugins.xml
+++ b/rmcs_ws/src/rmcs_core/plugins.xml
@@ -54,6 +54,7 @@
+
diff --git a/rmcs_ws/src/rmcs_core/src/controller/chassis/steering_wheel_controller.cpp b/rmcs_ws/src/rmcs_core/src/controller/chassis/steering_wheel_controller.cpp
index 83af9894..ef06236e 100644
--- a/rmcs_ws/src/rmcs_core/src/controller/chassis/steering_wheel_controller.cpp
+++ b/rmcs_ws/src/rmcs_core/src/controller/chassis/steering_wheel_controller.cpp
@@ -35,13 +35,28 @@ class SteeringWheelController
, no_load_power_(get_parameter("no_load_power").as_double())
, control_acceleration_filter_(5.0, 1000.0)
, chassis_velocity_expected_(Eigen::Vector3d::Zero())
- , chassis_translational_velocity_pid_(5.0, 0.0, 1.0)
- , chassis_angular_velocity_pid_(5.0, 0.0, 1.0)
+ , chassis_translational_velocity_pid_(
+ get_parameter("chassis_translation_kp").as_double(),
+ get_parameter("chassis_translation_ki").as_double(),
+ get_parameter("chassis_translation_kd").as_double())
+ , chassis_angular_velocity_pid_(
+ get_parameter("chassis_angular_velocity_kp").as_double(),
+ get_parameter("chassis_angular_velocity_ki").as_double(),
+ get_parameter("chassis_angular_velocity_kd").as_double())
, cos_varphi_(1, 0, -1, 0) // 0, pi/2, pi, 3pi/2
, sin_varphi_(0, 1, 0, -1)
- , steering_velocity_pid_(0.15, 0.0, 0.0)
- , steering_angle_pid_(30.0, 0.0, 0.0)
- , wheel_velocity_pid_(0.6, 0.0, 0.0) {
+ , steering_velocity_pid_(
+ get_parameter("steering_velocity_kp").as_double(),
+ get_parameter("steering_velocity_ki").as_double(),
+ get_parameter("steering_velocity_kd").as_double())
+ , steering_angle_pid_(
+ get_parameter("steering_angle_kp").as_double(),
+ get_parameter("steering_angle_ki").as_double(),
+ get_parameter("steering_angle_kd").as_double())
+ , wheel_velocity_pid_(
+ get_parameter("wheel_velocity_kp").as_double(),
+ get_parameter("wheel_velocity_ki").as_double(),
+ get_parameter("wheel_velocity_kd").as_double()) {
register_input("/remote/joystick/right", joystick_right_);
register_input("/remote/joystick/left", joystick_left_);
diff --git a/rmcs_ws/src/rmcs_core/src/referee/command/interaction/sentry_decision.cpp b/rmcs_ws/src/rmcs_core/src/referee/command/interaction/sentry_decision.cpp
index e69de29b..d62f48bb 100644
--- a/rmcs_ws/src/rmcs_core/src/referee/command/interaction/sentry_decision.cpp
+++ b/rmcs_ws/src/rmcs_core/src/referee/command/interaction/sentry_decision.cpp
@@ -0,0 +1,242 @@
+#include "referee/command/field.hpp"
+#include "referee/command/interaction/header.hpp"
+#include "referee/status/field.hpp"
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+namespace rmcs_core::referee::command::interaction {
+
+class SentryDecision
+ : public rmcs_executor::Component
+ , public rclcpp::Node {
+public:
+ using Command = status::SentryCommand;
+ using Posture = Command::Posture;
+ using SentryEvent = rmcs_msgs::SentryEvent;
+ using EventCounts = std::unordered_map;
+ using Clock = std::chrono::steady_clock;
+
+ InputInterface sentry_events_;
+ InputInterface robot_id_;
+ InputInterface sentry_posture_fb_;
+ InputInterface robot_hp_fb_;
+ InputInterface energy_core_status_;
+ InputInterface can_rebirth_free_;
+
+ OutputInterface sentry_decision_field_;
+
+ Header header_{};
+ Command command_{};
+
+ EventCounts cached_events_;
+ std::unordered_set requests_;
+ std::unordered_map pose_targets_;
+ std::unordered_set logged_events_;
+ std::uint8_t last_fb_posture_ = 3;
+ bool last_can_rebirth_free_ = false;
+
+ static inline const auto kPoseEvents = std::unordered_set{
+ SentryEvent::SWITCH_POSE_ATTACK,
+ SentryEvent::SWITCH_POSE_DEFENSE,
+ SentryEvent::SWITCH_POSE_MOVE,
+ SentryEvent::SWITCH_POSE_POWERED_ATTACK,
+ SentryEvent::SWITCH_POSE_POWERED_DEFENSE,
+ SentryEvent::SWITCH_POSE_POWERED_MOVE,
+ };
+
+ static auto to_posture(SentryEvent event) -> Posture {
+ switch (event) {
+ case SentryEvent::SWITCH_POSE_ATTACK: return Posture::ATTACK;
+ case SentryEvent::SWITCH_POSE_DEFENSE: return Posture::DEFENSE;
+ case SentryEvent::SWITCH_POSE_MOVE: return Posture::MOVE;
+ case SentryEvent::SWITCH_POSE_POWERED_ATTACK: return Posture::POWERED_ATTACK;
+ case SentryEvent::SWITCH_POSE_POWERED_DEFENSE: return Posture::POWERED_DEFENSE;
+ case SentryEvent::SWITCH_POSE_POWERED_MOVE: return Posture::POWERED_MOVE;
+ default: return Posture::UNKNOWN;
+ }
+ }
+
+ static constexpr auto kEventPriority = std::array{
+ SentryEvent::CONFIRM_REBIRTH,
+ SentryEvent::CONFIRM_INSTANT_REBIRTH,
+ SentryEvent::SWITCH_POSE_ATTACK,
+ SentryEvent::SWITCH_POSE_DEFENSE,
+ SentryEvent::SWITCH_POSE_MOVE,
+ SentryEvent::SWITCH_POSE_POWERED_ATTACK,
+ SentryEvent::SWITCH_POSE_POWERED_DEFENSE,
+ SentryEvent::SWITCH_POSE_POWERED_MOVE,
+ SentryEvent::EXCHANGE_AMMO_SUPPLY_POINT,
+ SentryEvent::EXCHANGE_AMMO_REMOTE,
+ SentryEvent::EXCHANGE_HP_REMOTE,
+ SentryEvent::ACTIVATE_ENERGY_CORE,
+ };
+
+ SentryDecision()
+ : Node{
+ get_component_name(),
+ rclcpp::NodeOptions{}.automatically_declare_parameters_from_overrides(true)} {
+
+ register_input("/referee/id", robot_id_);
+ register_input("/rmcs_navigation/sentry_events", sentry_events_, false);
+ register_input("/referee/sentry/posture", sentry_posture_fb_, false);
+ register_input("/referee/current_hp", robot_hp_fb_, false);
+ register_input(
+ "/referee/event/ally_big_energy_activation_status", energy_core_status_, false);
+ register_input("/referee/sentry/can_rebirth_free", can_rebirth_free_, false);
+
+ register_output("/referee/command/interaction/sentry_decision", sentry_decision_field_);
+ }
+
+ auto before_updating() -> void override {
+ if (!sentry_events_.ready())
+ sentry_events_.make_and_bind_directly();
+ if (!sentry_posture_fb_.ready())
+ sentry_posture_fb_.make_and_bind_directly(uint8_t{3});
+ if (!robot_hp_fb_.ready())
+ robot_hp_fb_.make_and_bind_directly(uint16_t{0});
+ if (!energy_core_status_.ready())
+ energy_core_status_.make_and_bind_directly(uint8_t{0});
+ if (!can_rebirth_free_.ready())
+ can_rebirth_free_.make_and_bind_directly(false);
+ }
+
+ auto update() -> void override {
+ if (*robot_id_ == rmcs_msgs::RobotId::UNKNOWN) {
+ *sentry_decision_field_ = Field{};
+ return;
+ }
+
+ detect_new_events();
+
+ const auto can_rebirth_free = *can_rebirth_free_;
+ if (can_rebirth_free && !last_can_rebirth_free_) {
+ requests_.insert(SentryEvent::CONFIRM_REBIRTH);
+ }
+ last_can_rebirth_free_ = can_rebirth_free;
+
+ consume_one_event();
+ verify_feedback();
+ }
+
+private:
+ auto detect_new_events() -> void {
+ const auto& input = *sentry_events_;
+
+ for (const auto event : kEventPriority) {
+ auto input_it = input.find(event);
+ auto input_count = (input_it != input.end()) ? input_it->second : uint16_t{0};
+ auto cache_count = cached_events_[event];
+
+ if (cache_count != input_count) {
+ if (kPoseEvents.contains(event)) {
+ for (const auto rm : kPoseEvents)
+ requests_.erase(rm);
+ }
+ requests_.insert(event);
+ cached_events_[event] = input_count;
+ }
+ }
+ }
+
+ auto consume_one_event() -> void {
+ if (requests_.empty()) {
+ *sentry_decision_field_ = Field{};
+ return;
+ }
+
+ const auto id = rmcs_msgs::FullRobotId{*robot_id_};
+ header_.command_id = 0x0120;
+ header_.sender_id = id;
+ header_.receiver_id = rmcs_msgs::FullRobotId::REFEREE_SERVER;
+
+ for (const auto event : kEventPriority) {
+ if (!requests_.contains(event))
+ continue;
+
+ command_ = Command{};
+
+ if (kPoseEvents.contains(event)) {
+ command_.posture = to_posture(event);
+ pose_targets_[event] = to_posture(event);
+ } else if (event == SentryEvent::CONFIRM_REBIRTH) {
+ command_.rebirth_confirm = 1;
+ } else if (event == SentryEvent::CONFIRM_INSTANT_REBIRTH) {
+ command_.instant_rebirth_confirm = 1;
+ } else if (event == SentryEvent::EXCHANGE_AMMO_SUPPLY_POINT) {
+ command_.ammo_exchange = 1;
+ } else if (event == SentryEvent::EXCHANGE_AMMO_REMOTE) {
+ command_.remote_ammo_request = 1;
+ } else if (event == SentryEvent::EXCHANGE_HP_REMOTE) {
+ command_.remote_hp_request = 1;
+ } else if (event == SentryEvent::ACTIVATE_ENERGY_CORE) {
+ command_.energy_core_confirm = 1;
+ }
+
+ *sentry_decision_field_ = MAKE_FIELD(header_, command_);
+
+ if (kPoseEvents.contains(event)) {
+ if (!logged_events_.contains(event)) {
+ RCLCPP_INFO(
+ get_logger(), "Sentry pose command: %d",
+ std::to_underlying(command_.posture));
+ logged_events_.insert(event);
+ }
+ }
+ break;
+ }
+ }
+
+ auto verify_feedback() -> void {
+ const auto fb_posture_id = *sentry_posture_fb_;
+ const auto fb_hp = *robot_hp_fb_;
+ const auto energy_core_status = *energy_core_status_;
+
+ if (fb_posture_id != last_fb_posture_) {
+ RCLCPP_INFO(
+ get_logger(), "Sentry posture feedback: %d → %d", last_fb_posture_, fb_posture_id);
+ last_fb_posture_ = fb_posture_id;
+ }
+
+ auto to_erase = std::vector{};
+ for (const auto event : requests_) {
+ if (kPoseEvents.contains(event)) {
+ auto it = pose_targets_.find(event);
+ if (it != pose_targets_.end()
+ && static_cast(it->second) == fb_posture_id) {
+ to_erase.push_back(event);
+ pose_targets_.erase(it);
+ logged_events_.erase(event);
+ }
+ } else if (
+ event == SentryEvent::CONFIRM_REBIRTH
+ || event == SentryEvent::CONFIRM_INSTANT_REBIRTH) {
+ if (fb_hp > 0) {
+ to_erase.push_back(event);
+ }
+ } else if (event == SentryEvent::ACTIVATE_ENERGY_CORE) {
+ if (energy_core_status != 0) {
+ to_erase.push_back(event);
+ }
+ } else {
+ to_erase.push_back(event);
+ }
+ }
+
+ for (const auto event : to_erase)
+ requests_.erase(event);
+ }
+};
+
+} // namespace rmcs_core::referee::command::interaction
+
+#include
+PLUGINLIB_EXPORT_CLASS(
+ rmcs_core::referee::command::interaction::SentryDecision, rmcs_executor::Component)
diff --git a/rmcs_ws/src/rmcs_core/src/referee/status.cpp b/rmcs_ws/src/rmcs_core/src/referee/status.cpp
index c29bc3c2..c0a7db62 100644
--- a/rmcs_ws/src/rmcs_core/src/referee/status.cpp
+++ b/rmcs_ws/src/rmcs_core/src/referee/status.cpp
@@ -49,6 +49,14 @@ class Status
register_output("/referee/chassis/buffer_energy", robot_buffer_energy_, 60.0);
register_output("/referee/chassis/output_status", chassis_output_status_, false);
+ register_output("/referee/sentry/posture", sentry_posture_, uint8_t{3});
+ register_output("/referee/sentry/is_powered", sentry_is_powered_, false);
+ register_output("/referee/sentry/is_disengaged", sentry_is_disengaged_, false);
+ register_output("/referee/sentry/can_rebirth_free", sentry_can_rebirth_free_, false);
+ register_output("/referee/sentry/can_rebirth_gold", sentry_can_rebirth_gold_, false);
+ register_output(
+ "/referee/sentry/rebirth_gold_cost", sentry_rebirth_gold_cost_, uint16_t{0});
+
register_output("/referee/robots/hp", robots_hp_);
register_output("/referee/ally/hero_hp", ally_hero_hp_, 0);
register_output("/referee/ally/engineer_hp", ally_engineer_hp_, 0);
@@ -56,6 +64,9 @@ class Status
register_output("/referee/ally/infantry_2_hp", ally_infantry_2_hp_, 0);
register_output("/referee/ally/outpost/hp", ally_outpost_hp_, 0);
register_output("/referee/ally/base/hp", ally_base_hp_, 0);
+ register_output("/referee/enemy/outpost/hp", enemy_outpost_hp_, 0);
+ register_output("/referee/enemy/base/hp", enemy_base_hp_, 0);
+ register_output("/referee/damage_difference", damage_difference_, int16_t{0});
register_output("/referee/current_hp", robot_current_hp_);
register_output("/referee/position/x", robot_position_x_, 0.0);
register_output("/referee/position/y", robot_position_y_, 0.0);
@@ -149,7 +160,7 @@ class Status
auto command_id = frame_.body.command_id;
if (command_id == 0x0001)
update_game_status();
- if (command_id == 0x0003)
+ else if (command_id == 0x0003)
update_game_robot_hp();
else if (command_id == 0x0101)
update_event_data();
@@ -167,6 +178,8 @@ class Status
update_shoot_data();
else if (command_id == 0x0208)
update_bullet_allowance();
+ else if (command_id == 0x020D)
+ update_sentry_info();
else if (command_id == 0x0303)
update_map_command();
}
@@ -187,16 +200,15 @@ class Status
void update_event_data() {
auto& data = reinterpret_cast(frame_.body.data);
- const uint32_t event_data = data.event_data;
- *ally_small_energy_activation_status_ = (event_data >> 3) & 0x03;
- *ally_big_energy_activation_status_ = (event_data >> 5) & 0x03;
- *ally_fortress_occupation_status_ = (event_data >> 25) & 0x03;
+ *ally_small_energy_activation_status_ = data.ally_small_energy_activation_status;
+ *ally_big_energy_activation_status_ = data.ally_big_energy_activation_status;
+ *ally_fortress_occupation_status_ = data.ally_fortress_occupation_status;
}
void update_dart_info() {
auto& data = reinterpret_cast(frame_.body.data);
- *dart_latest_hit_target_total_count_ = (data.dart_info >> 3) & 0x07;
+ *dart_latest_hit_target_total_count_ = data.latest_hit_target_total_count;
}
void update_game_robot_hp() {
@@ -208,6 +220,9 @@ class Status
*ally_infantry_2_hp_ = data.ally_4_robot_hp;
*ally_outpost_hp_ = data.ally_outpost_hp;
*ally_base_hp_ = data.ally_base_hp;
+ *enemy_outpost_hp_ = data.enemy_outpost_hp;
+ *enemy_base_hp_ = data.enemy_base_hp;
+ *damage_difference_ = data.damage_difference;
}
void update_robot_status() {
@@ -228,7 +243,7 @@ class Status
else
*robot_chassis_power_limit_ = static_cast(data.chassis_power_limit);
- *chassis_output_status_ = data.power_management_status & (1u << 1);
+ *chassis_output_status_ = data.power_management_chassis_output;
}
void update_power_heat_data() {
@@ -263,6 +278,17 @@ class Status
*robot_fortress_17mm_bullet_allowance_ = data.projectile_allowance_fortress;
}
+ void update_sentry_info() {
+ auto& data = reinterpret_cast(frame_.body.data);
+
+ *sentry_posture_ = static_cast(data.posture + (data.is_powered ? 3 : 0));
+ *sentry_is_powered_ = data.is_powered;
+ *sentry_is_disengaged_ = data.is_disengaged;
+ *sentry_can_rebirth_free_ = data.can_rebirth_free;
+ *sentry_can_rebirth_gold_ = data.can_rebirth_gold;
+ *sentry_rebirth_gold_cost_ = data.rebirth_gold_cost;
+ }
+
void update_map_command() {
if (frame_.header.data_length < sizeof(MapCommand)) {
RCLCPP_WARN(
@@ -329,6 +355,13 @@ class Status
OutputInterface robot_chassis_power_limit_;
OutputInterface chassis_output_status_;
+ OutputInterface sentry_posture_;
+ OutputInterface sentry_is_powered_;
+ OutputInterface sentry_is_disengaged_;
+ OutputInterface sentry_can_rebirth_free_;
+ OutputInterface sentry_can_rebirth_gold_;
+ OutputInterface sentry_rebirth_gold_cost_;
+
rmcs_utility::TickTimer power_heat_data_watchdog_;
OutputInterface robot_chassis_power_;
OutputInterface robot_buffer_energy_;
@@ -340,6 +373,9 @@ class Status
OutputInterface ally_infantry_2_hp_;
OutputInterface ally_outpost_hp_;
OutputInterface ally_base_hp_;
+ OutputInterface enemy_outpost_hp_;
+ OutputInterface enemy_base_hp_;
+ OutputInterface damage_difference_;
OutputInterface robot_current_hp_;
OutputInterface robot_position_x_;
OutputInterface robot_position_y_;
diff --git a/rmcs_ws/src/rmcs_core/src/referee/status/field.hpp b/rmcs_ws/src/rmcs_core/src/referee/status/field.hpp
index ad321125..ad5e2161 100644
--- a/rmcs_ws/src/rmcs_core/src/referee/status/field.hpp
+++ b/rmcs_ws/src/rmcs_core/src/referee/status/field.hpp
@@ -16,31 +16,56 @@ struct __attribute__((packed)) GameRobotHp {
uint16_t ally_2_robot_hp;
uint16_t ally_3_robot_hp;
uint16_t ally_4_robot_hp;
- uint16_t reserved;
+ int16_t damage_difference;
uint16_t ally_7_robot_hp;
uint16_t ally_outpost_hp;
uint16_t ally_base_hp;
+ uint16_t enemy_outpost_hp;
+ uint16_t enemy_base_hp;
};
struct __attribute__((packed)) EventData {
- uint32_t event_data;
+ std::uint32_t ally_supply_zone_occupied : 1 = 0;
+ std::uint32_t reserved_1 : 1 = 0;
+ std::uint32_t ally_supply_zone_occupied_rmul : 1 = 0;
+ std::uint32_t ally_small_energy_activation_status : 2 = 0;
+ std::uint32_t ally_big_energy_activation_status : 2 = 0;
+ std::uint32_t ally_central_highland_occupied : 2 = 0;
+ std::uint32_t ally_trapezoidal_highland_occupied : 2 = 0;
+ std::uint32_t enemy_dart_latest_hit_time : 9 = 0;
+ std::uint32_t enemy_dart_latest_hit_target : 3 = 0;
+ std::uint32_t center_gain_point_occupied : 2 = 0;
+ std::uint32_t ally_fortress_occupation_status : 2 = 0;
+ std::uint32_t ally_outpost_gain_point_occupied : 2 = 0;
+ std::uint32_t ally_base_gain_point_occupied : 1 = 0;
+ std::uint32_t reserved_30_31 : 2 = 0;
};
+static_assert(sizeof(EventData) == 4);
struct __attribute__((packed)) DartInfo {
- uint8_t dart_remaining_time;
- uint16_t dart_info;
+ std::uint8_t dart_remaining_time;
+ std::uint16_t latest_hit_target : 3 = 0;
+ std::uint16_t latest_hit_target_total_count : 3 = 0;
+ std::uint16_t selected_target : 3 = 0;
+ std::uint16_t reserved : 7 = 0;
};
+static_assert(sizeof(DartInfo) == 3);
struct __attribute__((packed)) RobotStatus {
- uint8_t robot_id;
- uint8_t robot_level;
- uint16_t current_hp;
- uint16_t maximum_hp;
- uint16_t shooter_barrel_cooling_value;
- uint16_t shooter_barrel_heat_limit;
- uint16_t chassis_power_limit;
- uint8_t power_management_status;
+ std::uint8_t robot_id;
+ std::uint8_t robot_level;
+ std::uint16_t current_hp;
+ std::uint16_t maximum_hp;
+ std::uint16_t shooter_barrel_cooling_value;
+ std::uint16_t shooter_barrel_heat_limit;
+ std::uint16_t chassis_power_limit;
+ float bullet_speed_limit;
+ std::uint8_t power_management_gimbal_output : 1 = 0;
+ std::uint8_t power_management_chassis_output : 1 = 0;
+ std::uint8_t power_management_shooter_output : 1 = 0;
+ std::uint8_t reserved : 5 = 0;
};
+static_assert(sizeof(RobotStatus) == 17);
struct __attribute__((packed)) PowerHeatData {
uint16_t reserved_1;
@@ -85,4 +110,52 @@ struct __attribute__((packed)) MapCommand {
};
static_assert(sizeof(MapCommand) == 12);
+struct __attribute__((packed)) SentryCommand {
+ enum class Posture : std::uint8_t {
+ UNKNOWN = 0,
+ ATTACK = 1,
+ DEFENSE = 2,
+ MOVE = 3,
+ POWERED_ATTACK = 4,
+ POWERED_DEFENSE = 5,
+ POWERED_MOVE = 6,
+ };
+
+ std::uint32_t rebirth_confirm : 1 = 0;
+ std::uint32_t instant_rebirth_confirm : 1 = 0;
+ std::uint32_t ammo_exchange : 11 = 0;
+ std::uint32_t remote_ammo_request : 4 = 0;
+ std::uint32_t remote_hp_request : 4 = 0;
+ Posture posture : 3 = Posture::UNKNOWN;
+ std::uint32_t energy_core_confirm : 1 = 0;
+ std::uint32_t reserved : 7 = 0;
+};
+static_assert(sizeof(SentryCommand) == 4);
+
+struct __attribute__((packed)) SentryInfo {
+ std::uint32_t ammo_exchange_count : 11 = 0;
+ std::uint32_t remote_ammo_exchange_count : 4 = 0;
+ std::uint32_t remote_hp_exchange_count : 4 = 0;
+ std::uint32_t can_rebirth_free : 1 = 0;
+ std::uint32_t can_rebirth_gold : 1 = 0;
+ std::uint32_t rebirth_gold_cost : 10 = 0;
+ std::uint32_t reserved_31 : 1 = 0;
+
+ std::uint16_t is_disengaged : 1 = 0;
+ std::uint16_t remaining_17mm_ammo_exchangeable : 11 = 0;
+ std::uint16_t posture : 2 = 0;
+ std::uint16_t energy_core_activatable : 1 = 0;
+ std::uint16_t is_powered : 1 = 0;
+
+ std::uint64_t attack_posture_remaining_time : 8 = 0;
+ std::uint64_t defense_posture_remaining_time : 8 = 0;
+ std::uint64_t move_posture_remaining_time : 8 = 0;
+ std::uint64_t reserved_24_31 : 8 = 0;
+ std::uint64_t powered_attack_remaining_time : 8 = 0;
+ std::uint64_t powered_defense_remaining_time : 8 = 0;
+ std::uint64_t powered_move_remaining_time : 8 = 0;
+ std::uint64_t reserved_56_63 : 8 = 0;
+};
+static_assert(sizeof(SentryInfo) == 14);
+
} // namespace rmcs_core::referee::status
diff --git a/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/rmcs_msgs.hpp b/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/rmcs_msgs.hpp
index 9694a65d..1cccd175 100644
--- a/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/rmcs_msgs.hpp
+++ b/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/rmcs_msgs.hpp
@@ -20,6 +20,7 @@
#include "mouse.hpp" // IWYU pragma: export
#include "robot_color.hpp" // IWYU pragma: export
#include "robot_id.hpp" // IWYU pragma: export
+#include "sentry_event.hpp" // IWYU pragma: export
#include "serial_interface.hpp" // IWYU pragma: export
#include "shoot_mode.hpp" // IWYU pragma: export
#include "shoot_status.hpp" // IWYU pragma: export
diff --git a/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/sentry_event.hpp b/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/sentry_event.hpp
new file mode 100644
index 00000000..be171924
--- /dev/null
+++ b/rmcs_ws/src/rmcs_msgs/include/rmcs_msgs/sentry_event.hpp
@@ -0,0 +1,27 @@
+#pragma once
+
+#include
+
+namespace rmcs_msgs {
+
+enum class SentryEvent : std::uint8_t {
+ SWITCH_POSE_ATTACK,
+ SWITCH_POSE_DEFENSE,
+ SWITCH_POSE_MOVE,
+ SWITCH_POSE_POWERED_ATTACK,
+ SWITCH_POSE_POWERED_DEFENSE,
+ SWITCH_POSE_POWERED_MOVE,
+
+ CONFIRM_REBIRTH,
+ CONFIRM_INSTANT_REBIRTH,
+
+ EXCHANGE_AMMO_SUPPLY_POINT,
+ EXCHANGE_AMMO_REMOTE,
+ EXCHANGE_HP_REMOTE,
+
+ ACTIVATE_ENERGY_CORE,
+
+ COUNT,
+};
+
+} // namespace rmcs_msgs