# disko:expr

> Presentation expressions every player's client evaluates each frame, for cameras, visuals, disc paint and HUD styles.

Import with `import * as expr from "disko:expr"`. Generated from the module's
shipped declarations. See [Cameras & expressions](/games/cameras-and-expressions)
for a guide.

`disko:expr` — presentation expressions: numbers and vectors a game declares once and every client evaluates on each frame it draws.

Expressions go wherever a presentation number or point is accepted: `world.camera`, `world.visual` and `disc.setAppearance`. They describe how presentation follows the drawn scene (a camera that follows the viewer, a ring that grows with speed, an opacity that pulses) and never affect game state.

The functions mirror `disko:math`: the same names mean the same things, but they return expressions instead of computing now. `disko:math`'s two-word functions are one word here and accept vectors (`lerpVector` is `lerp`, `scale` is `times`). Import the module as a namespace, `import * as expr from "disko:expr"`, so its names never clash with `disko:math`'s; for example `expr.lerp(expr.me.position, ball.position, 0.3)` is the point 30% of the way from the viewer's disc to the ball.

Mistakes throw where they are made: `TypeError` for wrong kinds or argument counts, `RangeError` for non-finite numbers, naming the function.

**Absence.** A reference to something that doesn't exist on a frame (a destroyed disc, `me` for a spectator) makes the expressions that read it absent; so do invalid operations (`sqrt` of a negative number, `clamp` with `min > max`, `normalize` of a zero vector). `or(a, b)` picks `b` then. An absent camera falls back to the next camera for the viewer, then the default view; an absent visual number hides the visual for that frame; an absent disc paint number uses its default.

Limits: at most 256 nodes and 32 levels per expression, at most 16 arguments per variadic function.

## Types

### Expression

An expression; each client computes its value on every frame.

```ts
export interface Expression<K extends "number" | "vector"> {
    readonly [kind]: K;
}
```

### NumberExpression

An expression producing a number.

```ts
export type NumberExpression = Expression<"number">;
```

### VectorExpression

An expression producing a vector.

```ts
export type VectorExpression = Expression<"vector">;
```

### NumberLike

A finite number or a number expression.

```ts
export type NumberLike = number | NumberExpression;
```

### PointLike

A point whose coordinates are numbers or number expressions.

```ts
export interface PointLike {
    readonly x: NumberLike;
    readonly y: NumberLike;
}
```

### VectorLike

A point or a vector expression.

```ts
export type VectorLike = PointLike | VectorExpression;
```

### DiscReference

A disc as each client draws it.

```ts
export interface DiscReference {
    readonly position: VectorExpression;
    readonly velocity: VectorExpression;
    readonly x: NumberExpression;
    readonly y: NumberExpression;
    readonly radius: NumberExpression;
    readonly speed: NumberExpression;
}
```

| Member | Description |
| --- | --- |
| `position` | Center. |
| `velocity` | Velocity in world units per tick. |
| `x` | Horizontal center. |
| `y` | Vertical center. |
| `radius` | Radius. |
| `speed` | Length of the velocity. |

## Constants

### me

The viewer's own controlled disc; absent for spectators and in replays.

```ts
export const me: DiscReference;
```

### time

Match time in seconds, interpolated; it stops while the match is paused.

```ts
export const time: NumberExpression;
```

### screen

The viewer's canvas in CSS pixels.

```ts
export const screen: {
    readonly width: NumberExpression;
    readonly height: NumberExpression;
    readonly aspect: NumberExpression;
};
```

## Functions

### disc

A disc as each client draws it. The disc must be live when the declaration using it is made; once destroyed, it is absent.

```ts
export function disc(disc: Disko.Disc): DiscReference;
```

### plus

Sum of 2 to 16 numbers.

Sum of 2 to 16 vectors.

```ts
export function plus(...values: NumberLike[]): NumberExpression;
export function plus(...values: VectorLike[]): VectorExpression;
```

### minus

`a - b` for two numbers.

`a - b` for two vectors.

