# URL State Model

Mechanica share links encode the current viewer state in query parameters. The format is intentionally compact, human-inspectable, and resilient to missing values.

## Implementation

```text
src/utils/urlState.ts
src/hooks/useUrlViewState.ts
```

## Parameter table

| Parameter | Example | Meaning |
| --- | --- | --- |
| `preset` | `isometric` | Camera preset ID |
| `cam` | `4.5,3.2,5.4` | Camera position vector |
| `target` | `0,0,0` | Camera target vector |
| `explode` | `1.25` | Exploded-view separation scalar |
| `mode` | `wireframe` | Display mode: `solid`, `wireframe`, `xray` |
| `clip` | `x` | Cross-section axis: `none`, `x`, `y`, `z` |
| `clipOffset` | `0.25` | Cross-section plane offset |
| `hidden` | `piston,crankshaft` | Comma-separated hidden part IDs |
| `opacity` | `housing:0.35,rotor:0.7` | Per-part opacity overrides |
| `labels` | `0` | Annotation labels on/off |

Machine identity is encoded in the route path:

```text
/machines/four-stroke-petrol-engine?preset=isometric&explode=0.8
```

## Defaults

If a value is absent or invalid, the viewer uses registry and store defaults:

- Camera preset: registry `viewer.initialCameraPreset`
- Explode: `0`
- Mode: `solid`
- Clip: `none`
- Labels: `true`
- Part visibility: visible
- Part opacity: `1`

## Parsing rules

- Numbers are clamped to safe viewer ranges.
- Vectors require exactly three finite numbers.
- Unknown modes, axes, and presets are ignored.
- Empty lists are treated as absent.
- Invalid opacity entries are ignored.

## Serialization rules

- Numbers are rounded to three decimal places.
- Default values are omitted where possible.
- Hidden parts and opacity maps use comma-separated part IDs.
- URLSearchParams handles percent encoding.

## Privacy and persistence

URL state is shareable and not persisted. User preferences such as favourites and theme live in localStorage through `preferencesStore`.

## Future additions

Potential future parameters:

| Parameter | Meaning |
| --- | --- |
| `tour` | Active guided-tour step |
| `rpm` | Playback speed when sharing animated state |
| `sectionCap` | Cut-surface cap material on/off |
| `input` / `output` | Mechanism-specific selectable constraints, e.g. planetary gearbox |
| `quality` | Mobile/desktop render quality override |

Future machine-specific parameters should be namespaced or whitelisted in the machine animation module rather than added ad hoc in viewer panels.
