@jgengine/assets 0.13.0 → 0.15.0-next.0

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.
@@ -16,6 +16,10 @@ Reach for these before hand-rolling. Each row is *the thing you need* → *the p
16
16
 
17
17
  - `GameContextModels` (interface) · `import { GameContextModels } from "@jgengine/core/runtime/gameContext"`
18
18
 
19
+ ## default-walk-codes — stock WASD + jump key codes for the shell walk controller
20
+
21
+ - `DEFAULT_WALK_CODES` (const) · `import { DEFAULT_WALK_CODES } from "@jgengine/shell/gameKit"`
22
+
19
23
  ## define-game — single public game-authoring path — compose systems, world, presentation, and authored scene in one definition
20
24
 
21
25
  - `defineGame` (function) · `import { defineGame } from "@jgengine/shell/gameKit"`
@@ -32,6 +36,10 @@ Reach for these before hand-rolling. Each row is *the thing you need* → *the p
32
36
 
33
37
  - `SystemDefinition` (interface) · `import { SystemDefinition } from "@jgengine/shell/gameKit"`
34
38
 
39
+ ## grounded — ground an XZ point onto the world surface as a pose triple
40
+
41
+ - `grounded` (function) · `import { grounded } from "@jgengine/shell/gameKit"`
42
+
35
43
  ## headless-runner — play a real game loop with no renderer — tick, feed input, read the world snapshot
36
44
 
37
45
  - `HeadlessRunner` (interface) · `import { HeadlessRunner } from "@jgengine/core/runtime/headlessRunner"`
@@ -95,8 +103,12 @@ Reach for these before hand-rolling. Each row is *the thing you need* → *the p
95
103
  ## render-fallback-diagnostics — Enable/disable the dev-only placeholder-fallback probe.
96
104
 
97
105
  - `armFallbackSeams` (function) · `import { armFallbackSeams } from "@jgengine/core/devtools/fallbackSeams"`
106
+ - `armTextureErrors` (function) · `import { armTextureErrors } from "@jgengine/core/devtools/textureErrors"`
98
107
  - `fallbackSeamsSnapshot` (function) · `import { fallbackSeamsSnapshot } from "@jgengine/core/devtools/fallbackSeams"`
99
108
  - `reportFallbackSeam` (function) · `import { reportFallbackSeam } from "@jgengine/core/devtools/fallbackSeams"`
109
+ - `reportTextureLoadError` (function) · `import { reportTextureLoadError } from "@jgengine/core/devtools/textureErrors"`
110
+ - `resetTextureErrors` (function) · `import { resetTextureErrors } from "@jgengine/core/devtools/textureErrors"`
111
+ - `textureErrorsSnapshot` (function) · `import { textureErrorsSnapshot } from "@jgengine/core/devtools/textureErrors"`
100
112
 
101
113
  ## runtime-save — save/load the whole game world through a pluggable backend, autosave or save points
102
114
 
