reachy-mini 1.2.5rc1__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.
Files changed (479) hide show
  1. reachy_mini/__init__.py +4 -0
  2. reachy_mini/apps/__init__.py +25 -0
  3. reachy_mini/apps/app.py +258 -0
  4. reachy_mini/apps/assistant.py +787 -0
  5. reachy_mini/apps/manager.py +312 -0
  6. reachy_mini/apps/sources/__init__.py +4 -0
  7. reachy_mini/apps/sources/hf_space.py +106 -0
  8. reachy_mini/apps/sources/local_common_venv.py +567 -0
  9. reachy_mini/apps/templates/README.md.j2 +12 -0
  10. reachy_mini/apps/templates/gitignore.j2 +3 -0
  11. reachy_mini/apps/templates/index.html.j2 +40 -0
  12. reachy_mini/apps/templates/main.py.j2 +74 -0
  13. reachy_mini/apps/templates/pyproject.toml.j2 +28 -0
  14. reachy_mini/apps/templates/static/index.html.j2 +27 -0
  15. reachy_mini/apps/templates/static/main.js.j2 +47 -0
  16. reachy_mini/apps/templates/static/style.css.j2 +25 -0
  17. reachy_mini/apps/templates/style.css.j2 +411 -0
  18. reachy_mini/apps/utils.py +30 -0
  19. reachy_mini/assets/config/hardware_config.yaml +164 -0
  20. reachy_mini/assets/confused1.wav +0 -0
  21. reachy_mini/assets/count.wav +0 -0
  22. reachy_mini/assets/dance1.wav +0 -0
  23. reachy_mini/assets/firmware/CHANGELOG.md +15 -0
  24. reachy_mini/assets/firmware/reachymini_ua_io16_lin_v2.1.2.bin +0 -0
  25. reachy_mini/assets/firmware/reachymini_ua_io16_lin_v2.1.3.bin +0 -0
  26. reachy_mini/assets/firmware/update.sh +9 -0
  27. reachy_mini/assets/go_sleep.wav +0 -0
  28. reachy_mini/assets/impatient1.wav +0 -0
  29. reachy_mini/assets/kinematics_data.json +253 -0
  30. reachy_mini/assets/models/fknetwork.dynamic.onnx +0 -0
  31. reachy_mini/assets/models/fknetwork.onnx +0 -0
  32. reachy_mini/assets/models/fknetwork_int8.onnx +0 -0
  33. reachy_mini/assets/models/iknetwork.onnx +0 -0
  34. reachy_mini/assets/wake_up.wav +0 -0
  35. reachy_mini/daemon/__init__.py +1 -0
  36. reachy_mini/daemon/app/__init__.py +1 -0
  37. reachy_mini/daemon/app/bg_job_register.py +142 -0
  38. reachy_mini/daemon/app/dashboard/static/assets/KO-cartoon-static.svg +40 -0
  39. reachy_mini/daemon/app/dashboard/static/assets/awake-cartoon-static.svg +42 -0
  40. reachy_mini/daemon/app/dashboard/static/assets/awake-cartoon.svg +6 -0
  41. reachy_mini/daemon/app/dashboard/static/assets/go-to-sleep-cartoon.svg +6 -0
  42. reachy_mini/daemon/app/dashboard/static/assets/no-wifi-cartoon-static.svg +50 -0
  43. reachy_mini/daemon/app/dashboard/static/assets/no-wifi-cartoon.svg +6 -0
  44. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-awake.svg +18 -0
  45. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-connection-lost-animation.svg +6 -0
  46. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-go-to-sleep-animation.svg +6 -0
  47. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-ko-animation.svg +6 -0
  48. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-ko.svg +22 -0
  49. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-sleeping-static.svg +41 -0
  50. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-sleeping.svg +18 -0
  51. reachy_mini/daemon/app/dashboard/static/assets/reachy-mini-wake-up-animation.svg +6 -0
  52. reachy_mini/daemon/app/dashboard/static/css/app.css +1433 -0
  53. reachy_mini/daemon/app/dashboard/static/fonts/Archivo-Italic-VariableFont_wdth,wght.ttf +0 -0
  54. reachy_mini/daemon/app/dashboard/static/fonts/Archivo-VariableFont_wdth,wght.ttf +0 -0
  55. reachy_mini/daemon/app/dashboard/static/fonts/Asap-Italic-VariableFont_wdth,wght.ttf +0 -0
  56. reachy_mini/daemon/app/dashboard/static/fonts/Asap-VariableFont_wdth,wght.ttf +0 -0
  57. reachy_mini/daemon/app/dashboard/static/js/3rdparty/gstwebrtc-api-2.0.0.min.js +5 -0
  58. reachy_mini/daemon/app/dashboard/static/js/apps.js +323 -0
  59. reachy_mini/daemon/app/dashboard/static/js/appstore.js +167 -0
  60. reachy_mini/daemon/app/dashboard/static/js/daemon.js +169 -0
  61. reachy_mini/daemon/app/dashboard/static/js/health_check.js +9 -0
  62. reachy_mini/daemon/app/dashboard/static/js/move_player.js +132 -0
  63. reachy_mini/daemon/app/dashboard/static/js/notification.js +41 -0
  64. reachy_mini/daemon/app/dashboard/static/js/update.js +132 -0
  65. reachy_mini/daemon/app/dashboard/static/js/volume_control.js +252 -0
  66. reachy_mini/daemon/app/dashboard/static/js/wifi.js +176 -0
  67. reachy_mini/daemon/app/dashboard/tailwindcss/README.md +15 -0
  68. reachy_mini/daemon/app/dashboard/tailwindcss/package-lock.json +1127 -0
  69. reachy_mini/daemon/app/dashboard/tailwindcss/package.json +6 -0
  70. reachy_mini/daemon/app/dashboard/tailwindcss/pnpm-lock.yaml +608 -0
  71. reachy_mini/daemon/app/dashboard/tailwindcss/postcss.config.js +6 -0
  72. reachy_mini/daemon/app/dashboard/tailwindcss/styles/app.css +185 -0
  73. reachy_mini/daemon/app/dashboard/tailwindcss/tailwind.config.js +11 -0
  74. reachy_mini/daemon/app/dashboard/templates/base.html +21 -0
  75. reachy_mini/daemon/app/dashboard/templates/index.html +20 -0
  76. reachy_mini/daemon/app/dashboard/templates/sections/apps.html +8 -0
  77. reachy_mini/daemon/app/dashboard/templates/sections/appstore.html +35 -0
  78. reachy_mini/daemon/app/dashboard/templates/sections/daemon.html +45 -0
  79. reachy_mini/daemon/app/dashboard/templates/sections/move_player.html +121 -0
  80. reachy_mini/daemon/app/dashboard/templates/sections/notification.html +19 -0
  81. reachy_mini/daemon/app/dashboard/templates/sections/update.html +54 -0
  82. reachy_mini/daemon/app/dashboard/templates/sections/wifi.html +46 -0
  83. reachy_mini/daemon/app/dashboard/templates/settings.html +14 -0
  84. reachy_mini/daemon/app/dependencies.py +41 -0
  85. reachy_mini/daemon/app/main.py +469 -0
  86. reachy_mini/daemon/app/models.py +149 -0
  87. reachy_mini/daemon/app/routers/apps.py +114 -0
  88. reachy_mini/daemon/app/routers/daemon.py +85 -0
  89. reachy_mini/daemon/app/routers/kinematics.py +57 -0
  90. reachy_mini/daemon/app/routers/motors.py +41 -0
  91. reachy_mini/daemon/app/routers/move.py +265 -0
  92. reachy_mini/daemon/app/routers/state.py +146 -0
  93. reachy_mini/daemon/app/routers/update.py +86 -0
  94. reachy_mini/daemon/app/routers/volume.py +423 -0
  95. reachy_mini/daemon/app/routers/wifi_config.py +219 -0
  96. reachy_mini/daemon/app/services/__init__.py +1 -0
  97. reachy_mini/daemon/app/services/bluetooth/bluetooth_service.py +796 -0
  98. reachy_mini/daemon/app/services/bluetooth/commands/HOTSPOT.sh +7 -0
  99. reachy_mini/daemon/app/services/bluetooth/commands/RESTART_DAEMON.sh +4 -0
  100. reachy_mini/daemon/app/services/bluetooth/commands/SOFTWARE_RESET.sh +7 -0
  101. reachy_mini/daemon/app/services/bluetooth/install_service_bluetooth.sh +39 -0
  102. reachy_mini/daemon/app/services/gpio_shutdown/__init__.py +1 -0
  103. reachy_mini/daemon/app/services/gpio_shutdown/install_service.sh +33 -0
  104. reachy_mini/daemon/app/services/gpio_shutdown/launcher.sh +3 -0
  105. reachy_mini/daemon/app/services/gpio_shutdown/shutdown_monitor.py +28 -0
  106. reachy_mini/daemon/app/services/wireless/generate_asoundrc.sh +70 -0
  107. reachy_mini/daemon/app/services/wireless/install_service.sh +33 -0
  108. reachy_mini/daemon/app/services/wireless/launcher.sh +5 -0
  109. reachy_mini/daemon/backend/__init__.py +1 -0
  110. reachy_mini/daemon/backend/abstract.py +815 -0
  111. reachy_mini/daemon/backend/mujoco/__init__.py +36 -0
  112. reachy_mini/daemon/backend/mujoco/backend.py +395 -0
  113. reachy_mini/daemon/backend/mujoco/utils.py +59 -0
  114. reachy_mini/daemon/backend/mujoco/video_udp.py +57 -0
  115. reachy_mini/daemon/backend/robot/__init__.py +8 -0
  116. reachy_mini/daemon/backend/robot/backend.py +597 -0
  117. reachy_mini/daemon/daemon.py +651 -0
  118. reachy_mini/daemon/utils.py +116 -0
  119. reachy_mini/descriptions/reachy_mini/mjcf/additional.xml +6 -0
  120. reachy_mini/descriptions/reachy_mini/mjcf/assets/5w_speaker.part +13 -0
  121. reachy_mini/descriptions/reachy_mini/mjcf/assets/5w_speaker.stl +0 -0
  122. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna.part +13 -0
  123. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna.stl +0 -0
  124. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_body_3dprint.part +13 -0
  125. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_body_3dprint.stl +0 -0
  126. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_holder_l_3dprint.part +13 -0
  127. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_holder_l_3dprint.stl +0 -0
  128. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_holder_r_3dprint.part +13 -0
  129. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_holder_r_3dprint.stl +0 -0
  130. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_interface_3dprint.part +13 -0
  131. reachy_mini/descriptions/reachy_mini/mjcf/assets/antenna_interface_3dprint.stl +0 -0
  132. reachy_mini/descriptions/reachy_mini/mjcf/assets/arducam.part +13 -0
  133. reachy_mini/descriptions/reachy_mini/mjcf/assets/arducam.stl +0 -0
  134. reachy_mini/descriptions/reachy_mini/mjcf/assets/b3b_eh.part +13 -0
  135. reachy_mini/descriptions/reachy_mini/mjcf/assets/b3b_eh.stl +0 -0
  136. reachy_mini/descriptions/reachy_mini/mjcf/assets/b3b_eh_1.part +13 -0
  137. reachy_mini/descriptions/reachy_mini/mjcf/assets/b3b_eh_1.stl +0 -0
  138. reachy_mini/descriptions/reachy_mini/mjcf/assets/bearing_85x110x13.part +13 -0
  139. reachy_mini/descriptions/reachy_mini/mjcf/assets/bearing_85x110x13.stl +0 -0
  140. reachy_mini/descriptions/reachy_mini/mjcf/assets/big_lens_d40.part +13 -0
  141. reachy_mini/descriptions/reachy_mini/mjcf/assets/big_lens_d40.stl +0 -0
  142. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_down_3dprint.part +13 -0
  143. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_down_3dprint.stl +0 -0
  144. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_foot_3dprint.part +13 -0
  145. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_foot_3dprint.stl +0 -0
  146. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_top_3dprint.part +13 -0
  147. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_top_3dprint.stl +0 -0
  148. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_turning_3dprint.part +13 -0
  149. reachy_mini/descriptions/reachy_mini/mjcf/assets/body_turning_3dprint.stl +0 -0
  150. reachy_mini/descriptions/reachy_mini/mjcf/assets/bts2_m2_6x8.part +13 -0
  151. reachy_mini/descriptions/reachy_mini/mjcf/assets/bts2_m2_6x8.stl +0 -0
  152. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/README.m +1 -0
  153. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_back_0.stl +0 -0
  154. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_back_1.stl +0 -0
  155. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_back_2.stl +0 -0
  156. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_back_3.stl +0 -0
  157. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_front_0.stl +0 -0
  158. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_front_1.stl +0 -0
  159. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/body_top_3dprint_collider_front_2.stl +0 -0
  160. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/coarse/head_one_3dprint_collider_0.stl +0 -0
  161. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_back_0.stl +0 -0
  162. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_back_1.stl +0 -0
  163. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_back_2.stl +0 -0
  164. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_back_3.stl +0 -0
  165. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_front_0.stl +0 -0
  166. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_front_1.stl +0 -0
  167. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/body_top_3dprint_collider_front_2.stl +0 -0
  168. reachy_mini/descriptions/reachy_mini/mjcf/assets/collision/fine/head_one_3dprint_collider_0.stl +0 -0
  169. reachy_mini/descriptions/reachy_mini/mjcf/assets/croissant_1k.blend/croissant_1k.obj +5021 -0
  170. reachy_mini/descriptions/reachy_mini/mjcf/assets/croissant_1k.blend/textures/croissant_diff_1k.png +0 -0
  171. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_b_dummy.part +13 -0
  172. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_b_dummy.stl +0 -0
  173. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_f_dummy.part +13 -0
  174. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_f_dummy.stl +0 -0
  175. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_m_dummy.part +13 -0
  176. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_case_m_dummy.stl +0 -0
  177. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_horn_dummy.part +13 -0
  178. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_horn_dummy.stl +0 -0
  179. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_led_cap2_dummy.part +13 -0
  180. reachy_mini/descriptions/reachy_mini/mjcf/assets/dc15_a01_led_cap2_dummy.stl +0 -0
  181. reachy_mini/descriptions/reachy_mini/mjcf/assets/food_apple_01_1k.blend/food_apple_01_1k.obj +18045 -0
  182. reachy_mini/descriptions/reachy_mini/mjcf/assets/food_apple_01_1k.blend/textures/food_apple_01_diff_1k.png +0 -0
  183. reachy_mini/descriptions/reachy_mini/mjcf/assets/glasses_dolder_3dprint.part +13 -0
  184. reachy_mini/descriptions/reachy_mini/mjcf/assets/glasses_dolder_3dprint.stl +0 -0
  185. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_back_3dprint.part +13 -0
  186. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_back_3dprint.stl +0 -0
  187. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_front_3dprint.part +13 -0
  188. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_front_3dprint.stl +0 -0
  189. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_mic_3dprint.part +13 -0
  190. reachy_mini/descriptions/reachy_mini/mjcf/assets/head_mic_3dprint.stl +0 -0
  191. reachy_mini/descriptions/reachy_mini/mjcf/assets/lens_cap_d30_3dprint.part +13 -0
  192. reachy_mini/descriptions/reachy_mini/mjcf/assets/lens_cap_d30_3dprint.stl +0 -0
  193. reachy_mini/descriptions/reachy_mini/mjcf/assets/lens_cap_d40_3dprint.part +13 -0
  194. reachy_mini/descriptions/reachy_mini/mjcf/assets/lens_cap_d40_3dprint.stl +0 -0
  195. reachy_mini/descriptions/reachy_mini/mjcf/assets/m12_fisheye_lens_1_8mm.part +13 -0
  196. reachy_mini/descriptions/reachy_mini/mjcf/assets/m12_fisheye_lens_1_8mm.stl +0 -0
  197. reachy_mini/descriptions/reachy_mini/mjcf/assets/mp01062_stewart_arm_3.part +13 -0
  198. reachy_mini/descriptions/reachy_mini/mjcf/assets/mp01062_stewart_arm_3.stl +0 -0
  199. reachy_mini/descriptions/reachy_mini/mjcf/assets/neck_reference_3dprint.part +13 -0
  200. reachy_mini/descriptions/reachy_mini/mjcf/assets/neck_reference_3dprint.stl +0 -0
  201. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10.part +13 -0
  202. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10.stl +0 -0
  203. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_1.part +13 -0
  204. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_1.stl +0 -0
  205. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_2.part +13 -0
  206. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_2.stl +0 -0
  207. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_3.part +13 -0
  208. reachy_mini/descriptions/reachy_mini/mjcf/assets/phs_1_7x20_5_dc10_3.stl +0 -0
  209. reachy_mini/descriptions/reachy_mini/mjcf/assets/pp01102_arducam_carter.part +13 -0
  210. reachy_mini/descriptions/reachy_mini/mjcf/assets/pp01102_arducam_carter.stl +0 -0
  211. reachy_mini/descriptions/reachy_mini/mjcf/assets/rubber_duck_toy_1k.blend/rubber_duck_toy_1k.obj +8940 -0
  212. reachy_mini/descriptions/reachy_mini/mjcf/assets/rubber_duck_toy_1k.blend/textures/rubber_duck_toy_diff_1k.png +0 -0
  213. reachy_mini/descriptions/reachy_mini/mjcf/assets/small_lens_d30.part +13 -0
  214. reachy_mini/descriptions/reachy_mini/mjcf/assets/small_lens_d30.stl +0 -0
  215. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_ball.part +13 -0
  216. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_ball.stl +0 -0
  217. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_ball__2.part +13 -0
  218. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_ball__2.stl +0 -0
  219. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_rod.part +13 -0
  220. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_link_rod.stl +0 -0
  221. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_main_plate_3dprint.part +13 -0
  222. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_main_plate_3dprint.stl +0 -0
  223. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_tricap_3dprint.part +13 -0
  224. reachy_mini/descriptions/reachy_mini/mjcf/assets/stewart_tricap_3dprint.stl +0 -0
  225. reachy_mini/descriptions/reachy_mini/mjcf/assets/wooden_table_02_1k.blend/textures/wooden_table_02_diff_1k.png +0 -0
  226. reachy_mini/descriptions/reachy_mini/mjcf/assets/wooden_table_02_1k.blend/wooden_table_02_1k.obj +485 -0
  227. reachy_mini/descriptions/reachy_mini/mjcf/config.json +21 -0
  228. reachy_mini/descriptions/reachy_mini/mjcf/joints_properties.xml +29 -0
  229. reachy_mini/descriptions/reachy_mini/mjcf/reachy_mini.xml +642 -0
  230. reachy_mini/descriptions/reachy_mini/mjcf/reachy_mini.xml.bak +442 -0
  231. reachy_mini/descriptions/reachy_mini/mjcf/scene.xml +24 -0
  232. reachy_mini/descriptions/reachy_mini/mjcf/scenes/empty.xml +27 -0
  233. reachy_mini/descriptions/reachy_mini/mjcf/scenes/minimal.xml +132 -0
  234. reachy_mini/descriptions/reachy_mini/urdf/assets/5w_speaker.part +13 -0
  235. reachy_mini/descriptions/reachy_mini/urdf/assets/5w_speaker.stl +0 -0
  236. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna.part +13 -0
  237. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna.stl +0 -0
  238. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_body_3dprint.part +13 -0
  239. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_body_3dprint.stl +0 -0
  240. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_holder_l_3dprint.part +13 -0
  241. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_holder_l_3dprint.stl +0 -0
  242. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_holder_r_3dprint.part +13 -0
  243. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_holder_r_3dprint.stl +0 -0
  244. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_interface_3dprint.part +13 -0
  245. reachy_mini/descriptions/reachy_mini/urdf/assets/antenna_interface_3dprint.stl +0 -0
  246. reachy_mini/descriptions/reachy_mini/urdf/assets/arducam.part +13 -0
  247. reachy_mini/descriptions/reachy_mini/urdf/assets/arducam.stl +0 -0
  248. reachy_mini/descriptions/reachy_mini/urdf/assets/arm.part +13 -0
  249. reachy_mini/descriptions/reachy_mini/urdf/assets/arm.stl +0 -0
  250. reachy_mini/descriptions/reachy_mini/urdf/assets/b3b_eh.part +13 -0
  251. reachy_mini/descriptions/reachy_mini/urdf/assets/b3b_eh.stl +0 -0
  252. reachy_mini/descriptions/reachy_mini/urdf/assets/b3b_eh_1.part +13 -0
  253. reachy_mini/descriptions/reachy_mini/urdf/assets/b3b_eh_1.stl +0 -0
  254. reachy_mini/descriptions/reachy_mini/urdf/assets/ball.part +13 -0
  255. reachy_mini/descriptions/reachy_mini/urdf/assets/ball.stl +0 -0
  256. reachy_mini/descriptions/reachy_mini/urdf/assets/bearing_85x110x13.part +13 -0
  257. reachy_mini/descriptions/reachy_mini/urdf/assets/bearing_85x110x13.stl +0 -0
  258. reachy_mini/descriptions/reachy_mini/urdf/assets/big_lens.part +13 -0
  259. reachy_mini/descriptions/reachy_mini/urdf/assets/big_lens.stl +0 -0
  260. reachy_mini/descriptions/reachy_mini/urdf/assets/big_lens_d40.part +13 -0
  261. reachy_mini/descriptions/reachy_mini/urdf/assets/big_lens_d40.stl +0 -0
  262. reachy_mini/descriptions/reachy_mini/urdf/assets/body_down_3dprint.part +13 -0
  263. reachy_mini/descriptions/reachy_mini/urdf/assets/body_down_3dprint.stl +0 -0
  264. reachy_mini/descriptions/reachy_mini/urdf/assets/body_foot_3dprint.part +13 -0
  265. reachy_mini/descriptions/reachy_mini/urdf/assets/body_foot_3dprint.stl +0 -0
  266. reachy_mini/descriptions/reachy_mini/urdf/assets/body_top_3dprint.part +13 -0
  267. reachy_mini/descriptions/reachy_mini/urdf/assets/body_top_3dprint.stl +0 -0
  268. reachy_mini/descriptions/reachy_mini/urdf/assets/body_turning_3dprint.part +13 -0
  269. reachy_mini/descriptions/reachy_mini/urdf/assets/body_turning_3dprint.stl +0 -0
  270. reachy_mini/descriptions/reachy_mini/urdf/assets/bottom_body.part +13 -0
  271. reachy_mini/descriptions/reachy_mini/urdf/assets/bottom_body.stl +0 -0
  272. reachy_mini/descriptions/reachy_mini/urdf/assets/bts2_m2_6x8.part +13 -0
  273. reachy_mini/descriptions/reachy_mini/urdf/assets/bts2_m2_6x8.stl +0 -0
  274. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/README.m +1 -0
  275. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_back_0.stl +0 -0
  276. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_back_1.stl +0 -0
  277. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_back_2.stl +0 -0
  278. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_back_3.stl +0 -0
  279. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_front_0.stl +0 -0
  280. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_front_1.stl +0 -0
  281. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/body_top_3dprint_collider_front_2.stl +0 -0
  282. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/coarse/head_one_3dprint_collider_0.stl +0 -0
  283. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_back_0.stl +0 -0
  284. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_back_1.stl +0 -0
  285. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_back_2.stl +0 -0
  286. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_back_3.stl +0 -0
  287. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_front_0.stl +0 -0
  288. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_front_1.stl +0 -0
  289. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/body_top_3dprint_collider_front_2.stl +0 -0
  290. reachy_mini/descriptions/reachy_mini/urdf/assets/collision/fine/head_one_3dprint_collider_0.stl +0 -0
  291. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_b_dummy.part +13 -0
  292. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_b_dummy.stl +0 -0
  293. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_f_dummy.part +13 -0
  294. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_f_dummy.stl +0 -0
  295. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_m_dummy.part +13 -0
  296. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_case_m_dummy.stl +0 -0
  297. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_horn_dummy.part +13 -0
  298. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_horn_dummy.stl +0 -0
  299. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_led_cap2_dummy.part +13 -0
  300. reachy_mini/descriptions/reachy_mini/urdf/assets/dc15_a01_led_cap2_dummy.stl +0 -0
  301. reachy_mini/descriptions/reachy_mini/urdf/assets/drive_palonier__configuration_default.part +14 -0
  302. reachy_mini/descriptions/reachy_mini/urdf/assets/drive_palonier__configuration_default.stl +0 -0
  303. reachy_mini/descriptions/reachy_mini/urdf/assets/drive_palonier__configuration_simple_axe.part +14 -0
  304. reachy_mini/descriptions/reachy_mini/urdf/assets/drive_palonier__configuration_simple_axe.stl +0 -0
  305. reachy_mini/descriptions/reachy_mini/urdf/assets/eye_support.part +13 -0
  306. reachy_mini/descriptions/reachy_mini/urdf/assets/eye_support.stl +0 -0
  307. reachy_mini/descriptions/reachy_mini/urdf/assets/foot.part +13 -0
  308. reachy_mini/descriptions/reachy_mini/urdf/assets/foot.stl +0 -0
  309. reachy_mini/descriptions/reachy_mini/urdf/assets/glasses_dolder_3dprint.part +13 -0
  310. reachy_mini/descriptions/reachy_mini/urdf/assets/glasses_dolder_3dprint.stl +0 -0
  311. reachy_mini/descriptions/reachy_mini/urdf/assets/head_back_3dprint.part +13 -0
  312. reachy_mini/descriptions/reachy_mini/urdf/assets/head_back_3dprint.stl +0 -0
  313. reachy_mini/descriptions/reachy_mini/urdf/assets/head_front_3dprint.part +13 -0
  314. reachy_mini/descriptions/reachy_mini/urdf/assets/head_front_3dprint.stl +0 -0
  315. reachy_mini/descriptions/reachy_mini/urdf/assets/head_head_back.part +13 -0
  316. reachy_mini/descriptions/reachy_mini/urdf/assets/head_head_back.stl +0 -0
  317. reachy_mini/descriptions/reachy_mini/urdf/assets/head_interface.part +13 -0
  318. reachy_mini/descriptions/reachy_mini/urdf/assets/head_interface.stl +0 -0
  319. reachy_mini/descriptions/reachy_mini/urdf/assets/head_mic_3dprint.part +13 -0
  320. reachy_mini/descriptions/reachy_mini/urdf/assets/head_mic_3dprint.stl +0 -0
  321. reachy_mini/descriptions/reachy_mini/urdf/assets/head_shell_front.part +13 -0
  322. reachy_mini/descriptions/reachy_mini/urdf/assets/head_shell_front.stl +0 -0
  323. reachy_mini/descriptions/reachy_mini/urdf/assets/lens_cap_d30_3dprint.part +13 -0
  324. reachy_mini/descriptions/reachy_mini/urdf/assets/lens_cap_d30_3dprint.stl +0 -0
  325. reachy_mini/descriptions/reachy_mini/urdf/assets/lens_cap_d40_3dprint.part +13 -0
  326. reachy_mini/descriptions/reachy_mini/urdf/assets/lens_cap_d40_3dprint.stl +0 -0
  327. reachy_mini/descriptions/reachy_mini/urdf/assets/m12_fisheye_lens_1_8mm.part +13 -0
  328. reachy_mini/descriptions/reachy_mini/urdf/assets/m12_fisheye_lens_1_8mm.stl +0 -0
  329. reachy_mini/descriptions/reachy_mini/urdf/assets/m12_lens.part +13 -0
  330. reachy_mini/descriptions/reachy_mini/urdf/assets/m12_lens.stl +0 -0
  331. reachy_mini/descriptions/reachy_mini/urdf/assets/main_plate.part +13 -0
  332. reachy_mini/descriptions/reachy_mini/urdf/assets/main_plate.stl +0 -0
  333. reachy_mini/descriptions/reachy_mini/urdf/assets/mid_plate.part +13 -0
  334. reachy_mini/descriptions/reachy_mini/urdf/assets/mid_plate.stl +0 -0
  335. reachy_mini/descriptions/reachy_mini/urdf/assets/mp01062_stewart_arm_3.part +13 -0
  336. reachy_mini/descriptions/reachy_mini/urdf/assets/mp01062_stewart_arm_3.stl +0 -0
  337. reachy_mini/descriptions/reachy_mini/urdf/assets/neck_reference_3dprint.part +13 -0
  338. reachy_mini/descriptions/reachy_mini/urdf/assets/neck_reference_3dprint.stl +0 -0
  339. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10.part +13 -0
  340. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10.stl +0 -0
  341. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_1.part +13 -0
  342. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_1.stl +0 -0
  343. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_2.part +13 -0
  344. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_2.stl +0 -0
  345. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_3.part +13 -0
  346. reachy_mini/descriptions/reachy_mini/urdf/assets/phs_1_7x20_5_dc10_3.stl +0 -0
  347. reachy_mini/descriptions/reachy_mini/urdf/assets/plateform.part +13 -0
  348. reachy_mini/descriptions/reachy_mini/urdf/assets/plateform.stl +0 -0
  349. reachy_mini/descriptions/reachy_mini/urdf/assets/pp00xxx_stewart_rod.part +13 -0
  350. reachy_mini/descriptions/reachy_mini/urdf/assets/pp00xxx_stewart_rod.stl +0 -0
  351. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01062_stewart_arm.part +13 -0
  352. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01062_stewart_arm.stl +0 -0
  353. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01063_stewart_plateform.part +13 -0
  354. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01063_stewart_plateform.stl +0 -0
  355. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01064_stewart_main_plate.part +13 -0
  356. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01064_stewart_main_plate.stl +0 -0
  357. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01065_stewart_side_plate.part +13 -0
  358. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01065_stewart_side_plate.stl +0 -0
  359. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01066_stewart_mid_plate.part +13 -0
  360. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01066_stewart_mid_plate.stl +0 -0
  361. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01067_bottom_body.part +13 -0
  362. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01067_bottom_body.stl +0 -0
  363. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01068_top_body.part +13 -0
  364. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01068_top_body.stl +0 -0
  365. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01069_head_shell_front.part +13 -0
  366. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01069_head_shell_front.stl +0 -0
  367. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01070_head_head_back.part +13 -0
  368. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01070_head_head_back.stl +0 -0
  369. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01071_turning_bowl.part +13 -0
  370. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01071_turning_bowl.stl +0 -0
  371. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01072_turning_end.part +13 -0
  372. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01072_turning_end.stl +0 -0
  373. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01078_glasses.part +13 -0
  374. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01078_glasses.stl +0 -0
  375. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01079_back_big_eye.part +13 -0
  376. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01079_back_big_eye.stl +0 -0
  377. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01080_back_small_eye.part +13 -0
  378. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01080_back_small_eye.stl +0 -0
  379. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01102_arducam_carter.part +13 -0
  380. reachy_mini/descriptions/reachy_mini/urdf/assets/pp01102_arducam_carter.stl +0 -0
  381. reachy_mini/descriptions/reachy_mini/urdf/assets/rod.part +13 -0
  382. reachy_mini/descriptions/reachy_mini/urdf/assets/rod.stl +0 -0
  383. reachy_mini/descriptions/reachy_mini/urdf/assets/shape.part +13 -0
  384. reachy_mini/descriptions/reachy_mini/urdf/assets/shape.stl +0 -0
  385. reachy_mini/descriptions/reachy_mini/urdf/assets/side_plate.part +13 -0
  386. reachy_mini/descriptions/reachy_mini/urdf/assets/side_plate.stl +0 -0
  387. reachy_mini/descriptions/reachy_mini/urdf/assets/small_lens.part +13 -0
  388. reachy_mini/descriptions/reachy_mini/urdf/assets/small_lens.stl +0 -0
  389. reachy_mini/descriptions/reachy_mini/urdf/assets/small_lens_d30.part +13 -0
  390. reachy_mini/descriptions/reachy_mini/urdf/assets/small_lens_d30.stl +0 -0
  391. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_ball.part +13 -0
  392. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_ball.stl +0 -0
  393. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_ball__2.part +13 -0
  394. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_ball__2.stl +0 -0
  395. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_rod.part +13 -0
  396. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_link_rod.stl +0 -0
  397. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_main_plate_3dprint.part +13 -0
  398. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_main_plate_3dprint.stl +0 -0
  399. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_tricap_3dprint.part +13 -0
  400. reachy_mini/descriptions/reachy_mini/urdf/assets/stewart_tricap_3dprint.stl +0 -0
  401. reachy_mini/descriptions/reachy_mini/urdf/assets/test_antenna.part +13 -0
  402. reachy_mini/descriptions/reachy_mini/urdf/assets/test_antenna.stl +0 -0
  403. reachy_mini/descriptions/reachy_mini/urdf/assets/test_antenna_body.part +13 -0
  404. reachy_mini/descriptions/reachy_mini/urdf/assets/test_antenna_body.stl +0 -0
  405. reachy_mini/descriptions/reachy_mini/urdf/assets/top_body.part +13 -0
  406. reachy_mini/descriptions/reachy_mini/urdf/assets/top_body.stl +0 -0
  407. reachy_mini/descriptions/reachy_mini/urdf/assets/turning_bowl.part +13 -0
  408. reachy_mini/descriptions/reachy_mini/urdf/assets/turning_bowl.stl +0 -0
  409. reachy_mini/descriptions/reachy_mini/urdf/assets/uc_a37_rev_a_step.part +13 -0
  410. reachy_mini/descriptions/reachy_mini/urdf/assets/uc_a37_rev_a_step.stl +0 -0
  411. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0122topcabinetcase_95__configuration_default.part +14 -0
  412. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0122topcabinetcase_95__configuration_default.stl +0 -0
  413. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0122topcabinetcase_95__configuration_simple_axe.part +14 -0
  414. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0122topcabinetcase_95__configuration_simple_axe.stl +0 -0
  415. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0123middlecase_56__configuration_default.part +14 -0
  416. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0123middlecase_56__configuration_default.stl +0 -0
  417. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0123middlecase_56__configuration_simple_axe.part +14 -0
  418. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0123middlecase_56__configuration_simple_axe.stl +0 -0
  419. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0124bottomcase_45__configuration_default.part +14 -0
  420. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0124bottomcase_45__configuration_default.stl +0 -0
  421. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0124bottomcase_45__configuration_simple_axe.part +14 -0
  422. reachy_mini/descriptions/reachy_mini/urdf/assets/wj_wk00_0124bottomcase_45__configuration_simple_axe.stl +0 -0
  423. reachy_mini/descriptions/reachy_mini/urdf/config.json +18 -0
  424. reachy_mini/descriptions/reachy_mini/urdf/robot.urdf +3281 -0
  425. reachy_mini/descriptions/reachy_mini/urdf/robot.urdf.bak +3282 -0
  426. reachy_mini/descriptions/reachy_mini/urdf/robot_no_collision.urdf +2316 -0
  427. reachy_mini/descriptions/reachy_mini/urdf/robot_simple_collision.urdf +2399 -0
  428. reachy_mini/io/__init__.py +15 -0
  429. reachy_mini/io/abstract.py +70 -0
  430. reachy_mini/io/audio_ws.py +242 -0
  431. reachy_mini/io/protocol.py +44 -0
  432. reachy_mini/io/video_ws.py +135 -0
  433. reachy_mini/io/ws_controller.py +120 -0
  434. reachy_mini/io/zenoh_client.py +273 -0
  435. reachy_mini/io/zenoh_server.py +230 -0
  436. reachy_mini/kinematics/__init__.py +68 -0
  437. reachy_mini/kinematics/analytical_kinematics.py +151 -0
  438. reachy_mini/kinematics/nn_kinematics.py +109 -0
  439. reachy_mini/kinematics/placo_kinematics.py +656 -0
  440. reachy_mini/media/__init__.py +1 -0
  441. reachy_mini/media/audio_base.py +111 -0
  442. reachy_mini/media/audio_control_utils.py +455 -0
  443. reachy_mini/media/audio_gstreamer.py +272 -0
  444. reachy_mini/media/audio_sounddevice.py +321 -0
  445. reachy_mini/media/audio_utils.py +114 -0
  446. reachy_mini/media/camera_base.py +100 -0
  447. reachy_mini/media/camera_constants.py +152 -0
  448. reachy_mini/media/camera_gstreamer.py +231 -0
  449. reachy_mini/media/camera_opencv.py +89 -0
  450. reachy_mini/media/camera_utils.py +111 -0
  451. reachy_mini/media/media_manager.py +281 -0
  452. reachy_mini/media/webrtc_client_gstreamer.py +288 -0
  453. reachy_mini/media/webrtc_daemon.py +334 -0
  454. reachy_mini/motion/__init__.py +4 -0
  455. reachy_mini/motion/goto.py +71 -0
  456. reachy_mini/motion/move.py +43 -0
  457. reachy_mini/motion/recorded_move.py +146 -0
  458. reachy_mini/reachy_mini.py +753 -0
  459. reachy_mini/tools/reflash_motors.py +116 -0
  460. reachy_mini/tools/setup_motor.py +422 -0
  461. reachy_mini/tools/setup_motor_rpi.py +108 -0
  462. reachy_mini/utils/__init__.py +46 -0
  463. reachy_mini/utils/constants.py +9 -0
  464. reachy_mini/utils/hardware_config/__init__.py +1 -0
  465. reachy_mini/utils/hardware_config/parser.py +65 -0
  466. reachy_mini/utils/interpolation.py +227 -0
  467. reachy_mini/utils/parse_urdf_for_kinematics.py +110 -0
  468. reachy_mini/utils/rerun.py +320 -0
  469. reachy_mini/utils/wireless_version/__init__.py +1 -0
  470. reachy_mini/utils/wireless_version/startup_check.py +144 -0
  471. reachy_mini/utils/wireless_version/update.py +20 -0
  472. reachy_mini/utils/wireless_version/update_available.py +61 -0
  473. reachy_mini/utils/wireless_version/utils.py +39 -0
  474. reachy_mini-1.2.5rc1.dist-info/METADATA +161 -0
  475. reachy_mini-1.2.5rc1.dist-info/RECORD +479 -0
  476. reachy_mini-1.2.5rc1.dist-info/WHEEL +5 -0
  477. reachy_mini-1.2.5rc1.dist-info/entry_points.txt +4 -0
  478. reachy_mini-1.2.5rc1.dist-info/licenses/LICENSE +201 -0
  479. reachy_mini-1.2.5rc1.dist-info/top_level.txt +1 -0
