Jump to content

First steps with VidPly

Welcome to VidPly! This guide will help you set up VidPly in 5 minutes.

VidPly Logo

Prerequisites

  • Node.js 20+ installed
  • A text editor
  • A modern web browser
 

Quick installation

1. Download the code

 
git clone github.com/MatthiasPeltzer/vidply.git
cd vidply
 

2. Install dependencies

 
npm install
 

This will install the following:

  • esbuild - Fast TypeScript/JavaScript bundler
  • typescript - Strict type checking and .d.ts output
  • clean-css - CSS minifier
  • vitest + @playwright/test - Unit and end-to-end tests

3. Creating the player

 
npm run build
 

This generates production-ready files in dist/:

  • prod/vidply.esm.min.js - Minified ES module (recommended for production)
  • legacy/vidply.min.js - Minified IIFE bundle (global VidPly)
  • types/index.d.ts - TypeScript type declarations for IDE / tsc users
  • vidply.min.css - Minified styles (~12 KB)

4. Watch the demo

 
npm run dev
 

Open http://localhost:3000/demo/ to see VidPly in action!

Your first video player

Create index.html

 
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>My Video Player</title>
  <link rel="stylesheet" href="dist/vidply.min.css">
</head>
<body>
  <h1>My Video Player</h1>
  
  <video 
    data-vidply 
    width="800" 
    height="450"
    poster="poster.jpg"
  >
    <source src="video.mp4" type="video/mp4">
    <track 
      kind="captions" 
      src="captions.vtt" 
      srclang="en" 
      label="English"
    >
  </video>

  <script type="module">
    import Player from './dist/prod/vidply.esm.min.js';
    // That's it! Player auto-initializes
  </script>
</body>
</html>
 

Test

 
# Start a local server
npm run dev

# Or use Python
python -m http.server 3000

# Or use PHP
php -S localhost:3000
 

Open http://localhost:3000 in your browser.

Quick start in 3 steps

If you want to use the source files directly without compiling them:

Step 1: Insert the CSS

 
<link rel="stylesheet" href="src/styles/vidply.css">
 

Step 2: Add your video

 
<video data-vidply width="800" height="450">
  <source src="your-video.mp4" type="video/mp4">
</video>
 

Step 3: Import the player

 
<script type="module">
  import Player from './src/index.js';
</script>
 

That’s it!

Simple examples

Example 1: Simple video

 
<!DOCTYPE html>
<html>
<head>
  <link rel="stylesheet" href="src/styles/vidply.css">
</head>
<body>
  <video data-vidply src="video.mp4" width="800" height="450"></video>
  
  <script type="module">
    import Player from './src/index.js';
  </script>
</body>
</html>
 

Example 2: Audio player

 
<audio data-vidply>
  <source src="music.mp3" type="audio/mpeg">
  <track kind="captions" src="lyrics.vtt" srclang="en" label="Lyrics">
</audio>
 

Example 3: YouTube video

 
<video 
  data-vidply 
  src="https://www.youtube.com/watch?v=dQw4w9WgXcQ"
></video>
 

Example 4: Vimeo video

 
<video 
  data-vidply 
  src="https://vimeo.com/76979871"
></video>
 

Example 5: SoundCloud track

 
<audio
  data-vidply
  src="https://soundcloud.com/artist/track-name"
></audio>
 

Example 6: HLS streaming

 
<video 
  data-vidply 
  src="https://example.com/stream.m3u8"
></video>
 

Example 7: DASH streaming

 
<video 
  data-vidply 
  src="https://example.com/video/dash/manifest.mpd"
></video>
 

Example 8: With download button

 
<video
  data-vidply
  data-vidply-download-button="true"
  data-vidply-download-url="/files/lecture.mp4"
  src="/streams/lecture/manifest.mpd">
</video>
 

Example 9: With the custom floating player

Enable the on-page floating player (“custom PiP”). When the original content is scrolled out of view, VidPly displays the video in a movable, resizable floating shell in the selected corner; when it is scrolled back into view, the player re-docks. The PiP button in the control bar manually locks or unlocks the floating shell. The native browser PiP is automatically suppressed whilst the floating player is active.

 
<video
  data-vidply
  data-vidply-options='{"floating": true, "floatingPosition": "bottom-right", "floatingMinViewportWidth": 768}'
  src="video.mp4"
  width="800" height="450">
  <track kind="subtitles" src="captions.vtt" srclang="en" label="English">
