3.9 KiB
Observer
(no submodules)
Purpose
Re-exports the ObserverPosition discriminated union that every universe-family entry point consumes. The union has three branches — SurfaceObserver, AtmosphericObserver, and SpaceObserver — distinguished by a kind literal field so call sites can narrow exhaustively without runtime type tags or class hierarchies.
Centralising these types in one module gives @suaveplan/universe/client/client, providers, and frame-conversion utilities a single shape to consume. Because the source declarations live in @suaveplan/types (zero-runtime, types-only), this re-export adds no bundle weight; it exists so consumers can import observer shapes without crossing into the foundational types package directly.
Features
ObserverPosition— full discriminated union, switch onkind.SurfaceObserver— planet-bound observer at a{latitude, longitude}coordinate.AtmosphericObserver— same as surface but withaltitudeMetres(planes, balloons, drones).SpaceObserver— heliocentric vector + referenceframe(e.g."icrs").- All three branches share the
kindliteral as the discriminator. - Pure types — zero runtime cost, tree-shaken to nothing.
Usage: Basic Example
import type { ObserverPosition } from "@suaveplan/universe";
const observer: ObserverPosition = {
kind: "space",
heliocentricVec: { x: 1, y: 0, z: 0 },
frame: "icrs",
};
Usage: Advanced Example
import type {
AtmosphericObserver,
ObserverPosition,
SpaceObserver,
SurfaceObserver,
} from "@suaveplan/universe";
function describe(o: ObserverPosition): string {
switch (o.kind) {
case "surface":
return `surface at ${o.coord.latitude},${o.coord.longitude}`;
case "atmospheric":
return `${o.altitudeMetres} m above ${o.planet.name}`;
case "space":
return `space, ${o.frame} vector ${JSON.stringify(o.heliocentricVec)}`;
}
}
const earth = {
name: "Earth",
mass: 1,
radius: 1,
polarRadius: 1,
surfaceGravity: 1,
rotationPeriod: 1,
axialTilt: 23.4,
atmosphere: null,
satellites: [],
};
const surface: SurfaceObserver = {
kind: "surface",
planet: earth,
coord: { latitude: 51.5, longitude: -0.12 },
};
const balloon: AtmosphericObserver = {
kind: "atmospheric",
planet: earth,
coord: { latitude: 51.5, longitude: -0.12 },
altitudeMetres: 12000,
};
const probe: SpaceObserver = {
kind: "space",
heliocentricVec: { x: 1.0, y: 0.0, z: 0.0 },
frame: "icrs",
};
[surface, balloon, probe].forEach((o) => describe(o));
API Reference
type SurfaceObserver
| Property | Type | Description |
|---|---|---|
kind |
"surface" |
Discriminator literal. |
planet |
PlanetConfig |
Host body (mass, radius, axial tilt, satellites …). |
coord |
{ latitude: number; longitude: number } |
Geographic location in degrees. |
type AtmosphericObserver
Extends SurfaceObserver shape with an additional altitudeMetres: number and kind: "atmospheric".
type SpaceObserver
| Property | Type | Description |
|---|---|---|
kind |
"space" |
Discriminator literal. |
heliocentricVec |
{ x: number; y: number; z: number } |
Cartesian position in AU. |
frame |
string |
Reference frame label, e.g. "icrs". |
type ObserverPosition
SurfaceObserver | AtmosphericObserver | SpaceObserver — exhaustive switch on kind.
Implementation Notes
These types are re-exported from @suaveplan/types; this module contains no runtime code and contributes nothing to the emitted bundle. Keeping the canonical declarations in @suaveplan/types preserves the universe-family rule that any observer-shaped value flowing through providers, the client, frame conversions, or packet codecs is structurally identical no matter which sibling package produced it.