-
Notifications
You must be signed in to change notification settings - Fork 22
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Sim zbot2 support #135
Closed
Closed
Sim zbot2 support #135
Changes from 3 commits
Commits
Show all changes
22 commits
Select commit
Hold shift + click to select a range
3f1e3be
add zbot2 files
alik-git 29e492f
hacky v1
alik-git 1bc382a
lint
alik-git 929ae9a
remove termination contact
WT-MM 5ceacb3
n
WT-MM 9a8fae1
make new config and env for zbot2
alik-git c85bf12
updated joints py
alik-git cc94c62
updated fixed urdf
alik-git db507d5
updated urdf from onshape
alik-git 95b6d1e
robot fixed from new onshape (create fixed torso py)
alik-git c464aea
update values in joints py
alik-git bef3951
updated urdf
alik-git 03e16c6
linting
alik-git 396e435
add standing config
alik-git 2845775
add xml from urdf2mjcf
alik-git a18c253
manual changes to statisfy mujoco
alik-git c45b261
manually update starting position for mjcf xml
alik-git 0ede12f
save xml updates
budzianowski af1ef56
save xml
budzianowski 8c0db98
Merge branch 'master' of github.com:kscalelabs/sim into sim_zbot_support
budzianowski 4273ffa
add schema
budzianowski 0009c00
save walking setup
budzianowski File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,211 @@ | ||
"""Provides a Pythonic interface for referencing joint names from the given MuJoCo XML. | ||
|
||
Organizes them by sub-assembly (arms, legs) and defines convenient methods for | ||
defaults, limits, etc. | ||
""" | ||
|
||
import textwrap | ||
from abc import ABC | ||
from typing import Dict, List, Tuple, Union | ||
|
||
|
||
class Node(ABC): | ||
@classmethod | ||
def children(cls) -> List["Union[Node, str]"]: | ||
# Returns Node or string attributes (for recursion) | ||
return [ | ||
attr | ||
for attr in (getattr(cls, attr_name) for attr_name in dir(cls) if not attr_name.startswith("__")) | ||
if isinstance(attr, (Node, str)) | ||
] | ||
|
||
@classmethod | ||
def joints(cls) -> List[str]: | ||
# Returns only the attributes that are strings (i.e., joint names). | ||
return [ | ||
attr | ||
for attr in (getattr(cls, attr_name) for attr_name in dir(cls) if not attr_name.startswith("__")) | ||
if isinstance(attr, str) | ||
] | ||
|
||
@classmethod | ||
def joints_motors(cls) -> List[Tuple[str, str]]: | ||
# Returns pairs of (attribute_name, joint_string) | ||
joint_names: List[Tuple[str, str]] = [] | ||
for attr_name in dir(cls): | ||
if not attr_name.startswith("__"): | ||
attr = getattr(cls, attr_name) | ||
if isinstance(attr, str): | ||
joint_names.append((attr_name, attr)) | ||
return joint_names | ||
|
||
@classmethod | ||
def all_joints(cls) -> List[str]: | ||
# Recursively collect all string joint names | ||
leaves = cls.joints() | ||
for child in cls.children(): | ||
if isinstance(child, Node): | ||
leaves.extend(child.all_joints()) | ||
return leaves | ||
|
||
def __str__(self) -> str: | ||
# Pretty-print the hierarchy | ||
parts = [str(child) for child in self.children() if isinstance(child, Node)] | ||
parts_str = textwrap.indent("\n" + "\n".join(parts), " ") if parts else "" | ||
return f"[{self.__class__.__name__}]{parts_str}" | ||
|
||
|
||
# ----- Define the sub-assemblies --------------------------------------------------- | ||
class RightArm(Node): | ||
shoulder_yaw = "right_shoulder_yaw" | ||
shoulder_pitch = "right_shoulder_pitch" | ||
elbow_yaw = "right_elbow_yaw" | ||
gripper = "right_gripper" | ||
|
||
|
||
class LeftArm(Node): | ||
shoulder_yaw = "left_shoulder_yaw" | ||
shoulder_pitch = "left_shoulder_pitch" | ||
elbow_yaw = "left_elbow_yaw" | ||
gripper = "left_gripper" | ||
|
||
|
||
class Arms(Node): | ||
right = RightArm() | ||
left = LeftArm() | ||
|
||
|
||
class RightLeg(Node): | ||
hip_roll = "right_hip_roll" | ||
hip_yaw = "right_hip_yaw" | ||
hip_pitch = "right_hip_pitch" | ||
knee_pitch = "right_knee_pitch" | ||
ankle_pitch = "right_ankle_pitch" | ||
|
||
|
||
class LeftLeg(Node): | ||
hip_roll = "left_hip_roll" | ||
hip_yaw = "left_hip_yaw" | ||
hip_pitch = "left_hip_pitch" | ||
knee_pitch = "left_knee_pitch" | ||
ankle_pitch = "left_ankle_pitch" | ||
|
||
|
||
class Legs(Node): | ||
right = RightLeg() | ||
left = LeftLeg() | ||
|
||
|
||
# ----- Top-level Robot ------------------------------------------------------------ | ||
class Robot(Node): | ||
height = 0.34 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What's the current starting pose in mujoco and isaac? |
||
rotation = [0, 0, 0, 1.0] | ||
|
||
arms = Arms() | ||
legs = Legs() | ||
|
||
@classmethod | ||
def default_standing(cls) -> Dict[str, float]: | ||
"""Example angles for a nominal 'standing' pose. Adjust as needed.""" | ||
return { | ||
# Right Arm | ||
cls.arms.right.shoulder_yaw: 0.0, | ||
cls.arms.right.shoulder_pitch: 0.0, | ||
cls.arms.right.elbow_yaw: 0.0, | ||
cls.arms.right.gripper: 0.0, | ||
# Left Arm | ||
cls.arms.left.shoulder_yaw: 0.0, | ||
cls.arms.left.shoulder_pitch: 0.0, | ||
cls.arms.left.elbow_yaw: 0.0, | ||
cls.arms.left.gripper: 0.0, | ||
# Right Leg | ||
cls.legs.right.hip_roll: 0.0, | ||
cls.legs.right.hip_yaw: 0.0, | ||
cls.legs.right.hip_pitch: -0.2, | ||
cls.legs.right.knee_pitch: 0.4, | ||
cls.legs.right.ankle_pitch: -0.2, | ||
# Left Leg | ||
cls.legs.left.hip_roll: 0.0, | ||
cls.legs.left.hip_yaw: 0.0, | ||
cls.legs.left.hip_pitch: -0.2, | ||
cls.legs.left.knee_pitch: 0.4, | ||
cls.legs.left.ankle_pitch: -0.2, | ||
} | ||
|
||
@classmethod | ||
def default_limits(cls) -> Dict[str, Dict[str, float]]: | ||
"""Minimal example of per-joint limits. | ||
|
||
You can refine these to match your MJCF's 'range' tags or real specs. | ||
""" | ||
return { | ||
# Right side | ||
cls.arms.right.shoulder_yaw: {"lower": -1.22173, "upper": 0.349066}, | ||
cls.arms.right.shoulder_pitch: {"lower": -3.14159, "upper": 3.14159}, | ||
cls.arms.right.elbow_yaw: {"lower": -1.5708, "upper": 2.0944}, | ||
cls.arms.right.gripper: {"lower": -0.349066, "upper": 0.872665}, | ||
cls.legs.right.hip_roll: {"lower": -1.0472, "upper": 1.0472}, | ||
cls.legs.right.hip_yaw: {"lower": -0.174533, "upper": 1.91986}, | ||
cls.legs.right.hip_pitch: {"lower": -1.74533, "upper": 1.8326}, | ||
cls.legs.right.knee_pitch: {"lower": -0.174533, "upper": 2.96706}, | ||
cls.legs.right.ankle_pitch: {"lower": -1.5708, "upper": 1.5708}, | ||
# Left side | ||
cls.arms.left.shoulder_yaw: {"lower": -0.349066, "upper": 1.22173}, | ||
cls.arms.left.shoulder_pitch: {"lower": -3.14159, "upper": 3.14159}, | ||
cls.arms.left.elbow_yaw: {"lower": -2.0944, "upper": 1.5708}, | ||
cls.arms.left.gripper: {"lower": -0.872665, "upper": 0.349066}, | ||
cls.legs.left.hip_roll: {"lower": -1.0472, "upper": 1.0472}, | ||
cls.legs.left.hip_yaw: {"lower": -1.91986, "upper": 0.174533}, | ||
cls.legs.left.hip_pitch: {"lower": -1.8326, "upper": 1.74533}, | ||
cls.legs.left.knee_pitch: {"lower": -0.174533, "upper": 2.96706}, | ||
cls.legs.left.ankle_pitch: {"lower": -1.5708, "upper": 1.5708}, | ||
} | ||
|
||
@classmethod | ||
def stiffness(cls) -> Dict[str, float]: | ||
"""Example of a uniform stiffness for all joints.""" | ||
# Adjust per your controller’s needs | ||
return {joint: 20.0 for joint in cls.all_joints()} | ||
|
||
@classmethod | ||
def damping(cls) -> Dict[str, float]: | ||
"""Example of a uniform damping for all joints.""" | ||
return {joint: 0.5 for joint in cls.all_joints()} | ||
|
||
@classmethod | ||
def effort(cls) -> Dict[str, float]: | ||
"""Max torque/effort per joint. | ||
|
||
The MuJoCo 'range' was -80 to 80 in the actuator, | ||
so we might store 80 here (or a smaller number if you want a realistic limit). | ||
""" | ||
return {joint: 80.0 for joint in cls.all_joints()} | ||
|
||
@classmethod | ||
def velocity(cls) -> Dict[str, float]: | ||
"""Max velocity (rad/s) for each joint, arbitrary example.""" | ||
return {joint: 10.0 for joint in cls.all_joints()} | ||
|
||
@classmethod | ||
def friction(cls) -> Dict[str, float]: | ||
"""Example friction dictionary for certain joints.""" | ||
# Usually you'd have more specific friction values or a model. | ||
return { | ||
cls.legs.left.ankle_pitch: 0.01, | ||
cls.legs.right.ankle_pitch: 0.01, | ||
# etc... | ||
} | ||
|
||
|
||
def print_joints() -> None: | ||
# Gather all joints and check for duplicates | ||
joints_list = Robot.all_joints() | ||
assert len(joints_list) == len(set(joints_list)), "Duplicate joint names found!" | ||
|
||
# Print out the structure for debugging | ||
print(Robot()) | ||
print("\nAll Joints:", joints_list) | ||
|
||
|
||
if __name__ == "__main__": | ||
print_joints() |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Update also terminate_after_contacts_on