kuavo-humanoid-sdk 1.2.1b3279__20250911210455-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.

Potentially problematic release.


This version of kuavo-humanoid-sdk might be problematic. Click here for more details.

Files changed (184) hide show
  1. kuavo_humanoid_sdk/__init__.py +6 -0
  2. kuavo_humanoid_sdk/common/logger.py +45 -0
  3. kuavo_humanoid_sdk/interfaces/__init__.py +4 -0
  4. kuavo_humanoid_sdk/interfaces/data_types.py +288 -0
  5. kuavo_humanoid_sdk/interfaces/end_effector.py +62 -0
  6. kuavo_humanoid_sdk/interfaces/robot.py +22 -0
  7. kuavo_humanoid_sdk/interfaces/robot_info.py +56 -0
  8. kuavo_humanoid_sdk/kuavo/__init__.py +16 -0
  9. kuavo_humanoid_sdk/kuavo/core/audio.py +32 -0
  10. kuavo_humanoid_sdk/kuavo/core/core.py +666 -0
  11. kuavo_humanoid_sdk/kuavo/core/dex_hand_control.py +114 -0
  12. kuavo_humanoid_sdk/kuavo/core/leju_claw_control.py +67 -0
  13. kuavo_humanoid_sdk/kuavo/core/llm_doubao.py +608 -0
  14. kuavo_humanoid_sdk/kuavo/core/microphone.py +192 -0
  15. kuavo_humanoid_sdk/kuavo/core/navigation.py +70 -0
  16. kuavo_humanoid_sdk/kuavo/core/ros/audio.py +110 -0
  17. kuavo_humanoid_sdk/kuavo/core/ros/control.py +1524 -0
  18. kuavo_humanoid_sdk/kuavo/core/ros/microphone.py +38 -0
  19. kuavo_humanoid_sdk/kuavo/core/ros/navigation.py +217 -0
  20. kuavo_humanoid_sdk/kuavo/core/ros/observation.py +94 -0
  21. kuavo_humanoid_sdk/kuavo/core/ros/param.py +201 -0
  22. kuavo_humanoid_sdk/kuavo/core/ros/sat_utils.py +103 -0
  23. kuavo_humanoid_sdk/kuavo/core/ros/state.py +652 -0
  24. kuavo_humanoid_sdk/kuavo/core/ros/tools.py +220 -0
  25. kuavo_humanoid_sdk/kuavo/core/ros/vision.py +234 -0
  26. kuavo_humanoid_sdk/kuavo/core/ros_env.py +238 -0
  27. kuavo_humanoid_sdk/kuavo/demo_climbstair.py +249 -0
  28. kuavo_humanoid_sdk/kuavo/dexterous_hand.py +238 -0
  29. kuavo_humanoid_sdk/kuavo/leju_claw.py +235 -0
  30. kuavo_humanoid_sdk/kuavo/logger_client.py +80 -0
  31. kuavo_humanoid_sdk/kuavo/robot.py +561 -0
  32. kuavo_humanoid_sdk/kuavo/robot_arm.py +299 -0
  33. kuavo_humanoid_sdk/kuavo/robot_audio.py +39 -0
  34. kuavo_humanoid_sdk/kuavo/robot_blockly.py +1162 -0
  35. kuavo_humanoid_sdk/kuavo/robot_climbstair.py +1607 -0
  36. kuavo_humanoid_sdk/kuavo/robot_head.py +74 -0
  37. kuavo_humanoid_sdk/kuavo/robot_info.py +134 -0
  38. kuavo_humanoid_sdk/kuavo/robot_microphone.py +19 -0
  39. kuavo_humanoid_sdk/kuavo/robot_navigation.py +135 -0
  40. kuavo_humanoid_sdk/kuavo/robot_observation.py +64 -0
  41. kuavo_humanoid_sdk/kuavo/robot_speech.py +24 -0
  42. kuavo_humanoid_sdk/kuavo/robot_state.py +310 -0
  43. kuavo_humanoid_sdk/kuavo/robot_tool.py +109 -0
  44. kuavo_humanoid_sdk/kuavo/robot_vision.py +81 -0
  45. kuavo_humanoid_sdk/kuavo_strategy/__init__.py +2 -0
  46. kuavo_humanoid_sdk/kuavo_strategy/grasp_box/grasp_box_strategy.py +1325 -0
  47. kuavo_humanoid_sdk/kuavo_strategy/kuavo_strategy.py +106 -0
  48. kuavo_humanoid_sdk/kuavo_strategy_v2/common/data_type.py +340 -0
  49. kuavo_humanoid_sdk/kuavo_strategy_v2/common/events/base_event.py +215 -0
  50. kuavo_humanoid_sdk/kuavo_strategy_v2/common/robot_sdk.py +25 -0
  51. kuavo_humanoid_sdk/kuavo_strategy_v2/pick_place_box/case.py +331 -0
  52. kuavo_humanoid_sdk/kuavo_strategy_v2/pick_place_box/strategy.py +504 -0
  53. kuavo_humanoid_sdk/kuavo_strategy_v2/utils/logger_setup.py +40 -0
  54. kuavo_humanoid_sdk/kuavo_strategy_v2/utils/utils.py +88 -0
  55. kuavo_humanoid_sdk/msg/__init__.py +4 -0
  56. kuavo_humanoid_sdk/msg/kuavo_msgs/__init__.py +7 -0
  57. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_AprilTagDetection.py +306 -0
  58. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_AprilTagDetectionArray.py +437 -0
  59. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_AudioReceiverData.py +122 -0
  60. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_FTsensorData.py +260 -0
  61. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_JoySticks.py +191 -0
  62. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_Metadata.py +199 -0
  63. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_MmDetectionMsg.py +264 -0
  64. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_RobotActionState.py +112 -0
  65. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_TFArray.py +323 -0
  66. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_TaskPoint.py +175 -0
  67. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/__init__.py +62 -0
  68. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_armCollisionCheckInfo.py +160 -0
  69. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_armHandPose.py +161 -0
  70. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_armHandPoseFree.py +171 -0
  71. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_armPoseWithTimeStamp.py +168 -0
  72. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_armTargetPoses.py +171 -0
  73. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_bezierCurveCubicPoint.py +178 -0
  74. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_dexhandCommand.py +229 -0
  75. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_dexhandTouchState.py +256 -0
  76. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_endEffectorData.py +227 -0
  77. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPose.py +123 -0
  78. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPose6D.py +123 -0
  79. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPose6DTargetTrajectories.py +320 -0
  80. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPoseTargetTrajectories.py +301 -0
  81. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPoseWithVision.py +136 -0
  82. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPoseWithVisionArray.py +231 -0
  83. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPoses.py +149 -0
  84. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_footPoses6D.py +149 -0
  85. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_fullBodyTargetTrajectories.py +258 -0
  86. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_gaitTimeName.py +147 -0
  87. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_gestureInfo.py +218 -0
  88. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_gestureTask.py +149 -0
  89. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_handPose.py +136 -0
  90. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_headBodyPose.py +145 -0
  91. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_ikSolveError.py +171 -0
  92. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_ikSolveParam.py +140 -0
  93. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_imuData.py +165 -0
  94. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_jointBezierTrajectory.py +201 -0
  95. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_jointCmd.py +390 -0
  96. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_jointData.py +205 -0
  97. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_kuavoModeSchedule.py +224 -0
  98. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_lejuClawCommand.py +320 -0
  99. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_lejuClawState.py +341 -0
  100. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_motorParam.py +122 -0
  101. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_picoPoseInfo.py +143 -0
  102. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_picoPoseInfoList.py +220 -0
  103. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_planArmState.py +120 -0
  104. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_qv.py +121 -0
  105. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_robotArmQVVD.py +177 -0
  106. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_robotBodyMatrices.py +332 -0
  107. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_robotHandPosition.py +225 -0
  108. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_robotHeadMotionData.py +128 -0
  109. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_robotState.py +222 -0
  110. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_sensorsData.py +655 -0
  111. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_switchGaitByName.py +200 -0
  112. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_tagDataArray.py +216 -0
  113. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_touchSensorStatus.py +162 -0
  114. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_twoArmHandPose.py +273 -0
  115. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_twoArmHandPoseCmd.py +316 -0
  116. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_twoArmHandPoseCmdFree.py +338 -0
  117. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_twoArmHandPoseFree.py +299 -0
  118. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_yoloDetection.py +251 -0
  119. kuavo_humanoid_sdk/msg/kuavo_msgs/msg/_yoloOutputData.py +168 -0
  120. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_CreatePath.py +581 -0
  121. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_ExecuteArmAction.py +281 -0
  122. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_GetAllMaps.py +241 -0
  123. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_GetCurrentMap.py +225 -0
  124. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_GetTargetPartPoseInCamera.py +298 -0
  125. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_InitialPoseWithTaskPoint.py +281 -0
  126. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_LoadMap.py +281 -0
  127. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_NavigateToTaskPoint.py +281 -0
  128. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_RepublishTFs.py +373 -0
  129. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_SetInitialPose.py +394 -0
  130. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_SetJoyTopic.py +282 -0
  131. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_SetLEDMode.py +468 -0
  132. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_SetLEDMode_free.py +289 -0
  133. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_SpeechSynthesis.py +270 -0
  134. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_TaskPointOperation.py +536 -0
  135. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/__init__.py +43 -0
  136. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_adjustZeroPoint.py +277 -0
  137. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_changeArmCtrlMode.py +275 -0
  138. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_changeArmCtrlModeKuavo.py +236 -0
  139. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_changeMotorParam.py +299 -0
  140. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_changeTorsoCtrlMode.py +274 -0
  141. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_controlLejuClaw.py +408 -0
  142. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_enableHandTouchSensor.py +304 -0
  143. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_fkSrv.py +395 -0
  144. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_footPose6DTargetTrajectoriesSrv.py +426 -0
  145. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_footPoseTargetTrajectoriesSrv.py +409 -0
  146. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_gestureExecute.py +339 -0
  147. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_gestureExecuteState.py +257 -0
  148. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_gestureList.py +418 -0
  149. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_getCurrentGaitName.py +253 -0
  150. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_getMotorParam.py +299 -0
  151. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_getMotorZeroPoints.py +286 -0
  152. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_handForceLevel.py +330 -0
  153. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_jointMoveTo.py +302 -0
  154. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_planArmTrajectoryBezierCurve.py +422 -0
  155. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_planArmTrajectoryCubicSpline.py +490 -0
  156. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_playmusic.py +268 -0
  157. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_setHwIntialState.py +304 -0
  158. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_setMmCtrlFrame.py +273 -0
  159. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_setMotorEncoderRoundService.py +283 -0
  160. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_setTagId.py +275 -0
  161. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_singleStepControl.py +444 -0
  162. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_twoArmHandPoseCmdFreeSrv.py +716 -0
  163. kuavo_humanoid_sdk/msg/kuavo_msgs/srv/_twoArmHandPoseCmdSrv.py +664 -0
  164. kuavo_humanoid_sdk/msg/motion_capture_ik/__init__.py +7 -0
  165. kuavo_humanoid_sdk/msg/ocs2_msgs/__init__.py +7 -0
  166. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/__init__.py +12 -0
  167. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_constraint.py +142 -0
  168. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_controller_data.py +121 -0
  169. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_lagrangian_metrics.py +148 -0
  170. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mode_schedule.py +150 -0
  171. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_flattened_controller.py +666 -0
  172. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_input.py +122 -0
  173. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_observation.py +209 -0
  174. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_performance_indices.py +140 -0
  175. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_solver_data.py +886 -0
  176. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_state.py +122 -0
  177. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_mpc_target_trajectories.py +239 -0
  178. kuavo_humanoid_sdk/msg/ocs2_msgs/msg/_multiplier.py +148 -0
  179. kuavo_humanoid_sdk/msg/ocs2_msgs/srv/__init__.py +1 -0
  180. kuavo_humanoid_sdk/msg/ocs2_msgs/srv/_reset.py +376 -0
  181. kuavo_humanoid_sdk-1.2.1b3279.dist-info/METADATA +296 -0
  182. kuavo_humanoid_sdk-1.2.1b3279.dist-info/RECORD +184 -0
  183. kuavo_humanoid_sdk-1.2.1b3279.dist-info/WHEEL +6 -0
  184. kuavo_humanoid_sdk-1.2.1b3279.dist-info/top_level.txt +1 -0
