Skip to content

Commit a16de47

Browse files
Passing improvements (#2516)
* Almost completed behaviour the passing works, but there are some issues still left in terms of wait time, kick distance, and occasional bugs that need to be worked on. * Current working implementation of offense passing along with fix (maybe) on grey field bug. * Reverting some changes to make seperate PRs for them. * can_i_shoot function implemented. Should now only pass if there's a bot capable on shooting. * More passing additions. Prevents passing to unessesary recievers or over goalie boxes. * More changes towards the final PR, needs more work on conditions and add a skip feature if the kick doesn't trigger. * Failsafe behind passing. If failure to pass, both bots go to default. * Final change focusing on sending passing requests constantly and defaulting to shooting if no one's open. * Fix Code Style On passing-improvements (#2517) automated style fixes Co-authored-by: CameronLyon <CameronLyon@users.noreply.github.com> * Final adjustments based on PR comments. * Fix Code Style On passing-improvements (#2521) automated style fixes Co-authored-by: CameronLyon <CameronLyon@users.noreply.github.com> --------- Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: CameronLyon <CameronLyon@users.noreply.github.com>
1 parent b6f8302 commit a16de47

13 files changed

Lines changed: 261 additions & 36 deletions

File tree

src/rj_config_server/src/config_server.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,7 @@ using config_server::GameSettingsMsg;
7272
*/
7373
GameSettingsMsg parse_game_settings(const std::vector<std::string>& args) {
7474
GameSettingsMsg game_settings;
75+
7576
for (size_t i = 1; i < args.size(); i++) {
7677
const std::string& arg = args.at(i);
7778
if (arg == "-b") {

src/rj_msgs/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ rosidl_generate_interfaces(
7575
request/LeaveWallRequest.msg
7676
request/ResetScorerRequest.msg
7777
request/IncomingBallRequest.msg
78+
request/PassReceivedRequest.msg
7879

7980
# Agent Response Messages
8081
response/ScorerResponse.msg

src/rj_msgs/msg/AgentRequest.msg

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,4 +12,5 @@ SeekerRequest[<=1] seeker_request
1212
PositionRequest[<=1] position_request
1313
LeaveWallRequest[<=1] leave_wall_request
1414
ResetScorerRequest[<=1] reset_scorer_request
15-
IncomingBallRequest[<=1] incoming_ball_request
15+
IncomingBallRequest[<=1] incoming_ball_request
16+
PassReceivedRequest[<=1] pass_received_request
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# Request sent by the receiver to the passer indicating that the receiver
2+
# has controlled the ball. The passer uses this to transition out of
3+
# PASSING_FINISHED and back to DEFAULT (so it does not chase the ball).
4+
uint32 request_uid
5+
uint8 from_robot_id

src/rj_strategy/include/rj_strategy/agent/communication.hpp

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
#include "rj_strategy/agent/communication/join_wall_response.hpp"
1919
#include "rj_strategy/agent/communication/leave_wall_request.hpp"
2020
#include "rj_strategy/agent/communication/leave_wall_response.hpp"
21+
#include "rj_strategy/agent/communication/pass_received_request.hpp"
2122
#include "rj_strategy/agent/communication/pass_request.hpp"
2223
#include "rj_strategy/agent/communication/pass_response.hpp"
2324
#include "rj_strategy/agent/communication/position_request.hpp"
@@ -34,9 +35,10 @@ namespace strategy::communication {
3435
/**
3536
* @brief a conglomeration of the different request types.
3637
*/
37-
using AgentRequest = std::variant<JoinWallRequest, TestRequest, PassRequest, ScorerRequest,
38-
BallInTransitRequest, SeekerRequest, PositionRequest,
39-
LeaveWallRequest, ResetScorerRequest, IncomingBallRequest>;
38+
using AgentRequest =
39+
std::variant<JoinWallRequest, TestRequest, PassRequest, ScorerRequest, BallInTransitRequest,
40+
SeekerRequest, PositionRequest, LeaveWallRequest, ResetScorerRequest,
41+
IncomingBallRequest, PassReceivedRequest>;
4042

4143
/**
4244
* @brief a conglomeration of the different response types.
@@ -159,6 +161,9 @@ struct RosConverter<strategy::communication::AgentRequest, rj_msgs::msg::AgentRe
159161
} else if (const auto* incoming_ball_request =
160162
std::get_if<strategy::communication::IncomingBallRequest>(&from)) {
161163
result.incoming_ball_request.emplace_back(convert_to_ros(*incoming_ball_request));
164+
} else if (const auto* pass_received_request =
165+
std::get_if<strategy::communication::PassReceivedRequest>(&from)) {
166+
result.pass_received_request.emplace_back(convert_to_ros(*pass_received_request));
162167
} else {
163168
throw std::runtime_error("Invalid variant of AgentRequest");
164169
}
@@ -187,6 +192,8 @@ struct RosConverter<strategy::communication::AgentRequest, rj_msgs::msg::AgentRe
187192
result = convert_from_ros(from.reset_scorer_request.front());
188193
} else if (!from.incoming_ball_request.empty()) {
189194
result = convert_from_ros(from.incoming_ball_request.front());
195+
} else if (!from.pass_received_request.empty()) {
196+
result = convert_from_ros(from.pass_received_request.front());
190197
} else {
191198
throw std::runtime_error("Invalid variant of AgentRequest");
192199
}
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
#pragma once
2+
3+
#include <mutex>
4+
#include <string>
5+
#include <variant>
6+
#include <vector>
7+
8+
#include <rj_common/time.hpp>
9+
#include <rj_convert/ros_convert.hpp>
10+
11+
#include "rj_msgs/msg/pass_received_request.hpp"
12+
13+
namespace strategy::communication {
14+
15+
struct PassReceivedRequest {
16+
uint32_t request_uid;
17+
uint8_t from_robot_id;
18+
};
19+
20+
bool operator==(const PassReceivedRequest& a, const PassReceivedRequest& b);
21+
void generate_uid(PassReceivedRequest& request);
22+
23+
} // namespace strategy::communication
24+
25+
namespace rj_convert {
26+
27+
template <>
28+
struct RosConverter<strategy::communication::PassReceivedRequest,
29+
rj_msgs::msg::PassReceivedRequest> {
30+
static rj_msgs::msg::PassReceivedRequest to_ros(
31+
const strategy::communication::PassReceivedRequest& from) {
32+
rj_msgs::msg::PassReceivedRequest result;
33+
result.request_uid = from.request_uid;
34+
result.from_robot_id = from.from_robot_id;
35+
return result;
36+
}
37+
38+
static strategy::communication::PassReceivedRequest from_ros(
39+
const rj_msgs::msg::PassReceivedRequest& from) {
40+
return strategy::communication::PassReceivedRequest{
41+
from.request_uid,
42+
from.from_robot_id,
43+
};
44+
}
45+
};
46+
47+
ASSOCIATE_CPP_ROS(strategy::communication::PassReceivedRequest, rj_msgs::msg::PassReceivedRequest);
48+
49+
} // namespace rj_convert

src/rj_strategy/include/rj_strategy/agent/position.hpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -174,6 +174,15 @@ class Position {
174174
*/
175175
virtual void send_pass_confirmation(u_int8_t target_robot);
176176

177+
/**
178+
* @brief tell the passer that this robot has received/controlled the ball.
179+
* Called by the receiver when it has the ball so the passer can leave
180+
* PASSING_FINISHED and return to DEFAULT.
181+
*
182+
* @param passer_robot_id the robot that passed the ball (recipient of this message)
183+
*/
184+
virtual void send_pass_received_to_passer(u_int8_t passer_robot_id);
185+
177186
/**
178187
* @brief acknowledges the pass confirmation from another robot
179188
*

src/rj_strategy/include/rj_strategy/agent/position/offense.hpp

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ class Offense : public Position {
5454
POSSESSION_START, // Try to shoot and send pass request
5555
POSSESSION, // Holding the ball
5656
PASSING, // Pass the ball
57+
PASSING_FINISHED, // Kicked the ball, waiting for receiver to confirm
5758
STEALING, // Getting the ball
5859
RECEIVING_START, // Facing the ball
5960
RECEIVING, // Getting the ball from a pass
@@ -95,11 +96,13 @@ class Offense : public Position {
9596
case SEEKING:
9697
return RJ::Seconds{-1};
9798
case POSSESSION:
98-
return RJ::Seconds{-1};
99+
return RJ::Seconds{5};
99100
case POSSESSION_START:
100101
return RJ::Seconds{-1};
101102
case PASSING:
102103
return RJ::Seconds{5};
104+
case PASSING_FINISHED:
105+
return RJ::Seconds{5};
103106
case STEALING:
104107
return RJ::Seconds{10};
105108
case RECEIVING_START:
@@ -126,6 +129,8 @@ class Offense : public Position {
126129
return "POSSESSION_START";
127130
case PASSING:
128131
return "PASSING";
132+
case PASSING_FINISHED:
133+
return "PASSING_FINISHED";
129134
case STEALING:
130135
return "STEALING";
131136
case RECEIVING_START:
@@ -187,6 +192,12 @@ class Offense : public Position {
187192
// Used to tell if an enemy is close enough to block a shot
188193
static constexpr double kEnemyTooCloseRadius{kStealBallRadius};
189194

195+
static constexpr double kMinPassDistance{0.5};
196+
197+
// If the ball hasn't left the passer within this window after the kick
198+
// command fires, the kick is considered failed and both robots reset.
199+
static constexpr RJ::Seconds kKickFailsafeTimeout{2.0};
200+
190201
/* Utility functions for State or Task Calculation */
191202

192203
/**
@@ -218,6 +229,12 @@ class Offense : public Position {
218229
* @param target_robot_shell the robot shell to check if open
219230
*/
220231
bool check_if_open(int target_robot_shell);
232+
233+
/**
234+
* @return whether or not a robot is capable of shooting from their pos
235+
*/
236+
bool can_i_shoot() const;
237+
221238
/**
222239
* @return the target (within the goal) that would be the most clear shot
223240
*/
@@ -228,6 +245,19 @@ class Offense : public Position {
228245
*/
229246
bool ball_in_red() const;
230247

248+
/**
249+
* @return true when in PASSING_FINISHED and the kick failsafe timeout has
250+
* elapsed while the ball is still within possession range of this robot.
251+
*/
252+
bool kick_failed() const;
253+
254+
/**
255+
* @brief Notify the receiver that the kick failed so it can abort and
256+
* return to default behaviour. Uses the same PassReceivedRequest
257+
* message type that the receiver normally sends to the passer.
258+
*/
259+
void send_kick_failed_to_receiver(u_int8_t receiver_robot_id);
260+
231261
void broadcast_seeker_request(rj_geometry::Point seeking_point, bool adding);
232262

233263
std::unordered_map<int, rj_geometry::Point> seeker_points_;

src/rj_strategy/include/rj_strategy/agent/position/robot_factory_position.hpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,10 @@ class RobotFactoryPosition : public Position {
110110
current_position_->send_pass_confirmation(target_robot);
111111
}
112112

113+
void send_pass_received_to_passer(u_int8_t passer_robot_id) override {
114+
current_position_->send_pass_received_to_passer(passer_robot_id);
115+
}
116+
113117
void set_override_position(const OverridingPositions& overriding_position);
114118

115119
private:

src/rj_strategy/src/agent/communication.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,10 @@ bool operator==(const IncomingBallRequest& a, const IncomingBallRequest& b) {
4848
return a.request_uid == b.request_uid;
4949
}
5050

51+
bool operator==(const PassReceivedRequest& a, const PassReceivedRequest& b) {
52+
return a.request_uid == b.request_uid;
53+
}
54+
5155
bool operator==(const ScorerResponse& a, const ScorerResponse& b) {
5256
return a.response_uid == b.response_uid;
5357
}
@@ -150,6 +154,13 @@ void generate_uid(IncomingBallRequest& request) {
150154
request_uid_mutex.unlock();
151155
}
152156

157+
void generate_uid(PassReceivedRequest& request) {
158+
request_uid_mutex.lock();
159+
request.request_uid = request_uid;
160+
request_uid++;
161+
request_uid_mutex.unlock();
162+
}
163+
153164
void generate_uid(ScorerResponse& response) {
154165
response_uid_mutex.lock();
155166
response.response_uid = response_uid;

0 commit comments

Comments
 (0)