@@ -72,10 +72,13 @@ export function onNewPlayer(ctx: GameContext): void {
72
72
  ```
73
73
 
74
74
  `GameUI` starts as an empty `HudCanvas` (`useHudLayout` + `HudCanvas` from the kit). That is
75
- intentional: **every game owns its UI**. Write a short UI art direction, then build custom
76
- panels for this pitch — do not ship stock drop-in widgets (`StatBar`, `Hotbar`, `Coins`, glass
77
- frames) as the product face. Reach for engine pieces only as headless data, layout, or
78
- interaction models under game-owned chrome (see `jgengine-ui`).
75
+ intentional: **every game owns its UI composition** — layout, terminology, placement, and art
76
+ direction. Compose the shipped building blocks the moment you need them (`StatBar`, `Hotbar`,
77
+ `Coins`, `InventoryGrid`, `CharacterSheet`, window shells from `jgengine-ui`), then reskin via
78
+ `HudTheme` tokens. Reaching for those is using the engine correctly, not incomplete work. What
79
+ the engine does not ship is a whole finished game *face* or genre theme preset — do not leave an
80
+ unarranged, unskinned generic dashboard as the product. Hand-roll markup only where no building
81
+ block fits (see `jgengine-ui`).
79
82
 
80
83
  ## 3. Author, play, win
81
84
 
@@ -9,7 +9,7 @@ description: Source, license, catalog, and resolve game-ready media assets.
9
9
 
10
10
  This skill owns model, sprite, texture/material, and audio-file discovery; licensing; catalog metadata; pull/index workflows; and runtime asset references. Placement belongs to `jgengine-editor`, spatial audio behavior to `jgengine-world`, and rendering/UI composition to their respective domains.
11
11
 
12
- Search [capabilities.md](capabilities.md) before adding a resolver or catalog path. Use [api.md](api.md) for exact exports.
12
+ Search [capabilities.md](capabilities.md) before adding a resolver or catalog path. Use [api.md](api.md) for exact exports. Turning a real item or scene into an asset via video capture and 3D reconstruction is a sourcing method under this skill — see [references/video-to-3d-capture.md](references/video-to-3d-capture.md) for the offline pipeline, hardware/cost notes, and import steps.
13
13
 
14
14
  ## Canonical workflow
15
15
 
@@ -119,6 +119,16 @@
119
119
 
120
120
  - `COLLISION_MESH_ASSET_IDS` (const): const COLLISION_MESH_ASSET_IDS: ReadonlySet<string> — Catalog assets that ship a collision mesh in the generated index. Opt-in only: each entry adds ~10-30KB of quantized triangles to the index and a BVH raycast per query, so list only concave models whose fitted box lies (archways, rings, frames).
121
121
 
122
+ ## @jgengine/assets/credits
123
+
124
+ - `CreditsGrouping` (type): type CreditsGrouping = "license" | "provider" — Grouping for {@link creditsForSources} — one section per license (default) or per provider.
125
+ - `allAssetSources` (function): function allAssetSources(): readonly AssetSource[] — Every catalogued source, for a credits screen that lists the whole shipped catalog.
126
+ - `creditsForAssetIds` (function): function creditsForAssetIds(ids: Iterable<string>, options: { title?: string; grouping?: CreditsGrouping; notice?: string } = {}): CreditsDocument — One call from the asset ids a game ships to a ready {@link CreditsDocument} — the credit obligation for borrowed assets, derived rather than hand-maintained.
127
+ - `creditsForSourceIds` (function): function creditsForSourceIds(ids: Iterable<string>, options: { title?: string; grouping?: CreditsGrouping; notice?: string } = {}): CreditsDocument — One call from the source ids a game declares to a ready {@link CreditsDocument} — the usual entry point, since `buildCatalog({ sources })` already names them.
128
+ - `creditsForSources` (function): function creditsForSources(used: readonly AssetSource[], grouping: CreditsGrouping = "license"): CreditsSection[] — Turns asset sources into credit sections, one per license or provider, each entry naming the pack and its author with the pack homepage as `href`. Feed it {@link sourcesForAssetIds} so the screen credits what shipped, and fold the result into the game's hand-authored credits with `mergeCredits`.
129
+ - `sourcesForAssetIds` (function): function sourcesForAssetIds(ids: Iterable<string>): AssetSource[] — The distinct asset sources behind a set of asset ids — the packs a game actually ships, not the whole catalog. Unknown ids are skipped; order follows first use so a stable id list gives a stable credits screen.
130
+ - `sourcesForSourceIds` (function): function sourcesForSourceIds(ids: Iterable<string>): AssetSource[] — The distinct sources behind a set of source ids — the shape a game already declares to `buildCatalog({ sources })` / `buildMaterialCatalog`. Unknown ids are skipped.
131
+
122
132
  ## @jgengine/assets/dims
123
133
 
124
134
  - `ModelDims` (interface): interface ModelDims — Measured horizontal footprint, footprint center, and lowest Y of a model in model space.
@@ -12,6 +12,26 @@ Reach for these before hand-rolling. Each row is *the thing you need* → *the p
12
12
 
13
13
  - `readGlbClips` (function) · `import { readGlbClips } from "@jgengine/assets/dims"`
14
14
 
15
+ ## credits-for-asset-ids — build a credits document from the asset ids a game ships
16
+
17
+ - `creditsForAssetIds` (function) · `import { creditsForAssetIds } from "@jgengine/assets/credits"`
18
+
19
+ ## credits-for-source-ids — build a credits document from the asset source ids a game declares
20
+
21
+ - `creditsForSourceIds` (function) · `import { creditsForSourceIds } from "@jgengine/assets/credits"`
22
+
23
+ ## credits-for-sources — generate credit sections from asset pack metadata, grouped by license or provider
24
+
25
+ - `creditsForSources` (function) · `import { creditsForSources } from "@jgengine/assets/credits"`
26
+
27
+ ## sources-for-asset-ids — resolve the asset packs behind the ids a game actually ships
28
+
29
+ - `sourcesForAssetIds` (function) · `import { sourcesForAssetIds } from "@jgengine/assets/credits"`
30
+
31
+ ## sources-for-source-ids — resolve the asset pack metadata behind the source ids a game declares
32
+
33
+ - `sourcesForSourceIds` (function) · `import { sourcesForSourceIds } from "@jgengine/assets/credits"`
34
+
15
35
  ## starter-packs — themed CC0 model ids (people/props/nature/urban) ready for entityModels
16
36
 
17
37
  - `StarterTheme` (type) · `import { StarterTheme } from "@jgengine/assets"`
@@ -0,0 +1,69 @@
1
+ # Video-to-3D capture (photogrammetry-via-video)
2
+
3
+ An offline path for turning a real item or location into a game-ready asset:
4
+ film it, reconstruct it, mesh it, import it. This is a **capture/sourcing**
5
+ recipe, not a runtime feature — nothing here runs inside the engine or a
6
+ shipped game.
7
+
8
+ Adapts the reconstruction step around
9
+ [LingBot-Map](https://github.com/Robbyant/lingbot-map) (Apache-2.0) — see
10
+ `CREDITS.md`.
11
+
12
+ ## Why offline
13
+
14
+ LingBot-Map is a feed-forward 3D reconstruction model: PyTorch 2.8 + CUDA
15
+ 12.8, needs an NVIDIA GPU. It has no place running per-frame in a browser
16
+ game or inside `@jgengine/shell`. Treat it as a one-shot batch job: video in,
17
+ point cloud out, done — same category of tool as a photogrammetry rig, not a
18
+ package dependency.
19
+
20
+ ## What it needs
21
+
22
+ - NVIDIA GPU, CUDA 12.8, Python 3.10, PyTorch 2.8.0.
23
+ - No hard VRAM floor is published, but the tool ships `--offload_to_cpu` and
24
+ a lower `--num_scale_frames` specifically for constrained cards — an
25
+ 8–12GB consumer GPU (3060/3080) works chunked; a 16–24GB card (4090/A6000)
26
+ runs full-speed without offload.
27
+ - No CPU-only mode.
28
+
29
+ ## Cost if you rent instead of own
30
+
31
+ Spot GPU pricing (Vast.ai/RunPod-class) for a 4090 or A6000 runs roughly
32
+ **$0.35–0.80/hr**. At ~20 FPS on 518×378, a short 10–30s item/scene capture
33
+ reconstructs in well under a minute of GPU time — each asset costs pennies
34
+ to about a quarter, plus a couple minutes of environment spin-up. Cheap
35
+ enough to do per-asset, not something to batch-justify.
36
+
37
+ ## Pipeline
38
+
39
+ 1. **Capture** — film the item or scene as a short, steady walk-around or
40
+ pan (good, even lighting; avoid pure reflective/transparent surfaces —
41
+ they break most feed-forward reconstruction). 10–30s is plenty.
42
+ 2. **Reconstruct** (rented or owned GPU box, outside this repo) — run
43
+ LingBot-Map's streaming inference on the clip per its README. Output is a
44
+ point cloud plus per-frame NPZ/depth/trajectory data, not a mesh.
45
+ 3. **Mesh + clean** (local, no GPU needed) —
46
+ `scripts/asset-pipeline/pointcloud_to_glb.py` in this repo turns an
47
+ exported point cloud (`.ply`/`.npz`) into a Poisson-reconstructed mesh and
48
+ writes a `.glb`. Expect to hand-clean the result (decimate, fill holes,
49
+ fix scale/facing) in Blender before it's asset-grade — this step is a
50
+ starting point, not a finisher.
51
+ 4. **Import** — bring the cleaned `.glb` in through the editor's asset
52
+ import flow (`jgengine-editor`) into a promoted project's `extras` array
53
+ (`src/game/assets.ts`), same as any other authored asset. Record source
54
+ units, pivot, canonical facing, and footprint in the catalog metadata per
55
+ `jgengine-assets`' canonical workflow — do not hardcode the geometry or
56
+ skip cataloging because it was scanned rather than downloaded.
57
+ 5. **Credit** — LingBot-Map is Apache-2.0 (commercial use fine); keep the
58
+ `CREDITS.md` entry current and add the specific asset's provenance to its
59
+ catalog metadata.
60
+
61
+ ## Traps
62
+
63
+ - Point clouds are not meshes and meshes are not game-ready — budget real
64
+ cleanup time at step 3, not just format conversion.
65
+ - Scale and pivot come out of the reconstruction arbitrary; fix them once in
66
+ catalog metadata (per `jgengine-assets`' traps), never with a per-placement
67
+ corrective transform.
68
+ - Reflective, transparent, or textureless surfaces reconstruct badly — pick
69
+ capture subjects accordingly, or expect heavy manual repair.