</video>
 

Ignore audio player floating. The function is available under floatingMinViewportWidth (default 768px) and the button for the floating PiP player never appears in the overflow menu.

 

Example 10: With options

 
<video 
  data-vidply 
  data-vidply-options='{"autoplay": true, "loop": true, "muted": true}'
  src="video.mp4"
></video>
 

Example 11: Manual initialisation

 
<video id="my-video" src="video.mp4"></video>

<script type="module">
  import Player from './dist/prod/vidply.esm.min.js';

  const player = new Player('#my-video', {
    controls: true,
    autoplay: false,
    volume: 0.8,
    language: 'en'
  });

  player.on('ready', () => {
    console.log('Player is ready!');
  });
</script>
 

Do you work with TypeScript? Import directly from the source code directory (import Player from 'vidply') – VidPly provides its own .d.ts declarations, giving you full type safety PlayerOptions, events and renderer APIs.

 

Configuration

About data attributes

 
<video 
  data-vidply 
  data-vidply-options='{
    "autoplay": true,
    "loop": true,
    "volume": 0.5,
    "language": "de"
  }'
  src="video.mp4"
></video>
 

About JavaScript

 
const player = new Player('#my-video', {
  controls: true,
  autoplay: false,
  loop: false,
  volume: 0.8,
  playbackSpeed: 1.0,
  captions: true,
  captionsDefault: true,
  keyboard: true,
  language: 'en',
  responsive: true
});
 

General options

 
{
  // Playback
  autoplay: false,      // Auto-start playback
  loop: false,          // Loop video
  muted: false,         // Start muted
  volume: 0.8,          // Volume (0-1)
  playbackSpeed: 1.0,   // Speed (0.25-2.0)
  
  // Display
  responsive: true,     // Responsive sizing
  controls: true,       // Show controls
  
  // Captions
  captions: true,       // Enable captions
  captionsDefault: false, // Show captions by default
  
  // Accessibility
  keyboard: true,       // Keyboard shortcuts
  
  // Language
  language: 'en'        // UI language (en, es, fr, de, ja)
}
 

Multilingual captions

 
<video data-vidply src="video.mp4">
  <track kind="captions" src="en.vtt" srclang="en" label="English">
  <track kind="captions" src="es.vtt" srclang="es" label="Español">
  <track kind="captions" src="fr.vtt" srclang="fr" label="Français">
  <track kind="captions" src="de.vtt" srclang="de" label="Deutsch">
</video>
 

How it works:

  • Click the CC button to open the subtitles menu
  • Select your preferred language
  • Or press C to open the menu (if multiple audio tracks are available)
  • The active audio track is marked with a tick

Create subtitles (WebVTT)

Create a file named captions.vtt:

 
WEBVTT

00:00:00.000 --> 00:00:05.000
Welcome to my video!

00:00:05.000 --> 00:00:10.000
This is how captions work.

00:00:10.000 --> 00:00:15.000
Pretty easy, right?
 

Player controls

 
const player = new Player('#video');

// Playback
player.play();
player.pause();
player.stop();
player.seek(60);  // Jump to 1 minute

// Volume
player.setVolume(0.5);  // 50% volume
player.mute();
player.unmute();

// Speed
player.setPlaybackSpeed(1.5);  // 1.5x speed

// Fullscreen
player.enterFullscreen();
player.exitFullscreen();

// Captions
player.enableCaptions();
player.disableCaptions();

// Events
player.on('play', () => console.log('Playing!'));
player.on('pause', () => console.log('Paused'));
player.on('ended', () => console.log('Finished'));
player.on('timeupdate', (time) => {
  console.log('Current time:', time);
});
 

Keyboard shortcuts

