Web API Reference

The complete Board object surface. Board is a compile-time readonly object (export const Board = {...} as const); every feature hangs off it, grouped into six domains plus top-level properties.

import { Board, BoardContactType } from "@board.fun/web-sdk";

Board.isOnDevice; // boolean, true on a real device
Board.sdkVersion; // string, informational only, NOT a feature gate

The public Board.* API is append-only: nothing is removed or renamed once shipped, so a game built against an older SDK keeps working on newer devices. There is intentionally no bridge or OS version exposed to games. New OS capabilities degrade gracefully via in-bridge capability checks; where needed, gate on Board.session.areServicesReady().

The SDK also exposes the same surface as direct named ES exports for callers who prefer named imports over Board.*: the domain objects input, session, save, avatar, pause, application; isBoardDevice(); SDK_VERSION; and the TouchFrameCallback type (alongside the Board* enums and interfaces).

Top-level

Member Type Description
Board.isOnDevice boolean true when running on Board hardware. Gate every device call on this.
Board.sdkVersion string SDK version string. Informational only.

Async style

The SDK uses two async styles:

  • Promises for request and response calls, anything that fetches or mutates state (Board.save.*, Board.avatar.*, Board.session.presentAddPlayer(), and so on) returns a Promise.
  • Callbacks and subscriptions for streams, touch contacts (Board.input.subscribe) and pause results (Board.pause.onResult) are delivered to a callback you register.

Board.input

Member Description
Board.input.subscribe(callback) Start receiving a per-frame snapshot of all active contacts.
Board.input.unsubscribe(callback) Stop receiving snapshots.
Board.input.getContacts() Snapshot of the current active contacts as a ReadonlyArray<BoardContact>.
Board.input.getContactsByType(type) Same snapshot filtered to a BoardContactType, as a ReadonlyArray<BoardContact>.
Board.input.isSubscribed boolean getter, whether the push channel is active.
BoardContactType Enum, Finger, Glyph, Blob.
BoardContactPhase Enum, None, Began, Moved, Ended, Canceled, Stationary.

Each contact in a snapshot carries: contactId, type, glyphId, x, y, orientation, phase, isTouched. Positions are device pixels, origin top-left, Y down. orientation is in degrees and is only meaningful for Glyph contacts. phase is the contact’s lifecycle stage; a still Piece reappears every frame with phase Stationary. isTouched is true while a hand is physically touching the Piece. Identify Pieces by glyphId, not by the type.

Board.session

Member Description
Board.session.getPlayers() The current roster.
Board.session.getPlayerCount() Number of players.
Board.session.addGuest(sessionId) Add a guest player with a session-unique id.
Board.session.removePlayer(sessionId) Remove a player.
Board.session.resetPlayers() Clear to initial state.
Board.session.getActiveProfile() The OS active profile, or null.
Board.session.presentAddPlayer(aiTypeIndices?) Open the selector to add. Resolves Promise<boolean>.
Board.session.presentReplacePlayer(sessionId, aiTypeIndices?) Open the selector to replace. Resolves Promise<boolean>.
Board.session.setAIPlayerTypes(types) Declare AI types ({ name, description }[]) for the selector.
Board.session.isReady() Whether the session manager is ready.
Board.session.areServicesReady() Whether device services are up.
BoardPlayerType Enum (string-valued), Profile ("profile"), Guest ("guest"), AI ("ai"). The type of BoardPlayer.type and BoardSaveGamePlayer.type.

Deprecated showProfileSwitcher() / hideProfileSwitcher() aliases also exist on Board.session for back-compat; prefer Board.application.showProfileSwitcher() / Board.application.hideProfileSwitcher().

The roster is OS-owned. Games never silently add or remove players; changes go through the selector or resetPlayers().

BoardPlayer (returned by getPlayers() and getActiveProfile()):

Field Type Description
playerId string Persistent app-specific player ID.
sessionId number Session-unique ID.
name string Display name.
type BoardPlayerType Whether this is a profile, guest, or AI player.
avatarId string Avatar identifier.
aiTypeIndex number? AI personality index when type is AI. Absent for human players.

Board.save

