![SlashedCloud Player](public/SlashedCloud.png)

- [SlashedCloud Player](#slashedcloud-player)
- [Usage](#usage)
  - [Basic Installation](#basic-installation)
  - [Event listeners](#event-listeners)
  - [Advanced](#advanced)
    - [Custom Plugins](#custom-plugins)
- [Options](#options)
  - [Autoplay](#autoplay)
  - [Debug](#debug)
  - [Height](#height)
  - [Language](#language)
  - [Muted](#muted)
  - [Persister](#persister)
  - [Plays Inline](#plays-inline)
  - [Src](#src)
    - [IMA SDK Integration](#ima-sdk-integration)
    - [AWS Elemental MediaTailor Integration](#aws-elemental-mediatailor-integration)
    - [HTTP Live Streaming (HLS), MPEG-DASH (MPD)](#http-live-streaming-hls-mpeg-dash-mpd)
    - [Progressive Download](#progressive-download)
  - [Width](#width)
- [Extra Options](#extra-options)
  - [Ad Statistics List](#ad-statistics-list)
  - [Add BigPlay Button](#add-bigplay-button)
  - [Add Seek Bar](#add-seek-bar)
  - [Cast Android Receiver Compatible](#cast-android-receiver-compatible)
  - [Cast Receiver App Id](#cast-receiver-app-id)
  - [Clear Buffer On Quality Change](#clear-buffer-on-quality-change)
  - [Context Menu Elements](#context-menu-elements)
  - [Control Panel Elements](#control-panel-elements)
  - [Custom Context Menu](#custom-context-menu)
  - [Default Vr Projection Mode](#default-vr-projection-mode)
  - [Display In Vr Mode](#display-in-vr-mode)
  - [Double Click For Fullscreen](#double-click-for-fullscreen)
  - [Enable Fullscreen On Rotation](#enable-fullscreen-on-rotation)
  - [Enable Keyboard Playback Controls](#enable-keyboard-playback-controls)
  - [Enable Tooltips](#enable-tooltips)
  - [Fade Delay](#fade-delay)
  - [Fast Forward Rates](#fast-forward-rates)
  - [Force Landscape On Fullscreen](#force-landscape-on-fullscreen)
  - [Full Screen Element](#full-screen-element)
  - [Keyboard Large Seek Distance](#keyboard-large-seek-distance)
  - [Keyboard Seek Distance](#keyboard-seek-distance)
  - [Overflow Menu Buttons](#overflow-menu-buttons)
  - [Playback Rates](#playback-rates)
  - [Prefer Document Picture In Picture](#prefer-document-picture-in-picture)
  - [Refresh Tick In Seconds](#refresh-tick-in-seconds)
  - [Rewind Rates](#rewind-rates)
  - [Seek On Taps](#seek-on-taps)
  - [Setup Media Session](#setup-media-session)
  - [Show Audio Channel Count Variants](#show-audio-channel-count-variants)
  - [Show Unbuffered Start](#show-unbuffered-start)
  - [Single Click For Play And Pause](#single-click-for-play-and-pause)
  - [Statistics List](#statistics-list)
  - [Tap Seek Distance](#tap-seek-distance)
  - [Text Track Label Format](#text-track-label-format)
  - [Track Label Format](#track-label-format)
- [Plugins](#plugins)
  - [Accent Color](#accent-color)
  - [AdBlock Detection](#adblock-detection)
  - [Ad Overlay](#ad-overlay)
  - [Ads](#ads)
  - [Analytics](#analytics)
  - [Chapter](#chapter)
  - [Download](#download)
  - [Error Tracker](#error-tracker)
  - [Logo](#logo)
  - [markers](#markers)
  - [Pixel Tag](#pixel-tag)
  - [Pop Up](#pop-up)
  - [Poster](#poster)
  - [Sentry Monitoring](#sentry-monitoring)
  - [Subtitles](#subtitles)
  - [Thumbnails](#thumbnails)
  - [Volume](#volume)
- [License](#license)

# SlashedCloud Player

SlashedCloud Player is a web-based player. It is built on top of [Shaka Player](https://github.com/shaka-project/shaka-player). Is designed to be a simple and easy-to-use player for streaming video content. Supports adaptive streaming (hls, dash) and progressive download.

[Shaka Player](https://github.com/shaka-project/shaka-player) is under the Apache License, Version 2.0. See the [LICENSE](https://github.com/shaka-project/shaka-player/blob/main/LICENSE) file for details.

# Usage

Simple Tutorial on How to use the Slashedcloud Player

## Basic Installation

1. `npm install @slashedcloud/player`
2. Import the player in your project
   ```ts
   import Player from '@slashedcloud/player';
   ```
3. Create a  const player = new Player(and set your options
   ```ts
   const player =  const player = new Player('player_container', {
     src: 'https://example.com/video.mp4',
   });
   ```
4. Initialize the player
   ```ts
   player.initialize();
   ```
5. Create a container for the player in your HTML
   ```html
   <div id="player_container"></div>
   ```

Example:

```html
<!-- index.html -->

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>SlashedCloud Player</title>
  </head>
  <body>
    <!-- HTML container for the player -->
    <div id="player_container"></div>
    <!-- Import the player script -->
    <script src="path/to/your/script.ts"></script>
  </body>
</html>
```

```ts
// script.ts

import Player from '@slashedcloud/player';
// Create a new player instance
const player = new Player(const player =  const player = new Player('player_container', {
  src: 'https://example.com/video.mp4',
});
// Initialize the player
player.initialize();
```

## Event listeners

The player instance emits events that you can listen to or emit custom events. The player instance has the following methods for event handling:

| Method           | Description                                                                   |
| ---------------- | ----------------------------------------------------------------------------- |
| `on`             | Adds an event listener for the specified event.                               |
| `once`           | Adds an event listener for the specified event that will only be called once. |
| `all`            | Adds an event listener for all events.                                        |
| `removeListener` | Removes an event listener for the specified event.                            |
| `off`            | Removes all event listeners for the specified event.                          |
| `emit`           | Emits an event with the specified data.                                       |

For now the player emits the following events:

| Event Name      | Description                                          |
| --------------- | ---------------------------------------------------- |
| `firstPlay`     | Trigger when the video is played for the first time. |
| `play`          | Trigger when the video is played.                    |
| `playing`       | Trigger when the video is playing.                   |
| `pause`         | Trigger when the video is paused.                    |
| `ended`         | Trigger  When the video has ended.                   |
| `seeking`       | Trigger when the video is seeking.                   |
| `seeked`        | Trigger when the video has seeked.                   |
| `fullScreenIn`  | Trigger when the video is in full screen.            |
| `fullScreenOut` | Trigger when the video is out of full screen.        |
| `volumeChange`  | Trigger when the volume of the video changes.        |
| `unmute`        | Trigger when the video is unmuted.                   |
| `mute`          | Trigger when the video is muted.                     |
| `playAttempt`   | Trigger when the video is played for the first time. |
| `error`         | Trigger when an error occurs.                        |


Exemple:
```ts
// script.ts
import Player from '@slashedcloud/player';
// Create a new player instance
const player = new Player('player_container', {
  src: 'https://example.com/video.mp4',
});
// Initialize the player
player.initialize();
// Listen to the 'play' event
player.on('play', () => {
  console.log('The video is playing');
});
// custom function
const customFunction = (name: string, args: { time: number }) => {
    console.log('Custom event name:', name);
    console.log('Custom event data:', args);
};
// Listen to the custom event and save the remove listener
const remove = player.on('custom_event', customFunction);
// emit a custom event
player.emit('custom_event', { time: 12 });
// Remove the custom event listener
player.removeListener('custom_event', customFunction);
// or remove listener
remove();
// when is a array of remove listeners
remove.forEach((removeListener) => removeListener());
```

## Advanced

### Custom Plugins

The SlashedCloud Player allows you to add custom plugins, where each plugin class must extend the `Plugin` class from the player package. The plugin class should implement a constructor, a name property, and a setup method.

The `constructor` method should call the `super` method with the `player` parameter to allow access to the player instance.

The `name` property is a read-only string that uniquely identifies a plugin, typically set during the creation of the plugin instance, ensuring consistent and descriptive labeling throughout its use.

The `setup` method should be an async method that is called when the player is initialized, where will be the logic of the feature.

To load custom plugins into the player, use the `loadPlugin` method of the player instance. This method accepts two parameters: the plugin class and its configuration options. You can load multiple plugins simultaneously.

Example:
```ts
// script.ts
import Player from '@slashedcloud/player';
import TestPlugin from './TestPlugin';
// Create a new player instance
const player = new Player(const player =  const player = new Player('player_container', {
  src: 'https://example.com/video.mp4',
});
// Add the custom feature
player.loadPlugin(TestPlugin, { test: 'test' });
// Add more that one plugin
// player.loadPlugin(OtherPlugin, { color: '#2D5A4B' });
// Initialize the player
player.initialize();
```

```ts
// TestPlugin.ts
import Player, { BaseFeature } from '@slashedcloud/player';

type TestPluginOptions = {
  test: string;
};

export default class TestPlugin extends Plugin {
  options: TestPluginOptions;
  constructor(player: Player, options: TestPluginOptions) {
    super(player);
    this.options = options;
  }

  async setup() {
    console.log('options test', this.options.test);
    console.log('TestFeature setup');
  }
}
```

# Options

## Autoplay
The player will start playing the video automatically when it is ready.

The autoplay is a boolean. Default: `false`.

Example:
```ts
const options = {
  ...
  autoplay: true,
};
const player = new Player('player_container', options);
```

## Debug
Show debug information on the player. The debug information is shown on the player.

The debug is a boolean. Default: `false`.

Example:
```ts
const options = {
  ...
  debug: true,
};
const player = new Player('player_container', options);
```
## Height
when not set the player will take the height of the video, otherwise it will take the height set by the user.

The height is a number. no Default.
Example:
```ts
const options = {
  ...
  height: 500,
};
const player = new Player('player_container', options);
```
## Language


Example:
```ts
const options = {
  ...
  language: 'fr',
};
const player = new Player('player_container', options);
```
## Muted
The player will start muted.

The muted is a boolean. Default: `false`.

Example:
```ts
const options = {
  ...
  muted: true,
};
const player = new Player('player_container', options);
```
## Persister
Is used to save values in the browser's local storage where can be used next time the player is loaded.

The persister is an object with the following properties:

| Property    | Type   | Description                                                           | Required |
| ----------- | ------ | --------------------------------------------------------------------- | -------- |
| `prefix`    | String | The prefix to use for the keys in the local storage.                  | No       |
| `expiresIn` | Number | The time in milliseconds before the value expires. Default is 1 year. | No       |

Default values:
```ts
{
  prefix: 'player_persister',
  expiresIn:  365 * 30 * 24 * 60 * 60 * 1000,
}
```
Example:
```ts
const options = {
  ...
  persister: {
     prefix: 'player_persister',
     expiresIn: 3600,
  },
};
const player = new Player('player_container', options);
// Get and set values
player.persister.get<number>('volume');
player.persister.set('volume', 0.5);

```
## Plays Inline
Is used to specify whether the video should play inline or in fullscreen mode on iOS devices.

The playsInline is a boolean. Default: `false`.

Example:
```ts
const options = {
  ...
  playsInline: false,
};
const player = new Player('player_container', options);
```

## Src

The video source supports the following types: mpd, hls, ima-dai, and media-tailor.
Additionally, multiple sources can be specified for progressive download.
Source is **REQUIRED** for the player to work.

The source can be as simple as a string with the following properties:

| Property | Type   | Description          | Required |
| -------- | ------ | -------------------- | -------- |
| `src`    | String | The URL of the video | Yes      |

Example:
```ts
const player = new Player('player_container',{
  src: 'https://example.com/video.mp4',
});
```

### IMA SDK Integration

To integrate Server Side ads into a presentation, you need to have a Google Ad Manager account and host your streams on Google Ad Manager's servers. To find out more about the Google Ad Manager service or sign up for an account, visit [https://admanager.google.com/](https://admanager.google.com/)

The source is an object with the following properties:

| Property |                           | Type          | Description                                                            | Required             |
| -------- | ------------------------- | ------------- | ---------------------------------------------------------------------- | -------------------- |
| `src`    |                           | Object        | The source object containing video details                             | Yes                  |
| -        | `type`                    | `ima-dai`     |                                                                        | Yes                  |
| -        | `stream`                  | `vod`, `live` | Type of stream                                                         | Yes                  |
| -        | `contentSourceId`         | String        | Unique identifier for the publisher content, from a CMS                | `steam`: `vod`, Yes  |
| -        | `videoId`                 | String        | Identifier for the video content source                                | `steam`: `vod`, Yes  |
| -        | `assetKey`                | String        | This is used to determine which stream should be played                | `steam`: `live`, Yes |
| -        | `adTagParameters`         | Unknown       |                                                                        | No                   |
| -        | `authToken`               | Unknown       | Authorization token                                                    | No                   |
| -        | `format`                  | `hls`, `dash` | The stream format to request. default `hls`                            | No                   |
| -        | `omidAccessModeRules`     | Unknown       | Settings object for mapping verification vendors to OMID Access Modes  | No                   |
| -        | `streamActivityMonitorId` | Unknown       | The ID to be used to debug the stream with the stream activity monitor | No                   |
| -        | `apiKey`                  | String        | The stream request API key                                             | No                   |


Example:
```ts
const player = new Player('player_container',{
  src: {
    type: 'ima-dai',
    stream: 'vod',
    contentSourceId: 'contentSourceId',
    videoId: 'videoId',
  },
});
```

**For details on the request object:** [VOD Stream](https://developers.google.com/ad-manager/dynamic-ad-insertion/sdk/html5/reference/js/VODStreamRequest),
[Live Stream](https://developers.google.com/ad-manager/dynamic-ad-insertion/sdk/html5/reference/js/LiveStreamRequest)

### AWS Elemental MediaTailor Integration

The source is an object with the following properties:

| Property |               | Type           | Description                                                                                      | Required |
| -------- | ------------- | -------------- | ------------------------------------------------------------------------------------------------ | -------- |
| `src`    |               | Object         | The source object containing video details                                                       | Yes      |
| -        | `type`        | `media-tailor` | The type of the source                                                                           | Yes      |
| -        | `url`         | String         | The URL of the video, typically the master manifest URL for the stream.                          | Yes      |
| -        | `assetId`     | String         | The unique identifier for the asset, used to differentiate content within the same video source. | No       |
| -        | `podDuration` | String         | Specifies the duration (in seconds) for ad pods, which are groups of ads played consecutively.   | No       |


Example:
```ts
const player = new Player('player_container',{
  src: {
    assetId: 'assetId',
    podDuration: 30,
    type: 'video/mp4',
    url: 'https://example.com/index.mpd',
  },
});
```

**For details on the request object:** [Media Tailor](https://docs.aws.amazon.com/mediatailor/latest/ug/setting-up.html)

### HTTP Live Streaming (HLS), MPEG-DASH (MPD)
hls or mpd: The source is an object with the following properties:

| Property |        | Type                                    | Description                                                            | Required |
| -------- | ------ | --------------------------------------- | ---------------------------------------------------------------------- | -------- |
| `src`    |        | Object                                  | The source object containing video details                             | Yes      |
| -        | `type` | `application/x-mpegURL`, `hls`, `m3u8`, | MIME type of the video                                                 | Yes      |
|          |        | `application/dash+xml`, `mpd`, `dash`   |                                                                        |          |
| -        | `url`  | String                                  | The URL of the video, typically the master manifest URL for the stream | Yes      |

Example:
```ts
const player = new Player('player_container',{
  src: {
    type: 'application/x-mpegURL',
    url: 'https://example.com/index.m3u8',
  },
});
```

### Progressive Download

The source is an array of object with the following properties:

| Property |         | Type   | Description                                         | Required |
| -------- | ------- | ------ | --------------------------------------------------- | -------- |
| `src`    |         | Array  | Array of video source objects                       | Yes      |
| -        | `type`  | String | MIME type of the video                              | Yes      |
| -        | `label` | String | Used to sort the list and name the selection button | Yes      |
| -        | `url`   | String | The URL of the video                                | Yes      |

Example:
```ts
const player = new Player('player_container',{
  src: [
    {
      label: '2160p',
      type: 'video/mp4',
      url: 'http://localhost:8000/av1_3840px.mp4',
    },
    {
      label: '1080p',
      type: 'video/mp4',
      url: 'http://localhost:8000/av1_1920px.mp4',
    },
  ],
});
```
## Width
when not set the player will take the width of the video, otherwise it will take the width set by the user.

The width is a number. no Default.
Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    width: 500,
};
const player = new Player('player_container', options)
```

# Extra Options

## Ad Statistics List
The ordered list of ad statistics present in the ad statistics container.

The adStatisticsList is an array of strings with the following properties:

| Property           | Type   | Description                                                   | Required |
| ------------------ | ------ | ------------------------------------------------------------- | -------- |
| `loadTimes`        | String | The set of amounts of time it took to get the final manifest. | No       |
| `averageLoadTime`  | String | The average time taken to load the ad.                        | No       |
| `started`          | String | The number of ads started.                                    | No       |
| `playedCompletely` | String | The number of ads played completely.                          | No       |
| `skipped`          | String | The number of ads skipped.                                    | No       |
| `errors`           | String | The number of ads with errors.                                | No       |

Example:
```ts
import player from '@slashedcloud/player';
type AdStatisticsList = 'loadTimes'|'averageLoadTime'|'started'|'playedCompletely'|'skipped'| 'errors';
const options = {
    ...
    adStatisticsList: ['started'],
};
const player = new Player('player_container', options)
```

## Add BigPlay Button
Whether or not a big play button in the center of the video should be part of the UI.

The addBigPlayButton is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    addBigPlayButton: true,
};
const player = new Player('player_container', options)
```

## Add Seek Bar
Whether or not a seek bar should be part of the UI.

The addSeekBar is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    addSeekBar: true,
};
const player = new Player('player_container', options)
```

## Cast Android Receiver Compatible
Indicates if the app is compatible with an Android Cast Receiver.

The castAndroidReceiverCompatible is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    castAndroidReceiverCompatible: true,
};
const player = new Player('player_container', options)
```

## Cast Receiver App Id
Receiver app id to use for the Chromecast support.

The castReceiverAppId is a string. no Default

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    castReceiverAppId: '07AEE832',
};
const player = new Player('player_container', options)
```

## Clear Buffer On Quality Change
Only applicable if the resolution selection is part of the UI. Whether buffer should be cleared when changing resolution via UI. Clearing buffer would result in immidiate change of quality, but playback may flicker/stall for a sec as the content in new resolution is being buffered. Not clearing the buffer will mean we play the content in the previously selected resolution that we already have buffered before switching to the new resolution.

The clearBufferOnQualityChange is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    clearBufferOnQualityChange: true,
};
const player = new Player('player_container', options)
```

## Context Menu Elements
The ordered list of buttons in the context menu.

The contextMenuElements is an array of strings with the following properties:

| Property             | Type   | Description                                                                                                                                                                                             | Required |
| -------------------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------- |
| `statistics`         | String | adds a button that displays statistics of the video.                                                                                                                                                    | No       |
| `loop`               | String | adds a button that displays statistics of the video.                                                                                                                                                    | No       |
| `picture_in_picture` | String | adds a button that enables/disables picture-in-picture mode on browsers that support it. Button is invisible on other browsers. Note that it will use the Document Picture-in-Picture API if supported. | No       |
| `ad_statistics`      | String | adds a button that displays ad statistics of the video. menu.                                                                                                                                           | No       |
| `save_video_frame`   | String | adds a button to save the current video frame.menu.                                                                                                                                                     | No       |

Example:
```ts
import player from '@slashedcloud/player';
type ContextMenuElement = 'statistics'|'loop'|'picture_in_picture'|'ad_statistics'|'save_video_frame';
const options = {
    ...
    contextMenuElements: ['statistics'],
};
const player = new Player('player_container', options)
contextMenuElements?: string[];
```

## Control Panel Elements
The ordered list of control panel elements of the UI.

The controlPanelElements is an array of strings with the following properties:

| Property              | Type   | Description                                                                                                                                                                                                                                                                                   | Required |
| --------------------- | ------ | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------- |
| `time_and_duration`   | String | adds an element tracking and displaying current progress of the presentation and the full presentation duration in the "0:10 / 1:00" form where "0:10" (ten seconds) is the number of seconds passed from the start of the presentation and "1:00" (one minute) is the presentation duration. | No       |
| `play_pause`          | String | adds a button that plays/pauses the video on click.                                                                                                                                                                                                                                           | No       |
| `mute`                | String | adds a button that mutes/unmutes the video on click.                                                                                                                                                                                                                                          | No       |
| `volume`              | String | adds a volume slider.                                                                                                                                                                                                                                                                         | No       |
| `fullscreen`          | String | adds a button that toggles full screen mode on click.                                                                                                                                                                                                                                         | No       |
| `overflow_menu`       | String | adds a button that opens an overflow menu with additional settings buttons. It's content is also configurable.                                                                                                                                                                                | No       |
| `rewind`              | String | adds a button that rewinds the presentation on click; that is, it starts playing the presentation backwards.                                                                                                                                                                                  | No       |
| `fast_forward`        | String | adds a button that fast forwards the presentation on click; that is, it starts playing the presentation at an increased speed                                                                                                                                                                 | No       |
| `spacer`              | String | adds a chunk of empty space between the adjacent elements.                                                                                                                                                                                                                                    | No       |
| `picture_in_picture`  | String | adds a button that enables/disables picture-in-picture mode on browsers that support it. Button is invisible on other browsers. Note that it will use the Document Picture-in-Picture API if supported.                                                                                       | No       |
| `loop`                | String | adds a button that controls if the currently selected video is played in a loop.                                                                                                                                                                                                              | No       |
| `airplay`             | String | adds a button that opens a AirPlay dialog. The button is visible only if the browser supports AirPlay.                                                                                                                                                                                        | No       |
| `cast`                | String | adds a button that opens a Chromecast dialog. The button is visible only if there is at least one Chromecast device on the same network available for casting.                                                                                                                                | No       |
| `remote`              | String | adds a button that opens a Remote Playback dialog. The button is visible only if the browser supports Remote Playback API.                                                                                                                                                                    | No       |
| `quality`             | String | adds a button that controls enabling/disabling of abr and video resolution selection.                                                                                                                                                                                                         | No       |
| `language`            | String | adds a button that controls audio language selection.                                                                                                                                                                                                                                         | No       |
| `playback_rate`       | String | adds a button that controls the playback rate selection.                                                                                                                                                                                                                                      | No       |
| `captions`            | String | adds a button that controls the current text track selection (including turning it off).                                                                                                                                                                                                      | No       |
| `recenter_vr`         | String | adds a button that recenter the VR view to the initial view. The button is visible only if playing a VR content.                                                                                                                                                                              | No       |
| `toggle_stereoscopic` | String | adds a button that toggle between monoscopic and stereoscopic. The button is visible only if playing a VR content.                                                                                                                                                                            | No       |
| `chapter`             | String | adds a button that controls the chapter selection.                                                                                                                                                                                                                                            | No       |

Example:
```ts
import player from '@slashedcloud/player';
type ControlPanelElements = 'time_and_duration'|'play_pause'|'mute'|'volume'|'fullscreen'|'overflow_menu'|'rewind'|'fast_forward'|'spacer'|'picture_in_picture'|'loop'|'airplay'|'cast'|'remote'|'quality'|'language'|'playback_rate'|'captions'|'recenter_vr'|'toggle_stereoscopic'|'chapter';
const options = {
    ...
    controlPanelElements:  [
    'play_pause',
    'mute',
    'volume',
    'time_and_duration',
    'spacer',
    'playback_rate',
    // 'language',
    // 'captions',
    'recenter_vr',
    'toggle_stereoscopic',
    'quality',
    'fullscreen',
  ],
};
const player = new Player('player_container', options)
```

## Custom Context Menu
Whether or not a custom context menu replaces the default.

The customContextMenu is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    customContextMenu: false,
};
const player = new Player('player_container', options)
```

## Default Vr Projection Mode
Indicate the default VR projection mode. Possible values: <code>'equirectangular'</code> or <code>'cubemap'</code>.

The defaultVrProjectionMode is a string. Default: `equirectangular`.

Example:
```ts
import player from '@slashedcloud/player';
type VrProjectionMode = 'equirectangular' | 'cubemap';
const options = {
    ...
    defaultVrProjectionMode: 'equirectangular',
};
const player = new Player('player_container', options)
```

## Display In Vr Mode
If true, the content will be treated as VR. If false, it will only be treated as VR if we automatically detect it as such. (See the Enabling VR section in docs/tutorials/ui.md).

The displayInVrMode is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    displayInVrMode: false,
};
const player = new Player('player_container', options)
```

## Double Click For Fullscreen
Whether or not double-clicking on the UI should cause it to enter fullscreen.

The doubleClickForFullscreen is a boolean. Default: `true`.
Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    doubleClickForFullscreen: true,
};
const player = new Player('player_container', options)
```

## Enable Fullscreen On Rotation
Whether or not to enter/exit fullscreen mode when the screen is rotated.

The enableFullscreenOnRotation is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    enableFullscreenOnRotation: true,
};
const player = new Player('player_container', options)
```

## Enable Keyboard Playback Controls
Whether or not playback controls via keyboard is enabled, such as seek forward, seek backward, jump to the beginning/end of the video.

The enableKeyboardPlaybackControls is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    enableKeyboardPlaybackControls: true,
};
const player = new Player('player_container', options)
```

## Enable Tooltips
Whether or not buttons in the control panel display tooltips that contain information about their function.

The enableTooltips is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    enableTooltips: true,
};
const player = new Player('player_container', options)
```

## Fade Delay
The delay (in seconds) before fading out the controls once the user stops interacting with them We recommend setting this to 3 on your cast receiver UI.

The fadeDelay is a number. Default: `0`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    fadeDelay: 3,
};
const player = new Player('player_container', options)
```

## Fast Forward Rates
The ordered list of rates for fast forward selection.

The fastForwardRates is an array of numbers.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    fastForwardRates: [2, 4, 8, 16, 32],
};
const player = new Player('player_container', options)
```

## Force Landscape On Fullscreen
Whether or not the device should rotate to landscape mode when the video enters fullscreen Note that this behavior is based on an experimental browser API, and may not work on all platforms.

The forceLandscapeOnFullscreen is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    forceLandscapeOnFullscreen: true,
};
const player = new Player('player_container', options)
```

## Full Screen Element
DOM element on which fullscreen will be done.

The fullScreenElement is a HTMLElement. Default: Shaka Player Container.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    fullScreenElement: document.getElementById('fullScreenElement'),
};
const player = new Player('player_container', options)
```

## Keyboard Large Seek Distance
The time interval, in seconds, to seek when the user presses the page up or page down keyboard keys when the video is selected. If less than or equal to 0, no seeking will occur.

The keyboardLargeSeekDistance is a number. Default: `60`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    keyboardLargeSeekDistance: 60,
};
const player = new Player('player_container', options)
```

## Keyboard Seek Distance
The time interval, in seconds, to seek when the user presses the left or right keyboard keys when the video is selected. If less than or equal to 0, no seeking will occur.

The keyboardSeekDistance is a number. Default: `5`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    keyboardSeekDistance: 5,
};
const player = new Player('player_container', options)
```

## Overflow Menu Buttons
The ordered list of the overflow menu buttons.

The overflowMenuButtons is an array of strings with the following properties:

| Property              | Type   | Description                                                                                                                                                                                             | Required |
| --------------------- | ------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------- |
| `captions`            | String | adds a button that controls the current text track selection (including turning it off). The button is visible only if the content has at least one text track.                                         | No       |
| `cast`                | String | adds a button that opens a Chromecast dialog. The button is visible only if there is at least one Chromecast device on the same network available for casting.                                          | No       |
| `quality`             | String | adds a button that controls enabling/disabling of abr and video resolution selection.                                                                                                                   | No       |
| `language`            | String | adds a button that controls audio language selection.                                                                                                                                                   | No       |
| `picture_in_picture`  | String | adds a button that enables/disables picture-in-picture mode on browsers that support it. Button is invisible on other browsers. Note that it will use the Document Picture-in-Picture API if supported. | No       |
| `loop`                | String | adds a button that controls if the currently selected video is played in a loop.                                                                                                                        | No       |
| `playback_rate`       | String | adds a button that controls the playback rate selection.                                                                                                                                                | No       |
| `airplay`             | String | adds a button that opens a AirPlay dialog. The button is visible only if the browser supports AirPlay.                                                                                                  | No       |
| `remote`              | String | adds a button that opens a Remote Playback dialog. The button is visible only if the browser supports Remote Playback API.                                                                              | No       |
| `statistics`          | String | adds a button that displays statistics of the video.                                                                                                                                                    | No       |
| `recenter_vr`         | String | adds a button that recenter the VR view to the initial view. The button is visible only if playing a VR content.                                                                                        | No       |
| `toggle_stereoscopic` | String | adds a button that toggle between monoscopic and stereoscopic. The button is visible only if playing a VR content.                                                                                      | No       |
| `ad_statistics`       | String | adds a button that displays ad statistics of the video.                                                                                                                                                 | No       |
| `save_video_frame`    | String | adds a button to save the current video frame.                                                                                                                                                          | No       |
| `chapter`             | String | adds a button that controls the chapter selection.                                                                                                                                                      | No       |

Example:
```ts
import player from '@slashedcloud/player';

type OverflowMenuButtons = 'captions'|'cast'|'quality'|'language'|'picture_in_picture'|'loop'|'playback_rate'|'airplay'|'remote'|'statistics'|'recenter_vr'|'toggle_stereoscopic'|'ad_statistics'|'save_video_frame'|'chapter';

const options = {
    ...
    overflowMenuButtons: ['picture_in_picture'],
};
const player = new Player('player_container', options)
```

## Playback Rates
The ordered list of rates for playback selection.

The playbackRates is an array of numbers.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    playbackRates: [0.5, 0.75, 1, 1.25, 1.5, 1.75, 2],
};
const player = new Player('player_container', options)
```

## Prefer Document Picture In Picture
Indicates whether the Document Picture in Picture API is preferred or the Video Element Picture in Picture API is preferred. Changing this property in mid-playback may produce undesired behavior if you are already in PiP.

The preferDocumentPictureInPicture is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    preferDocumentPictureInPicture: true,
};
const player = new Player('player_container', options)
```

## Refresh Tick In Seconds
The time interval, in seconds, to update the seek bar.

The refreshTickInSeconds is a number. Default: `0.125`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    refreshTickInSeconds:  0.125,
};
const player = new Player('player_container', options)
```

## Rewind Rates
The ordered list of rates for rewind selection.

The rewindRates is an array of numbers.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    rewindRates: [-1, -2, -4, -8],
};
const player = new Player('player_container', options)

```

## Seek On Taps
Indicates whether or not a fast-forward and rewind tap button that seeks video some seconds.

The seekOnTaps is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    seekOnTaps: true,
};
const player = new Player('player_container', options)
```

## Setup Media Session
If true, MediaSession controls will be managed by the UI. It will also use the ID3 APIC and TIT2 as image and title in Media Session, and ID3 APIC will also be used to change video poster.

The setupMediaSession is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    setupMediaSession: true,
};
const player = new Player('player_container', options)
```

## Show Audio Channel Count Variants
Indicates whether the combination of language and channel count should be displayed or if, on the contrary, only the language should be displayed regardless of the channel count.

The showAudioChannelCountVariants is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    showAudioChannelCountVariants: true,
};
const player = new Player('player_container', options)
```

## Show Unbuffered Start
If true, color any unbuffered region at the start of the seek bar as unbuffered (using the "base" color) If false; color any unbuffered region at the start of the seek bar as played (using the "played" color). <br> A value of false matches the default behavior of Chrome's native controls and Shaka Player v3.0+. <br> A value of true matches the default behavior of Shaka Player v2.5.

The showUnbufferedStart is a boolean. Default: `false`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    showUnbufferedStart: true,
};
const player = new Player('player_container', options)
```

## Single Click For Play And Pause
Whether or not clicking on the video should cause it to play or pause. It does not work in VR mode.

The singleClickForPlayAndPause is a boolean. Default: `true`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    singleClickForPlayAndPause: true,
};
const player = new Player('player_container', options)
```

## Statistics List
The ordered list of statistics present in the statistics container.

The statisticsList is an array of strings with the following properties:

| Property              | Description                                                                                                                                                                                                                                             |
| --------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `width`               | The width of the current video track. If nothing is loaded or the content is audio-only                                                                                                                                                                 |
| `height`              | The height of the current video track. If nothing is loaded or the content is audio-only.                                                                                                                                                               |
| `streamBandwidth`     | The bandwidth required for the current streams (total, in bit/sec). It takes into account the playbackrate. If nothing is loaded.                                                                                                                       |
| `decodedFrames`       | The total number of frames decoded by the Player. If not reported by the browser.                                                                                                                                                                       |
| `droppedFrames`       | The total number of frames dropped by the Player. If not reported by the browser.                                                                                                                                                                       |
| `corruptedFrames`     | The total number of corrupted frames dropped by the browser. If not reported by the browser.                                                                                                                                                            |
| `estimatedBandwidth`  | The current estimated network bandwidth (in bit/sec). If no estimate available.                                                                                                                                                                         |
| `gapsJumped`          | The total number of playback gaps jumped by the GapJumpingController. If nothing is loaded.                                                                                                                                                             |
| `stallsDetected`      | The total number of playback stalls detected by the StallDetector. If nothing is loaded.                                                                                                                                                                |
| `completionPercent`   | This is the greatest completion percent that the user has experienced in playback. Also known as the "high water mark". If nothing is loaded, or the stream is live (and therefore indefinite).                                                         |
| `loadLatency`         | This is the number of seconds it took for the video element to have enough data to begin playback. This is measured from the time load() is called to the time the <code>'loadeddata'</code> event is fired by the media element. If nothing is loaded. |
| `manifestTimeSeconds` | The amount of time it took to download and parse the manifest. If nothing is loaded.                                                                                                                                                                    |
| `drmTimeSeconds`      | The amount of time it took to download the first drm key, and load that key into the drm system. If nothing is loaded or DRM is not in use.                                                                                                             |
| `playTime`            | The total time spent in a playing state in seconds. If nothing is loaded.                                                                                                                                                                               |
| `pauseTime`           | The total time spent in a paused state in seconds. If nothing is loaded.                                                                                                                                                                                |
| `bufferingTime`       | The total time spent in a buffering state in seconds. If nothing is loaded.                                                                                                                                                                             |
| `licenseTime`         | The time spent on license requests during this session in seconds. If DRM is not in use.                                                                                                                                                                |
| `liveLatency`         | The time between the capturing of a frame and the end user having it displayed on their screen. If nothing is loaded or the content is VOD.                                                                                                             |
| `maxSegmentDuration`  | The presentation's max segment duration in seconds. If nothing is loaded.                                                                                                                                                                               |
| `manifestSizeBytes`   | Size of the manifest payload. For DASH &amp; MSS it will match the latest downloaded manifest. For HLS, it will match the lastly downloaded playlist. If nothing is loaded or in src= mode.                                                             |
| `bytesDownloaded`     | The bytes downloaded during the playback. If nothing is loaded.                                                                                                                                                                                         |
| `nonFatalErrorCount`  | The amount of non fatal errors that occurred If nothing is loaded.                                                                                                                                                                                      |
| `manifestPeriodCount` | The amount of periods occurred in the manifest. For DASH it represents number of Period elements in a manifest. For HLS &amp; MSS it is always 1. In src= mode or if nothing is loaded.                                                                 |
| `manifestGapCount`    | The amount of gaps found in a manifest. For DASH, it represents number of discontinuities found between periods. For HLS, it is a number of EXT-X-GAP and GAP=YES occurrences. For MSS, it is always set to 0. If in src= mode or nothing is loaded.    |
| `switchHistory`       | A history of the stream changes.                                                                                                                                                                                                                        |
| `stateHistory`        | A history of the state changes.                                                                                                                                                                                                                         |

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    statisticsList: ['width', 'height', 'playTime', 'bufferingTime'],
};
const player = new Player('player_container', options)
```

## Tap Seek Distance
The time interval, in seconds, to seek when the user presses the left or right part of the video. If less than or equal to 0, no seeking will occur.

The tapSeekDistance is a number. Default: `10`.

Example:
```ts
import player from '@slashedcloud/player';
const options = {
    ...
    tapSeekDistance: 10,
};
const player = new Player('player_container', options)
```

## Text Track Label Format
An enum that determines what is shown in the labels for text track selection. LANGUAGE means that only the language of the item is shown. ROLE means that only the role of the item is shown. LANGUAGE_ROLE means both language and role are shown, or just language if there is no role. LABEL means the non-standard DASH "label" attribute or the standard DASH "Label" element or the HLS "NAME" attribute are shown. Defaults to LANGUAGE.

The textTrackLabelFormat is an enum with the following properties:

| Property        | Type   | Required |
| --------------- | ------ | -------- |
| `LANGUAGE`      | String | No       |
| `ROLE`          | String | No       |
| `LANGUAGE_ROLE` | String | No       |
| `LABEL`         | String | No       |


Example:
```ts
import player from '@slashedcloud/player';

type TrackLabelFormat = 'LANGUAGE' | 'ROLE' | 'LANGUAGE_ROLE' | 'LABEL';

const options = {
    ...
    textTrackLabelFormat: 'LANGUAGE_ROLE',
};
const player = new Player('player_container', options)
```

## Track Label Format
An enum that determines what is shown in the labels for audio variant selection. LANGUAGE means that only the language of the item is shown. ROLE means that only the role of the item is shown. LANGUAGE_ROLE means both language and role are shown, or just language if there is no role. LABEL means the non-standard DASH "label" attribute or the standard DASH "Label" element or the HLS "NAME" attribute are shown. Defaults to LANGUAGE.

The trackLabelFormat is an enum with the following properties:

| Property        | Type   | Required |
| --------------- | ------ | -------- |
| `LANGUAGE`      | String | No       |
| `ROLE`          | String | No       |
| `LANGUAGE_ROLE` | String | No       |
| `LABEL`         | String | No       |

Example:
```ts
import player from '@slashedcloud/player';

type TrackLabelFormat = 'LANGUAGE' | 'ROLE' | 'LANGUAGE_ROLE' | 'LABEL';

const options = {
  ...
  trackLabelFormat: 'LANGUAGE_ROLE',
};
const player = new Player('player_container', options)
...
```

# Plugins

## Accent Color

Change the accent color of the player. The accent color is used for the progress bar, the volume bar, and the download button.

The accentColor is an object with the following properties:

| Property     | Type   | Description                                                                                                                                   | Default     | Required |
| ------------ | ------ | --------------------------------------------------------------------------------------------------------------------------------------------- | ----------- | -------- |
| `base`       | String | Color applied to the base of the seek bar and base of the volume bar                                                                          | `#ffffff4d` | no       |
| `buffered`   | String | Color applied to the portion of the seek bar showing what has been buffered ahead of the playback position.                                   | `#ffffff8a` | no       |
| `played`     | String | Color applied to the portion of the seek bar showing what has been played already and the portion of the volume bar showing the volume level. | `#ffffff`   | no       |
| `adBreaks`   | String | Color applied to the portion of the seek bar showing when the ad breaks are scheduled to occur on the timeline.                               | `#ffcc00`   | no       |
| `background` | String | Color applied to rhe background of the player                                                                                                 | `#000000`   | no       |

**Note:** Only hexadecimal colors are supported.

Example:
```ts
// Import Player
import Player from '@slashedcloud/player';
// Import AccentColor Plugin
import AccentColorPlugin, { AccentColorPluginOption } from '@slashedcloud/player/Plugins/AccentColor';
// Create a new player instance
const player = new Player(const player =  const player = new Player('player_container', {
  src: 'https://example.com/video.mp4',
});

const options: AccentColorPluginOption = {
  base: '#00387b',
  buffered: '#ff0000',
  played: '#00ff00',
  adBreaks: '#ff00ff',
  marker: '#80ff00',
  background: '#000000',
};
// Add the Plugin to the player
player.loadPlugin(AccentColorPlugin, options);
// Initialize the player
player.initialize();
```

## AdBlock Detection

Detect if the user has an ad blocker enabled. If an ad blocker is detected, a message will be shown to the user, and the video will not play.

Example:
```ts
// Import AdBlockDetector Plugin
import AdBlockDetectorPlugin from '@slashedcloud/player/Plugins/';
...
const player =  const player = new Player('player_container',{
  src: 'https://example.com/video.mp4',
});
// Add the Plugin to the player
player.loadPlugin(AdBlockDetectorPlugin);
...
```

**Note:** You can customize the displayed message by setting the `DISABLE_ADBLOCKER` key in the `Language` object.

## Ad Overlay

Show an ad overlay on the player. The ad overlay is a div that is shown on top of the player. The ad overlay can be used to show ads or other content.

The adOverlay is an object with the following properties:

| Property | Type                  | Description                                | Required            |
| -------- | --------------------- | ------------------------------------------ | ------------------- |
| `src`    | Object                | URL of the ad overlay                      | Yes                 |
| `kind`   | `'image'`, `'iframe'` | kind of the ad overlay                     | Yes                 |
| `link`   | String                | URL to open when the ad overlay is clicked | `kind`: `image`, No |
| `width`  | String                | width of the ad overlay                    | No                  |
| `height` | String                | height of the ad overlay                   | Yes                 |

Example:
```ts
// Import AdOverlay Plugin
import AdOverlayPlugin, { AdOverlayPluginOption } from '@slashedcloud/player/Plugins/AdOverlay';
...
const options: AdOverlayPluginOption = {
  src: 'https://example.com/ad.jpg',
  kind: 'image',
  link: 'https://example.com',
  width: 300,
  height: 250,
};
// Add the Plugin to the player
player.loadPlugin(AdOverlayPlugin, options);
...
```

## Ads

This is client-side ads with IMA SDK. The ads are shown on the player.

The ads is an object with the following properties:

| Property   | Type   | Description    | Required |
| ---------- | ------ | -------------- | -------- |
| `adTagUrl` | String | URL of the ad. | Yes      |

Example:
```ts
// Import Ads Plugin
import AdsPlugin, { AdsPluginOption } from '@slashedcloud/player/Plugins/AdsClient';
...
const options: AdsPluginOption = {
  adTagUrl: 'https://example.com/ad.xml',
};
// Add the Plugin to the player
player.loadPlugin(AdsPlugin, options);
...
```

## Analytics

This is client-side analytics. The analytics are sent to the server.

The analytics is an array of object with the following properties:

| Property   | Type       | Description                                                                                                                                               | Required |
| ---------- | ---------- | --------------------------------------------------------------------------------------------------------------------------------------------------------- | -------- |
| `provider` | `'google'` | The provider of the analytics. For now is only `'google'`.                                                                                                | Yes      |
| `params`   | Object     | The parameters that should be sent to.                                                                                                                    | No       |
| `events`   | Array      | The events to track.                                                                                                                                      | Yes      |
|            |            | For video: `firstPlay`, `play`, `playing`, `pause`, `ended`, `seeking`, `seeked`, `volumeChange`, `unmute`, `mute`, `acknowledge`, `playAttempt`, `error` |
|            |            | For ads: `adStart`, `adComplete`, `adAllCompleted`, `adClick`, `adError`                                                                                  |          |
|            |            | For AdBlock: `adBlockDetected`                                                                                                                            |          |

Example:
```ts
// Import Analytics Plugin
import AnalyticsPlugin, { AnalyticsPluginOption } from '@slashedcloud/player/Plugins/Analytics';
...
const options: AnalyticsPluginOption[] = [
  {
    provider: 'google',
    params: {
      videoId: '2394',
    },
    events: ['play', 'pause', 'ended'],
  },
];
// Add the Plugin to the player
player.loadPlugin(AnalyticsPlugin, options);
...
```

## Chapter

Show chapters on the player. The chapters are shown on the progress bar.

The chapters is an object in `tracks` option with the following properties:

| Property   |             | Type                                                                                                                              | Description                          | Required                     |
| ---------- | ----------- | --------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------ | ---------------------------- |
| `lang`     |             | `ar`, `de`, `en`, `en-GB`, `es`, `es-419`, `fr`, `it`, `ja`, `ko`, `nl`, `pl`, `pt-BR`, `ru`, `th`, `tr`, `zh`, `zh-TW` or String | Language of the track                | Yes                          |
| `src`      |             | String                                                                                                                            | URL of the track's VTT file          | When `chapters` not provided |
| `chapters` |             | Array                                                                                                                             |                                      | When `src` not provided      |
| -          | `startTime` | String                                                                                                                            | Start time in seconds of the chapter | Yes                          |
| -          | `endTime`   | String                                                                                                                            | End time in seconds of the chapter   | No                           |
| -          | `title`     | String                                                                                                                            | Title of the chapter                 | Yes                          |

**Note:** When `endTime` is not provided, the chapter will be shown until the next chapter.

Example:
```ts
// Import Chapters Plugin
import ChaptersPlugin, { ChapterPluginOptions } from '@slashedcloud/player/Plugins/Chapters';
...
const options: ChapterPluginOptions = {
  tracks: [
    {
      kind: 'chapters',
      lang: 'en',
      src: 'https://example.com/chapters.vtt',
    },
    {
      kind: 'chapters',
      lang: 'pt',
      chapters: [
        {
          startTime: 0,
          title: 'Chapter 1 - Where it all begins',
        },
        {
          startTime: 200,
          endTime: 600,
          title: 'Chapter 2 - Something happens',
        },
        {
          startTime: 600,
          title: 'Chapter 3 - Happy ever after',
        },
      ],
    },
  ],
};
// Add the Plugin to the player
player.loadPlugin(ChaptersPlugin, options);
...
```

## Download

Show a download button on the player. The download button allows the user to download the video.

The download is an array of object with the following properties:

| Property | Type   | Description                                         | Required |
| -------- | ------ | --------------------------------------------------- | -------- |
| `url`    | String | URL of the video to download                        | Yes      |
| `label`  | String | Used to sort the list and name the selection button | Yes      |
| `size`   | Number | Size of the video in MB                             | Yes      |

Example:
```ts
// Import Download Plugin
import DownloadPlugin, { DownloadPluginOption } from '@slashedcloud/player/Plugins/Download';
...
const options: DownloadPluginOption[] = [
  {
    url: 'https://example.com/video_1080p.mp4',
    label: '1080p',
    size: 200,
  },
  {
    url: 'https://example.com/video_720p.mp4',
    label: '720p',
    size: 150,
  },
];
// Add the Plugin to the player
player.loadPlugin(DownloadPlugin, options);
...
```

## Error Tracker

Example:
```ts
// Import ErrorTracker Plugin
import ErrorTrackerPlugin, { ErrorTrackerPluginOptions } from '@slashedcloud/player/Plugins/ErrorTracker';
...
const options: ErrorTrackerPluginOptions = {
  params: {
    videoId: '2394',
  },
  event: 'player_error',
  rate: 0.1,
  headers: {
    'Content-Type': 'application/x-www-form-urlencoded',
  },
  url: 'https://example.com/error',
};
// Add the Plugin to the player
player.loadPlugin(ErrorTrackerPlugin, options);
...
```

## Logo

Show a logo on the player. The logo is shown on the top left corner of the player.

The logo is an object with the following properties:

| Property | Type   | Description                  | Required |
| -------- | ------ | ---------------------------- | -------- |
| `src`    | String | URL of the logo              | Yes      |
| `link`   | String | to open when logo is clicked | No       |

Example:
```ts
// Import Logo Plugin
import LogoPlugin, { LogoPluginOption } from '@slashedcloud/player/Plugins/Logo';

const options: LogoPluginOption = {
  src: 'https://example.com/logo.png',
  link: 'https://example.com',
};
// Add the Plugin to the player
player.loadPlugin(LogoPlugin, options);
...
```

## markers

Show markers on the player. The markers are shown on the player.

The markers is an object in `tracks` option with the following properties:

| Property  |         | Type        | Description                   | Required |
| --------- | ------- | ----------- | ----------------------------- | -------- |
| `kind`    |         | `'markers'` |                               | Yes      |
| `color`   |         | String      | Color of the markers          | No       |
| `src`     |         | String      | URL of the track's VTT file   | Yes      |
| `markers` |         | Array       |                               | No       |
| -         | `time`  | String      | Time in seconds of the marker | Yes      |
| -         | `title` | String      | Title of the marker           | Yes      |
| -         | `thumb` | String      | URL of the thumbnail          | No       |

Example:
```ts
// Import Marker Plugin
import MarkerPlugin, { MarkerPluginOption } from '@slashedcloud/player/Plugins/Markers';
...
const options: MarkerPluginOption = {
      kind: 'markers',
      color: '#ff0000',
      src: 'https://example.com/markers.vtt',
};
// Or
// const options: MarkerPluginOption = {
//   kind: 'markers',
//   color: '#ff0000',
//   markers: [
//     {
//       time: 0,
//       title: 'Marker 1',
//       thumb: 'https://example.com/thumb1.jpg',
//     },
//     {
//       time: 200,
//       title: 'Marker 2',
//       thumb: 'https://example.com/thumb2.jpg',
//     },
//     {
//       time: 400,
//       title: 'Marker 3',
//       thumb: 'https://example.com/thumb3.jpg',
//     },
//   ],
// };
// Add the Plugin to the player
player.loadPlugin(MarkerPlugin, options);
...
```
## Pixel Tag

Show a pixel tag on the player. The pixel tag is a tracking pixel that is shown on the player.

The pixelTag is an object with the following properties:

| Property          | Type   | Description          | Required |
| ----------------- | ------ | -------------------- | -------- |
| `firstPlay`       | String | URL of the pixel tag | No       |
| `play`            | String | URL of the pixel tag | No       |
| `playing`         | String | URL of the pixel tag | No       |
| `pause`           | String | URL of the pixel tag | No       |
| `ended`           | String | URL of the pixel tag | No       |
| `seeking`         | String | URL of the pixel tag | No       |
| `seeked`          | String | URL of the pixel tag | No       |
| `volumeChange`    | String | URL of the pixel tag | No       |
| `unmute`          | String | URL of the pixel tag | No       |
| `mute`            | String | URL of the pixel tag | No       |
| `acknowledge`     | String | URL of the pixel tag | No       |
| `playAttempt`     | String | URL of the pixel tag | No       |
| `error`           | String | URL of the pixel tag | No       |
| `adStart`         | String | URL of the pixel tag | No       |
| `adComplete`      | String | URL of the pixel tag | No       |
| `adAllCompleted`  | String | URL of the pixel tag | No       |
| `adClick`         | String | URL of the pixel tag | No       |
| `adSkip`          | String | URL of the pixel tag | No       |
| `adError`         | String | URL of the pixel tag | No       |
| `adBlockDetected` | String | URL of the pixel tag | No       |

Example:
```ts
// Import PixelTag Plugin
import PixelTagPlugin, { PixelTagPluginOption } from '@slashedcloud/player/Plugins/PixelTag';
...
const options: PixelTagPluginOption = {
    firstPlay: 'https://dev.com/firstPlay',
    play: 'https://dev.com/play',
    playing: 'https://dev.com/playing',
    pause: 'https://dev.com/pause',
    ended: 'https://dev.com/ended',
};
// Add the Plugin to the player
player.loadPlugin(PixelTagPlugin, options);
...
```
## Pop Up

Show a popup button on the player. The popup button allows the user to pop out the player into a new window.

The popup is an object with the following properties:

| Property   | Type   | Description                                   | Required             |
| ---------- | ------ | --------------------------------------------- | -------------------- |
| `url`      | String | URL of the popup                              | Yes                  |
| `clicks`   | Number | Number of clicks to open the popup window     | No                   |
| `open`     | String | How to open the popup window: `tab`, `window` | No                   |
| `height`   | String | Height of the popup window: `800px`           | `open`: `window`, No |
| `width`    | String | Width of the popup window: `600px`            | `open`: `window`, No |
| `features` | String | Features of the popup window: `fullscreen`    | `open`: `window`, No |

Example:
```ts
// Import PopUp Plugin
import PopUpPlugin, { PopUpPluginOption } from '@slashedcloud/player/Plugins/PopUp';
...
const options: PopUpPluginOption = {
  url: 'https://example.com',
  clicks: 2,
  open: 'window',
  features: 'fullscreen',
};
// Add the Plugin to the player
player.loadPlugin(PopUpPlugin, options);
...
```
## Poster

Show a poster on the player. Specifies an image to be shown while the video is downloading, or until the user hits the play button.
If this is not included, the first frame of the video will be used instead

The poster is an URL of the image file.

Example:
```ts
// Import Poster Plugin
import PosterPlugin from '@slashedcloud/player/Plugins/Poster';

const options: PosterPluginOption = {
  poster: 'https://example.com/poster.jpg',
};
// Add the Plugin to the player
player.loadPlugin(PosterPlugin, options);
```
## Sentry Monitoring

Example:
```ts
// Import SentryMonitoring Plugin
import SentryMonitoringPlugin, { SentryMonitoringPluginOptions } from '@slashedcloud/player/Plugins/SentryMonitoring';
...
const options: SentryMonitoringPluginOptions = {
  debug: true,
  dsn: 'https://example.com/sentry',
  environment: 'production',
  release: '1.0.0',
  sampleRate: 0.5,
};
// Add the Plugin to the player
player.loadPlugin(SentryMonitoringPlugin, options);
```
## Subtitles

Show subtitles on the player. The subtitles are shown on the player.

The subtitles is an object in `tracks` option with the following properties:

| Property    |             | Type                                                                                                                              | Description                           | Required                      |
| ----------- | ----------- | --------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------- | ----------------------------- |
| `lang`      |             | `ar`, `de`, `en`, `en-GB`, `es`, `es-419`, `fr`, `it`, `ja`, `ko`, `nl`, `pl`, `pt-BR`, `ru`, `th`, `tr`, `zh`, `zh-TW` or String | Language of the track                 | Yes                           |
| `src`       |             | String                                                                                                                            | URL of the track's VTT file           | When `subtitles` not provided |
| `subtitles` |             | Array                                                                                                                             |                                       | When `src` not provided       |
| -           | `startTime` | String                                                                                                                            | Start time in seconds of the subtitle | Yes                           |
| -           | `endTime`   | String                                                                                                                            | End time in seconds of the subtitle   | Yes                           |
| -           | `title`     | String                                                                                                                            | Title of the subtitle                 | Yes                           |

Example:
```ts
// Import Subtitles Plugin
import SubtitlesPlugin, { SubtitlesPluginOptions } from '@slashedcloud/player/Plugins/Subtitles';
...
const options: SubtitlesPluginOptions[] =  [
    {
      lang: 'en',
      src: 'https://example.com/subtitles.vtt',
    },
    {
      lang: 'fr',
      subtitles: [
        {
          startTime: 0,
          endTime: 100,
          title: 'Hello World',
        },
        {
          startTime: 200,
          endTime: 300,
          title: 'nice to meet you',
        },
        {
          startTime: 400,
          title: 'Goodbye World',
        },
      ],
    },
];
// Add the Plugin to the player
player.loadPlugin(SubtitlesPlugin, options);
...
```
## Thumbnails

Show thumbnails on the player. The thumbnails are shown on the player.

The thumbnails is an object in `tracks` option with the following properties:

| Property | Type   | Description                 | Required |
| -------- | ------ | --------------------------- | -------- |
| `src`    | String | URL of the track's VTT file | Yes      |

Example:
```ts
// Import Thumbnails Plugin
import ThumbnailsPlugin, { ThumbnailPluginOptions } from '@slashedcloud/player/Plugins/Thumbnails';
...
const options: ThumbnailPluginOptions = {
  src: 'https://example.com/thumbnails.vtt',
};
// Add the Plugin to the player
player.loadPlugin(ThumbnailsPlugin, options);
```
Translations

Customize the messages shown to the user. The translations are used for the messages shown to the user.

The translations is an object with the following properties:

| Property    |                            | Type   | Description                  | Required |
| ----------- | -------------------------- | ------ | ---------------------------- | -------- |
| `$language` |                            | Object | The key of the translation   | No       |
| -           | `AUTO_QUALITY`             | String | The value of the translation | No       |
| -           | `DISABLE_ADBLOCKER`        | String | The value of the translation | No       |
| -           | `REWIND`                   | String | The value of the translation | No       |
| -           | `STATISTICS`               | String | The value of the translation | No       |
| -           | `SUBTITLE_FORCED`          | String | The value of the translation | No       |
| -           | `EXIT_LOOP_MODE`           | String | The value of the translation | No       |
| -           | `MULTIPLE_LANGUAGES`       | String | The value of the translation | No       |
| -           | `OFF`                      | String | The value of the translation | No       |
| -           | `EXIT_PICTURE_IN_PICTURE`  | String | The value of the translation | No       |
| -           | `EXIT_FULL_SCREEN`         | String | The value of the translation | No       |
| -           | `UNRECOGNIZED_LANGUAGE`    | String | The value of the translation | No       |
| -           | `LANGUAGE`                 | String | The value of the translation | No       |
| -           | `CAPTIONS`                 | String | The value of the translation | No       |
| -           | `MUTE`                     | String | The value of the translation | No       |
| -           | `PLAY`                     | String | The value of the translation | No       |
| -           | `PICTURE_IN_PICTURE`       | String | The value of the translation | No       |
| -           | `RESOLUTION`               | String | The value of the translation | No       |
| -           | `CAST`                     | String | The value of the translation | No       |
| -           | `SEEK`                     | String | The value of the translation | No       |
| -           | `MORE_SETTINGS`            | String | The value of the translation | No       |
| -           | `FAST_FORWARD`             | String | The value of the translation | No       |
| -           | `SKIP_TO_LIVE`             | String | The value of the translation | No       |
| -           | `BACK`                     | String | The value of the translation | No       |
| -           | `AIRPLAY`                  | String | The value of the translation | No       |
| -           | `LIVE`                     | String | The value of the translation | No       |
| -           | `AD_DURATION`              | String | The value of the translation | No       |
| -           | `QUALITY`                  | String | The value of the translation | No       |
| -           | `SURROUND`                 | String | The value of the translation | No       |
| -           | `UNMUTE`                   | String | The value of the translation | No       |
| -           | `ENTER_LOOP_MODE`          | String | The value of the translation | No       |
| -           | `PLAYBACK_RATE`            | String | The value of the translation | No       |
| -           | `REPLAY`                   | String | The value of the translation | No       |
| -           | `NOT_APPLICABLE`           | String | The value of the translation | No       |
| -           | `UNDETERMINED_LANGUAGE`    | String | The value of the translation | No       |
| -           | `VOLUME`                   | String | The value of the translation | No       |
| -           | `ENTER_PICTURE_IN_PICTURE` | String | The value of the translation | No       |
| -           | `AD_TIME`                  | String | The value of the translation | No       |
| -           | `FULL_SCREEN`              | String | The value of the translation | No       |
| -           | `SKIP_AD`                  | String | The value of the translation | No       |
| -           | `ON`                       | String | The value of the translation | No       |
| -           | `AD_PROGRESS`              | String | The value of the translation | No       |
| -           | `PAUSE`                    | String | The value of the translation | No       |
| -           | `AUTO_QUALITY`             | String | The value of the translation | No       |
| -           | `LOOP`                     | String | The value of the translation | No       |

Example:
```ts
// Import Translation Plugin
import TranslationPlugin, { TranslationPluginOptions } from '@slashedcloud/player/Plugins/Translations';
...
const options: TranslationPluginOptions = {
  en: 'https://languages.com/en.json',
  pt: {
    AUTO_QUALITY: 'Automática',
    RESOLUTION: 'Resolução',
    DISABLE_ADBLOCKER: 'Desative o bloqueador de anúncios!',
  },
  es: {
    AUTO_QUALITY: 'Automático',
    RESOLUTION: 'Resolución',
    DISABLE_ADBLOCKER: 'Desactivar el bloqueador de anuncios!',
  },
};
// Add the Plugin to the player
player.loadPlugin(TranslationPlugin, options);
```

## Volume
This plugin allows the user to control the volume of the player. Next visit the player will remember the volume set by the user.

Example:
```ts
// Import Volume Plugin
import Volume from '@slashedcloud/player/Plugins/Volume';
...
// Add the Plugin to the player
player.loadPlugin(Volume);
```

# License

SlashedCloud Player is under the Apache License, Version 2.0. See the [LICENSE](https://github.com/SlashedCloud/player/blob/develop/LICENSE) file for details.
