Skip to main content
Markers allow you to add named points on the timeline for navigation and organization.

Marker

Interface representing a timeline marker.
interface Marker {
  id: string;
  time: number;              // seconds
  label?: string;
  color?: string;            // hex code
  metadata?: Record<string, any>;
}

validateMarker()

Validates a single marker.
const validated = validateMarker(marker);
marker
Marker
required
Marker object to validate
validated
Marker
Validated marker (throws error if invalid)

Example

import { validateMarker } from '@heliosvideo/core';

const marker = validateMarker({
  id: 'intro-end',
  time: 5.5,
  label: 'End of intro',
  color: '#3b82f6',
});

// Throws if invalid:
// - Missing or empty ID
// - Negative time

validateMarkers()

Validates an array of markers.
const validated = validateMarkers(markers);
markers
Marker[]
required
Array of markers to validate
validated
Marker[]
Validated and sorted markers (throws error if invalid or duplicate IDs)

Example

import { validateMarkers } from '@heliosvideo/core';

const markers = validateMarkers([
  { id: 'scene-2', time: 10, label: 'Scene 2' },
  { id: 'intro', time: 0, label: 'Intro' },
  { id: 'outro', time: 25, label: 'Outro' },
]);

// Returns sorted by time:
// [
//   { id: 'intro', time: 0, label: 'Intro' },
//   { id: 'scene-2', time: 10, label: 'Scene 2' },
//   { id: 'outro', time: 25, label: 'Outro' },
// ]

Using markers with Helios

Setting markers

import { Helios } from '@heliosvideo/core';

const helios = new Helios({
  duration: 30,
  fps: 30,
  markers: [
    { id: 'intro', time: 0, label: 'Intro', color: '#3b82f6' },
    { id: 'main', time: 5, label: 'Main Content', color: '#10b981' },
    { id: 'outro', time: 25, label: 'Outro', color: '#f59e0b' },
  ],
});

Adding markers dynamically

helios.addMarker({
  id: 'highlight',
  time: 15.5,
  label: 'Important moment',
  color: '#ef4444',
  metadata: {
    importance: 'high',
    notes: 'Key talking point',
  },
});

Removing markers

helios.removeMarker('highlight');

Seeking to markers

helios.seekToMarker('intro');
helios.seekToMarker('outro');

Accessing markers

// Get all markers
const allMarkers = helios.markers.value;

// Subscribe to marker changes
helios.markers.subscribe((markers) => {
  console.log('Markers updated:', markers);
});

// Find marker by ID
const introMarker = allMarkers.find(m => m.id === 'intro');

Complete example

import { Helios } from '@heliosvideo/core';

const helios = new Helios({
  duration: 60,
  fps: 30,
  markers: [
    {
      id: 'chapter-1',
      time: 0,
      label: 'Chapter 1: Introduction',
      color: '#3b82f6',
      metadata: { chapter: 1 },
    },
    {
      id: 'chapter-2',
      time: 20,
      label: 'Chapter 2: Main Content',
      color: '#10b981',
      metadata: { chapter: 2 },
    },
    {
      id: 'chapter-3',
      time: 45,
      label: 'Chapter 3: Conclusion',
      color: '#f59e0b',
      metadata: { chapter: 3 },
    },
  ],
});

// Render timeline with markers
function renderTimeline() {
  const markers = helios.markers.value;
  const duration = helios.duration.value;
  
  markers.forEach((marker) => {
    const position = (marker.time / duration) * 100;
    
    createMarkerElement({
      position: `${position}%`,
      color: marker.color,
      label: marker.label,
      onClick: () => helios.seekToMarker(marker.id),
    });
  });
}

// Navigate between chapters
function nextChapter() {
  const markers = helios.markers.value;
  const currentTime = helios.currentTime.value;
  
  const nextMarker = markers.find(m => m.time > currentTime);
  if (nextMarker) {
    helios.seekToMarker(nextMarker.id);
  }
}

function previousChapter() {
  const markers = helios.markers.value;
  const currentTime = helios.currentTime.value;
  
  const previousMarker = markers
    .reverse()
    .find(m => m.time < currentTime);
  
  if (previousMarker) {
    helios.seekToMarker(previousMarker.id);
  }
}

Marker metadata

The metadata field can store arbitrary data:
helios.addMarker({
  id: 'scene-change',
  time: 12.5,
  label: 'Scene Change',
  metadata: {
    sceneId: 'beach-scene',
    camera: 'wide-shot',
    notes: 'Transition to beach',
    tags: ['outdoor', 'sunset'],
  },
});

// Access metadata
const marker = helios.markers.value.find(m => m.id === 'scene-change');
const sceneId = marker?.metadata?.sceneId;

Build docs developers (and LLMs) love