Pybullet imports URDF files - and creates constraints

Pybullet imports URDF files - and creates constraints

Problem Description

Generally, when a URDF file is imported in Pybullet, it will move when it is hit by a collision ; if you want to fix the imported URDF file, like a static obstacle, you need to create additional constraints on it .

Import URDF file

pybullet.loadURDF(path,position,orientation,flags=0): Send information to the physical server, load the URDF file; return the ID of the created model

  • path: URDF file path
  • position: X, Y, Z three-dimensional coordinates of the world coordinate system
  • orientation: quaternion
  • useFixedBase: True or False, whether to keep the Base link fixed ; note that it does not mean to make it immobile as a whole, to make it immobile as a whole, you need createConstraint to create constraints
  • flags: certain flags

create constraints

pybullet.createConstraint(parentBodyUniqueId, parentLinkIndex, childBodyUniqueId, childLinkIndex, jointType, jointAxis, parentFramePosition, childFramePosition): Constrain the joints of the two links

Note: The relationship between the joint and the link is as follows:
insert image description here

The meaning of each parameter ( Pybullet official ):

  • parentBodyUniqueId: parent entity index, loadURDF gets
  • parentLinkIndex: The link index of the parent entity, getNumJoints to get the number of joints, and then use getLinkState to output the information of each joint in turn
  • childBodyUniqueId: child entity index
  • childLinkIndex: link index of the child entity
  • jointType: Joint constraint type, such as fixed (JOINT_PRISMATIC, JOINT_FIXED, JOINT_POINT2POINT, JOINT_GEAR)
  • jointAxis: The joint axis expressed in the sub-link coordinate system
  • parentFramePosition: The position of the joint coordinate system relative to the center of mass coordinate system of the parent entity (if the parent entity is the ground, then it is the center of mass coordinate system of the child entity)
  • childFramePosition: The position of the joint coordinate system relative to the center of mass coordinate system of the subentity (the 15th value returned by the getJointInfo function)
  • Other parameters omitted (non-required parameters)

Create a constraint:

floor_id = p.loadURDF('plane.urdf')
box_id = p.loadURDF(fileName='cube_no_rotation.urdf',basePosition=[2,2,0],baseOrientation=p.getQuaternionFromEuler([0, 0, 0]),useFixedBase=True)
p.createConstraint(floor_id, -1, box_id, 0, p.JOINT_FIXED, [0, 0, 0], [2, 2, 0], [0, 0, 0])  # 添加约束

Note: Sometimes the URDF file does not have only one joint, and fixing only one will still make it move, so it is necessary to fix as many joints as possible to ensure that the last loaded object will not move.

For complete code see:

import pybullet as p
import pybullet_data
import os
# p.connect(p.DIRECT)
p.connect(p.GUI)
p.resetSimulation()
p.setGravity(0,0,-9.8)
p.setTimeStep(1./60)
p.setRealTimeSimulation(0)
p.setAdditionalSearchPath(pybullet_data.getDataPath())

# 加载模型
floor_id = p.loadURDF('plane.urdf')
box_id = p.loadURDF(fileName='cube_no_rotation.urdf',basePosition=[2,2,0],baseOrientation=p.getQuaternionFromEuler([0, 0, 0]),useFixedBase=True)
# 需要改一下自己的路径
robot_id1 = p.loadURDF(fileName='/home/xxx/urdf_and_meshes/robomaster.urdf',basePosition=[-3,2,1],baseOrientation=p.getQuaternionFromEuler([0, 0, 0]))
robot_id2 = p.loadURDF(fileName='/home/xxx/urdf_and_meshes/robomaster.urdf',basePosition=[2,-3,1],baseOrientation=p.getQuaternionFromEuler([0, 0, 0]))

numJoints = p.getNumJoints(box_id)
print("机器人关节的数量:", numJoints)

