Skip to content

Commit d8c6a11

Browse files
committed
Add Hotkeys Plugin
1 parent 8a45ec7 commit d8c6a11

File tree

7 files changed

+164
-98
lines changed

7 files changed

+164
-98
lines changed

README.md

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ Sizes of the `vlitejs` bundle compared to the competition:
4646
- [**Cast**](./src/plugins/cast/README.md) - Supports for Google Cast API.
4747
- [**AirPlay**](./src/plugins/airplay/README.md) - Supports for Apple AirPlay API.
4848
- [**Monetization**](./src/plugins/ima/README.md) - Supports for Google IMA SDK.
49+
- [**Hotkeys**](./src/plugins/hotkeys/README.md) - Supports for hotkeys to add shortcuts.
4950
- **Playsinline** - Supports the `playsinline` attribute.
5051
- **SVG icons** - SVG are inlined into the library, no sprites to includes.
5152
- [**Shortcuts**](#shortcuts) - Supports keyboard shortcuts.
@@ -334,19 +335,6 @@ The player exposes some custom CSS properties, locally scopped under the `.v-vli
334335

335336
---
336337

337-
## Shortcuts
338-
339-
The player accepts the following keyboard shortcuts.
340-
341-
| Key | Action |
342-
| :---------------: | ------------------------ |
343-
| <kbd>space</kbd> | Toggle playback |
344-
| <kbd>Esc</kbd> | Exit the fullscreen |
345-
| <kbd>&larr;</kbd> | Seek backward of `5s` |
346-
| <kbd>&rarr;</kbd> | Seek forward of `5s` |
347-
| <kbd>&uarr;</kbd> | Increase volume of `10%` |
348-
| <kbd>&darr;</kbd> | Decrease volume of `10%` |
349-
350338
## Contributors
351339

352340
Many thanks to [Victor Schirm](https://www.behance.net/victorshm) for the `vlitejs` logo.

config/package.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,4 @@ const { author, license, name, version } = pkg
33

44
export const banner = `/*!\n * @license ${license}\n * @name ${name}\n * @version ${version}\n * @copyright ${new Date().getUTCFullYear()} ${author}\n */`
55
export const providers = ['youtube', 'vimeo', 'dailymotion']
6-
export const plugins = ['subtitle', 'pip', 'cast', 'airplay', 'ima', 'volume-bar', 'sticky']
6+
export const plugins = ['subtitle', 'pip', 'cast', 'airplay', 'ima', 'volume-bar', 'sticky', 'hotkeys']

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,8 @@
2121
"monetization",
2222
"ima-sdk",
2323
"sticky",
24-
"volume bar"
24+
"volume bar",
25+
"hotkeys"
2526
],
2627
"homepage": "https://vlite.js.org",
2728
"bugs": "https://github.com/vlitejs/vlite/issues",

src/core/vlite.ts

Lines changed: 0 additions & 83 deletions
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,6 @@ class Vlitejs {
134134

135135
this.onClickOnPlayer = this.onClickOnPlayer.bind(this)
136136
this.onDoubleClickOnPlayer = this.onDoubleClickOnPlayer.bind(this)
137-
this.onKeydown = this.onKeydown.bind(this)
138137
this.onMousemove = this.onMousemove.bind(this)
139138
this.onChangeFullScreen = this.onChangeFullScreen.bind(this)
140139

@@ -245,57 +244,6 @@ class Vlitejs {
245244
}
246245
}
247246

248-
/**
249-
* On keydown event on the media element
250-
* @param e Event listener datas
251-
*/
252-
onKeydown(e: KeyboardEvent) {
253-
const activeElement = document.activeElement
254-
const { keyCode } = e
255-
256-
// Stop and start the auto hide timer on selected key code
257-
if (
258-
[9, 32, 37, 39].includes(keyCode) &&
259-
this.autoHideGranted &&
260-
(activeElement === this.container || activeElement?.closest('.v-vlite'))
261-
) {
262-
this.stopAutoHideTimer()
263-
this.startAutoHideTimer()
264-
}
265-
266-
// Backward or forward video with arrow keys
267-
if (
268-
[37, 39].includes(keyCode) &&
269-
(activeElement === this.container || activeElement === this.player.elements.progressBar)
270-
) {
271-
// Prevent default behavior on input range
272-
e.preventDefault()
273-
274-
if (keyCode === 37) {
275-
this.fastForward('backward')
276-
} else if (keyCode === 39) {
277-
this.fastForward('forward')
278-
}
279-
}
280-
281-
// Increase or decrease volume with arrow keys
282-
if (
283-
[38, 40].includes(keyCode) &&
284-
(activeElement === this.container || activeElement === this.player.elements.volume)
285-
) {
286-
if (keyCode === 38) {
287-
this.increaseVolume()
288-
} else if (keyCode === 40) {
289-
this.decreaseVolume()
290-
}
291-
}
292-
293-
// Toggle the media playback with spacebar key
294-
if (keyCode === 32 && activeElement === this.container) {
295-
this.player.controlBar.togglePlayPause(e)
296-
}
297-
}
298-
299247
/**
300248
* On mousemove on the player
301249
*/
@@ -316,37 +264,6 @@ class Vlitejs {
316264
}
317265
}
318266

319-
/**
320-
* Trigger the video fast forward (front and rear)
321-
* @param direction Direction (backward|forward)
322-
*/
323-
fastForward(direction: string) {
324-
this.player.getCurrentTime().then((seconds: number) => {
325-
this.player.seekTo(
326-
direction === 'backward' ? seconds - this.options.seekTime : seconds + this.options.seekTime
327-
)
328-
})
329-
}
330-
331-
/**
332-
* Increase the player volume
333-
*/
334-
increaseVolume() {
335-
this.player.isMuted && this.player.unMute()
336-
this.player.getVolume().then((volume: number) => {
337-
this.player.setVolume(Math.min(Math.round((volume + this.options.volumeStep) * 10) / 10, 1))
338-
})
339-
}
340-
341-
/**
342-
* Decrease the player volume
343-
*/
344-
decreaseVolume() {
345-
this.player.getVolume().then((volume: number) => {
346-
this.player.setVolume(Math.max(Math.round((volume - this.options.volumeStep) * 10) / 10, 0))
347-
})
348-
}
349-
350267
/**
351268
* Stop the auto hide timer and show the video control bar
352269
*/

src/plugins/README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ Each plugin can be loaded on demand with the API.
1515
| [AirPlay](./airplay/README.md) | Supports for Apple AirPlay API |
1616
| [Ima](./ima/README.md) | Supports for Google IMA SDK |
1717
| [Sticky](./sticky/README.md) | Supports for sticky mode |
18+
| [Hotkeys](./hotkeys/README.md) | Supports for hotkeys to add shortcuts |
1819

1920
## Create a custom plugin
2021

src/plugins/hotkeys/README.md

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
# Plugin: Hotkeys
2+
3+
Supports for hotkeys to add shortcuts.
4+
5+
## Overview
6+
7+
| <!-- --> | <!-- --> |
8+
| ---------------- | -------------------------------------------- |
9+
| Name | `pip` |
10+
| Path | `vlitejs/plugins/hotkeys` |
11+
| Entry point | `vlitejs/plugins/hotkeys/hotkeys.js` |
12+
| Provider&sup2; | `'html5', 'youtube', 'vimeo', 'dailymotion'` |
13+
| Media type&sup3; | `'video', 'audio'` |
14+
15+
## Hotkeys
16+
17+
The player accepts the following keyboard shortcuts.
18+
19+
| Key | Action |
20+
| :---------------: | ------------------------ |
21+
| <kbd>space</kbd> | Toggle playback |
22+
| <kbd>Esc</kbd> | Exit the fullscreen |
23+
| <kbd>&larr;</kbd> | Seek backward of `5s` |
24+
| <kbd>&rarr;</kbd> | Seek forward of `5s` |
25+
| <kbd>&uarr;</kbd> | Increase volume of `10%` |
26+
| <kbd>&darr;</kbd> | Decrease volume of `10%` |
27+
28+
## Usage
29+
30+
### HTML
31+
32+
```html
33+
<video id="player" src="<path_to_video_mp4>"></video>
34+
```
35+
36+
### JavaScript
37+
38+
```js
39+
import 'vlitejs/vlite.css';
40+
import Vlitejs from 'vlitejs';
41+
import VlitejsHotkeys from 'vlitejs/plugins/hotkeys.js';
42+
43+
Vlitejs.registerPlugin('hotkeys', VlitejsHotkeys);
44+
45+
new Vlitejs('#player', {
46+
plugins: ['hotkeys']
47+
});
48+
```
49+
50+
## Demo
51+
52+
# TODO
53+
See the [volume-bar plugin on audio](https://glitch.com/edit/#!/vlitejs-html5-audio-volume-bar?previewSize=50&attributionHidden=false&sidebarCollapsed=false&path=index.html&previewFirst=false) and [volume-bar plugin on video](https://glitch.com/edit/#!/vlitejs-html5-video-volume-bar?previewSize=50&attributionHidden=false&sidebarCollapsed=false&path=index.html&previewFirst=false) demo.

src/plugins/hotkeys/hotkeys.ts

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
import './volume-bar.css'
2+
import type { pluginParameter } from 'shared/assets/types/types.js'
3+
4+
/**
5+
* Vlitejs Volume bar plugin
6+
* @module Vlitejs/plugins/Hotkeys
7+
*/
8+
export default class Hotkeys {
9+
player: any
10+
11+
providers = ['html5', 'youtube', 'dailymotion', 'vimeo']
12+
types = ['video', 'audio']
13+
14+
/**
15+
* @constructor
16+
* @param options
17+
* @param options.player Player instance
18+
*/
19+
constructor({ player }: pluginParameter) {
20+
this.player = player
21+
22+
this.player.onKeydown = this.onKeydown.bind(this)
23+
}
24+
25+
/**
26+
* On keydown event on the media element
27+
* @param e Event listener datas
28+
*/
29+
onKeydown(e: KeyboardEvent) {
30+
const activeElement = document.activeElement
31+
const { keyCode } = e
32+
33+
// Stop and start the auto hide timer on selected key code
34+
if (
35+
[9, 32, 37, 39].includes(keyCode) &&
36+
this.player.autoHideGranted &&
37+
(activeElement === this.player.container || activeElement?.closest('.v-vlite'))
38+
) {
39+
this.player.stopAutoHideTimer()
40+
this.player.startAutoHideTimer()
41+
}
42+
43+
// Backward or forward video with arrow keys
44+
if (
45+
[37, 39].includes(keyCode) &&
46+
(activeElement === this.player.container || activeElement === this.player.elements.progressBar)
47+
) {
48+
// Prevent default behavior on input range
49+
e.preventDefault()
50+
51+
if (keyCode === 37) {
52+
this.fastForward('backward')
53+
} else if (keyCode === 39) {
54+
this.player.fastForward('forward')
55+
}
56+
}
57+
58+
// Increase or decrease volume with arrow keys
59+
if (
60+
[38, 40].includes(keyCode) &&
61+
(activeElement === this.player.container || activeElement === this.player.elements.volume)
62+
) {
63+
if (keyCode === 38) {
64+
this.increaseVolume()
65+
} else if (keyCode === 40) {
66+
this.decreaseVolume()
67+
}
68+
}
69+
70+
// Toggle the media playback with spacebar key
71+
if (keyCode === 32 && activeElement === this.player.container) {
72+
this.player.controlBar.togglePlayPause(e)
73+
}
74+
}
75+
76+
/**
77+
* Trigger the video fast forward (front and rear)
78+
* @param direction Direction (backward|forward)
79+
*/
80+
fastForward(direction: string) {
81+
this.player.getCurrentTime().then((seconds: number) => {
82+
this.player.seekTo(
83+
direction === 'backward' ? seconds - this.player.options.seekTime : seconds + this.player.options.seekTime
84+
)
85+
})
86+
}
87+
88+
/**
89+
* Increase the player volume
90+
*/
91+
increaseVolume() {
92+
this.player.isMuted && this.player.unMute()
93+
this.player.getVolume().then((volume: number) => {
94+
this.player.setVolume(Math.min(Math.round((volume + this.player.options.volumeStep) * 10) / 10, 1))
95+
})
96+
}
97+
98+
/**
99+
* Decrease the player volume
100+
*/
101+
decreaseVolume() {
102+
this.player.getVolume().then((volume: number) => {
103+
this.player.setVolume(Math.max(Math.round((volume - this.player.options.volumeStep) * 10) / 10, 0))
104+
})
105+
}
106+
}

0 commit comments

Comments
 (0)