Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/sanchedev/fraxel/llms.txt

Use this file to discover all available pages before exploring further.

Math utilities are exported from the main fraxel package. The module provides Vector2 for 2D coordinates and directions, the VectorLike union type accepted by all JSX props that deal with positions and sizes, and the Color RGBA tuple type used by filter and tint props. You will use these types constantly when writing game logic, setting up collision shapes, or configuring raycasts. See also the Collision API and Filters guide for context on where each type appears.
import { Vector2 } from 'fraxel'
import type { VectorLike, Color } from 'fraxel'

Vector2

A mutable 2D vector. All mutating methods (add, subtract, multiply, normalize) modify the instance in place and return this for chaining. Non-mutating equivalents (toAdded, toSubtracted, toMultiplied) clone the vector first.

Constructor

const pos  = new Vector2(100, 200)
const zero = new Vector2(0, 0)
x
number
required
The x-coordinate (horizontal axis, increasing rightward).
y
number
required
The y-coordinate (vertical axis, increasing downward in screen space).

Static factories

Vector2.ZERO
Vector2
Returns a new Vector2(0, 0). A fresh instance is returned each time — safe to mutate.
Vector2.ONE
Vector2
Returns a new Vector2(1, 1). Useful as a default scale or unit vector.
Vector2.fromJSON(position)
Vector2
Creates a Vector2 from a plain Position object { x: number, y: number }. Handy when deserialising saved game state.
const v = Vector2.fromJSON({ x: 10, y: 20 })
Vector2.vectorize(vectorLike)
Vector2
Converts any VectorLike value to a Vector2. See VectorLike below for the accepted forms.

Properties

x
number
The x-coordinate. Publicly writable.
y
number
The y-coordinate. Publicly writable.

Mutating methods

All mutating methods return this for chaining.
add(vector2: Vector2 | number)
Vector2
Adds another Vector2 component-wise, or adds a scalar to both x and y. Mutates in place.
const pos = new Vector2(10, 20)
pos.add(new Vector2(5, 5))  // { x: 15, y: 25 }
pos.add(10)                  // { x: 25, y: 35 }
subtract(vector2: Vector2 | number)
Vector2
Subtracts another Vector2 component-wise, or subtracts a scalar from both axes. Mutates in place.
const v = new Vector2(100, 80)
v.subtract(new Vector2(40, 30))  // { x: 60, y: 50 }
multiply(vector2: Vector2 | number)
Vector2
Multiplies component-wise by another Vector2, or scales both axes by a scalar. Mutates in place.
const scale = new Vector2(2, 3)
scale.multiply(2)  // { x: 4, y: 6 }
normalize()
Vector2
Scales the vector to unit length (magnitude = 1). If the vector is zero, it remains zero. Mutates in place.
const dir = new Vector2(3, 4)
dir.normalize()  // { x: 0.6, y: 0.8 } — magnitude is now 1
apply(fn: (coord: number, axis: 'x' | 'y') => number)
Vector2
Applies a function to each component independently. Mutates in place.
const v = new Vector2(3.7, -1.2)
v.apply(Math.round)  // { x: 4, y: -1 }

Non-mutating (clone) methods

These return a new Vector2 and leave the original unchanged.
toAdded(vector2: Vector2 | number)
Vector2
Returns a new vector equal to this + arg.
toSubtracted(vector2: Vector2 | number)
Vector2
Returns a new vector equal to this - arg.
toMultiplied(vector2: Vector2 | number)
Vector2
Returns a new vector equal to this * arg.
toApplied(fn)
Vector2
Returns a new vector with fn applied to each component.
clone()
Vector2
Returns a deep copy of this vector with the same x and y values.
const original = new Vector2(5, 10)
const copy = original.clone()
copy.x = 99
console.log(original.x)  // 5 — untouched

Comparison and serialisation

equals(vector2: Vector2)
boolean
Returns true if both x and y are strictly equal.
new Vector2(1, 2).equals(new Vector2(1, 2))  // true
toJSON()
Position
Converts to a plain { x: number, y: number } object. Useful for serialisation.
new Vector2(10, 20).toJSON()  // { x: 10, y: 20 }

Practical examples

import { Vector2 } from 'fraxel'

// --- Position arithmetic ---
const playerPos = new Vector2(100, 200)
const velocity  = new Vector2(3, 0)
const delta     = 0.016 // 16 ms frame

// Move player (non-mutating — keeps original for comparison)
const nextPos = playerPos.toAdded(velocity.toMultiplied(delta * 60))

// --- Distance check ---
const enemyPos = new Vector2(150, 200)
const diff     = enemyPos.toSubtracted(playerPos)
const dx = diff.x, dy = diff.y
const distSq   = dx * dx + dy * dy
const inRange  = distSq < 100 * 100  // cheaper than sqrt

// --- Direction vector for a raycast ---
const lookDir = new Vector2(1, 0)     // point right
const rayLen  = 128
const rayDir  = lookDir.toMultiplied(rayLen)  // scale to ray length
// <ray-cast direction={rayDir} collidesWith={['enemy']} />

// --- Normalise movement input ---
const input = new Vector2(1, 1)  // diagonal
input.normalize().multiply(200)  // speed 200 px/s in any direction

VectorLike

export type VectorLike = Vector2 | Position | [x: number, y: number] | number
VectorLike is the union type accepted by any JSX prop that represents a 2D coordinate, size, or direction — position, size, direction, scale, etc. This means you can write positions as:
// All of these are equivalent for a position prop:
<transform position={new Vector2(100, 200)} />
<transform position={[100, 200]} />
<transform position={{ x: 100, y: 200 }} />
<transform position={50} />  // shorthand — both axes set to 50
Internally Fraxel calls Vector2.vectorize() on every VectorLike prop before using it:
Input formConverted to
Vector2Returned as-is
[number, number]new Vector2(arr[0], arr[1])
{ x: number, y: number }Vector2.fromJSON(pos)
numbernew Vector2(n, n) — same value for both axes

Color

export type Color = [number, number, number, number]
A four-element tuple [r, g, b, a] where every channel is in the range 0–1 (not 0–255). Used by filter and tint props that accept colour values.
import type { Color } from 'fraxel'

const red:              Color = [1, 0, 0, 1]
const green:            Color = [0, 1, 0, 1]
const blue:             Color = [0, 0, 1, 1]
const orange:           Color = [1, 0.5, 0, 1]
const semiTransparent:  Color = [1, 1, 1, 0.5]
const invisible:        Color = [0, 0, 0, 0]
Converting from a CSS 0–255 value: divide each channel by 255.
// CSS rgb(72, 209, 204) → fraxel Color
const turquoise: Color = [72 / 255, 209 / 255, 204 / 255, 1]
The alpha channel controls opacity — 0 is fully transparent, 1 is fully opaque. See the Filters guide for nodes that accept Color props.

Position interface

export interface Position {
  x: number
  y: number
}
A plain data interface — no methods. Used as the serialisation target of vector.toJSON() and accepted anywhere a lightweight { x, y } object is needed instead of a full Vector2.

Related guides

Build docs developers (and LLMs) love