feat: mpv player integration

This commit is contained in:
4gray committed 2023-03-23 23:41:13 +01:00
1 parent c7a2b3f6aa
commit 21b9c8f804
8 files changed
+102 -11

No files matched your search

@@ -25,6 +25,7 @@
[class.hide-captions]="!playerSettings.showCaptions"
></app-vjs-player>
</ng-container>
<!-- default html player component -->
<app-html-video-player
*ngIf="playerSettings.player === 'html5'"
@@ -33,6 +34,13 @@
>
</app-html-video-player>
<ng-container *ngIf="(activeChannel$ | async) && playerSettings.player === 'mpv'">
<div class="mpv-player">
<img src="./assets/images/custom-player.png" />
<p>The channel is played in a separate window in the MPV player. (<a [routerLink] style="cursor: pointer;" (click)="openUrl('https://github.com/4gray/iptvnator/wiki/What-is-mpv-video-player-and-how-to-install-it-on-different-operating-systems%3F')">Installation instructions</a>)</p>
</div>
</ng-container>
<!-- channel overlay -->
<app-info-overlay
[channel]="activeChannel$ | async"
@@ -22,3 +22,17 @@
min-width: 200px;
}
}
@media (prefers-color-scheme: dark) {
.mpv-player {
display: flex;
margin-top: 50px;
flex-direction: column;
align-items: center;
img {
filter: invert(100%);
width: 400px;
}
}
}
@@ -8,6 +8,7 @@ import {
OnDestroy,
OnInit,
} from '@angular/core';
import { MatSnackBar } from '@angular/material/snack-bar';
import { ActivatedRoute } from '@angular/router';
import { Store } from '@ngrx/store';
import { StorageMap } from '@ngx-pwa/local-storage';
@@ -20,6 +21,7 @@ import {
} from 'rxjs';
import { Channel } from '../../../../../shared/channel.interface';
import {
ERROR,
PLAYLIST_PARSE_BY_URL,
PLAYLIST_PARSE_RESPONSE,
} from '../../../../../shared/ipc-commands';
@@ -73,6 +75,14 @@ export class VideoPlayerComponent implements OnInit, OnDestroy {
/** IPC Renderer commands list with callbacks */
commandsList = [
{
id: ERROR,
execute: (response: { message: string }): void => {
this.snackBar.open(response.message, '', {
duration: 3100,
});
},
},
{
id: PLAYLIST_PARSE_RESPONSE,
execute: (response: { payload: Playlist }): void => {
@@ -109,6 +119,7 @@ export class VideoPlayerComponent implements OnInit, OnDestroy {
private ngZone: NgZone,
private overlay: Overlay,
private playlistsService: PlaylistsService,
private snackBar: MatSnackBar,
private storage: StorageMap,
private store: Store
) {}
@@ -217,4 +228,8 @@ export class VideoPlayerComponent implements OnInit, OnDestroy {
this.overlayRef.addPanelClass('epg-overlay');
this.overlayRef.attach(componentPortal);
}
openUrl(url: string) {
window.open(url, '_blank');
}
}
+4
View File
@@ -47,6 +47,10 @@ export class SettingsComponent implements OnInit {
id: VideoPlayer.VideoJs,
label: 'VideoJs Player',
},
{
id: VideoPlayer.MPV,
label: 'MPV Player',
},
];
/** Current version of the app */
+1
View File
@@ -8,6 +8,7 @@ import { Theme } from './theme.enum';
export enum VideoPlayer {
VideoJs = 'videojs',
Html5Player = 'html5',
MPV = 'mpv',
}
/**
+20
View File
@@ -4,14 +4,19 @@ import { MatSnackBar } from '@angular/material/snack-bar';
import { Router } from '@angular/router';
import { Actions, createEffect, ofType } from '@ngrx/effects';
import { Store } from '@ngrx/store';
import { StorageMap } from '@ngx-pwa/local-storage';
import { TranslateService } from '@ngx-translate/core';
import { firstValueFrom } from 'rxjs';
import { combineLatestWith, map, switchMap, tap } from 'rxjs/operators';
import {
CHANNEL_SET_USER_AGENT,
EPG_GET_PROGRAM,
OPEN_MPV_PLAYER,
} from '../../../shared/ipc-commands';
import { DataService } from '../services/data.service';
import { PlaylistsService } from '../services/playlists.service';
import { Settings, VideoPlayer } from '../settings/settings.interface';
import { STORE_KEY } from '../shared/enums/store-keys.enum';
import * as PlaylistActions from './actions';
import {
selectActivePlaylistId,
@@ -72,6 +77,20 @@ export class PlaylistEffects {
userAgent: channel.http['user-agent'],
});
}
firstValueFrom(this.storage.get(STORE_KEY.Settings)).then(
(settings: Settings) => {
if (
settings &&
Object.keys(settings).length > 0 &&
settings.player === VideoPlayer.MPV
)
this.dataService.sendIpcEvent(OPEN_MPV_PLAYER, {
url: channel.url,
});
}
);
return PlaylistActions.setActiveChannelSuccess({
channel: action.channel,
});
@@ -230,6 +249,7 @@ export class PlaylistEffects {
private dataService: DataService,
private router: Router,
private snackBar: MatSnackBar,
private storage: StorageMap,
private store: Store,
private translate: TranslateService
) {}