xarm-python-sdk 1.15.2__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- xarm/__init__.py +2 -0
- xarm/build_backend.py +17 -0
- xarm/core/__init__.py +2 -0
- xarm/core/comm/__init__.py +5 -0
- xarm/core/comm/base.py +303 -0
- xarm/core/comm/serial_port.py +44 -0
- xarm/core/comm/socket_port.py +150 -0
- xarm/core/comm/uxbus_cmd_protocol.py +100 -0
- xarm/core/config/__init__.py +0 -0
- xarm/core/config/x_code.py +1427 -0
- xarm/core/config/x_config.py +553 -0
- xarm/core/utils/__init__.py +3 -0
- xarm/core/utils/convert.py +124 -0
- xarm/core/utils/crc16.py +76 -0
- xarm/core/utils/debug_print.py +21 -0
- xarm/core/utils/log.py +98 -0
- xarm/core/version.py +1 -0
- xarm/core/wrapper/__init__.py +11 -0
- xarm/core/wrapper/uxbus_cmd.py +1457 -0
- xarm/core/wrapper/uxbus_cmd_ser.py +94 -0
- xarm/core/wrapper/uxbus_cmd_tcp.py +305 -0
- xarm/tools/__init__.py +0 -0
- xarm/tools/blockly/__init__.py +1 -0
- xarm/tools/blockly/_blockly_base.py +416 -0
- xarm/tools/blockly/_blockly_handler.py +1338 -0
- xarm/tools/blockly/_blockly_highlight.py +94 -0
- xarm/tools/blockly/_blockly_node.py +61 -0
- xarm/tools/blockly/_blockly_tool.py +480 -0
- xarm/tools/blockly_tool.py +1864 -0
- xarm/tools/gcode.py +90 -0
- xarm/tools/list_ports.py +39 -0
- xarm/tools/modbus_tcp.py +205 -0
- xarm/tools/threads.py +30 -0
- xarm/tools/utils.py +36 -0
- xarm/version.py +1 -0
- xarm/wrapper/__init__.py +1 -0
- xarm/wrapper/studio_api.py +34 -0
- xarm/wrapper/xarm_api.py +4416 -0
- xarm/x3/__init__.py +2 -0
- xarm/x3/base.py +2638 -0
- xarm/x3/base_board.py +198 -0
- xarm/x3/code.py +62 -0
- xarm/x3/decorator.py +104 -0
- xarm/x3/events.py +166 -0
- xarm/x3/ft_sensor.py +264 -0
- xarm/x3/gpio.py +457 -0
- xarm/x3/grammar_async.py +21 -0
- xarm/x3/grammar_coroutine.py +24 -0
- xarm/x3/gripper.py +830 -0
- xarm/x3/modbus_tcp.py +84 -0
- xarm/x3/parse.py +110 -0
- xarm/x3/record.py +216 -0
- xarm/x3/report.py +204 -0
- xarm/x3/robotiq.py +220 -0
- xarm/x3/servo.py +485 -0
- xarm/x3/studio.py +138 -0
- xarm/x3/track.py +424 -0
- xarm/x3/utils.py +43 -0
- xarm/x3/xarm.py +1928 -0
- xarm_python_sdk-1.15.2.dist-info/METADATA +103 -0
- xarm_python_sdk-1.15.2.dist-info/RECORD +63 -0
- xarm_python_sdk-1.15.2.dist-info/WHEEL +4 -0
- xarm_python_sdk-1.15.2.dist-info/licenses/LICENSE +27 -0
xarm/x3/ft_sensor.py
ADDED
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
# Software License Agreement (BSD License)
|
|
3
|
+
#
|
|
4
|
+
# Copyright (c) 2021, UFACTORY, Inc.
|
|
5
|
+
# All rights reserved.
|
|
6
|
+
#
|
|
7
|
+
# Author: Vinman <vinman.wen@ufactory.cc> <vinman.cub@gmail.com>
|
|
8
|
+
import time
|
|
9
|
+
from ..core.utils.log import logger
|
|
10
|
+
from ..core.utils import convert
|
|
11
|
+
from .base import Base
|
|
12
|
+
from .code import APIState
|
|
13
|
+
from .decorator import xarm_is_connected
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class FtSensor(Base):
|
|
17
|
+
def __init__(self):
|
|
18
|
+
super(FtSensor, self).__init__()
|
|
19
|
+
|
|
20
|
+
@xarm_is_connected(_type='set')
|
|
21
|
+
def set_impedance(self, coord, c_axis, M, K, B, **kwargs):
|
|
22
|
+
if len(c_axis) < 6 or len(M) < 6 or len(K) < 6 or len(B) < 6:
|
|
23
|
+
logger.error('set_impedance: parameters error')
|
|
24
|
+
return APIState.API_EXCEPTION
|
|
25
|
+
params_limit = kwargs.get('params_limit', True)
|
|
26
|
+
if params_limit:
|
|
27
|
+
for i in range(6):
|
|
28
|
+
if i < 3:
|
|
29
|
+
if M[i] < 0.02 or M[i] > 1.0:
|
|
30
|
+
logger.error('set_impedance, M[{}] over range, range=[0.02, 1.0]'.format(i))
|
|
31
|
+
return APIState.API_EXCEPTION
|
|
32
|
+
if K[i] < 0 or K[i] > 2000:
|
|
33
|
+
logger.error('set_impedance, K[{}] over range, range=[0, 2000]'.format(i))
|
|
34
|
+
return APIState.API_EXCEPTION
|
|
35
|
+
else:
|
|
36
|
+
if M[i] < 0.0001 or M[i] > 0.01:
|
|
37
|
+
logger.error('set_impedance, M[{}] over range, range=[0.0001, 0.01]'.format(i))
|
|
38
|
+
return APIState.API_EXCEPTION
|
|
39
|
+
if K[i] < 0 or K[i] > 20:
|
|
40
|
+
logger.error('set_impedance, K[{}] over range, range=[0, 20]'.format(i))
|
|
41
|
+
return APIState.API_EXCEPTION
|
|
42
|
+
if B[i] < 0:
|
|
43
|
+
logger.error('set_impedance, the value of B[{}] must be greater than or equal to 0'.format(i))
|
|
44
|
+
return APIState.API_EXCEPTION
|
|
45
|
+
ret = self.arm_cmd.set_impedance(coord, c_axis, M, K, B)
|
|
46
|
+
self.log_api_info('API -> set_impedance -> code={}'.format(ret[0]), code=ret[0])
|
|
47
|
+
return self._check_code(ret[0])
|
|
48
|
+
|
|
49
|
+
@xarm_is_connected(_type='set')
|
|
50
|
+
def set_impedance_mbk(self, M, K, B, **kwargs):
|
|
51
|
+
if len(M) < 6 or len(K) < 6 or len(B) < 6:
|
|
52
|
+
logger.error('set_impedance_mbk: parameters error')
|
|
53
|
+
return APIState.API_EXCEPTION
|
|
54
|
+
params_limit = kwargs.get('params_limit', True)
|
|
55
|
+
if params_limit:
|
|
56
|
+
for i in range(6):
|
|
57
|
+
if i < 3:
|
|
58
|
+
if M[i] < 0.02 or M[i] > 1.0:
|
|
59
|
+
logger.error('set_impedance_mbk, M[{}] over range, range=[0.02, 1.0]'.format(i))
|
|
60
|
+
return APIState.API_EXCEPTION
|
|
61
|
+
if K[i] < 0 or K[i] > 2000:
|
|
62
|
+
logger.error('set_impedance_mbk, K[{}] over range, range=[0, 2000]'.format(i))
|
|
63
|
+
return APIState.API_EXCEPTION
|
|
64
|
+
else:
|
|
65
|
+
if M[i] < 0.0001 or M[i] > 0.01:
|
|
66
|
+
logger.error('set_impedance_mbk, M[{}] over range, range=[0.0001, 0.01]'.format(i))
|
|
67
|
+
return APIState.API_EXCEPTION
|
|
68
|
+
if K[i] < 0 or K[i] > 20:
|
|
69
|
+
logger.error('set_impedance_mbk, K[{}] over range, range=[0, 20]'.format(i))
|
|
70
|
+
return APIState.API_EXCEPTION
|
|
71
|
+
if B[i] < 0:
|
|
72
|
+
logger.error('set_impedance_mbk, the value of B[{}] must be greater than or equal to 0'.format(i))
|
|
73
|
+
return APIState.API_EXCEPTION
|
|
74
|
+
ret = self.arm_cmd.set_impedance_mbk(M, K, B)
|
|
75
|
+
self.log_api_info('API -> set_impedance_mbk -> code={}'.format(ret[0]), code=ret[0])
|
|
76
|
+
return self._check_code(ret[0])
|
|
77
|
+
|
|
78
|
+
@xarm_is_connected(_type='set')
|
|
79
|
+
def set_impedance_config(self, coord, c_axis):
|
|
80
|
+
if len(c_axis) < 6:
|
|
81
|
+
logger.error('set_impedance_config: parameters error')
|
|
82
|
+
return APIState.API_EXCEPTION
|
|
83
|
+
ret = self.arm_cmd.set_impedance_config(coord, c_axis)
|
|
84
|
+
self.log_api_info('API -> set_impedance_config -> code={}'.format(ret[0]), code=ret[0])
|
|
85
|
+
return self._check_code(ret[0])
|
|
86
|
+
|
|
87
|
+
@xarm_is_connected(_type='set')
|
|
88
|
+
def config_force_control(self, coord, c_axis, f_ref, limits, **kwargs):
|
|
89
|
+
if len(c_axis) < 6 or len(f_ref) < 6 or len(limits) < 6:
|
|
90
|
+
logger.error('config_force_control: parameters error')
|
|
91
|
+
return APIState.API_EXCEPTION
|
|
92
|
+
params_limit = kwargs.get('params_limit', True)
|
|
93
|
+
if params_limit:
|
|
94
|
+
max_f_ref = [150, 150, 200, 4, 4, 4]
|
|
95
|
+
for i in range(6):
|
|
96
|
+
if f_ref[i] < -max_f_ref[i] or f_ref[i] > max_f_ref[i]:
|
|
97
|
+
logger.error('config_force_control, f_ref[{}] over range, range=[{}, {}]'.format(i, -max_f_ref[i], max_f_ref[i]))
|
|
98
|
+
return APIState.API_EXCEPTION
|
|
99
|
+
ret = self.arm_cmd.config_force_control(coord, c_axis, f_ref, limits)
|
|
100
|
+
self.log_api_info('API -> config_force_control -> code={}'.format(ret[0]), code=ret[0])
|
|
101
|
+
return self._check_code(ret[0])
|
|
102
|
+
|
|
103
|
+
@xarm_is_connected(_type='set')
|
|
104
|
+
def set_force_control_pid(self, kp, ki, kd, xe_limit, **kwargs):
|
|
105
|
+
if len(kp) < 6 or len(ki) < 6 or len(kd) < 6 or len(xe_limit) < 6:
|
|
106
|
+
logger.error('set_force_control_pid: parameters error')
|
|
107
|
+
return APIState.API_EXCEPTION
|
|
108
|
+
params_limit = kwargs.get('params_limit', True)
|
|
109
|
+
if params_limit:
|
|
110
|
+
for i in range(6):
|
|
111
|
+
if kp[i] < 0 or kp[i] > 0.05:
|
|
112
|
+
logger.error('set_force_control_pid, kp[{}] over range, range=[0, 0.05]'.format(i))
|
|
113
|
+
return APIState.API_EXCEPTION
|
|
114
|
+
if ki[i] < 0 or ki[i] > 0.0005:
|
|
115
|
+
logger.error('set_force_control_pid, ki[{}] over range, range=[0, 0.0005]'.format(i))
|
|
116
|
+
return APIState.API_EXCEPTION
|
|
117
|
+
if kd[i] < 0 or kd[i] > 0.05:
|
|
118
|
+
logger.error('set_force_control_pid, kd[{}] over range, range=[0, 0.05]'.format(i))
|
|
119
|
+
return APIState.API_EXCEPTION
|
|
120
|
+
if xe_limit[i] < 0 or xe_limit[i] > 200:
|
|
121
|
+
logger.error('set_force_control_pid, xe_limit[{}] over range, range=[0, 200]'.format(i))
|
|
122
|
+
return APIState.API_EXCEPTION
|
|
123
|
+
ret = self.arm_cmd.set_force_control_pid(kp, ki, kd, xe_limit)
|
|
124
|
+
self.log_api_info('API -> set_force_control_pid -> code={}'.format(ret[0]), code=ret[0])
|
|
125
|
+
return self._check_code(ret[0])
|
|
126
|
+
|
|
127
|
+
@xarm_is_connected(_type='set')
|
|
128
|
+
def ft_sensor_set_zero(self):
|
|
129
|
+
ret = self.arm_cmd.ft_sensor_set_zero()
|
|
130
|
+
self.log_api_info('API -> ft_sensor_set_zero -> code={}'.format(ret[0]), code=ret[0])
|
|
131
|
+
return self._check_code(ret[0])
|
|
132
|
+
|
|
133
|
+
@xarm_is_connected(_type='get')
|
|
134
|
+
def ft_sensor_iden_load(self):
|
|
135
|
+
protocol_identifier = self.arm_cmd.get_protocol_identifier()
|
|
136
|
+
self.arm_cmd.set_protocol_identifier(2)
|
|
137
|
+
self._keep_heart = False
|
|
138
|
+
ret = self.arm_cmd.ft_sensor_iden_load()
|
|
139
|
+
self.arm_cmd.set_protocol_identifier(protocol_identifier)
|
|
140
|
+
self._keep_heart = True
|
|
141
|
+
self.log_api_info('API -> ft_sensor_iden_load -> code={}'.format(ret[0]), code=ret[0])
|
|
142
|
+
code = self._check_code(ret[0])
|
|
143
|
+
if code == 0 or len(ret) > 5:
|
|
144
|
+
ret[2] = ret[2] * 1000 # x_centroid, 从m转成mm
|
|
145
|
+
ret[3] = ret[3] * 1000 # y_centroid, 从m转成mm
|
|
146
|
+
ret[4] = ret[4] * 1000 # z_centroid, 从m转成mm
|
|
147
|
+
return self._check_code(ret[0]), ret[1:11]
|
|
148
|
+
|
|
149
|
+
@xarm_is_connected(_type='set')
|
|
150
|
+
def ft_sensor_cali_load(self, iden_result_list, association_setting_tcp_load=False, **kwargs):
|
|
151
|
+
if len(iden_result_list) < 10:
|
|
152
|
+
return APIState.PARAM_ERROR
|
|
153
|
+
params = iden_result_list[:]
|
|
154
|
+
params[1] = params[1] / 1000.0 # x_centroid, 从mm转成m
|
|
155
|
+
params[2] = params[2] / 1000.0 # y_centroid, 从mm转成m
|
|
156
|
+
params[3] = params[3] / 1000.0 # z_centroid, 从mm转成m
|
|
157
|
+
ret = self.arm_cmd.ft_sensor_cali_load(params)
|
|
158
|
+
self.log_api_info('API -> ft_sensor_cali_load -> code={}, iden_result_list={}'.format(ret[0], iden_result_list), code=ret[0])
|
|
159
|
+
ret[0] = self._check_code(ret[0])
|
|
160
|
+
if ret[0] == 0 and association_setting_tcp_load:
|
|
161
|
+
m = kwargs.get('m', 0.270) # 0.325
|
|
162
|
+
x = kwargs.get('x', -17)
|
|
163
|
+
y = kwargs.get('y', 9)
|
|
164
|
+
z = kwargs.get('z', 11.8)
|
|
165
|
+
weight = params[0] + m
|
|
166
|
+
center_of_gravity = [
|
|
167
|
+
(m * x + params[0] * params[1]) / weight,
|
|
168
|
+
(m * y + params[0] * params[2]) / weight,
|
|
169
|
+
(m * z + params[0] * (32 + params[3])) / weight
|
|
170
|
+
]
|
|
171
|
+
self.set_state(0)
|
|
172
|
+
return self.set_tcp_load(weight, center_of_gravity)
|
|
173
|
+
return ret[0]
|
|
174
|
+
|
|
175
|
+
@xarm_is_connected(_type='set')
|
|
176
|
+
def ft_sensor_enable(self, on_off):
|
|
177
|
+
ret = self.arm_cmd.ft_sensor_enable(on_off)
|
|
178
|
+
self.log_api_info('API -> ft_sensor_enable -> code={}, on_off={}'.format(ret[0], on_off), code=ret[0])
|
|
179
|
+
return self._check_code(ret[0])
|
|
180
|
+
|
|
181
|
+
@xarm_is_connected(_type='get')
|
|
182
|
+
def ft_sensor_app_set(self, app_code):
|
|
183
|
+
ret = self.arm_cmd.ft_sensor_app_set(app_code)
|
|
184
|
+
self.log_api_info('API -> ft_sensor_app_set -> code={}, app_code={}'.format(ret[0], app_code), code=ret[0])
|
|
185
|
+
return self._check_code(ret[0])
|
|
186
|
+
|
|
187
|
+
@xarm_is_connected(_type='get')
|
|
188
|
+
def ft_sensor_app_get(self):
|
|
189
|
+
ret = self.arm_cmd.ft_sensor_app_get()
|
|
190
|
+
return self._check_code(ret[0]), ret[1]
|
|
191
|
+
|
|
192
|
+
@xarm_is_connected(_type='get')
|
|
193
|
+
def get_ft_sensor_data(self):
|
|
194
|
+
ret = self.arm_cmd.ft_sensor_get_data(self.version_is_ge(1, 8, 3))
|
|
195
|
+
return self._check_code(ret[0]), ret[1:7]
|
|
196
|
+
|
|
197
|
+
@xarm_is_connected(_type='get')
|
|
198
|
+
def get_ft_sensor_config(self):
|
|
199
|
+
ret = self.arm_cmd.ft_sensor_get_config()
|
|
200
|
+
ret[0] = self._check_code(ret[0])
|
|
201
|
+
return ret[0], ret[1:]
|
|
202
|
+
|
|
203
|
+
@xarm_is_connected(_type='get')
|
|
204
|
+
def get_ft_sensor_error(self):
|
|
205
|
+
ret = self.arm_cmd.ft_sensor_get_error()
|
|
206
|
+
ret[0] = self._check_code(ret[0])
|
|
207
|
+
return ret[0], ret[1]
|
|
208
|
+
|
|
209
|
+
def set_ft_sensor_sn(self, sn):
|
|
210
|
+
assert len(sn) >= 14, 'The length of SN is wrong'
|
|
211
|
+
ret = [0]
|
|
212
|
+
if len(sn) == 14:
|
|
213
|
+
for i in range(0, 14):
|
|
214
|
+
value = ord(sn[i])
|
|
215
|
+
if i < 8:
|
|
216
|
+
ret = self.arm_cmd.servo_addr_w16(8, 0x1300+i, value)
|
|
217
|
+
ret[0] = self._check_code(ret[0])
|
|
218
|
+
else:
|
|
219
|
+
ret = self.arm_cmd.servo_addr_w16(8, 0x1400+(i-8), value)
|
|
220
|
+
ret[0] = self._check_code(ret[0])
|
|
221
|
+
if ret[0] != 0:
|
|
222
|
+
break
|
|
223
|
+
time.sleep(0.05)
|
|
224
|
+
self.log_api_info('API -> set_ft_sensor_sn -> code={}, sn={}'.format(ret[0], sn), code=ret[0])
|
|
225
|
+
return ret[0]
|
|
226
|
+
|
|
227
|
+
def get_ft_sensor_sn(self):
|
|
228
|
+
rd_sn = ''
|
|
229
|
+
ret = [0, '']
|
|
230
|
+
for i in range(0, 14):
|
|
231
|
+
if i < 8:
|
|
232
|
+
ret = self.arm_cmd.servo_addr_r16(8, 0x0300+i)
|
|
233
|
+
ret[0] = self._check_code(ret[0])
|
|
234
|
+
else:
|
|
235
|
+
ret = self.arm_cmd.servo_addr_r16(8, 0x0400+(i-8))
|
|
236
|
+
ret[0] = self._check_code(ret[0])
|
|
237
|
+
if i < 2 and ret[-1] not in [65, 73]:
|
|
238
|
+
return 1, "********"
|
|
239
|
+
|
|
240
|
+
if chr(ret[-1]).isalnum():
|
|
241
|
+
rd_sn = ''.join([rd_sn, chr(ret[-1])])
|
|
242
|
+
else:
|
|
243
|
+
rd_sn = ''.join([rd_sn, '*'])
|
|
244
|
+
time.sleep(0.05)
|
|
245
|
+
self.log_api_info('API -> get_ft_sensor_sn -> code={}, sn={}'.format(ret[0], rd_sn), code=ret[0])
|
|
246
|
+
return ret[0], rd_sn
|
|
247
|
+
|
|
248
|
+
def get_ft_sensor_version(self):
|
|
249
|
+
versions = ['*', '*', '*']
|
|
250
|
+
ret1 = self.arm_cmd.servo_addr_r16(8, 0x0801)
|
|
251
|
+
ret1[0] = self._check_code(ret1[0])
|
|
252
|
+
ret2 = self.arm_cmd.servo_addr_r16(8, 0x0802)
|
|
253
|
+
ret2[0] = self._check_code(ret2[0])
|
|
254
|
+
ret3 = self.arm_cmd.servo_addr_r16(8, 0x0803)
|
|
255
|
+
ret3[0] = self._check_code(ret3[0])
|
|
256
|
+
|
|
257
|
+
if ret1[0] == 0 and ret1[1] < 10:
|
|
258
|
+
versions[0] = ret1[1]
|
|
259
|
+
if ret2[0] == 0 and ret1[1] < 100:
|
|
260
|
+
versions[1] = ret2[1]
|
|
261
|
+
if ret3[0] == 0 and ret1[1] < 1000:
|
|
262
|
+
versions[2] = ret3[1]
|
|
263
|
+
|
|
264
|
+
return ret1[0] or ret2[0] or ret3[0], '.'.join(map(str, versions))
|