```ts
export function minus(a: NumberLike, b: NumberLike): NumberExpression;
export function minus(a: VectorLike, b: VectorLike): VectorExpression;
```

### times

Product of 2 to 16 numbers.

A vector scaled by one or more numbers.

```ts
export function times(...values: NumberLike[]): NumberExpression;
export function times(vector: VectorLike, ...factors: NumberLike[]): VectorExpression;
```

### over

`a / b`.

A vector divided by a number.

```ts
export function over(a: NumberLike, b: NumberLike): NumberExpression;
export function over(a: VectorLike, b: NumberLike): VectorExpression;
```

### negate

The opposite number.

The opposite vector.

```ts
export function negate(value: NumberLike): NumberExpression;
export function negate(value: VectorLike): VectorExpression;
```

### min

Smallest of 2 to 16 numbers.

```ts
export function min(...values: NumberLike[]): NumberExpression;
```

### max

Largest of 2 to 16 numbers.

```ts
export function max(...values: NumberLike[]): NumberExpression;
```

### abs

Absolute value.

```ts
export function abs(value: NumberLike): NumberExpression;
```

### floor

Largest integer not above the number.

```ts
export function floor(value: NumberLike): NumberExpression;
```

### round

Nearest integer, halves away from zero.

```ts
export function round(value: NumberLike): NumberExpression;
```

### sqrt

Square root; absent for negative numbers.

```ts
export function sqrt(value: NumberLike): NumberExpression;
```

### sin

Sine of radians.

```ts
export function sin(radians: NumberLike): NumberExpression;
```

### cos

Cosine of radians.

```ts
export function cos(radians: NumberLike): NumberExpression;
```

### clamp

`value` limited to `[min, max]`; absent when `min > max`.

```ts
export function clamp(value: NumberLike, min: NumberLike, max: NumberLike): NumberExpression;
```

### hypot

Length of `(x, y)`.

```ts
export function hypot(x: NumberLike, y: NumberLike): NumberExpression;
```

### atan2

Angle of `(x, y)` in radians.

```ts
export function atan2(y: NumberLike, x: NumberLike): NumberExpression;
```

### lerp

`a + (b - a) * t` for two numbers.

`a + (b - a) * t` for two vectors.

```ts
export function lerp(a: NumberLike, b: NumberLike, t: NumberLike): NumberExpression;
export function lerp(a: VectorLike, b: VectorLike, t: NumberLike): VectorExpression;
```

### smoothstep

Smooth Hermite step from 0 to 1; absent when the edges are equal.

```ts
export function smoothstep(edge0: NumberLike, edge1: NumberLike, x: NumberLike): NumberExpression;
```

### remap

`value` mapped linearly from one range to another; absent when `fromMin == fromMax`.

```ts
export function remap(value: NumberLike, fromMin: NumberLike, fromMax: NumberLike, toMin: NumberLike, toMax: NumberLike): NumberExpression;
```

### vec

A vector from two numbers.

```ts
export function vec(x: NumberLike, y: NumberLike): VectorExpression;
```

### length

Length of a vector.

```ts
export function length(vector: VectorLike): NumberExpression;
```

### distance

Distance between two points.

```ts
export function distance(a: VectorLike, b: VectorLike): NumberExpression;
```

### dot

Dot product.

```ts
export function dot(a: VectorLike, b: VectorLike): NumberExpression;
```

### midpoint

Point halfway between two points.

```ts
export function midpoint(a: VectorLike, b: VectorLike): VectorExpression;
```

### normalize

Unit vector in the same direction; absent for the zero vector.

```ts
export function normalize(vector: VectorLike): VectorExpression;
```

### rotate

A vector rotated by radians, as in `disko:math` (clockwise on screen).

```ts
export function rotate(vector: VectorLike, radians: NumberLike): VectorExpression;
```

### or

The first of 2 to 16 numbers that is present and finite.

The first of 2 to 16 vectors that is present and finite.

```ts
export function or(...values: NumberLike[]): NumberExpression;
export function or(...values: VectorLike[]): VectorExpression;
```
