1
0
Fork 0
mirror of https://github.com/jellyfin/jellyfin-web synced 2025-03-30 19:56:21 +00:00

Merge pull request #4263 from dmitrylyzo/fix-change-track

This commit is contained in:
Bill Thornton 2023-01-12 17:39:02 -05:00 committed by GitHub
commit 9139153d16
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 81 additions and 45 deletions

View file

@ -11,6 +11,7 @@ import { appHost } from '../apphost';
import Screenfull from 'screenfull';
import ServerConnections from '../ServerConnections';
import alert from '../alert';
import { includesAny } from '../../utils/container.ts';
const UNLIMITED_ITEMS = -1;
@ -1306,6 +1307,7 @@ class PlaybackManager {
return false;
}
const container = mediaSource.Container.toLowerCase();
const codec = (mediaStream.Codec || '').toLowerCase();
if (!codec) {
@ -1314,22 +1316,11 @@ class PlaybackManager {
const profiles = deviceProfile.DirectPlayProfiles || [];
return profiles.filter(function (p) {
if (p.Type === 'Video') {
if (!p.AudioCodec) {
return true;
}
// This is an exclusion filter
if (p.AudioCodec.indexOf('-') === 0) {
return p.AudioCodec.toLowerCase().indexOf(codec) === -1;
}
return p.AudioCodec.toLowerCase().indexOf(codec) !== -1;
}
return false;
}).length > 0;
return profiles.some(function (p) {
return p.Type === 'Video'
&& includesAny((p.Container || '').toLowerCase(), container)
&& includesAny((p.AudioCodec || '').toLowerCase(), codec);
});
}
self.setAudioStreamIndex = function (index, player) {

View file

@ -28,8 +28,9 @@ import itemHelper from '../../components/itemHelper';
import Screenfull from 'screenfull';
import globalize from '../../scripts/globalize';
import ServerConnections from '../../components/ServerConnections';
import profileBuilder from '../../scripts/browserDeviceProfile';
import profileBuilder, { canPlaySecondaryAudio } from '../../scripts/browserDeviceProfile';
import { getIncludeCorsCredentials } from '../../scripts/settings/webSettings';
import { includesAny } from '../../utils/container.ts';
/**
* Returns resolved URL.
@ -602,7 +603,7 @@ function tryRemoveElement(elem) {
/**
* @private
*/
isAudioStreamSupported(stream, deviceProfile) {
isAudioStreamSupported(stream, deviceProfile, container) {
const codec = (stream.Codec || '').toLowerCase();
if (!codec) {
@ -616,17 +617,11 @@ function tryRemoveElement(elem) {
const profiles = deviceProfile.DirectPlayProfiles || [];
return profiles.filter(function (p) {
if (p.Type === 'Video') {
if (!p.AudioCodec) {
return true;
}
return p.AudioCodec.toLowerCase().includes(codec);
}
return false;
}).length > 0;
return profiles.some(function (p) {
return p.Type === 'Video'
&& includesAny((p.Container || '').toLowerCase(), container)
&& includesAny((p.AudioCodec || '').toLowerCase(), codec);
});
}
/**
@ -635,8 +630,11 @@ function tryRemoveElement(elem) {
getSupportedAudioStreams() {
const profile = this.#lastProfile;
return getMediaStreamAudioTracks(this._currentPlayOptions.mediaSource).filter((stream) => {
return this.isAudioStreamSupported(stream, profile);
const mediaSource = this._currentPlayOptions.mediaSource;
const container = mediaSource.Container.toLowerCase();
return getMediaStreamAudioTracks(mediaSource).filter((stream) => {
return this.isAudioStreamSupported(stream, profile, container);
});
}
@ -1559,15 +1557,9 @@ function tryRemoveElement(elem) {
}
canSetAudioStreamIndex() {
if (browser.tizen || browser.orsay) {
return true;
}
const video = this.#mediaElement;
if (video) {
if (video.audioTracks) {
return true;
}
return canPlaySecondaryAudio(video);
}
return false;

View file

@ -353,6 +353,23 @@ import browser from './browser';
return 2;
}
/**
* Checks if the web engine supports secondary audio.
* @param {HTMLVideoElement} videoTestElement The video test element
* @returns {boolean} _true_ if the web engine supports secondary audio.
*/
export function canPlaySecondaryAudio(videoTestElement) {
// We rely on HTMLMediaElement.audioTracks
// It works in Chrome 79+ with "Experimental Web Platform features" enabled
return !!videoTestElement.audioTracks
// It doesn't work in Firefox 108 even with "media.track.enabled" enabled (it only sees the first audio track)
&& !browser.firefox
// It seems to work on Tizen 5.5+ (2020, Chrome 69+). See https://developer.tizen.org/forums/web-application-development/video-tag-not-work-audiotracks
&& (browser.tizenVersion >= 5.5 || !browser.tizen)
// Assume webOS 5+ (2020, Chrome 68+) supports secondary audio like Tizen 5.5+
&& (browser.web0sVersion >= 5.0 || !browser.web0sVersion);
}
export default function (options) {
options = options || {};
@ -752,13 +769,7 @@ import browser from './browser';
profile.CodecProfiles = [];
// We rely on HTMLMediaElement.audioTracks
// It works in Chrome 79+ with "Experimental Web Platform features" enabled
// It doesn't work in Firefox 108 even with "media.track.enabled" enabled (it only sees the first audio track)
// It seems to work on Tizen 5.5+ (Chrome 69+). See https://developer.tizen.org/forums/web-application-development/video-tag-not-work-audiotracks
const supportsSecondaryAudio = !!videoTestElement.audioTracks
&& !browser.firefox
&& (browser.tizenVersion >= 5.5 || !browser.tizen);
const supportsSecondaryAudio = canPlaySecondaryAudio(videoTestElement);
const aacCodecProfileConditions = [];

42
src/utils/container.ts Normal file
View file

@ -0,0 +1,42 @@
/**
* Checks if the list includes any value from the search.
* @param list The list to search in.
* @param search The values to search.
* @returns _true_ if the list includes any value from the search.
* @remarks The list (string) can start with '-', in which case the logic is inverted.
*/
export function includesAny(list: string | string[] | null | undefined, search: string | string[]): boolean {
if (!list) {
return true;
}
let inverseMatch = false;
if (typeof list === 'string') {
if (list.startsWith('-')) {
inverseMatch = true;
list = list.substring(1);
}
list = list.split(',');
}
list = list.filter(i => i);
if (!list.length) {
return true;
}
if (typeof search === 'string') {
search = search.split(',');
}
search = search.filter(i => i);
/* eslint-disable-next-line @typescript-eslint/no-non-null-assertion */
if (search.some(s => list!.includes(s))) {
return !inverseMatch;
}
return inverseMatch;
}