@@ -0,0 +1,235 @@
1
+ #!/usr/bin/env python3
2
+ # coding: utf-8
3
+ import time
4
+ from typing import Tuple
5
+ from kuavo_humanoid_sdk.interfaces.end_effector import EndEffector
6
+ from kuavo_humanoid_sdk.interfaces.data_types import EndEffectorSide, EndEffectorState
7
+ from kuavo_humanoid_sdk.kuavo.core.leju_claw_control import LejuClawControl
8
+ from kuavo_humanoid_sdk.kuavo.core.ros.state import KuavoRobotStateCore
9
+
10
+ class LejuClaw(EndEffector):
11
+ def __init__(self):
12
+ super().__init__(joint_names=['left_claw', 'right_claw'])
13
+ self.leju_claw_control = LejuClawControl()
14
+ self._rb_state = KuavoRobotStateCore()
15
+
16
+ def control(self, target_positions: list, target_velocities:list=None, target_torques: list=None)->bool:
17
+ """控制机器人夹爪抓取。
18
+
19
+ Args:
20
+ target_positions (list): 夹爪的目标位置。\n
21
+ target_velocities (list, optional): 夹爪的目标速度。如果为None,将使用默认值[90, 90]。\n
22
+ target_torques (list, optional): 夹爪的目标扭矩。如果为None,将使用默认值[1.0, 1.0]。\n
23
+
24
+ Note:
25
+ target_positions、target_velocities 和 target_torques 必须是长度为`self.joint_count()`的列表。\n
26
+ 调用此函数后,可以调用 :meth:`LejuClaw.wait_for_finish` 等待夹爪到达目标位置。
27
+
28
+ Warning:
29
+ 如果夹爪仍在执行上一个命令(运动未结束),这个请求可能会被丢弃。
30
+
31
+ Returns:
32
+ bool: 如果夹爪成功发送命令返回True,否则返回False。
33
+ """
34
+ if target_positions is None or len(target_positions) != self.joint_count():
35
+ raise ValueError("Target positions must be provided.")
36
+
37
+ target_positions = [max(0.0, min(100.0, pos)) for pos in target_positions]
38
+ if target_velocities is None:
39
+ target_velocities = [90, 90]
40
+ else:
41
+ if len(target_velocities) != self.joint_count():
42
+ raise ValueError("Target velocities must be a list of length 2.")
43
+ target_velocities = [max(0.0, min(100.0, vel)) for vel in target_velocities]
44
+
45
+ if target_torques is None:
46
+ target_torques = [1.0, 1.0]
47
+ else:
48
+ if len(target_torques) != self.joint_count():
49
+ raise ValueError("Target torques must be a list of length 2.")
50
+ target_torques = [max(0.0, min(10.0, torque)) for torque in target_torques]
51
+
52
+ return self.leju_claw_control.control(target_positions, target_velocities, target_torques, EndEffectorSide.BOTH)
53
+
54
+ def control_left(self, target_positions:list, target_velocities:list=None, target_torques:list=None)->bool:
55
+ """控制机器人左夹爪抓取。
56
+
57
+ Args:
58
+ target_positions (list): 左夹爪的目标位置。\n
59
+ target_velocities (list, optional): 左夹爪的目标速度。如果为None,将使用默认值[90, 90]。\n
60
+ target_torques (list, optional): 左夹爪的目标扭矩。如果为None,将使用默认值[1.0, 1.0]。\n
61
+
62
+ Note:
63
+ target_positions、target_velocities 和 target_torques 必须是长度为`self.joint_count()/2`的列表。\n
64
+ 调用此函数后,可以调用 :meth:`LejuClaw.wait_for_finish` 等待夹爪到达目标位置。
65
+
66
+ Warning:
67
+ 如果夹爪仍在执行上一个命令(运动未结束),这个请求可能会被丢弃。
68
+
69
+ Returns:
70
+ bool: 如果夹爪成功发送命令返回True,否则返回False。
71
+ """
72
+ if target_positions is None:
73
+ raise ValueError("Target positions must be provided.")
74
+
75
+ for data in [target_positions, target_velocities, target_torques]:
76
+ if data is not None and len(data) != self.joint_count()/2:
77
+ raise ValueError(f"Target data must be a list of length {self.joint_count()/2}.")
78
+
79
+ q = max(0.0, min(100.0, target_positions[0]))
80
+
81
+ if target_velocities is not None:
82
+ v = max(0.0, min(100.0, target_velocities[0]))
83
+ else:
84
+ v = 90
85
+
86
+ if target_torques is not None:
87
+ tau = max(0.0, min(10.0, target_torques[0]))
88
+ else:
89
+ tau = 1.0
90
+
91
+ return self.leju_claw_control.control([q], [v], [tau], EndEffectorSide.LEFT)
92
+
93
+ def control_right(self, target_positions:list, target_velocities:list=None, target_torques:list=None)->bool:
94
+ """控制机器人右夹爪抓取。
95
+
96
+ Args:
97
+ target_positions (list): 右夹爪的目标位置。\n
98
+ target_velocities (list, optional): 右夹爪的目标速度。如果为None,将使用默认值[90, 90]。\n
99
+ target_torques (list, optional): 右夹爪的目标扭矩。如果为None,将使用默认值[1.0, 1.0]。\n
100
+
101
+ Returns:
102
+ bool: 如果夹爪成功发送命令返回True,否则返回False。
103
+
104
+ Note:
105
+ target_positions、target_velocities 和 target_torques 必须是长度为`self.joint_count()/2`的列表。\n
106
+ 调用此函数后,可以调用 :meth:`LejuClaw.wait_for_finish` 等待夹爪到达目标位置。
107
+
108
+ Warning:
109
+ If the claws are still in motion from a previous command, this request may be dropped.
110
+ """
111
+ if target_positions is None:
112
+ raise ValueError("Target positions must be provided.")
113
+
114
+ for data in [target_positions, target_velocities, target_torques]:
115
+ if data is not None and len(data) != self.joint_count()/2:
116
+ raise ValueError(f"Target data must be a list of length {self.joint_count()/2}.")
117
+
118
+ q = max(0.0, min(100.0, target_positions[0]))
119
+
120
+ if target_velocities is not None:
121
+ v = max(0.0, min(100.0, target_velocities[0]))
122
+ else:
123
+ v = 90
124
+
125
+ if target_torques is not None:
126
+ tau = max(0.0, min(10.0, target_torques[0]))
127
+ else:
128
+ tau = 1.0
129
+
130
+ return self.leju_claw_control.control([q], [v], [tau], EndEffectorSide.RIGHT)
131
+
132
+ def open(self, side:EndEffectorSide=EndEffectorSide.BOTH)->bool:
133
+ """控制夹爪释放/打开。
134
+
135
+ Note:
136
+ 控制夹爪打开。 \n
137
+ 调用此函数后,可以调用 :meth:`LejuClaw.wait_for_finish` 等待夹爪到达目标位置。
138
+
139
+ Args:
140
+ side (EndEffectorSide, optional): 要控制的夹爪侧(左/右或左右),默认为 :attr:`EndEffectorSide.BOTH` 。
141
+
142
+ Returns:
143
+ bool: 如果夹爪成功发送命令返回True,否则返回False。
144
+ """
145
+ return self.leju_claw_control.release(side)
146
+
147
+ def close(self, side:EndEffectorSide=EndEffectorSide.BOTH)->bool:
148
+ """控制二指夹爪闭合/抓取。
149
+
150
+ Note:
151
+ 控制二指夹爪闭合 \n
152
+ 调用此函数后,可以调用 :meth:`LejuClaw.wait_for_finish` 等待二指夹爪到达目标位置 \n
153
+
154
+ Args:
155
+ side (EndEffectorSide, optional): 要控制的二指夹爪侧(左/右或左右),默认为 :attr:`EndEffectorState.BOTH`
156
+
157
+ Returns:
158
+ bool: 如果二指夹爪闭合命令发送成功返回 True, 否则返回 False。 \n
159
+
160
+ Warning:
161
+ 二指夹爪的闭合范围为 [0, 100],其中 0 表示完全闭合,100 表示完全打开。
162
+ """
163
+ return self.leju_claw_control.control(position=[100, 100], velocity=[90, 90], torque=[1.0, 1.0], side=side)
164
+
165
+ def get_grasping_state(self)->Tuple[EndEffectorState.GraspingState, EndEffectorState.GraspingState]:
166
+ """获取夹爪的抓取状态。
167
+
168
+ Returns:
169
+ Tuple[EndEffectorState.GraspingState, EndEffectorState.GraspingState]: 夹爪的抓取状态。
170
+ """
171
+ return self._rb_state.eef_state.state
172
+
173
+ def get_position(self)->Tuple[list, list]:
174
+ """获取夹爪的位置。
175
+
176
+ Returns:
177
+ Tuple[list, list]: 夹爪的位置,范围 [0.0, 100.0]。
178
+ """
179
+ claw_state = self._rb_state.eef_state
180
+ return (claw_state[0].position, claw_state[1].position)
181
+
182
+ def get_velocity(self)->Tuple[list, list]:
183
+ """获取夹爪的速度。
184
+
185
+ Returns:
186
+ Tuple[list, list]: 夹爪的速度。
187
+ """
188
+ claw_state = self._rb_state.eef_state
189
+ return (claw_state[0].velocity, claw_state[1].velocity)
190
+
191
+ def get_effort(self)->Tuple[list, list]:
192
+ """获取夹爪的力。
193
+
194
+ Returns:
195
+ Tuple[list, list]: 夹爪的力。
196
+ """
197
+ claw_state = self._rb_state.eef_state
198
+ return (claw_state[0].effort, claw_state[1].effort)
199
+
200
+ def get_state(self)->Tuple[EndEffectorState, EndEffectorState]:
201
+ """获取夹爪的状态。
202
+
203
+ Returns:
204
+ Tuple[EndEffectorState, EndEffectorState]: 夹爪的状态。
205
+ - position: 夹爪的位置,范围 [0.0, 100.0]。
206
+ - velocity: 夹爪的速度。
207
+ - effort: 夹爪的力。
208
+ - state: 夹爪的抓取状态。
209
+ """
210
+ return self._rb_state.eef_state
211
+
212
+ def wait_for_finish(self, side: EndEffectorSide=EndEffectorSide.BOTH, timeout:float=2.5):
213
+ """等待夹爪运动完成。
214
+
215
+ Args:
216
+ side (EndEffectorSide, optional): 要等待的夹爪侧(左/右或左右),默认为 :attr:`EndEffectorSide.BOTH` 。
217
+ timeout (float, optional): 等待超时时间,默认为 2.5 秒。
218
+
219
+ Returns:
220
+ bool: 如果运动在超时前完成返回True,否则返回False。
221
+ """
222
+ start_time = time.time()
223
+ while time.time() - start_time < timeout:
224
+ if side == EndEffectorSide.BOTH:
225
+ if self._rb_state.eef_state[0].state >= EndEffectorState.GraspingState.REACHED and \
226
+ self._rb_state.eef_state[1].state >= EndEffectorState.GraspingState.REACHED:
227
+ return True
228
+ elif side == EndEffectorSide.LEFT:
229
+ if self._rb_state.eef_state[0].state >= EndEffectorState.GraspingState.REACHED:
230
+ return True
231
+ elif side == EndEffectorSide.RIGHT:
232
+ if self._rb_state.eef_state[1].state >= EndEffectorState.GraspingState.REACHED:
233
+ return True
234
+ time.sleep(0.1)
235
+ return False
@@ -0,0 +1,80 @@
1
+ # logger_client.py
2
+ import asyncio
3
+ import websockets
4
+ import json
5
+ import threading
6
+ import datetime
7
+ import inspect
8
+
9
+ # 全局单例对象
10
+ _logger_instance = None
11
+
12
+ def get_logger(timeout: int = 3):
13
+ global _logger_instance
14
+ if _logger_instance is None:
15
+ _logger_instance = LoggerClient(timeout=timeout)
16
+ return _logger_instance
17
+
18
+
19
+ class LoggerClient:
20
+ def __init__(self, uri: str = None, timeout=3):
21
+ # 强制使用 localhost
22
+ self.uri = "ws://localhost:8889"
23
+ print(f"[LoggerClient] 使用 localhost 构造连接地址: {self.uri}")
24
+
25
+ self._loop = None
26
+ self._ws = None
27
+ self._connected_event = threading.Event()
28
+ self._thread = threading.Thread(target=self._run_loop, daemon=True)
29
+ self._thread.start()
30
+
31
+ if not self._connected_event.wait(timeout=timeout + 2):
32
+ print("[LoggerClient] 连接日志服务器超时")
33
+
34
+ def _run_loop(self):
35
+ self._loop = asyncio.new_event_loop()
36
+ asyncio.set_event_loop(self._loop)
37
+ self._loop.run_until_complete(self._connect())
38
+ self._loop.run_forever()
39
+
40
+ async def _connect(self):
41
+ try:
42
+ self._ws = await websockets.connect(self.uri)
43
+ print(f"[LoggerClient] 已连接到日志服务器 {self.uri}")
44
+ self._connected_event.set()
45
+ await self._listen()
46
+ except Exception as e:
47
+ print(f"[LoggerClient] 连接失败: {e}")
48
+
49
+ async def _listen(self):
50
+ try:
51
+ async for _ in self._ws:
52
+ pass
53
+ except:
54
+ pass
55
+
56
+ def send_log(self, msg: str, level: str = "INFO"):
57
+ if not self._loop or not self._ws:
58
+ print("[LoggerClient] 日志服务器未连接")
59
+ return
60
+
61
+ async def _send():
62
+ try:
63
+ frame = inspect.currentframe().f_back
64
+ module = inspect.getmodule(frame)
65
+ module_name = module.__name__ if module else "unknown_module"
66
+ function_name = frame.f_code.co_name if frame else "unknown_function"
67
+
68
+ log_data = {
69
+ "level": level,
70
+ "timestamp": datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S.%f")[:-3],
71
+ "message": msg,
72
+ "module": module_name,
73
+ "function": function_name
74
+ }
75
+
76
+ await self._ws.send(json.dumps(log_data, ensure_ascii=False))
77
+ except Exception as e:
78
+ print(f"[LoggerClient] 发送日志失败: {e}")
79
+
80
+ asyncio.run_coroutine_threadsafe(_send(), self._loop)