for index in range(numJoints):
    pos = p.getLinkState(box_id,index)
    print('rbox_id index is:',pos)

print("机器人关节的信息:")
for joint_index in range(numJoints):
    joint_info = p.getJointInfo(box_id, joint_index)
    # [0]关节索引:{joint_info[0]}
    # [1]关节名称:{joint_info[1]}
    # [2]关节类型:{joint_info[2]}
    # [3]此主体的位置状态变量中的第一个位置索引:{joint_info[3]}
    # [4]在这个物体的速度状态变量中的第一个速度索引:{joint_info[4]}
    # [5]保留参数:{joint_info[5]}
    # [6]关节阻尼大小:{joint_info[6]}
    # [7]关节摩擦系数:{joint_info[7]}
    # [8]滑动或旋转关节的位置下限:{joint_info[8]}
    # [9]滑动或旋转关节的位置上限:{joint_info[9]}
    # [10]关节最大力矩:{joint_info[10]}
    # [11]关节最大速度:{joint_info[11]}
    # [12]连杆名称:{joint_info[12]}
    # [13]在当前连杆坐标系中表示的移动或转动的关节轴(忽略JOINT_FIXED固定关节):{joint_info[13]}
    # [14]在父连杆坐标系中表示的关节位置:{joint_info[14]}
    # [15]在父连杆坐标系中表示的关节姿态(四元数x、y、z、w):{joint_info[15]}
    # [16]父连杆的索引,若是base连杆则返回-1:{joint_info[16]}

# 打印可使用关节
joints_indexes = [i for i in range(numJoints) if p.getJointInfo(box_id, i)[2] != p.JOINT_FIXED]  # 可以使用的关节索引
print([p.getJointInfo(box_id, i) for i in joints_indexes])

# 注意因为有四个关节,所以要有四个约束;否则最终还是会移动
cid1 = p.createConstraint(floor_id, -1, box_id, 0, p.JOINT_FIXED, [0, 0, 0], [2, 2, 0], [0, 0, 0])  # 添加约束
cid2 = p.createConstraint(floor_id, -1, box_id, 1, p.JOINT_FIXED, [0, 0, 0], [2, 2, 0], [0, 0, 0])  # 添加约束
cid3 = p.createConstraint(floor_id, -1, box_id, 2, p.JOINT_FIXED, [0, 0, 0], [2, 2, 0], [0, 0, 0])  # 添加约束
cid4 = p.createConstraint(floor_id, -1, box_id, 3, p.JOINT_FIXED, [0, 0, 0], [2, 2, 0], [0, 0, 0])  # 添加约束

while True:
    p.stepSimulation()
    # 验证小车装上之后,障碍物是否会移动
    p.resetBaseVelocity(objectUniqueId=robot_id1,
                        linearVelocity=[0.1, 0, 0],
                        angularVelocity=[0, 0, 0],
                        )
    p.resetBaseVelocity(objectUniqueId=robot_id2,
                        linearVelocity=[0, 0.1, 0],
                        angularVelocity=[0, 0, 0],
                        )

PS:

You can also use the createMultiBody function to create immovable obstacles, just change the first parameter to GEOM_BOX when creating createCollisionShape and createVisualShape

box_id = p.createCollisionShape(p.GEOM_BOX, halfExtents=[1+0.05, 1+0.05, 1])# 创建碰撞箱模型
box_visual_id = p.createVisualShape(p.GEOM_BOX,halfExtents=[1, 1, 1],rgbaColor=(0.1, 0.5, 0.1, 1))# 创建视觉模型
OBSTACLES_IDS[index] = p.createMultiBody(baseMass=0,baseCollisionShapeIndex=box_id,baseVisualShapeIndex=box_visual_id,basePosition=[1, 2, 0])

Reference: Problems with the closed-chain mechanism of
API functions commonly used in PyBullet simulation software

Guess you like

Origin blog.csdn.net/weixin_43789096/article/details/130702187