@volter/cyclotron 0.0.0-stage → 0.5.192

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 (607) hide show
  1. package/BUNDLED_NOTICES +6877 -0
  2. package/LICENSE +670 -0
  3. package/LICENSE-BLENDER +1409 -0
  4. package/LICENSE-MCP +21 -0
  5. package/NOTICE +20 -0
  6. package/README.md +91 -2
  7. package/dist/.vite/manifest.json +5432 -0
  8. package/dist/assets/BVHLoader-Dxn1IBPh.js +1 -0
  9. package/dist/assets/ColladaLoader-FWjhft-R.js +3 -0
  10. package/dist/assets/EntityModelDocument-KYkNDaSy.js +1 -0
  11. package/dist/assets/EnvironmentAssetDocument-Bn36-K03.js +1 -0
  12. package/dist/assets/FBXLoader-B6D0-2sM.js +1 -0
  13. package/dist/assets/InspectorObjectPreview-CQMs9zha.js +1 -0
  14. package/dist/assets/LineSegments2-D1_2s-N-.js +370 -0
  15. package/dist/assets/LiveModuleDocument-ye1IT-i6.js +2 -0
  16. package/dist/assets/LutAssetDocument-CouZZubV.js +1 -0
  17. package/dist/assets/MTLLoader-BwtVpZY2.js +2 -0
  18. package/dist/assets/ModelAssetDocument-SpE-ctRj.js +1 -0
  19. package/dist/assets/NonThreeAuthoringBootstrap-BAe_hy9t.js +1 -0
  20. package/dist/assets/OBJLoader-Cwe-BN99.js +5 -0
  21. package/dist/assets/Object3DDocumentToolbar-Bfm-RTS8.js +1 -0
  22. package/dist/assets/Object3DPreview-C4Ai3BNI.js +2 -0
  23. package/dist/assets/OrbitControls-Cn2q_IQK.js +1 -0
  24. package/dist/assets/PLYLoader-DOl6qb2a.js +2 -0
  25. package/dist/assets/QuarksAssetDocument-CqYjSnLo.js +2 -0
  26. package/dist/assets/RectAreaLightUniformsLib-CobhIWNK.js +1 -0
  27. package/dist/assets/STLLoader-B5YpfCGT.js +1 -0
  28. package/dist/assets/ShaderAssetDocument-BBT3ENGG.js +1 -0
  29. package/dist/assets/StageHost-qZAn6HZ3.js +1179 -0
  30. package/dist/assets/TDSLoader-BdQ2M2WU.js +1 -0
  31. package/dist/assets/ToolObject3DPreview-ClIcOYFk.js +1 -0
  32. package/dist/assets/ViewportShadingMenu-DmM-Odyl.js +1 -0
  33. package/dist/assets/animation-mixers.service-CsBdF1O3.js +1 -0
  34. package/dist/assets/animation-timeline.utility-DRfepAbV.js +1 -0
  35. package/dist/assets/anthropic-DwpKRVGM.svg +1 -0
  36. package/dist/assets/asset-preview-jtcCFntF.js +4 -0
  37. package/dist/assets/blender-display-shaders-BpnqnkG8.lut +0 -0
  38. package/dist/assets/blender-emscripten-engine-DEk9HdR1.js +2 -0
  39. package/dist/assets/blender-motion-worker-CtT2cV3V.js +1 -0
  40. package/dist/assets/blender-node-editor.document-Bi2T12bG.js +1 -0
  41. package/dist/assets/blender-properties-model-Yj49RcLm.js +1 -0
  42. package/dist/assets/blender-properties-tab-Dtap7p2U.js +3 -0
  43. package/dist/assets/blender-runtime-host-CMI7ldx1.js +17 -0
  44. package/dist/assets/blender-runtime.document-D0NB4iPR.js +13 -0
  45. package/dist/assets/blender-screenshot.menu-D0-n31XK.js +1 -0
  46. package/dist/assets/blender-timeline.document-_1xorgQ6.js +1 -0
  47. package/dist/assets/blender-uv-editor.document-Dki4Ui-b.js +1 -0
  48. package/dist/assets/blender-version.status-DlBU0k-r.js +1 -0
  49. package/dist/assets/blender-wali-engine-D2ymLooc.js +2 -0
  50. package/dist/assets/blender.command-BcpIwWTF.js +1 -0
  51. package/dist/assets/blender.environment-CG-pC7sk.js +1 -0
  52. package/dist/assets/blender.keymap-BmOBRY7p.js +1 -0
  53. package/dist/assets/blender.status-B1L-FZyU.js +1 -0
  54. package/dist/assets/blender.style-DaIh9SiA.js +1 -0
  55. package/dist/assets/city-EkhAOo5s.exr +0 -0
  56. package/dist/assets/clip-planes-CmZu3QTO.js +8 -0
  57. package/dist/assets/content-bounds-Dg9hT5Gp.js +85 -0
  58. package/dist/assets/courtyard-DqlebbpC.exr +0 -0
  59. package/dist/assets/forest-P_CQY3b_.exr +0 -0
  60. package/dist/assets/icon-BkiLD9ed.png +0 -0
  61. package/dist/assets/index-7vd2obXq.js +3 -0
  62. package/dist/assets/index-BP6wv2A0.js +5 -0
  63. package/dist/assets/index-BRLA7zdc.js +7 -0
  64. package/dist/assets/index-BxW3iIJI.js +952 -0
  65. package/dist/assets/index-CnvSS9lU.js +2 -0
  66. package/dist/assets/index-DYNMP0kE.js +1 -0
  67. package/dist/assets/index-Dz8qGBZc.js +13 -0
  68. package/dist/assets/index-Fv4R0cYr.js +1 -0
  69. package/dist/assets/index-f-MQ14bP.js +1 -0
  70. package/dist/assets/index-ux8XhRyW.js +1 -0
  71. package/dist/assets/interior-Bo_lba15.exr +0 -0
  72. package/dist/assets/live-mixers-B-bwLZ7c.js +1 -0
  73. package/dist/assets/model-inspection-jRplyguX.js +1 -0
  74. package/dist/assets/model.layout-BpZE1W9V.js +1 -0
  75. package/dist/assets/models.finder-jvcjSDNd.js +1 -0
  76. package/dist/assets/night-CvV4Gybt.exr +0 -0
  77. package/dist/assets/object3d-document-session-registry-_NnPOZmk.js +2 -0
  78. package/dist/assets/openai-DHNKzFtc.svg +1 -0
  79. package/dist/assets/play-mode-DljPhCBr.js +7208 -0
  80. package/dist/assets/png-encode.worker-E8zk28Vl.js +1 -0
  81. package/dist/assets/product-BxXXdFxI.css +1 -0
  82. package/dist/assets/product-Dcs9ogdH.js +14 -0
  83. package/dist/assets/properties-bone-constraints.inspector-sNOrOqmn.js +1 -0
  84. package/dist/assets/properties-bone.inspector-DrRAhkXh.js +1 -0
  85. package/dist/assets/properties-collection.inspector-D2bNhLqd.js +1 -0
  86. package/dist/assets/properties-constraints.inspector-CGTEqVBY.js +1 -0
  87. package/dist/assets/properties-data.inspector-nwiHdy4s.js +1 -0
  88. package/dist/assets/properties-material.inspector-CPW_Te19.js +1 -0
  89. package/dist/assets/properties-modifiers.inspector-CsIgxGPe.js +1 -0
  90. package/dist/assets/properties-object.inspector-Cwx4QctT.js +1 -0
  91. package/dist/assets/properties-output.inspector-CgChOQat.js +1 -0
  92. package/dist/assets/properties-particles.inspector-B8j59UFB.js +1 -0
  93. package/dist/assets/properties-physics.inspector-ComSsHn6.js +1 -0
  94. package/dist/assets/properties-render.inspector-BTqY-F5-.js +1 -0
  95. package/dist/assets/properties-scene.inspector-C-R7eu1o.js +1 -0
  96. package/dist/assets/properties-texture.inspector-CFmTTdHS.js +1 -0
  97. package/dist/assets/properties-view-layer.inspector-BvMUCTd_.js +1 -0
  98. package/dist/assets/properties-world.inspector-Dpb6EWk8.js +1 -0
  99. package/dist/assets/react-18-BDYozTc0.js +1 -0
  100. package/dist/assets/regions-DWeEBnE2.js +1 -0
  101. package/dist/assets/sculpt.layout-D-K5cLw6.js +1 -0
  102. package/dist/assets/session-C0OdhDD8.js +5393 -0
  103. package/dist/assets/shading.layout-CZZHKBer.js +1 -0
  104. package/dist/assets/sky-precompute-worker-CPGW9t_C.js +1 -0
  105. package/dist/assets/spark.module-GpLuSFtI.js +12120 -0
  106. package/dist/assets/stage-keyboard-Cjy_uKPi.js +1 -0
  107. package/dist/assets/stage-overlay-set-BV78wZfK.js +1 -0
  108. package/dist/assets/stage-presence-markers-CJVuC1Vh.js +1 -0
  109. package/dist/assets/stage-transform-tools-B21BRk-L.js +1 -0
  110. package/dist/assets/standard-viewport-dressing-zXbS_1ew.js +24 -0
  111. package/dist/assets/studio-CysTBGIb.exr +0 -0
  112. package/dist/assets/sunrise-Dj0psFrf.exr +0 -0
  113. package/dist/assets/sunset-Bw3x2Bot.exr +0 -0
  114. package/dist/assets/texture.layout-DASpHVht.js +1 -0
  115. package/dist/assets/three-integration.service-Bfy6rPSh.js +2 -0
  116. package/dist/assets/three.module-dk_BdrjN.js +3840 -0
  117. package/dist/assets/uv-editing.layout-A8RA-cbM.js +1 -0
  118. package/dist/assets/volter-sdk-BwU3fa6G.js +2358 -0
  119. package/dist/assets/volter-sdk-account-BlUZdl9g.js +1 -0
  120. package/dist/assets/volter-sdk-client-C_pM7u8F.js +1 -0
  121. package/dist/assets/volter-sdk-contributions-CyyzzsHD.js +1 -0
  122. package/dist/assets/volter-sdk-css-numeric-style-B404pZI8.js +1 -0
  123. package/dist/assets/volter-sdk-document-probe-DAjYzNFt.js +1 -0
  124. package/dist/assets/volter-sdk-editor-view-suHsPgK2.js +1 -0
  125. package/dist/assets/volter-sdk-host-58UWGff-.js +1 -0
  126. package/dist/assets/volter-sdk-http-transport.browser-VJksIuNN.js +1 -0
  127. package/dist/assets/volter-sdk-index-DQpzb0WD.js +1 -0
  128. package/dist/assets/volter-sdk-kit-CapabilityCoverageSection-C41uHAFx.js +1 -0
  129. package/dist/assets/volter-sdk-kit-account-client-BnrRHdPV.js +1 -0
  130. package/dist/assets/volter-sdk-kit-action-registry-Co0Hbo6i.js +1 -0
  131. package/dist/assets/volter-sdk-kit-active-product-7gseHcVz.js +1 -0
  132. package/dist/assets/volter-sdk-kit-active-project-Bmrlj0XL.js +1 -0
  133. package/dist/assets/volter-sdk-kit-adapter-editor-config-DqGAdw2_.js +1 -0
  134. package/dist/assets/volter-sdk-kit-adapter-observation-Y-Cr3BiX.js +1 -0
  135. package/dist/assets/volter-sdk-kit-animation-animation-clock-BYmBGV0P.js +1 -0
  136. package/dist/assets/volter-sdk-kit-animation-stage-transport-CY7-VoVp.js +1 -0
  137. package/dist/assets/volter-sdk-kit-api-assets-CRsoN16p.js +1 -0
  138. package/dist/assets/volter-sdk-kit-api-base-Dw9L5xJS.js +1 -0
  139. package/dist/assets/volter-sdk-kit-api-build-BapF1Knc.js +1 -0
  140. package/dist/assets/volter-sdk-kit-api-logs-ClNHtQ6y.js +1 -0
  141. package/dist/assets/volter-sdk-kit-api-project-identity-CLam3F93.js +1 -0
  142. package/dist/assets/volter-sdk-kit-api-project-open-D9BK6gAR.js +1 -0
  143. package/dist/assets/volter-sdk-kit-api-project-source-B4ZDf1-O.js +1 -0
  144. package/dist/assets/volter-sdk-kit-api-project-state-Q0gbhHMy.js +1 -0
  145. package/dist/assets/volter-sdk-kit-api-relay-CEs5T2gc.js +1 -0
  146. package/dist/assets/volter-sdk-kit-api-settings-DQhJJaCN.js +1 -0
  147. package/dist/assets/volter-sdk-kit-api-themes-CK0mpUed.js +1 -0
  148. package/dist/assets/volter-sdk-kit-api-worktrees-CZAcA-yg.js +1 -0
  149. package/dist/assets/volter-sdk-kit-asset-capabilities-BH2tqp_X.js +1 -0
  150. package/dist/assets/volter-sdk-kit-asset-compare-core-CO4rbaNo.js +1 -0
  151. package/dist/assets/volter-sdk-kit-asset-editor-context-Crd2QR_x.js +1 -0
  152. package/dist/assets/volter-sdk-kit-asset-events-Cfuds14S.js +1 -0
  153. package/dist/assets/volter-sdk-kit-asset-inspector-actions-BOh3j-zP.js +1 -0
  154. package/dist/assets/volter-sdk-kit-asset-selection-UhfuT50E.js +1 -0
  155. package/dist/assets/volter-sdk-kit-asset-selection-viewer-registry-EWMtCoHo.js +1 -0
  156. package/dist/assets/volter-sdk-kit-asset-thumbnails-CzMUys7a.js +1 -0
  157. package/dist/assets/volter-sdk-kit-asset-viewers-Cf_KVYEv.js +1 -0
  158. package/dist/assets/volter-sdk-kit-asset-workflow-asset-import-jobs-CBNjRa8N.js +1 -0
  159. package/dist/assets/volter-sdk-kit-asset-workflow-asset-ledger-_i8-7mdV.js +1 -0
  160. package/dist/assets/volter-sdk-kit-asset-workflow-asset-ledger-backend-C20xqeUO.js +1 -0
  161. package/dist/assets/volter-sdk-kit-asset-workflow-asset-materialization-report-Dech0lQC.js +1 -0
  162. package/dist/assets/volter-sdk-kit-asset-workflow-asset-pack-manifest-pPS9qzPW.js +1 -0
  163. package/dist/assets/volter-sdk-kit-asset-workflow-audio-preview-player-0wPh24zI.js +1 -0
  164. package/dist/assets/volter-sdk-kit-asset-workflow-audio-waveform-BAY5AA4K.js +1 -0
  165. package/dist/assets/volter-sdk-kit-asset-workflow-cloud-asset-client-DRc8hWEO.js +1 -0
  166. package/dist/assets/volter-sdk-kit-asset-workflow-hosted-asset-materialization-BW7Al90A.js +1 -0
  167. package/dist/assets/volter-sdk-kit-asset-workflow-image-view-scale-DNIgToKY.js +1 -0
  168. package/dist/assets/volter-sdk-kit-asset-workflow-ledger-write-lock-DT7NxaAG.js +1 -0
  169. package/dist/assets/volter-sdk-kit-asset-workflow-pixi-spritesheet-F0tDOvEn.js +1 -0
  170. package/dist/assets/volter-sdk-kit-asset-workflow-preview-resource-lifetime-BvmHntAY.js +1 -0
  171. package/dist/assets/volter-sdk-kit-asset-workflow-project-asset-commands-Dar362Gf.js +1 -0
  172. package/dist/assets/volter-sdk-kit-asset-workflow-project-content-DAMV_NEZ.js +1 -0
  173. package/dist/assets/volter-sdk-kit-asset-workflow-thumbnail-system-D9b6o-CL.js +1 -0
  174. package/dist/assets/volter-sdk-kit-authoring-active-adapter-BZ9hzFLG.js +1 -0
  175. package/dist/assets/volter-sdk-kit-authoring-active-systems-Cpbjxaoi.js +1 -0
  176. package/dist/assets/volter-sdk-kit-authoring-adapter-key-CNJDTSi4.js +1 -0
  177. package/dist/assets/volter-sdk-kit-authoring-authoring-asset-url-BnteIxrT.js +1 -0
  178. package/dist/assets/volter-sdk-kit-authoring-bootstrap-state-DMaoNrQW.js +1 -0
  179. package/dist/assets/volter-sdk-kit-authoring-boundary-authoring-adapter-DBAwTDuf.js +1 -0
  180. package/dist/assets/volter-sdk-kit-authoring-canvas-scene-guides-DWrvby2w.js +1 -0
  181. package/dist/assets/volter-sdk-kit-authoring-composite-authoring-adapter-C4-Kp99J.js +1 -0
  182. package/dist/assets/volter-sdk-kit-authoring-consumer-actions-CBBDoLEX.js +1 -0
  183. package/dist/assets/volter-sdk-kit-authoring-design-time-layers-DuxPqGrN.js +1 -0
  184. package/dist/assets/volter-sdk-kit-authoring-design-time-mount-registry-Div61xFj.js +1 -0
  185. package/dist/assets/volter-sdk-kit-authoring-edit-mode-authoring-lp1HgOZY.js +1 -0
  186. package/dist/assets/volter-sdk-kit-authoring-empty-project-authoring-DESJUilA.js +1 -0
  187. package/dist/assets/volter-sdk-kit-authoring-instance-source-menu-Yw8ilOpP.js +1 -0
  188. package/dist/assets/volter-sdk-kit-authoring-layered-pick-CnFv-JJ4.js +1 -0
  189. package/dist/assets/volter-sdk-kit-authoring-mounted-root-subjects-BG3VV4R2.js +1 -0
  190. package/dist/assets/volter-sdk-kit-authoring-no-authoring-adapter-DdsbWdzA.js +1 -0
  191. package/dist/assets/volter-sdk-kit-authoring-object3d-document-persistence-Cz3dTWOm.js +1 -0
  192. package/dist/assets/volter-sdk-kit-authoring-panel-authoring-CVVMuMz7.js +1 -0
  193. package/dist/assets/volter-sdk-kit-authoring-project-authoring-session-Dr97ZYKO.js +1 -0
  194. package/dist/assets/volter-sdk-kit-authoring-provenance-B5PenuKN.js +1 -0
  195. package/dist/assets/volter-sdk-kit-authoring-react-canvas-navigation-C-FLncdT.js +1 -0
  196. package/dist/assets/volter-sdk-kit-authoring-react-design-canvas-style-mWGHuhfC.js +1 -0
  197. package/dist/assets/volter-sdk-kit-authoring-react-story-board-BJdVcnM0.js +1 -0
  198. package/dist/assets/volter-sdk-kit-authoring-seam-evidence-kaO6Kcw3.js +1 -0
  199. package/dist/assets/volter-sdk-kit-authoring-selection-scope-MaPGsoaC.js +1 -0
  200. package/dist/assets/volter-sdk-kit-authoring-shell-document-ops-fzF3ajnE.js +1 -0
  201. package/dist/assets/volter-sdk-kit-authoring-story-board-chrome-fit-BmaeUc2Q.js +1 -0
  202. package/dist/assets/volter-sdk-kit-authoring-three-root-_Iik8VOw.js +1 -0
  203. package/dist/assets/volter-sdk-kit-authoring-viewport-tool-context-BMaVuFyB.js +1 -0
  204. package/dist/assets/volter-sdk-kit-authoring-viewport-tool-owner-D7gzEf8Y.js +1 -0
  205. package/dist/assets/volter-sdk-kit-authoring-world-session-state-DHU1uP-A.js +1 -0
  206. package/dist/assets/volter-sdk-kit-availability-tick-mnrfOjCO.js +1 -0
  207. package/dist/assets/volter-sdk-kit-bitmap-label-tfpyi7Ai.js +1 -0
  208. package/dist/assets/volter-sdk-kit-boot-routing-BHPc5GLo.js +1 -0
  209. package/dist/assets/volter-sdk-kit-breakpoint-state-Db1oqXJX.js +1 -0
  210. package/dist/assets/volter-sdk-kit-build-identity-BTQ1Xdpa.js +1 -0
  211. package/dist/assets/volter-sdk-kit-bytes-codec-DvWCmxma.js +1 -0
  212. package/dist/assets/volter-sdk-kit-cancellation-reason-BEjzQjCf.js +1 -0
  213. package/dist/assets/volter-sdk-kit-canvas-frames-BJEuXRrc.js +1 -0
  214. package/dist/assets/volter-sdk-kit-capture-camera-pose-YJBoQ23O.js +1 -0
  215. package/dist/assets/volter-sdk-kit-capture-size-EmnVLs8n.js +1 -0
  216. package/dist/assets/volter-sdk-kit-chrome-registry-Cs0k1OX1.js +1 -0
  217. package/dist/assets/volter-sdk-kit-chrome-slot-registry-BwDDbLjQ.js +1 -0
  218. package/dist/assets/volter-sdk-kit-collaboration-client-C2jtyYW3.js +1 -0
  219. package/dist/assets/volter-sdk-kit-collaboration-presence-D3UftauX.js +1 -0
  220. package/dist/assets/volter-sdk-kit-command-dispatch-BZWUjbx5.js +1 -0
  221. package/dist/assets/volter-sdk-kit-command-listener-CfFEgEYh.js +1 -0
  222. package/dist/assets/volter-sdk-kit-command-registry-CxqLDZ_t.js +1 -0
  223. package/dist/assets/volter-sdk-kit-component-board-registry-wPpm4hz2.js +1 -0
  224. package/dist/assets/volter-sdk-kit-component-states-registry-DUnoMxYg.js +1 -0
  225. package/dist/assets/volter-sdk-kit-components-AlignToolbar-kgkYRPYY.js +1 -0
  226. package/dist/assets/volter-sdk-kit-components-ApplicationMenus-DSUoF1z8.js +1 -0
  227. package/dist/assets/volter-sdk-kit-components-AssetEditorShell-BsmfaAE9.js +1 -0
  228. package/dist/assets/volter-sdk-kit-components-AssetInspectorToolSection-GxYRyjBh.js +1 -0
  229. package/dist/assets/volter-sdk-kit-components-BoardRulers-XXJ7RCz4.js +1 -0
  230. package/dist/assets/volter-sdk-kit-components-CanvasAddNodeDialogs-DSg-5iRY.js +1 -0
  231. package/dist/assets/volter-sdk-kit-components-CanvasSceneViewport-C8suTPNd.js +1 -0
  232. package/dist/assets/volter-sdk-kit-components-ChromeSlot-kgnOcXb4.js +1 -0
  233. package/dist/assets/volter-sdk-kit-components-CodeView-8_n22zvN.js +1 -0
  234. package/dist/assets/volter-sdk-kit-components-CompactInspectorShell-DkR_oNfI.js +1 -0
  235. package/dist/assets/volter-sdk-kit-components-ConsolePanel-DiI4aQRP.js +1 -0
  236. package/dist/assets/volter-sdk-kit-components-GameplaySessionTimeline-BwzyAzUn.js +1 -0
  237. package/dist/assets/volter-sdk-kit-components-InspectionProjection-Cz94_Rt7.js +1 -0
  238. package/dist/assets/volter-sdk-kit-components-Inspector-BPFGLp3d.js +1 -0
  239. package/dist/assets/volter-sdk-kit-components-InspectorCanvasPreview-CA1NTcqw.js +1 -0
  240. package/dist/assets/volter-sdk-kit-components-InspectorFieldsSection-BuwRGDJ0.js +1 -0
  241. package/dist/assets/volter-sdk-kit-components-InspectorStoriesSection-BsVaquIj.js +1 -0
  242. package/dist/assets/volter-sdk-kit-components-InspectorToolSection-Di0bMd01.js +1 -0
  243. package/dist/assets/volter-sdk-kit-components-InspectorTransformSection-_E4Y2mdm.js +1 -0
  244. package/dist/assets/volter-sdk-kit-components-LightExplorerPanel-4D34umvc.js +1 -0
  245. package/dist/assets/volter-sdk-kit-components-MediaProperties-BtpXA40W.js +1 -0
  246. package/dist/assets/volter-sdk-kit-components-ProjectHeader-COVqavbg.js +1 -0
  247. package/dist/assets/volter-sdk-kit-components-ReactCanvasControls-lvb140oy.js +1 -0
  248. package/dist/assets/volter-sdk-kit-components-RootSelectionOverlay-BWDtha0N.js +1 -0
  249. package/dist/assets/volter-sdk-kit-components-RootTextEditor-E99FydcX.js +1 -0
  250. package/dist/assets/volter-sdk-kit-components-SaveStatus-DolfRGCT.js +1 -0
  251. package/dist/assets/volter-sdk-kit-components-SurfaceStateOverlay-BHtKccFF.js +1 -0
  252. package/dist/assets/volter-sdk-kit-components-ToolContributionSurfaces-D02jF-QD.js +1 -0
  253. package/dist/assets/volter-sdk-kit-components-ToolHost-xY2N5GR3.js +1 -0
  254. package/dist/assets/volter-sdk-kit-components-Toolbar-XTw72bRl.js +1 -0
  255. package/dist/assets/volter-sdk-kit-components-TransientHint-LyCJ6M5h.js +1 -0
  256. package/dist/assets/volter-sdk-kit-components-VersionControlSection-CaUBgU7Q.js +1 -0
  257. package/dist/assets/volter-sdk-kit-components-ViewportOverlaysMenu-DJm0Vtra.js +1 -0
  258. package/dist/assets/volter-sdk-kit-components-VolterLogo-7QJN2Aue.js +1 -0
  259. package/dist/assets/volter-sdk-kit-components-WorktreeSwitcher-Cm6EQlo9.js +1 -0
  260. package/dist/assets/volter-sdk-kit-components-account-documents-C1w8-N3m.js +1 -0
  261. package/dist/assets/volter-sdk-kit-components-asset-documents-o5P9hniy.js +1 -0
  262. package/dist/assets/volter-sdk-kit-components-asset-editor-persistence-DLsU0r1E.js +1 -0
  263. package/dist/assets/volter-sdk-kit-components-asset-selection-section-BYEwJfLy.js +1 -0
  264. package/dist/assets/volter-sdk-kit-components-asset-thumbnails-C-LgDd2_.js +1 -0
  265. package/dist/assets/volter-sdk-kit-components-asset-viewers-AudioViewer-BR48_QX5.js +1 -0
  266. package/dist/assets/volter-sdk-kit-components-asset-viewers-GenericJsonViewer-C9IP9LWM.js +1 -0
  267. package/dist/assets/volter-sdk-kit-components-asset-viewers-ImageViewer-Dffdgv60.js +1 -0
  268. package/dist/assets/volter-sdk-kit-components-asset-viewers-JsonAssetDocument-ChmgYQAP.js +1 -0
  269. package/dist/assets/volter-sdk-kit-components-asset-viewers-OnlineAssetDetail-Bdpm--Jx.js +1 -0
  270. package/dist/assets/volter-sdk-kit-components-asset-viewers-SourceAssetViewer-DdJX9xCd.js +1 -0
  271. package/dist/assets/volter-sdk-kit-components-asset-viewers-SpritesheetSpriteView-DYXAuujE.js +1 -0
  272. package/dist/assets/volter-sdk-kit-components-asset-viewers-VideoViewer-6xqrjETd.js +1 -0
  273. package/dist/assets/volter-sdk-kit-components-asset-viewers-shader-source-cHZlxpZt.js +1 -0
  274. package/dist/assets/volter-sdk-kit-components-board-guides-7WFdaGRg.js +1 -0
  275. package/dist/assets/volter-sdk-kit-components-canvas-scene-hotkeys-CnxAX0SN.js +1 -0
  276. package/dist/assets/volter-sdk-kit-components-canvas-temporary-pivot-CtpM87Bn.js +1 -0
  277. package/dist/assets/volter-sdk-kit-components-core-utilities-CHVzLxwg.js +1 -0
  278. package/dist/assets/volter-sdk-kit-components-inspector-preview-section-B8TaQyFK.js +1 -0
  279. package/dist/assets/volter-sdk-kit-components-inspector-revert-label-BNzoXVNS.js +1 -0
  280. package/dist/assets/volter-sdk-kit-components-inspector-selection-BpPShgrU.js +1 -0
  281. package/dist/assets/volter-sdk-kit-components-inspector-stories-gating-DiH66VA6.js +1 -0
  282. package/dist/assets/volter-sdk-kit-components-inspector-transform-CmjteW7M.js +1 -0
  283. package/dist/assets/volter-sdk-kit-components-inspector-transform-subject-DrIk_jIn.js +1 -0
  284. package/dist/assets/volter-sdk-kit-components-kind-documents-BK3KZxJA.js +1 -0
  285. package/dist/assets/volter-sdk-kit-components-primitives-DraftColorInput-1nPD0Wmj.js +1 -0
  286. package/dist/assets/volter-sdk-kit-components-project-tool-documents-DJ4Ucdcc.js +1 -0
  287. package/dist/assets/volter-sdk-kit-components-scene-documents-D0S3Ip8u.js +1 -0
  288. package/dist/assets/volter-sdk-kit-components-status-contributions-CnD50KDE.js +1 -0
  289. package/dist/assets/volter-sdk-kit-components-tool-documents-CFPlSwI0.js +1 -0
  290. package/dist/assets/volter-sdk-kit-components-tool-schema-form-DDm00y0g.js +1 -0
  291. package/dist/assets/volter-sdk-kit-components-use-after-paint-DvCjTL4J.js +1 -0
  292. package/dist/assets/volter-sdk-kit-components-use-project-image-assets-C2yOGb4T.js +1 -0
  293. package/dist/assets/volter-sdk-kit-components-workspace-history-cK1qO4Ko.js +1 -0
  294. package/dist/assets/volter-sdk-kit-components-world-documents-Ca0Kvd6F.js +1 -0
  295. package/dist/assets/volter-sdk-kit-components-world-overlay-gestures-D9tS4EXa.js +1 -0
  296. package/dist/assets/volter-sdk-kit-composite-screenshot-DrxN3o4m.js +1 -0
  297. package/dist/assets/volter-sdk-kit-content-entry-source-registry-WrKmcDj4.js +1 -0
  298. package/dist/assets/volter-sdk-kit-contribution-surfaces-DkZ0OqGh.js +1 -0
  299. package/dist/assets/volter-sdk-kit-coverage-canvas-reveal-C8pETRas.js +1 -0
  300. package/dist/assets/volter-sdk-kit-coverage-design-time-surfaces-BEEt0Akm.js +1 -0
  301. package/dist/assets/volter-sdk-kit-coverage-ontology-invariants-Bxd6b-Me.js +1 -0
  302. package/dist/assets/volter-sdk-kit-coverage-session-vitals-C_KOh0vV.js +1 -0
  303. package/dist/assets/volter-sdk-kit-creation-site-registry-xToT1mgQ.js +1 -0
  304. package/dist/assets/volter-sdk-kit-delegate-harness-registry-BQ2Z3x4u.js +1 -0
  305. package/dist/assets/volter-sdk-kit-document-areas-BoFteXyg.js +1 -0
  306. package/dist/assets/volter-sdk-kit-document-context-registry-DCltdAwX.js +1 -0
  307. package/dist/assets/volter-sdk-kit-document-open-registry-nUKbpgXi.js +1 -0
  308. package/dist/assets/volter-sdk-kit-document-play-extension-LhA9YSwP.js +1 -0
  309. package/dist/assets/volter-sdk-kit-document-preview-source-BjKu56A5.js +1 -0
  310. package/dist/assets/volter-sdk-kit-document-renderer-session-CmO67Fns.js +1 -0
  311. package/dist/assets/volter-sdk-kit-document-stage-sessions-DhjElggV.js +1 -0
  312. package/dist/assets/volter-sdk-kit-document-viewports-JkYxkBPk.js +1 -0
  313. package/dist/assets/volter-sdk-kit-editor-api-CkTONSnh.js +1 -0
  314. package/dist/assets/volter-sdk-kit-editor-chrome-capture-Ryy6MFML.js +1 -0
  315. package/dist/assets/volter-sdk-kit-editor-commands-A6xFbhNt.js +1 -0
  316. package/dist/assets/volter-sdk-kit-editor-console-CfXqiRHJ.js +1 -0
  317. package/dist/assets/volter-sdk-kit-editor-current-view-Blu4WXH4.js +1 -0
  318. package/dist/assets/volter-sdk-kit-editor-document-probe-DLQ4_TGz.js +1 -0
  319. package/dist/assets/volter-sdk-kit-editor-git-client-79qLddTa.js +1 -0
  320. package/dist/assets/volter-sdk-kit-editor-hotkeys-Bf8x8pPR.js +1 -0
  321. package/dist/assets/volter-sdk-kit-editor-lease-DnDA6DTK.js +1 -0
  322. package/dist/assets/volter-sdk-kit-editor-lease-view-DnYNNuac.js +1 -0
  323. package/dist/assets/volter-sdk-kit-editor-mode-TyppF_mm.js +1 -0
  324. package/dist/assets/volter-sdk-kit-editor-notifications-DbJyIY8R.js +1 -0
  325. package/dist/assets/volter-sdk-kit-editor-presence-CDht_mUS.js +1 -0
  326. package/dist/assets/volter-sdk-kit-editor-presentation-activity-BAw4OBGu.js +1 -0
  327. package/dist/assets/volter-sdk-kit-editor-presentation-notice-vPwlLZpU.js +1 -0
  328. package/dist/assets/volter-sdk-kit-editor-runtime-BM50QyRE.js +1 -0
  329. package/dist/assets/volter-sdk-kit-editor-server-response-BMR_IEYq.js +1 -0
  330. package/dist/assets/volter-sdk-kit-editor-session-attribution-GlzM29Xi.js +1 -0
  331. package/dist/assets/volter-sdk-kit-editor-session-mode-zTS3Hh7x.js +1 -0
  332. package/dist/assets/volter-sdk-kit-editor-state-facets-iq5aCQYy.js +1 -0
  333. package/dist/assets/volter-sdk-kit-editor-view-presentation-D-Zr2xsr.js +1 -0
  334. package/dist/assets/volter-sdk-kit-environment-images-BBbuCQN0.js +1 -0
  335. package/dist/assets/volter-sdk-kit-eyedropper-session-CVQTFAKM.js +1 -0
  336. package/dist/assets/volter-sdk-kit-files-file-provider-DnQAC1u2.js +1 -0
  337. package/dist/assets/volter-sdk-kit-files-project-files-CwASwqrX.js +1 -0
  338. package/dist/assets/volter-sdk-kit-finders-index-CclbaymG.js +1 -0
  339. package/dist/assets/volter-sdk-kit-finders-scenes-from-entrypoint-selection-B17U2yvo.js +1 -0
  340. package/dist/assets/volter-sdk-kit-frame-frame-parts-VVzfs78H.js +1 -0
  341. package/dist/assets/volter-sdk-kit-framed-document-capture-Cha1yjuL.js +1 -0
  342. package/dist/assets/volter-sdk-kit-game-surface-defaults-CsAR7C_G.js +1 -0
  343. package/dist/assets/volter-sdk-kit-gameplay-export-state-D2gCoh9n.js +1 -0
  344. package/dist/assets/volter-sdk-kit-gameplay-replay-DkkfYYwX.js +1 -0
  345. package/dist/assets/volter-sdk-kit-gameplay-session-time-Dht9eZ_4.js +1 -0
  346. package/dist/assets/volter-sdk-kit-gameplay-sessions-CCOOL4Eg.js +1 -0
  347. package/dist/assets/volter-sdk-kit-hierarchy-component-marks-CTw2KFgo.js +1 -0
  348. package/dist/assets/volter-sdk-kit-hierarchy-internals-D8gRo1WQ.js +1 -0
  349. package/dist/assets/volter-sdk-kit-hierarchy-kind-icon-D0OctdvL.js +1 -0
  350. package/dist/assets/volter-sdk-kit-hierarchy-menu-registry-DwA4Z2A9.js +1 -0
  351. package/dist/assets/volter-sdk-kit-hierarchy-node-rows-BGNi2kxs.js +1 -0
  352. package/dist/assets/volter-sdk-kit-hierarchy-panel-view-Bb1EP0Bk.js +1 -0
  353. package/dist/assets/volter-sdk-kit-hierarchy-projection-BtCzTzOY.js +1 -0
  354. package/dist/assets/volter-sdk-kit-hierarchy-row-media-CnHgcQM8.js +1 -0
  355. package/dist/assets/volter-sdk-kit-hierarchy-row-model-l7Qbe9Dk.js +1 -0
  356. package/dist/assets/volter-sdk-kit-hierarchy-rows-C20aO3up.js +1 -0
  357. package/dist/assets/volter-sdk-kit-hierarchy-walk-CE_FQf5c.js +1 -0
  358. package/dist/assets/volter-sdk-kit-history-editor-session-CS5IwxZx.js +1 -0
  359. package/dist/assets/volter-sdk-kit-history-history-commands-VU0Tf0lj.js +1 -0
  360. package/dist/assets/volter-sdk-kit-history-history-delegate-ZQwI-0MR.js +1 -0
  361. package/dist/assets/volter-sdk-kit-history-history-limit-notices-BrhHiRSY.js +1 -0
  362. package/dist/assets/volter-sdk-kit-history-history-service-BZ4AidfS.js +1 -0
  363. package/dist/assets/volter-sdk-kit-history-persistence-coordinator-Bpi3os_u.js +1 -0
  364. package/dist/assets/volter-sdk-kit-history-project-file-history-hDI70zmi.js +1 -0
  365. package/dist/assets/volter-sdk-kit-history-project-root-history-backends-BAfTGdrX.js +1 -0
  366. package/dist/assets/volter-sdk-kit-history-resource-registry-CGjyTLt-.js +1 -0
  367. package/dist/assets/volter-sdk-kit-history-snapshot-store-BgZ7Byks.js +1 -0
  368. package/dist/assets/volter-sdk-kit-history-source-history-backend-B25Z4lQz.js +1 -0
  369. package/dist/assets/volter-sdk-kit-hmr-registration-group-CiEUgAw2.js +1 -0
  370. package/dist/assets/volter-sdk-kit-hmr-stable-react-context-AymxVJvR.js +1 -0
  371. package/dist/assets/volter-sdk-kit-hotkeys-DlADec38.js +1 -0
  372. package/dist/assets/volter-sdk-kit-inference-diagnostics-GA9FnyOh.js +1 -0
  373. package/dist/assets/volter-sdk-kit-initial-project-zsKWa81T.js +1 -0
  374. package/dist/assets/volter-sdk-kit-inspection-active-subject-qZ5hTw90.js +1 -0
  375. package/dist/assets/volter-sdk-kit-inspection-active-surface-PhQ5uNsI.js +1 -0
  376. package/dist/assets/volter-sdk-kit-inspection-compose-subject-BgSCqJ-r.js +1 -0
  377. package/dist/assets/volter-sdk-kit-inspection-display-D8Nr6_ES.js +1 -0
  378. package/dist/assets/volter-sdk-kit-inspection-document-subject-DGznaZh-.js +1 -0
  379. package/dist/assets/volter-sdk-kit-inspection-game-subject-N0AxqX7G.js +1 -0
  380. package/dist/assets/volter-sdk-kit-inspection-model-hQetv0U9.js +1 -0
  381. package/dist/assets/volter-sdk-kit-inspection-node-media-fGRDtgJj.js +1 -0
  382. package/dist/assets/volter-sdk-kit-inspection-null-subject-ClNE9x2e.js +1 -0
  383. package/dist/assets/volter-sdk-kit-inspection-serialize-CpExrPTA.js +1 -0
  384. package/dist/assets/volter-sdk-kit-inspection-use-active-inspection-CRPvV320.js +1 -0
  385. package/dist/assets/volter-sdk-kit-inspector-presentation-BFfpxT4_.js +1 -0
  386. package/dist/assets/volter-sdk-kit-inspector-property-grouping-o7vgYhKg.js +1 -0
  387. package/dist/assets/volter-sdk-kit-inspector-section-registry-R5_0mSBl.js +1 -0
  388. package/dist/assets/volter-sdk-kit-instance-source-actions-B0lePqHO.js +1 -0
  389. package/dist/assets/volter-sdk-kit-js-heap-BpRVEyaI.js +1 -0
  390. package/dist/assets/volter-sdk-kit-key-actions-BEL1ou9N.js +1 -0
  391. package/dist/assets/volter-sdk-kit-keymap-presets-Qdpmq1MJ.js +1 -0
  392. package/dist/assets/volter-sdk-kit-layout-policy-CoLfPtzo.js +1 -0
  393. package/dist/assets/volter-sdk-kit-light-explorer-model-lqJF5X7X.js +1 -0
  394. package/dist/assets/volter-sdk-kit-live-canvas-frame-DdlhSZOw.js +1 -0
  395. package/dist/assets/volter-sdk-kit-live-document-MPCQkIxv.js +1 -0
  396. package/dist/assets/volter-sdk-kit-live-gesture-lock-BGiQikS-.js +1 -0
  397. package/dist/assets/volter-sdk-kit-live-seam-evidence-HsOKXOM-.js +1 -0
  398. package/dist/assets/volter-sdk-kit-live-session-registry-DPshp-zS.js +1 -0
  399. package/dist/assets/volter-sdk-kit-live-transition-SzISwcSc.js +1 -0
  400. package/dist/assets/volter-sdk-kit-manifest-project-BaQmD3cM.js +1 -0
  401. package/dist/assets/volter-sdk-kit-module-fetch-diagnosis-DVmHXvNS.js +1 -0
  402. package/dist/assets/volter-sdk-kit-mount-failure-report-Dk4LNPuk.js +1 -0
  403. package/dist/assets/volter-sdk-kit-native-selection-style-Bz3kzLsL.js +1 -0
  404. package/dist/assets/volter-sdk-kit-object3d-document-write-policy-yZfQc3Ch.js +1 -0
  405. package/dist/assets/volter-sdk-kit-packaged-runtime-Bofk4pL5.js +1 -0
  406. package/dist/assets/volter-sdk-kit-performance-profiler-BCQbvJC2.js +1 -0
  407. package/dist/assets/volter-sdk-kit-performance-sources-DmFnsOyy.js +1 -0
  408. package/dist/assets/volter-sdk-kit-photograph-notice-Ba8RTcKf.js +1 -0
  409. package/dist/assets/volter-sdk-kit-play-boot-phase-BtZNGfEm.js +1 -0
  410. package/dist/assets/volter-sdk-kit-play-camera-flight-DyDq7TW9.js +1 -0
  411. package/dist/assets/volter-sdk-kit-presentation-surface-CcUgETps.js +1 -0
  412. package/dist/assets/volter-sdk-kit-product-command-CTGtMf--.js +1 -0
  413. package/dist/assets/volter-sdk-kit-project-adapter-CncSm07i.js +1 -0
  414. package/dist/assets/volter-sdk-kit-project-asset-refresh-ff5GvzjI.js +1 -0
  415. package/dist/assets/volter-sdk-kit-project-asset-roots-2I55e0Tl.js +1 -0
  416. package/dist/assets/volter-sdk-kit-project-local-state-CoOxczZf.js +1 -0
  417. package/dist/assets/volter-sdk-kit-project-manager-CXwXszeS.js +1 -0
  418. package/dist/assets/volter-sdk-kit-project-module-changes-Df7bwGJA.js +1 -0
  419. package/dist/assets/volter-sdk-kit-project-module-split-CoOXmcMq.js +1 -0
  420. package/dist/assets/volter-sdk-kit-project-provenance-CsWz3dFr.js +1 -0
  421. package/dist/assets/volter-sdk-kit-project-ready-CEngokqw.js +1 -0
  422. package/dist/assets/volter-sdk-kit-project-shape-Bnk7IlEF.js +1 -0
  423. package/dist/assets/volter-sdk-kit-project-tools-CIrlsLd2.js +1 -0
  424. package/dist/assets/volter-sdk-kit-readiness-8iK1xUw-.js +1 -0
  425. package/dist/assets/volter-sdk-kit-renderer-resource-counts-BRlynwAB.js +1 -0
  426. package/dist/assets/volter-sdk-kit-reported-play-state-CdpNf7iS.js +1 -0
  427. package/dist/assets/volter-sdk-kit-resolve-contributed-command-CAPTMDEe.js +1 -0
  428. package/dist/assets/volter-sdk-kit-resolve-relative-specifier-CQavCIRh.js +1 -0
  429. package/dist/assets/volter-sdk-kit-retained-document-states-CkXz8CLe.js +1 -0
  430. package/dist/assets/volter-sdk-kit-scene-document-plan-C29w0uq_.js +1 -0
  431. package/dist/assets/volter-sdk-kit-scene-live-open-fodeYzCv.js +1 -0
  432. package/dist/assets/volter-sdk-kit-scoped-game-css-C2WRruBw.js +1 -0
  433. package/dist/assets/volter-sdk-kit-served-url-C17qOcC3.js +1 -0
  434. package/dist/assets/volter-sdk-kit-session-close-BKSX8DPi.js +1 -0
  435. package/dist/assets/volter-sdk-kit-session-tombstone-CQ1abA0T.js +1 -0
  436. package/dist/assets/volter-sdk-kit-settings-settings-provider-Drp8Ja5S.js +1 -0
  437. package/dist/assets/volter-sdk-kit-settings-store-DVv602rH.js +1 -0
  438. package/dist/assets/volter-sdk-kit-shell-store-Dwkc4LeK.js +1 -0
  439. package/dist/assets/volter-sdk-kit-shell-store-door-D6VAgShZ.js +1 -0
  440. package/dist/assets/volter-sdk-kit-source-conflict-BsgmQDuR.js +1 -0
  441. package/dist/assets/volter-sdk-kit-stage-context-CF3ATuJX.js +1 -0
  442. package/dist/assets/volter-sdk-kit-stage-invalidation-D1EKNjPS.js +1 -0
  443. package/dist/assets/volter-sdk-kit-stage-store-registry-DMqC8KJA.js +1 -0
  444. package/dist/assets/volter-sdk-kit-startup-failure-CJjXtSxT.js +1 -0
  445. package/dist/assets/volter-sdk-kit-state-report-deferral-BZ1Gll2x.js +1 -0
  446. package/dist/assets/volter-sdk-kit-storage-host-files-storage-BeBBCrF4.js +1 -0
  447. package/dist/assets/volter-sdk-kit-storage-http-storage-DMwE4aCU.js +1 -0
  448. package/dist/assets/volter-sdk-kit-storage-index-85BJsCgw.js +1 -0
  449. package/dist/assets/volter-sdk-kit-storage-mem-storage-Cp5EThww.js +1 -0
  450. package/dist/assets/volter-sdk-kit-storage-path-lock-BEHmTQkG.js +1 -0
  451. package/dist/assets/volter-sdk-kit-storage-paths-GkBBUtDn.js +1 -0
  452. package/dist/assets/volter-sdk-kit-stories-StoryPreviewMount-D07t88Iu.js +1 -0
  453. package/dist/assets/volter-sdk-kit-stories-compose-project-stories-BAw1haKj.js +1 -0
  454. package/dist/assets/volter-sdk-kit-stories-prefabs-finder-EMDMwLXg.js +1 -0
  455. package/dist/assets/volter-sdk-kit-stories-prefabs-from-stories-CEQekPVJ.js +1 -0
  456. package/dist/assets/volter-sdk-kit-stories-project-story-regions-m9-rTkrt.js +1 -0
  457. package/dist/assets/volter-sdk-kit-stories-scope-PLybjgWr.js +1 -0
  458. package/dist/assets/volter-sdk-kit-stories-story-capture-B3uLpufo.js +1 -0
  459. package/dist/assets/volter-sdk-kit-stories-story-declared-medium-D92bJmIo.js +1 -0
  460. package/dist/assets/volter-sdk-kit-stories-story-discovery-DtaxRT_i.js +1 -0
  461. package/dist/assets/volter-sdk-kit-stories-story-dom-runtime-BjR7PW3K.js +1 -0
  462. package/dist/assets/volter-sdk-kit-stories-story-grouping-BibwARwc.js +1 -0
  463. package/dist/assets/volter-sdk-kit-stories-story-presentation-DaweRLV-.js +1 -0
  464. package/dist/assets/volter-sdk-kit-stories-story-registry-BuTw7T27.js +1 -0
  465. package/dist/assets/volter-sdk-kit-story-document-openers-COzuCirA.js +1 -0
  466. package/dist/assets/volter-sdk-kit-story-thumbnails-DsLqdnDq.js +1 -0
  467. package/dist/assets/volter-sdk-kit-surface-keyboard-RiClmb_a.js +1 -0
  468. package/dist/assets/volter-sdk-kit-surface-state-DjeLKyCd.js +1 -0
  469. package/dist/assets/volter-sdk-kit-system-seam-evidence-omzWuzNM.js +1 -0
  470. package/dist/assets/volter-sdk-kit-tab-census-C8mQ0l9z.js +1 -0
  471. package/dist/assets/volter-sdk-kit-tab-lifecycle-client-28DSypwI.js +1 -0
  472. package/dist/assets/volter-sdk-kit-theme-library-DCToyXQ0.js +1 -0
  473. package/dist/assets/volter-sdk-kit-theme-preference-Dc-_5b1n.js +1 -0
  474. package/dist/assets/volter-sdk-kit-three-viewport-presentation-1LxA9rSc.js +1 -0
  475. package/dist/assets/volter-sdk-kit-tool-contribution-play--JvesPkN.js +1 -0
  476. package/dist/assets/volter-sdk-kit-tool-loader-LTQw0aL4.js +1 -0
  477. package/dist/assets/volter-sdk-kit-transform-mode-request-BY9JxShG.js +1 -0
  478. package/dist/assets/volter-sdk-kit-transient-hint-CM0bpYj2.js +1 -0
  479. package/dist/assets/volter-sdk-kit-transport-strip-5bUygAkv.js +1 -0
  480. package/dist/assets/volter-sdk-kit-ui-source-file-region-resolver-CQMWmqhP.js +1 -0
  481. package/dist/assets/volter-sdk-kit-ui-source-inspect-CfayTFdC.js +1 -0
  482. package/dist/assets/volter-sdk-kit-ui-source-source-write-backend-DzQseyn4.js +1 -0
  483. package/dist/assets/volter-sdk-kit-ui-source-tier-source-write-backend-3NgYZbUE.js +1 -0
  484. package/dist/assets/volter-sdk-kit-user-local-state-BZf1C-cO.js +1 -0
  485. package/dist/assets/volter-sdk-kit-viewport-activation-timings-C-7ETz2q.js +1 -0
  486. package/dist/assets/volter-sdk-kit-viewport-editor-controls-f4cwlOWa.js +1 -0
  487. package/dist/assets/volter-sdk-kit-viewport-presentation-Il1TLCMT.js +1 -0
  488. package/dist/assets/volter-sdk-kit-viewport-surface-status-CXyJJGil.js +1 -0
  489. package/dist/assets/volter-sdk-kit-wait-until-D3i87ehY.js +1 -0
  490. package/dist/assets/volter-sdk-kit-worker-call-metrics-DAK8SW-7.js +1 -0
  491. package/dist/assets/volter-sdk-kit-workspace-areas-DxhakPE3.js +1 -0
  492. package/dist/assets/volter-sdk-kit-workspace-aux-commands-j3FyV7Rh.js +1 -0
  493. package/dist/assets/volter-sdk-kit-workspace-available-documents-DS5ZkDU4.js +1 -0
  494. package/dist/assets/volter-sdk-kit-workspace-core-utilities-BbuDHrHq.js +1 -0
  495. package/dist/assets/volter-sdk-kit-workspace-document-ids-Bm3qMqdx.js +1 -0
  496. package/dist/assets/volter-sdk-kit-workspace-document-registry-CfkdJLBO.js +1 -0
  497. package/dist/assets/volter-sdk-kit-workspace-document-restore-BqBMoUhE.js +1 -0
  498. package/dist/assets/volter-sdk-kit-workspace-host-commands-BC-mYI2s.js +1 -0
  499. package/dist/assets/volter-sdk-kit-workspace-persistence-gate-CN-Z9G7V.js +1 -0
  500. package/dist/assets/volter-sdk-kit-workspace-play-utilities-C5iNgpyt.js +1 -0
  501. package/dist/assets/volter-sdk-kit-workspace-presets-B6MKS0jx.js +1 -0
  502. package/dist/assets/volter-sdk-kit-workspace-regions-DZevxGmg.js +1 -0
  503. package/dist/assets/volter-sdk-kit-workspace-static-panels-CUVjETSY.js +1 -0
  504. package/dist/assets/volter-sdk-kit-workspace-status-registry-Cim_nGuV.js +1 -0
  505. package/dist/assets/volter-sdk-kit-workspace-storage-B9Vf07gg.js +1 -0
  506. package/dist/assets/volter-sdk-kit-workspace-style-yCExFcBd.js +1 -0
  507. package/dist/assets/volter-sdk-kit-workspace-utility-commands-C3a_TCq8.js +1 -0
  508. package/dist/assets/volter-sdk-kit-workspace-utility-registry-CmYswBtf.js +1 -0
  509. package/dist/assets/volter-sdk-kit-world-adoption-1Q7uBdLI.js +1 -0
  510. package/dist/assets/volter-sdk-kit-world-canvas-viewport-state-DaZzYmQU.js +1 -0
  511. package/dist/assets/volter-sdk-kit-world-document-routing-d9K0XNhN.js +1 -0
  512. package/dist/assets/volter-sdk-kit-world-pan-state-Bui5iuls.js +1 -0
  513. package/dist/assets/volter-sdk-kit-write-pipe-BMOSwffA.js +1 -0
  514. package/dist/assets/volter-sdk-layout-arrangements-DMEnPpvu.js +1 -0
  515. package/dist/assets/volter-sdk-layouts-DKIqaCd4.js +1 -0
  516. package/dist/assets/volter-sdk-selection-DM8JuNxQ.js +1 -0
  517. package/dist/assets/volter-sdk-session-command-table-G119qBvl.js +1 -0
  518. package/dist/assets/volter-sdk-session-editor-brand-DCHKPDxT.js +1 -0
  519. package/dist/assets/volter-sdk-session-editor-compatibility-B165I_B1.js +1 -0
  520. package/dist/assets/volter-sdk-session-editor-control-protocol-DwV-576_.js +1 -0
  521. package/dist/assets/volter-sdk-session-entrypoint-selection-readers-D88QrS-p.js +1 -0
  522. package/dist/assets/volter-sdk-session-game-css-scope-UkCRVi6L.js +1 -0
  523. package/dist/assets/volter-sdk-session-project-module-url-B49W1ltn.js +1 -0
  524. package/dist/assets/volter-sdk-session-relative-path-guard-Bk6lCH4Z.js +1 -0
  525. package/dist/assets/volter-sdk-session-tool-contribution-convention-QXzdw52f.js +1 -0
  526. package/dist/assets/volter-sdk-types-yKC1STwH.js +1 -0
  527. package/dist/assets/volter-sdk-views-CLPSu14j.js +1 -0
  528. package/dist/assets/volter-sdk-widgets-design-system-842xdooz.js +1 -0
  529. package/dist/assets/volter-sdk-widgets-editor-appearance-CoihkoDV.js +1 -0
  530. package/dist/assets/volter-sdk-widgets-editor-material-B4PbVOyD.js +1 -0
  531. package/dist/assets/volter-sdk-widgets-icon-set-registry-DzBkVTxs.js +1 -0
  532. package/dist/assets/volter-sdk-widgets-index-DRlEnpTD.js +1 -0
  533. package/dist/assets/volter-sdk-widgets-inspector-widgets-AlignmentGrid-DKC7RjtF.js +1 -0
  534. package/dist/assets/volter-sdk-widgets-inspector-widgets-AssetSlotPicker-CGyznIv-.js +1 -0
  535. package/dist/assets/volter-sdk-widgets-inspector-widgets-BorderEditor-C74QsfSH.js +1 -0
  536. package/dist/assets/volter-sdk-widgets-inspector-widgets-ColorPicker-Czwcm_Fi.js +1 -0
  537. package/dist/assets/volter-sdk-widgets-inspector-widgets-CurveEditor-Tij7lXpB.js +1 -0
  538. package/dist/assets/volter-sdk-widgets-inspector-widgets-FilterEditor-CY45gPqT.js +1 -0
  539. package/dist/assets/volter-sdk-widgets-inspector-widgets-FontPicker-BnGlrZAL.js +1 -0
  540. package/dist/assets/volter-sdk-widgets-inspector-widgets-GradientEditor-uN_3-0Hz.js +1 -0
  541. package/dist/assets/volter-sdk-widgets-inspector-widgets-ScrubbableInput-kk1HfmXA.js +1 -0
  542. package/dist/assets/volter-sdk-widgets-inspector-widgets-ShadowEditor-OuqeQbiU.js +1 -0
  543. package/dist/assets/volter-sdk-widgets-inspector-widgets-color-utils-BArl9zsg.js +1 -0
  544. package/dist/assets/volter-sdk-widgets-inspector-widgets-curve-utils-C9xyDCr6.js +1 -0
  545. package/dist/assets/volter-sdk-widgets-inspector-widgets-index-DCEai530.js +1 -0
  546. package/dist/assets/volter-sdk-widgets-inspector-widgets-shared-CJSGOgSm.js +1 -0
  547. package/dist/assets/volter-sdk-widgets-interactive-edit-scope-6PmN1jnt.js +1 -0
  548. package/dist/assets/volter-sdk-widgets-patterns-Dialog-CnuLoAXX.js +1 -0
  549. package/dist/assets/volter-sdk-widgets-patterns-Fields-wFJZE-ci.js +1 -0
  550. package/dist/assets/volter-sdk-widgets-patterns-List-DNL6_6To.js +1 -0
  551. package/dist/assets/volter-sdk-widgets-patterns-StateSurface-Ih0mzWk7.js +1 -0
  552. package/dist/assets/volter-sdk-widgets-patterns-Surfaces-07TRSs2c.js +1 -0
  553. package/dist/assets/volter-sdk-widgets-patterns-Tabs-BKYsTo--.js +1 -0
  554. package/dist/assets/volter-sdk-widgets-patterns-Toolbar-BxOrCYIs.js +1 -0
  555. package/dist/assets/volter-sdk-widgets-patterns-Tree-BfYgX2pa.js +1 -0
  556. package/dist/assets/volter-sdk-widgets-primitives-AnchoredMenu-BgHf-cYK.js +1 -0
  557. package/dist/assets/volter-sdk-widgets-primitives-Button-BUrjXrb8.js +1 -0
  558. package/dist/assets/volter-sdk-widgets-primitives-ColorInput-BiRkft3M.js +1 -0
  559. package/dist/assets/volter-sdk-widgets-primitives-DraftTextInput-B1KK1N_R.js +1 -0
  560. package/dist/assets/volter-sdk-widgets-primitives-EditorIcon-CP8wT6d7.js +1 -0
  561. package/dist/assets/volter-sdk-widgets-primitives-FormControls-ScHBA1o4.js +1 -0
  562. package/dist/assets/volter-sdk-widgets-primitives-HoverPreview-CSS-glOy.js +1 -0
  563. package/dist/assets/volter-sdk-widgets-primitives-JsonInput-C0TAVCVh.js +1 -0
  564. package/dist/assets/volter-sdk-widgets-primitives-Layout-CfLBd5Or.js +1 -0
  565. package/dist/assets/volter-sdk-widgets-primitives-Menu-C-Wd4QZF.js +1 -0
  566. package/dist/assets/volter-sdk-widgets-primitives-NumberInput-sPbmhEcp.js +1 -0
  567. package/dist/assets/volter-sdk-widgets-primitives-Panel-CssQZiuw.js +1 -0
  568. package/dist/assets/volter-sdk-widgets-primitives-SectionHeader-CCbuJZbe.js +1 -0
  569. package/dist/assets/volter-sdk-widgets-primitives-Text-CnnND9sI.js +1 -0
  570. package/dist/assets/volter-sdk-widgets-primitives-ThemeRootPortal-DmN1LfqW.js +1 -0
  571. package/dist/assets/volter-sdk-widgets-primitives-Tooltip-D9uLAtac.js +1 -0
  572. package/dist/assets/volter-sdk-widgets-primitives-Vec3Input-CbkOGVMc.js +1 -0
  573. package/dist/assets/volter-sdk-widgets-primitives-banner-tones-D4w8jWDq.js +1 -0
  574. package/dist/assets/volter-sdk-widgets-primitives-clamp-to-viewport-DUn6HqOF.js +1 -0
  575. package/dist/assets/volter-sdk-widgets-primitives-editor-icons-Dw62jIE_.js +1 -0
  576. package/dist/assets/volter-sdk-widgets-primitives-panel-header-styles-BsPj50mE.js +1 -0
  577. package/dist/assets/volter-sdk-widgets-theme-CWND6gaS.js +1 -0
  578. package/dist/assets/volter-sdk-widgets-z-index-CAROhwsS.js +1 -0
  579. package/dist/assets/volter-shared-fontawesome-CU2fjApc.js +1 -0
  580. package/dist/assets/volter-shared-jsx-dev-runtime-CSjBZz-G.js +1 -0
  581. package/dist/assets/volter-shared-jsx-runtime-BfW1mwnX.js +1 -0
  582. package/dist/assets/volter-shared-react-B7X6VYnC.js +1 -0
  583. package/dist/assets/volter-shared-react-dom-DjKMQVYW.js +1 -0
  584. package/dist/assets/volter-shared-react-dom-client-76WJXUTi.js +1 -0
  585. package/dist/assets/volter-shared-three-wYzUWvH9.js +1 -0
  586. package/dist/assets/worker-D1j8wqVo.js +4 -0
  587. package/dist/volter-shared-react.json +10 -0
  588. package/dist/volter-shared-sdk.json +462 -0
  589. package/dist/volter-shared-three.json +3 -0
  590. package/dist-node/cli.js +21181 -0
  591. package/dist-node/create.js +14272 -0
  592. package/package.json +84 -4
  593. package/presets.mjs +2 -0
  594. package/src/contributions.d.ts +4 -0
  595. package/src/index.ts +10 -0
  596. package/starter/AGENTS.md +400 -0
  597. package/starter/CLAUDE.md +1 -0
  598. package/starter/cube.blend +0 -0
  599. package/starter/cube.py +82 -0
  600. package/starter/package.json +9 -0
  601. package/starter/race-state.ts +22 -0
  602. package/starter/track.blend +0 -0
  603. package/starter/track.play.ts +343 -0
  604. package/starter/track.py +324 -0
  605. package/starter/ui/game.stories.tsx +12 -0
  606. package/starter/ui/game.tsx +10 -0
  607. package/starter/ui/race-hud.tsx +29 -0
