Examples

This page provides practical examples for common Web SDK use cases.

Basic Examples

Minimal Setup

The simplest way to get started with a preset:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin'
});

anyline.onResult = ({ result }) => {
  console.log('Scanned:', result);
};

anyline.startScanning();

With Error Handling

Always handle errors for production use:

import { init } from '@anyline/anyline-js';

async function startScanner() {
  try {
    const anyline = init({
      license: 'YOUR_LICENSE_KEY',
      element: document.getElementById('scanner-root'),
      preset: 'vin'
    });

    anyline.onResult = ({ result }) => {
      console.log('Scanned:', result);
    };

    await anyline.startScanning();
    console.log('Scanning started successfully');
  } catch (error) {
    console.error('Failed to start scanning:', error);
  }
}

startScanner();

With Lifecycle Management

Complete example with start/stop/pause controls:

import { init, AnylineJS } from '@anyline/anyline-js';

let anyline: AnylineJS | null = null;

// Initialize
function initScanner() {
  const container = document.getElementById('scanner-root');
  if (!container) {
    throw new Error('Scanner container not found');
  }

  anyline = init({
    license: 'YOUR_LICENSE_KEY',
    element: container,
    preset: 'vin'
  });

  anyline.onResult = ({ result }) => {
    console.log('Scanned:', result);
    displayResult(result);
  };
}

// Start scanning
async function startScanning() {
  if (!anyline) initScanner();

  try {
    await anyline?.startScanning();
    updateUI('scanning');
  } catch (error) {
    console.error('Start failed:', error);
  }
}

// Stop scanning
function stopScanning() {
  anyline?.stopScanning();
  updateUI('stopped');
}

// Pause scanning
function pauseScanning() {
  anyline?.pauseScanning();
  updateUI('paused');
}

// Resume scanning
async function resumeScanning() {
  try {
    await anyline?.resumeScanning();
    updateUI('scanning');
  } catch (error) {
    console.error('Resume failed:', error);
  }
}

// Cleanup
function cleanup() {
  anyline?.dispose();
  anyline = null;
}

// UI helpers
function updateUI(state: string) {
  document.getElementById('status')!.textContent = `Status: ${state}`;
}

function displayResult(result: any) {
  document.getElementById('result')!.textContent = JSON.stringify(result, null, 2);
}

// Cleanup on page unload
window.addEventListener('beforeunload', cleanup);

Advanced Examples

Preload Assets

Improve performance by preloading assets before scanning:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  preload: true,
  preloadCallback: () => {
    console.log('Assets preloaded successfully');
    document.getElementById('loader')?.remove();
  }
});

// Trigger preload
anyline.preload();

// Start scanning when ready
document.getElementById('start-btn')?.addEventListener('click', () => {
  anyline.startScanning();
});

Lock Screen Orientation

Lock to portrait mode for mobile devices:

import { init } from '@anyline/anyline-js';

const container = document.getElementById('scanner-root')!;

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: container,
  preset: 'universalid_dl_at_de',
  lockPortraitOrientation: {
    element: container,
    lock: true
  }
});

anyline.onResult = ({ result }) => {
  console.log('Scanned:', result);
};

anyline.startScanning();

Manual Frame Capture

Capture camera frames manually:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin'
});

async function bootstrap() {
  await anyline.startScanning();

  document.getElementById('capture-btn')?.addEventListener('click', () => {
    const frame = anyline.getFrame();

    if (frame?.fullImage) {
      const canvas = document.createElement('canvas');
      const ctx = canvas.getContext('2d');

      canvas.width = frame.fullImage.width;
      canvas.height = frame.fullImage.height;

      if (ctx) {
        ctx.putImageData(frame.fullImage, 0, 0);

        // Convert to image element
        const img = document.createElement('img');
        img.src = canvas.toDataURL();
        img.style.maxWidth = '300px';
        document.body.appendChild(img);
      }
    }
  });
}

bootstrap();

Camera Mirror Control

Mirror the camera stream on desktop:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  mirrorOnDesktop: true
});

// Toggle mirror at runtime; isMirrored() reflects the SDK's
// auto-detected state, so no manual bookkeeping is needed
document.getElementById('mirror-btn')?.addEventListener('click', () => {
  anyline.camera.mirrorStream(!anyline.camera.isMirrored());
});

anyline.startScanning();

Inverted Camera Mount

Scan with a camera mounted 180° (upside down), showing an upright preview to the operator. The OCR-frame flips correct the image for the recognizer; the preview flips only change what the operator sees. In every combination, the recognizer processes exactly what is visible inside the cutout:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  // Rotate the image sent to the recognizer by 180°
  enableFlipFramesLeftRight: true,
  enableFlipFramesTopBottom: true
});

async function start() {
  await anyline.startScanning();

  // Rotate the preview by 180° so the operator sees an upright image
  anyline.camera.mirrorStream(true);
  anyline.camera.flipStream(true);
}

start();

Flash Control

Control camera flash/torch (Chrome for Android, Safari 18.4+):

import { init, OnlyAndroidChromeError } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin'
});

let flashOn = false;

(async () => {
  await anyline.startScanning();

  const button = document.getElementById('flash-btn');
  if (!button) return;

  button.addEventListener('click', async () => {
    const nextState = !flashOn;
    try {
      await anyline.camera.activateFlash(nextState);
      flashOn = nextState;
      button.textContent = flashOn ? 'Flash On' : 'Flash Off';
    } catch (error) {
      if (error instanceof OnlyAndroidChromeError) {
        console.warn('Flash control not supported on this browser');
      } else {
        console.warn('Flash control failed', error);
      }
    }
  });
})();

Custom Camera Constraints

Specify custom camera resolution and facing mode:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  mediaConstraints: {
    video: {
      width: { ideal: 1920 },
      height: { ideal: 1080 },
      facingMode: 'environment'  // Use rear camera
    }
  }
});

anyline.startScanning();
mediaConstraints uses the browser’s MediaDevices API and inherits its limitations. When manually set, the Anyline camera selection logic is overridden and camera selection may fail on specific devices.

Haptic Feedback

Enable sound and vibration on scan:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  hapticFeedback: true,
  flashOnResult: true  // Also flash on result
});

anyline.startScanning();

State Management

Monitor SDK state changes:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin'
});

function checkState() {
  const state = anyline.getState();
  console.log('Current state:', state);
  updateStatusUI(state);
}

function updateStatusUI(state: string) {
  document.getElementById('status')!.textContent = `Status: ${state}`;
}

(async () => {
  await anyline.startScanning();
  checkState();  // 'scanning'

  anyline.pauseScanning();
  checkState();  // 'paused'

  anyline.stopScanning();
  checkState();  // 'stopped'

  anyline.dispose();
  checkState();  // 'disposed'
})();

Custom ViewConfig

Customize the visual appearance with custom colors and cutout styling:

import { init } from '@anyline/anyline-js';

const anyline = init({
  license: 'YOUR_LICENSE_KEY',
  element: document.getElementById('scanner-root'),
  preset: 'vin',
  viewConfig: {
    outerColor: '000000',
    outerAlpha: 0.5,
    cutouts: [
      {
        cutoutConfig: {
          alignment: 'center',
          width: 300,
          maxWidthPercent: '80%',
          style: 'rect',
          strokeColor: '00FF00',
          strokeWidth: 3,
          cornerRadius: 10,
          ratioFromSize: {
            width: 250,
            height: 60
          }
        },
        scanFeedback: {
          style: 'rect',
          strokeColor: '00FF00',
          strokeWidth: 4
        }
      }
    ]
  }
});

anyline.startScanning();

See Also