本节聚焦 ApexHand SDK 的 运动控制相关接口,包括:
move_jointmove_j_position_followregister_servo_joint_control_callbackset_max_joint_speed、set_max_joint_accel、set_max_finger_torque假定你已阅读「枚举与结构体概览」,并了解 JointId、JointControlParam 等基础类型。
move_joint 阻塞式位置控制from dexcelbot_apexhand_sdk import (
DexcelBot,
JointId,
create_joint_control_param,
ErrorCode,
)
bot = DexcelBot()
# 省略 connect() 与 set_all_fingers_enabled() ...
cmds = [
create_joint_control_param(
joint_id=JointId.JOINT_ID_THUMB_MCP,
position=0.5,
velocity=0.2,
acceleration=0.0,
)
]
result = bot.move_joint(cmds)
if result != ErrorCode.ERROR_CODE_OK:
raise RuntimeError(f"move_joint 失败: {result}")
commands为 任意数量关节 的组合,可在一次调用中同时下发多关节目标。
move_j_position_follow 跟随控制import time
from dexcelbot_apexhand_sdk import (
DexcelBot,
JointId,
create_move_j_position_follow_param,
ErrorCode,
)
bot = DexcelBot()
# 省略 connect() 与 set_all_fingers_enabled() ...
for i in range(100):
position = 0.1 + 0.4 * (i / 99)
params = [
create_move_j_position_follow_param(
joint_id=JointId.JOINT_ID_INDEX_MCP_0,
position=position,
)
]
result = bot.move_j_position_follow(params)
if result != ErrorCode.ERROR_CODE_OK:
print("move_j_position_follow 失败:", result)
break
time.sleep(0.01)
注意事项:
params 中加入多个 MoveJPositionFollowParam。register_servo_joint_control_callback 伺服回调register_servo_joint_control_callback 提供了高级的 闭环伺服控制 能力:SDK 会在内部周期性调用你注册的回调,将当前关节状态传入,并期望你填充目标控制指令列表。
在 Python 中,回调的预期形式为:
def servo_callback(joint_states, servo_params):
# joint_states: JointStates
# servo_params: List[ServoJointParam](由 SDK 创建并传入)
...
你需要在回调中修改 servo_params(例如设置每个关节的目标位置与速度),SDK 会自动将这些值发送到底层控制器。
import math
import time
from dexcelbot_apexhand_sdk import (
DexcelBot,
JointId,
ErrorCode,
)
bot = DexcelBot()
# 省略 connect() 与 set_all_fingers_enabled() ...
start_time = time.time()
def servo_callback(joint_states, servo_params):
t = time.time() - start_time
target_pos = 0.3 * math.sin(2 * math.pi * 0.5 * t) # 0.5 Hz 正弦
for p in servo_params:
if p.joint_id == JointId.JOINT_ID_INDEX_MCP_0:
p.position = target_pos
p.velocity = 0.5
result = bot.register_servo_joint_control_callback(servo_callback, freq_hz=100)
if result != ErrorCode.ERROR_CODE_OK:
raise RuntimeError("注册伺服控制回调失败")
time.sleep(10.0) # 运行一段时间
bot.unregister_servo_joint_control_callback()
伺服回调适合实现基于关节状态的自定义控制律(如阻抗控制、力控制上层逻辑等),请确保回调函数内部运算时间足够短,以满足给定的
freq_hz要求。
set_max_joint_speed设置每个关节的最大速度限制:
from dexcelbot_apexhand_sdk import DexcelBot, MaxJointSpeed, JointId
bot = DexcelBot()
limits = []
for jid in JointId:
s = MaxJointSpeed()
s.joint_id = jid
s.speed = 1.0 # 示例:为所有关节设置 1 rad/s
limits.append(s)
bot.set_max_joint_speed(limits)
如果给定速度超出允许范围,函数会返回 ERROR_CODE_OUT_OF_RANGE。
set_max_joint_accel设置每个关节的最大加速度限制:
from dexcelbot_apexhand_sdk import DexcelBot, MaxJointAccel, JointId
bot = DexcelBot()
accels = []
for jid in JointId:
a = MaxJointAccel()
a.joint_id = jid
a.accel = 2.0 # 示例:统一 2 rad/s²
accels.append(a)
bot.set_max_joint_accel(accels)
set_max_finger_torque设置每个手指的最大扭矩(单位为 0–100%):
from dexcelbot_apexhand_sdk import DexcelBot, MaxFingerTorque, FingerId
bot = DexcelBot()
torques = []
for fid in FingerId:
t = MaxFingerTorque()
t.finger_id = fid
t.torque = 80.0 # 将所有手指限制在 80% 以内
torques.append(t)
bot.set_max_finger_torque(torques)
建议在任何实际接触或抓取任务中,都先配置合理的速度、加速度和扭矩限制,以保证安全。
from dexcelbot_apexhand_sdk import (
DexcelBot,
FingerId,
JointId,
MaxFingerTorque,
MaxJointSpeed,
MaxJointAccel,
create_joint_control_param,
ErrorCode,
)
bot = DexcelBot()
# 1. 连接与使能略
# 2. 配置安全限制
torques = []
for fid in FingerId:
t = MaxFingerTorque()
t.finger_id = fid
t.torque = 60.0
torques.append(t)
bot.set_max_finger_torque(torques)
speeds = []
accels = []
for jid in JointId:
s = MaxJointSpeed()
s.joint_id = jid
s.speed = 0.8
speeds.append(s)
a = MaxJointAccel()
a.joint_id = jid
a.accel = 1.5
accels.append(a)
bot.set_max_joint_speed(speeds)
bot.set_max_joint_accel(accels)
# 3. 简单抓取动作(示意)
cmds = [
create_joint_control_param(JointId.JOINT_ID_INDEX_PIP, position=0.9, velocity=0.3),
create_joint_control_param(JointId.JOINT_ID_MIDDLE_PIP, position=0.9, velocity=0.3),
create_joint_control_param(JointId.JOINT_ID_RING_PIP, position=0.9, velocity=0.3),
create_joint_control_param(JointId.JOINT_ID_PINKY_PIP, position=0.9, velocity=0.3),
]
result = bot.move_joint(cmds)
if result != ErrorCode.ERROR_CODE_OK:
print("抓取动作失败:", result)
通过本节你可以完成大部分基于关节空间的轨迹控制。下一节将介绍 状态读取与触觉图像,帮助你在任务中实时感知 ApexHand 的运动与接触情况。