@@ -0,0 +1,343 @@
1
+ // SPDX-License-Identifier: MIT
2
+ // Copyright 2026 Volter AI, Inc.
3
+
4
+ /** Drive the detached Cube. All positions under root are Blender's metres, Z up. */
5
+ import * as THREE from 'three';
6
+ import { publishRaceState } from './race-state';
7
+
8
+ export default function play(context: {
9
+ readonly root: THREE.Object3D;
10
+ find(name: string): THREE.Object3D | null;
11
+ readonly camera: THREE.Camera;
12
+ readonly keys: ReadonlySet<string>;
13
+ /** Offers the bot the Game panel's Autoplay switches on; absent outside the editor. */
14
+ autoplay?(controller: (input: { readonly tick: number }) => Iterable<string>): void;
15
+ }) {
16
+ const { root, find, keys } = context;
17
+ const car = find('Cube');
18
+ if (!car || !find('Track')) throw new Error('Open track.blend and run track.py first.');
19
+ const startPosition = car.position.clone();
20
+ const startHeading = car.rotation.z;
21
+ const wheels = ['Wheel.FL', 'Wheel.FR', 'Wheel.RL', 'Wheel.RR'].map((name) => {
22
+ const wheel = find(name);
23
+ if (!wheel) throw new Error(`The track model has no ${name}.`);
24
+ wheel.rotation.reorder('ZXY');
25
+ return wheel;
26
+ });
27
+ const startWheelRotations = wheels.map(wheel => wheel.quaternion.clone());
28
+ const surfaces: THREE.Object3D[] = [];
29
+ const kerbs: THREE.Vector3[] = [];
30
+ const obstacles: {
31
+ object: THREE.Object3D; position: THREE.Vector3; rotation: THREE.Quaternion;
32
+ velocity: THREE.Vector3; spin: THREE.Vector3; floor: number; hit: boolean;
33
+ }[] = [];
34
+ root.traverse((object) => {
35
+ if (!(object as THREE.Mesh).isMesh) return;
36
+ if (object.name.startsWith('Kerb.')) kerbs.push(object.position.clone());
37
+ if (object.name === 'Track' || object.name.startsWith('Ramp')) surfaces.push(object);
38
+ if (/^(Cone|Crate)\./.test(object.name)) {
39
+ find(object.name);
40
+ obstacles.push({ object, position: object.position.clone(), rotation: object.quaternion.clone(),
41
+ velocity: new THREE.Vector3(), spin: new THREE.Vector3(), floor: object.position.z, hit: false });
42
+ }
43
+ });
44
+ let speed = 0;
45
+ let heading = car.rotation.z;
46
+ let steering = 0;
47
+ let verticalSpeed = 0;
48
+ let grounded = true;
49
+ let pitch = 0;
50
+ let cameraStarted = false;
51
+ let elapsed = 0;
52
+ let lap = 0;
53
+ let lapStarted = 0;
54
+ let lastLap = 0;
55
+ let checkpoint = 0;
56
+ let previousY = car.position.y;
57
+ let effectClock = 0;
58
+ let hudClock = 0;
59
+ let restartHeld = false;
60
+ const checkpoints = [1, 2, 3].map(i => find(`Checkpoint.${i}`)).filter((o): o is THREE.Object3D => o !== null);
61
+ const velocity = new THREE.Vector2();
62
+ const effects = new THREE.Group();
63
+ effects.name = 'Race effects';
64
+ root.add(effects);
65
+ const markGeometry = new THREE.PlaneGeometry(0.32, 0.7);
66
+ const markMaterial = new THREE.MeshBasicMaterial({ color: '#0f1a1f', transparent: true, opacity: 0.6, depthWrite: false });
67
+ const marks = Array.from({ length: 128 }, () => {
68
+ const mark = new THREE.Mesh(markGeometry, markMaterial);
69
+ mark.visible = false;
70
+ effects.add(mark);
71
+ return mark;
72
+ });
73
+ let nextMark = 0;
74
+ const puffGeometry = new THREE.IcosahedronGeometry(0.22, 0);
75
+ const puffs = Array.from({ length: 24 }, () => {
76
+ const material = new THREE.MeshBasicMaterial({ color: '#e9edef', transparent: true, opacity: 0, depthWrite: false });
77
+ const mesh = new THREE.Mesh(puffGeometry, material);
78
+ mesh.visible = false;
79
+ effects.add(mesh);
80
+ return { mesh, life: 0 };
81
+ });
82
+ let nextPuff = 0;
83
+ let fps = 0;
84
+ let measuredFrames = 0;
85
+ let measuredSince = performance.now();
86
+ const ray = new THREE.Raycaster();
87
+ const origin = new THREE.Vector3();
88
+ const down = new THREE.Vector3();
89
+ const up = new THREE.Vector3();
90
+ const hitPoint = new THREE.Vector3();
91
+ const eye = new THREE.Vector3();
92
+ const target = new THREE.Vector3();
93
+ const cameraPosition = new THREE.Vector3();
94
+ const cameraTarget = new THREE.Vector3();
95
+ const held = (arrow: string, letter: string): boolean => keys.has(arrow) || keys.has(letter);
96
+ const approach = (value: number, goal: number, step: number): number =>
97
+ value < goal ? Math.min(value + step, goal) : Math.max(value - step, goal);
98
+ const surfaceAt = (x: number, y: number): number | null => {
99
+ root.localToWorld(origin.set(x, y, 40));
100
+ ray.set(origin, down);
101
+ ray.far = 100;
102
+ const hit = ray.intersectObjects(surfaces, false)[0];
103
+ return hit ? root.worldToLocal(hitPoint.copy(hit.point)).z : null;
104
+ };
105
+
106
+ const restart = () => {
107
+ car.position.copy(startPosition);
108
+ heading = startHeading;
109
+ car.rotation.set(0, 0, heading, 'ZXY');
110
+ speed = steering = verticalSpeed = pitch = 0;
111
+ velocity.set(0, 0);
112
+ grounded = true;
113
+ cameraStarted = false;
114
+ elapsed = lap = lapStarted = lastLap = checkpoint = effectClock = hudClock = 0;
115
+ previousY = startPosition.y;
116
+ for (const [index, wheel] of wheels.entries()) wheel.quaternion.copy(startWheelRotations[index]!);
117
+ for (const obstacle of obstacles) {
118
+ obstacle.object.position.copy(obstacle.position);
119
+ obstacle.object.quaternion.copy(obstacle.rotation);
120
+ obstacle.velocity.set(0, 0, 0);
121
+ obstacle.spin.set(0, 0, 0);
122
+ obstacle.hit = false;
123
+ }
124
+ for (const mark of marks) mark.visible = false;
125
+ for (const puff of puffs) {
126
+ puff.life = 0;
127
+ puff.mesh.visible = false;
128
+ puff.mesh.material.opacity = 0;
129
+ }
130
+ publishRaceState({ lap: 1, lapTime: 0, lastLap: 0, speed: 0, fps, airborne: false });
131
+ };
132
+
133
+ // THE BOT, offered to the editor: Autoplay in the Game panel lets it drive, and any key or
134
+ // click in the game hands the car back. It holds the same keys a person would, aiming at the
135
+ // next of track.py's control points and braking into turns it is taking too fast.
136
+ const route = [[32, -30], [32, -10], [32, 10], [32, 26], [22, 36], [8, 32], [4, 18], [-8, 16], [-16, 28],
137
+ [-30, 24], [-34, 10], [-22, 0], [-10, -4], [-16, -18], [-34, -28], [-30, -42], [-12, -44], [10, -44], [26, -40]]
138
+ .map(([x, y]) => new THREE.Vector2(x, y));
139
+ let waypoint = 0;
140
+ let botTick = -1;
141
+ context.autoplay?.(({ tick }) => {
142
+ const at = new THREE.Vector2(car.position.x, car.position.y);
143
+ // Switched on (again): aim past the nearest point, wherever the person left the car.
144
+ if (tick !== botTick + 1) {
145
+ const nearest = route.reduce((best, point, index) => point.distanceTo(at) < route[best]!.distanceTo(at) ? index : best, 0);
146
+ waypoint = (nearest + 1) % route.length;
147
+ }
148
+ botTick = tick;
149
+ if (route[waypoint]!.distanceTo(at) < 9) waypoint = (waypoint + 1) % route.length;
150
+ const target = route[waypoint]!;
151
+ const error = Math.atan2(target.y - at.y, target.x - at.x) - (heading + Math.PI / 2);
152
+ const turn = Math.atan2(Math.sin(error), Math.cos(error));
153
+ const hold = [Math.abs(turn) > 0.6 && speed > 14 ? 'ArrowDown' : 'ArrowUp'];
154
+ if (turn > 0.08) hold.push('ArrowLeft');
155
+ else if (turn < -0.08) hold.push('ArrowRight');
156
+ return hold;
157
+ });
158
+
159
+ return {
160
+ update(dt: number) {
161
+ if (dt <= 0) return;
162
+ const restarting = keys.has('KeyR');
163
+ const firstRestartFrame = restarting && !restartHeld;
164
+ restartHeld = restarting;
165
+ if (firstRestartFrame) {
166
+ restart();
167
+ return;
168
+ }
169
+ elapsed += dt;
170
+ measuredFrames++;
171
+ const now = performance.now();
172
+ if (now - measuredSince >= 1000) {
173
+ fps = measuredFrames * 1000 / (now - measuredSince);
174
+ measuredFrames = 0;
175
+ measuredSince = now;
176
+ }
177
+ root.updateMatrixWorld(true);
178
+ up.set(0, 0, 1).transformDirection(root.matrixWorld);
179
+ down.copy(up).negate();
180
+ const throttle = held('ArrowUp', 'KeyW');
181
+ const brake = held('ArrowDown', 'KeyS');
182
+ const turn = Number(held('ArrowLeft', 'KeyA')) - Number(held('ArrowRight', 'KeyD'));
183
+ const steps = Math.ceil(dt / (1 / 60));
184
+ const h = dt / steps;
185
+ let travelled = 0;
186
+ for (let step = 0; step < steps; step++) {
187
+ if (throttle && !brake) speed = approach(speed, 30, (speed < 0 ? 20 : 10) * h);
188
+ else if (brake && !throttle) speed = approach(speed, -8, (speed > 0 ? 20 : 7) * h);
189
+ else speed = approach(speed, 0, (throttle && brake ? 20 : 3) * h);
190
+ steering = approach(steering, turn * 0.5, 3 * h);
191
+ if (grounded) heading += speed / 1.8 * Math.tan(steering) / (1 + Math.abs(speed) / 8) * h;
192
+ const drifting = grounded && Math.abs(steering) > 0.3 && Math.abs(speed) > 13;
193
+ const grip = grounded ? (drifting ? 1.6 : 8) : 0.2;
194
+ velocity.lerp(new THREE.Vector2(-Math.sin(heading) * speed, Math.cos(heading) * speed), 1 - Math.exp(-grip * h));
195
+ travelled += velocity.length() * h * Math.sign(speed);
196
+ car.position.x += velocity.x * h;
197
+ car.position.y += velocity.y * h;
198
+ const road = surfaceAt(car.position.x, car.position.y);
199
+ const floor = road ?? 0;
200
+ if (road === null && grounded) {
201
+ speed *= Math.exp(-2 * h);
202
+ speed = THREE.MathUtils.clamp(speed, -4, 4);
203
+ velocity.multiplyScalar(Math.exp(-2 * h));
204
+ }
205
+ // Follow a rising surface; retain its launch velocity when the surface drops away.
206
+ if (grounded && floor >= car.position.z - 0.15) {
207
+ verticalSpeed = (floor - car.position.z) / h;
208
+ car.position.z = floor;
209
+ const ahead = surfaceAt(car.position.x - Math.sin(heading), car.position.y + Math.cos(heading));
210
+ const behind = surfaceAt(car.position.x + Math.sin(heading), car.position.y - Math.cos(heading));
211
+ const slope = ahead === null || behind === null ? 0 : Math.atan2(ahead - behind, 2);
212
+ pitch = THREE.MathUtils.lerp(pitch, slope, 1 - Math.exp(-10 * h));
213
+ } else {
214
+ grounded = false;
215
+ verticalSpeed -= 30 * h;
216
+ car.position.z += verticalSpeed * h;
217
+ if (car.position.z <= floor && verticalSpeed <= 0) {
218
+ car.position.z = floor;
219
+ verticalSpeed = 0;
220
+ grounded = true;
221
+ }
222
+ pitch = THREE.MathUtils.lerp(pitch, Math.atan2(verticalSpeed, Math.max(10, Math.abs(speed))), 1 - Math.exp(-3 * h));
223
+ }
224
+ for (const obstacle of obstacles) {
225
+ const { object, velocity, spin } = obstacle;
226
+ const dx = object.position.x - car.position.x;
227
+ const dy = object.position.y - car.position.y;
228
+ if (!obstacle.hit && Math.hypot(dx, dy) < 1.7 && Math.abs(object.position.z - car.position.z) < 2 && Math.abs(speed) > 1) {
229
+ obstacle.hit = true;
230
+ velocity.set(-Math.sin(heading) * speed * 0.8 + dx * 2, Math.cos(heading) * speed * 0.8 + dy * 2, 5);
231
+ spin.set(3, -4, 2);
232
+ speed *= 0.93;
233
+ }
234
+ if (!obstacle.hit) continue;
235
+ velocity.z -= 18 * h;
236
+ object.position.addScaledVector(velocity, h);
237
+ object.rotation.x += spin.x * h;
238
+ object.rotation.y += spin.y * h;
239
+ object.rotation.z += spin.z * h;
240
+ if (object.position.z < obstacle.floor) {
241
+ object.position.z = obstacle.floor;
242
+ velocity.z = Math.abs(velocity.z) * 0.25;
243
+ velocity.x *= Math.exp(-5 * h);
244
+ velocity.y *= Math.exp(-5 * h);
245
+ spin.multiplyScalar(Math.exp(-5 * h));
246
+ }
247
+ }
248
+ }
249
+ const roll = grounded ? -steering * Math.min(Math.abs(speed), 24) * 0.018 : 0;
250
+ car.rotation.set(pitch, roll, heading, 'ZXY');
251
+ effectClock += dt;
252
+ const slipping = grounded && Math.abs(steering) > 0.3 && Math.abs(speed) > 13;
253
+ const offroad = grounded && surfaceAt(car.position.x, car.position.y) === null;
254
+ if ((slipping || offroad) && effectClock > 0.06) {
255
+ effectClock = 0;
256
+ for (const side of [-1, 1]) {
257
+ const mark = marks[nextMark++ % marks.length]!;
258
+ mark.position.copy(car.position).add(new THREE.Vector3(side * 1.2 * Math.cos(heading) + Math.sin(heading) * 0.78,
259
+ side * 1.2 * Math.sin(heading) - Math.cos(heading) * 0.78, 0.018));
260
+ mark.rotation.z = heading;
261
+ mark.visible = true;
262
+ const puff = puffs[nextPuff++ % puffs.length]!;
263
+ puff.mesh.position.copy(mark.position).add(new THREE.Vector3(0, 0, 0.3));
264
+ puff.mesh.scale.setScalar(1);
265
+ puff.mesh.material.color.set(offroad ? '#c7641a' : '#e9edef');
266
+ puff.life = 0.7;
267
+ puff.mesh.visible = true;
268
+ }
269
+ }
270
+ for (const puff of puffs) {
271
+ if (puff.life <= 0) continue;
272
+ puff.life -= dt;
273
+ puff.mesh.visible = puff.life > 0;
274
+ puff.mesh.material.opacity = Math.max(0, puff.life * 0.5);
275
+ puff.mesh.position.z += dt * 0.9;
276
+ puff.mesh.scale.addScalar(dt * 1.8);
277
+ }
278
+ const nextCheckpoint = checkpoints[checkpoint];
279
+ if (lap > 0 && nextCheckpoint && Math.hypot(car.position.x - nextCheckpoint.position.x, car.position.y - nextCheckpoint.position.y) < 10)
280
+ checkpoint++;
281
+ if (previousY < -24 && car.position.y >= -24 && Math.abs(car.position.x - 32) < 5 && speed > 0) {
282
+ if (lap === 0 || checkpoint === checkpoints.length) {
283
+ lastLap = lap === 0 ? 0 : elapsed - lapStarted;
284
+ lap++;
285
+ checkpoint = 0;
286
+ lapStarted = elapsed;
287
+ }
288
+ }
289
+ previousY = car.position.y;
290
+ hudClock += dt;
291
+ if (hudClock >= 0.1) {
292
+ hudClock = 0;
293
+ publishRaceState({ lap: Math.max(1, lap), lapTime: lap ? elapsed - lapStarted : 0,
294
+ lastLap, speed: Math.abs(speed) * 3.6, fps, airborne: !grounded });
295
+ }
296
+ for (const [index, wheel] of wheels.entries()) {
297
+ wheel.rotation.z = index < 2 ? steering : 0;
298
+ wheel.rotation.x = (wheel.rotation.x - travelled / 0.57) % (2 * Math.PI);
299
+ }
300
+
301
+ // Smooth our own stage-space pose; navigation re-poses the stage camera each frame.
302
+ root.updateMatrixWorld(true);
303
+ const pace = Math.min(30, Math.abs(speed));
304
+ const distance = grounded ? 11 + pace * 0.07 : 12;
305
+ const lookAhead = grounded ? 2.5 + pace * 0.04 : 0.5;
306
+ const fov = 36 + pace * 0.28;
307
+ const height = 1.2 + (distance + lookAhead) * Math.tan(THREE.MathUtils.degToRad(fov * 0.22));
308
+ const kerb = grounded && kerbs.some(point => Math.hypot(point.x - car.position.x, point.y - car.position.y) < 1.4);
309
+ const rumble = kerb ? Math.sin(elapsed * 90) * Math.min(0.05, pace * 0.003) : 0;
310
+ const side = grounded ? 3 : 10;
311
+ root.localToWorld(eye.set(car.position.x + Math.sin(heading) * distance + side * Math.cos(heading),
312
+ car.position.y - Math.cos(heading) * distance + side * Math.sin(heading), car.position.z + height + rumble));
313
+ root.localToWorld(target.set(car.position.x - Math.sin(heading) * lookAhead,
314
+ car.position.y + Math.cos(heading) * lookAhead, car.position.z + (grounded ? 1.4 : 0.4)));
315
+ if (!cameraStarted) {
316
+ cameraPosition.copy(eye);
317
+ cameraTarget.copy(target);
318
+ cameraStarted = true;
319
+ }
320
+ const blend = 1 - Math.exp(-12 * dt);
321
+ cameraPosition.lerp(eye, blend);
322
+ cameraTarget.lerp(target, blend);
323
+ const camera = context.camera;
324
+ camera.position.copy(cameraPosition);
325
+ if (camera.parent) camera.parent.worldToLocal(camera.position);
326
+ camera.up.copy(up).applyAxisAngle(new THREE.Vector3().subVectors(cameraTarget, cameraPosition).normalize(), -roll * 0.3);
327
+ if ((camera as THREE.PerspectiveCamera).isPerspectiveCamera) {
328
+ const perspective = camera as THREE.PerspectiveCamera;
329
+ perspective.fov = fov;
330
+ perspective.updateProjectionMatrix();
331
+ }
332
+ camera.lookAt(cameraTarget);
333
+ camera.updateMatrixWorld(true);
334
+ },
335
+ dispose() {
336
+ root.remove(effects);
337
+ markGeometry.dispose();
338
+ markMaterial.dispose();
339
+ puffGeometry.dispose();
340
+ for (const puff of puffs) puff.mesh.material.dispose();
341
+ },
342
+ };
343
+ }
@@ -0,0 +1,324 @@
1
+ # SPDX-License-Identifier: GPL-3.0-or-later
2
+ # Copyright 2026 Volter AI, Inc.
3
+ #
4
+ # Like cube.py, this bpy script is GPL-3.0-or-later; the .blend it authors
5
+ # is your artwork, and the project's other starter source is MIT.
6
+
7
+ """The race source for Volter Cyclotron, built on Blender.
8
+
9
+ Open Track, then run through the session's Blender:
10
+ editor.blender('blender-execute', { code: open('src/models/track.py').read() })
11
+ The agent's blender MCP server is declared in .mcp.json and runs the project's
12
+ installed Cyclotron CLI directly in Node, without an npm/bin shim.
13
+
14
+ Only track.blend may be replaced; the session saves it. View > Play drives
15
+ its grey Cube with arrows/WASD. Move any Ramp* mesh onto the circuit to jump.
16
+ Coordinates are metres, Z is up, and local +Y is forward.
17
+ """
18
+
19
+ import math
20
+ from pathlib import Path
21
+
22
+ import bpy
23
+ from mathutils import Matrix, Vector
24
+
25
+ if Path(bpy.data.filepath).name != "track.blend":
26
+ raise RuntimeError("Open the Track model (track.blend) first: this replaces the open model.")
27
+
28
+ for obj in list(bpy.data.objects):
29
+ bpy.data.objects.remove(obj, do_unlink=True)
30
+ # This file owns its entire scene, including its display collections.
31
+ for group in list(bpy.data.collections):
32
+ if group.name != "Collection":
33
+ bpy.data.collections.remove(group)
34
+ for collection in (bpy.data.meshes, bpy.data.materials, bpy.data.lights, bpy.data.cameras, bpy.data.curves):
35
+ for data in list(collection):
36
+ collection.remove(data)
37
+
38
+
39
+ def colour(value):
40
+ rgb = tuple(int(value[i:i + 2], 16) / 255 for i in (1, 3, 5))
41
+ return tuple(c / 12.92 if c <= 0.04045 else ((c + 0.055) / 1.055) ** 2.4 for c in rgb)
42
+
43
+
44
+ def material(name, value):
45
+ result = bpy.data.materials.new(name=name)
46
+ result.use_nodes = True
47
+ rgba = (*colour(value), 1.0)
48
+ result.diffuse_color = rgba
49
+ result.node_tree.nodes.get("Principled BSDF").inputs["Base Color"].default_value = rgba
50
+ return result
51
+
52
+
53
+ # Volter's light semantic roles from brand.volter.ai/tokens.json, in linear RGB.
54
+ asphalt = material("Asphalt", "#16252c") # surface.inverse
55
+ # Dry asphalt scatters the low sun; it must not read as a polished mirror.
56
+ asphalt.node_tree.nodes.get("Principled BSDF").inputs["Roughness"].default_value = 1.0
57
+ asphalt.node_tree.nodes.get("Principled BSDF").inputs["Specular IOR Level"].default_value = 0.05
58
+ grass = material("Grass", "#5f9a2e") # scene.instance
59
+ grass.node_tree.nodes.get("Principled BSDF").inputs["Roughness"].default_value = 1.0
60
+ grass.node_tree.nodes.get("Principled BSDF").inputs["Specular IOR Level"].default_value = 0.05
61
+ orange = material("Orange", "#ff6a1f") # accent.orange
62
+ white = material("White", "#f3f2ec") # text.inverse
63
+ rubber = material("Rubber", "#0f1a1f") # surface.media
64
+ violet = material("Violet", "#6a5a92") # scene.dynamicSoft
65
+ wood = material("Wood", "#c7641a") # data.amber
66
+ leaves = material("Leaves", "#5f9a2e") # scene.instance
67
+ cube_material = bpy.data.materials.new(name="Material")
68
+ cube_material.use_nodes = True
69
+
70
+
71
+ def box(name, location, dimensions, surface, parent=None):
72
+ bpy.ops.mesh.primitive_cube_add(size=1.0, location=location)
73
+ obj = bpy.context.active_object
74
+ obj.name = name
75
+ obj.data.name = name
76
+ obj.dimensions = dimensions
77
+ bpy.ops.object.transform_apply(location=False, rotation=False, scale=True)
78
+ obj.data.materials.append(surface)
79
+ obj.parent = parent
80
+ return obj
81
+
82
+
83
+ def mesh(name, vertices, faces, surface, location=(0.0, 0.0, 0.0)):
84
+ data = bpy.data.meshes.new(name)
85
+ data.from_pydata(vertices, [], faces)
86
+ data.update()
87
+ obj = bpy.data.objects.new(name, data)
88
+ bpy.context.collection.objects.link(obj)
89
+ obj.location = location
90
+ obj.data.materials.append(surface)
91
+ return obj
92
+
93
+
94
+ # A long start straight, a tight northern turn and alternating infield bends.
95
+ points = [
96
+ (32, -30), (32, -10), (32, 10), (32, 26), (22, 36), (8, 32),
97
+ (4, 18), (-8, 16), (-16, 28), (-30, 24), (-34, 10), (-22, 0),
98
+ (-10, -4), (-16, -18), (-34, -28), (-30, -42), (-12, -44),
99
+ (10, -44), (26, -40),
100
+ ]
101
+
102
+
103
+ def path(index, t):
104
+ a, b, c, d = [Vector((*points[(index + offset) % len(points)], 0)) for offset in (-1, 0, 1, 2)]
105
+ return 0.5 * ((2 * b) + (-a + c) * t + (2 * a - 5 * b + 4 * c - d) * t * t + (-a + 3 * b - 3 * c + d) * t * t * t)
106
+
107
+
108
+ samples = []
109
+ for i in range(len(points)):
110
+ for step in range(12):
111
+ t = step / 12
112
+ centre = path(i, t)
113
+ tangent = (path(i, t + 0.001) - centre).normalized()
114
+ normal = Vector((-tangent.y, tangent.x, 0))
115
+ samples.append((centre, tangent, normal))
116
+
117
+ vertices = []
118
+ for centre, tangent, normal in samples:
119
+ vertices.extend([tuple(centre - normal * 5), tuple(centre + normal * 5)])
120
+ faces = []
121
+ for i in range(len(samples)):
122
+ j = (i + 1) % len(samples)
123
+ faces.append((2 * i, 2 * j, 2 * j + 1, 2 * i + 1))
124
+ mesh("Track", vertices, faces, asphalt)
125
+ # Raised just above the asphalt, with face normals up: crisp road markings.
126
+ for side in (-1, 1):
127
+ edge = []
128
+ for centre, tangent, normal in samples:
129
+ edge.extend([tuple(centre + normal * (side * 4.62 - 0.09) + Vector((0, 0, 0.012))),
130
+ tuple(centre + normal * (side * 4.62 + 0.09) + Vector((0, 0, 0.012)))])
131
+ mesh(f"Edge.{side}", edge, faces, white)
132
+ for i, (centre, tangent, normal) in enumerate(samples):
133
+ if i % 4 == 0:
134
+ line = box(f"Centre.{i}", (centre.x, centre.y, 0.015), (0.16, 1.5, 0.02), white)
135
+ line.rotation_euler.z = math.atan2(tangent.y, tangent.x) - math.pi / 2
136
+
137
+ bpy.ops.mesh.primitive_plane_add(size=300, location=(0, -4, -0.04))
138
+ ground = bpy.context.active_object
139
+ ground.name = "Ground"
140
+ ground.data.materials.append(grass)
141
+
142
+ for i, (centre, tangent, normal) in enumerate(samples):
143
+ if i % 3 != 0:
144
+ continue
145
+ for side in (-1, 1):
146
+ at = centre + normal * (5.3 * side)
147
+ kerb = box(f"Kerb.{i}.{side}", (at.x, at.y, 0.09), (0.6, 1.7, 0.18), white if i % 2 else orange)
148
+ kerb.rotation_euler.z = math.atan2(tangent.y, tangent.x) - math.pi / 2
149
+ if i % 12 == 0:
150
+ at = centre - normal * 7.3
151
+ for tyre in range(3):
152
+ bpy.ops.mesh.primitive_torus_add(major_segments=12, minor_segments=6, major_radius=0.52, minor_radius=0.22, location=(at.x + tangent.x * (tyre - 1) * 1.4, at.y + tangent.y * (tyre - 1) * 1.4, 0.35))
153
+ obj = bpy.context.active_object
154
+ obj.name = f"Barrier.{i}.{tyre}"
155
+ obj.data.materials.append(rubber)
156
+
157
+ # The checker line and gantry make the start readable from the chase camera.
158
+ for row in range(2):
159
+ for column in range(10):
160
+ box(f"Start.{row}.{column}", (27.5 + column, -24 + row * 0.5, 0.015), (1, 0.5, 0.03), white if (row + column) % 2 else asphalt)
161
+ for x in (25.8, 38.2):
162
+ box(f"Gantry.Post.{x}", (x, -24, 3.1), (0.35, 0.5, 6.2), white)
163
+ box("Gantry.Beam", (32, -24, 6.0), (13, 0.6, 0.8), orange)
164
+ for i in range(7):
165
+ box(f"Gantry.Check.{i}", (27.5 + i * 1.5, -24.32, 6.0), (0.75, 0.04, 0.55), white)
166
+
167
+ # A wedge's top is read by the play script, including after an editor move.
168
+ mesh("Ramp.Jump", [(-3, -4, 0), (3, -4, 0), (3, 4, 2.4), (-3, 4, 2.4), (-3, 4, 0), (3, 4, 0)],
169
+ [(0, 1, 2, 3), (3, 2, 5, 4), (0, 3, 4), (1, 5, 2), (0, 4, 5, 1)], violet, (32, -2, 0))
170
+
171
+ for i in range(6):
172
+ bpy.ops.mesh.primitive_cone_add(vertices=8, radius1=0.4, radius2=0.06, depth=0.85, location=(29 + i * 1.2, 12, 0.425))
173
+ cone = bpy.context.active_object
174
+ cone.name = f"Cone.{i}"
175
+ cone.data.materials.append(orange)
176
+ box(f"ConeBase.{i}", (0, 0, -0.4), (0.8, 0.8, 0.08), rubber, cone)
177
+ for i in range(4):
178
+ crate = box(f"Crate.{i}", (-27 + i * 1.5, -28, 0.65), (1.2, 1.2, 1.3), wood)
179
+ box(f"CrateBand.{i}", (0, 0, 0), (1.25, 0.15, 1.35), white, crate)
180
+
181
+ for i in range(56):
182
+ angle = math.tau * i / 56
183
+ x, y = (53 + i % 3 * 7) * math.cos(angle), -4 + (56 + i % 4 * 4) * math.sin(angle)
184
+ box(f"Tree.Trunk.{i}", (x, y, 1.4), (0.4, 0.4, 2.8), wood)
185
+ bpy.ops.mesh.primitive_ico_sphere_add(subdivisions=1, radius=2.6, location=(x, y, 4.0))
186
+ tree = bpy.context.active_object
187
+ tree.name = f"Tree.Crown.{i}"
188
+ tree.scale.z = 1.35
189
+ tree.data.materials.append(leaves if i % 2 else grass)
190
+
191
+ # Low-poly hills close the horizon without textures or a skybox.
192
+ for i in range(18):
193
+ angle = math.tau * i / 18
194
+ bpy.ops.mesh.primitive_ico_sphere_add(subdivisions=1, radius=1, location=(150 * math.cos(angle), -4 + 150 * math.sin(angle), 0))
195
+ hill = bpy.context.active_object
196
+ hill.name = f"Hill.{i}"
197
+ hill.scale = (55, 55, 6 + i % 4 * 3)
198
+ hill.data.materials.append(grass if i % 2 else leaves)
199
+ for i in range(5):
200
+ for tier in range(3):
201
+ box(f"Stand.{i}.{tier}", (44 + tier * 1.3, -28 + i * 5, 0.5 + tier * 0.6), (1.3, 4.5, 1 + tier * 1.2), orange if i % 2 else violet)
202
+ box(f"Stand.Roof.{i}", (45.3, -28 + i * 5, 4.2), (5, 4.8, 0.2), white)
203
+
204
+ for i, (x, y) in enumerate(((22, 2), (42, 14), (-40, 18), (-24, -50))):
205
+ box(f"Billboard.Post.{i}", (x, y, 1.5), (0.3, 0.4, 3), white)
206
+ box(f"Billboard.{i}", (x, y, 3), (0.35, 6, 2), orange if i % 2 else violet)
207
+ for stripe in range(3):
208
+ box(f"Billboard.Stripe.{i}.{stripe}", (x + 0.2, y - 1.6 + stripe * 1.5, 3), (0.05, 0.65, 1.4), white)
209
+
210
+ # Ordered checkpoints prevent lap counts from shuttling over the start line.
211
+ for i, (x, y) in enumerate(((8, 32), (-34, 10), (-12, -44)), 1):
212
+ checkpoint = bpy.data.objects.new(f"Checkpoint.{i}", None)
213
+ bpy.context.collection.objects.link(checkpoint)
214
+ checkpoint.location = (x, y, 0)
215
+
216
+ # Default cube geometry and material; its ground-level origin carries the wheels.
217
+ car = box("Cube", (32, -28, 0), (2, 2, 2), cube_material)
218
+ car.data.transform(Matrix.Translation((0, 0, 1.42)))
219
+ for name, x, y in (("Wheel.FL", -1.2, 0.78), ("Wheel.FR", 1.2, 0.78), ("Wheel.RL", -1.2, -0.78), ("Wheel.RR", 1.2, -0.78)):
220
+ bpy.ops.mesh.primitive_cylinder_add(vertices=16, radius=0.57, depth=0.55, location=(x, y, 0.57), rotation=(0, math.pi / 2, 0))
221
+ wheel = bpy.context.active_object
222
+ wheel.name = name
223
+ bpy.ops.object.transform_apply(location=False, rotation=True, scale=True)
224
+ wheel.data.materials.append(rubber)
225
+ wheel.parent = car
226
+ box(name + ".Spoke", (math.copysign(0.29, x), 0, 0), (0.04, 0.14, 0.85), white, wheel)
227
+
228
+ scene = bpy.context.scene
229
+ scene.unit_settings.system = "METRIC"
230
+ scene.unit_settings.scale_length = 1
231
+ scene.world.use_nodes = True
232
+ scene.world.node_tree.nodes.clear()
233
+ background = scene.world.node_tree.nodes.new("ShaderNodeBackground")
234
+ output = scene.world.node_tree.nodes.new("ShaderNodeOutputWorld")
235
+ scene.world.node_tree.links.new(background.outputs[0], output.inputs[0])
236
+ sky = scene.world.node_tree.nodes.new("ShaderNodeTexSky")
237
+ # Blender 5.2 calls its Nishita successor MULTIPLE_SCATTERING; the presenter supports it.
238
+ sky.sky_type = "MULTIPLE_SCATTERING"
239
+ sky.sun_elevation = math.radians(16)
240
+ sky.sun_rotation = math.radians(225)
241
+ sky.aerosol_density = 0.0
242
+ sky.altitude = 0.0
243
+ scene.world.node_tree.links.new(sky.outputs["Color"], background.inputs["Color"])
244
+ # Separate visible sky brightness from ambient radiance, as an ordinary World shader.
245
+ light_path = scene.world.node_tree.nodes.new("ShaderNodeLightPath")
246
+ ambient = scene.world.node_tree.nodes.new("ShaderNodeBackground")
247
+ ambient.inputs["Strength"].default_value = 0.03
248
+ scene.world.node_tree.links.new(sky.outputs["Color"], ambient.inputs["Color"])
249
+ mix = scene.world.node_tree.nodes.new("ShaderNodeMixShader")
250
+ scene.world.node_tree.links.new(light_path.outputs["Is Camera Ray"], mix.inputs[0])
251
+ scene.world.node_tree.links.new(ambient.outputs["Background"], mix.inputs[1])
252
+ scene.world.node_tree.links.new(background.outputs["Background"], mix.inputs[2])
253
+ scene.world.node_tree.links.new(mix.outputs[0], output.inputs["Surface"])
254
+ background.inputs["Strength"].default_value = 0.06
255
+ scene.view_settings.view_transform = "Standard"
256
+ scene.view_settings.look = "None"
257
+ scene.view_settings.exposure = 0
258
+ bpy.ops.object.light_add(type="SUN", rotation=(math.radians(74), 0, math.radians(-55)))
259
+ sun = bpy.context.active_object
260
+ sun.name = "Sun"
261
+ sun.data.energy = 3.0
262
+ sun.data.color = (1.0, 0.88, 0.68)
263
+ sun.data.angle = math.radians(0.5)
264
+
265
+ bpy.ops.object.camera_add(location=(39, -36, 3.8))
266
+ camera = bpy.context.active_object
267
+ camera.name = "Camera"
268
+ camera.rotation_euler = (Vector((32, -22, 1.4)) - camera.location).to_track_quat('-Z', 'Y').to_euler()
269
+ camera.data.lens = 28
270
+ scene.camera = camera
271
+ scene.render.resolution_x = 1280
272
+ scene.render.resolution_y = 720
273
+ scene.render.resolution_percentage = 100
274
+ for screen in bpy.data.screens:
275
+ for area in screen.areas:
276
+ if area.type == "VIEW_3D":
277
+ space = area.spaces.active
278
+ # Blender demotes Rendered to Solid when loading a file. Material
279
+ # Preview with the scene's World/lights survives that native load.
280
+ space.shading.type = "MATERIAL"
281
+ space.shading.use_scene_world = True
282
+ space.shading.use_scene_lights = True
283
+ space.region_3d.view_location = (32, -22, 1.4)
284
+ space.region_3d.view_distance = 16
285
+ space.region_3d.view_rotation = camera.rotation_euler.to_quaternion()
286
+
287
+ # Collections organize Blender files; parent empties also survive as the Play hierarchy.
288
+ # Identity group transforms keep the script's Blender-space obstacle/kerb positions intact.
289
+ main = bpy.data.collections.get("Collection")
290
+ groups = {}
291
+ for name in ("Kerbs", "Cones", "Crates", "Trees", "Tyres", "Scenery", "Gantry", "Ramps"):
292
+ group = bpy.data.objects.new(name, None)
293
+ main.objects.link(group)
294
+ group.empty_display_type = "PLAIN_AXES"
295
+ group.empty_display_size = 0.5
296
+ groups[name] = group
297
+
298
+ for obj in list(bpy.data.objects):
299
+ if obj.parent or obj.name in groups or obj.name in {"Cube", "Track", "Ground", "Sun", "Camera"}:
300
+ continue
301
+ prefix = obj.name.split(".")[0]
302
+ if prefix in {"Edge", "Centre"}:
303
+ parent = bpy.data.objects["Track"]
304
+ else:
305
+ group = {
306
+ "Kerb": "Kerbs", "Cone": "Cones", "Crate": "Crates", "Tree": "Trees",
307
+ "Barrier": "Tyres", "Gantry": "Gantry", "Start": "Gantry", "Ramp": "Ramps",
308
+ }.get(prefix, "Scenery")
309
+ parent = groups[group]
310
+ world = obj.matrix_world.copy()
311
+ obj.parent = parent
312
+ obj.matrix_world = world
313
+
314
+ # Expanded object rows should name their geometry, not a primitive's .001 data.
315
+ for obj in bpy.data.objects:
316
+ if obj.data is not None:
317
+ obj.data.name = obj.name
318
+
319
+ # Cameras are useful for a render, but their overlay rectangle obscures the edit.
320
+ camera.hide_set(True)
321
+
322
+ bpy.ops.object.select_all(action="DESELECT")
323
+ car.select_set(True)
324
+ bpy.context.view_layer.objects.active = car
@@ -0,0 +1,12 @@
1
+ // SPDX-License-Identifier: MIT
2
+ // Copyright 2026 Volter AI, Inc.
3
+ import GameUI from './game';
4
+ import { RaceHud } from './race-hud';
5
+ export default {
6
+ title: 'Race/HUD', component: GameUI, render: (args) => <RaceHud {...args} />,
7
+ parameters: { layout: 'fullscreen', volter: { defaultStory: 'StartLine' } },
8
+ args: { lap: 1, lapTime: 0, lastLap: 0, speed: 0, fps: 60, airborne: false },
9
+ };
10
+ export const StartLine = {};
11
+ export const Racing = { args: { lap: 2, lapTime: 18.24, lastLap: 42.15, speed: 96 } };
12
+ export const Jump = { args: { lapTime: 5.82, speed: 88, airborne: true } };