@hyprune/schema 0.7.0 → 0.8.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 +92 -0
- package/README.md +25 -4
- package/examples/world-npcs.json +493 -0
- package/lib/validate.d.mts +11 -1
- package/lib/validate.mjs +172 -18
- package/package.json +1 -1
- package/v0.23/ipc.schema.json +19261 -0
- package/v0.9/common.schema.json +478 -0
- package/v0.9/world.schema.json +2390 -0
package/CHANGELOG.md
CHANGED
|
@@ -298,3 +298,95 @@ Object manifests use the world format numbering: a world may use objects whose
|
|
|
298
298
|
## @hyprune/schema 0.7.0 (2026-10-12)
|
|
299
299
|
|
|
300
300
|
Publishes IPC 0.21 (markers, personal quests, focus sessions) and IPC 0.22 (object catalog, user placements, libraries), plus the object manifest (`object.json` 0.9 and the 0.10 draft), library and library release-record schemas.
|
|
301
|
+
|
|
302
|
+
## World 0.9: characters, paths, seats and keepClear (RFC-0011 P2)
|
|
303
|
+
|
|
304
|
+
- `objectAssets[]` (at most 32, ids unique) take exactly one source: inline
|
|
305
|
+
`{id, scene, animations?, collision?, lighting?, traits?, slots?}` (the 0.8
|
|
306
|
+
asset plus object.json 0.9 `traits` and `slots`; `decorative`, `collidable`,
|
|
307
|
+
`movable`, `character` and `seat` are allowed, `mover`, `mount`, `machine` and
|
|
308
|
+
`interactive` rejected), `dir {id, dir}` (a package directory holding
|
|
309
|
+
`object.json`, object format at most the world's) or `library {id, library,
|
|
310
|
+
object}` (`library` is `<reverse-domain id>@<semver>`, `object` a slug).
|
|
311
|
+
`animations` is shorthand for `traits.decorative.animations` and `collision`
|
|
312
|
+
for `traits.collidable`; giving both forms of one is invalid.
|
|
313
|
+
- `objects[]` gain `path` (a `route` path; replaces `pose`), `reverse` (only
|
|
314
|
+
with `path`), `seat` (a `seats[]` id, `<objectId>/<anchorId>` or
|
|
315
|
+
`<objectId>`; characters without a path), `accent` (linear RGB 0..1),
|
|
316
|
+
`interactions` (1..8, replacing the asset's list) and `locked` (movable
|
|
317
|
+
assets). `pose` is required unless `path` is set and forbidden with it. A
|
|
318
|
+
character's `scale` must be 1; at most 16 character instances and 8 per path.
|
|
319
|
+
- Instance interactions `{id, label (1..32), prompt? (1..64), action}` with
|
|
320
|
+
`say {lines[1..8]}`, `waypoint {target: {zoneId}|{position}|{anchor}|{object}}`,
|
|
321
|
+
`guide {path}` (a route) or `panel {panel}`. `travel` and `quest` are
|
|
322
|
+
reserved and rejected. Asset-level interactions stay `say`/`panel`.
|
|
323
|
+
- `paths[]` (at most 64, 1,024 points in total): `{id, name?, use?
|
|
324
|
+
(route|track|generic, default generic), closed?, points[2..256] {position,
|
|
325
|
+
type: line|curve|arc}, speed? (0.1..30), stops?[<=32]}`. A stop is `{point,
|
|
326
|
+
seconds? (0.5..600), clip? (look_around|wave|nod|idle_fidget), face?
|
|
327
|
+
({position}|{anchor}|{object}), seat?}` with at most one of clip, face and
|
|
328
|
+
seat, one stop per point and the point below the point count. Track stops
|
|
329
|
+
take only `point` and `seconds`; generic paths have no stops. An `arc` needs
|
|
330
|
+
a horizontal chord of at least 0.1 m.
|
|
331
|
+
- `seats[]` (at most 64): `{id, pose, height (0.2..1), use? (["sit"]),
|
|
332
|
+
approach? (0.3..2)}`. `keepClear[]` (at most 64): `{id, min, max}`, min
|
|
333
|
+
below max on every axis.
|
|
334
|
+
- `validate('world', manifest, undefined, '0.9', {assets})` adds unique ids,
|
|
335
|
+
asset, path, seat, waypoint and face references, route-only bindings,
|
|
336
|
+
character-only and movable-only fields, pose/path exclusivity, normalised
|
|
337
|
+
seat poses, arc chords, the point total, keepClear ordering and the
|
|
338
|
+
character limits. `assets` maps a dir or library asset id to its parsed
|
|
339
|
+
`object.json`, so its traits are checked like an inline asset's; without it
|
|
340
|
+
those checks skip the asset. Reserved traits and actions are reported with a
|
|
341
|
+
plain reason. `worldLimits` exports the limits.
|
|
342
|
+
- `validate('scene', gltf, undefined, '0.9', {world, asset})` reads an inline
|
|
343
|
+
asset's animations and proxy from either form and checks an inline
|
|
344
|
+
character's skin and clips; dir and library assets are checked as objects.
|
|
345
|
+
- `v0.9/common.schema.json` is the 0.8 common definitions under the 0.9 `$id`
|
|
346
|
+
(the directory's IPC, input, object and library schemas are untouched).
|
|
347
|
+
`examples/world-npcs.json` is a synthetic 0.9 manifest. Everything else is
|
|
348
|
+
inherited from 0.8 unchanged. Inheritance test included.
|
|
349
|
+
|
|
350
|
+
## IPC 0.23: characters, paths and interactions (RFC-0011 P2)
|
|
351
|
+
|
|
352
|
+
- Required state key `npcs {motion (auto|always|still|off), state
|
|
353
|
+
(none|animating|paused|still|off), reason (null or up to 64 characters, e.g.
|
|
354
|
+
battery), usage {authored, user}, limits {authored (<=16), user (<=8)},
|
|
355
|
+
drawing, aimed, interaction}`. `drawing` is null or `{pathId, use, spawn:
|
|
356
|
+
null|{ref}, bind: null|objectId}` (a `paths.draw` in progress); `aimed` is null
|
|
357
|
+
or `{objectId, name, prompt, interactions[<=8] {id, label, type}}`;
|
|
358
|
+
`interaction` is null or `{objectId, interactionId|null, type
|
|
359
|
+
(choose|say|waypoint|guide|panel), label, choices[<=8] {id, label},
|
|
360
|
+
line|null, lineIndex, lineCount, panel|null}`.
|
|
361
|
+
- `objects.instances[]` gain required `character` (boolean) and `accent`
|
|
362
|
+
(null or linear RGB); `path` is null or a qualified path ref
|
|
363
|
+
(`package/<id>`, `user/<id>`), `activity` null or
|
|
364
|
+
`idle|walking|running|stopped|sitting|guiding|interacting|suspended`, `seat`
|
|
365
|
+
null or a seat ref (up to 192 characters).
|
|
366
|
+
- `editor.paths[]` gain required `use` (route|track|generic), `name`
|
|
367
|
+
(string|null), `speed` (number|null) and `stops` (at most 32, the world 0.9
|
|
368
|
+
stop shape).
|
|
369
|
+
- `interaction.reticle.action` gains `interact`. `graphicsConfig` and
|
|
370
|
+
`graphicsPatch` gain `npc_motion` (`auto`, `always`, `still`, `off`).
|
|
371
|
+
- Methods: `npcs.spawn {ref, path?, pose?, phase?, speed? (0.25..2), accent?,
|
|
372
|
+
reverse?}` (`{revision, id}`; path and pose exclusive, reverse needs a path);
|
|
373
|
+
`npcs.bind {id, path?, pose?, phase?, speed?, accent?, reverse?}` (at least one
|
|
374
|
+
setting); `npcs.disable {id, disabled}`; `npcs.remove {id}|{all:true}`;
|
|
375
|
+
`paths.list {}` (`{paths[<=192]}`: `{ref, source (package|user), id, name,
|
|
376
|
+
use, closed, points, speed, stops, walkable (null for non-routes),
|
|
377
|
+
problems[<=8], bound[<=8]}`); `paths.set {path: {id?, name?, use, closed,
|
|
378
|
+
points[2..256], speed?, stops?}}` (`{revision, id}`); `paths.remove {id,
|
|
379
|
+
unbind?}`; `paths.draw {use?, name?, spawn? {ref, phase?, speed?, accent?},
|
|
380
|
+
bind?}` (`{revision, id}`; spawn and bind exclusive); `paths.finish {}`
|
|
381
|
+
(`{revision, id|null, bound|null}`); `interaction.choose {objectId,
|
|
382
|
+
interactionId|null}`. Path params take a qualified ref or a bare id
|
|
383
|
+
(`package/<id>`); `paths.set/remove/draw/finish` ids are user path ids.
|
|
384
|
+
Grants: `npcs.*` and `paths.set/remove/draw/finish` need `objects.control`,
|
|
385
|
+
`paths.list` needs `state.read`, `interaction.choose` needs `world.control`.
|
|
386
|
+
- Everything else is inherited from 0.22 unchanged (no new grant or event);
|
|
387
|
+
`session.hello` reports `0.23` and lists the ten methods. Inheritance test
|
|
388
|
+
included.
|
|
389
|
+
|
|
390
|
+
## @hyprune/schema 0.8.0 (2026-10-12)
|
|
391
|
+
|
|
392
|
+
Publishes IPC 0.23 and world format 0.9: characters and NPC instances, authored paths (route/track/generic) with stops, seats, keepClear volumes and NPC interactions.
|
package/README.md
CHANGED
|
@@ -2,19 +2,19 @@
|
|
|
2
2
|
|
|
3
3
|
> **Hyprune** is an explorable, world-driven desktop environment for Hyprland: your workspaces become places you can walk through, with live windows on the walls. This repository holds the versioned **schemas** for world packages, IPC and manifests, and their validator. Install Hyprune through the [hyprune](https://github.com/hyprune/hyprune) repository (starter kits, Nix, Arch); learn more at [hyprune.com](https://hyprune.com). Licence: MIT.
|
|
4
4
|
|
|
5
|
-
Versioned contracts for Hyprune, a world-driven Hyprland desktop: world packages (formats 0.1–0.
|
|
5
|
+
Versioned contracts for Hyprune, a world-driven Hyprland desktop: world packages (formats 0.1–0.9), the IPC protocol (0.1–0.23), object and library manifests (0.9, draft 0.10), extension and screen-type manifests and the input keymap. JSON Schema dialect: **2020-12**. Every version is frozen once published; core, the shell and the SDK pin these exact files. Readable reference: [hyprune.com/reference/schema](https://hyprune.com/reference/schema/).
|
|
6
6
|
|
|
7
7
|
## Install
|
|
8
8
|
|
|
9
9
|
```sh
|
|
10
10
|
npm i -D @hyprune/schema
|
|
11
|
-
npx hyprune-validate world world.json - 0.
|
|
12
|
-
npx hyprune-validate scene scene.gltf - 0.
|
|
11
|
+
npx hyprune-validate world world.json - 0.9 # a world package manifest
|
|
12
|
+
npx hyprune-validate scene scene.gltf - 0.9 world.json # its glTF against the world format
|
|
13
13
|
```
|
|
14
14
|
|
|
15
15
|
```js
|
|
16
16
|
import { validate, worldFormats } from '@hyprune/schema';
|
|
17
|
-
import schema from '@hyprune/schema/v0.
|
|
17
|
+
import schema from '@hyprune/schema/v0.9/world.schema.json' with { type: 'json' };
|
|
18
18
|
|
|
19
19
|
const result = validate('world', manifest, undefined, worldFormats.at(-1));
|
|
20
20
|
if (!result.valid) console.error(result.errors.join('\n'));
|
|
@@ -127,6 +127,17 @@ from the proxy. Check an asset's glTF with
|
|
|
127
127
|
`npm run validate -- scene objects/armillary.gltf - 0.8 world.json armillary`).
|
|
128
128
|
See RFC-0004 "world 0.8 placed world objects".
|
|
129
129
|
|
|
130
|
+
World format **0.9** adds characters, paths, seats and keep-clear volumes
|
|
131
|
+
(RFC-0011 P2). An object asset is an inline package glTF (now with optional
|
|
132
|
+
object.json `traits` and `slots`), a package object directory (`dir`) or a
|
|
133
|
+
library object (`library` + `object`). Instances gain `path` (a `route`; it
|
|
134
|
+
replaces `pose`), `reverse`, `seat`, `accent`, `interactions` (`say`,
|
|
135
|
+
`waypoint`, `guide`, `panel`) and `locked`. New top-level `paths` (route,
|
|
136
|
+
track or generic; stops with a clip, facing or seat), `seats` and `keepClear`.
|
|
137
|
+
Pass the object.json of dir and library assets to check their traits too:
|
|
138
|
+
`validate('world', manifest, undefined, '0.9', {assets: {resident: objectJson}})`.
|
|
139
|
+
`examples/world-npcs.json` is a synthetic example. See RFC-0011 "World format 0.9".
|
|
140
|
+
|
|
130
141
|
IPC **0.16** adds the `upscaler` graphics key (`"fsr1"`, `"bilinear"` or `null` to
|
|
131
142
|
inherit the preset) to `graphicsConfig`/`graphicsPatch`. Every 0.15 definition is
|
|
132
143
|
otherwise unchanged; earlier schemas stay frozen. See RFC-0003/0008 amendments.
|
|
@@ -182,6 +193,16 @@ new `editor.gizmo` carries the tool 4 axis space, pivot and snapping. Error
|
|
|
182
193
|
`data` may name the refusing placement `rule`. Every other 0.21 definition is
|
|
183
194
|
unchanged. See the RFC-0011 amendment "P1 in IPC 0.22".
|
|
184
195
|
|
|
196
|
+
IPC **0.23** adds characters, paths and interactions (RFC-0011 P2): a required
|
|
197
|
+
`npcs` state key (motion setting and effective state, character budgets, the
|
|
198
|
+
path being drawn, the aimed character and the running interaction),
|
|
199
|
+
`character` and `accent` on object instances with path, activity and seat
|
|
200
|
+
values, `use`/`name`/`speed`/`stops` on editor paths, the reticle action
|
|
201
|
+
`interact` and the graphics key `npc_motion`. New methods
|
|
202
|
+
`npcs.spawn/bind/disable/remove` and `paths.set/remove/draw/finish`
|
|
203
|
+
(objects.control), `paths.list` (state.read) and `interaction.choose`
|
|
204
|
+
(world.control). Every other 0.22 definition is unchanged.
|
|
205
|
+
|
|
185
206
|
## Objects and libraries (RFC-0011)
|
|
186
207
|
|
|
187
208
|
Object manifests (`object.json`) and library manifests (`library.json`) use the
|
|
@@ -0,0 +1,493 @@
|
|
|
1
|
+
{
|
|
2
|
+
"formatVersion": "0.9",
|
|
3
|
+
"id": "com.hyprune.example.courtyard",
|
|
4
|
+
"version": "0.1.0",
|
|
5
|
+
"name": "Courtyard",
|
|
6
|
+
"description": "Synthetic world 0.9 manifest: characters on routes, seats, interactions and keep-clear volumes. Referenced files are not supplied.",
|
|
7
|
+
"license": "CC-BY-4.0",
|
|
8
|
+
"scene": "scene.gltf",
|
|
9
|
+
"defaultSpawn": "arrival",
|
|
10
|
+
"spawns": [
|
|
11
|
+
{
|
|
12
|
+
"id": "arrival",
|
|
13
|
+
"pose": {
|
|
14
|
+
"position": [
|
|
15
|
+
0,
|
|
16
|
+
1,
|
|
17
|
+
0
|
|
18
|
+
],
|
|
19
|
+
"rotation": [
|
|
20
|
+
0,
|
|
21
|
+
0,
|
|
22
|
+
0,
|
|
23
|
+
1
|
|
24
|
+
]
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
],
|
|
28
|
+
"attribution": [
|
|
29
|
+
{
|
|
30
|
+
"path": ".",
|
|
31
|
+
"author": "Hyprune contributors",
|
|
32
|
+
"license": "CC-BY-4.0"
|
|
33
|
+
}
|
|
34
|
+
],
|
|
35
|
+
"zones": [
|
|
36
|
+
{
|
|
37
|
+
"id": "work",
|
|
38
|
+
"name": "Work",
|
|
39
|
+
"bounds": {
|
|
40
|
+
"min": [
|
|
41
|
+
-4,
|
|
42
|
+
0,
|
|
43
|
+
-4
|
|
44
|
+
],
|
|
45
|
+
"max": [
|
|
46
|
+
4,
|
|
47
|
+
4,
|
|
48
|
+
4
|
|
49
|
+
]
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
],
|
|
53
|
+
"anchors": [
|
|
54
|
+
{
|
|
55
|
+
"id": "desk",
|
|
56
|
+
"pose": {
|
|
57
|
+
"position": [
|
|
58
|
+
0,
|
|
59
|
+
1.4,
|
|
60
|
+
-3
|
|
61
|
+
],
|
|
62
|
+
"rotation": [
|
|
63
|
+
0,
|
|
64
|
+
0,
|
|
65
|
+
0,
|
|
66
|
+
1
|
|
67
|
+
]
|
|
68
|
+
},
|
|
69
|
+
"size": [
|
|
70
|
+
1.6,
|
|
71
|
+
0.9
|
|
72
|
+
],
|
|
73
|
+
"screenType": "com.hyprune.window"
|
|
74
|
+
}
|
|
75
|
+
],
|
|
76
|
+
"collision": [
|
|
77
|
+
{
|
|
78
|
+
"node": 0,
|
|
79
|
+
"shape": "mesh",
|
|
80
|
+
"layer": "static"
|
|
81
|
+
}
|
|
82
|
+
],
|
|
83
|
+
"navigation": {
|
|
84
|
+
"kind": "mesh",
|
|
85
|
+
"node": 1,
|
|
86
|
+
"agentRadius": 0.3,
|
|
87
|
+
"agentHeight": 1.8
|
|
88
|
+
},
|
|
89
|
+
"lightmaps": [
|
|
90
|
+
{
|
|
91
|
+
"material": 0,
|
|
92
|
+
"texture": 1,
|
|
93
|
+
"texCoord": 1,
|
|
94
|
+
"encoding": "linear",
|
|
95
|
+
"intensity": 1
|
|
96
|
+
}
|
|
97
|
+
],
|
|
98
|
+
"audio": [
|
|
99
|
+
{
|
|
100
|
+
"id": "air",
|
|
101
|
+
"path": "audio/air.ogg",
|
|
102
|
+
"position": [
|
|
103
|
+
0,
|
|
104
|
+
2,
|
|
105
|
+
0
|
|
106
|
+
],
|
|
107
|
+
"radius": 10,
|
|
108
|
+
"gain": 0.2,
|
|
109
|
+
"loop": true
|
|
110
|
+
}
|
|
111
|
+
],
|
|
112
|
+
"objectAssets": [
|
|
113
|
+
{
|
|
114
|
+
"id": "resident",
|
|
115
|
+
"dir": "characters/resident-blue"
|
|
116
|
+
},
|
|
117
|
+
{
|
|
118
|
+
"id": "porter",
|
|
119
|
+
"library": "com.hyprune.starter@0.1.0",
|
|
120
|
+
"object": "porter"
|
|
121
|
+
},
|
|
122
|
+
{
|
|
123
|
+
"id": "guide",
|
|
124
|
+
"scene": "characters/guide.glb",
|
|
125
|
+
"traits": {
|
|
126
|
+
"character": {
|
|
127
|
+
"clips": {
|
|
128
|
+
"walk": {
|
|
129
|
+
"speed": 1.1
|
|
130
|
+
},
|
|
131
|
+
"idle": {},
|
|
132
|
+
"wave": {},
|
|
133
|
+
"nod": {},
|
|
134
|
+
"sit": {
|
|
135
|
+
"seatHeight": 0.46
|
|
136
|
+
},
|
|
137
|
+
"sit_idle": {}
|
|
138
|
+
},
|
|
139
|
+
"height": 1.72,
|
|
140
|
+
"radius": 0.3,
|
|
141
|
+
"accent": true,
|
|
142
|
+
"interactions": [
|
|
143
|
+
{
|
|
144
|
+
"id": "talk",
|
|
145
|
+
"label": "Talk",
|
|
146
|
+
"action": {
|
|
147
|
+
"type": "say",
|
|
148
|
+
"lines": [
|
|
149
|
+
"Welcome to the courtyard."
|
|
150
|
+
]
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
]
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
},
|
|
157
|
+
{
|
|
158
|
+
"id": "court-bench",
|
|
159
|
+
"scene": "objects/bench.glb",
|
|
160
|
+
"collision": {
|
|
161
|
+
"node": "proxy"
|
|
162
|
+
},
|
|
163
|
+
"traits": {
|
|
164
|
+
"movable": {},
|
|
165
|
+
"seat": {
|
|
166
|
+
"capacity": 2,
|
|
167
|
+
"anchors": [
|
|
168
|
+
{
|
|
169
|
+
"id": "left",
|
|
170
|
+
"position": [
|
|
171
|
+
-0.4,
|
|
172
|
+
0,
|
|
173
|
+
0.55
|
|
174
|
+
],
|
|
175
|
+
"yaw": 0,
|
|
176
|
+
"height": 0.45
|
|
177
|
+
},
|
|
178
|
+
{
|
|
179
|
+
"id": "right",
|
|
180
|
+
"position": [
|
|
181
|
+
0.4,
|
|
182
|
+
0,
|
|
183
|
+
0.55
|
|
184
|
+
],
|
|
185
|
+
"yaw": 0,
|
|
186
|
+
"height": 0.45
|
|
187
|
+
}
|
|
188
|
+
]
|
|
189
|
+
}
|
|
190
|
+
}
|
|
191
|
+
},
|
|
192
|
+
{
|
|
193
|
+
"id": "fountain",
|
|
194
|
+
"scene": "objects/fountain.glb",
|
|
195
|
+
"animations": [
|
|
196
|
+
{
|
|
197
|
+
"node": "spray",
|
|
198
|
+
"type": "spin",
|
|
199
|
+
"axis": [
|
|
200
|
+
0,
|
|
201
|
+
1,
|
|
202
|
+
0
|
|
203
|
+
],
|
|
204
|
+
"pivot": [
|
|
205
|
+
0,
|
|
206
|
+
0,
|
|
207
|
+
0
|
|
208
|
+
],
|
|
209
|
+
"period": 12
|
|
210
|
+
}
|
|
211
|
+
],
|
|
212
|
+
"lighting": {
|
|
213
|
+
"mode": "probe"
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
],
|
|
217
|
+
"objects": [
|
|
218
|
+
{
|
|
219
|
+
"id": "fountain-1",
|
|
220
|
+
"asset": "fountain",
|
|
221
|
+
"pose": {
|
|
222
|
+
"position": [
|
|
223
|
+
1.5,
|
|
224
|
+
0,
|
|
225
|
+
0
|
|
226
|
+
],
|
|
227
|
+
"rotation": [
|
|
228
|
+
0,
|
|
229
|
+
0,
|
|
230
|
+
0,
|
|
231
|
+
1
|
|
232
|
+
]
|
|
233
|
+
}
|
|
234
|
+
},
|
|
235
|
+
{
|
|
236
|
+
"id": "bench-east",
|
|
237
|
+
"asset": "court-bench",
|
|
238
|
+
"pose": {
|
|
239
|
+
"position": [
|
|
240
|
+
3.6,
|
|
241
|
+
0,
|
|
242
|
+
-2
|
|
243
|
+
],
|
|
244
|
+
"rotation": [
|
|
245
|
+
0,
|
|
246
|
+
-0.7071068,
|
|
247
|
+
0,
|
|
248
|
+
0.7071068
|
|
249
|
+
]
|
|
250
|
+
},
|
|
251
|
+
"locked": true
|
|
252
|
+
},
|
|
253
|
+
{
|
|
254
|
+
"id": "porter-1",
|
|
255
|
+
"asset": "porter",
|
|
256
|
+
"path": "court-loop",
|
|
257
|
+
"phase": 0.25,
|
|
258
|
+
"speed": 1,
|
|
259
|
+
"accent": [
|
|
260
|
+
0.9,
|
|
261
|
+
0.5,
|
|
262
|
+
0.1
|
|
263
|
+
],
|
|
264
|
+
"interactions": [
|
|
265
|
+
{
|
|
266
|
+
"id": "talk",
|
|
267
|
+
"label": "Talk",
|
|
268
|
+
"action": {
|
|
269
|
+
"type": "say",
|
|
270
|
+
"lines": [
|
|
271
|
+
"The desk is on the north side.",
|
|
272
|
+
"Mind the fountain."
|
|
273
|
+
]
|
|
274
|
+
}
|
|
275
|
+
},
|
|
276
|
+
{
|
|
277
|
+
"id": "where",
|
|
278
|
+
"label": "Where is work?",
|
|
279
|
+
"prompt": "Mark it",
|
|
280
|
+
"action": {
|
|
281
|
+
"type": "waypoint",
|
|
282
|
+
"target": {
|
|
283
|
+
"zoneId": "work"
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
},
|
|
287
|
+
{
|
|
288
|
+
"id": "show-desk",
|
|
289
|
+
"label": "Show me the desk",
|
|
290
|
+
"prompt": "Follow me",
|
|
291
|
+
"action": {
|
|
292
|
+
"type": "guide",
|
|
293
|
+
"path": "to-desk"
|
|
294
|
+
}
|
|
295
|
+
},
|
|
296
|
+
{
|
|
297
|
+
"id": "map",
|
|
298
|
+
"label": "Open the map",
|
|
299
|
+
"action": {
|
|
300
|
+
"type": "panel",
|
|
301
|
+
"panel": "map"
|
|
302
|
+
}
|
|
303
|
+
}
|
|
304
|
+
]
|
|
305
|
+
},
|
|
306
|
+
{
|
|
307
|
+
"id": "guide-1",
|
|
308
|
+
"asset": "guide",
|
|
309
|
+
"path": "court-loop",
|
|
310
|
+
"phase": 0.75,
|
|
311
|
+
"reverse": true,
|
|
312
|
+
"accent": [
|
|
313
|
+
0.2,
|
|
314
|
+
0.4,
|
|
315
|
+
0.9
|
|
316
|
+
]
|
|
317
|
+
},
|
|
318
|
+
{
|
|
319
|
+
"id": "reader",
|
|
320
|
+
"asset": "resident",
|
|
321
|
+
"pose": {
|
|
322
|
+
"position": [
|
|
323
|
+
1.5,
|
|
324
|
+
0,
|
|
325
|
+
1.8
|
|
326
|
+
],
|
|
327
|
+
"rotation": [
|
|
328
|
+
0,
|
|
329
|
+
1,
|
|
330
|
+
0,
|
|
331
|
+
0
|
|
332
|
+
]
|
|
333
|
+
},
|
|
334
|
+
"seat": "fountain-ledge",
|
|
335
|
+
"interactions": [
|
|
336
|
+
{
|
|
337
|
+
"id": "fountain",
|
|
338
|
+
"label": "The fountain?",
|
|
339
|
+
"action": {
|
|
340
|
+
"type": "waypoint",
|
|
341
|
+
"target": {
|
|
342
|
+
"object": "fountain-1"
|
|
343
|
+
}
|
|
344
|
+
}
|
|
345
|
+
}
|
|
346
|
+
]
|
|
347
|
+
}
|
|
348
|
+
],
|
|
349
|
+
"paths": [
|
|
350
|
+
{
|
|
351
|
+
"id": "court-loop",
|
|
352
|
+
"name": "Court loop",
|
|
353
|
+
"use": "route",
|
|
354
|
+
"closed": true,
|
|
355
|
+
"speed": 1.1,
|
|
356
|
+
"points": [
|
|
357
|
+
{
|
|
358
|
+
"position": [
|
|
359
|
+
-3.5,
|
|
360
|
+
0,
|
|
361
|
+
3
|
|
362
|
+
],
|
|
363
|
+
"type": "line"
|
|
364
|
+
},
|
|
365
|
+
{
|
|
366
|
+
"position": [
|
|
367
|
+
-3.5,
|
|
368
|
+
0,
|
|
369
|
+
-2
|
|
370
|
+
],
|
|
371
|
+
"type": "line"
|
|
372
|
+
},
|
|
373
|
+
{
|
|
374
|
+
"position": [
|
|
375
|
+
3,
|
|
376
|
+
0,
|
|
377
|
+
-2
|
|
378
|
+
],
|
|
379
|
+
"type": "curve"
|
|
380
|
+
},
|
|
381
|
+
{
|
|
382
|
+
"position": [
|
|
383
|
+
3,
|
|
384
|
+
0,
|
|
385
|
+
3
|
|
386
|
+
],
|
|
387
|
+
"type": "arc"
|
|
388
|
+
}
|
|
389
|
+
],
|
|
390
|
+
"stops": [
|
|
391
|
+
{
|
|
392
|
+
"point": 1,
|
|
393
|
+
"seconds": 3,
|
|
394
|
+
"clip": "look_around"
|
|
395
|
+
},
|
|
396
|
+
{
|
|
397
|
+
"point": 2,
|
|
398
|
+
"seconds": 20,
|
|
399
|
+
"seat": "bench-east/left"
|
|
400
|
+
},
|
|
401
|
+
{
|
|
402
|
+
"point": 3,
|
|
403
|
+
"seconds": 4,
|
|
404
|
+
"face": {
|
|
405
|
+
"anchor": "desk"
|
|
406
|
+
}
|
|
407
|
+
}
|
|
408
|
+
]
|
|
409
|
+
},
|
|
410
|
+
{
|
|
411
|
+
"id": "to-desk",
|
|
412
|
+
"name": "To the desk",
|
|
413
|
+
"use": "route",
|
|
414
|
+
"points": [
|
|
415
|
+
{
|
|
416
|
+
"position": [
|
|
417
|
+
0,
|
|
418
|
+
0,
|
|
419
|
+
3
|
|
420
|
+
],
|
|
421
|
+
"type": "line"
|
|
422
|
+
},
|
|
423
|
+
{
|
|
424
|
+
"position": [
|
|
425
|
+
0,
|
|
426
|
+
0,
|
|
427
|
+
-2
|
|
428
|
+
],
|
|
429
|
+
"type": "line"
|
|
430
|
+
}
|
|
431
|
+
]
|
|
432
|
+
},
|
|
433
|
+
{
|
|
434
|
+
"id": "garden-walk",
|
|
435
|
+
"points": [
|
|
436
|
+
{
|
|
437
|
+
"position": [
|
|
438
|
+
-2,
|
|
439
|
+
0,
|
|
440
|
+
2
|
|
441
|
+
],
|
|
442
|
+
"type": "line"
|
|
443
|
+
},
|
|
444
|
+
{
|
|
445
|
+
"position": [
|
|
446
|
+
2,
|
|
447
|
+
0,
|
|
448
|
+
2
|
|
449
|
+
],
|
|
450
|
+
"type": "curve"
|
|
451
|
+
}
|
|
452
|
+
]
|
|
453
|
+
}
|
|
454
|
+
],
|
|
455
|
+
"seats": [
|
|
456
|
+
{
|
|
457
|
+
"id": "fountain-ledge",
|
|
458
|
+
"pose": {
|
|
459
|
+
"position": [
|
|
460
|
+
1.5,
|
|
461
|
+
0,
|
|
462
|
+
1.2
|
|
463
|
+
],
|
|
464
|
+
"rotation": [
|
|
465
|
+
0,
|
|
466
|
+
1,
|
|
467
|
+
0,
|
|
468
|
+
0
|
|
469
|
+
]
|
|
470
|
+
},
|
|
471
|
+
"height": 0.5,
|
|
472
|
+
"use": [
|
|
473
|
+
"sit"
|
|
474
|
+
],
|
|
475
|
+
"approach": 0.6
|
|
476
|
+
}
|
|
477
|
+
],
|
|
478
|
+
"keepClear": [
|
|
479
|
+
{
|
|
480
|
+
"id": "north-door",
|
|
481
|
+
"min": [
|
|
482
|
+
-0.8,
|
|
483
|
+
0,
|
|
484
|
+
-4.2
|
|
485
|
+
],
|
|
486
|
+
"max": [
|
|
487
|
+
0.8,
|
|
488
|
+
2.4,
|
|
489
|
+
-3.6
|
|
490
|
+
]
|
|
491
|
+
}
|
|
492
|
+
]
|
|
493
|
+
}
|
package/lib/validate.d.mts
CHANGED
|
@@ -19,9 +19,17 @@ export interface ValidateOptions {
|
|
|
19
19
|
/**
|
|
20
20
|
* For kind `scene` from world 0.8: validate `value` as the glTF of this
|
|
21
21
|
* `world.objectAssets[].id` (extension rules, animation and collision node
|
|
22
|
-
* names, nesting
|
|
22
|
+
* names, nesting; from 0.9 also an inline character's skin and clips) instead
|
|
23
|
+
* of the world's scene.gltf.
|
|
23
24
|
*/
|
|
24
25
|
asset?: string;
|
|
26
|
+
/**
|
|
27
|
+
* For kind `world` from 0.9: the parsed object.json of `dir` and `library` object
|
|
28
|
+
* assets, keyed by `objectAssets[].id`. Their traits make the character-only
|
|
29
|
+
* fields, seat anchor references, `locked` and the character limit checkable as
|
|
30
|
+
* for inline assets; without them those checks skip the asset.
|
|
31
|
+
*/
|
|
32
|
+
assets?: Record<string, { id?: string; formatVersion?: string; traits?: Record<string, unknown> }>;
|
|
25
33
|
/** Kind object: the parsed scene glTF (or a GLB's JSON chunk) for node, material, variant, clip, budget and bounds checks. */
|
|
26
34
|
gltf?: unknown;
|
|
27
35
|
/** Kind object: the directory name, which must equal the object id. */
|
|
@@ -60,5 +68,7 @@ export const contractVersions: readonly string[];
|
|
|
60
68
|
export const objectFormats: readonly string[];
|
|
61
69
|
/** RFC-0011 directory, asset and library limits the object and library checks apply. */
|
|
62
70
|
export const objectLimits: Readonly<Record<string, number>>;
|
|
71
|
+
/** World 0.9 limits the world checks apply: character instances, characters per path, path points in total, minimum arc chord (m). */
|
|
72
|
+
export const worldLimits: Readonly<{ characters: number; charactersPerPath: number; pathPoints: number; arcChord: number }>;
|
|
63
73
|
/** glTF extensions a scene may list in extensionsRequired for a world format. */
|
|
64
74
|
export function sceneExtensions(version: string): string[];
|