diff options
-rw-r--r-- | client/src/app/+videos/+video-watch/shared/playlist/video-watch-playlist.component.ts | 8 | ||||
-rw-r--r-- | client/src/app/+videos/+video-watch/video-watch.component.ts | 11 | ||||
-rw-r--r-- | client/src/assets/player/videojs-components/next-previous-video-button.ts | 1 | ||||
-rw-r--r-- | client/src/sass/player/_player-variables.scss | 14 | ||||
-rw-r--r-- | client/src/sass/player/control-bar.scss | 447 | ||||
-rw-r--r-- | client/src/sass/player/dock.scss | 53 | ||||
-rw-r--r-- | client/src/sass/player/index.scss | 2 | ||||
-rw-r--r-- | client/src/sass/player/peertube-skin.scss | 521 | ||||
-rw-r--r-- | client/src/sass/player/settings-menu.scss | 20 |
9 files changed, 537 insertions, 540 deletions
diff --git a/client/src/app/+videos/+video-watch/shared/playlist/video-watch-playlist.component.ts b/client/src/app/+videos/+video-watch/shared/playlist/video-watch-playlist.component.ts index fbf9a3687..b44238310 100644 --- a/client/src/app/+videos/+video-watch/shared/playlist/video-watch-playlist.component.ts +++ b/client/src/app/+videos/+video-watch/shared/playlist/video-watch-playlist.component.ts | |||
@@ -143,6 +143,14 @@ export class VideoWatchPlaylistComponent { | |||
143 | this.onPlaylistVideosNearOfBottom(position) | 143 | this.onPlaylistVideosNearOfBottom(position) |
144 | } | 144 | } |
145 | 145 | ||
146 | hasPreviousVideo () { | ||
147 | return !!this.findPlaylistVideo(this.currentPlaylistPosition - 1, 'previous') | ||
148 | } | ||
149 | |||
150 | hasNextVideo () { | ||
151 | return !!this.findPlaylistVideo(this.currentPlaylistPosition + 1, 'next') | ||
152 | } | ||
153 | |||
146 | navigateToPreviousPlaylistVideo () { | 154 | navigateToPreviousPlaylistVideo () { |
147 | const previous = this.findPlaylistVideo(this.currentPlaylistPosition - 1, 'previous') | 155 | const previous = this.findPlaylistVideo(this.currentPlaylistPosition - 1, 'previous') |
148 | if (!previous) return | 156 | if (!previous) return |
diff --git a/client/src/app/+videos/+video-watch/video-watch.component.ts b/client/src/app/+videos/+video-watch/video-watch.component.ts index d542f243c..d3d04d236 100644 --- a/client/src/app/+videos/+video-watch/video-watch.component.ts +++ b/client/src/app/+videos/+video-watch/video-watch.component.ts | |||
@@ -474,6 +474,14 @@ export class VideoWatchComponent implements OnInit, OnDestroy { | |||
474 | }) | 474 | }) |
475 | } | 475 | } |
476 | 476 | ||
477 | private hasNextVideo () { | ||
478 | if (this.playlist) { | ||
479 | return this.videoWatchPlaylist.hasNextVideo() | ||
480 | } | ||
481 | |||
482 | return true | ||
483 | } | ||
484 | |||
477 | private playNextVideoInAngularZone () { | 485 | private playNextVideoInAngularZone () { |
478 | if (this.playlist) { | 486 | if (this.playlist) { |
479 | this.zone.run(() => this.videoWatchPlaylist.navigateToNextPlaylistVideo()) | 487 | this.zone.run(() => this.videoWatchPlaylist.navigateToNextPlaylistVideo()) |
@@ -559,6 +567,7 @@ export class VideoWatchComponent implements OnInit, OnDestroy { | |||
559 | autoplay: this.isAutoplay(), | 567 | autoplay: this.isAutoplay(), |
560 | p2pEnabled: isP2PEnabled(video, this.serverConfig, loggedInOrAnonymousUser.p2pEnabled), | 568 | p2pEnabled: isP2PEnabled(video, this.serverConfig, loggedInOrAnonymousUser.p2pEnabled), |
561 | 569 | ||
570 | hasNextVideo: () => this.hasNextVideo(), | ||
562 | nextVideo: () => this.playNextVideoInAngularZone(), | 571 | nextVideo: () => this.playNextVideoInAngularZone(), |
563 | 572 | ||
564 | playerElement: this.playerElement, | 573 | playerElement: this.playerElement, |
@@ -615,6 +624,8 @@ export class VideoWatchComponent implements OnInit, OnDestroy { | |||
615 | 624 | ||
616 | // Only set this if we're in a playlist | 625 | // Only set this if we're in a playlist |
617 | if (this.playlist) { | 626 | if (this.playlist) { |
627 | options.common.hasPreviousVideo = () => this.videoWatchPlaylist.hasPreviousVideo() | ||
628 | |||
618 | options.common.previousVideo = () => { | 629 | options.common.previousVideo = () => { |
619 | this.zone.run(() => this.videoWatchPlaylist.navigateToPreviousPlaylistVideo()) | 630 | this.zone.run(() => this.videoWatchPlaylist.navigateToPreviousPlaylistVideo()) |
620 | } | 631 | } |
diff --git a/client/src/assets/player/videojs-components/next-previous-video-button.ts b/client/src/assets/player/videojs-components/next-previous-video-button.ts index fe17ce2ce..228231a22 100644 --- a/client/src/assets/player/videojs-components/next-previous-video-button.ts +++ b/client/src/assets/player/videojs-components/next-previous-video-button.ts | |||
@@ -40,6 +40,7 @@ class NextPreviousVideoButton extends Button { | |||
40 | 40 | ||
41 | update () { | 41 | update () { |
42 | const disabled = this.nextPreviousVideoButtonOptions.isDisabled() | 42 | const disabled = this.nextPreviousVideoButtonOptions.isDisabled() |
43 | console.log(disabled) | ||
43 | 44 | ||
44 | if (disabled) this.addClass('vjs-disabled') | 45 | if (disabled) this.addClass('vjs-disabled') |
45 | else this.removeClass('vjs-disabled') | 46 | else this.removeClass('vjs-disabled') |
diff --git a/client/src/sass/player/_player-variables.scss b/client/src/sass/player/_player-variables.scss index 1d94b6f96..2625576d4 100644 --- a/client/src/sass/player/_player-variables.scss +++ b/client/src/sass/player/_player-variables.scss | |||
@@ -3,9 +3,15 @@ $primary-foreground-opacity: 0.9; | |||
3 | $primary-foreground-opacity-hover: 1; | 3 | $primary-foreground-opacity-hover: 1; |
4 | $primary-background-color: rgba(0, 0, 0, 0.8); | 4 | $primary-background-color: rgba(0, 0, 0, 0.8); |
5 | 5 | ||
6 | $play-control-font-size: 16px; | ||
7 | $font-size: 13px; | 6 | $font-size: 13px; |
8 | $control-bar-height: 34px; | 7 | |
8 | $control-bar-height: 38px; | ||
9 | $control-bar-icon-size: 26px; | ||
10 | $control-bar-volume-slider-height: 14px; | ||
11 | $control-bar-font-size: 14px; | ||
12 | $control-bar-play-font-size: 34px; | ||
13 | $control-bar-next-previous-play-font-size: 14px; | ||
14 | $control-bar-button-width: 38px; | ||
9 | 15 | ||
10 | $slider-bg-color: lighten($primary-background-color, 33%); | 16 | $slider-bg-color: lighten($primary-background-color, 33%); |
11 | 17 | ||
@@ -16,4 +22,8 @@ $dock-padding: 20px; | |||
16 | $first-control-bar-element-margin-left: 10px; | 22 | $first-control-bar-element-margin-left: 10px; |
17 | $first-control-bar-element-margin-left-small-width: 5px; | 23 | $first-control-bar-element-margin-left-small-width: 5px; |
18 | 24 | ||
25 | $screen-width-750: 750px; | ||
26 | $screen-width-570: 570px; | ||
27 | $screen-width-350: 350px; | ||
28 | |||
19 | $assets-path: '../../assets/' !default; | 29 | $assets-path: '../../assets/' !default; |
diff --git a/client/src/sass/player/control-bar.scss b/client/src/sass/player/control-bar.scss new file mode 100644 index 000000000..dd4e33e75 --- /dev/null +++ b/client/src/sass/player/control-bar.scss | |||
@@ -0,0 +1,447 @@ | |||
1 | @use 'sass:math'; | ||
2 | @use '_variables' as *; | ||
3 | @use '_mixins' as *; | ||
4 | @use './_player-variables' as *; | ||
5 | |||
6 | .video-js.vjs-peertube-skin .vjs-control-bar { | ||
7 | height: $control-bar-height; | ||
8 | background: linear-gradient(rgba(0, 0, 0, 0.2), rgba(0, 0, 0, 0.6)); | ||
9 | box-shadow: 0 -15px 40px 10px rgba(0, 0, 0, 0.2); | ||
10 | text-shadow: 0 0 2px rgba(0, 0, 0, 0.5); | ||
11 | transition: visibility 0.3s, opacity 0.3s !important; | ||
12 | |||
13 | > button:first-child { | ||
14 | @include margin-left($first-control-bar-element-margin-left); | ||
15 | } | ||
16 | |||
17 | > button:last-child { | ||
18 | @include margin-right($first-control-bar-element-margin-left); | ||
19 | } | ||
20 | |||
21 | .vjs-progress-control, | ||
22 | .vjs-play-control, | ||
23 | .vjs-playback-rate, | ||
24 | .vjs-mute-control, | ||
25 | .vjs-volume-control, | ||
26 | .vjs-resolution-control, | ||
27 | .vjs-fullscreen-control, | ||
28 | .vjs-peertube-link, | ||
29 | .vjs-theater-control, | ||
30 | .vjs-settings { | ||
31 | color: pvar(--embedForegroundColor) !important; | ||
32 | |||
33 | opacity: $primary-foreground-opacity; | ||
34 | transition: opacity .1s; | ||
35 | |||
36 | &:hover { | ||
37 | opacity: $primary-foreground-opacity-hover; | ||
38 | } | ||
39 | } | ||
40 | |||
41 | .vjs-current-time, | ||
42 | .vjs-duration, | ||
43 | .vjs-peertube { | ||
44 | color: pvar(--embedForegroundColor); | ||
45 | opacity: $primary-foreground-opacity; | ||
46 | } | ||
47 | |||
48 | .vjs-progress-control { | ||
49 | @include margin-left($progress-margin); | ||
50 | |||
51 | position: absolute; | ||
52 | top: -10px; | ||
53 | z-index: 100; // On top of the progress bar | ||
54 | width: calc(100% - (2 * #{$progress-margin})); | ||
55 | height: 14px; | ||
56 | |||
57 | .vjs-slider { | ||
58 | margin: 0; | ||
59 | border-radius: 0; | ||
60 | background-color: rgba(255, 255, 255, .2); | ||
61 | height: 3px; | ||
62 | transition: none; | ||
63 | |||
64 | .vjs-play-progress { | ||
65 | background: pvar(--embedForegroundColor); | ||
66 | |||
67 | // Not display the circle if the progress is not hovered | ||
68 | &::before { | ||
69 | opacity: 0; | ||
70 | transition: opacity 0.1s ease; | ||
71 | font-size: 14px; | ||
72 | |||
73 | top: -0.3em; | ||
74 | } | ||
75 | |||
76 | .vjs-time-tooltip { | ||
77 | display: none; | ||
78 | } | ||
79 | } | ||
80 | |||
81 | .vjs-load-progress { | ||
82 | &, | ||
83 | div { | ||
84 | background: rgba(255, 255, 255, .2); | ||
85 | } | ||
86 | } | ||
87 | } | ||
88 | } | ||
89 | |||
90 | .vjs-progress-control:hover .vjs-slider, | ||
91 | .vjs-progress-control .vjs-slider.vjs-sliding { | ||
92 | height: 5px; | ||
93 | |||
94 | .vjs-play-progress::before { | ||
95 | opacity: 1; | ||
96 | } | ||
97 | } | ||
98 | |||
99 | |||
100 | .vjs-play-control { | ||
101 | @include disable-outline; | ||
102 | |||
103 | cursor: pointer; | ||
104 | width: $control-bar-button-width; | ||
105 | |||
106 | .vjs-icon-placeholder::before { | ||
107 | font-size: $control-bar-play-font-size; | ||
108 | line-height: initial; | ||
109 | } | ||
110 | } | ||
111 | |||
112 | .vjs-time-control { | ||
113 | line-height: inherit; | ||
114 | |||
115 | &.vjs-current-time { | ||
116 | @include margin-left(.5em); | ||
117 | |||
118 | font-size: $control-bar-font-size; | ||
119 | display: inline-block; | ||
120 | padding: 0; | ||
121 | |||
122 | .vjs-current-time-display { | ||
123 | line-height: calc(#{$control-bar-height} - 1px); | ||
124 | |||
125 | &::after { | ||
126 | @include margin(0, 1px, 0, 2px); | ||
127 | |||
128 | content: '/'; | ||
129 | } | ||
130 | } | ||
131 | } | ||
132 | |||
133 | &.vjs-duration { | ||
134 | font-size: $control-bar-font-size; | ||
135 | display: inline-block; | ||
136 | padding: 0; | ||
137 | |||
138 | .vjs-duration-display { | ||
139 | line-height: calc(#{$control-bar-height} - 1px); | ||
140 | } | ||
141 | } | ||
142 | |||
143 | &.vjs-remaining-time { | ||
144 | display: none; | ||
145 | } | ||
146 | } | ||
147 | |||
148 | .vjs-live-control { | ||
149 | line-height: $control-bar-height; | ||
150 | min-width: 4em; | ||
151 | width: inherit; | ||
152 | } | ||
153 | |||
154 | .vjs-peertube { | ||
155 | @include margin-right(6px); | ||
156 | |||
157 | width: 100%; | ||
158 | line-height: $control-bar-height; | ||
159 | text-align: end; | ||
160 | overflow: hidden; | ||
161 | font-size: $control-bar-font-size; | ||
162 | |||
163 | .vjs-peertube-displayed { | ||
164 | display: block; | ||
165 | } | ||
166 | |||
167 | .vjs-peertube-hidden { | ||
168 | display: none; | ||
169 | } | ||
170 | |||
171 | .download-speed-number, | ||
172 | .upload-speed-number, | ||
173 | .peers-number, | ||
174 | .http-fallback { | ||
175 | font-weight: $font-semibold; | ||
176 | } | ||
177 | |||
178 | .download-speed-text, | ||
179 | .upload-speed-text, | ||
180 | .peers-text, | ||
181 | .http-fallback { | ||
182 | @include margin-right(15px); | ||
183 | } | ||
184 | |||
185 | .icon { | ||
186 | @include margin-right(2px); | ||
187 | |||
188 | display: inline-block; | ||
189 | width: 15px; | ||
190 | height: 15px; | ||
191 | background-size: contain; | ||
192 | vertical-align: middle; | ||
193 | background-repeat: no-repeat; | ||
194 | position: relative; | ||
195 | top: -1px; | ||
196 | |||
197 | &.icon-download { | ||
198 | background-image: url('#{$assets-path}/player/images/arrow-down.svg'); | ||
199 | } | ||
200 | |||
201 | &.icon-upload { | ||
202 | background-image: url('#{$assets-path}/player/images/arrow-up.svg'); | ||
203 | } | ||
204 | } | ||
205 | } | ||
206 | |||
207 | .vjs-next-video, | ||
208 | .vjs-previous-video { | ||
209 | width: $control-bar-button-width - 4px; | ||
210 | |||
211 | &.vjs-disabled { | ||
212 | cursor: default; | ||
213 | } | ||
214 | |||
215 | .icon { | ||
216 | &.icon-next, | ||
217 | &.icon-previous { | ||
218 | mask-image: url('#{$assets-path}/player/images/next.svg'); | ||
219 | -webkit-mask-image: url('#{$assets-path}/player/images/next.svg'); | ||
220 | mask-size: cover; | ||
221 | -webkit-mask-size: cover; | ||
222 | |||
223 | background-color: #fff; | ||
224 | width: $control-bar-next-previous-play-font-size; | ||
225 | height: $control-bar-next-previous-play-font-size; | ||
226 | display: inline-block; | ||
227 | } | ||
228 | |||
229 | &.icon-previous { | ||
230 | transform: rotate(180deg); | ||
231 | } | ||
232 | } | ||
233 | } | ||
234 | |||
235 | .vjs-mute-control { | ||
236 | @include disable-outline; | ||
237 | |||
238 | padding: 0; | ||
239 | width: $control-bar-icon-size; | ||
240 | |||
241 | .vjs-icon-placeholder { | ||
242 | display: inline-block; | ||
243 | width: $control-bar-icon-size; | ||
244 | height: $control-bar-icon-size; | ||
245 | vertical-align: middle; | ||
246 | background: url('#{$assets-path}/player/images/volume.svg') no-repeat; | ||
247 | background-size: contain; | ||
248 | |||
249 | &::before { | ||
250 | content: ''; | ||
251 | } | ||
252 | } | ||
253 | |||
254 | &.vjs-vol-0 .vjs-icon-placeholder { | ||
255 | background: url('#{$assets-path}/player/images/volume-mute.svg') no-repeat; | ||
256 | background-size: contain; | ||
257 | } | ||
258 | } | ||
259 | |||
260 | .vjs-volume-control { | ||
261 | @include margin(0, 5px, 0, 5px); | ||
262 | |||
263 | width: $control-bar-icon-size; | ||
264 | display: flex; | ||
265 | align-items: center; | ||
266 | } | ||
267 | |||
268 | .vjs-volume-bar { | ||
269 | background: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACwAAAAcCAQAAACw95UnAAAAMElEQVRIx2NgoBL4n4YKGUYNHkEG4zJg1OCRYDCpBowaPJwMppbLRg0eNXjUYBLEAXWNUA6QNm1lAAAAAElFTkSuQmCC') no-repeat; | ||
270 | background-size: $control-bar-icon-size $control-bar-volume-slider-height; | ||
271 | height: 100%; | ||
272 | width: 100%; | ||
273 | max-width: $control-bar-icon-size; | ||
274 | max-height: $control-bar-volume-slider-height; | ||
275 | margin: 0; | ||
276 | border-radius: 0; | ||
277 | |||
278 | .vjs-volume-level { | ||
279 | background: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACwAAAAcAQAAAAAyhWABAAAAAnRSTlMAAHaTzTgAAAAZSURBVHgBYwAB/g9EUv+JokCqiaT+U4MCAPKPS7WUUOc1AAAAAElFTkSuQmCC') no-repeat; | ||
280 | background-size: $control-bar-icon-size $control-bar-volume-slider-height; | ||
281 | max-width: $control-bar-icon-size; | ||
282 | height: 100%; | ||
283 | max-height: $control-bar-volume-slider-height; | ||
284 | } | ||
285 | |||
286 | &:focus { | ||
287 | text-shadow: none; | ||
288 | box-shadow: none; | ||
289 | } | ||
290 | } | ||
291 | |||
292 | .vjs-volume-panel.vjs-volume-panel-horizontal.vjs-slider-active, | ||
293 | .vjs-volume-panel.vjs-volume-panel-horizontal:active, | ||
294 | .vjs-volume-panel.vjs-volume-panel-horizontal:focus, | ||
295 | .vjs-volume-panel.vjs-volume-panel-horizontal:hover { | ||
296 | width: 6em; | ||
297 | transition-property: none; | ||
298 | } | ||
299 | |||
300 | .vjs-volume-panel .vjs-mute-control:hover ~ .vjs-volume-control.vjs-volume-horizontal { | ||
301 | width: 3em; | ||
302 | height: auto; | ||
303 | } | ||
304 | |||
305 | .vjs-volume-panel .vjs-mute-control:hover ~ .vjs-volume-control { | ||
306 | transition-property: none; | ||
307 | } | ||
308 | |||
309 | .vjs-volume-panel { | ||
310 | .vjs-mute-control { | ||
311 | width: 2em; | ||
312 | z-index: 1; | ||
313 | padding: 0; | ||
314 | } | ||
315 | |||
316 | .vjs-volume-control { | ||
317 | display: inline-block; | ||
318 | position: relative; | ||
319 | left: 5px; | ||
320 | opacity: 1; | ||
321 | width: 3em; | ||
322 | height: auto; | ||
323 | } | ||
324 | } | ||
325 | |||
326 | .vjs-settings { | ||
327 | @include disable-outline; | ||
328 | |||
329 | cursor: pointer; | ||
330 | width: $control-bar-button-width; | ||
331 | |||
332 | .vjs-icon-placeholder { | ||
333 | display: inline-block; | ||
334 | height: $control-bar-icon-size - 5px; | ||
335 | width: $control-bar-icon-size - 5px; | ||
336 | vertical-align: middle; | ||
337 | background: url('#{$assets-path}/player/images/settings.svg') no-repeat; | ||
338 | background-size: contain; | ||
339 | |||
340 | &::before { | ||
341 | content: ''; | ||
342 | } | ||
343 | } | ||
344 | } | ||
345 | |||
346 | .vjs-peertube-link { | ||
347 | @include disable-outline; | ||
348 | @include disable-default-a-behaviour; | ||
349 | |||
350 | text-decoration: none; | ||
351 | line-height: $control-bar-height; | ||
352 | font-weight: $font-semibold; | ||
353 | padding: 0 5px; | ||
354 | } | ||
355 | |||
356 | .vjs-theater-control { | ||
357 | @include disable-outline; | ||
358 | |||
359 | width: $control-bar-button-width; | ||
360 | cursor: pointer; | ||
361 | |||
362 | .vjs-icon-placeholder { | ||
363 | transition: transform 0.2s ease; | ||
364 | display: inline-block; | ||
365 | width: $control-bar-icon-size; | ||
366 | height: $control-bar-icon-size; | ||
367 | vertical-align: middle; | ||
368 | background: url('#{$assets-path}/player/images/theater.svg') no-repeat; | ||
369 | background-size: contain; | ||
370 | |||
371 | &::before { | ||
372 | content: ''; | ||
373 | } | ||
374 | } | ||
375 | } | ||
376 | |||
377 | .vjs-fullscreen-control { | ||
378 | @include disable-outline; | ||
379 | |||
380 | width: $control-bar-button-width; | ||
381 | |||
382 | .vjs-icon-placeholder { | ||
383 | display: inline-block; | ||
384 | width: $control-bar-icon-size; | ||
385 | height: $control-bar-icon-size; | ||
386 | vertical-align: middle; | ||
387 | background: url('#{$assets-path}/player/images/fullscreen.svg') no-repeat; | ||
388 | background-size: contain; | ||
389 | |||
390 | &::before { | ||
391 | content: ''; | ||
392 | } | ||
393 | } | ||
394 | } | ||
395 | |||
396 | @media screen and (max-width: $screen-width-750) { | ||
397 | .vjs-theater-control { | ||
398 | display: none; | ||
399 | } | ||
400 | } | ||
401 | |||
402 | @media screen and (max-width: $screen-width-570) { | ||
403 | .vjs-peertube { | ||
404 | padding: 0 !important; | ||
405 | |||
406 | .vjs-peertube-displayed { | ||
407 | display: none !important; | ||
408 | } | ||
409 | } | ||
410 | |||
411 | &.vjs-live { | ||
412 | .vjs-duration { | ||
413 | display: none !important; | ||
414 | } | ||
415 | |||
416 | .vjs-peertube { | ||
417 | display: none !important; | ||
418 | } | ||
419 | } | ||
420 | } | ||
421 | |||
422 | @media screen and (max-width: $screen-width-350) { | ||
423 | .vjs-volume-control, | ||
424 | .vjs-next-video, | ||
425 | .vjs-previous-video { | ||
426 | display: none !important; | ||
427 | } | ||
428 | |||
429 | .vjs-peertube-link { | ||
430 | padding: 0 !important; | ||
431 | } | ||
432 | |||
433 | > button:first-child { | ||
434 | @include margin-left($first-control-bar-element-margin-left-small-width); | ||
435 | } | ||
436 | |||
437 | > button:last-child { | ||
438 | @include margin-right($first-control-bar-element-margin-left-small-width); | ||
439 | } | ||
440 | |||
441 | &.vjs-live { | ||
442 | .vjs-current-time { | ||
443 | display: none !important; | ||
444 | } | ||
445 | } | ||
446 | } | ||
447 | } | ||
diff --git a/client/src/sass/player/dock.scss b/client/src/sass/player/dock.scss new file mode 100644 index 000000000..79600ac93 --- /dev/null +++ b/client/src/sass/player/dock.scss | |||
@@ -0,0 +1,53 @@ | |||
1 | @use 'sass:math'; | ||
2 | @use '_variables' as *; | ||
3 | @use '_mixins' as *; | ||
4 | @use './_player-variables' as *; | ||
5 | |||
6 | .video-js.vjs-peertube-skin { | ||
7 | .vjs-dock-text { | ||
8 | @include padding-right(60px); | ||
9 | |||
10 | padding: $dock-padding; | ||
11 | background: linear-gradient(to bottom, rgba(0, 0, 0, .6) 0, rgba(0, 0, 0, 0.2) 70%, rgba(0, 0, 0, 0) 100%); | ||
12 | } | ||
13 | |||
14 | .vjs-dock-title, | ||
15 | .vjs-dock-description { | ||
16 | text-shadow: 0 0 2px rgba(0, 0, 0, .5); | ||
17 | } | ||
18 | |||
19 | .vjs-dock-description { | ||
20 | font-size: 11px; | ||
21 | |||
22 | .text::before { | ||
23 | @include margin-right(4px); | ||
24 | } | ||
25 | |||
26 | .text::after { | ||
27 | @include margin-left(4px); | ||
28 | transform: scale(-1, 1); | ||
29 | } | ||
30 | } | ||
31 | |||
32 | @media screen and (max-width: $screen-width-750) { | ||
33 | .vjs-dock-text { | ||
34 | font-size: 16px; | ||
35 | } | ||
36 | |||
37 | .vjs-dock-description { | ||
38 | font-size: 9px; | ||
39 | } | ||
40 | } | ||
41 | |||
42 | @media screen and (max-width: $screen-width-570) { | ||
43 | .vjs-dock-text { | ||
44 | font-size: 14px; | ||
45 | } | ||
46 | } | ||
47 | |||
48 | @media screen and (max-width: $screen-width-350) { | ||
49 | .vjs-dock-text { | ||
50 | font-size: 13px; | ||
51 | } | ||
52 | } | ||
53 | } | ||
diff --git a/client/src/sass/player/index.scss b/client/src/sass/player/index.scss index 385365b6d..7420460e7 100644 --- a/client/src/sass/player/index.scss +++ b/client/src/sass/player/index.scss | |||
@@ -1,4 +1,6 @@ | |||
1 | @use './peertube-skin'; | 1 | @use './peertube-skin'; |
2 | @use './dock'; | ||
3 | @use './control-bar'; | ||
2 | @use './mobile'; | 4 | @use './mobile'; |
3 | @use './context-menu'; | 5 | @use './context-menu'; |
4 | @use './settings-menu'; | 6 | @use './settings-menu'; |
diff --git a/client/src/sass/player/peertube-skin.scss b/client/src/sass/player/peertube-skin.scss index 332a0e17d..5f873d495 100644 --- a/client/src/sass/player/peertube-skin.scss +++ b/client/src/sass/player/peertube-skin.scss | |||
@@ -20,31 +20,6 @@ body { | |||
20 | font-size: $font-size; | 20 | font-size: $font-size; |
21 | color: pvar(--embedForegroundColor); | 21 | color: pvar(--embedForegroundColor); |
22 | 22 | ||
23 | .vjs-dock-text { | ||
24 | @include padding-right(60px); | ||
25 | |||
26 | padding: $dock-padding; | ||
27 | background: linear-gradient(to bottom, rgba(0, 0, 0, .6) 0, rgba(0, 0, 0, 0.2) 70%, rgba(0, 0, 0, 0) 100%); | ||
28 | } | ||
29 | |||
30 | .vjs-dock-title, | ||
31 | .vjs-dock-description { | ||
32 | text-shadow: 0 0 2px rgba(0, 0, 0, .5); | ||
33 | } | ||
34 | |||
35 | .vjs-dock-description { | ||
36 | font-size: 11px; | ||
37 | |||
38 | .text::before { | ||
39 | @include margin-right(4px); | ||
40 | } | ||
41 | |||
42 | .text::after { | ||
43 | @include margin-left(4px); | ||
44 | transform: scale(-1, 1); | ||
45 | } | ||
46 | } | ||
47 | |||
48 | .vjs-volume-level::before { | 23 | .vjs-volume-level::before { |
49 | content: ''; /* Remove Circle From Progress Bar */ | 24 | content: ''; /* Remove Circle From Progress Bar */ |
50 | } | 25 | } |
@@ -129,431 +104,7 @@ body { | |||
129 | outline: 0; | 104 | outline: 0; |
130 | } | 105 | } |
131 | 106 | ||
132 | .vjs-control-bar { | 107 | @media screen and (max-width: $screen-width-750) { |
133 | height: $control-bar-height; | ||
134 | background: linear-gradient(rgba(0, 0, 0, 0.2), rgba(0, 0, 0, 0.6)); | ||
135 | box-shadow: 0 -15px 40px 10px rgba(0, 0, 0, 0.2); | ||
136 | text-shadow: 0 0 2px rgba(0, 0, 0, 0.5); | ||
137 | transition: visibility 0.3s, opacity 0.3s !important; | ||
138 | |||
139 | > button:first-child { | ||
140 | @include margin-left($first-control-bar-element-margin-left); | ||
141 | } | ||
142 | |||
143 | .vjs-progress-control, | ||
144 | .vjs-play-control, | ||
145 | .vjs-playback-rate, | ||
146 | .vjs-mute-control, | ||
147 | .vjs-volume-control, | ||
148 | .vjs-resolution-control, | ||
149 | .vjs-fullscreen-control, | ||
150 | .vjs-peertube-link, | ||
151 | .vjs-theater-control, | ||
152 | .vjs-settings { | ||
153 | color: pvar(--embedForegroundColor) !important; | ||
154 | |||
155 | opacity: $primary-foreground-opacity; | ||
156 | transition: opacity .1s; | ||
157 | |||
158 | &:hover { | ||
159 | opacity: $primary-foreground-opacity-hover; | ||
160 | } | ||
161 | } | ||
162 | |||
163 | .vjs-current-time, | ||
164 | .vjs-duration, | ||
165 | .vjs-peertube { | ||
166 | color: pvar(--embedForegroundColor); | ||
167 | opacity: $primary-foreground-opacity; | ||
168 | } | ||
169 | |||
170 | .vjs-progress-control { | ||
171 | @include margin-left($progress-margin); | ||
172 | |||
173 | position: absolute; | ||
174 | z-index: 100; // On top of the progress bar | ||
175 | bottom: 29px; | ||
176 | width: calc(100% - (2 * #{$progress-margin})); | ||
177 | height: 14px; | ||
178 | |||
179 | .vjs-slider { | ||
180 | margin: 0; | ||
181 | border-radius: 0; | ||
182 | background-color: rgba(255, 255, 255, .2); | ||
183 | height: 3px; | ||
184 | transition: none; | ||
185 | |||
186 | .vjs-play-progress { | ||
187 | background: pvar(--embedForegroundColor); | ||
188 | |||
189 | // Not display the circle if the progress is not hovered | ||
190 | &::before { | ||
191 | opacity: 0; | ||
192 | transition: opacity 0.1s ease; | ||
193 | font-size: 14px; | ||
194 | |||
195 | top: -0.3em; | ||
196 | } | ||
197 | |||
198 | .vjs-time-tooltip { | ||
199 | display: none; | ||
200 | } | ||
201 | } | ||
202 | |||
203 | .vjs-load-progress { | ||
204 | &, | ||
205 | div { | ||
206 | background: rgba(255, 255, 255, .2); | ||
207 | } | ||
208 | } | ||
209 | } | ||
210 | } | ||
211 | |||
212 | .vjs-progress-control:hover .vjs-slider, | ||
213 | .vjs-progress-control .vjs-slider.vjs-sliding { | ||
214 | height: 5px; | ||
215 | |||
216 | .vjs-play-progress::before { | ||
217 | opacity: 1; | ||
218 | } | ||
219 | } | ||
220 | |||
221 | |||
222 | .vjs-play-control { | ||
223 | @include disable-outline; | ||
224 | |||
225 | cursor: pointer; | ||
226 | width: 2em; | ||
227 | |||
228 | .vjs-icon-placeholder { | ||
229 | line-height: $control-bar-height; | ||
230 | position: relative; | ||
231 | top: -1px; | ||
232 | |||
233 | &::before { | ||
234 | font-size: 28px; | ||
235 | line-height: unset; | ||
236 | position: relative; | ||
237 | } | ||
238 | } | ||
239 | } | ||
240 | |||
241 | .vjs-time-control { | ||
242 | line-height: inherit; | ||
243 | |||
244 | &.vjs-current-time { | ||
245 | @include margin-left(.5em); | ||
246 | |||
247 | font-size: $font-size; | ||
248 | display: inline-block; | ||
249 | padding: 0; | ||
250 | |||
251 | .vjs-current-time-display { | ||
252 | line-height: calc(#{$control-bar-height} - 1px); | ||
253 | |||
254 | &::after { | ||
255 | @include margin(0, 1px, 0, 2px); | ||
256 | |||
257 | content: '/'; | ||
258 | } | ||
259 | } | ||
260 | } | ||
261 | |||
262 | &.vjs-duration { | ||
263 | font-size: $font-size; | ||
264 | display: inline-block; | ||
265 | padding: 0; | ||
266 | |||
267 | .vjs-duration-display { | ||
268 | line-height: calc(#{$control-bar-height} - 1px); | ||
269 | } | ||
270 | } | ||
271 | |||
272 | &.vjs-remaining-time { | ||
273 | display: none; | ||
274 | } | ||
275 | } | ||
276 | |||
277 | .vjs-live-control { | ||
278 | line-height: $control-bar-height; | ||
279 | min-width: 4em; | ||
280 | width: inherit; | ||
281 | } | ||
282 | |||
283 | .vjs-peertube { | ||
284 | @include margin-right(6px); | ||
285 | |||
286 | width: 100%; | ||
287 | line-height: $control-bar-height; | ||
288 | text-align: end; | ||
289 | overflow: hidden; | ||
290 | |||
291 | .vjs-peertube-displayed { | ||
292 | display: block; | ||
293 | } | ||
294 | |||
295 | .vjs-peertube-hidden { | ||
296 | display: none; | ||
297 | } | ||
298 | |||
299 | .download-speed-number, | ||
300 | .upload-speed-number, | ||
301 | .peers-number, | ||
302 | .http-fallback { | ||
303 | font-weight: $font-semibold; | ||
304 | } | ||
305 | |||
306 | .download-speed-text, | ||
307 | .upload-speed-text, | ||
308 | .peers-text, | ||
309 | .http-fallback { | ||
310 | @include margin-right(15px); | ||
311 | } | ||
312 | |||
313 | .icon { | ||
314 | &.icon-download { | ||
315 | background-image: url('#{$assets-path}/player/images/arrow-down.svg'); | ||
316 | } | ||
317 | |||
318 | &.icon-upload { | ||
319 | background-image: url('#{$assets-path}/player/images/arrow-up.svg'); | ||
320 | } | ||
321 | } | ||
322 | } | ||
323 | |||
324 | .vjs-next-video, | ||
325 | .vjs-previous-video { | ||
326 | line-height: $control-bar-height; | ||
327 | text-align: end; | ||
328 | |||
329 | .icon { | ||
330 | &.icon-next, | ||
331 | &.icon-previous { | ||
332 | mask-image: url('#{$assets-path}/player/images/next.svg'); | ||
333 | -webkit-mask-image: url('#{$assets-path}/player/images/next.svg'); | ||
334 | mask-size: cover; | ||
335 | -webkit-mask-size: cover; | ||
336 | |||
337 | background-color: #fff; | ||
338 | width: 11px; | ||
339 | height: 11px; | ||
340 | margin-top: -2px; | ||
341 | display: inline-block; | ||
342 | } | ||
343 | |||
344 | &.icon-previous { | ||
345 | transform: rotate(180deg); | ||
346 | } | ||
347 | } | ||
348 | } | ||
349 | |||
350 | .vjs-peertube { | ||
351 | .icon { | ||
352 | display: inline-block; | ||
353 | width: 15px; | ||
354 | height: 15px; | ||
355 | background-size: contain; | ||
356 | vertical-align: middle; | ||
357 | background-repeat: no-repeat; | ||
358 | position: relative; | ||
359 | top: -1px; | ||
360 | } | ||
361 | } | ||
362 | |||
363 | .vjs-playback-rate { | ||
364 | font-size: 10px; | ||
365 | width: 37px !important; | ||
366 | |||
367 | .vjs-playback-rate-value { | ||
368 | font-size: 13px; | ||
369 | line-height: $control-bar-height; | ||
370 | } | ||
371 | |||
372 | .vjs-menu .vjs-menu-content { | ||
373 | width: 37px !important; | ||
374 | } | ||
375 | } | ||
376 | |||
377 | .vjs-mute-control { | ||
378 | @include disable-outline; | ||
379 | |||
380 | padding: 0; | ||
381 | width: 30px; | ||
382 | |||
383 | .vjs-icon-placeholder { | ||
384 | display: inline-block; | ||
385 | width: 22px; | ||
386 | height: 22px; | ||
387 | vertical-align: middle; | ||
388 | background: url('#{$assets-path}/player/images/volume.svg') no-repeat; | ||
389 | background-size: contain; | ||
390 | |||
391 | &::before { | ||
392 | content: ''; | ||
393 | } | ||
394 | } | ||
395 | |||
396 | &.vjs-vol-0 .vjs-icon-placeholder { | ||
397 | background: url('#{$assets-path}/player/images/volume-mute.svg') no-repeat; | ||
398 | background-size: contain; | ||
399 | } | ||
400 | } | ||
401 | |||
402 | .vjs-volume-control { | ||
403 | @include margin(0, 5px, 0, 0); | ||
404 | |||
405 | width: 30px; | ||
406 | } | ||
407 | |||
408 | .vjs-volume-bar { | ||
409 | background: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACwAAAAcCAQAAACw95UnAAAAMElEQVRIx2NgoBL4n4YKGUYNHkEG4zJg1OCRYDCpBowaPJwMppbLRg0eNXjUYBLEAXWNUA6QNm1lAAAAAElFTkSuQmCC') no-repeat; | ||
410 | background-size: 22px 14px; | ||
411 | height: 100%; | ||
412 | width: 100%; | ||
413 | max-width: 22px; | ||
414 | max-height: 14px; | ||
415 | margin: 7px 4px; | ||
416 | border-radius: 0; | ||
417 | top: 3px; | ||
418 | |||
419 | .vjs-volume-level { | ||
420 | background: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACwAAAAcAQAAAAAyhWABAAAAAnRSTlMAAHaTzTgAAAAZSURBVHgBYwAB/g9EUv+JokCqiaT+U4MCAPKPS7WUUOc1AAAAAElFTkSuQmCC') no-repeat; | ||
421 | background-size: 22px 14px; | ||
422 | max-width: 22px; | ||
423 | max-height: 14px; | ||
424 | height: 100%; | ||
425 | } | ||
426 | |||
427 | &:focus { | ||
428 | text-shadow: none; | ||
429 | box-shadow: none; | ||
430 | } | ||
431 | } | ||
432 | |||
433 | .vjs-volume-panel.vjs-volume-panel-horizontal.vjs-slider-active, | ||
434 | .vjs-volume-panel.vjs-volume-panel-horizontal:active, | ||
435 | .vjs-volume-panel.vjs-volume-panel-horizontal:focus, | ||
436 | .vjs-volume-panel.vjs-volume-panel-horizontal:hover { | ||
437 | width: 6em; | ||
438 | transition-property: none; | ||
439 | } | ||
440 | |||
441 | .vjs-volume-panel .vjs-mute-control:hover ~ .vjs-volume-control.vjs-volume-horizontal { | ||
442 | width: 3em; | ||
443 | height: auto; | ||
444 | } | ||
445 | |||
446 | .vjs-volume-panel .vjs-mute-control:hover ~ .vjs-volume-control { | ||
447 | transition-property: none; | ||
448 | } | ||
449 | |||
450 | .vjs-volume-panel { | ||
451 | .vjs-mute-control { | ||
452 | width: 2em; | ||
453 | z-index: 1; | ||
454 | padding: 0; | ||
455 | } | ||
456 | |||
457 | .vjs-volume-control { | ||
458 | display: inline-block; | ||
459 | position: relative; | ||
460 | left: 5px; | ||
461 | opacity: 1; | ||
462 | width: 3em; | ||
463 | height: auto; | ||
464 | } | ||
465 | } | ||
466 | |||
467 | .vjs-peertube-link { | ||
468 | @include disable-outline; | ||
469 | @include disable-default-a-behaviour; | ||
470 | |||
471 | text-decoration: none; | ||
472 | line-height: $control-bar-height; | ||
473 | font-weight: $font-semibold; | ||
474 | padding: 0 5px; | ||
475 | } | ||
476 | |||
477 | .vjs-theater-control { | ||
478 | @include disable-outline; | ||
479 | @include margin-right(1px); | ||
480 | |||
481 | width: 37px; | ||
482 | cursor: pointer; | ||
483 | |||
484 | .vjs-icon-placeholder { | ||
485 | transition: transform 0.2s ease; | ||
486 | display: inline-block; | ||
487 | width: 22px; | ||
488 | height: 22px; | ||
489 | vertical-align: middle; | ||
490 | background: url('#{$assets-path}/player/images/theater.svg') no-repeat; | ||
491 | background-size: contain; | ||
492 | |||
493 | &::before { | ||
494 | content: ''; | ||
495 | } | ||
496 | } | ||
497 | } | ||
498 | |||
499 | .vjs-fullscreen-control { | ||
500 | @include disable-outline; | ||
501 | @include margin-left($first-control-bar-element-margin-left); | ||
502 | |||
503 | width: 37px; | ||
504 | |||
505 | .vjs-icon-placeholder { | ||
506 | display: inline-block; | ||
507 | width: 22px; | ||
508 | height: 22px; | ||
509 | vertical-align: middle; | ||
510 | background: url('#{$assets-path}/player/images/fullscreen.svg') no-repeat; | ||
511 | background-size: contain; | ||
512 | |||
513 | &::before { | ||
514 | content: ''; | ||
515 | } | ||
516 | } | ||
517 | } | ||
518 | |||
519 | .vjs-menu-button-popup { | ||
520 | font-weight: $font-semibold; | ||
521 | width: 50px; | ||
522 | |||
523 | .vjs-resolution-button { | ||
524 | @include disable-outline; | ||
525 | } | ||
526 | |||
527 | .vjs-menu { | ||
528 | top: 20px; | ||
529 | left: 0; | ||
530 | |||
531 | .vjs-menu-content { | ||
532 | width: 50px; | ||
533 | bottom: 20px; | ||
534 | } | ||
535 | |||
536 | li { | ||
537 | text-transform: none; | ||
538 | font-size: 13px; | ||
539 | } | ||
540 | } | ||
541 | } | ||
542 | } | ||
543 | |||
544 | @media screen and (max-width: 750px) { | ||
545 | .vjs-theater-control { | ||
546 | display: none; | ||
547 | } | ||
548 | |||
549 | .vjs-dock-text { | ||
550 | font-size: 16px; | ||
551 | } | ||
552 | |||
553 | .vjs-dock-description { | ||
554 | font-size: 9px; | ||
555 | } | ||
556 | |||
557 | .vjs-big-play-button { | 108 | .vjs-big-play-button { |
558 | font-size: 5em; | 109 | font-size: 5em; |
559 | border-width: 3px; | 110 | border-width: 3px; |
@@ -564,11 +115,7 @@ body { | |||
564 | } | 115 | } |
565 | } | 116 | } |
566 | 117 | ||
567 | @media screen and (max-width: 570px) { | 118 | @media screen and (max-width: $screen-width-570) { |
568 | .vjs-dock-text { | ||
569 | font-size: 14px; | ||
570 | } | ||
571 | |||
572 | .vjs-big-play-button { | 119 | .vjs-big-play-button { |
573 | font-size: 4.5em; | 120 | font-size: 4.5em; |
574 | border-width: 2.5px; | 121 | border-width: 2.5px; |
@@ -577,31 +124,9 @@ body { | |||
577 | @include big-play-button-triangle-size(27px); | 124 | @include big-play-button-triangle-size(27px); |
578 | } | 125 | } |
579 | } | 126 | } |
580 | |||
581 | .vjs-peertube { | ||
582 | padding: 0 !important; | ||
583 | |||
584 | .vjs-peertube-displayed { | ||
585 | display: none !important; | ||
586 | } | ||
587 | } | ||
588 | |||
589 | &.vjs-live { | ||
590 | .vjs-duration { | ||
591 | display: none !important; | ||
592 | } | ||
593 | |||
594 | .vjs-peertube { | ||
595 | display: none !important; | ||
596 | } | ||
597 | } | ||
598 | } | 127 | } |
599 | 128 | ||
600 | @media screen and (max-width: 350px) { | 129 | @media screen and (max-width: $screen-width-350) { |
601 | .vjs-dock-text { | ||
602 | font-size: 13px; | ||
603 | } | ||
604 | |||
605 | .vjs-big-play-button { | 130 | .vjs-big-play-button { |
606 | font-size: 3em; | 131 | font-size: 3em; |
607 | border-width: 2px; | 132 | border-width: 2px; |
@@ -610,36 +135,6 @@ body { | |||
610 | @include big-play-button-triangle-size(20px); | 135 | @include big-play-button-triangle-size(20px); |
611 | } | 136 | } |
612 | } | 137 | } |
613 | |||
614 | .vjs-volume-control, | ||
615 | .vjs-next-video, | ||
616 | .vjs-previous-video { | ||
617 | display: none !important; | ||
618 | } | ||
619 | |||
620 | .vjs-peertube-link { | ||
621 | padding: 0 !important; | ||
622 | } | ||
623 | |||
624 | .vjs-settings { | ||
625 | width: 33px; | ||
626 | } | ||
627 | |||
628 | .vjs-control-bar { | ||
629 | > button:first-child { | ||
630 | @include margin-left($first-control-bar-element-margin-left-small-width); | ||
631 | } | ||
632 | } | ||
633 | |||
634 | .vjs-fullscreen-control { | ||
635 | @include margin-right($first-control-bar-element-margin-left-small-width); | ||
636 | } | ||
637 | |||
638 | &.vjs-live { | ||
639 | .vjs-current-time { | ||
640 | display: none !important; | ||
641 | } | ||
642 | } | ||
643 | } | 138 | } |
644 | 139 | ||
645 | // Theater mode is enabled | 140 | // Theater mode is enabled |
@@ -707,13 +202,3 @@ body { | |||
707 | display: block; | 202 | display: block; |
708 | } | 203 | } |
709 | } | 204 | } |
710 | |||
711 | .vjs-no-next-in-playlist { | ||
712 | .vjs-next-video { | ||
713 | cursor: default; | ||
714 | |||
715 | .icon { | ||
716 | background-color: rgba(255, 255, 255, 0.5); | ||
717 | } | ||
718 | } | ||
719 | } | ||
diff --git a/client/src/sass/player/settings-menu.scss b/client/src/sass/player/settings-menu.scss index 9932fc8c8..5a476259e 100644 --- a/client/src/sass/player/settings-menu.scss +++ b/client/src/sass/player/settings-menu.scss | |||
@@ -9,26 +9,6 @@ $setting-transition-easing: ease-out; | |||
9 | 9 | ||
10 | .video-js { | 10 | .video-js { |
11 | 11 | ||
12 | .vjs-settings { | ||
13 | @include disable-outline; | ||
14 | |||
15 | cursor: pointer; | ||
16 | width: 33px; | ||
17 | |||
18 | .vjs-icon-placeholder { | ||
19 | display: inline-block; | ||
20 | width: 17px; | ||
21 | height: 17px; | ||
22 | vertical-align: middle; | ||
23 | background: url('#{$assets-path}/player/images/settings.svg') no-repeat; | ||
24 | background-size: contain; | ||
25 | |||
26 | &::before { | ||
27 | content: ''; | ||
28 | } | ||
29 | } | ||
30 | } | ||
31 | |||
32 | .vjs-settings-sub-menu-title { | 12 | .vjs-settings-sub-menu-title { |
33 | width: 4em; | 13 | width: 4em; |
34 | text-transform: initial; | 14 | text-transform: initial; |