# World Editor / Journey V1 Specification

Source decision: `discussion/workflow/decisions/DEC-0001-world-editor-journey-v1.md`

## Purpose

The World Editor defines the macro-world contract for Gardens of Nil. It does not edit internal Stage content. Journey is the runtime-readable logical graph published from the World Editor.

This specification defines the V1 authoring and runtime boundary.

## Ownership Boundary

The World Editor SHALL own:

- macro WorldLayers;
- WorldTile occupancy;
- logical Stage placement;
- Journey endpoints;
- Journey connections;
- commit-time validation;
- publication of logical Journey data.

The Stage Editor SHALL own:

- internal Stage geometry;
- floors inside a Stage;
- Stage props;
- Stage objects;
- Stage scene generation;
- Stage bake.

The World Editor commit MUST NOT create Stage scenes, Stage geometry, internal Stage objects, or baked Stage content.

## Authoring Asset

`WorldLayoutSO` is the editor-only authoring ScriptableObject for the World Editor.

`WorldLayoutSO` MUST contain:

- a stable layout id;
- `worldTileSize`, defaulting to `24m`;
- `worldLayerHeight`, defaulting to `24m`;
- authoring Stage records;
- occupied WorldTiles per Stage;
- authoring endpoint records;
- authoring connection records;
- editor metadata.

`worldTileSize` and `worldLayerHeight` MUST be configurable. V1 defaults are `24m`.

`WorldLayoutSO` MAY reference editor-only Stage authoring data, including `StageDefinition`, but runtime code MUST NOT consume `WorldLayoutSO`.

## Runtime Asset

`JGraphSO` is the runtime Journey ScriptableObject.

Journey elements MUST use the `J` prefix. Journey ScriptableObjects MUST also use the `SO` suffix.

`JGraphSO` MUST contain:

- `sourceWorldLayoutId`;
- `publishedAt`;
- `schemaVersion`;
- optional `contentHash`;
- `JStage` records;
- `JEndpoint` records;
- `JConnection` records.

Runtime Journey code MUST consume `JGraphSO`. Runtime Journey code MUST NOT depend on `WorldLayoutSO`, `StageDefinition`, or any type under `Assets/Scripts/Editor`.

## World Model

The World Editor is 2D per `WorldLayer`.

A Stage:

- belongs to exactly one `WorldLayer`;
- occupies a set of WorldTiles;
- MUST NOT overlap another Stage on the same WorldLayer tile.

A WorldTile can be occupied by at most one Stage within a WorldLayer.

All physical space MUST belong to a Stage. `JConnection` MUST NOT own physical space. If a corridor, transition room, long lift, loading mask, or similar physical traversal space is needed, it MUST be represented as a Stage.

## JStage

`JStage` is the runtime logical representation of a Stage inside `JGraphSO`.

`JStage` MUST have a stable GUID/string id. Tags MAY be used for classification and lookup, but tags MUST NOT replace stable identity.

`JStage` is not Stage scene generation data and is not Stage bake data.

## Endpoints

Initial endpoint types are:

- `JEndpointSocket`;
- `JEndpointAnchor`;
- `JEndpointLift`.

Every endpoint MUST have:

- a stable GUID/string id;
- an owning `JStage` id;
- a WorldTile coordinate;
- an endpoint type;
- a required/optional flag.

### JEndpointSocket

`JEndpointSocket` represents a physical side connection on a free tile face.

It MUST:

- exist only on a free face of a Stage WorldTile;
- use one of `North`, `South`, `East`, or `West`;
- accept at most one `JConnection`;
- connect only to another `JEndpointSocket`.

Socket-to-socket physical connections MUST connect opposite faces on adjacent WorldTiles.

### JEndpointAnchor

`JEndpointAnchor` represents an abstract travel point such as a portal, hub, or fast-travel anchor.

It MAY have multiple `JConnections`. Runtime destination selection for multi-connection anchors is outside V1.

### JEndpointLift

`JEndpointLift` represents macro vertical travel between WorldLayers.

It MUST:

- accept exactly one `JConnection` in V1;
- connect only to another `JEndpointLift`;
- align on the same 2D WorldTile coordinate as its paired lift;
- connect across different WorldLayers.

## Endpoint Coexistence

A WorldTile MAY contain sockets and one non-socket endpoint.

`JEndpointAnchor` and `JEndpointLift` MUST NOT coexist on the same WorldTile.

Sockets MAY coexist with anchors or lifts.

## Connections

`JConnection` is a logical edge between exactly two endpoints.

`JConnection` MUST:

- have a stable GUID/string id;
- reference endpoint A by id;
- reference endpoint B by id;
- connect endpoints of compatible type;
- not own physical space.

Endpoint compatibility in V1 is same-type only:

- socket to socket;
- anchor to anchor;
- lift to lift.

Directionality MAY be represented in V1. Concrete requirement modeling and loading hints are outside V1, but `JConnection` SHOULD remain extensible so those fields can be added later.

## Commit Flow

The World Editor SHALL publish Journey data through an explicit commit action.

The commit action MUST:

- validate `WorldLayoutSO`;
- abort if commit-blocking errors exist;
- allow publication when only warnings exist;
- create or update `JGraphSO`;
- write `JStage`, `JEndpoint`, and `JConnection` records;
- write publication metadata.

The commit action MUST NOT:

- generate Stage scenes;
- generate Stage geometry;
- generate internal Stage objects;
- run Stage bake;
- write Stage Editor content.

## Validation

Commit-blocking errors include:

- same-layer WorldTile overlap between Stages;
- connection referencing a missing endpoint;
- connection linking an endpoint to itself;
- incompatible endpoint types;
- socket with more than one connection;
- socket on an internal Stage face;
- socket connected to a non-opposite or non-adjacent socket;
- anchor and lift on the same WorldTile;
- lift connected to a lift with a different 2D coordinate;
- required endpoint without connection.

Warnings include:

- optional endpoint without connection;
- Stage without endpoints;
- authoring metadata missing from non-critical fields.

## Editor Technology

World Editor V1 SHALL use the same window technology as the existing Stage Editor:

- `EditorWindow`;
- UI Toolkit via `UnityEngine.UIElements` and `UnityEditor.UIElements`;
- custom canvas based on `VisualElement.generateVisualContent`.

Stage Editor integration remains manual in V1.

## V1 Non-Goals

V1 does not include:

- loading hints;
- streaming policies;
- concrete `JRequirement` structures;
- runtime destination selection UI or logic for multi-connection anchors;
- deep Stage Editor marker sync;
- automatic Stage Editor opening from the World Editor;
- unified World/Stage Editor shell.
