@jgengine/assets 0.10.0 → 0.12.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.
- package/CHANGELOG.md +39 -2
- package/README.md +103 -50
- package/dist/aliases.d.ts +5 -0
- package/dist/aliases.js +28 -9
- package/dist/catalogs/build.d.ts +27 -0
- package/dist/catalogs/build.js +28 -2
- package/dist/catalogs/buildSprites.d.ts +10 -0
- package/dist/catalogs/buildSprites.js +15 -0
- package/dist/catalogs/starter.d.ts +5 -0
- package/dist/catalogs/starter.js +10 -1
- package/dist/cli/paths.d.ts +9 -1
- package/dist/cli/paths.js +11 -1
- package/dist/cli/pull.d.ts +12 -0
- package/dist/cli/pull.js +216 -25
- package/dist/collisionMeshAssets.d.ts +2 -0
- package/dist/collisionMeshAssets.js +6 -0
- package/dist/dims.d.ts +7 -0
- package/dist/dims.js +154 -0
- package/dist/download.d.ts +66 -7
- package/dist/download.js +264 -18
- package/dist/find.d.ts +20 -1
- package/dist/find.js +52 -2
- package/dist/generated/index.js +18 -6
- package/dist/generated/kaykit-adventurers.json +706 -0
- package/dist/generated/kaykit-city-builder.json +904 -0
- package/dist/generated/kaykit-dungeon.json +5002 -0
- package/dist/generated/kaykit-furniture.json +1168 -0
- package/dist/generated/kaykit-skeletons.json +410 -0
- package/dist/generated/kaykit-space-base.json +1199 -0
- package/dist/generated/quaternius-medieval-village.json +3698 -0
- package/dist/generated/quaternius-modular-scifi.json +4013 -0
- package/dist/generated/quaternius-stylized-nature.json +1498 -0
- package/dist/generated-sprites/index.d.ts +5 -0
- package/dist/generated-sprites/index.js +4 -0
- package/dist/index.d.ts +9 -2
- package/dist/index.js +9 -2
- package/dist/indexGen.d.ts +2 -2
- package/dist/indexGen.js +34 -10
- package/dist/manifest.d.ts +16 -1
- package/dist/materials.d.ts +61 -0
- package/dist/materials.js +98 -0
- package/dist/packs/starter.d.ts +46 -0
- package/dist/packs/starter.js +248 -0
- package/dist/provisioning.d.ts +88 -0
- package/dist/provisioning.js +74 -0
- package/dist/registry-catalog.json +35 -0
- package/dist/snippet.d.ts +4 -0
- package/dist/snippet.js +27 -0
- package/dist/sources/ambientcg.d.ts +5 -0
- package/dist/sources/ambientcg.js +64 -0
- package/dist/sources/gameicons.d.ts +10 -0
- package/dist/sources/gameicons.js +21 -0
- package/dist/sources/index.d.ts +9 -2
- package/dist/sources/index.js +11 -3
- package/dist/sources/kaykit.js +55 -6
- package/dist/sources/quaternius.js +60 -9
- package/dist/spriteIndexGen.d.ts +17 -0
- package/dist/spriteIndexGen.js +108 -0
- package/dist/verify.d.ts +1 -0
- package/dist/verify.js +38 -1
- package/package.json +4 -4
- package/skills/jgengine/SKILL.md +54 -0
- package/skills/jgengine/api.md +527 -0
- package/skills/jgengine/capabilities.md +131 -0
- package/skills/jgengine/recipes/minimal-game.md +88 -0
- package/skills/jgengine-assets/SKILL.md +45 -0
- package/skills/jgengine-assets/api.md +282 -0
- package/skills/jgengine-assets/capabilities.md +13 -0
- package/dist/generated/kenney-blaster.json +0 -362
- package/dist/generated/kenney-nature.json +0 -3292
- package/dist/generated/kenney-space.json +0 -1532
- package/dist/sources/kenney.d.ts +0 -2
- package/dist/sources/kenney.js +0 -36
- package/llms.txt +0 -1010
package/CHANGELOG.md
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
|
|
3
|
+
The lockstep game SDK set is `@jgengine/{core,react,ws,node,sql,convex,shell,editor,assets}`
|
|
4
|
+
(this file’s 0.x.y releases). The CLI package `jgengine` and `@jgengine/github` use
|
|
5
|
+
**separate** version lines and may lag. Format follows [Keep a Changelog](https://keepachangelog.com);
|
|
5
6
|
each release **leads with a Migrate block** — the concrete steps to move a game
|
|
6
7
|
from the previous version onto the new APIs — because the point of a bump is to
|
|
7
8
|
let consumers pick up the better stuff, not just to list what moved.
|
|
@@ -11,6 +12,42 @@ Agents building on the published SDK can also read this programmatically:
|
|
|
11
12
|
same data as typed values, so an updater can diff its installed version against
|
|
12
13
|
the latest and surface the migration steps.
|
|
13
14
|
|
|
15
|
+
## 0.12.0
|
|
16
|
+
|
|
17
|
+
### Migrate
|
|
18
|
+
|
|
19
|
+
- **Author games through `defineGame` from `@jgengine/shell`** — it is the single public authoring entry (and carries the define-game capability tag). Core's constructor was renamed `defineGame` → `defineGameDefinition` (`@jgengine/core/game/defineGame`); only hosts and tooling call it. If you imported `defineGame` from core, switch the import to `@jgengine/shell`. `GamePlayer`/`GamePlayerShell` are `@internal` now — `GameHost` is the documented mount, and it owns the editor summon (`?mode=editor`, F2+E, dev save endpoint), so delete any per-game editor bootstrap.
|
|
20
|
+
- **Declare your world with `world()`** (`@jgengine/core/world/place`): `world({ id, ground: { mode, size, surface? }, physics? })` with `flat` / `round` / `voxel` / `board` ground. New scaffolds emit a thin infinite flat place instead of the old 96 m meadow. `environment()` still works but is demoted to the legacy consumption path for editor-written scene data — **nothing required** for existing games; new worlds should use `world()` and author all dressing in the editor.
|
|
21
|
+
- Everything else is additive — stat pools, minimap marker sources, auction house, city/path generation, editor workspaces require no changes to existing games.
|
|
22
|
+
|
|
23
|
+
### Added
|
|
24
|
+
|
|
25
|
+
- **World = place: `world()` API** (#1178) — a world is substrate + laws, not a coded diorama. `@jgengine/core/world/place` ships `world({ id, ground: { mode, size, surface?, generator? }, physics? })`; size is discriminated by mode (flat `{x,z}` with `Infinity` axes, round `{radius}`, voxel generator domain, board `{x,y}` cells — TS and runtime both reject mismatches). `ground.surface` carries matter/feel laws (metal vs slime vs felt) read by the same rule systems; per-place `physics` resolves over the game default; multiple worlds per game are first-class. The shell renders place substrates (`PlaceScene`) under the engine default sky; seeds derive from world id + save via `seedForPlace`.
|
|
26
|
+
- **`@jgengine/shell/gameKit`** — happy-path authoring surface: authoring, mount, stores, systems, authored-scene helpers, HUD primitives, seeded rng in one import.
|
|
27
|
+
- **Portable generic stat pools** — `@jgengine/core/stats/statPool`: bounded named pools (health, energy, heat, ammo…) with the entity-stats integration rebuilt on them; recipe in skill `jgengine-combat`.
|
|
28
|
+
- **Auction-house economy primitives** (#1086) — `@jgengine/core/economy/auctionBook` (timed bid auctions, escrowed bids, outbid refunds, optional buyout, anti-snipe close extension, seller settlement minus house cut) plus market price history.
|
|
29
|
+
- **Portable minimap marker sources** — core world seam feeding game minimaps; recipe in skill `jgengine-ui`.
|
|
30
|
+
- **Unified seed-driven path network + city generation v2** (#1103, #1106) — streets/blocks/buildings with grid-ness, curviness, branching and block-size dials; zone bands, weighted building-class mixes, massing pieces, balance presets, junction-centered clustering, road-derived block polygons and parcels. Shell renders realistic roads: real intersections, curbs, lane lines, tunnels, and roads riding bridge decks.
|
|
31
|
+
- **Physical fidelity** — mesh-accurate hitboxes (shots pass through holes in concave models, #1075), auto-fit entity/object colliders from measured model bounds (#1072), movement obstruction reading fitted boxes + compound-box openings (#1077).
|
|
32
|
+
- **Editor overhaul** (#1110) — materials / lighting / scripting / animation-timeline / multiplayer workspaces, command palette, minimap bake wired end-to-end (#1036), real offscreen GLB thumbnails in the content browser, hierarchy drag-drop + keyboard + context menus + per-object visibility/lock, multi-select inspector, console RPC, asset drag-place, ortho projection, pivot modes, play chrome.
|
|
33
|
+
- **Editor authoring pipeline** — author entity definitions and starter catalogs (#1012), author catalogs/schema fields in the Data tab (#1043), promote an authored scene folder into a runnable game (#1011), authored triggers promoted to a shared primitive with goal/win rules (#1013), asset import rewrites the game's `game/assets.ts` (#1042).
|
|
34
|
+
- **Skills** — research-backed `game-design` and `level-design` skills (#962); every-game-owns-custom-UI invariant codified (#1148).
|
|
35
|
+
|
|
36
|
+
### Changed
|
|
37
|
+
|
|
38
|
+
- `npx jgengine create` scaffolds a thin infinite flat `world()` place; the editor `blankWorld` no longer pre-bakes seeded grass. Dressing belongs in `editor.scene.json`.
|
|
39
|
+
- Environment studio visual-quality pass — turf tufts, depth-aware water, relief soil, weathered poles; grass fields no longer rebuild geometry per frame (#1090).
|
|
40
|
+
|
|
41
|
+
## 0.11.0
|
|
42
|
+
|
|
43
|
+
### Migrate
|
|
44
|
+
|
|
45
|
+
- **Nothing required** — classic `loop.onTick` fan-out still runs after systems. Prefer moving per-frame work into `defineGame({ systems: [...] })` with `defineSystem` (`@jgengine/core/game/defineSystem`); install a system with `feature: "quest"` (etc.) instead of a redundant `features` flag. See skill `jgengine` → [reference-systems.md](.claude/skills/jgengine/reference-systems.md).
|
|
46
|
+
|
|
47
|
+
### Added
|
|
48
|
+
|
|
49
|
+
- **Composable game systems** (#842) — `defineSystem` / `compileSystemSchedule` / `composeGameLoop` / `installSystems`. `defineGame({ systems })` is the single authoring path: fixed / frame / interval / event-only / manual ticks, multi-subscribe channels, deterministic stage order + optional `before`/`after`/`dependsOn`, system-owned save / replicate / reset / dispose. Installing a system activates its `feature` without a separate flag. `GameLoop` gains optional `onReset` / `onDispose`. `ctx.game.registerSave` / `registerReplicate` for system modules. Adopters: tower-guard, claudecraft (runtime without a giant tick fan-out).
|
|
50
|
+
|
|
14
51
|
## 0.10.0
|
|
15
52
|
|
|
16
53
|
### Migrate
|
package/README.md
CHANGED
|
@@ -1,37 +1,45 @@
|
|
|
1
1
|
# @jgengine/assets
|
|
2
2
|
|
|
3
|
-
A self-generating, license-verified index of thousands of CC0 3D models
|
|
3
|
+
A self-generating, license-verified index of thousands of CC0 3D models, PBR materials, **and 2D sprite/icon packs** G�� hosted at **zero cost**. No GLB, texture, or sprite bytes ship in the npm tarball; every byte comes from infrastructure you don't pay for:
|
|
4
4
|
|
|
5
5
|
| What | Where it lives | Whose bandwidth |
|
|
6
6
|
|------|----------------|-----------------|
|
|
7
|
-
| Pack GLBs (
|
|
7
|
+
| Pack GLBs (Quaternius, KayKitGǪ) | Fetched at `pull` time from the provider's CDN | Provider's |
|
|
8
|
+
| PBR materials (ambientCG) | Fetched at `pull` time (provider or the `packs` release mirror) | Provider's / GitHub's |
|
|
9
|
+
| Sprite/icon packs (game-icons.net) | Fetched at `pull` time (provider or the `packs` release mirror) | Provider's / GitHub's |
|
|
8
10
|
| The generated index (JSON) | Inside this npm package | npm (KB) |
|
|
9
11
|
| Your one-off models | `packages/assets/local/`, served via jsDelivr-over-GitHub | GitHub + jsDelivr |
|
|
10
|
-
| A consumer's downloaded bytes | Their `public/models/` (gitignored) | The consumer's |
|
|
12
|
+
| A consumer's downloaded bytes | Their `public/models/` + `public/materials/` + `public/sprites/` (gitignored) | The consumer's |
|
|
11
13
|
|
|
12
14
|
## Layers
|
|
13
15
|
|
|
14
|
-
1. **Sources** (`src/sources/*.ts`)
|
|
15
|
-
2. **Generated index** (`src/generated/*.json`)
|
|
16
|
-
3. **Aliases** (`src/aliases.ts`)
|
|
17
|
-
4. **Singles** (`src/singles.json`)
|
|
16
|
+
1. **Sources** (`src/sources/*.ts`) G�� one entry per downloadable pack. Every entry carries required `license` + `author` and a `download` that is either a pinned `{ url, sha256? }` or a `{ scrape }` marker.
|
|
17
|
+
2. **Generated index** (`src/generated/*.json`) G�� machine-produced from the real `.glb` filenames after a pack is extracted. Never hand-typed. Committed JSON; bytes are not.
|
|
18
|
+
3. **Aliases** (`src/aliases.ts`) G�� hand-authored semantic keys (`nature/tree_pine G�� quaternius-stylized-nature/Pine_1`).
|
|
19
|
+
4. **Singles** (`src/singles.json`) G�� long-tail one-offs (per-model `url` + `license`).
|
|
20
|
+
5. **Materials** (`src/sources/ambientcg.ts` + `src/materials.ts`) G�� `kind: "material"` sources, one CC0 PBR material each (hundreds of ambientCG materials: grass, rock, wood, brick, metal, fabricGǪ). `pull` normalizes the maps to fixed filenames, so `buildMaterialCatalog({ basePath })` resolves ids and `material/GǪ` aliases to map URLs with no generated index at all.
|
|
21
|
+
6. **Sprites** (`src/sources/gameicons.ts` + `src/spriteIndexGen.ts`) G�� `kind: "sprite"` sources, packs of individual SVG/PNG icon and UI files (game-icons.net's ~4,000 CC BY 3.0 icons as one mirrored repo). Same shape as models G�� `reindex-sprites` discovers real files after a pull and writes `src/generated-sprites/*.json`, resolved through `buildSpriteCatalog({ basePath })`.
|
|
18
22
|
|
|
19
|
-
|
|
23
|
+
Model entries collapse into the core `AssetCatalog` via `buildCatalog({ basePath })`; materials resolve through `buildMaterialCatalog({ basePath })`; sprites/icons resolve through `buildSpriteCatalog({ basePath })`.
|
|
20
24
|
|
|
21
|
-
## `add`
|
|
25
|
+
## `add` G�� one command for anything
|
|
22
26
|
|
|
23
|
-
`assets add <query>` is the front door. It fuzzy-searches **every** catalog at once
|
|
27
|
+
`assets add <query>` is the front door. It fuzzy-searches **every** catalog at once G�� 3D models, whole packs, PBR materials, sprite/icon packs, HUD components (the shadcn registry), and `game-icon` glyphs G�� then does the fetch and prints the exact copy-paste wiring. One mental model instead of six.
|
|
24
28
|
|
|
25
29
|
```bash
|
|
26
|
-
assets add astronaut --dir ../../apps/dev/public # model
|
|
27
|
-
assets add nature --dir ../../apps/dev/public # whole pack
|
|
28
|
-
assets add
|
|
29
|
-
assets add
|
|
30
|
+
assets add astronaut --dir ../../apps/dev/public # model G�� pull + reindex + print the assets.ts snippet
|
|
31
|
+
assets add nature --dir ../../apps/dev/public # whole pack G�� pull + reindex + how to wire an id
|
|
32
|
+
assets add grass --kind material --dir ../../apps/dev/public # PBR material G�� pull maps + resolve snippet
|
|
33
|
+
assets add "game icons" --dir ../../apps/dev/public # sprite pack G�� pull + reindex-sprites + resolve snippet
|
|
34
|
+
assets add "mana bar" # HUD component G�� the `npx shadcn add` cmd + <VitalBar/> usage
|
|
35
|
+
assets add sword # icon G�� the game-icon name to drop in a slot
|
|
30
36
|
```
|
|
31
37
|
|
|
32
38
|
- A **model / pack** match is fully automated: if the pack isn't already in `<dir>/models/`, it's pulled and extracted, then `reindex` runs so the id is addressable, then the `buildCatalog` + model-seam snippet is printed.
|
|
33
|
-
- A **
|
|
34
|
-
-
|
|
39
|
+
- A **material** match pulls the maps into `<dir>/materials/<id>/` with normalized names (`color.jpg`, `normal.jpg`, `roughness.jpg`, `ao.jpg`, `displacement.jpg`) and prints the `buildMaterialCatalog` resolve snippet G�� no reindex needed, the material catalog is fully static.
|
|
40
|
+
- A **sprite / spritePack** match works like model/pack: if the pack isn't already in `<dir>/sprites/`, it's pulled and extracted, then `reindex-sprites` runs so individual SVG/PNG ids are addressable, then the `buildSpriteCatalog` snippet is printed.
|
|
41
|
+
- A **component / icon** match prints the one-liner to run and the import + usage G�� no bytes to pull.
|
|
42
|
+
- Ambiguous query? `add` lists the top matches across kinds; narrow with `--kind model|pack|material|component|icon|sprite|spritePack` or a more specific term. `--json` emits the ranked matches for scripting.
|
|
35
43
|
|
|
36
44
|
The same ranking is available programmatically: `import { findAssets } from "@jgengine/assets"`.
|
|
37
45
|
|
|
@@ -39,98 +47,143 @@ The same ranking is available programmatically: `import { findAssets } from "@jg
|
|
|
39
47
|
|
|
40
48
|
```
|
|
41
49
|
assets add <query> [--kind <k>] [--dir <dir>] [--mirror <baseUrl>] [--json]
|
|
42
|
-
# unified import: models, packs, components, icons
|
|
43
|
-
assets list [--category <c>] [--source <s>]
|
|
44
|
-
|
|
50
|
+
# unified import: models, packs, materials, sprites, components, icons
|
|
51
|
+
assets list [--category <c>] [--source <s>] [--kind material|sprite|spritePack]
|
|
52
|
+
# browse the generated model/sprite index, or the material/sprite-pack catalog
|
|
53
|
+
assets search <term> # grep the model index
|
|
45
54
|
assets pull <source-id> [--dir public] [--mirror <baseUrl>] [--offline]
|
|
46
|
-
# download + extract a
|
|
55
|
+
# download + extract a pack into <dir>/models|materials|sprites/<source>/
|
|
47
56
|
assets register <path|url> --category <c> --license <l> [--author <a>]
|
|
48
57
|
# register a one-off single into the shipped index
|
|
49
|
-
assets reindex [public/models] # regenerate generated/*.json from pulled packs
|
|
58
|
+
assets reindex [public/models] # regenerate generated/*.json from pulled model packs
|
|
59
|
+
assets reindex-sprites [public/sprites] # regenerate generated-sprites/*.json from pulled sprite packs
|
|
50
60
|
assets verify # license + alias-integrity gate
|
|
61
|
+
assets provenance <id> [<id>...] # resolve each id's owner (committed/provisioned/dangling); non-zero on any dangling
|
|
51
62
|
```
|
|
52
63
|
|
|
53
|
-
|
|
64
|
+
### Reference integrity
|
|
65
|
+
|
|
66
|
+
Every logical asset id resolves to a declared **owner** through the provisioning contract (`resolveProvenance`): `committed` (a single's shipped URL — resolves on a clean clone with no pull), `provisioned` (a pack index entry whose GLB `assets pull <source>` fetches into the served dir), or `dangling` (nothing owns it, so it can never resolve). `validateAssetReferences(refs)` turns a set of `{ consumer, id }` references into a clean-clone gate: it fails on any dangling reference — naming the consumer, the logical id, and the null resolved path — and returns the exact `assets pull <source>` steps the checkout still needs so provisioning stays deterministic and `ensure-ready`-driven. It resolves references structurally against the catalog rather than grepping source text.
|
|
67
|
+
|
|
68
|
+
At runtime the shell validates a model fetch *before* parsing (`classifyAssetResponse` in `@jgengine/core/scene/assetDiagnostics`): it checks HTTP status, content type, and the GLB/glTF signature, then reports `missing`, `html` (a dev-server fallback page served in place of the file), `corrupt`, or `unsupported` with the URL — replacing the opaque `Unexpected token <` GLTF parse error the old path produced when a model was absent.
|
|
69
|
+
|
|
70
|
+
Run in-repo with `bun run --cwd packages/assets src/cli/pull.ts <verb> GǪ`. (`add <path|url> --license GǪ` still works as an alias for `register`.)
|
|
54
71
|
|
|
55
72
|
### Mirror fallback and offline pulls
|
|
56
73
|
|
|
57
74
|
`pull` never has just one path to the bytes. For a given `source-id` it tries, in order, until one succeeds:
|
|
58
75
|
|
|
59
|
-
1. **Mirror base override**
|
|
60
|
-
2. **The default GitHub-release mirror**
|
|
61
|
-
3. **The primary provider path**
|
|
62
|
-
4. **The pack's own `mirror`**
|
|
76
|
+
1. **Mirror base override** G�� `--mirror <baseUrl>` (or the `JGENGINE_ASSETS_MIRROR` env var if `--mirror` is not passed) G�� the archive is expected at `<baseUrl>/<provider>/<source-id>.zip`, e.g. `https://my-mirror.example.com/quaternius/quaternius-stylized-nature.zip`.
|
|
77
|
+
2. **The default GitHub-release mirror** G�� `https://github.com/Noisemaker111/jgengine/releases/download/packs/<provider>-<source-id>.zip`, on this repo's own rolling `packs` release (no separate assets repo). github.com is reachable from every cloud sandbox with no network-policy change, so zero-setup sessions still pull. `.github/workflows/mirror-assets.yml` (weekly cron + manual dispatch) keeps the release in sync with `src/sources/*.ts` automatically G�� adding a catalog entry is the whole publishing step, no manual upload. Skip this hop with `JGENGINE_ASSETS_NO_DEFAULT_MIRROR=1`. Model/sprite pack failures fail the job; individual ambientCG material 404s are soft (logged, non-fatal).
|
|
78
|
+
3. **The primary provider path** G�� pinned `{ url, sha256? }` when stable: **KayKit** G�� `github.com/KayKit-Game-Assets/*/archive/GǪ/main.zip`; **Quaternius** free Standard packs G�� OpenGameArt direct zips (site pages JS-gate). Else scrape. `extractGlbs` packs co-located `.gltf`+`.bin` into `.glb`, flattens external image URIs to basenames, and returns each referenced texture so `pull` writes it beside the models — a pulled pack renders textured out of the box.
|
|
79
|
+
4. **The pack's own `mirror`** G�� an optional direct archive URL set on the `AssetSource` entry itself (`src/sources/*.ts`), tried as a last resort.
|
|
63
80
|
|
|
64
|
-
If every attempt fails, `pull` throws one aggregated error naming every URL it tried and why each one failed. Whenever the source's `download` is pinned with a `sha256`, the downloaded bytes are hashed and checked against it **no matter which path supplied them**
|
|
81
|
+
If every attempt fails, `pull` throws one aggregated error naming every URL it tried and why each one failed. Whenever the source's `download` is pinned with a `sha256`, the downloaded bytes are hashed and checked against it **no matter which path supplied them** G�� a mirror serving stale or tampered bytes is rejected and the next source in the chain is tried instead.
|
|
65
82
|
|
|
66
|
-
`--offline` skips the network entirely: it succeeds immediately if `<dir>/models/<source-id>/` already has files in it, and otherwise fails fast with a message telling you to pull once on a connected machine or point `--mirror`/`JGENGINE_ASSETS_MIRROR` at a reachable archive
|
|
83
|
+
`--offline` skips the network entirely: it succeeds immediately if `<dir>/models/<source-id>/` already has files in it, and otherwise fails fast with a message telling you to pull once on a connected machine or point `--mirror`/`JGENGINE_ASSETS_MIRROR` at a reachable archive G�� useful for CI scripts that should error in seconds instead of hanging on a blocked fetch.
|
|
67
84
|
|
|
68
|
-
**Network-restricted environments**
|
|
85
|
+
**Network-restricted environments** G�� a `403` on `CONNECT` from an outbound proxy means the environment's network policy blocks that provider host (common in sandboxed cloud sessions); it is a policy decision, not a transient failure, so retrying never helps. Either allowlist the host in the environment settings, or pull once on a machine that can reach the providers, then:
|
|
69
86
|
|
|
70
87
|
- commit (or otherwise host) the resulting `public/models/<source-id>/` directory so restricted environments read it straight off disk and use `assets pull --offline` as a fast, honest no-op check, or
|
|
71
88
|
- host your own mirror of the zip archives at `<baseUrl>/<provider>/<source-id>.zip` and set `JGENGINE_ASSETS_MIRROR=<baseUrl>` (or pass `--mirror <baseUrl>`) so `pull` fetches from it instead of the original provider.
|
|
72
89
|
|
|
73
90
|
## Adding assets
|
|
74
91
|
|
|
75
|
-
**A whole new pack**
|
|
92
|
+
**A whole new pack** G�� add one entry to the matching `src/sources/*.ts` (this is the layer contributors PR). No filenames are hand-typed; `reindex` reads the real `.glb` names out of the extracted pack, so entries can't silently 404.
|
|
76
93
|
|
|
77
94
|
```ts
|
|
78
|
-
// src/sources/
|
|
79
|
-
{ id: "
|
|
95
|
+
// src/sources/quaternius.ts G�� QUATERNIUS_PACKS
|
|
96
|
+
{ id: "quaternius-fantasy-props", slug: "fantasypropsmegakit", title: "Fantasy Props MegaKit", categories: ["fantasy", "prop"] },
|
|
80
97
|
```
|
|
81
98
|
|
|
82
99
|
```bash
|
|
83
|
-
bun src/cli/pull.ts pull
|
|
84
|
-
bun src/cli/pull.ts reindex ../../apps/dev/public/models
|
|
85
|
-
bun src/cli/pull.ts verify
|
|
100
|
+
bun src/cli/pull.ts pull quaternius-fantasy-props --dir ../../apps/dev/public # fetch + extract GLBs
|
|
101
|
+
bun src/cli/pull.ts reindex ../../apps/dev/public/models # regenerate generated/*.json + barrel
|
|
102
|
+
bun src/cli/pull.ts verify # license + alias gate
|
|
86
103
|
```
|
|
87
104
|
|
|
88
|
-
A **new provider** is just a new `src/sources/<provider>.ts` added to the `sources` array in `src/sources/index.ts`. Pinned providers use `download: { url, sha256? }`; providers
|
|
105
|
+
A **new provider** is just a new `src/sources/<provider>.ts` added to the `sources` array in `src/sources/index.ts`. Pinned providers use `download: { url, sha256? }`; providers whose pages JS-gate the download and can't be pinned use `download: { scrape: <page> }`. Any entry can also carry an optional top-level `mirror: <archiveUrl>` G�� a direct URL `pull` falls back to if both a `--mirror`/`JGENGINE_ASSETS_MIRROR` override and the primary path fail (see "Mirror fallback and offline pulls" above). Kenney.nl is not an eligible provider for this repo G�� see CLAUDE.md "Never Kenney".
|
|
106
|
+
|
|
107
|
+
**A whole new sprite/icon pack** G�� same shape as a model pack, just `kind: "sprite"` and `reindex-sprites` instead of `reindex`; files are matched by `.svg`/`.png` extension, deduped by basename regardless of archive nesting, so no filenames are hand-typed here either. `src/sources/gameicons.ts` is the current example (`gameicons-icons`); a new sprite provider follows the same shape in its own `src/sources/<provider>.ts`.
|
|
108
|
+
|
|
109
|
+
```bash
|
|
110
|
+
bun src/cli/pull.ts pull gameicons-icons --dir ../../apps/dev/public # fetch + extract SVG/PNG
|
|
111
|
+
bun src/cli/pull.ts reindex-sprites ../../apps/dev/public/sprites # regenerate generated-sprites/*.json + barrel
|
|
112
|
+
```
|
|
89
113
|
|
|
90
|
-
**A single one-off**
|
|
114
|
+
**A single one-off** G�� no code edit, zero bytes stored (URL) or copied into `local/` (path):
|
|
91
115
|
|
|
92
116
|
```bash
|
|
93
|
-
assets add "https://poly.pizza
|
|
117
|
+
assets add "https://poly.pizza/GǪ/model.glb" --category prop --license CC0-1.0 --author "Some Author"
|
|
94
118
|
```
|
|
95
119
|
|
|
96
120
|
## Importing in code
|
|
97
121
|
|
|
98
|
-
Build the catalog once, then address ids (or aliases)
|
|
122
|
+
Build the catalog once, then address ids (or aliases) G�� resolve returns `{ url }`:
|
|
99
123
|
|
|
100
124
|
```ts
|
|
101
125
|
import { buildCatalog } from "@jgengine/assets";
|
|
102
126
|
|
|
103
127
|
const catalog = buildCatalog({ basePath: "/models" });
|
|
104
128
|
|
|
105
|
-
catalog.resolve("
|
|
106
|
-
catalog.resolve("nature/tree_pine");
|
|
129
|
+
catalog.resolve("quaternius-stylized-nature/Pine_1"); // { url: "/models/quaternius-stylized-nature/Pine_1.glb" }
|
|
130
|
+
catalog.resolve("nature/tree_pine"); // alias G�� same url
|
|
107
131
|
|
|
108
132
|
// wire ids straight into a game's model seams:
|
|
109
133
|
export const game: PlayableGame = {
|
|
110
|
-
//
|
|
134
|
+
// GǪ
|
|
111
135
|
objectModels: {
|
|
112
|
-
"
|
|
136
|
+
"quaternius-stylized-nature/Pine_1": { url: catalog.resolve("quaternius-stylized-nature/Pine_1")!.url, scale: 1.4 },
|
|
113
137
|
},
|
|
114
138
|
entityModels: {
|
|
115
|
-
hero: { url: catalog.resolve("
|
|
139
|
+
hero: { url: catalog.resolve("kaykit-adventurers/Barbarian")!.url, scale: 1.1 },
|
|
116
140
|
},
|
|
117
141
|
};
|
|
118
142
|
```
|
|
119
143
|
|
|
120
|
-
`buildCatalog({ sources: ["
|
|
144
|
+
`buildCatalog({ sources: ["quaternius-stylized-nature"] })` restricts to chosen packs; `includeAliases` / `includeSingles` default true. Discover ids with `assets add <query>` (or `assets search <term>` / `assets list --category <c>`) instead of memorizing them.
|
|
145
|
+
|
|
146
|
+
Materials resolve the same way G�� ids (or `material/GǪ` aliases) to normalized PBR map URLs:
|
|
147
|
+
|
|
148
|
+
```ts
|
|
149
|
+
import { buildMaterialCatalog } from "@jgengine/assets";
|
|
150
|
+
|
|
151
|
+
const materials = buildMaterialCatalog({ basePath: "/materials" });
|
|
152
|
+
|
|
153
|
+
materials.resolve("ambientcg-grass001")!.maps.color; // "/materials/ambientcg-grass001/color.jpg"
|
|
154
|
+
materials.resolve("material/grass")!.maps.normal; // alias G�� "/materials/ambientcg-grass001/normal.jpg"
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
Sprite/icon packs resolve the same way once pulled + reindexed G�� individual files, not whole packs:
|
|
158
|
+
|
|
159
|
+
```ts
|
|
160
|
+
import { buildSpriteCatalog } from "@jgengine/assets";
|
|
161
|
+
|
|
162
|
+
const sprites = buildSpriteCatalog({ basePath: "/sprites" });
|
|
163
|
+
|
|
164
|
+
sprites.resolve("gameicons-icons/sword")!.url; // "/sprites/gameicons-icons/sword.svg"
|
|
165
|
+
```
|
|
121
166
|
|
|
122
167
|
### Serving the bytes
|
|
123
168
|
|
|
124
|
-
A resolved id only yields a **URL**
|
|
169
|
+
A resolved id only yields a **URL** G�� the GLB must be somewhere your app serves. For a game, `pull` the packs into your app's `public/`, and line `basePath` up with it:
|
|
125
170
|
|
|
126
171
|
```bash
|
|
127
|
-
bun src/cli/pull.ts pull
|
|
172
|
+
bun src/cli/pull.ts pull quaternius-stylized-nature --dir ../../apps/dev/public # G�� apps/dev/public/models/quaternius-stylized-nature/*.glb
|
|
128
173
|
```
|
|
129
174
|
|
|
130
|
-
`buildCatalog({ basePath: "/models" })` then resolves to `/models/
|
|
175
|
+
`buildCatalog({ basePath: "/models" })` then resolves to `/models/quaternius-stylized-nature/GǪ`, which the dev server serves from `public/models/` (gitignored G�� the bytes are the consumer's, fetched once from the provider's CDN).
|
|
176
|
+
|
|
177
|
+
Sprite/icon packs pull the same way, into `public/sprites/`:
|
|
178
|
+
|
|
179
|
+
```bash
|
|
180
|
+
bun src/cli/pull.ts pull gameicons-icons --dir ../../apps/dev/public # G�� apps/dev/public/sprites/gameicons-icons/*.svg
|
|
181
|
+
bun src/cli/pull.ts reindex-sprites ../../apps/dev/public/sprites # G�� src/generated-sprites/gameicons-icons.json
|
|
182
|
+
```
|
|
131
183
|
|
|
132
184
|
## Notes
|
|
133
185
|
|
|
134
|
-
-
|
|
135
|
-
- Quaternius / KayKit pages gate downloads behind JS; automated `pull` falls back to a clear error when no archive link is found — download those manually into the staging dir, then `reindex`.
|
|
186
|
+
- Quaternius / KayKit pages gate downloads behind JS; sources without a pinned OpenGameArt/GitHub zip `scrape` the pack page as a fallback, and automated `pull` falls back to a clear error when no archive link is found G�� download those manually into the staging dir, then `reindex`.
|
|
136
187
|
- `pull`'s mirror fallback and `--offline` guard exist for network-restricted environments (CI, sandboxes without provider access); see "Mirror fallback and offline pulls" above.
|
|
188
|
+
- `gameicons-icons` is **CC BY 3.0**, not CC0 G�� a game using it needs one credit line (source, "game-icons.net contributors", license) per the engine's asset-credit rule; the repo's own per-author `license.txt` files carry the individual credits behind this pack's single collective `author` field.
|
|
189
|
+
- `src/generated-sprites/` starts empty for a brand-new sprite source G�� same as any brand-new model pack, the committed per-file index only exists after someone runs `pull` + `reindex-sprites` with real network access; until then the source is fully declared (and the weekly mirror job will fetch it) but has no individually-addressable ids yet.
|
package/dist/aliases.d.ts
CHANGED
|
@@ -1,2 +1,7 @@
|
|
|
1
1
|
import type { AssetAlias } from "./manifest.js";
|
|
2
|
+
/**
|
|
3
|
+
* Semantic keys → live catalog ids. Prefer these in games so re-homes only
|
|
4
|
+
* touch this table. Never point at kenney-*. Curated starter theme ids
|
|
5
|
+
* (`asset:person_casual`, `nature_tree`, …) come from {@link starterAliases}.
|
|
6
|
+
*/
|
|
2
7
|
export declare const aliases: readonly AssetAlias[];
|
package/dist/aliases.js
CHANGED
|
@@ -1,11 +1,30 @@
|
|
|
1
|
+
import { starterAliases } from "./packs/starter.js";
|
|
2
|
+
/**
|
|
3
|
+
* Semantic keys → live catalog ids. Prefer these in games so re-homes only
|
|
4
|
+
* touch this table. Never point at kenney-*. Curated starter theme ids
|
|
5
|
+
* (`asset:person_casual`, `nature_tree`, …) come from {@link starterAliases}.
|
|
6
|
+
*/
|
|
1
7
|
export const aliases = [
|
|
2
|
-
{ key: "nature/tree_pine", target: "
|
|
3
|
-
{ key: "nature/
|
|
4
|
-
{ key: "nature/
|
|
5
|
-
{ key: "nature/
|
|
6
|
-
{ key: "nature/
|
|
7
|
-
{ key: "
|
|
8
|
-
{ key: "
|
|
9
|
-
{ key: "
|
|
10
|
-
{ key: "
|
|
8
|
+
{ key: "nature/tree_pine", target: "quaternius-stylized-nature/Pine_1" },
|
|
9
|
+
{ key: "nature/tree_common", target: "quaternius-stylized-nature/CommonTree_1" },
|
|
10
|
+
{ key: "nature/tree_dead", target: "quaternius-stylized-nature/DeadTree_1" },
|
|
11
|
+
{ key: "nature/bush", target: "quaternius-stylized-nature/Bush_Common" },
|
|
12
|
+
{ key: "nature/rock", target: "quaternius-stylized-nature/Rock_Medium_1" },
|
|
13
|
+
{ key: "character/rogue", target: "kaykit-adventurers/Rogue" },
|
|
14
|
+
{ key: "character/knight", target: "kaykit-adventurers/Knight" },
|
|
15
|
+
{ key: "character/mage", target: "kaykit-adventurers/Mage" },
|
|
16
|
+
{ key: "character/barbarian", target: "kaykit-adventurers/Barbarian" },
|
|
17
|
+
{ key: "scifi/alien", target: "quaternius-modular-scifi/Alien_Cyclop" },
|
|
18
|
+
{ key: "scifi/chest", target: "quaternius-modular-scifi/Prop_Chest" },
|
|
19
|
+
{ key: "scifi/crate", target: "quaternius-modular-scifi/Prop_Crate3" },
|
|
20
|
+
{ key: "scifi/computer", target: "quaternius-modular-scifi/Prop_Computer" },
|
|
21
|
+
{ key: "dungeon/chest", target: "kaykit-dungeon/chest" },
|
|
22
|
+
{ key: "furniture/bed", target: "kaykit-furniture/bed_double_A" },
|
|
23
|
+
{ key: "furniture/couch", target: "kaykit-furniture/couch" },
|
|
24
|
+
{ key: "furniture/table", target: "kaykit-furniture/table_medium" },
|
|
25
|
+
{ key: "city/car_sedan", target: "kaykit-city-builder/car_sedan" },
|
|
26
|
+
{ key: "city/car_police", target: "kaykit-city-builder/car_police" },
|
|
27
|
+
{ key: "city/building_a", target: "kaykit-city-builder/building_A" },
|
|
28
|
+
{ key: "city/streetlight", target: "kaykit-city-builder/streetlight" },
|
|
29
|
+
...starterAliases(),
|
|
11
30
|
];
|
package/dist/catalogs/build.d.ts
CHANGED
|
@@ -1,5 +1,20 @@
|
|
|
1
1
|
import { type AssetCatalog } from "@jgengine/core/scene/assetCatalog";
|
|
2
2
|
import type { IndexEntry } from "../manifest.js";
|
|
3
|
+
/**
|
|
4
|
+
* A durable, hand-or-tool authored catalog entry that is not part of the generated pack index,
|
|
5
|
+
* singles, or aliases — the shape the editor writes into a promoted game's `src/game/assets.ts`
|
|
6
|
+
* when an asset is imported. `label` is human-facing only and is intentionally not registered
|
|
7
|
+
* into the catalog (it mirrors how a single asset's author/license live only in the source
|
|
8
|
+
* literal), so at runtime an extra resolves to exactly `{ url }`.
|
|
9
|
+
*/
|
|
10
|
+
export interface CatalogExtra {
|
|
11
|
+
/** Catalog id the entry resolves under (matches what a folder rescan would produce). */
|
|
12
|
+
id: string;
|
|
13
|
+
/** URL the shipped game serves the model from (e.g. `/models/imported/Ship.glb`). */
|
|
14
|
+
url: string;
|
|
15
|
+
/** Human-facing label kept only in the source literal; never registered into the catalog. */
|
|
16
|
+
label?: string;
|
|
17
|
+
}
|
|
3
18
|
export interface BuildCatalogOptions {
|
|
4
19
|
/** URL prefix where pulled pack GLBs live (consumer's `public/models`). */
|
|
5
20
|
basePath?: string;
|
|
@@ -7,6 +22,18 @@ export interface BuildCatalogOptions {
|
|
|
7
22
|
sources?: readonly string[];
|
|
8
23
|
includeAliases?: boolean;
|
|
9
24
|
includeSingles?: boolean;
|
|
25
|
+
/**
|
|
26
|
+
* Extra catalog entries registered after packs/singles and before aliases: imported assets the
|
|
27
|
+
* editor persists into a promoted game's typed catalog. Registered last-writer-wins after packs
|
|
28
|
+
* (so an extra can override a pack id) but before aliases (so an alias can target an extra).
|
|
29
|
+
*/
|
|
30
|
+
extras?: readonly CatalogExtra[];
|
|
10
31
|
}
|
|
11
32
|
export declare function entryUrl(basePath: string, entry: IndexEntry): string;
|
|
33
|
+
/**
|
|
34
|
+
* Builds a game's asset catalog from the generated CC0 pack index plus singles, extras, and aliases.
|
|
35
|
+
* Registration order is packs → singles → {@link BuildCatalogOptions.extras | extras} → aliases:
|
|
36
|
+
* packs and singles come first, extras override them last-writer-wins, and aliases resolve last so
|
|
37
|
+
* they can target an extra. See {@link BuildCatalogOptions} for filtering and opt-outs.
|
|
38
|
+
*/
|
|
12
39
|
export declare function buildCatalog(options?: BuildCatalogOptions): AssetCatalog;
|
package/dist/catalogs/build.js
CHANGED
|
@@ -2,32 +2,58 @@ import { createAssetCatalog } from "@jgengine/core/scene/assetCatalog";
|
|
|
2
2
|
import { aliases } from "../aliases.js";
|
|
3
3
|
import { generatedIndex } from "../generated/index.js";
|
|
4
4
|
import { singles } from "../singles.js";
|
|
5
|
+
import { sources as declaredSources } from "../sources/index.js";
|
|
5
6
|
export function entryUrl(basePath, entry) {
|
|
6
7
|
return `${basePath.replace(/\/+$/, "")}/${entry.source}/${entry.file}`;
|
|
7
8
|
}
|
|
9
|
+
/**
|
|
10
|
+
* Builds a game's asset catalog from the generated CC0 pack index plus singles, extras, and aliases.
|
|
11
|
+
* Registration order is packs → singles → {@link BuildCatalogOptions.extras | extras} → aliases:
|
|
12
|
+
* packs and singles come first, extras override them last-writer-wins, and aliases resolve last so
|
|
13
|
+
* they can target an extra. See {@link BuildCatalogOptions} for filtering and opt-outs.
|
|
14
|
+
*/
|
|
8
15
|
export function buildCatalog(options = {}) {
|
|
9
16
|
const basePath = options.basePath ?? "/models";
|
|
10
17
|
const includeAliases = options.includeAliases ?? true;
|
|
11
18
|
const includeSingles = options.includeSingles ?? true;
|
|
12
19
|
const sourceFilter = options.sources === undefined ? null : new Set(options.sources);
|
|
20
|
+
if (sourceFilter !== null) {
|
|
21
|
+
const knownSourceIds = new Set(declaredSources.map((source) => source.id));
|
|
22
|
+
for (const id of sourceFilter) {
|
|
23
|
+
if (!knownSourceIds.has(id)) {
|
|
24
|
+
throw new Error(`buildCatalog: unknown source id "${id}" — not declared in packages/assets/src/sources/*.ts`);
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
}
|
|
13
28
|
const catalog = createAssetCatalog();
|
|
14
29
|
for (const entry of generatedIndex) {
|
|
15
30
|
if (sourceFilter !== null && !sourceFilter.has(entry.source))
|
|
16
31
|
continue;
|
|
17
32
|
const url = entryUrl(basePath, entry);
|
|
18
|
-
catalog.register(entry.id,
|
|
33
|
+
catalog.register(entry.id, {
|
|
34
|
+
url,
|
|
35
|
+
...(entry.dims === undefined ? {} : { dims: entry.dims }),
|
|
36
|
+
...(entry.collisionMesh === undefined ? {} : { collisionMesh: entry.collisionMesh }),
|
|
37
|
+
});
|
|
19
38
|
}
|
|
20
39
|
if (includeSingles) {
|
|
21
40
|
for (const single of singles) {
|
|
22
41
|
catalog.register(single.id, { url: single.url });
|
|
23
42
|
}
|
|
24
43
|
}
|
|
44
|
+
for (const extra of options.extras ?? []) {
|
|
45
|
+
catalog.register(extra.id, { url: extra.url });
|
|
46
|
+
}
|
|
25
47
|
if (includeAliases) {
|
|
26
48
|
for (const alias of aliases) {
|
|
27
49
|
const ref = catalog.resolve(alias.target);
|
|
28
50
|
if (ref === null)
|
|
29
51
|
continue;
|
|
30
|
-
catalog.register(alias.key,
|
|
52
|
+
catalog.register(alias.key, {
|
|
53
|
+
url: ref.url,
|
|
54
|
+
...(ref.dims === undefined ? {} : { dims: ref.dims }),
|
|
55
|
+
...(ref.collisionMesh === undefined ? {} : { collisionMesh: ref.collisionMesh }),
|
|
56
|
+
});
|
|
31
57
|
}
|
|
32
58
|
}
|
|
33
59
|
return catalog;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { type AssetCatalog } from "@jgengine/core/scene/assetCatalog";
|
|
2
|
+
/** Options for `buildSpriteCatalog`. */
|
|
3
|
+
export interface BuildSpriteCatalogOptions {
|
|
4
|
+
/** URL prefix where pulled sprite/icon files live (consumer's `public/sprites`). */
|
|
5
|
+
basePath?: string;
|
|
6
|
+
/** Restrict to these source ids; omit for all. */
|
|
7
|
+
sources?: readonly string[];
|
|
8
|
+
}
|
|
9
|
+
/** Resolves individual pulled sprite/icon ids (e.g. `gameicons-icons/sword`) to `{ url }`. */
|
|
10
|
+
export declare function buildSpriteCatalog(options?: BuildSpriteCatalogOptions): AssetCatalog;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { createAssetCatalog } from "@jgengine/core/scene/assetCatalog";
|
|
2
|
+
import { generatedSpriteIndex } from "../generated-sprites/index.js";
|
|
3
|
+
import { entryUrl } from "./build.js";
|
|
4
|
+
/** Resolves individual pulled sprite/icon ids (e.g. `gameicons-icons/sword`) to `{ url }`. */
|
|
5
|
+
export function buildSpriteCatalog(options = {}) {
|
|
6
|
+
const basePath = options.basePath ?? "/sprites";
|
|
7
|
+
const sourceFilter = options.sources === undefined ? null : new Set(options.sources);
|
|
8
|
+
const catalog = createAssetCatalog();
|
|
9
|
+
for (const entry of generatedSpriteIndex) {
|
|
10
|
+
if (sourceFilter !== null && !sourceFilter.has(entry.source))
|
|
11
|
+
continue;
|
|
12
|
+
catalog.register(entry.id, { url: entryUrl(basePath, entry) });
|
|
13
|
+
}
|
|
14
|
+
return catalog;
|
|
15
|
+
}
|
|
@@ -1,2 +1,7 @@
|
|
|
1
1
|
import { type BuildCatalogOptions } from "./build.js";
|
|
2
|
+
/**
|
|
3
|
+
* Catalog restricted to the curated starter packs (people/props/nature/urban).
|
|
4
|
+
* Prefer this for scaffolds and probes so `asset:person_casual` etc. resolve
|
|
5
|
+
* without pulling the whole library. Full index: {@link buildCatalog}.
|
|
6
|
+
*/
|
|
2
7
|
export declare function createStarterCatalog(options?: BuildCatalogOptions): import("@jgengine/core/scene/assetCatalog").AssetCatalog<import("@jgengine/core/scene/assetCatalog").ModelAssetRef>;
|
package/dist/catalogs/starter.js
CHANGED
|
@@ -1,4 +1,13 @@
|
|
|
1
|
+
import { STARTER_SOURCE_PACKS } from "../packs/starter.js";
|
|
1
2
|
import { buildCatalog } from "./build.js";
|
|
3
|
+
/**
|
|
4
|
+
* Catalog restricted to the curated starter packs (people/props/nature/urban).
|
|
5
|
+
* Prefer this for scaffolds and probes so `asset:person_casual` etc. resolve
|
|
6
|
+
* without pulling the whole library. Full index: {@link buildCatalog}.
|
|
7
|
+
*/
|
|
2
8
|
export function createStarterCatalog(options = {}) {
|
|
3
|
-
return buildCatalog(
|
|
9
|
+
return buildCatalog({
|
|
10
|
+
...options,
|
|
11
|
+
sources: options.sources ?? STARTER_SOURCE_PACKS,
|
|
12
|
+
});
|
|
4
13
|
}
|
package/dist/cli/paths.d.ts
CHANGED
|
@@ -1,4 +1,12 @@
|
|
|
1
|
-
/** Sibling of `cli/` under `src/` (dev) or `dist/` (published) so reindex writes the tree consumers import.
|
|
1
|
+
/** Sibling of `cli/` under `src/` (dev) or `dist/` (published) so reindex writes the tree consumers import.
|
|
2
|
+
* @internal
|
|
3
|
+
*/
|
|
2
4
|
export declare function resolveGeneratedDir(cliDir: string): string;
|
|
5
|
+
/** Sprite-pack counterpart of `resolveGeneratedDir` — a separate generated tree, same sibling layout.
|
|
6
|
+
* @internal
|
|
7
|
+
*/
|
|
8
|
+
export declare function resolveGeneratedSpritesDir(cliDir: string): string;
|
|
9
|
+
/** @internal */
|
|
3
10
|
export declare function resolvePackageTreeRoot(cliDir: string): string;
|
|
11
|
+
/** @internal */
|
|
4
12
|
export declare function resolvePackageRoot(cliDir: string): string;
|
package/dist/cli/paths.js
CHANGED
|
@@ -1,11 +1,21 @@
|
|
|
1
1
|
import { join, resolve } from "node:path";
|
|
2
|
-
/** Sibling of `cli/` under `src/` (dev) or `dist/` (published) so reindex writes the tree consumers import.
|
|
2
|
+
/** Sibling of `cli/` under `src/` (dev) or `dist/` (published) so reindex writes the tree consumers import.
|
|
3
|
+
* @internal
|
|
4
|
+
*/
|
|
3
5
|
export function resolveGeneratedDir(cliDir) {
|
|
4
6
|
return join(resolve(cliDir, ".."), "generated");
|
|
5
7
|
}
|
|
8
|
+
/** Sprite-pack counterpart of `resolveGeneratedDir` — a separate generated tree, same sibling layout.
|
|
9
|
+
* @internal
|
|
10
|
+
*/
|
|
11
|
+
export function resolveGeneratedSpritesDir(cliDir) {
|
|
12
|
+
return join(resolve(cliDir, ".."), "generated-sprites");
|
|
13
|
+
}
|
|
14
|
+
/** @internal */
|
|
6
15
|
export function resolvePackageTreeRoot(cliDir) {
|
|
7
16
|
return resolve(cliDir, "..");
|
|
8
17
|
}
|
|
18
|
+
/** @internal */
|
|
9
19
|
export function resolvePackageRoot(cliDir) {
|
|
10
20
|
return resolve(cliDir, "..", "..");
|
|
11
21
|
}
|
package/dist/cli/pull.d.ts
CHANGED
|
@@ -1,8 +1,20 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
/** Sibling of `cli/` under `src/` (dev) or `dist/` (published) so reindex writes the tree consumers import. */
|
|
3
3
|
export declare const generatedDir: string;
|
|
4
|
+
/** Sprite-pack counterpart of `generatedDir`. */
|
|
5
|
+
export declare const generatedSpritesDir: string;
|
|
4
6
|
export { resolveGeneratedDir } from "./paths.js";
|
|
7
|
+
/** @internal */
|
|
5
8
|
export declare function flag(argv: string[], name: string): string | undefined;
|
|
9
|
+
/**
|
|
10
|
+
* The runtime's own fetch, with a curl fallback for hosts it cannot reach —
|
|
11
|
+
* some proxied sandboxes tear down bun's TLS stream to GitHub's release-asset
|
|
12
|
+
* host while curl (which honors SSL_CERT_FILE) gets through fine.
|
|
13
|
+
*/
|
|
14
|
+
export declare const cliFetch: typeof fetch;
|
|
15
|
+
/** @internal */
|
|
6
16
|
export declare function describeNetworkFailure(error: unknown): string;
|
|
17
|
+
/** @internal */
|
|
7
18
|
export declare function isPopulated(dir: string): boolean;
|
|
19
|
+
/** @internal */
|
|
8
20
|
export declare function cmdPull(argv: string[]): Promise<void>;
|