Skip to content

Commit f15f384

Browse files
author
Leonid Fedorenchik
committed
Merge remote-tracking branch 'github/main'
2 parents ad2efcf + cf77190 commit f15f384

17 files changed

+1460
-64
lines changed

demo/myAGVPro_Composite_Kit/README.md

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
# myAGVPro Composite Kit Handle Control Case
2+
3+
- [简体中文](./README_zh.md)
4+
- [English](./README.md)
5+
6+
## Program description
7+
8+
**The handle function of the myAGVPro composite kit is shown below:**
9+
![](./agvpro_handle_control.png)
10+
11+
**Note:**
12+
13+
1. Before starting the program, you need to connect the handle to myAGVPro and turn on the handle.
14+
2. The `myArmM750` robot arm does not support suction pumps, and the program will prompt when using it
15+
16+
**Kit Usage**
17+
18+
For the use of composite kits, please visit the following link:
19+
20+
- myAGVPro+MyArmM750: [Home storage training](https://docs.elephantrobotics.com/docs/myAGV_Pro_en/7-ExamplesRobotsUsing/7.1-MyArmM750.html)
21+
- myAGVPro+MyCobot320: [Warehouse cargo handling](https://docs.elephantrobotics.com/docs/myAGV_Pro_en/7-ExamplesRobotsUsing/7.2-MyCobot320.html)
22+
- myAGVPro+MyCobotPro630: [MCU door opening training](https://docs.elephantrobotics.com/docs/myAGV_Pro_en/7-ExamplesRobotsUsing/7.3-MyCobotPro630.html)
23+
24+
## Run the program
25+
26+
1. Clone the repository to the myAGVPro system
27+
```shell
28+
git clone https://github.com/elephantrobotics/pymycobot.git
29+
```
30+
2. Enter the repository directory
31+
```shell
32+
cd pymycobot/demo/myAGVPro_Composite_Kit
33+
```
34+
3. Install dependencies
35+
```shell
36+
pip install -r requirement.txt
37+
```
38+
4. Select the robot model
39+
40+
To select the robot model, you need to configure the values ​​of `COMPOSITE_KIT_TYPE` and `COMPOSITE_KIT_COMPORT`.
41+
`COMPOSITE_KIT_TYPE`
42+
indicates the currently selected robot. The modified value needs to match the actual robot model, otherwise the robot
43+
cannot be controlled normally. The current optional robot arm parameters and models are as follows:
44+
45+
| Parameters | Robot arm model |
46+
|-----------------|-----------------|
47+
| `MyCobotPro630` | MyCobot Pro630 |
48+
| `MyCobot320` | MyCobot320 M5 |
49+
| `MyArmM750` | MyArm M750 |
50+
| `Undefined` | / |
51+
52+
When `COMPOSITE_KIT_TYPE = Undefined`, it means that the robot arm is not used. At this time, the handle cannot
53+
control the robot arm and is only valid for MyAGVPro.
54+
55+
`COMPOSITE_KIT_COMPORT` represents the serial port number of the robot arm. The serial port number needs to be
56+
modified according to the actual connected robot arm. Configuration is required when the selected robot arm
57+
is `myArmM750` or `MyCobot320`.
58+
59+
When the selected robot arm is `MyCobotPro630`, no configuration is required, because the control of `MyCobot Pro630`
60+
uses TCP protocol instead of serial port protocol. The values ​​of `COMPOSITE_KIT_HOST` and `COMPOSITE_KIT_PORT` need
61+
to be configured.
62+
63+
`COMPOSITE_KIT_HOST` indicates the IP address of the robot, and `COMPOSITE_KIT_PORT` indicates the port number of the
64+
robot. The default value is `5001`, which needs to be modified according to the actual connected robot.
65+
The IP address and port number of the robot can be viewed through the built-in software `roboflow`. Note that the
66+
robot should be in the same LAN as MyAGVPro at this time.
67+
68+
5. Run the program
69+
70+
```shell
71+
python main.py
72+
```
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
# myAGVPro复合套件手柄控制案例
2+
3+
- [简体中文](./README_zh.md)
4+
- [English](./README.md)
5+
6+
## 程序说明
7+
8+
**myAGVPro复合套件的手柄功能如下图所示:**
9+
![](./agvpro_handle_control.png)
10+
11+
**注意:**
12+
13+
1. 在启动程序之前,您需要将手柄连接到 myAGVPro 并打开手柄。
14+
2. `myArmM750`机械臂不支持吸泵,使用时程序会提示
15+
16+
**套件使用:**
17+
复合套件使用请访问以下链接
18+
19+
- myAGVPro+MyArmM750 [家居收纳训练](https://docs.elephantrobotics.com/docs/myAGV_Pro_cn/7-ExamplesRobotsUsing/7.1-MyArmM750.html)
20+
- myAGVPro+MyCobot320 [仓储货物搬运](https://docs.elephantrobotics.com/docs/myAGV_Pro_cn/7-ExamplesRobotsUsing/7.2-MyCobot320.html)
21+
- myAGVPro+MyCobotPro630 [MCU开门训练](https://docs.elephantrobotics.com/docs/myAGV_Pro_cn/7-ExamplesRobotsUsing/7.3-MyCobotPro630.html)
22+
23+
## 程序运行
24+
25+
1. 克隆仓库到本地
26+
```shell
27+
git clone https://github.com/elephantrobotics/pymycobot.git
28+
```
29+
2. 进入仓库目录
30+
```shell
31+
cd pymycobot/demo/myAGVPro_Composite_Kit
32+
```
33+
3. 安装依赖
34+
```shell
35+
pip install -r requirement.txt
36+
```
37+
4. 选择机械臂型号
38+
39+
选择机械臂型号, 需要配置`COMPOSITE_KIT_TYPE``COMPOSITE_KIT_COMPORT`的值。
40+
`COMPOSITE_KIT_TYPE`
41+
表示当前选择的机械臂,修改的值需要与实际上的机械臂型号匹配,否则无法正常控制机械臂。当前可选机械臂参数及型号如下所示:
42+
43+
| 参数 | 机械臂型号 |
44+
|-----------------|----------------|
45+
| `MyCobotPro630` | MyCobot Pro630 |
46+
| `MyCobot320` | MyCobot320 M5 |
47+
| `MyArmM750` | MyArm M750 |
48+
| `Undefined` | / |
49+
50+
`COMPOSITE_KIT_TYPE = Undefined`时,表示不使用机械臂,此时手柄无法对机械臂进行控制,只对MyAGVPro有效。
51+
`COMPOSITE_KIT_COMPORT`代表机械臂的串口号,需要根据实际连接的机械臂修改串口号。 选择的机械臂为`myArmM750``MyCobot320`
52+
时需要配置。
53+
当选择的机械臂为`MyCobotPro630`时不需要配置, 因为控制`MyCobot Pro630`
54+
使用的是TCP协议,而不是串口协议。需要配置`COMPOSITE_KIT_HOST``COMPOSITE_KIT_PORT`的值。
55+
`COMPOSITE_KIT_HOST`表示机械臂的IP地址,`COMPOSITE_KIT_PORT`表示机械臂的端口号,默认为`5001`, 需要根据实际连接的机械臂进行修改。
56+
可以通过内置软件`roboflow`查看机械臂的IP地址和端口号。注意,此时机械臂应该和MyAGVPro在同一个局域网内。
57+
58+
5. 运行程序
59+
```shell
60+
python main.py
61+
```
62+
172 KB
Loading
Lines changed: 236 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,236 @@
1+
#!/usr/bin/env python
2+
# -*- coding: UTF-8 -*-
3+
import os
4+
import time
5+
from core import Number
6+
from core.joystick import InputJoystick, Hotkey
7+
from core.drive import AGVDriveAPI
8+
from core.controller import BaseControllerApi
9+
10+
11+
class AGVProCompositeKit(object):
12+
agvHorizontalSpeed: Number = Number(0.5, 0.1, 0.1)
13+
agvVerticalSpeed: Number = Number(0.75, 0.15, 0.15)
14+
agvRotationSpeed: Number = Number(1.5, 0.2, 0.1)
15+
16+
joystick = InputJoystick(raw_mapping=False)
17+
18+
def __init__(self, agv_pro_driver: AGVDriveAPI, arm_controller: BaseControllerApi):
19+
self.arm_controller = arm_controller
20+
self.agv_pro = agv_pro_driver
21+
22+
if self.agv_pro.is_power_on() is False:
23+
self.agv_pro.power_on()
24+
print(f" # Start the AGVPRO power supply.")
25+
else:
26+
print(f" # AGVPRO is already powered on.")
27+
28+
self.joystick.inject_caller(self)
29+
30+
self._agv_motion_control = False
31+
self._arm_motion_control = False
32+
33+
def init_joystick(self) -> bool:
34+
device = InputJoystick.get_gamepad(0)
35+
if device is not None:
36+
self.joystick.set_device(device)
37+
return device is not None
38+
39+
@joystick.register(hotkey=Hotkey.L1)
40+
def L1(self, value: int):
41+
if value == 1 and not self._agv_motion_control:
42+
self.agv_pro.rotate_right(self.agvRotationSpeed.value)
43+
self._agv_motion_control = True
44+
print(f" # Rotate right.")
45+
return
46+
47+
if value == 0 and self._agv_motion_control:
48+
self.agv_pro.stop()
49+
self._agv_motion_control = False
50+
print(f" # Stop rotating.")
51+
return
52+
53+
@joystick.register(hotkey=Hotkey.R1)
54+
def R1(self, value: int):
55+
if value == 1 and not self._agv_motion_control:
56+
self.agv_pro.rotate_left(self.agvRotationSpeed.value)
57+
self._agv_motion_control = True
58+
print(f" # Rotate left.")
59+
return
60+
61+
if value == 0 and self._agv_motion_control:
62+
self._agv_motion_control = False
63+
self.agv_pro.stop()
64+
print(f" # Stop rotating.")
65+
return
66+
67+
@joystick.register(hotkey=Hotkey.L2, value_filter=lambda value: value == 0)
68+
def L2(self, _: int):
69+
hs = self.agvHorizontalSpeed.decrease()
70+
vs = self.agvVerticalSpeed.decrease()
71+
rs = self.agvRotationSpeed.decrease()
72+
print(f" # Speed decreases {hs = :.2f} {vs = :.2f} {rs = :.2f}")
73+
74+
@joystick.register(hotkey=Hotkey.R2, value_filter=lambda value: value == 0)
75+
def R2(self, _: int):
76+
hs = self.agvHorizontalSpeed.increase()
77+
vs = self.agvVerticalSpeed.increase()
78+
rs = self.agvRotationSpeed.increase()
79+
print(f" # Speed increases {hs = :.2f} {vs = :.2f} {rs = :.2f}")
80+
81+
@joystick.register(hotkey=Hotkey.RIGHT_Y_AXIS)
82+
def RIGHT_X_AXIS(self, value: int):
83+
if value < 128 and not self._agv_motion_control:
84+
self.agv_pro.forward(self.agvVerticalSpeed.value)
85+
self._agv_motion_control = True
86+
print(f" # Move forward.")
87+
88+
elif value > 128 and not self._agv_motion_control:
89+
self.agv_pro.backward(self.agvVerticalSpeed.value)
90+
self._agv_motion_control = True
91+
print(f" # Move backward.")
92+
93+
elif value == 128 and self._agv_motion_control:
94+
self.agv_pro.stop()
95+
self._agv_motion_control = False
96+
print(f" # Stop moving.")
97+
98+
@joystick.register(hotkey=Hotkey.RIGHT_X_AXIS)
99+
def RIGHT_Y_AXIS(self, value: int):
100+
if value < 128 and not self._agv_motion_control:
101+
self._agv_motion_control = True
102+
self.agv_pro.pan_left(self.agvHorizontalSpeed.value)
103+
print(f" # Pan left.")
104+
105+
elif value > 128 and not self._agv_motion_control:
106+
self._agv_motion_control = True
107+
self.agv_pro.pan_right(self.agvHorizontalSpeed.value)
108+
print(f" # Pan right.")
109+
110+
elif value == 128 and self._agv_motion_control:
111+
self._agv_motion_control = False
112+
print(f" # Stop panning.")
113+
self.agv_pro.stop()
114+
115+
@joystick.register(hotkey=Hotkey.STARTUP, value_filter=lambda value: value == 0)
116+
def STARTUP(self, _):
117+
hs = self.agvHorizontalSpeed.reset()
118+
vs = self.agvVerticalSpeed.reset()
119+
rs = self.agvRotationSpeed.reset()
120+
121+
print(f" # Speed reset {hs = :.2f} {vs = :.2f} {rs = :.2f}")
122+
123+
if self.agv_pro.is_power_on() is False:
124+
print(f" # Abnormal power-off of AGVPRO has been detected, and it is trying to power on...")
125+
self.agv_pro.power_on()
126+
time.sleep(1)
127+
self.agv_pro.open_strip_light_diy_mode()
128+
self.agv_pro.set_strip_light_color([0, 1], (0, 255, 0), 255)
129+
else:
130+
self.agv_pro.stop()
131+
print(f" # Stop moving.")
132+
133+
self.arm_controller.go_home()
134+
self.arm_controller.close_suction_pump()
135+
136+
@joystick.register(hotkey=Hotkey.Y)
137+
def Y(self, value: int):
138+
print(f"{Hotkey.Y} {value}")
139+
if value == 1:
140+
print(f" # Open gripper.")
141+
self.arm_controller.open_gripper(1)
142+
else:
143+
self.arm_controller.stop()
144+
print(f" # Stop opening the gripper.")
145+
146+
@joystick.register(hotkey=Hotkey.A)
147+
def A(self, value: int):
148+
if value == 1:
149+
print(f" # Close gripper.")
150+
self.arm_controller.close_gripper(1)
151+
else:
152+
self.arm_controller.stop()
153+
print(f" # Stop closing the gripper.")
154+
155+
@joystick.register(hotkey=Hotkey.X, value_filter=lambda value: value == 0)
156+
def X(self, _: int):
157+
try:
158+
self.arm_controller.open_suction_pump()
159+
print(f"Open suction pump.")
160+
except NotImplementedError as e:
161+
print(e)
162+
163+
@joystick.register(hotkey=Hotkey.B, value_filter=lambda value: value == 0)
164+
def B(self, _: int):
165+
try:
166+
self.arm_controller.close_suction_pump()
167+
print(f"Close suction pump.")
168+
except NotImplementedError as e:
169+
print(e)
170+
171+
@joystick.register(hotkey=Hotkey.HORIZONTAL)
172+
def HORIZONTAL(self, value: int):
173+
if value == 1:
174+
print(f" # The end is rotated counterclockwise.")
175+
self.arm_controller.set_end_rotate(direction=-1, speed=1)
176+
177+
elif value == -1:
178+
print(f" # The end is rotate clockwise.")
179+
self.arm_controller.set_end_rotate(direction=1, speed=1)
180+
181+
else:
182+
print(" # Stop spinning.")
183+
self.arm_controller.stop()
184+
185+
@joystick.register(hotkey=Hotkey.VERTICAL)
186+
def VERTICAL(self, value: int):
187+
if value == -1:
188+
print(f"axis z +.")
189+
self.arm_controller.coordinate(axis=3, direction=1)
190+
elif value == 1:
191+
print(f"axis Z -.")
192+
self.arm_controller.coordinate(axis=3, direction=0)
193+
else:
194+
print("axis z stop.")
195+
self.arm_controller.stop()
196+
197+
@joystick.register(hotkey=Hotkey.LEFT_X_AXIS)
198+
def LEFT_X_AXIS(self, value: int):
199+
if value > 128 and not self._arm_motion_control:
200+
print(f"axis y -.") # Y+
201+
self.arm_controller.coordinate(axis=2, direction=0)
202+
self._arm_motion_control = True
203+
204+
elif value < 128 and not self._arm_motion_control:
205+
print(f"axis y +.") # Y-
206+
self.arm_controller.coordinate(axis=2, direction=1)
207+
self._arm_motion_control = True
208+
209+
elif value == 128 and self._arm_motion_control:
210+
self._arm_motion_control = False
211+
print(f"axis y stop.")
212+
self.arm_controller.stop()
213+
214+
@joystick.register(hotkey=Hotkey.LEFT_Y_AXIS)
215+
def LEFT_Y_AXIS(self, value: int):
216+
if value < 128 and not self._arm_motion_control:
217+
print(f"axis x +.") # X+
218+
self.arm_controller.coordinate(axis=1, direction=1)
219+
self._arm_motion_control = True
220+
221+
elif value > 128 and not self._arm_motion_control:
222+
print(f"axis x -.") # X-
223+
self.arm_controller.coordinate(axis=1, direction=0)
224+
self._arm_motion_control = True
225+
226+
elif value == 128 and self._arm_motion_control:
227+
self._arm_motion_control = False
228+
print(f"axis x stop.")
229+
self.arm_controller.stop()
230+
231+
def mainloop(self):
232+
self.joystick.run_with_loop()
233+
234+
235+
236+

0 commit comments

Comments
 (0)