@volter/editor-core 0.5.57
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.
- package/BUNDLED_NOTICES +1527 -0
- package/LICENSE +686 -0
- package/LICENSE-APACHE +202 -0
- package/NOTICE +18 -0
- package/README.md +24 -0
- package/dist/build/chunk-JS4D4XZ3.js +175 -0
- package/dist/build/chunk-JS4D4XZ3.js.map +7 -0
- package/dist/build/vite-plugin-product-contributions.js +100 -0
- package/dist/build/vite-plugin-product-contributions.js.map +7 -0
- package/dist/build/vite-plugin-shared-react.js +25 -0
- package/dist/build/vite-plugin-shared-react.js.map +7 -0
- package/dist/build/vite-plugin-shared-three.js +86 -0
- package/dist/build/vite-plugin-shared-three.js.map +7 -0
- package/dist/server/chunk-KMJC7AGO.js +98 -0
- package/dist/server/chunk-KMJC7AGO.js.map +7 -0
- package/dist/server/chunk-PSILUMGS.js +46 -0
- package/dist/server/chunk-PSILUMGS.js.map +7 -0
- package/dist/server/frame-proxy.js +255 -0
- package/dist/server/frame-proxy.js.map +7 -0
- package/dist/server/open-browser.js +53 -0
- package/dist/server/open-browser.js.map +7 -0
- package/dist/server/process-shutdown.js +127 -0
- package/dist/server/process-shutdown.js.map +7 -0
- package/dist/server/session-registry.js +141 -0
- package/dist/server/session-registry.js.map +7 -0
- package/dist/server/spawn-opener.js +11 -0
- package/dist/server/spawn-opener.js.map +7 -0
- package/dist/server/worktree-identity.js +11 -0
- package/dist/server/worktree-identity.js.map +7 -0
- package/dist-server/packaged.mjs +88816 -0
- package/package.json +118 -0
- package/scripts/build-plugins.mjs +14 -0
- package/scripts/build-server.mjs +26 -0
- package/scripts/build-session.mjs +9 -0
- package/server/account-credentials.ts +60 -0
- package/server/account-service.ts +1434 -0
- package/server/adapter-region-includes.ts +47 -0
- package/server/asset-catalog-v2.ts +175 -0
- package/server/asset-history-snapshots.ts +196 -0
- package/server/asset-ledger-store.ts +195 -0
- package/server/asset-library-routes.ts +1595 -0
- package/server/blender-wasm-artifact.ts +430 -0
- package/server/boot-timings.ts +106 -0
- package/server/canonical-path.ts +50 -0
- package/server/checkout-workspace-preflight.ts +349 -0
- package/server/cloud-asset-catalog.ts +158 -0
- package/server/coding-inference-launch.ts +237 -0
- package/server/collaboration-account-client.ts +202 -0
- package/server/collaboration-attribution.ts +122 -0
- package/server/collaboration-session.ts +934 -0
- package/server/comfyui-bridge.ts +248 -0
- package/server/console-ledger.ts +499 -0
- package/server/creation-site-transform.ts +304 -0
- package/server/creation-site-write.ts +648 -0
- package/server/data-file-serialize.ts +158 -0
- package/server/editor-brand-html.ts +72 -0
- package/server/editor-control-socket.ts +366 -0
- package/server/editor-server-options.ts +190 -0
- package/server/editor-server.ts +1483 -0
- package/server/editor-sse.ts +352 -0
- package/server/engine-provenance.ts +169 -0
- package/server/engine-source-restart.ts +117 -0
- package/server/frame-bridge.ts +115 -0
- package/server/frame-proxy.ts +490 -0
- package/server/frame-workbench.ts +259 -0
- package/server/frontend-handoff.ts +229 -0
- package/server/game-globals-shadow.ts +113 -0
- package/server/gameplay-session-retention.ts +149 -0
- package/server/gameplay-sessions.ts +123 -0
- package/server/generation-jobs.ts +201 -0
- package/server/generation-reconciler.ts +137 -0
- package/server/generative-execution-context.ts +59 -0
- package/server/git-workflow.ts +612 -0
- package/server/harness-chat-caller.ts +36 -0
- package/server/harness-chat-service.ts +1681 -0
- package/server/idle-shutdown.ts +170 -0
- package/server/js-profiling-policy.ts +52 -0
- package/server/launcher-settings.ts +84 -0
- package/server/local-asset-catalog.ts +410 -0
- package/server/managed-account-defaults.ts +22 -0
- package/server/mock-control-plane.ts +540 -0
- package/server/model-import-conversion.ts +345 -0
- package/server/native-credential-store.ts +162 -0
- package/server/open-browser.ts +118 -0
- package/server/packaged.ts +1192 -0
- package/server/play-stall.ts +126 -0
- package/server/process-shutdown.ts +218 -0
- package/server/product-presets.ts +55 -0
- package/server/project-build-artifact.ts +95 -0
- package/server/project-components.ts +100 -0
- package/server/project-dependency-invalidation.ts +114 -0
- package/server/project-file-scan.ts +235 -0
- package/server/project-hmr-files.ts +215 -0
- package/server/project-install-roots.ts +210 -0
- package/server/project-kinds.ts +71 -0
- package/server/project-mcp-servers.ts +82 -0
- package/server/project-module-freshness.ts +109 -0
- package/server/project-module-instance.ts +375 -0
- package/server/project-optimize-deps-entries.ts +827 -0
- package/server/project-output-writer.ts +679 -0
- package/server/project-package-origin.ts +63 -0
- package/server/project-root-surface.ts +831 -0
- package/server/project-scratch-path.ts +47 -0
- package/server/project-script-hmr.ts +619 -0
- package/server/project-serving-plugins.ts +236 -0
- package/server/project-tools.ts +653 -0
- package/server/project-validation.ts +250 -0
- package/server/project-verbs.ts +127 -0
- package/server/project-view.ts +52 -0
- package/server/project-watch.ts +1134 -0
- package/server/project-work-coordinator.ts +288 -0
- package/server/provider-credentials.ts +331 -0
- package/server/recent-projects-store.ts +98 -0
- package/server/redact-secrets.ts +71 -0
- package/server/repository-presence.ts +267 -0
- package/server/routes/account.ts +357 -0
- package/server/routes/agents.ts +60 -0
- package/server/routes/assets.ts +154 -0
- package/server/routes/build.ts +13 -0
- package/server/routes/collaboration.ts +595 -0
- package/server/routes/configurations.ts +419 -0
- package/server/routes/context.ts +264 -0
- package/server/routes/control-plane.ts +1811 -0
- package/server/routes/logs.ts +272 -0
- package/server/routes/project-identity.ts +302 -0
- package/server/routes/project-open.ts +429 -0
- package/server/routes/project-source.ts +686 -0
- package/server/routes/project-state.ts +383 -0
- package/server/routes/relay.ts +1029 -0
- package/server/routes/route-helpers.ts +29 -0
- package/server/routes/served-modules.ts +138 -0
- package/server/routes/session-tabs.ts +196 -0
- package/server/routes/settings.ts +121 -0
- package/server/routes/share-control.ts +486 -0
- package/server/routes/themes.ts +116 -0
- package/server/routes/tools.ts +230 -0
- package/server/routes/worktrees.ts +595 -0
- package/server/scoped-game-css.ts +461 -0
- package/server/server-utils.ts +1194 -0
- package/server/session-product.ts +112 -0
- package/server/session-registry.ts +230 -0
- package/server/share-claims.ts +138 -0
- package/server/share-host.ts +526 -0
- package/server/share-session-gateway.ts +1362 -0
- package/server/share-tunnel.ts +123 -0
- package/server/spawn-opener.ts +74 -0
- package/server/support/play/log-format.ts +76 -0
- package/server/support/play/session-record.ts +199 -0
- package/server/support/project/build-discipline.ts +718 -0
- package/server/support/project/inspection-node.ts +119 -0
- package/server/support/project/log-naming.ts +54 -0
- package/server/support/project/provenance.ts +290 -0
- package/server/support/project/run-name.ts +18 -0
- package/server/support/project/session-journal.ts +830 -0
- package/server/support/project/shared.ts +327 -0
- package/server/tab-bootstrap.ts +62 -0
- package/server/tab-heartbeat.ts +477 -0
- package/server/tab-lifecycle.ts +550 -0
- package/server/tab-presence.ts +1508 -0
- package/server/team-agent-mirror.ts +95 -0
- package/server/twin-auth.ts +138 -0
- package/server/vendored-lock-recorder.ts +968 -0
- package/server/worktree-identity.ts +121 -0
- package/server/worktree-management.ts +398 -0
- package/server/worktree-retention.d.mts +13 -0
- package/server/worktree-retention.mjs +205 -0
- package/src/EditorContext.tsx +169 -0
- package/src/account.ts +333 -0
- package/src/action-registry.ts +532 -0
- package/src/active-product.ts +74 -0
- package/src/active-project.ts +155 -0
- package/src/adapter-editor-config.ts +25 -0
- package/src/adapter-observation.ts +49 -0
- package/src/animation/stage-transport.ts +379 -0
- package/src/animation/three-clips-subject.ts +172 -0
- package/src/api/asset-library-wire.ts +45 -0
- package/src/api/assets.ts +365 -0
- package/src/api/base.ts +10 -0
- package/src/api/build.ts +99 -0
- package/src/api/git-wire.ts +56 -0
- package/src/api/logs.ts +92 -0
- package/src/api/project-identity.ts +74 -0
- package/src/api/project-open.ts +355 -0
- package/src/api/project-source.ts +162 -0
- package/src/api/project-state.ts +107 -0
- package/src/api/relay.ts +268 -0
- package/src/api/settings.ts +36 -0
- package/src/api/themes.ts +45 -0
- package/src/api/worktrees.ts +257 -0
- package/src/asset-compare-core.ts +171 -0
- package/src/asset-compare.ts +294 -0
- package/src/asset-editor-context.tsx +100 -0
- package/src/asset-events.ts +97 -0
- package/src/asset-inspector-actions.ts +87 -0
- package/src/asset-preview-framing.ts +357 -0
- package/src/asset-preview.ts +2802 -0
- package/src/asset-selection-viewer-registry.ts +113 -0
- package/src/asset-selection.ts +133 -0
- package/src/asset-workflow/asset-capabilities.ts +344 -0
- package/src/asset-workflow/asset-import-jobs.ts +106 -0
- package/src/asset-workflow/asset-ledger-backend.ts +126 -0
- package/src/asset-workflow/asset-ledger.ts +156 -0
- package/src/asset-workflow/asset-materialization-report.ts +140 -0
- package/src/asset-workflow/asset-pack-manifest.ts +320 -0
- package/src/asset-workflow/asset-types.ts +142 -0
- package/src/asset-workflow/asset-workflow-quality.ts +61 -0
- package/src/asset-workflow/audio-preview-player.ts +193 -0
- package/src/asset-workflow/audio-waveform.ts +22 -0
- package/src/asset-workflow/cloud-asset-client.ts +263 -0
- package/src/asset-workflow/folder-preview.ts +345 -0
- package/src/asset-workflow/hosted-asset-materialization.ts +236 -0
- package/src/asset-workflow/image-view-scale.ts +32 -0
- package/src/asset-workflow/import-contract.ts +124 -0
- package/src/asset-workflow/ledger-write-lock.ts +244 -0
- package/src/asset-workflow/model-inspection.ts +818 -0
- package/src/asset-workflow/pixi-spritesheet.ts +197 -0
- package/src/asset-workflow/preview-resource-lifetime.ts +44 -0
- package/src/asset-workflow/project-asset-commands.ts +23 -0
- package/src/asset-workflow/project-asset-health.ts +139 -0
- package/src/asset-workflow/project-asset-operations.ts +154 -0
- package/src/asset-workflow/project-asset-roots.ts +68 -0
- package/src/asset-workflow/project-content.ts +288 -0
- package/src/asset-workflow/project-source-index.ts +550 -0
- package/src/asset-workflow/thumbnail-system.ts +256 -0
- package/src/authoring/active-adapter.ts +199 -0
- package/src/authoring/active-systems.ts +422 -0
- package/src/authoring/adapter-key.ts +18 -0
- package/src/authoring/authoring-asset-url.ts +27 -0
- package/src/authoring/bootstrap-state.ts +49 -0
- package/src/authoring/boundary-authoring-adapter.ts +184 -0
- package/src/authoring/breakpoint-state.ts +43 -0
- package/src/authoring/canvas-scene-guides.ts +76 -0
- package/src/authoring/component-instance-root.ts +171 -0
- package/src/authoring/composite-authoring-adapter.ts +2110 -0
- package/src/authoring/consumer-actions.ts +520 -0
- package/src/authoring/css-numeric-style.ts +97 -0
- package/src/authoring/design-time-layers.ts +849 -0
- package/src/authoring/design-time-mount-registry.ts +235 -0
- package/src/authoring/design-time-settle.ts +343 -0
- package/src/authoring/edit-mode-authoring.ts +619 -0
- package/src/authoring/eyedropper-session.ts +60 -0
- package/src/authoring/instance-source-menu-register.ts +13 -0
- package/src/authoring/instance-source-menu.ts +135 -0
- package/src/authoring/layered-pick.ts +183 -0
- package/src/authoring/live-gesture-lock.ts +50 -0
- package/src/authoring/live-object-transform.ts +62 -0
- package/src/authoring/mount-failure-report.ts +154 -0
- package/src/authoring/mounted-root-subjects.ts +144 -0
- package/src/authoring/no-authoring-adapter.ts +55 -0
- package/src/authoring/null-inspection-subjects.tsx +75 -0
- package/src/authoring/object3d-document-persistence.ts +106 -0
- package/src/authoring/object3d-document-session-registry.ts +120 -0
- package/src/authoring/object3d-document-session.ts +1326 -0
- package/src/authoring/object3d-gesture-controller.ts +113 -0
- package/src/authoring/panel-authoring.ts +121 -0
- package/src/authoring/prefab-instance-inspector-section.tsx +237 -0
- package/src/authoring/prefab-instance-section-model.ts +55 -0
- package/src/authoring/project-authoring-session.ts +105 -0
- package/src/authoring/provenance.ts +99 -0
- package/src/authoring/quarks-particle-systems.ts +19 -0
- package/src/authoring/react-canvas-navigation.ts +255 -0
- package/src/authoring/react-design-canvas-style.ts +20 -0
- package/src/authoring/react-story-board.ts +937 -0
- package/src/authoring/selection-scope.ts +195 -0
- package/src/authoring/shell-document-ops.ts +169 -0
- package/src/authoring/shell-object3d-document-write-policy.ts +108 -0
- package/src/authoring/shell-viewport-policy.ts +48 -0
- package/src/authoring/source-object3d-authoring-adapter.ts +526 -0
- package/src/authoring/stories-scope.ts +35 -0
- package/src/authoring/story-board-chrome-fit.ts +107 -0
- package/src/authoring/story-board-presentation.ts +111 -0
- package/src/authoring/three-projection-core.ts +226 -0
- package/src/authoring/viewport-pick-context.ts +40 -0
- package/src/authoring/viewport-raycast.ts +240 -0
- package/src/authoring/viewport-tool-context.ts +73 -0
- package/src/authoring/world-canvas-viewport-state.ts +35 -0
- package/src/authoring/world-hidden-viewport.ts +152 -0
- package/src/authoring/world-pan-state.ts +198 -0
- package/src/authoring/world-session-state.ts +101 -0
- package/src/authoring/write-pipe.ts +173 -0
- package/src/availability-tick.ts +66 -0
- package/src/bitmap-label.ts +120 -0
- package/src/blender-tab-metrics.ts +161 -0
- package/src/board-open-actions.ts +20 -0
- package/src/boot-routing.ts +391 -0
- package/src/build-identity.ts +15 -0
- package/src/bytes-codec.ts +62 -0
- package/src/camera-authoring.ts +175 -0
- package/src/cancellation-reason.ts +58 -0
- package/src/canvas-preview-frames.ts +482 -0
- package/src/capture-camera-pose.ts +77 -0
- package/src/chrome-registry.ts +159 -0
- package/src/chrome-slot-registry.ts +91 -0
- package/src/collaboration-client.ts +264 -0
- package/src/collaboration-presence.ts +41 -0
- package/src/command-dispatch.ts +19 -0
- package/src/command-listener.ts +2743 -0
- package/src/command-registry.ts +70 -0
- package/src/component-board-registry.ts +205 -0
- package/src/component-states-registry.ts +200 -0
- package/src/components/AgentPresentationNotice.tsx +75 -0
- package/src/components/AlignToolbar.tsx +204 -0
- package/src/components/AppRoot.tsx +394 -0
- package/src/components/ApplicationMenus.tsx +415 -0
- package/src/components/AssetBrowser.tsx +2843 -0
- package/src/components/AssetEditorShell.tsx +216 -0
- package/src/components/AssetInspectorToolSection.tsx +124 -0
- package/src/components/BoardRulers.tsx +354 -0
- package/src/components/CameraInfo.tsx +81 -0
- package/src/components/CanvasSceneViewport.tsx +556 -0
- package/src/components/CapabilityCoverageSection.tsx +185 -0
- package/src/components/CenterDocuments.tsx +22 -0
- package/src/components/ChromeSlot.tsx +20 -0
- package/src/components/CodeView.tsx +470 -0
- package/src/components/CollaborationHeaderControl.css +74 -0
- package/src/components/CompactInspectorCard.tsx +190 -0
- package/src/components/CompactInspectorShell.tsx +39 -0
- package/src/components/ConsolePanel.css +55 -0
- package/src/components/ConsolePanel.tsx +270 -0
- package/src/components/DefaultEditorLayout.tsx +106 -0
- package/src/components/DocumentHeaderStrip.tsx +96 -0
- package/src/components/DocumentShelfRail.tsx +45 -0
- package/src/components/DocumentThumbnail.tsx +345 -0
- package/src/components/EditorLeaseGuard.tsx +372 -0
- package/src/components/ErrorBanner.tsx +123 -0
- package/src/components/FolderPreviewTile.tsx +159 -0
- package/src/components/GameHierarchy.tsx +3842 -0
- package/src/components/GameplaySessionTimeline.tsx +295 -0
- package/src/components/InspectionProjection.tsx +968 -0
- package/src/components/Inspector.tsx +233 -0
- package/src/components/InspectorCanvasPreview.tsx +35 -0
- package/src/components/InspectorFieldsSection.tsx +290 -0
- package/src/components/InspectorObjectPreview.tsx +57 -0
- package/src/components/InspectorStoriesSection.tsx +92 -0
- package/src/components/InspectorToolSection.tsx +96 -0
- package/src/components/InspectorTransformSection.tsx +245 -0
- package/src/components/LightExplorerPanel.tsx +433 -0
- package/src/components/MediaProperties.tsx +145 -0
- package/src/components/NonThreeAuthoringBootstrap.tsx +19 -0
- package/src/components/Object3DDocumentToolbar.css +100 -0
- package/src/components/Object3DDocumentToolbar.tsx +454 -0
- package/src/components/Object3DDocumentViewport.tsx +58 -0
- package/src/components/ProjectHeader.css +617 -0
- package/src/components/ProjectHeader.tsx +328 -0
- package/src/components/ProjectLayout.tsx +249 -0
- package/src/components/ReactCanvasControls.tsx +284 -0
- package/src/components/RootSelectionOverlay.tsx +3162 -0
- package/src/components/RootTextEditor.tsx +79 -0
- package/src/components/SaveStatus.tsx +70 -0
- package/src/components/StageHost.tsx +1954 -0
- package/src/components/StageOverlays.tsx +21 -0
- package/src/components/StartupErrorScreen.tsx +76 -0
- package/src/components/StartupLoadingScreen.tsx +65 -0
- package/src/components/StatsOverlay.tsx +78 -0
- package/src/components/SurfaceStateOverlay.tsx +24 -0
- package/src/components/ToolContributionSurfaces.tsx +65 -0
- package/src/components/ToolHost.tsx +370 -0
- package/src/components/ToolObject3DPreview.tsx +39 -0
- package/src/components/Toolbar.tsx +595 -0
- package/src/components/TransientHint.tsx +44 -0
- package/src/components/TransportStrip.tsx +174 -0
- package/src/components/VersionControlSection.tsx +470 -0
- package/src/components/VgaiLogo.css +83 -0
- package/src/components/VgaiLogo.tsx +35 -0
- package/src/components/ViewportControlsHint.tsx +60 -0
- package/src/components/ViewportFurniture.tsx +401 -0
- package/src/components/ViewportOverlay.tsx +145 -0
- package/src/components/ViewportOverlaysMenu.tsx +153 -0
- package/src/components/ViewportShadingMenu.tsx +300 -0
- package/src/components/ViewportViewMenu.tsx +101 -0
- package/src/components/WorkspaceDocumentSurface.tsx +204 -0
- package/src/components/WorkspaceUtilitySurface.tsx +22 -0
- package/src/components/WorktreeSwitcher.css +239 -0
- package/src/components/WorktreeSwitcher.tsx +890 -0
- package/src/components/account-documents.tsx +1162 -0
- package/src/components/asset-documents.tsx +812 -0
- package/src/components/asset-editor-persistence.ts +216 -0
- package/src/components/asset-selection-section.tsx +535 -0
- package/src/components/asset-thumbnails.tsx +312 -0
- package/src/components/asset-viewers/AudioViewer.tsx +201 -0
- package/src/components/asset-viewers/EntityModelDocument.tsx +122 -0
- package/src/components/asset-viewers/EnvironmentAssetDocument.tsx +440 -0
- package/src/components/asset-viewers/GenericJsonViewer.tsx +102 -0
- package/src/components/asset-viewers/ImageViewer.tsx +300 -0
- package/src/components/asset-viewers/JsonAssetDocument.tsx +93 -0
- package/src/components/asset-viewers/LiveModuleDocument.tsx +417 -0
- package/src/components/asset-viewers/LutAssetDocument.tsx +444 -0
- package/src/components/asset-viewers/ModelAssetDocument.tsx +105 -0
- package/src/components/asset-viewers/Object3DPreview.tsx +359 -0
- package/src/components/asset-viewers/OnlineAssetDetail.tsx +421 -0
- package/src/components/asset-viewers/PasteboardModuleDocument.tsx +67 -0
- package/src/components/asset-viewers/QuarksAssetDocument.tsx +526 -0
- package/src/components/asset-viewers/ShaderAssetDocument.tsx +743 -0
- package/src/components/asset-viewers/SourceAssetViewer.tsx +281 -0
- package/src/components/asset-viewers/SpritesheetSpriteView.tsx +102 -0
- package/src/components/asset-viewers/VideoViewer.tsx +101 -0
- package/src/components/asset-viewers/shader-source.ts +144 -0
- package/src/components/asset-workflow.css +731 -0
- package/src/components/board-guides.ts +150 -0
- package/src/components/compact-inspector.css +539 -0
- package/src/components/core-utilities.tsx +90 -0
- package/src/components/editor-notifications.css +40 -0
- package/src/components/engine-workspace.css +274 -0
- package/src/components/inspector-preview-section.tsx +238 -0
- package/src/components/inspector-property-grouping.ts +64 -0
- package/src/components/inspector-revert-label.ts +20 -0
- package/src/components/inspector-selection.ts +42 -0
- package/src/components/inspector-stories-gating.ts +171 -0
- package/src/components/inspector-transform-subject.ts +11 -0
- package/src/components/inspector-transform.ts +75 -0
- package/src/components/kind-documents.tsx +500 -0
- package/src/components/palette-action-publisher.tsx +140 -0
- package/src/components/primitives/DraftColorInput.tsx +74 -0
- package/src/components/product-shell.css +1829 -0
- package/src/components/project-tool-documents.tsx +410 -0
- package/src/components/scene-documents.tsx +223 -0
- package/src/components/stage-keyboard.tsx +37 -0
- package/src/components/stage-overlay-set.tsx +107 -0
- package/src/components/stage-presence-markers.ts +478 -0
- package/src/components/standard-viewport-dressing.ts +417 -0
- package/src/components/status-contributions.tsx +403 -0
- package/src/components/tool-documents.tsx +309 -0
- package/src/components/tool-schema-form.tsx +262 -0
- package/src/components/use-after-paint.ts +41 -0
- package/src/components/use-project-image-assets.ts +86 -0
- package/src/components/viewport-header-controls.css +90 -0
- package/src/components/viewport-surface-status.tsx +55 -0
- package/src/components/workspace-history.ts +32 -0
- package/src/components/workspace-static-panel-registry.tsx +152 -0
- package/src/components/workspace-surfaces.css +621 -0
- package/src/components/world-documents.tsx +586 -0
- package/src/components/world-overlay-gestures.ts +1694 -0
- package/src/composite-screenshot.ts +1641 -0
- package/src/console-sync.ts +131 -0
- package/src/constraint-helper.ts +338 -0
- package/src/content-entry-source-registry.ts +184 -0
- package/src/coverage/authoring-seam-evidence.ts +300 -0
- package/src/coverage/canvas-reveal.ts +192 -0
- package/src/coverage/design-time-surfaces.ts +101 -0
- package/src/coverage/live-seam-evidence.ts +11 -0
- package/src/coverage/ontology-invariants.ts +466 -0
- package/src/coverage/session-vitals.ts +501 -0
- package/src/coverage/system-seam-evidence.ts +72 -0
- package/src/crash-null-boundary.ts +36 -0
- package/src/creation-site-edit.ts +1479 -0
- package/src/creation-site-registry.ts +160 -0
- package/src/delegate-harness-registry.ts +143 -0
- package/src/document-context-registry.ts +177 -0
- package/src/document-open-registry.ts +200 -0
- package/src/document-preview-source.ts +20 -0
- package/src/document-renderer-session.ts +138 -0
- package/src/editor-api.ts +46 -0
- package/src/editor-chrome-capture.ts +139 -0
- package/src/editor-commands.ts +164 -0
- package/src/editor-console.ts +563 -0
- package/src/editor-current-view.ts +82 -0
- package/src/editor-document-probe.ts +881 -0
- package/src/editor-git-client.ts +115 -0
- package/src/editor-host-door.ts +462 -0
- package/src/editor-hotkeys.ts +842 -0
- package/src/editor-lease-view.ts +39 -0
- package/src/editor-lease.ts +415 -0
- package/src/editor-mode.ts +19 -0
- package/src/editor-notifications.ts +140 -0
- package/src/editor-presence.ts +563 -0
- package/src/editor-presentation-activity.ts +50 -0
- package/src/editor-presentation-notice.ts +42 -0
- package/src/editor-runtime.tsx +145 -0
- package/src/editor-server-response.ts +86 -0
- package/src/editor-session-attribution.ts +75 -0
- package/src/editor-session-mode.ts +54 -0
- package/src/editor-shell-store.ts +1304 -0
- package/src/editor-state-facets.ts +74 -0
- package/src/editor-styles.css +33 -0
- package/src/editor-view-presentation.ts +810 -0
- package/src/editor-viewport.ts +5302 -0
- package/src/entity-lod.ts +31 -0
- package/src/entity-object.ts +91 -0
- package/src/files/file-provider.ts +62 -0
- package/src/files/project-files.ts +264 -0
- package/src/finders/index.ts +136 -0
- package/src/finders/scenes-from-entrypoint-selection.ts +387 -0
- package/src/frame/bridge.tsx +1408 -0
- package/src/frame/product.ts +77 -0
- package/src/gameplay-dom-recording.ts +319 -0
- package/src/gameplay-export-state.ts +14 -0
- package/src/gameplay-replay.ts +417 -0
- package/src/gameplay-session-time.ts +9 -0
- package/src/gameplay-sessions.ts +204 -0
- package/src/harness-chat-types.ts +253 -0
- package/src/hierarchy-component-marks.ts +298 -0
- package/src/hierarchy-drop.ts +91 -0
- package/src/hierarchy-expansion-state.ts +80 -0
- package/src/hierarchy-header-slot.ts +52 -0
- package/src/hierarchy-internals.ts +197 -0
- package/src/hierarchy-kind-icon.ts +217 -0
- package/src/hierarchy-mark-reader.ts +73 -0
- package/src/hierarchy-menu-registry.ts +67 -0
- package/src/hierarchy-node-rows.ts +307 -0
- package/src/hierarchy-panel-view.ts +280 -0
- package/src/hierarchy-projection.ts +76 -0
- package/src/hierarchy-row-cache.ts +243 -0
- package/src/hierarchy-row-model.ts +308 -0
- package/src/hierarchy-rows.ts +11 -0
- package/src/hierarchy-walk.ts +86 -0
- package/src/history/editor-session.ts +25 -0
- package/src/history/history-commands.ts +147 -0
- package/src/history/history-delegate.ts +163 -0
- package/src/history/history-limit-notices.ts +43 -0
- package/src/history/history-service.ts +1173 -0
- package/src/history/persistence-coordinator.ts +35 -0
- package/src/history/project-file-history.ts +386 -0
- package/src/history/project-root-history-backends.ts +139 -0
- package/src/history/resource-registry.ts +209 -0
- package/src/history/snapshot-store.ts +103 -0
- package/src/history/source-history-backend.ts +546 -0
- package/src/history/types.ts +124 -0
- package/src/hmr-registration-group.ts +67 -0
- package/src/hmr-stable-react-context.ts +23 -0
- package/src/hotkeys.ts +188 -0
- package/src/inference-diagnostics.ts +69 -0
- package/src/initial-project.ts +80 -0
- package/src/inspection/active-subject.ts +578 -0
- package/src/inspection/active-surface.ts +142 -0
- package/src/inspection/compose.ts +1064 -0
- package/src/inspection/display.ts +170 -0
- package/src/inspection/document-subject.ts +109 -0
- package/src/inspection/game-subject.ts +85 -0
- package/src/inspection/model.ts +542 -0
- package/src/inspection/null-subject.ts +115 -0
- package/src/inspection/serialize.ts +357 -0
- package/src/inspection/use-active-inspection.ts +180 -0
- package/src/inspector-presentation.ts +201 -0
- package/src/inspector-section-registry.ts +221 -0
- package/src/instance-source-actions.ts +163 -0
- package/src/instanced-presentation.ts +164 -0
- package/src/js-heap.ts +71 -0
- package/src/key-actions.ts +91 -0
- package/src/keymap-presets.ts +401 -0
- package/src/layout-policy.ts +31 -0
- package/src/learn-links.ts +73 -0
- package/src/light-explorer-model.ts +134 -0
- package/src/live-canvas-frame.ts +55 -0
- package/src/live-document.ts +279 -0
- package/src/live-module-source.ts +230 -0
- package/src/live-session-registry.ts +220 -0
- package/src/live-transition.ts +633 -0
- package/src/manifest-project.ts +107 -0
- package/src/model-thumbnail.ts +523 -0
- package/src/native-selection-style.ts +202 -0
- package/src/object3d-document-write-policy.ts +137 -0
- package/src/packaged-runtime.ts +108 -0
- package/src/palettes/maya.palette.json +57 -0
- package/src/palettes/substance.palette.json +57 -0
- package/src/pasteboard-module.ts +81 -0
- package/src/performance-profiler.ts +367 -0
- package/src/performance-sources.ts +69 -0
- package/src/play-boot-phase.ts +145 -0
- package/src/presentation-surface.ts +248 -0
- package/src/project-adapter.ts +1143 -0
- package/src/project-asset-refresh.ts +26 -0
- package/src/project-declaration-refresh.ts +31 -0
- package/src/project-local-state.ts +118 -0
- package/src/project-manager.ts +243 -0
- package/src/project-module-changes.ts +163 -0
- package/src/project-module-split.ts +266 -0
- package/src/project-provenance.ts +115 -0
- package/src/project-ready.ts +42 -0
- package/src/project-session-reset.ts +67 -0
- package/src/project-shape.ts +68 -0
- package/src/project-tool-discovery.ts +66 -0
- package/src/project-tools.ts +107 -0
- package/src/project-work-types.ts +149 -0
- package/src/projection/three.ts +898 -0
- package/src/projection/types.ts +44 -0
- package/src/readiness.ts +113 -0
- package/src/reflection-probe-helper.ts +142 -0
- package/src/reported-play-state.ts +90 -0
- package/src/resolve-relative-specifier.ts +33 -0
- package/src/scene-document-plan.ts +315 -0
- package/src/scene-framing.ts +315 -0
- package/src/scene-live-open.ts +210 -0
- package/src/scene-view-fog.ts +89 -0
- package/src/scoped-game-css.ts +152 -0
- package/src/session-orphan-record.ts +193 -0
- package/src/session-tombstone.ts +126 -0
- package/src/settings/settings-provider.ts +82 -0
- package/src/settings-store.ts +345 -0
- package/src/shared-view-restore.ts +42 -0
- package/src/shell-store-door.ts +45 -0
- package/src/source-conflict.ts +122 -0
- package/src/spatial-handle-visuals.ts +332 -0
- package/src/stage-context.ts +341 -0
- package/src/stage-store-registry.ts +63 -0
- package/src/stale-chunk-recovery.ts +34 -0
- package/src/state-report-deferral.ts +73 -0
- package/src/storage/host-files-storage.ts +97 -0
- package/src/storage/http-storage.ts +174 -0
- package/src/storage/index.ts +75 -0
- package/src/storage/mem-storage.ts +149 -0
- package/src/storage/path-lock.ts +44 -0
- package/src/storage/paths.ts +26 -0
- package/src/storage/types.ts +116 -0
- package/src/stories/StoryComponentThumbnail.tsx +184 -0
- package/src/stories/StoryPreviewMount.tsx +306 -0
- package/src/stories/component-content-source.tsx +106 -0
- package/src/stories/component-states-source.ts +78 -0
- package/src/stories/compose-project-stories.ts +255 -0
- package/src/stories/pixi-story-model.ts +30 -0
- package/src/stories/prefabs-finder.ts +54 -0
- package/src/stories/prefabs-from-stories.ts +182 -0
- package/src/stories/project-story-discovery.ts +78 -0
- package/src/stories/project-story-regions.ts +24 -0
- package/src/stories/story-actions.ts +54 -0
- package/src/stories/story-capture-command.ts +124 -0
- package/src/stories/story-capture.ts +584 -0
- package/src/stories/story-declared-medium.ts +126 -0
- package/src/stories/story-discovery.ts +176 -0
- package/src/stories/story-document-openers.ts +36 -0
- package/src/stories/story-dom-runtime.ts +78 -0
- package/src/stories/story-grouping.ts +111 -0
- package/src/stories/story-lane.ts +88 -0
- package/src/stories/story-mount-turn.ts +27 -0
- package/src/stories/story-opener.ts +260 -0
- package/src/stories/story-pixi-preview.ts +408 -0
- package/src/stories/story-presentation.ts +215 -0
- package/src/stories/story-registry.ts +517 -0
- package/src/stories/story-three-preview.ts +807 -0
- package/src/stories/three-story-model.ts +96 -0
- package/src/story-three-preview-runtime.ts +56 -0
- package/src/surface-keyboard.ts +112 -0
- package/src/surface-state.ts +124 -0
- package/src/tab-bootstrap.js +628 -0
- package/src/tab-census.ts +198 -0
- package/src/tab-lifecycle-client.ts +196 -0
- package/src/theme-library.ts +844 -0
- package/src/theme-preference.ts +378 -0
- package/src/theme.css +3437 -0
- package/src/three-viewport/bone-selection-highlight.ts +119 -0
- package/src/three-viewport/camera-fit.ts +41 -0
- package/src/three-viewport/interactive-renderer.ts +132 -0
- package/src/three-viewport/selection-brackets.ts +310 -0
- package/src/three-viewport/selection-outline.ts +183 -0
- package/src/three-viewport/skeleton-helper.ts +61 -0
- package/src/three-viewport/source-color.ts +167 -0
- package/src/three-viewport/studio-environment.ts +96 -0
- package/src/three-viewport-presentation.ts +23 -0
- package/src/tool-contribution-play.ts +74 -0
- package/src/tool-loader.ts +1798 -0
- package/src/transform-mode-request.ts +57 -0
- package/src/transient-hint.ts +78 -0
- package/src/trigger-volume-helper.ts +116 -0
- package/src/ui-source/adapter-region-includes.ts +241 -0
- package/src/ui-source/ensure-import.ts +132 -0
- package/src/ui-source/file-region-resolver.ts +302 -0
- package/src/ui-source/inspect.ts +775 -0
- package/src/ui-source/oid-transform.ts +1845 -0
- package/src/ui-source/plan-csf-story.ts +196 -0
- package/src/ui-source/plan-extract-component.ts +421 -0
- package/src/ui-source/plan-fork-component.ts +621 -0
- package/src/ui-source/plan-named-style.ts +95 -0
- package/src/ui-source/plan-source-edit.ts +353 -0
- package/src/ui-source/r3f-contract-resolver.ts +327 -0
- package/src/ui-source/r3f-diagnostic-index.ts +165 -0
- package/src/ui-source/r3f-environment-binding.ts +133 -0
- package/src/ui-source/r3f-joint-binding.ts +251 -0
- package/src/ui-source/r3f-lod-binding.ts +91 -0
- package/src/ui-source/r3f-particle-binding.ts +235 -0
- package/src/ui-source/r3f-physics-binding.ts +483 -0
- package/src/ui-source/r3f-project-contracts.ts +444 -0
- package/src/ui-source/relative-import-specifier.ts +34 -0
- package/src/ui-source/reparent-guard.ts +544 -0
- package/src/ui-source/source-edit-request.ts +97 -0
- package/src/ui-source/source-write-backend.ts +618 -0
- package/src/ui-source/syntactic-prop-specs.ts +296 -0
- package/src/ui-source/tier-source-write-backend.ts +279 -0
- package/src/ui-source/ts-ast.ts +171 -0
- package/src/ui-source/utility-class-support.ts +169 -0
- package/src/ui-source/write-component-default.ts +133 -0
- package/src/ui-source/writer.ts +1989 -0
- package/src/viewport-activation-timings.ts +840 -0
- package/src/viewport-authoring-policy.ts +186 -0
- package/src/viewport-controls-hint.ts +57 -0
- package/src/viewport-door.ts +237 -0
- package/src/viewport-shading-boundary.ts +12 -0
- package/src/vite-error-surface.ts +141 -0
- package/src/wait-until.ts +37 -0
- package/src/workspace-areas.ts +156 -0
- package/src/workspace-aux-commands.ts +11 -0
- package/src/workspace-available-documents.ts +127 -0
- package/src/workspace-core-utilities.ts +31 -0
- package/src/workspace-document-ids.ts +59 -0
- package/src/workspace-document-registry.ts +612 -0
- package/src/workspace-document-restore.ts +145 -0
- package/src/workspace-host-commands.ts +141 -0
- package/src/workspace-persistence-gate.ts +40 -0
- package/src/workspace-play-utilities.ts +44 -0
- package/src/workspace-presets.ts +425 -0
- package/src/workspace-regions.ts +294 -0
- package/src/workspace-state-persistence.ts +536 -0
- package/src/workspace-static-panels.ts +73 -0
- package/src/workspace-status-registry.ts +121 -0
- package/src/workspace-style.ts +239 -0
- package/src/workspace-utility-commands.ts +74 -0
- package/src/workspace-utility-registry.ts +263 -0
- package/src/workspace-viewport-rect.ts +97 -0
- package/src/world-adoption.ts +115 -0
- package/src/world-document-routing.ts +104 -0
- package/vite-plugin-creation-site-write.ts +184 -0
- package/vite-plugin-creation-site.ts +80 -0
- package/vite-plugin-game-static.ts +303 -0
- package/vite-plugin-module-doorways.ts +336 -0
- package/vite-plugin-product-contributions.ts +197 -0
- package/vite-plugin-project-game-static.ts +125 -0
- package/vite-plugin-project-jsx-js.ts +65 -0
- package/vite-plugin-project-root-absolute-assets.ts +359 -0
- package/vite-plugin-shared-react.ts +420 -0
- package/vite-plugin-shared-three.ts +203 -0
- package/vite-plugin-ui-oid.ts +2106 -0
|
@@ -0,0 +1,444 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Project-local R3F component contract discovery.
|
|
3
|
+
*
|
|
4
|
+
* This deliberately follows ordinary TypeScript/React modules instead of
|
|
5
|
+
* asking game source to register components with vgai. Relative imports,
|
|
6
|
+
* named/default exports, aliases, and re-exports are enough for the editor to
|
|
7
|
+
* understand the shared-component shape coding models normally produce.
|
|
8
|
+
* External packages remain conservative: vgai never guesses at their runtime
|
|
9
|
+
* scene ownership.
|
|
10
|
+
*/
|
|
11
|
+
import { existsSync, readFileSync, statSync } from 'node:fs';
|
|
12
|
+
import { dirname, extname, resolve } from 'node:path';
|
|
13
|
+
import ts from 'typescript';
|
|
14
|
+
import {
|
|
15
|
+
isBuiltinR3fContract,
|
|
16
|
+
type R3fAuthoringDiagnostic,
|
|
17
|
+
type R3fComponentContract,
|
|
18
|
+
type R3fTypeAlias,
|
|
19
|
+
runtimeMotionRefs,
|
|
20
|
+
} from './oid-transform';
|
|
21
|
+
import {
|
|
22
|
+
type ContractHost,
|
|
23
|
+
type ModuleAnalysis,
|
|
24
|
+
ProjectContractResolver,
|
|
25
|
+
} from './r3f-contract-resolver';
|
|
26
|
+
import { parseAuthoringTsx } from './ts-ast';
|
|
27
|
+
|
|
28
|
+
/** Re-exported from its declaration site. The type moved to `oid-transform.ts`
|
|
29
|
+
* (browser-safe, no `node:fs`) when H5 made a diagnostic travel on an
|
|
30
|
+
* `OidEntry`; this module still PRODUCES them, and remains the import site
|
|
31
|
+
* every existing caller already uses. */
|
|
32
|
+
export type { R3fAuthoringDiagnostic };
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* THE ON-DISK HALF OF THE WALK, CACHED ACROSS CALLS — stamped by the file's
|
|
36
|
+
* own bytes, so it still "naturally tracks the latest bytes on disk without a
|
|
37
|
+
* cache invalidation protocol" (the property the fresh-resolver-per-call rule
|
|
38
|
+
* below exists to keep), while no longer re-deriving the same unchanged module
|
|
39
|
+
* once per importer.
|
|
40
|
+
*
|
|
41
|
+
* WHY IT HAD TO EXIST. `uiOidPlugin`'s `transform` builds one resolver per
|
|
42
|
+
* MODULE TRANSFORM (`vite-plugin-ui-oid.ts`, `importedR3fContracts(code,
|
|
43
|
+
* clean)`), and each resolver walks that module's whole transitive
|
|
44
|
+
* RELATIVE-import closure with `ts.createSourceFile`. The per-resolver cache
|
|
45
|
+
* therefore only ever helped inside one file's walk and was thrown away
|
|
46
|
+
* immediately after, so a project's shared modules were re-parsed once per
|
|
47
|
+
* importer — quadratic in the shared-component fan-in, and invisible on a
|
|
48
|
+
* small project. Measured on an imported 3D FPS project port (528 source files,
|
|
49
|
+
* ~200 project modules served during one editor boot), V8 CPU profile of the
|
|
50
|
+
* dev server across the whole ready -> page-bound window: **46.9s of 72.7s
|
|
51
|
+
* sampled (64.5%) inside `typescript.js`**, entered from here and from
|
|
52
|
+
* `oid-transform.ts`. The server's event loop was blocked ~80-90% of every
|
|
53
|
+
* 5s bucket for two minutes, which is why a static `editor-mark.svg` took
|
|
54
|
+
* 38s to serve and the browser's own module waterfall could not start.
|
|
55
|
+
*
|
|
56
|
+
* THE STAMP IS TAKEN TWICE, AROUND THE READ. A single stat cannot tell a
|
|
57
|
+
* concurrent save from a quiet file: stat-then-read caches new bytes under an
|
|
58
|
+
* old stamp, read-then-stat caches old bytes under a new one, and either way
|
|
59
|
+
* the entry is stale FOREVER because its stamp looks current. Only a
|
|
60
|
+
* before/after pair that AGREES proves nothing was written across the read;
|
|
61
|
+
* a disagreeing pair is simply not cached (the analysis is still returned).
|
|
62
|
+
*/
|
|
63
|
+
const analysisByFile = new Map<string, { stamp: string; analysis: ModuleAnalysis }>();
|
|
64
|
+
/** Bound: a dev session may open many projects, and nothing else evicts. */
|
|
65
|
+
const MAX_CACHED_ANALYSES = 4096;
|
|
66
|
+
|
|
67
|
+
function fileStamp(file: string): string | null {
|
|
68
|
+
try {
|
|
69
|
+
const stat = statSync(file);
|
|
70
|
+
return `${stat.mtimeMs}:${stat.size}`;
|
|
71
|
+
} catch {
|
|
72
|
+
return null;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/** The dev server's host: `node:fs` reads, `node:path` joins, and the
|
|
77
|
+
* stamp-checked shared cache described above. */
|
|
78
|
+
const nodeContractHost: ContractHost = {
|
|
79
|
+
read(file) {
|
|
80
|
+
try {
|
|
81
|
+
return readFileSync(file, 'utf8');
|
|
82
|
+
} catch {
|
|
83
|
+
return null;
|
|
84
|
+
}
|
|
85
|
+
},
|
|
86
|
+
exists: (file) => existsSync(file),
|
|
87
|
+
resolve: (fromFile, specifier) => resolve(dirname(fromFile), specifier),
|
|
88
|
+
extname: (file) => extname(file),
|
|
89
|
+
join: (base, name) => resolve(base, name),
|
|
90
|
+
analyzeFileCached(file, analyze) {
|
|
91
|
+
const shared = analysisByFile.get(file);
|
|
92
|
+
const before = fileStamp(file);
|
|
93
|
+
if (shared && before !== null && shared.stamp === before) return shared.analysis;
|
|
94
|
+
const analysis = analyze();
|
|
95
|
+
// Only a stamp that is unchanged ACROSS the read describes these bytes.
|
|
96
|
+
if (before !== null && fileStamp(file) === before) {
|
|
97
|
+
if (analysisByFile.size >= MAX_CACHED_ANALYSES) analysisByFile.clear();
|
|
98
|
+
analysisByFile.set(file, { stamp: before, analysis });
|
|
99
|
+
}
|
|
100
|
+
return analysis;
|
|
101
|
+
},
|
|
102
|
+
};
|
|
103
|
+
|
|
104
|
+
function newResolver(): ProjectContractResolver {
|
|
105
|
+
return new ProjectContractResolver(nodeContractHost);
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/** Resolve the contracts of component identifiers imported into one source
|
|
109
|
+
* module. A fresh resolver per call makes save/HMR behavior naturally track
|
|
110
|
+
* the latest bytes on disk without a cache invalidation protocol; the walk's
|
|
111
|
+
* on-disk half reuses {@link analysisByFile}, which keeps that property by
|
|
112
|
+
* stamping every entry with the bytes it was derived from. */
|
|
113
|
+
export function importedR3fContracts(
|
|
114
|
+
code: string,
|
|
115
|
+
file: string,
|
|
116
|
+
): Map<string, R3fComponentContract> {
|
|
117
|
+
return newResolver().importedForSource(code, file);
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/** The prop-shape type aliases one module's relative imports bring into
|
|
121
|
+
* scope, under their local names — the alias half of `importedR3fContracts`,
|
|
122
|
+
* and the other input `transformSource` needs to read a shared prop shape. */
|
|
123
|
+
export function importedR3fTypeAliases(code: string, file: string): Map<string, R3fTypeAlias> {
|
|
124
|
+
return newResolver().typeAliasesForSource(code, file);
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
/** All local and imported component bindings visible to one module. Used by
|
|
128
|
+
* the live index endpoint to refresh metadata after a shared component HMRs. */
|
|
129
|
+
export function visibleR3fContracts(code: string, file: string): Map<string, R3fComponentContract> {
|
|
130
|
+
return newResolver().analyzeSource(code, file).visible;
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
/**
|
|
134
|
+
* The component a `default` export names, when the export is
|
|
135
|
+
* `export default World` or `export default function World() {…}`.
|
|
136
|
+
*
|
|
137
|
+
* A three root's entry module default-exports its component (D26,
|
|
138
|
+
* `r3fRootFactory`) — the same contract dom roots use. That component IS the
|
|
139
|
+
* adapter root, so the single-spatial-root rule must not fire on it: a world
|
|
140
|
+
* legitimately returns a fragment of lights, scenery and players.
|
|
141
|
+
*/
|
|
142
|
+
function defaultExportedComponent(sf: ts.SourceFile): string | null {
|
|
143
|
+
let name: string | null = null;
|
|
144
|
+
const visit = (node: ts.Node): void => {
|
|
145
|
+
if (name) return;
|
|
146
|
+
if (ts.isExportAssignment(node) && !node.isExportEquals) {
|
|
147
|
+
if (ts.isIdentifier(node.expression)) name = node.expression.text;
|
|
148
|
+
} else if (
|
|
149
|
+
ts.isFunctionDeclaration(node) &&
|
|
150
|
+
node.name &&
|
|
151
|
+
node.modifiers?.some((m) => m.kind === ts.SyntaxKind.DefaultKeyword)
|
|
152
|
+
) {
|
|
153
|
+
name = node.name.text;
|
|
154
|
+
}
|
|
155
|
+
ts.forEachChild(node, visit);
|
|
156
|
+
};
|
|
157
|
+
visit(sf);
|
|
158
|
+
return name;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
function locationOf(sf: ts.SourceFile, node: ts.Node): { line: number; col: number } {
|
|
162
|
+
const location = sf.getLineAndCharacterOfPosition(node.getStart(sf));
|
|
163
|
+
return { line: location.line + 1, col: location.character };
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
function componentNameOfFunction(node: ts.SignatureDeclaration): string | null {
|
|
167
|
+
if (node.name && ts.isIdentifier(node.name)) return node.name.text;
|
|
168
|
+
const parent = node.parent;
|
|
169
|
+
return ts.isVariableDeclaration(parent) && ts.isIdentifier(parent.name) ? parent.name.text : null;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
/** Return the component whose direct return value is `element`; nested visual
|
|
173
|
+
* children intentionally return null. */
|
|
174
|
+
// biome-ignore lint/complexity/noExcessiveCognitiveComplexity: this is a bounded parent-chain type dispatcher over TypeScript syntax.
|
|
175
|
+
function returnedRootComponent(element: ts.JsxElement | ts.JsxSelfClosingElement): string | null {
|
|
176
|
+
let cursor: ts.Node | undefined = element.parent;
|
|
177
|
+
while (cursor) {
|
|
178
|
+
if (ts.isJsxElement(cursor) || ts.isJsxFragment(cursor)) return null;
|
|
179
|
+
if (ts.isReturnStatement(cursor)) {
|
|
180
|
+
let owner: ts.Node | undefined = cursor.parent;
|
|
181
|
+
while (owner && !ts.isFunctionLike(owner)) owner = owner.parent;
|
|
182
|
+
return owner && ts.isFunctionLike(owner) ? componentNameOfFunction(owner) : null;
|
|
183
|
+
}
|
|
184
|
+
if (ts.isArrowFunction(cursor) && cursor.body === element) {
|
|
185
|
+
return componentNameOfFunction(cursor);
|
|
186
|
+
}
|
|
187
|
+
if (ts.isFunctionLike(cursor)) return null;
|
|
188
|
+
cursor = cursor.parent;
|
|
189
|
+
}
|
|
190
|
+
return null;
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
/**
|
|
194
|
+
* R3F002's subject: a component with one native root that does not route every
|
|
195
|
+
* authored transform channel to it.
|
|
196
|
+
*
|
|
197
|
+
* A simulation-owned root is NOT that (FX-9/PD-11). The component's own source
|
|
198
|
+
* already says who writes the transform — it takes no transform prop and drives
|
|
199
|
+
* its root ref every frame — so asking it to "keep instances movable" asks for
|
|
200
|
+
* an authored placement the next tick overwrites. The warning was permanent and
|
|
201
|
+
* unactionable on exactly the components (prey, projectiles, anything mapped
|
|
202
|
+
* over simulation state) it fired on most.
|
|
203
|
+
*/
|
|
204
|
+
function needsForwardedTransforms(
|
|
205
|
+
contract: R3fComponentContract | undefined,
|
|
206
|
+
): contract is R3fComponentContract {
|
|
207
|
+
return (
|
|
208
|
+
contract?.root === 'single' &&
|
|
209
|
+
contract.transformProps.length < 3 &&
|
|
210
|
+
!contract.simulationOwnedTransform
|
|
211
|
+
);
|
|
212
|
+
}
|
|
213
|
+
|
|
214
|
+
/**
|
|
215
|
+
* True when this callsite is one item of a rendered list — inside a `.map(…)`
|
|
216
|
+
* callback and carrying React's own `key`.
|
|
217
|
+
*
|
|
218
|
+
* R3F004 asks for a `name` so an instance is recognizable in the hierarchy. A
|
|
219
|
+
* keyed list item is generated from data, not hand-placed: a literal `name`
|
|
220
|
+
* would give every item the SAME row label (worse than none), and the honest
|
|
221
|
+
* name is derived per item — `name={`rabbit-${i}`}`, which R3F004 already
|
|
222
|
+
* accepts, since it asks for the prop and never for a literal. Warning when the
|
|
223
|
+
* author has not derived one turns a suggestion into permanent noise on
|
|
224
|
+
* legitimate code, so a keyed map instance is left alone.
|
|
225
|
+
*/
|
|
226
|
+
function isKeyedListItem(
|
|
227
|
+
element: ts.JsxElement | ts.JsxSelfClosingElement,
|
|
228
|
+
opening: ts.JsxOpeningLikeElement,
|
|
229
|
+
sf: ts.SourceFile,
|
|
230
|
+
): boolean {
|
|
231
|
+
const keyed = opening.attributes.properties.some(
|
|
232
|
+
(property) => ts.isJsxAttribute(property) && property.name.getText(sf) === 'key',
|
|
233
|
+
);
|
|
234
|
+
if (!keyed) return false;
|
|
235
|
+
for (let cursor: ts.Node | undefined = element.parent; cursor; cursor = cursor.parent) {
|
|
236
|
+
if (
|
|
237
|
+
ts.isCallExpression(cursor) &&
|
|
238
|
+
ts.isPropertyAccessExpression(cursor.expression) &&
|
|
239
|
+
cursor.expression.name.text === 'map'
|
|
240
|
+
) {
|
|
241
|
+
return true;
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
return false;
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
export interface R3fAuthoringDiagnosticsOptions {
|
|
248
|
+
/**
|
|
249
|
+
* The caller has RESOLVED this file's region and it is a `three` one —
|
|
250
|
+
* `server/project-root-surface.ts`'s `resolveOidSurface`, which reads the
|
|
251
|
+
* region's declared `include` globs, the manifest's root entries, and live
|
|
252
|
+
* import reach. Absent or `false` means the caller resolved something else,
|
|
253
|
+
* or resolved nothing, and this analyzer stays silent.
|
|
254
|
+
*
|
|
255
|
+
* It USED to default to a source-text sniff — does this file's text name
|
|
256
|
+
* `@react-three/fiber`? — and that sniff is the reason a project could not
|
|
257
|
+
* centralize its R3F imports: a terminal whose 138 components take their
|
|
258
|
+
* prop shape from one shared `prefab.ts` and otherwise render nothing but
|
|
259
|
+
* intrinsic `<group>`/`<mesh>` tags had 12 files pass it and 126 SILENTLY
|
|
260
|
+
* SKIPPED, reported as no findings. Silence that cannot be distinguished
|
|
261
|
+
* from a clean bill of health is the worst thing an analyzer can produce,
|
|
262
|
+
* and reach answers all 138 because reach does not care where a project
|
|
263
|
+
* keeps its imports.
|
|
264
|
+
*
|
|
265
|
+
* Refusing to answer without a resolved surface is not a smaller analyzer,
|
|
266
|
+
* it is an honest one: a project's DOM regions run through here too
|
|
267
|
+
* (`project-validation.ts` validates every source file, whatever its
|
|
268
|
+
* adapter), and every rule below would fire on a `<div>`-rooted component —
|
|
269
|
+
* R3F002 would tell it to forward `position`. A caller with no region answer
|
|
270
|
+
* has an AMBIGUOUS file, which `resolveOidSurface` already reports as
|
|
271
|
+
* `OID001`/`OID002` with the declaration that fixes it.
|
|
272
|
+
*/
|
|
273
|
+
knownThreeSurface?: boolean;
|
|
274
|
+
}
|
|
275
|
+
|
|
276
|
+
/** Convention diagnostics for ordinary R3F source. These are warnings, not a
|
|
277
|
+
* validity gate: every valid R3F program still runs, while the editor explains
|
|
278
|
+
* why a component would be only partially authorable. */
|
|
279
|
+
export function r3fAuthoringDiagnostics(
|
|
280
|
+
code: string,
|
|
281
|
+
file: string,
|
|
282
|
+
opts?: R3fAuthoringDiagnosticsOptions,
|
|
283
|
+
): R3fAuthoringDiagnostic[] {
|
|
284
|
+
if (!opts?.knownThreeSurface) return [];
|
|
285
|
+
const analysis = newResolver().analyzeSource(code, file);
|
|
286
|
+
const sf = parseAuthoringTsx(file, code);
|
|
287
|
+
const diagnostics: R3fAuthoringDiagnostic[] = [];
|
|
288
|
+
const diagnosedDefinitions = new Set<string>();
|
|
289
|
+
const diagnosedMultiRoots = new Set<string>();
|
|
290
|
+
const diagnosedMotionRoots = new Set<string>();
|
|
291
|
+
// `export default World` IS the adapter root (D26 — the one entry shape).
|
|
292
|
+
const adapterRootComponents = new Set<string>();
|
|
293
|
+
const defaultExport = defaultExportedComponent(sf);
|
|
294
|
+
if (defaultExport) adapterRootComponents.add(defaultExport);
|
|
295
|
+
const motionRefs = runtimeMotionRefs(sf, sf);
|
|
296
|
+
|
|
297
|
+
// biome-ignore lint/complexity/noExcessiveCognitiveComplexity: one read-only AST walk keeps the related authoring convention diagnostics on one traversal.
|
|
298
|
+
const visit = (node: ts.Node): void => {
|
|
299
|
+
if (
|
|
300
|
+
ts.isFunctionDeclaration(node) &&
|
|
301
|
+
node.name &&
|
|
302
|
+
/^[A-Z]/.test(node.name.text) &&
|
|
303
|
+
!adapterRootComponents.has(node.name.text)
|
|
304
|
+
) {
|
|
305
|
+
const contract = analysis.visible.get(node.name.text);
|
|
306
|
+
if (contract?.root === 'multiple') {
|
|
307
|
+
diagnosedMultiRoots.add(node.name.text);
|
|
308
|
+
diagnostics.push({
|
|
309
|
+
code: 'R3F003',
|
|
310
|
+
severity: 'warning',
|
|
311
|
+
file,
|
|
312
|
+
...locationOf(sf, node.name),
|
|
313
|
+
component: node.name.text,
|
|
314
|
+
message: `${node.name.text} returns multiple spatial roots. Wrap them in one ordinary group so the instance has integral selection, grouping, and transform semantics.`,
|
|
315
|
+
});
|
|
316
|
+
}
|
|
317
|
+
if (needsForwardedTransforms(contract)) {
|
|
318
|
+
diagnosedDefinitions.add(node.name.text);
|
|
319
|
+
const missing = ['position', 'rotation', 'scale'].filter(
|
|
320
|
+
(channel) =>
|
|
321
|
+
!contract.transformProps.includes(channel as 'position' | 'rotation' | 'scale'),
|
|
322
|
+
);
|
|
323
|
+
diagnostics.push({
|
|
324
|
+
code: 'R3F002',
|
|
325
|
+
severity: 'warning',
|
|
326
|
+
file,
|
|
327
|
+
...locationOf(sf, node.name),
|
|
328
|
+
component: node.name.text,
|
|
329
|
+
message: `${node.name.text} does not forward ${missing.join(', ')} to its ${contract.rootTag ?? 'native'} root. Accept and spread the matching ThreeElements props to keep instances movable.`,
|
|
330
|
+
});
|
|
331
|
+
}
|
|
332
|
+
}
|
|
333
|
+
if (
|
|
334
|
+
ts.isVariableDeclaration(node) &&
|
|
335
|
+
ts.isIdentifier(node.name) &&
|
|
336
|
+
/^[A-Z]/.test(node.name.text) &&
|
|
337
|
+
!adapterRootComponents.has(node.name.text)
|
|
338
|
+
) {
|
|
339
|
+
const contract = analysis.visible.get(node.name.text);
|
|
340
|
+
if (!diagnosedMultiRoots.has(node.name.text) && contract?.root === 'multiple') {
|
|
341
|
+
diagnosedMultiRoots.add(node.name.text);
|
|
342
|
+
diagnostics.push({
|
|
343
|
+
code: 'R3F003',
|
|
344
|
+
severity: 'warning',
|
|
345
|
+
file,
|
|
346
|
+
...locationOf(sf, node.name),
|
|
347
|
+
component: node.name.text,
|
|
348
|
+
message: `${node.name.text} returns multiple spatial roots. Wrap them in one ordinary group so the instance has integral selection, grouping, and transform semantics.`,
|
|
349
|
+
});
|
|
350
|
+
}
|
|
351
|
+
if (!diagnosedDefinitions.has(node.name.text) && needsForwardedTransforms(contract)) {
|
|
352
|
+
const missing = ['position', 'rotation', 'scale'].filter(
|
|
353
|
+
(channel) =>
|
|
354
|
+
!contract.transformProps.includes(channel as 'position' | 'rotation' | 'scale'),
|
|
355
|
+
);
|
|
356
|
+
diagnostics.push({
|
|
357
|
+
code: 'R3F002',
|
|
358
|
+
severity: 'warning',
|
|
359
|
+
file,
|
|
360
|
+
...locationOf(sf, node.name),
|
|
361
|
+
component: node.name.text,
|
|
362
|
+
message: `${node.name.text} does not forward ${missing.join(', ')} to its ${contract.rootTag ?? 'native'} root. Accept and spread the matching ThreeElements props to keep instances movable.`,
|
|
363
|
+
});
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
if (ts.isJsxOpeningElement(node) || ts.isJsxSelfClosingElement(node)) {
|
|
367
|
+
const tag = node.tagName.getText(sf);
|
|
368
|
+
const contract = analysis.visible.get(tag);
|
|
369
|
+
const element = ts.isJsxOpeningElement(node) ? node.parent : node;
|
|
370
|
+
// A `name` the analyzer can SEE, or one it cannot prove absent. A spread
|
|
371
|
+
// of an opaque props object (`<EnemyBody {...props} />`) carries whatever
|
|
372
|
+
// the caller passed, `name` included — which is the whole point of a
|
|
373
|
+
// guard wrapper that re-renders its own props — so claiming the element
|
|
374
|
+
// "has no name" states as fact something this analyzer cannot read. An
|
|
375
|
+
// object LITERAL spread is readable, so it is still checked.
|
|
376
|
+
const hasName = node.attributes.properties.some((property) => {
|
|
377
|
+
if (ts.isJsxAttribute(property)) return property.name.getText(sf) === 'name';
|
|
378
|
+
if (ts.isJsxSpreadAttribute(property)) {
|
|
379
|
+
if (!ts.isObjectLiteralExpression(property.expression)) return true;
|
|
380
|
+
return property.expression.properties.some(
|
|
381
|
+
(member) => member.name !== undefined && member.name.getText(sf) === 'name',
|
|
382
|
+
);
|
|
383
|
+
}
|
|
384
|
+
return false;
|
|
385
|
+
});
|
|
386
|
+
const ref = node.attributes.properties.find(
|
|
387
|
+
(property) => ts.isJsxAttribute(property) && property.name.getText(sf) === 'ref',
|
|
388
|
+
);
|
|
389
|
+
const refExpression =
|
|
390
|
+
ref &&
|
|
391
|
+
ts.isJsxAttribute(ref) &&
|
|
392
|
+
ref.initializer &&
|
|
393
|
+
ts.isJsxExpression(ref.initializer) &&
|
|
394
|
+
ref.initializer.expression &&
|
|
395
|
+
ts.isIdentifier(ref.initializer.expression)
|
|
396
|
+
? ref.initializer.expression
|
|
397
|
+
: null;
|
|
398
|
+
const rootComponent = returnedRootComponent(element);
|
|
399
|
+
if (
|
|
400
|
+
rootComponent &&
|
|
401
|
+
!adapterRootComponents.has(rootComponent) &&
|
|
402
|
+
refExpression &&
|
|
403
|
+
motionRefs.has(refExpression.text) &&
|
|
404
|
+
// Nothing to fight over: this component exposes no authorable
|
|
405
|
+
// transform, so there is no editor value for the runtime to overwrite.
|
|
406
|
+
!analysis.visible.get(rootComponent)?.simulationOwnedTransform &&
|
|
407
|
+
!diagnosedMotionRoots.has(rootComponent)
|
|
408
|
+
) {
|
|
409
|
+
diagnosedMotionRoots.add(rootComponent);
|
|
410
|
+
diagnostics.push({
|
|
411
|
+
code: 'R3F005',
|
|
412
|
+
severity: 'warning',
|
|
413
|
+
file,
|
|
414
|
+
...locationOf(sf, refExpression),
|
|
415
|
+
component: rootComponent,
|
|
416
|
+
message: `${rootComponent} animates its authored outer root through useFrame. Keep the outer root stable and animate an inner child so editor transforms do not fight runtime motion.`,
|
|
417
|
+
});
|
|
418
|
+
}
|
|
419
|
+
if (
|
|
420
|
+
/^[A-Z]/.test(tag) &&
|
|
421
|
+
contract?.root === 'single' &&
|
|
422
|
+
// A package component vgai knows only through the built-in table is not
|
|
423
|
+
// a hierarchy row of its own — `<RigidBody>` never receives the editor's
|
|
424
|
+
// stamp, so its props are attributed to the node it wraps
|
|
425
|
+
// (`collapsedWrappersOf`). Naming it would name nothing.
|
|
426
|
+
!isBuiltinR3fContract(contract) &&
|
|
427
|
+
!hasName &&
|
|
428
|
+
!isKeyedListItem(element, node, sf)
|
|
429
|
+
) {
|
|
430
|
+
diagnostics.push({
|
|
431
|
+
code: 'R3F004',
|
|
432
|
+
severity: 'warning',
|
|
433
|
+
file,
|
|
434
|
+
...locationOf(sf, node),
|
|
435
|
+
component: tag,
|
|
436
|
+
message: `${tag} has no name. Add the ordinary R3F name prop so its instance is recognizable in the hierarchy.`,
|
|
437
|
+
});
|
|
438
|
+
}
|
|
439
|
+
}
|
|
440
|
+
ts.forEachChild(node, visit);
|
|
441
|
+
};
|
|
442
|
+
visit(sf);
|
|
443
|
+
return diagnostics;
|
|
444
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The relative import specifier a human would write from one module to
|
|
3
|
+
* another — the ONE copy of the shared-prefix walk that existed five times
|
|
4
|
+
* (owner-directed overlap audit, 2026-08-22): `R3fSourceAuthoringAdapter.
|
|
5
|
+
* relativeModuleSpecifier`, `ReactRootAuthoringAdapter.relativeProjectModule`,
|
|
6
|
+
* `pixi-source-write-target`'s `relativeProjectModule`, and the
|
|
7
|
+
* `relativeSpecifier` locals in `plan-fork-component.ts` and
|
|
8
|
+
* `plan-extract-component.ts`.
|
|
9
|
+
*
|
|
10
|
+
* Dependency-free on purpose (no `node:path`): two of the five consumers are
|
|
11
|
+
* pure planner modules that must stay headlessly probeable, and a specifier is
|
|
12
|
+
* a POSIX-slash artifact regardless of host platform.
|
|
13
|
+
*
|
|
14
|
+
* What stays at the call site, deliberately: resolving the two paths into the
|
|
15
|
+
* SAME address space (project-relative vs absolute — both work, the walk eats
|
|
16
|
+
* any shared prefix, but they must match). A source extension on the target is
|
|
17
|
+
* stripped; an extension-less module id passes through unchanged.
|
|
18
|
+
*/
|
|
19
|
+
export function relativeImportSpecifier(fromFile: string, toModule: string): string {
|
|
20
|
+
const from = normalize(fromFile).split('/').filter(Boolean).slice(0, -1);
|
|
21
|
+
const to = normalize(toModule)
|
|
22
|
+
.replace(/\.[cm]?[jt]sx?$/, '')
|
|
23
|
+
.split('/')
|
|
24
|
+
.filter(Boolean);
|
|
25
|
+
let shared = 0;
|
|
26
|
+
while (shared < from.length && shared < to.length && from[shared] === to[shared]) shared += 1;
|
|
27
|
+
const up = new Array(from.length - shared).fill('..');
|
|
28
|
+
const specifier = [...up, ...to.slice(shared)].join('/');
|
|
29
|
+
return specifier.startsWith('.') ? specifier : `./${specifier}`;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
function normalize(path: string): string {
|
|
33
|
+
return path.replace(/\\/g, '/').replace(/^\.\//, '');
|
|
34
|
+
}
|