-
Notifications
You must be signed in to change notification settings - Fork 18
/
main.js
167 lines (135 loc) · 4.07 KB
/
main.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
import {Events, Styler, UICorePlugin, template} from '@clappr/player'
import pluginHtml from './public/playback-rate-selector.html'
import pluginStyle from './public/style.scss'
const DEFAULT_PLAYBACK_RATES = [
{value: 0.5, label: '0.5x'},
{value: 0.75, label: '0.75x'},
{value: 1, label: 'Normal'},
{value: 1.5, label: '1.5x'},
{value: 2, label: '2x'}
]
const DEFAULT_PLAYBACK_RATE = 1
const DEFAULT_PLAYBACK_RATE_SUFFIX = 'x' // Used by getTitle method
export default class PlaybackRatePlugin extends UICorePlugin {
get name() { return 'playback_rate' }
get template() { return template(pluginHtml) }
/**
* Clappr 0.4.x wants to know what versions this plugin is targeting.
*/
get supportedVersion()
{
return { min: '0.4.0', max: '0.5.0' };
}
get attributes() {
return {
'class': this.name,
'data-playback-rate-select': ''
}
}
get events() {
return {
'click [data-playback-rate-select]': 'onRateSelect',
'click [data-playback-rate-button]': 'onShowMenu'
}
}
get container() {
return this.core.activeContainer
? this.core.activeContainer
: this.core.mediaControl.container
}
get playback() {
return this.core.activePlayback
? this.core.activePlayback
: this.core.getCurrentPlayback()
}
bindEvents() {
if (Events.CORE_ACTIVE_CONTAINER_CHANGED)
this.listenTo(this.core, Events.CORE_ACTIVE_CONTAINER_CHANGED, this.reload)
else
this.listenTo(this.core.mediaControl, Events.MEDIACONTROL_CONTAINERCHANGED, this.reload)
this.listenTo(this.core.mediaControl, Events.MEDIACONTROL_RENDERED, this.render)
this.listenTo(this.core.mediaControl, Events.MEDIACONTROL_HIDE, this.hideContextMenu)
}
getExternalInterface() {
return {
getPlaybackRate: this.getSelectedRate,
setPlaybackRate: this.setSelectedRate
}
}
reload() {
this.stopListening()
this.bindEvents()
}
shouldRender() {
return this.container && (
this.playback.tagName === 'video'
|| this.playback.tagName === 'audio'
)
}
render() {
if (! this.shouldRender())
return this
const cfg = this.core.options.playbackRateConfig || {}
this.playbackRates = cfg.options || DEFAULT_PLAYBACK_RATES
this.selectedRate = cfg.defaultValue || DEFAULT_PLAYBACK_RATE
this.rateSuffix = cfg.rateSuffix || DEFAULT_PLAYBACK_RATE_SUFFIX
let t = template(pluginHtml)
let html = t({playbackRates: this.playbackRates, title: this.getTitle()})
this.$el.html(html)
let style = Styler.getStyleFor(pluginStyle, {baseUrl: this.core.options.baseUrl})
this.$el.append(style)
this.core.mediaControl.$('.media-control-right-panel').append(this.el)
this.updateText()
return this
}
onRateSelect(event) {
event.stopPropagation()
let rate = event.target.dataset.playbackRateSelect // data-playback-rate-select
this.setSelectedRate(rate)
this.toggleContextMenu()
return false
}
onShowMenu() {
this.toggleContextMenu()
}
toggleContextMenu() {
this.$('.playback_rate ul').toggle()
}
hideContextMenu() {
this.$('.playback_rate ul').hide()
}
toNumber(value) {
value = Number(value)
// Fallback to default playback rate if cannot be converted
return isNaN(value) ? DEFAULT_PLAYBACK_RATE : value
}
setSelectedRate(rate) {
rate = this.toNumber(rate)
this.playback.el.playbackRate = rate
this.selectedRate = rate
this.updateText()
}
getSelectedRate() {
return this.selectedRate
}
setActiveListItem(rateValue) {
this.$('a').removeClass('active')
this.$(`a[data-playback-rate-select="${rateValue}"]`).addClass('active')
}
buttonElement() {
return this.$('.playback_rate button')
}
getTitle() {
let rate = this.selectedRate
for (const i in this.playbackRates) {
if (this.playbackRates[i].value == rate)
return this.playbackRates[i].label
}
// Unknown rate formatted title
return rate + this.rateSuffix
}
updateText() {
this.buttonElement().text(this.getTitle())
this.setActiveListItem(this.selectedRate)
}
}