Member Description
Board.save.create(description, data, playedTime, gameVersion) Create a save. Resolves the BoardSaveGameMetadata.
Board.save.load(saveId) Load a save, including payload.
Board.save.list() List saves (metadata).
Board.save.update(saveId, description, data, playedTime, gameVersion) Update a save. Resolves void.
Board.save.removePlayersFromSave(saveId) Remove the current game’s players from a save. The system deletes the save once no players remain.
Board.save.removeActiveProfileFromSave(saveId) Remove only the active profile from a save. The system deletes the save once no players remain.
Board.save.loadCoverImage(saveId) Load a save’s cover image.
Board.save.getMaxDataSize() Max payload size in bytes for a single save.
Board.save.getMaxAppStorageSize() Max total storage in bytes across all saves.
Board.save.getMaxDescriptionLength() Max description length.
Board.save.getAppStorageInfo() Storage totals and usage percentage.
Board.save.getUniquePlayers(saves) Unique profile players across saves.

Save metadata: id, description, createdAt, updatedAt, playedTime, fileSize, gameVersion, playerCount, players (each playerId, name, avatarId, type, aiTypeIndex), hasCoverImage, payloadChecksum, coverImageChecksum.

BoardAppStorageInfo (returned by getAppStorageInfo()):

Field Type Description
totalStorage number Total storage available to the app, in bytes.
usedStorage number Storage currently used by the app, in bytes.
remainingStorage number Storage still available to the app, in bytes.
usagePercentage number Fraction of storage used, from 0.0 to 1.0.

Board.avatar

Member Description
Board.avatar.loadPNG(avatarId) Load an avatar image as a PNG data URI. Cached by avatarId.
Board.avatar.getDefault() The default avatar (0) as a data URI.
Board.avatar.forPlayer(player) Load a player’s avatar as a data URI.
Board.avatar.clearCache() Drop the avatar cache.

Board.pause

Member Description
Board.pause.setContext(context) Set the pause-menu context.
Board.pause.updateContext(partial) Merge a partial update.
Board.pause.clearContext() Clear the context.
Board.pause.onResult(callback) Subscribe to pause results. Preferred.
Board.pause.pollResult() Legacy, poll the last result.

The OS owns the menu button and UI. The game supplies context and reads results.

BoardPauseContext (passed to setContext(); updateContext() takes a partial):

Field Type Description
gameId string? App/game ID. Used by the OS pause overlay to attribute the session.
gameName string? Display name of the game, shown in the pause menu header.
offerSaveOption boolean? Whether the pause menu shows a “Save & Quit” option in addition to “Quit”.
customButtons BoardPauseButton[]? Custom buttons appended to the pause menu.
audioTracks BoardPauseAudioTrack[]? Audio track volume sliders shown in the pause menu.

BoardPauseButton:

Field Type Description
id string Stable identifier for this button. Returned as customButtonId on BoardPauseResult when pressed.
title string Text shown on the button.
icon 'circulararrow' \| 'doorwitharrow' \| 'leftarrow' \| 'square' \| '' Icon name; the empty string means no icon.

BoardPauseAudioTrack:

Field Type Description
id string Stable identifier for this audio track. Returned on BoardPauseResult.audioTracks when the user adjusts the slider.
name string Display name shown next to the volume slider.
value number Volume value, 0-100.

BoardPauseResult (delivered to onResult(); also returned by pollResult()):

Field Type Description
action 'resume' \| 'quit' \| 'save_and_quit' \| 'custom_button' Action taken. For a custom button this is 'custom_button' and the specific button is in customButtonId.
customButtonId string? ID of the custom button that was pressed, when action is 'custom_button'.
audioTracks BoardPauseAudioTrackResult[]? Updated audio track values, if the user adjusted any sliders before dismissing the menu.

BoardPauseAudioTrackResult:

Field Type Description
id string ID of the audio track (matches BoardPauseAudioTrack.id).
value number New volume value, 0-100, after the user adjusted the slider.

Board.application

Member Description
Board.application.quit() Close the web app, return to the launcher.
Board.application.showProfileSwitcher() Open the OS profile switcher.
Board.application.hideProfileSwitcher() Close the OS profile switcher.

See also