Once the player is in focus:

  • Space bar / P / K – Play/Pause
  • F – Full screen
  • M – Mute/Unmute
  • / – Increase/decrease volume
  • / – Skip forward/backward 10 seconds
  • C – Turn subtitles on/off
  • A – Open subtitle style menu
  • < / > – Decrease/increase speed
  • S – Open speed menu
  • Q – Open quality menu
  • J – Open chapter menu
  • T – Turn transcript on/off
  • D – Toggle drag mode (transcript/sign language)
  • R – Switch between resize mode (transcript/sign language)
  • Home – Reset position (transcript/sign language)
  • Esc – Exit mode or close menu

Customise styles

Override CSS variables

 
.vidply-player {
  --vidply-primary-color: #ff0000;
  --vidply-background: rgba(0, 0, 0, 0.9);
}
 

Custom progress bar

 
.vidply-progress-played {
  background: linear-gradient(90deg, #ff0000, #ff00ff);
}
 

Custom button hover

 
.vidply-button:hover {
  background: rgba(255, 0, 0, 0.2);
}
 

Change language

Supported languages

VidPly includes translations for 5 languages:

  • en - English
  • es - Spanish (Español)
  • fr - French (Français)
  • de - German
  • ja - Japanese (日本語)
const player = new Player('#video', {
  language: 'de'  // German UI
});
 

Custom translations

You can add your own translations by loading language files via URLs. The player supports the JSON and YAML formats.

Using data attributes

Loading multiple language files:

 
<video 
  data-vidply 
  data-vidply-language-files='{"pt": "languages/pt.json", "it": "languages/it.json"}'
  src="video.mp4"
></video>
 

Loading a single language file:

 
<video 
  data-vidply 
  data-vidply-language-file='{"pt": "languages/pt.json"}'
  src="video.mp4"
></video>
 

Or use separate attributes:

 
<video 
  data-vidply 
  data-vidply-language-file-code="pt"
  data-vidply-language-file-url="languages/pt.json"
  src="video.mp4"
></video>
 

Using JavaScript options

 
const player = new Player('#video', {
  language: 'pt',  // Set language after loading
  languageFiles: {
    'pt': 'languages/pt.json',
    'it': 'languages/it.json'
  }
});
 

Language file format (JSON)

Create file languages/pt.json:

 
{
  "player": {
    "play": "Reproduzir",
    "pause": "Pausar",
    "mute": "Silenciar",
    "unmute": "Ativar som",
    "fullscreen": "Tela cheia",
    "exitFullscreen": "Sair da tela cheia",
    "captions": "Legendas",
    "settings": "Configurações"
  },
  "time": {
    "currentTime": "Tempo atual",
    "duration": "Duração"
  }
}
 

Automatic detection from HTML

The player automatically detects the language based on the HTML attribute lang , provided a suitable translation is available:

 
<html lang="pt">
  <video data-vidply 
         data-vidply-language-file='{"pt": "languages/pt.json"}'
         src="video.mp4">
  </video>
</html>
 

Programmatic loading of translations

 
import { i18n } from './src/i18n/i18n.js';

// Load a language file
await i18n.loadLanguageFromUrl('pt', 'languages/pt.json');

// Or load multiple languages
await i18n.loadLanguagesFromUrls({
  'pt': 'languages/pt.json',
  'it': 'languages/it.json'
});

// Set the language
i18n.setLanguage('pt');
 

Development mode

Enable debug logging:

 
const player = new Player('#video', {
  debug: true
});
 

Check the browser console for detailed logs.

Deployment options

Option 1: ES module (modern browsers)

 
<link rel="stylesheet" href="dist/vidply.min.css">
<script type="module">
  import Player from './dist/prod/vidply.esm.min.js';
</script>
 

Option 2: Traditional script tag (IIFE)

 
<link rel="stylesheet" href="dist/vidply.min.css">
<script src="dist/legacy/vidply.min.js"></script>
<script>
  const player = new VidPly.Player('#video');
</script>
 

Option 3: CDN (future)

 
<!-- Will be available after publishing to npm -->
<link rel="stylesheet" href="https://cdn.example.com/vidply@1.0.0/vidply.min.css">
<script type="module">
  import Player from 'https://cdn.example.com/vidply@1.0.0/vidply.esm.min.js';
</script>
 

Optimisation for mobile devices

VidPly is mobile-friendly by default, with a mobile breakpoint at 768px. For best results:

 
<meta name="viewport" content="width=device-width, initial-scale=1.0">
 

And use responsive mode:

 
const player = new Player('#video', {
  responsive: true
});
 

Mobile-specific behaviour (< 768px breakpoint):

  • The transcript window appears below the video (cannot be moved or resized)
  • The sign language video cannot be moved or resized
  • Optimised control bar with overflow menu for numerous buttons
  • Touch-friendly interface with touch targets of at least 44px
  • Minimum width of the transcript window: 300px

Accessibility

VidPly is WCAG 2.2 AA-compliant by default:

  • Full keyboard navigation
  • Support for screen readers
  • High-contrast mode
  • Focus indicators
  • ARIA labels

No additional configuration required!

Troubleshooting

Video won't play

  1. Check the console for errors (press F12)
  2. Check that the video URL is correct
  3. Check the CORS headers if the video is being loaded from a different domain
  4. Enable debug mode: { debug: true }

Subtitles are not displayed

  1. Check that the VTT file format is correct
  2. Check the file path
  3. Enable subtitles: Click the CC button
  4. Or enable by default: { captionsDefault: true }

Creation failed

 
# Clean and rebuild
npm run clean
rm -rf node_modules
npm install
npm run build
 

Autoplay is not working

Browsers block automatic playback with sound. Solution:

 
const player = new Player('#video', {
  autoplay: true,
  muted: true  // Required for autoplay
});
 

Available build scripts

 
npm run build        # Build everything
npm run build:js     # Build JS only
npm run build:css    # Build CSS only
npm run watch        # Watch mode for development
npm run clean        # Clean dist/
npm run dev          # Start dev server (port 3000)
npm start            # Alias for npm run dev
 

File structure

Once created, you will receive:

 
vidply/
├── dist/
│   ├── dev/
│   │   └── vidply.esm.js       # ES Module (dev)
│   ├── prod/
│   │   └── vidply.esm.min.js   # ES Module (prod)
│   ├── legacy/
│   │   ├── vidply.js           # IIFE (dev)
│   │   └── vidply.min.js       # IIFE (prod)
│   ├── types/
│   │   └── index.d.ts          # TypeScript declarations
│   ├── vidply.css              # Styles (dev)
│   └── vidply.min.css          # Styles (prod)
└── ...
 

Include in production only:

  • dist/prod/vidply.esm.min.js (or dist/legacy/vidply.min.js)
  • dist/vidply.min.css

Total: ~62 KB uncompressed, ~18 KB gzipped

Streaming (HLS & DASH)

VidPly automatically recognises streaming formats based on the file extension:

  • HLS (.m3u8) – Used hls.js in Chrome / Firefox / Edge / Desktop Safari (loaded automatically from the CDN). On iOS / iPadOS, native <video> HLS support is used and integrated via the TextTrack API.
  • DASH (.mpd) – Used dash.js, automatically loaded from the CDN.
  • SoundCloud – Detected automatically for every URL that soundcloud.com; the SoundCloud Widget API is loaded on demand.
<!-- HLS -->
<video data-vidply src="https://example.com/stream.m3u8"></video>

<!-- DASH -->
<video data-vidply src="https://example.com/manifest.mpd"></video>

<!-- SoundCloud -->
<audio data-vidply src="https://soundcloud.com/artist/track-name"></audio>
 

All formats support adaptive quality selection and subtitles. DASH streams with embedded TTML subtitles are rendered natively by dash.js, whilst WebVTT subtitles are processed by VidPly’s subtitling system and also support the interactive transcript.

Next steps

Tips

  1. Always use a local server – do not open HTML files directly (file://)
  2. Enable subtitles by default for better accessibility
  3. Use responsive mode to support mobile devices
  4. Test keyboard shortcuts to ensure accessibility
  5. Check the browser console for helpful debug messages

You're all set!

That’s it! You now know how to:

  • Install and create
  • Create video/audio players
  • Add subtitles
  • Configure options
  • control playback
  • Customise styles

Enjoy coding!

Need help? Check the README file or create a ticket.

Share page