listCameras
listCameras(language?) → Promise<MediaDeviceInfo[]>Enumeration never acquires a stream; labels may be empty until permission has been granted.
| Name | Type | Description |
|---|---|---|
| language? | BrowserLanguage |
API reference · @scanlatch/sdk
Generated from the package entry point. New here? Start with the example below.
Start here
Everything starts with createBrowserSdk. Initialize it once, then ask the instance for a decoder, a camera scanner or a scanline read. When your screen goes away, call destroy and it cleans up everything it made.
Decoding factories live on the instance only. The package root exports no decoder of its own.
import { createBrowserSdk } from '@scanlatch/sdk';
const sdk = createBrowserSdk({ key: accountKey });
await sdk.initialize();
// still images
const decoder = await sdk.createDecoder();
const results = await decoder.decode(file, { symbologies: ['qr', 'ean13'] });
// live camera
const scanner = sdk.createCameraScanner(video, { onDetections: show });
await scanner.start();
sdk.destroy();01 / Instance
Create it with your key and initialize it once, then ask it for a decoder, a camera scanner, a scanline read or detection feedback. Destroying the instance stops everything it made. Camera enumeration and the permission state are exported on their own as well, for use before an instance exists.
listCameras(language?) → Promise<MediaDeviceInfo[]>Enumeration never acquires a stream; labels may be empty until permission has been granted.
| Name | Type | Description |
|---|---|---|
| language? | BrowserLanguage |
cameraPermission() → Promise<CameraPermission>Unsupported Permissions API camera queries are unknown, never inferred by acquisition.
createBrowserSdk(options) → BrowserSdk| Name | Type | Description |
|---|---|---|
| options | BrowserSdkOptions |
createFeedback(options?) → FeedbackLocally synthesized audio, with HTML media fallback; no remote assets or shared AudioContext.
| Name | Type | Description |
|---|---|---|
| options? | FeedbackOptions |
extends Error
| Name | Type | Description |
|---|---|---|
| code | string | Read-only. |
| cameraAccess | boolean | Read-only. |
| Name | Type | Description |
|---|---|---|
| constructor(code: string, message: string, options?: ErrorOptions & { cameraAccess?: boolean; name?: string }) | ||
| Name | Type | Description |
|---|---|---|
| audio? | boolean | { enabled?: boolean; audioSessionType?: AudioSessionType | null; implementation?: AudioImplementation; backend?: AudioBackend } | |
| vibration? | boolean | number | readonly number[] |
| Name | Type | Description |
|---|---|---|
| play() → Promise<void> | ||
| destroy() → void | ||
| Name | Type | Description |
|---|---|---|
| id? | string | null | Local application label only; null clears it. Never persisted or transmitted. |
| language? | BrowserLanguage | |
| audioBackend? | AudioBackend |
| Name | Type | Description |
|---|---|---|
| key | string | |
| decoder? | ImageDecoderOptions | |
| audioImplementation? | AudioImplementation | |
| id? | string | null | Local application label only; null clears it. Never persisted or transmitted.from BrowserSdkConfiguration |
| language? | BrowserLanguage | from BrowserSdkConfiguration |
| audioBackend? | AudioBackend | from BrowserSdkConfiguration |
| Name | Type | Description |
|---|---|---|
| state | BrowserSdkState | Read-only. |
| version | string | Read-only. |
| id | string | null | Read-only. |
| language | BrowserLanguage | Read-only. |
| licenseStatus | LicenseStatus | Read-only. |
| Name | Type | Description |
|---|---|---|
| configure(configuration: BrowserSdkConfiguration) → void | ||
| initialize(signal?: AbortSignal) → Promise<void> | ||
| listCameras() → Promise<MediaDeviceInfo[]> | ||
| cameraPermission() → Promise<CameraPermission> | ||
| createDecoder(options?: ImageDecoderOptions) → Promise<ImageDecoder> | ||
| createCameraScanner(video: HTMLVideoElement | string, options: CameraOptions) → CameraScanner | ||
| decodeScanline(samples: Uint8Array | Uint8ClampedArray, options?: ScanlineOptions) → ScanlineDetection | null | ||
| createFeedback(options?: FeedbackOptions) → Feedback | ||
| destroy() → void | ||
BrowserLanguage="en" | "es"BrowserSdkState="new" | "initializing" | "ready" | "destroyed"CameraPermission="granted" | "denied" | "prompt" | "unknown"AudioSessionType="auto" | "ambient" | "playback" | "transient" | "transient-solo" | "play-and-record"AudioImplementation=() => void | Promise<void>AudioBackend="auto" | "web-audio" | "html-audio"02 / Images
A decoder accepts pixels, an image element, an ImageBitmap, a Blob, a File or a URL, and returns one detection per barcode it read: payload, format, geometry and how the text was resolved.
imageSymbologies = [ 'ean13', 'ean8', 'upca', 'upce', 'databar', 'databar-exp', 'code39', 'code93', 'code128', 'i25', 'codabar', 'qr', 'aztec', 'datamatrix', 'pdf417' ] as const| Name | Type | Description |
|---|---|---|
| x | number | |
| y | number |
| Name | Type | Description |
|---|---|---|
| text | string | |
| format | ImageSymbology | |
| bytes | Uint8Array | |
| symbologyIdentifier | string | |
| rawBytes | Uint8Array | Native message after native checksum disposition, before Scanlatch framing presentation. |
| eciBytes | Uint8Array | Owned standard ECI-protocol bytes; not Unicode re-encoded as bytes. |
| hasECI | boolean | |
| textStatus | 'decoded' | 'unknown-encoding' | |
| contentType | 'text' | 'binary' | 'mixed' | 'gs1' | 'iso15434' | 'unknown-encoding' | |
| readerInitialization | boolean | |
| sequence? | { index: number; total: number; id: string } | |
| supplement? | string | |
| messageAppend | boolean | |
| quadrilateral | [ImagePoint, ImagePoint, ImagePoint, ImagePoint] | |
| boundingRect | { x: number; y: number; width: number; height: number } | |
| decodeDurationMs | number | Worker decode duration in milliseconds, excluding acquisition and queueing. |
| inputReceivedAt | number | Unix milliseconds when decode() accepted the input; not camera exposure time. |
| Name | Type | Description |
|---|---|---|
| format | ImageSymbology | |
| minLength? | number | Bounds on delivered bytes, after framing and checksum disposition. When omitted, ITF requires at least 6 and Codabar at least 2; shorter reads are mostly false positives. |
| maxLength? | number | |
| quietZone? | number | Required exterior margin in module widths, on both sides of a linear symbol. |
| checksum? | ChecksumDisposition | |
| alphabet? | 'basic' | 'extended' | Code 39 shift pairs are literal in basic mode. |
| roundedFinders? | boolean | |
| supplements? | 'ignore' | 'read' | 'require' | Retail add-on symbols are reported separately from the base payload. |
| profile? | 'itf14' | ITF-14 requires the GTIN check digit, regardless of optional-check policy. |
| curved? | boolean |
| Name | Type | Description |
|---|---|---|
| symbologies? | readonly (ImageSymbology | ImageFormatRule)[] | Omitted or empty enables all fifteen families. |
| inverted? | boolean | |
| maxDetections? | number | Integer from 1 to 255; defaults to 1. |
| minimumScanlines? | number | Distinct source scanlines required for linear decoding. Defaults to 2. |
| signal? | AbortSignal |
| Name | Type | Description |
|---|---|---|
| wasmUrl? | string | URL | |
| signal? | AbortSignal | Cancels initialization only; the SDK instance owns the returned decoder's lifetime. |
| Name | Type | Description |
|---|---|---|
| decode(input: ImageInput, options?: ImageDecodeOptions) → Promise<ImageDetection[]> | ||
| destroy() → void | ||
ImageSymbology="ean13" | "ean8" | "upca" | "upce" | "databar" | "databar-exp" | "code39" | "code93" | "code128" | "i25" | "codabar" | "qr" | "aztec" | "datamatrix" | "pdf417"ChecksumDisposition="none" | "strip" | "retain"ImageInput=string | ImageData | HTMLImageElement | ImageBitmap | Blob | File03 / Camera
You supply a video element and a detection callback. The scanner owns the stream, the frames, the camera switch and the torch and focus controls, and calls you back whenever it reads something.
Fractions of the displayed video content box; each inset is in [0, 0.5]. Capture keeps the visible frame. A detection is kept only when its center lies inside these insets.
| Name | Type | Description |
|---|---|---|
| top? | number | |
| right? | number | |
| bottom? | number | |
| left? | number |
| Name | Type | Description |
|---|---|---|
| torch | boolean | |
| focus | boolean |
extends FrameOptions
| Name | Type | Description |
|---|---|---|
| onDetections | (detections: ImageDetection[]) => void | |
| onError? | (error: Error) => void | |
| decoder? | ImageDecoder | Borrowed decoders are never destroyed by the camera controller. |
| constraints? | MediaTrackConstraints | |
| resolution? | 'auto' | 'hd' | 'full-hd' | |
| rememberCamera? | boolean | string | True uses the default local-storage key; a string selects an application key. |
| imageOptions? | Omit<ImageDecodeOptions, 'signal'> | |
| frameIntervalMs? | number | |
| duplicateIntervalMs? | number | |
| hysteresis? | { count: number; intervalMs: number } | |
| mode? | 'continuous' | 'triggered' | |
| triggerDurationMs? | number | |
| feedback? | FeedbackOptions | |
| language? | 'en' | 'es' | |
| region? | ScanRegion | from FrameOptions |
| backend? | 'auto' | 'cpu' | 'webgl2' | from FrameOptions |
| readback? | 'auto' | 'sync' | 'deferred' | from FrameOptions |
| chromaReject? | boolean | Apply filterChromaticDetections to the original captured pixels before remapping results.from FrameOptions |
| Name | Type | Description |
|---|---|---|
| state | 'new' | 'initializing' | 'ready' | 'running' | 'destroyed' | Read-only. |
| visible | boolean | Read-only. |
| backend | 'cpu' | 'webgl2' | undefined | Read-only. |
| readback | 'sync' | 'deferred' | undefined | Read-only. |
| readbackReason | string | undefined | Read-only. |
| Name | Type | Description |
|---|---|---|
| initialize() → Promise<void> | ||
| start() → Promise<void> | ||
| stop() → void | ||
| destroy() → void | ||
| switchCamera(deviceId: string) → Promise<void> | ||
| setVisible(visible: boolean) → void | ||
| trigger() → void | ||
| getCapabilities() → CameraCapabilities | ||
| setTorch(enabled: boolean) → Promise<void> | ||
| focus(point: { x: number; y: number }) → Promise<void> | ||
04 / Overlay
Optional. It draws a viewfinder, marks what was found, and can add a camera picker, a torch toggle and tap to focus. It never changes how the scanner is configured.
createCameraOverlay(container, scanner, video, options?) → CameraOverlayAn opt-in presenter in an isolated shadow root. The container and video stay caller-owned. Placement follows the video's viewport, object fit/position and supported axis-aligned transforms. Create once, forward onDetections to update(), and destroy independently of the scanner.
| Name | Type | Description |
|---|---|---|
| container | HTMLElement | |
| scanner | CameraScanner | |
| video | HTMLVideoElement | |
| options? | CameraOverlayOptions |
| Name | Type | Description |
|---|---|---|
| primaryColor? | string | Colors accept only sRGB #RRGGBB or #RRGGBBAA. Defaults use neutral black/white. |
| detectionFillColor? | string | |
| detectionBorderColor? | string | |
| targetingLineActiveColor? | string | |
| maskColor? | string | |
| detectionBorderWidth? | number | Finite CSS-pixel width clamps to [0, 4], default 0 (no outline). |
| viewfinderBorderWidth? | number | Finite CSS-pixel width clamps to [1, 20], default 1. |
| cornerRadius? | number | Finite general/control corner radius clamps to [0, 8], default 0. |
| viewfinderCornerRadius? | number | Overrides the general radius; clamps to [0, 20], then half the shorter side. |
| Name | Type | Description |
|---|---|---|
| language? | BrowserLanguage | Explicit language wins over SDK language, then browser language, then English. |
| sdk? | Pick<BrowserSdk, 'language' | 'listCameras'> | |
| cameras? | boolean | ((camera: MediaDeviceInfo) => boolean) | False hides the selector; a predicate filters enumerated video inputs. Never requests permission. |
| torch? | boolean | |
| tapFocus? | boolean | |
| trigger? | boolean | Enable for a scanner configured with mode:'triggered'. Default false. |
| targetingLine? | boolean | |
| detections? | boolean | Detection visuals are enabled by default. |
| detectionDurationMs? | number | Finite display lifetime clamps to [0, 60000] milliseconds, default 1000. |
| region? | ScanRegion | Pass the same region as CameraOptions.region; the presenter cannot change scanner configuration. |
| logo? | { url: string; alt: string } | HTTP(S), blob or data:image URLs; alt must be nonempty. Caller owns URL lifetime. |
| theme? | CameraOverlayTheme | |
| onError? | (error: Error) => void |
| Name | Type | Description |
|---|---|---|
| update(detections: ImageDetection[]) → void | Replaces displayed detections. Geometry is copied; caller-owned results are never mutated. | |
| destroy() → void | Removes only owned DOM/listeners. Does not stop scanning, tracks, or the caller's video. | |
05 / Scanline
Reads the retail formats from a single line of grayscale samples, on the calling thread, with no worker and nothing to download.
| Name | Type | Description |
|---|---|---|
| symbologies? | readonly RetailSymbology[] | Omitted or empty enables all four retail formats. |
| inverted? | boolean | Also recognize light bars on a dark background. |
| Name | Type | Description |
|---|---|---|
| data | string | Includes the check digit; UPC-E also includes its number-system digit. |
| typeName | RetailSymbology | |
| start | number | Increasing, half-open pixel bounds in the original input, excluding quiet zones. |
| end | number | |
| direction | "forward" | "reverse" |
RetailSymbology="ean13" | "ean8" | "upca" | "upce"06 / Your key
Read the status off the instance at any time. When a check refuses, the SDK throws a LicenseError carrying the reason.
extends Error
| Name | Type | Description |
|---|---|---|
| code | LicenseFailure | Read-only. |
| Name | Type | Description |
|---|---|---|
| constructor(code: LicenseFailure) | ||
| Name | Type | Description |
|---|---|---|
| state | 'new' | 'checking' | 'trial' | 'paid-online' | 'paid-offline' | 'blocked' | 'protocol-error' | 'destroyed' | Read-only. |
| installationId? | string | Read-only. |
| trialEndsAt? | number | Read-only. |
| reason? | LicenseFailure | Read-only. |
LicenseFailure="destroyed" | "not-initialized" | "unavailable" | "protocol-error" | "storage" | "expired" | "aborted" | "origin-not-registered" | "trial-expired" | "trial-required" | "subscription-inactive" | "payment-required"Next
The setup guide takes you from account to a working camera in about ten minutes.