
--- README.md
+++ README.md
... | ... | @@ -1,4 +1,19 @@ |
1 |
+# 원본으로부터 특기할만한 변경점 |
|
2 |
+ |
|
3 |
+## `p9n_example` 에서의 변경점 |
|
4 |
+ |
|
5 |
+기존에는 단순히 플레이스테이션 컨트롤러의 입력을 받아 출력하는 역할만 있었으나, 이를 publish 할 수 있는 능력 부여 |
|
6 |
+ |
|
7 |
+또한, 동시 키 입력 지원 (기존 코드는 모든 인풋에 대하여 if else 로 switch 하는 방식이었으나 수정된 코드는 이를 개별로 처리하고 publish) |
|
8 |
+ |
|
9 |
+이 외에도 `CmakeList.txt`, `package.xml` 파일의 스크립트간 의존관계 변경에 따른 수정 |
|
10 |
+ |
|
11 |
+또한 이를 통하여 python 상에서 플레이스테이션 컨트롤러의 입력을 처리 할 수 있도록 joy_feed_back_receiver.py 예제 추가 |
|
12 |
+ |
|
13 |
+p9n_example 폴더내부의 cpp 코드, include hpp 코드, 모두 수정되었음. |
|
14 |
+ |
|
1 | 15 |
# PlayStation-JoyInterface-ROS2 |
16 |
+ |
|
2 | 17 |
PlayStation Joy Controller Interface Package for ROS2. |
3 | 18 |
|
4 | 19 |
|
--- p9n_example/CMakeLists.txt
+++ p9n_example/CMakeLists.txt
... | ... | @@ -27,4 +27,12 @@ |
27 | 27 |
ament_lint_auto_find_test_dependencies() |
28 | 28 |
endif() |
29 | 29 |
|
30 |
+# ===========python node ============ |
|
31 |
+# Install Python scripts |
|
32 |
+install( |
|
33 |
+ PROGRAMS |
|
34 |
+ scripts/joy_feedback_receiver.py |
|
35 |
+ DESTINATION lib/${PROJECT_NAME} |
|
36 |
+) |
|
37 |
+ |
|
30 | 38 |
ament_auto_package(INSTALL_TO_SHARE launch) |
--- p9n_example/include/p9n_example/display_node.hpp
+++ p9n_example/include/p9n_example/display_node.hpp
... | ... | @@ -20,6 +20,7 @@ |
20 | 20 |
#include <p9n_interface/p9n_interface.hpp> |
21 | 21 |
#include <rclcpp/rclcpp.hpp> |
22 | 22 |
#include <sensor_msgs/msg/joy.hpp> |
23 |
+#include <std_msgs/msg/string.hpp> |
|
23 | 24 |
|
24 | 25 |
namespace p9n_example |
25 | 26 |
{ |
... | ... | @@ -30,6 +31,7 @@ |
30 | 31 |
std::unique_ptr<p9n_interface::PlayStationInterface> p9n_if_; |
31 | 32 |
|
32 | 33 |
rclcpp::Subscription<sensor_msgs::msg::Joy>::SharedPtr joy_sub_; |
34 |
+ rclcpp::Publisher<std_msgs::msg::String>::SharedPtr feedback_pub_; |
|
33 | 35 |
|
34 | 36 |
public: |
35 | 37 |
explicit DisplayNode(const rclcpp::NodeOptions &); |
--- p9n_example/package.xml
+++ p9n_example/package.xml
... | ... | @@ -12,6 +12,9 @@ |
12 | 12 |
<depend>rclcpp_components</depend> |
13 | 13 |
<depend>p9n_interface</depend> |
14 | 14 |
<exec_depend>joy</exec_depend> |
15 |
+ |
|
16 |
+ <exec_depend>python3</exec_depend> |
|
17 |
+ <exec_depend>setuptools</exec_depend> |
|
15 | 18 |
|
16 | 19 |
<test_depend>ament_lint_auto</test_depend> |
17 | 20 |
<test_depend>ament_lint_common</test_depend> |
+++ p9n_example/scripts/joy_feedback_receiver.py
... | ... | @@ -0,0 +1,36 @@ |
1 | +#!/usr/bin/env python3 | |
2 | +# shebang line for directing correct python executables. ROS2 uses system python installation, not conda. | |
3 | +import rclpy | |
4 | +from rclpy.node import Node | |
5 | +from std_msgs.msg import String | |
6 | + | |
7 | +class JoyFeedbackReceiver(Node): | |
8 | + def __init__(self): | |
9 | + super().__init__('joy_feedback_receiver') | |
10 | + # Create a subscription to the 'joy_feedback' topic | |
11 | + self.subscription = self.create_subscription( | |
12 | + String, | |
13 | + 'joy_feedback', | |
14 | + self.listener_callback, | |
15 | + 10 # QoS depth | |
16 | + ) | |
17 | + self.get_logger().info('Joy Feedback Receiver Node Initialized') | |
18 | + | |
19 | + def listener_callback(self, msg): | |
20 | + # Log and print the received message | |
21 | + self.get_logger().info(f'Received feedback: {msg.data}') | |
22 | + | |
23 | +def main(args=None): | |
24 | + rclpy.init(args=args) | |
25 | + receiver_node = JoyFeedbackReceiver() | |
26 | + try: | |
27 | + rclpy.spin(receiver_node) | |
28 | + except KeyboardInterrupt: | |
29 | + receiver_node.get_logger().info('Shutting down node...') | |
30 | + finally: | |
31 | + receiver_node.destroy_node() | |
32 | + rclpy.shutdown() | |
33 | + | |
34 | +if __name__ == '__main__': | |
35 | + main() | |
36 | + |
--- p9n_example/src/display_node.cpp
+++ p9n_example/src/display_node.cpp
... | ... | @@ -14,6 +14,7 @@ |
14 | 14 |
|
15 | 15 |
|
16 | 16 |
#include "p9n_example/display_node.hpp" |
17 |
+#include "std_msgs/msg/string.hpp" |
|
17 | 18 |
|
18 | 19 |
|
19 | 20 |
namespace p9n_example |
... | ... | @@ -45,6 +46,10 @@ |
45 | 46 |
"joy", rclcpp::SensorDataQoS(rclcpp::KeepLast(1)), |
46 | 47 |
std::bind(&DisplayNode::onJoy, this, std::placeholders::_1)); |
47 | 48 |
|
49 |
+ // Define the publisher |
|
50 |
+ this->feedback_pub_ = this->create_publisher<std_msgs::msg::String>( |
|
51 |
+ "joy_feedback", 10); |
|
52 |
+ |
|
48 | 53 |
|
49 | 54 |
if (this->joy_sub_->get_publisher_count() == 0) { |
50 | 55 |
RCLCPP_WARN( |
... | ... | @@ -57,112 +62,163 @@ |
57 | 62 |
{ |
58 | 63 |
this->p9n_if_->setJoyMsg(joy_msg); |
59 | 64 |
|
65 |
+ std::string feedback; |
|
66 |
+ // for handling multi button press |
|
60 | 67 |
if (this->p9n_if_->pressedCross()) { |
68 |
+ auto msg = std_msgs::msg::String(); |
|
69 |
+ msg.data = "Cross button pressed!"; |
|
61 | 70 |
RCLCPP_INFO(this->get_logger(), " ☓ Pressed!"); |
71 |
+ this->feedback_pub_->publish(msg); |
|
62 | 72 |
} |
63 | 73 |
|
64 | 74 |
if (this->p9n_if_->pressedCircle()) { |
65 |
- RCLCPP_INFO(this->get_logger(), " ○ Pressed!"); |
|
75 |
+ auto msg = std_msgs::msg::String(); |
|
76 |
+ msg.data = "Circle button pressed!"; |
|
77 |
+ RCLCPP_INFO(this->get_logger(), " ○ Pressed!"); |
|
78 |
+ this->feedback_pub_->publish(msg); |
|
66 | 79 |
} |
67 | 80 |
|
68 | 81 |
if (this->p9n_if_->pressedTriangle()) { |
69 |
- RCLCPP_INFO(this->get_logger(), " △ Pressed!"); |
|
82 |
+ auto msg = std_msgs::msg::String(); |
|
83 |
+ msg.data = "Triangle button pressed!"; |
|
84 |
+ RCLCPP_INFO(this->get_logger(), " △ Pressed!"); |
|
85 |
+ this->feedback_pub_->publish(msg); |
|
70 | 86 |
} |
71 | 87 |
|
72 | 88 |
if (this->p9n_if_->pressedSquare()) { |
73 |
- RCLCPP_INFO(this->get_logger(), " □ Pressed!"); |
|
89 |
+ auto msg = std_msgs::msg::String(); |
|
90 |
+ msg.data = "Square button pressed!"; |
|
91 |
+ RCLCPP_INFO(this->get_logger(), " □ Pressed!"); |
|
92 |
+ this->feedback_pub_->publish(msg); |
|
74 | 93 |
} |
75 | 94 |
|
76 | 95 |
if (this->p9n_if_->pressedL1()) { |
77 |
- RCLCPP_INFO(this->get_logger(), " L1 Pressed!"); |
|
96 |
+ auto msg = std_msgs::msg::String(); |
|
97 |
+ msg.data = "L1 button pressed!"; |
|
98 |
+ RCLCPP_INFO(this->get_logger(), " L1 Pressed!"); |
|
99 |
+ this->feedback_pub_->publish(msg); |
|
78 | 100 |
} |
79 | 101 |
|
80 | 102 |
if (this->p9n_if_->pressedR1()) { |
81 |
- RCLCPP_INFO(this->get_logger(), " R1 Pressed!"); |
|
103 |
+ auto msg = std_msgs::msg::String(); |
|
104 |
+ msg.data = "R1 button pressed!"; |
|
105 |
+ RCLCPP_INFO(this->get_logger(), " R1 Pressed!"); |
|
106 |
+ this->feedback_pub_->publish(msg); |
|
82 | 107 |
} |
83 | 108 |
|
84 | 109 |
if (this->p9n_if_->pressedL2()) { |
85 |
- RCLCPP_INFO_STREAM( |
|
86 |
- this->get_logger(), |
|
87 |
- " L2 Pressed! : " << |
|
88 |
- std::right << std::setw(6) << |
|
89 |
- std::fixed << std::setprecision(3) << |
|
90 |
- this->p9n_if_->pressedL2Analog()); |
|
110 |
+ auto msg = std_msgs::msg::String(); |
|
111 |
+ msg.data = "L2 button pressed with analog value: " + |
|
112 |
+ std::to_string(this->p9n_if_->pressedL2Analog()); |
|
113 |
+ RCLCPP_INFO_STREAM( |
|
114 |
+ this->get_logger(), |
|
115 |
+ " L2 Pressed! : " << std::right << std::setw(6) << std::fixed << std::setprecision(3) |
|
116 |
+ << this->p9n_if_->pressedL2Analog()); |
|
117 |
+ this->feedback_pub_->publish(msg); |
|
91 | 118 |
} |
92 | 119 |
|
93 | 120 |
if (this->p9n_if_->pressedR2()) { |
94 |
- RCLCPP_INFO_STREAM( |
|
95 |
- this->get_logger(), |
|
96 |
- " R2 Pressed! : " << |
|
97 |
- std::right << std::setw(6) << |
|
98 |
- std::fixed << std::setprecision(3) << |
|
99 |
- this->p9n_if_->pressedR2Analog()); |
|
121 |
+ auto msg = std_msgs::msg::String(); |
|
122 |
+ msg.data = "R2 button pressed with analog value: " + |
|
123 |
+ std::to_string(this->p9n_if_->pressedR2Analog()); |
|
124 |
+ RCLCPP_INFO_STREAM( |
|
125 |
+ this->get_logger(), |
|
126 |
+ " R2 Pressed! : " << std::right << std::setw(6) << std::fixed << std::setprecision(3) |
|
127 |
+ << this->p9n_if_->pressedR2Analog()); |
|
128 |
+ this->feedback_pub_->publish(msg); |
|
100 | 129 |
} |
101 | 130 |
|
102 | 131 |
if (this->p9n_if_->pressedSelect()) { |
103 |
- RCLCPP_INFO( |
|
104 |
- this->get_logger(), " Select Pressed!"); |
|
132 |
+ auto msg = std_msgs::msg::String(); |
|
133 |
+ msg.data = "Select button pressed!"; |
|
134 |
+ RCLCPP_INFO(this->get_logger(), " Select Pressed!"); |
|
135 |
+ this->feedback_pub_->publish(msg); |
|
105 | 136 |
} |
106 | 137 |
|
107 | 138 |
if (this->p9n_if_->pressedStart()) { |
108 |
- RCLCPP_INFO( |
|
109 |
- this->get_logger(), " Start Pressed!"); |
|
139 |
+ auto msg = std_msgs::msg::String(); |
|
140 |
+ msg.data = "Start button pressed!"; |
|
141 |
+ RCLCPP_INFO(this->get_logger(), " Start Pressed!"); |
|
142 |
+ this->feedback_pub_->publish(msg); |
|
110 | 143 |
} |
111 | 144 |
|
112 | 145 |
if (this->p9n_if_->pressedPS()) { |
113 |
- RCLCPP_INFO( |
|
114 |
- this->get_logger(), " PS Pressed!"); |
|
146 |
+ auto msg = std_msgs::msg::String(); |
|
147 |
+ msg.data = "PS button pressed!"; |
|
148 |
+ RCLCPP_INFO(this->get_logger(), " PS Pressed!"); |
|
149 |
+ this->feedback_pub_->publish(msg); |
|
115 | 150 |
} |
116 | 151 |
|
117 | 152 |
if (this->p9n_if_->pressedDPadUp()) { |
118 |
- RCLCPP_INFO( |
|
119 |
- this->get_logger(), " ↑ Pressed!"); |
|
153 |
+ auto msg = std_msgs::msg::String(); |
|
154 |
+ msg.data = "D-Pad Up pressed!"; |
|
155 |
+ RCLCPP_INFO(this->get_logger(), " ↑ Pressed!"); |
|
156 |
+ this->feedback_pub_->publish(msg); |
|
120 | 157 |
} |
121 | 158 |
|
122 | 159 |
if (this->p9n_if_->pressedDPadDown()) { |
123 |
- RCLCPP_INFO( |
|
124 |
- this->get_logger(), " ↓ Pressed!"); |
|
160 |
+ auto msg = std_msgs::msg::String(); |
|
161 |
+ msg.data = "D-Pad Down pressed!"; |
|
162 |
+ RCLCPP_INFO(this->get_logger(), " ↓ Pressed!"); |
|
163 |
+ this->feedback_pub_->publish(msg); |
|
125 | 164 |
} |
126 | 165 |
|
127 | 166 |
if (this->p9n_if_->pressedDPadRight()) { |
128 |
- RCLCPP_INFO( |
|
129 |
- this->get_logger(), " → Pressed!"); |
|
167 |
+ auto msg = std_msgs::msg::String(); |
|
168 |
+ msg.data = "D-Pad Right pressed!"; |
|
169 |
+ RCLCPP_INFO(this->get_logger(), " → Pressed!"); |
|
170 |
+ this->feedback_pub_->publish(msg); |
|
130 | 171 |
} |
131 | 172 |
|
132 | 173 |
if (this->p9n_if_->pressedDPadLeft()) { |
133 |
- RCLCPP_INFO( |
|
134 |
- this->get_logger(), " ← Pressed!"); |
|
174 |
+ auto msg = std_msgs::msg::String(); |
|
175 |
+ msg.data = "D-Pad Left pressed!"; |
|
176 |
+ RCLCPP_INFO(this->get_logger(), " ← Pressed!"); |
|
177 |
+ this->feedback_pub_->publish(msg); |
|
178 |
+ } |
|
179 |
+ |
|
180 |
+ // L and R stick |
|
181 |
+ if ( |
|
182 |
+ std::abs(this->p9n_if_->tiltedStickLX()) > 1e-2 || |
|
183 |
+ std::abs(this->p9n_if_->tiltedStickLY()) > 1e-2) |
|
184 |
+ { |
|
185 |
+ std::ostringstream oss; |
|
186 |
+ oss << "LStick Tilted! x: " << std::fixed << std::setw(6) << std::setprecision(3) |
|
187 |
+ << this->p9n_if_->tiltedStickLX() |
|
188 |
+ << " y: " << std::fixed << std::setw(6) << std::setprecision(3) |
|
189 |
+ << this->p9n_if_->tiltedStickLY(); |
|
190 |
+ std::string feedback = oss.str(); |
|
191 |
+ |
|
192 |
+ RCLCPP_INFO_STREAM(this->get_logger(), feedback); |
|
193 |
+ |
|
194 |
+ // Publish the feedback message |
|
195 |
+ auto msg = std_msgs::msg::String(); |
|
196 |
+ msg.data = feedback; |
|
197 |
+ this->feedback_pub_->publish(msg); |
|
135 | 198 |
} |
136 | 199 |
|
137 | 200 |
if ( |
138 |
- std::abs(this->p9n_if_->tiltedStickLX()) > 1e-2 || |
|
139 |
- std::abs(this->p9n_if_->tiltedStickLY()) > 1e-2) |
|
201 |
+ std::abs(this->p9n_if_->tiltedStickRX()) > 1e-2 || |
|
202 |
+ std::abs(this->p9n_if_->tiltedStickRY()) > 1e-2) |
|
140 | 203 |
{ |
141 |
- RCLCPP_INFO_STREAM( |
|
142 |
- this->get_logger(), |
|
143 |
- " LStick Tilted!" << |
|
144 |
- " x:" << std::fixed << std::setw(6) << std::setprecision(3) << |
|
145 |
- this->p9n_if_->tiltedStickLX() << |
|
146 |
- " y:" << std::fixed << std::setw(6) << std::setprecision(3) << |
|
147 |
- this->p9n_if_->tiltedStickLY()); |
|
148 |
- } |
|
204 |
+ std::ostringstream oss; |
|
205 |
+ oss << "RStick Tilted! x: " << std::fixed << std::setw(6) << std::setprecision(3) |
|
206 |
+ << this->p9n_if_->tiltedStickRX() |
|
207 |
+ << " y: " << std::fixed << std::setw(6) << std::setprecision(3) |
|
208 |
+ << this->p9n_if_->tiltedStickRY(); |
|
209 |
+ std::string feedback = oss.str(); |
|
149 | 210 |
|
150 |
- if ( |
|
151 |
- std::abs(this->p9n_if_->tiltedStickRX()) > 1e-2 || |
|
152 |
- std::abs(this->p9n_if_->tiltedStickRY()) > 1e-2) |
|
153 |
- { |
|
154 |
- RCLCPP_INFO_STREAM( |
|
155 |
- this->get_logger(), |
|
156 |
- " RStick Tilted!" << |
|
157 |
- " x:" << std::fixed << std::setw(6) << std::setprecision(3) << |
|
158 |
- this->p9n_if_->tiltedStickRX() << |
|
159 |
- " y:" << std::fixed << std::setw(6) << std::setprecision(3) << |
|
160 |
- this->p9n_if_->tiltedStickRY()); |
|
211 |
+ RCLCPP_INFO_STREAM(this->get_logger(), feedback); |
|
212 |
+ |
|
213 |
+ // Publish the feedback message |
|
214 |
+ auto msg = std_msgs::msg::String(); |
|
215 |
+ msg.data = feedback; |
|
216 |
+ this->feedback_pub_->publish(msg); |
|
161 | 217 |
} |
162 | 218 |
|
163 | 219 |
if (this->p9n_if_->pressedAny()) { |
164 | 220 |
using namespace std::chrono_literals; // NOLINT |
165 |
- rclcpp::sleep_for(200ms); |
|
221 |
+ rclcpp::sleep_for(100ms); |
|
166 | 222 |
} |
167 | 223 |
} |
168 | 224 |
} // namespace p9n_example |
Add a comment
Delete comment
Once you delete this comment, you won't be able to recover it. Are you sure you want to delete this comment?