@@ -0,0 +1,753 @@
1
+ """Reachy Mini class for controlling a simulated or real Reachy Mini robot.
2
+
3
+ This class provides methods to control the head and antennas of the Reachy Mini robot,
4
+ set their target positions, and perform various behaviors such as waking up and going to sleep.
5
+
6
+ It also includes methods for multimedia interactions like playing sounds and looking at specific points in the image frame or world coordinates.
7
+ """
8
+
9
+ import asyncio
10
+ import json
11
+ import logging
12
+ import time
13
+ from typing import Dict, List, Optional, Union
14
+
15
+ import cv2
16
+ import numpy as np
17
+ import numpy.typing as npt
18
+ from asgiref.sync import async_to_sync
19
+ from scipy.spatial.transform import Rotation as R
20
+
21
+ from reachy_mini.daemon.utils import daemon_check
22
+ from reachy_mini.io.protocol import GotoTaskRequest
23
+ from reachy_mini.io.zenoh_client import ZenohClient
24
+ from reachy_mini.media.media_manager import MediaBackend, MediaManager
25
+ from reachy_mini.motion.move import Move
26
+ from reachy_mini.utils.interpolation import InterpolationTechnique, minimum_jerk
27
+
28
+ # Behavior definitions
29
+ INIT_HEAD_POSE = np.eye(4)
30
+
31
+ SLEEP_HEAD_JOINT_POSITIONS = [
32
+ 0,
33
+ -0.9848156658225817,
34
+ 1.2624661884298831,
35
+ -0.24390294527381684,
36
+ 0.20555342557667577,
37
+ -1.2363885150358267,
38
+ 1.0032234352772091,
39
+ ]
40
+
41
+
42
+ SLEEP_ANTENNAS_JOINT_POSITIONS = [-3.05, 3.05]
43
+ SLEEP_HEAD_POSE = np.array(
44
+ [
45
+ [0.911, 0.004, 0.413, -0.021],
46
+ [-0.004, 1.0, -0.001, 0.001],
47
+ [-0.413, -0.001, 0.911, -0.044],
48
+ [0.0, 0.0, 0.0, 1.0],
49
+ ]
50
+ )
51
+
52
+
53
+ class ReachyMini:
54
+ """Reachy Mini class for controlling a simulated or real Reachy Mini robot.
55
+
56
+ Args:
57
+ localhost_only (bool): If True, will only connect to localhost daemons, defaults to True.
58
+ spawn_daemon (bool): If True, will spawn a daemon to control the robot, defaults to False.
59
+ use_sim (bool): If True and spawn_daemon is True, will spawn a simulated robot, defaults to True.
60
+
61
+ """
62
+
63
+ def __init__(
64
+ self,
65
+ robot_name: str = "reachy_mini",
66
+ localhost_only: bool = True,
67
+ spawn_daemon: bool = False,
68
+ use_sim: bool = False,
69
+ timeout: float = 5.0,
70
+ automatic_body_yaw: bool = True,
71
+ log_level: str = "INFO",
72
+ media_backend: str = "default",
73
+ ) -> None:
74
+ """Initialize the Reachy Mini robot.
75
+
76
+ Args:
77
+ robot_name (str): Name of the robot, defaults to "reachy_mini".
78
+ localhost_only (bool): If True, will only connect to localhost daemons, defaults to True.
79
+ spawn_daemon (bool): If True, will spawn a daemon to control the robot, defaults to False.
80
+ use_sim (bool): If True and spawn_daemon is True, will spawn a simulated robot, defaults to True.
81
+ timeout (float): Timeout for the client connection, defaults to 5.0 seconds.
82
+ automatic_body_yaw (bool): If True, the body yaw will be used to compute the IK and FK. Default is False.
83
+ log_level (str): Logging level, defaults to "INFO".
84
+ media_backend (str): Media backend to use, either "default" (OpenCV), "gstreamer" or "webrtc", defaults to "default".
85
+
86
+ It will try to connect to the daemon, and if it fails, it will raise an exception.
87
+
88
+ """
89
+ self.logger = logging.getLogger(__name__)
90
+ self.logger.setLevel(log_level)
91
+ self.robot_name = robot_name
92
+ daemon_check(spawn_daemon, use_sim)
93
+ self.client = ZenohClient(robot_name, localhost_only)
94
+ self.client.wait_for_connection(timeout=timeout)
95
+ self.set_automatic_body_yaw(automatic_body_yaw)
96
+ self._last_head_pose: Optional[npt.NDArray[np.float64]] = None
97
+ self.is_recording = False
98
+
99
+ self.T_head_cam = np.eye(4)
100
+ self.T_head_cam[:3, 3][:] = [0.0437, 0, 0.0512]
101
+ self.T_head_cam[:3, :3] = np.array(
102
+ [
103
+ [0, 0, 1],
104
+ [-1, 0, 0],
105
+ [0, -1, 0],
106
+ ]
107
+ )
108
+
109
+ self.media_manager = self._configure_mediamanager(media_backend, log_level)
110
+
111
+ def __del__(self) -> None:
112
+ """Destroy the Reachy Mini instance.
113
+
114
+ The client is disconnected explicitly to avoid a thread pending issue.
115
+
116
+ """
117
+ if hasattr(self, "client"):
118
+ self.client.disconnect()
119
+
120
+ def __enter__(self) -> "ReachyMini":
121
+ """Context manager entry point for Reachy Mini."""
122
+ return self
123
+
124
+ def __exit__(self, exc_type, exc_value, traceback) -> None: # type: ignore [no-untyped-def]
125
+ """Context manager exit point for Reachy Mini."""
126
+ self.media_manager.close()
127
+ self.client.disconnect()
128
+
129
+ @property
130
+ def media(self) -> MediaManager:
131
+ """Expose the MediaManager instance used by ReachyMini."""
132
+ return self.media_manager
133
+
134
+ def _configure_mediamanager(
135
+ self, media_backend: str, log_level: str
136
+ ) -> MediaManager:
137
+ mbackend = MediaBackend.DEFAULT
138
+ daemon_status = self.client.get_status()
139
+
140
+ # If wireless, force webrtc unless no_media is selected
141
+ if media_backend != "no_media" and daemon_status.get(
142
+ "wireless_version"
143
+ ):
144
+ mbackend = MediaBackend.WEBRTC
145
+ else:
146
+ match media_backend.lower():
147
+ case "webrtc":
148
+ if not daemon_status.get("wireless_version"):
149
+ self.logger.warning(
150
+ "Non-wireless version detected, daemon should use the flag '--wireless-version'. Reverting to default"
151
+ )
152
+ mbackend = MediaBackend.DEFAULT
153
+ else:
154
+ self.logger.info("WebRTC backend configured successfully.")
155
+ mbackend = MediaBackend.WEBRTC
156
+ case "gstreamer":
157
+ mbackend = MediaBackend.GSTREAMER
158
+ case "default":
159
+ mbackend = MediaBackend.DEFAULT
160
+ case "no_media":
161
+ mbackend = MediaBackend.NO_MEDIA
162
+ case "default_no_video":
163
+ mbackend = MediaBackend.DEFAULT_NO_VIDEO
164
+ case _:
165
+ raise ValueError(
166
+ f"Invalid media_backend '{media_backend}'. Supported values are 'default', 'gstreamer', 'no_media', 'default_no_video', and 'webrtc'."
167
+ )
168
+
169
+ return MediaManager(
170
+ use_sim=self.client.get_status()["simulation_enabled"],
171
+ backend=mbackend,
172
+ log_level=log_level,
173
+ signalling_host=self.client.get_status()["wlan_ip"],
174
+ )
175
+
176
+ def set_target(
177
+ self,
178
+ head: Optional[npt.NDArray[np.float64]] = None, # 4x4 pose matrix
179
+ antennas: Optional[
180
+ Union[npt.NDArray[np.float64], List[float]]
181
+ ] = None, # [right_angle, left_angle] (in rads)
182
+ body_yaw: Optional[float] = None, # Body yaw angle in radians
183
+ ) -> None:
184
+ """Set the target pose of the head and/or the target position of the antennas.
185
+
186
+ Args:
187
+ head (Optional[np.ndarray]): 4x4 pose matrix representing the head pose.
188
+ antennas (Optional[Union[np.ndarray, List[float]]]): 1D array with two elements representing the angles of the antennas in radians.
189
+ body_yaw (Optional[float]): Body yaw angle in radians.
190
+
191
+ Raises:
192
+ ValueError: If neither head nor antennas are provided, or if the shape of head is not (4, 4), or if antennas is not a 1D array with two elements.
193
+
194
+ """
195
+ if head is None and antennas is None and body_yaw is None:
196
+ raise ValueError(
197
+ "At least one of head, antennas or body_yaw must be provided."
198
+ )
199
+
200
+ if head is not None and not head.shape == (4, 4):
201
+ raise ValueError(f"Head pose must be a 4x4 matrix, got shape {head.shape}.")
202
+
203
+ if antennas is not None and not len(antennas) == 2:
204
+ raise ValueError(
205
+ "Antennas must be a list or 1D np array with two elements."
206
+ )
207
+
208
+ if body_yaw is not None and not isinstance(body_yaw, (int, float)):
209
+ raise ValueError("body_yaw must be a float.")
210
+
211
+ if head is not None:
212
+ self.set_target_head_pose(head)
213
+
214
+ if antennas is not None:
215
+ self.set_target_antenna_joint_positions(list(antennas))
216
+ # self._set_joint_positions(
217
+ # antennas_joint_positions=list(antennas),
218
+ # )
219
+
220
+ if body_yaw is not None:
221
+ self.set_target_body_yaw(body_yaw)
222
+
223
+ self._last_head_pose = head
224
+
225
+ record: Dict[str, float | List[float] | List[List[float]]] = {
226
+ "time": time.time(),
227
+ "body_yaw": body_yaw if body_yaw is not None else 0.0,
228
+ }
229
+ if head is not None:
230
+ record["head"] = head.tolist()
231
+ if antennas is not None:
232
+ record["antennas"] = list(antennas)
233
+ if body_yaw is not None:
234
+ record["body_yaw"] = body_yaw
235
+ self._set_record_data(record)
236
+
237
+ def goto_target(
238
+ self,
239
+ head: Optional[npt.NDArray[np.float64]] = None, # 4x4 pose matrix
240
+ antennas: Optional[
241
+ Union[npt.NDArray[np.float64], List[float]]
242
+ ] = None, # [right_angle, left_angle] (in rads)
243
+ duration: float = 0.5, # Duration in seconds for the movement, default is 0.5 seconds.
244
+ method: InterpolationTechnique = InterpolationTechnique.MIN_JERK, # can be "linear", "minjerk", "ease" or "cartoon", default is "minjerk")
245
+ body_yaw: float | None = 0.0, # Body yaw angle in radians
246
+ ) -> None:
247
+ """Go to a target head pose and/or antennas position using task space interpolation, in "duration" seconds.
248
+
249
+ Args:
250
+ head (Optional[np.ndarray]): 4x4 pose matrix representing the target head pose.
251
+ antennas (Optional[Union[np.ndarray, List[float]]]): 1D array with two elements representing the angles of the antennas in radians.
252
+ duration (float): Duration of the movement in seconds.
253
+ method (InterpolationTechnique): Interpolation method to use ("linear", "minjerk", "ease", "cartoon"). Default is "minjerk".
254
+ body_yaw (float | None): Body yaw angle in radians. Use None to keep the current yaw.
255
+
256
+ Raises:
257
+ ValueError: If neither head nor antennas are provided, or if duration is not positive.
258
+
259
+ """
260
+ if head is None and antennas is None and body_yaw is None:
261
+ raise ValueError(
262
+ "At least one of head, antennas or body_yaw must be provided."
263
+ )
264
+
265
+ if duration <= 0.0:
266
+ raise ValueError(
267
+ "Duration must be positive and non-zero. Use set_target() for immediate position setting."
268
+ )
269
+
270
+ req = GotoTaskRequest(
271
+ head=np.array(head, dtype=np.float64).flatten().tolist()
272
+ if head is not None
273
+ else None,
274
+ antennas=np.array(antennas, dtype=np.float64).flatten().tolist()
275
+ if antennas is not None
276
+ else None,
277
+ duration=duration,
278
+ method=method,
279
+ body_yaw=body_yaw,
280
+ )
281
+
282
+ task_uid = self.client.send_task_request(req)
283
+ self.client.wait_for_task_completion(task_uid, timeout=duration + 1.0)
284
+
285
+ def wake_up(self) -> None:
286
+ """Wake up the robot - go to the initial head position and play the wake up emote and sound."""
287
+ self.goto_target(INIT_HEAD_POSE, antennas=[0.0, 0.0], duration=2)
288
+ time.sleep(0.1)
289
+
290
+ # Toudoum
291
+ self.media.play_sound("wake_up.wav")
292
+
293
+ # Roll 20° to the left
294
+ pose = INIT_HEAD_POSE.copy()
295
+ pose[:3, :3] = R.from_euler("xyz", [20, 0, 0], degrees=True).as_matrix()
296
+ self.goto_target(pose, duration=0.2)
297
+
298
+ # Go back to the initial position
299
+ self.goto_target(INIT_HEAD_POSE, duration=0.2)
300
+
301
+ def goto_sleep(self) -> None:
302
+ """Put the robot to sleep by moving the head and antennas to a predefined sleep position."""
303
+ # Check if we are too far from the initial position
304
+ # Move to the initial position if necessary
305
+ current_positions, _ = self.get_current_joint_positions()
306
+ # init_positions = self.head_kinematics.ik(INIT_HEAD_POSE)
307
+ # Todo : get init position from the daemon?
308
+ init_positions = [
309
+ 6.959852054044218e-07,
310
+ 0.5251518455536499,
311
+ -0.668710345667336,
312
+ 0.6067086443974802,
313
+ -0.606711497194891,
314
+ 0.6687148024583701,
315
+ -0.5251586523105128,
316
+ ]
317
+ dist = np.linalg.norm(np.array(current_positions) - np.array(init_positions))
318
+ if dist > 0.2:
319
+ self.goto_target(INIT_HEAD_POSE, antennas=[0.0, 0.0], duration=1)
320
+ time.sleep(0.2)
321
+
322
+ # Pfiou
323
+ self.media.play_sound("go_sleep.wav")
324
+
325
+ # # Move to the sleep position
326
+ self.goto_target(
327
+ SLEEP_HEAD_POSE, antennas=SLEEP_ANTENNAS_JOINT_POSITIONS, duration=2
328
+ )
329
+
330
+ self._last_head_pose = SLEEP_HEAD_POSE
331
+ time.sleep(2)
332
+
333
+ def look_at_image(
334
+ self, u: int, v: int, duration: float = 1.0, perform_movement: bool = True
335
+ ) -> npt.NDArray[np.float64]:
336
+ """Make the robot head look at a point defined by a pixel position (u,v).
337
+
338
+ # TODO image of reachy mini coordinate system
339
+
340
+ Args:
341
+ u (int): Horizontal coordinate in image frame.
342
+ v (int): Vertical coordinate in image frame.
343
+ duration (float): Duration of the movement in seconds. If 0, the head will snap to the position immediately.
344
+ perform_movement (bool): If True, perform the movement. If False, only calculate and return the pose.
345
+
346
+ Returns:
347
+ np.ndarray: The calculated head pose as a 4x4 matrix.
348
+
349
+ Raises:
350
+ ValueError: If duration is negative.
351
+
352
+ """
353
+ if self.media_manager.camera is None:
354
+ raise RuntimeError("Camera is not initialized.")
355
+
356
+ # TODO this is false for the raspicam for now
357
+ assert 0 < u < self.media_manager.camera.resolution[0], (
358
+ f"u must be in [0, {self.media_manager.camera.resolution[0]}], got {u}."
359
+ )
360
+ assert 0 < v < self.media_manager.camera.resolution[1], (
361
+ f"v must be in [0, {self.media_manager.camera.resolution[1]}], got {v}."
362
+ )
363
+
364
+ if duration < 0:
365
+ raise ValueError("Duration can't be negative.")
366
+
367
+ if self.media.camera is None or self.media.camera.camera_specs is None:
368
+ raise RuntimeError("Camera specs not set.")
369
+
370
+ points = np.array([[[u, v]]], dtype=np.float32)
371
+ x_n, y_n = cv2.undistortPoints(
372
+ points,
373
+ self.media.camera.K, # type: ignore
374
+ self.media.camera.D, # type: ignore
375
+ )[0, 0]
376
+
377
+ ray_cam = np.array([x_n, y_n, 1.0])
378
+ ray_cam /= np.linalg.norm(ray_cam)
379
+
380
+ T_world_head = self.get_current_head_pose()
381
+ T_world_cam = T_world_head @ self.T_head_cam
382
+
383
+ R_wc = T_world_cam[:3, :3]
384
+ t_wc = T_world_cam[:3, 3]
385
+
386
+ ray_world = R_wc @ ray_cam
387
+
388
+ P_world = t_wc + ray_world
389
+
390
+ return self.look_at_world(
391
+ x=P_world[0],
392
+ y=P_world[1],
393
+ z=P_world[2],
394
+ duration=duration,
395
+ perform_movement=perform_movement,
396
+ )
397
+
398
+ def look_at_world(
399
+ self,
400
+ x: float,
401
+ y: float,
402
+ z: float,
403
+ duration: float = 1.0,
404
+ perform_movement: bool = True,
405
+ ) -> npt.NDArray[np.float64]:
406
+ """Look at a specific point in 3D space in Reachy Mini's reference frame.
407
+
408
+ TODO include image of reachy mini coordinate system
409
+
410
+ Args:
411
+ x (float): X coordinate in meters.
412
+ y (float): Y coordinate in meters.
413
+ z (float): Z coordinate in meters.
414
+ duration (float): Duration of the movement in seconds. If 0, the head will snap to the position immediately.
415
+ perform_movement (bool): If True, perform the movement. If False, only calculate and return the pose.
416
+
417
+ Returns:
418
+ np.ndarray: The calculated head pose as a 4x4 matrix.
419
+
420
+ Raises:
421
+ ValueError: If duration is negative.
422
+
423
+ """
424
+ if duration < 0:
425
+ raise ValueError("Duration can't be negative.")
426
+
427
+ # Head is at the origin, so vector from head to target position is directly the target position
428
+ # TODO FIX : Actually, the head frame is not the origin frame wrt the kinematics. Close enough for now.
429
+ target_position = np.array([x, y, z])
430
+ target_vector = target_position / np.linalg.norm(
431
+ target_position
432
+ ) # normalize the vector
433
+
434
+ # head_pointing straight vector
435
+ straight_head_vector = np.array([1, 0, 0])
436
+
437
+ # Calculate the rotation needed to align the head with the target vector
438
+ v1 = straight_head_vector
439
+ v2 = target_vector
440
+ axis = np.cross(v1, v2)
441
+ axis_norm = np.linalg.norm(axis)
442
+ if axis_norm < 1e-8:
443
+ # Vectors are (almost) parallel
444
+ if np.dot(v1, v2) > 0:
445
+ rot_mat = np.eye(3)
446
+ else:
447
+ # Opposite direction: rotate 180° around any perpendicular axis
448
+ perp = np.array([0, 1, 0]) if abs(v1[0]) < 0.9 else np.array([0, 0, 1])
449
+ axis = np.cross(v1, perp)
450
+ axis /= np.linalg.norm(axis)
451
+ rot_mat = R.from_rotvec(np.pi * axis).as_matrix()
452
+ else:
453
+ axis = axis / axis_norm
454
+ angle = np.arccos(np.clip(np.dot(v1, v2), -1.0, 1.0))
455
+ rotation_vector = angle * axis
456
+ rot_mat = R.from_rotvec(rotation_vector).as_matrix()
457
+
458
+ target_head_pose = np.eye(4)
459
+ target_head_pose[:3, :3] = rot_mat
460
+
461
+ # If perform_movement is True, execute the movement
462
+ if perform_movement:
463
+ # If duration is specified, use the goto_target method to move smoothly
464
+ # Otherwise, set the position immediately
465
+ if duration > 0:
466
+ self.goto_target(target_head_pose, duration=duration)
467
+ else:
468
+ self.set_target(target_head_pose)
469
+
470
+ return target_head_pose
471
+
472
+ def _goto_joint_positions(
473
+ self,
474
+ head_joint_positions: Optional[
475
+ List[float]
476
+ ] = None, # [yaw, stewart_platform x 6] length 7
477
+ antennas_joint_positions: Optional[
478
+ List[float]
479
+ ] = None, # [right_angle, left_angle] length 2
480
+ duration: float = 0.5, # Duration in seconds for the movement
481
+ ) -> None:
482
+ """Go to a target head joint positions and/or antennas joint positions using joint space interpolation, in "duration" seconds.
483
+
484
+ [Internal] Go to a target head joint positions and/or antennas joint positions using joint space interpolation, in "duration" seconds.
485
+
486
+ Args:
487
+ head_joint_positions (Optional[List[float]]): List of head joint positions in radians (length 7).
488
+ antennas_joint_positions (Optional[List[float]]): List of antennas joint positions in radians (length 2).
489
+ duration (float): Duration of the movement in seconds. Default is 0.5 seconds.
490
+
491
+ Raises:
492
+ ValueError: If neither head_joint_positions nor antennas_joint_positions are provided, or if duration is not positive.
493
+
494
+ """
495
+ if duration <= 0.0:
496
+ raise ValueError(
497
+ "Duration must be positive and non-zero. Use set_target() for immediate position setting."
498
+ )
499
+
500
+ cur_head, cur_antennas = self.get_current_joint_positions()
501
+ current = cur_head + cur_antennas
502
+
503
+ target = []
504
+ if head_joint_positions is not None:
505
+ target.extend(head_joint_positions)
506
+ else:
507
+ target.extend(cur_head)
508
+ if antennas_joint_positions is not None:
509
+ target.extend(antennas_joint_positions)
510
+ else:
511
+ target.extend(cur_antennas)
512
+
513
+ traj = minimum_jerk(np.array(current), np.array(target), duration)
514
+
515
+ t0 = time.time()
516
+ while time.time() - t0 < duration:
517
+ t = time.time() - t0
518
+ angles = traj(t)
519
+
520
+ head_joint = angles[:7] # First 7 angles for the head
521
+ antennas_joint = angles[7:]
522
+
523
+ self._set_joint_positions(list(head_joint), list(antennas_joint))
524
+ time.sleep(0.01)
525
+
526
+ def get_current_joint_positions(self) -> tuple[list[float], list[float]]:
527
+ """Get the current joint positions of the head and antennas.
528
+
529
+ Get the current joint positions of the head and antennas (in rad)
530
+
531
+ Returns:
532
+ tuple: A tuple containing two lists:
533
+ - List of head joint positions (rad) (length 7).
534
+ - List of antennas joint positions (rad) (length 2).
535
+
536
+ """
537
+ return self.client.get_current_joints()
538
+
539
+ def get_present_antenna_joint_positions(self) -> list[float]:
540
+ """Get the present joint positions of the antennas.
541
+
542
+ Get the present joint positions of the antennas (in rad)
543
+
544
+ Returns:
545
+ list: A list of antennas joint positions (rad) (length 2).
546
+
547
+ """
548
+ return self.get_current_joint_positions()[1]
549
+
550
+ def get_current_head_pose(self) -> npt.NDArray[np.float64]:
551
+ """Get the current head pose as a 4x4 matrix.
552
+
553
+ Get the current head pose as a 4x4 matrix.
554
+
555
+ Returns:
556
+ np.ndarray: A 4x4 matrix representing the current head pose.
557
+
558
+ """
559
+ return self.client.get_current_head_pose()
560
+
561
+ def _set_joint_positions(
562
+ self,
563
+ head_joint_positions: list[float] | None = None,
564
+ antennas_joint_positions: list[float] | None = None,
565
+ ) -> None:
566
+ """Set the joint positions of the head and/or antennas.
567
+
568
+ [Internal] Set the joint positions of the head and/or antennas.
569
+
570
+ Args:
571
+ head_joint_positions (Optional[List[float]]): List of head joint positions in radians (length 7).
572
+ antennas_joint_positions (Optional[List[float]]): List of antennas joint positions in radians (length 2).
573
+ record (Optional[Dict]): If provided, the command will be logged with the given record data.
574
+
575
+ """
576
+ cmd = {}
577
+
578
+ if head_joint_positions is not None:
579
+ assert len(head_joint_positions) == 7, (
580
+ f"Head joint positions must have length 7, got {head_joint_positions}."
581
+ )
582
+ cmd["head_joint_positions"] = list(head_joint_positions)
583
+
584
+ if antennas_joint_positions is not None:
585
+ assert len(antennas_joint_positions) == 2, "Antennas must have length 2."
586
+ cmd["antennas_joint_positions"] = list(antennas_joint_positions)
587
+
588
+ if not cmd:
589
+ raise ValueError(
590
+ "At least one of head_joint_positions or antennas must be provided."
591
+ )
592
+
593
+ self.client.send_command(json.dumps(cmd))
594
+
595
+ def set_target_head_pose(self, pose: npt.NDArray[np.float64]) -> None:
596
+ """Set the head pose to a specific 4x4 matrix.
597
+
598
+ Args:
599
+ pose (np.ndarray): A 4x4 matrix representing the desired head pose.
600
+ body_yaw (float): The yaw angle of the body, used to adjust the head pose.
601
+
602
+ Raises:
603
+ ValueError: If the shape of the pose is not (4, 4).
604
+
605
+ """
606
+ cmd = {}
607
+
608
+ if pose is not None:
609
+ assert pose.shape == (4, 4), (
610
+ f"Head pose should be a 4x4 matrix, got {pose.shape}."
611
+ )
612
+ cmd["head_pose"] = pose.tolist()
613
+ else:
614
+ raise ValueError("Pose must be provided as a 4x4 matrix.")
615
+
616
+ self.client.send_command(json.dumps(cmd))
617
+
618
+ def set_target_antenna_joint_positions(self, antennas: List[float]) -> None:
619
+ """Set the target joint positions of the antennas."""
620
+ cmd = {"antennas_joint_positions": antennas}
621
+ self.client.send_command(json.dumps(cmd))
622
+
623
+ def set_target_body_yaw(self, body_yaw: float) -> None:
624
+ """Set the target body yaw.
625
+
626
+ Args:
627
+ body_yaw (float): The yaw angle of the body in radians.
628
+
629
+ """
630
+ cmd = {"body_yaw": body_yaw}
631
+ self.client.send_command(json.dumps(cmd))
632
+
633
+ def start_recording(self) -> None:
634
+ """Start recording data."""
635
+ self.client.send_command(json.dumps({"start_recording": True}))
636
+ self.is_recording = True
637
+
638
+ def stop_recording(
639
+ self,
640
+ ) -> Optional[List[Dict[str, float | List[float] | List[List[float]]]]]:
641
+ """Stop recording data and return the recorded data."""
642
+ self.client.send_command(json.dumps({"stop_recording": True}))
643
+ self.is_recording = False
644
+ if not self.client.wait_for_recorded_data(timeout=5):
645
+ raise RuntimeError("Daemon did not provide recorded data in time!")
646
+ recorded_data = self.client.get_recorded_data(wait=False)
647
+
648
+ return recorded_data
649
+
650
+ def _set_record_data(
651
+ self, record: Dict[str, float | List[float] | List[List[float]]]
652
+ ) -> None:
653
+ """Set the record data to be logged by the backend.
654
+
655
+ Args:
656
+ record (Dict): The record data to be logged.
657
+
658
+ """
659
+ if not isinstance(record, dict):
660
+ raise ValueError("Record must be a dictionary.")
661
+
662
+ # Send the record data to the backend
663
+ self.client.send_command(json.dumps({"set_target_record": record}))
664
+
665
+ def enable_motors(self, ids: List[str] | None = None) -> None:
666
+ """Enable the motors.
667
+
668
+ Args:
669
+ ids (List[str] | None): List of motor names to enable. If None, all motors will be enabled.
670
+
671
+ """
672
+ self._set_torque(True, ids=ids)
673
+
674
+ def disable_motors(self, ids: List[str] | None = None) -> None:
675
+ """Disable the motors.
676
+
677
+ Args:
678
+ ids (List[str] | None): List of motor names to disable. If None, all motors will be disabled.
679
+
680
+ """
681
+ self._set_torque(False, ids=ids)
682
+
683
+ def _set_torque(self, on: bool, ids: List[str] | None = None) -> None:
684
+ self.client.send_command(json.dumps({"torque": on, "ids": ids}))
685
+
686
+ def enable_gravity_compensation(self) -> None:
687
+ """Enable gravity compensation for the head motors."""
688
+ self.client.send_command(json.dumps({"gravity_compensation": True}))
689
+
690
+ def disable_gravity_compensation(self) -> None:
691
+ """Disable gravity compensation for the head motors."""
692
+ self.client.send_command(json.dumps({"gravity_compensation": False}))
693
+
694
+ def set_automatic_body_yaw(self, body_yaw: float) -> None:
695
+ """Set the automatic body yaw.
696
+
697
+ Args:
698
+ body_yaw (float): The yaw angle of the body in radians.
699
+
700
+ """
701
+ self.client.send_command(json.dumps({"automatic_body_yaw": body_yaw}))
702
+
703
+ async def async_play_move(
704
+ self,
705
+ move: Move,
706
+ play_frequency: float = 100.0,
707
+ initial_goto_duration: float = 0.0,
708
+ sound: bool = True,
709
+ ) -> None:
710
+ """Asynchronously play a Move.
711
+
712
+ Args:
713
+ move (Move): The Move object to be played.
714
+ play_frequency (float): The frequency at which to evaluate the move (in Hz).
715
+ initial_goto_duration (float): Duration for the initial goto to the starting position of the move (in seconds). If 0, no initial goto is performed.
716
+ sound (bool): If True, play the sound associated with the move (if any).
717
+
718
+ """
719
+ if initial_goto_duration > 0.0:
720
+ start_head_pose, start_antennas_positions, start_body_yaw = move.evaluate(
721
+ 0.0
722
+ )
723
+ self.goto_target(
724
+ head=start_head_pose,
725
+ antennas=start_antennas_positions,
726
+ duration=initial_goto_duration,
727
+ body_yaw=start_body_yaw,
728
+ )
729
+
730
+ sleep_period = 1.0 / play_frequency
731
+
732
+ if move.sound_path is not None and sound:
733
+ self.media_manager.play_sound(str(move.sound_path))
734
+
735
+ t0 = time.time()
736
+ while time.time() - t0 < move.duration:
737
+ t = min(time.time() - t0, move.duration - 1e-2)
738
+
739
+ head, antennas, body_yaw = move.evaluate(t)
740
+ if head is not None:
741
+ self.set_target_head_pose(head)
742
+ if body_yaw is not None:
743
+ self.set_target_body_yaw(body_yaw)
744
+ if antennas is not None:
745
+ self.set_target_antenna_joint_positions(list(antennas))
746
+
747
+ elapsed = time.time() - t0 - t
748
+ if elapsed < sleep_period:
749
+ await asyncio.sleep(sleep_period - elapsed)
750
+ else:
751
+ await asyncio.sleep(0.001)
752
+
753
+ play_move = async_to_sync(async_play_move)