Compare commits
2 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
d6280f3ce8 | ||
|
|
43e002fcdd |
@@ -3,8 +3,8 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net9.0</TargetFramework>
|
<TargetFramework>net9.0</TargetFramework>
|
||||||
<RootNamespace>Jellyfin.Plugin.CinemaTrailers4Jellyfins</RootNamespace>
|
<RootNamespace>Jellyfin.Plugin.CinemaTrailers4Jellyfins</RootNamespace>
|
||||||
<AssemblyVersion>1.0.0.15</AssemblyVersion>
|
<AssemblyVersion>1.0.0.16</AssemblyVersion>
|
||||||
<FileVersion>1.0.0.15</FileVersion>
|
<FileVersion>1.0.0.16</FileVersion>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
<GenerateDocumentationFile>false</GenerateDocumentationFile>
|
<GenerateDocumentationFile>false</GenerateDocumentationFile>
|
||||||
<TreatWarningsAsErrors>false</TreatWarningsAsErrors>
|
<TreatWarningsAsErrors>false</TreatWarningsAsErrors>
|
||||||
|
|||||||
@@ -90,31 +90,37 @@ namespace Jellyfin.Plugin.CinemaTrailers4Jellyfins.Services
|
|||||||
.GetManifestAsync($"https://www.youtube.com/watch?v={key}", ct)
|
.GetManifestAsync($"https://www.youtube.com/watch?v={key}", ct)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
// Muxed streams include audio+video in one file. YouTube rarely serves them
|
// Best video-only stream at or below the height limit. MP4 (H.264) is preferred for
|
||||||
// anymore, but use one when it exists since it needs no merge.
|
// client compatibility; any container is the fallback.
|
||||||
|
var videoStreams = manifest.GetVideoOnlyStreams().ToList();
|
||||||
|
var audioStreams = manifest.GetAudioOnlyStreams().ToList();
|
||||||
|
var mp4Video = videoStreams.Where(s => s.Container == Container.Mp4).ToList();
|
||||||
|
var video = videoStreams.Count > 0
|
||||||
|
? PickByHeight(mp4Video.Count > 0 ? mp4Video : videoStreams, preferredHeight)
|
||||||
|
: null;
|
||||||
|
|
||||||
|
// Muxed streams (audio+video in one file) need no merge, but YouTube only serves
|
||||||
|
// them at 360p. Use one only when the separate streams can't do better.
|
||||||
var muxedStreams = manifest.GetMuxedStreams().ToList();
|
var muxedStreams = manifest.GetMuxedStreams().ToList();
|
||||||
if (muxedStreams.Count > 0)
|
if (muxedStreams.Count > 0)
|
||||||
{
|
{
|
||||||
var muxed = PickByHeight(muxedStreams, preferredHeight);
|
var muxed = PickByHeight(muxedStreams, preferredHeight);
|
||||||
_logger.LogInformation(
|
if (video == null || audioStreams.Count == 0
|
||||||
"|CinemaTrailers4Jellyfins| Downloading {Key} at {Quality} (muxed) to {Path}",
|
|| muxed.VideoQuality.MaxHeight >= video.VideoQuality.MaxHeight)
|
||||||
key, muxed.VideoQuality.Label, outputPath);
|
{
|
||||||
await youtube.Videos.Streams.DownloadAsync(muxed, outputPath, cancellationToken: ct).ConfigureAwait(false);
|
_logger.LogInformation(
|
||||||
return true;
|
"|CinemaTrailers4Jellyfins| Downloading {Key} at {Quality} (muxed) to {Path}",
|
||||||
|
key, muxed.VideoQuality.Label, outputPath);
|
||||||
|
await youtube.Videos.Streams.DownloadAsync(muxed, outputPath, cancellationToken: ct).ConfigureAwait(false);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Otherwise download the best video-only and audio-only streams and merge them.
|
if (video == null || audioStreams.Count == 0)
|
||||||
// MP4 (H.264/AAC) is preferred for client compatibility; any container is the fallback.
|
|
||||||
var videoStreams = manifest.GetVideoOnlyStreams().ToList();
|
|
||||||
var audioStreams = manifest.GetAudioOnlyStreams().ToList();
|
|
||||||
if (videoStreams.Count == 0 || audioStreams.Count == 0)
|
|
||||||
{
|
{
|
||||||
_logger.LogWarning("|CinemaTrailers4Jellyfins| No usable video/audio streams for {Key}.", key);
|
_logger.LogWarning("|CinemaTrailers4Jellyfins| No usable video/audio streams for {Key}.", key);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
var mp4Video = videoStreams.Where(s => s.Container == Container.Mp4).ToList();
|
|
||||||
var video = PickByHeight(mp4Video.Count > 0 ? mp4Video : videoStreams, preferredHeight);
|
|
||||||
var mp4Audio = audioStreams.Where(s => s.Container == Container.Mp4).ToList();
|
var mp4Audio = audioStreams.Where(s => s.Container == Container.Mp4).ToList();
|
||||||
var audio = (mp4Audio.Count > 0 ? mp4Audio : audioStreams).GetWithHighestBitrate();
|
var audio = (mp4Audio.Count > 0 ? mp4Audio : audioStreams).GetWithHighestBitrate();
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
---
|
---
|
||||||
version: 1.0.0.15
|
version: 1.0.0.16
|
||||||
name: CinemaTrailers4Jellyfins
|
name: CinemaTrailers4Jellyfins
|
||||||
guid: b581493e-1046-40ed-b6dc-cb8027624984
|
guid: b581493e-1046-40ed-b6dc-cb8027624984
|
||||||
description: >
|
description: >
|
||||||
@@ -12,10 +12,9 @@ category: General
|
|||||||
owner: 514mart
|
owner: 514mart
|
||||||
targetAbi: 10.11.0.0
|
targetAbi: 10.11.0.0
|
||||||
changelog:
|
changelog:
|
||||||
- Trailer Languages now also checks the original language of the movie or
|
- The built-in downloader no longer picks YouTube's 360p combined file
|
||||||
show. Before, only the trailer's own language tag was checked, and
|
when separate video and audio streams give a better picture. This
|
||||||
TMDB often tags subtitled foreign trailers as English, so Korean,
|
mostly showed up when yt-dlp failed and the built-in downloader took over
|
||||||
Chinese or Japanese trailers got through
|
|
||||||
|
|
||||||
dotnetProjects:
|
dotnetProjects:
|
||||||
- name: Jellyfin.Plugin.CinemaTrailers4Jellyfins
|
- name: Jellyfin.Plugin.CinemaTrailers4Jellyfins
|
||||||
|
|||||||
@@ -8,6 +8,14 @@
|
|||||||
"owner": "514mart",
|
"owner": "514mart",
|
||||||
"imageUrl": "https://www.git.quarantinedstudio.com/mvezina/CinemaTrailers4Jellyfins/raw/branch/main/Jellyfin.Plugin.CinemaTrailers4Jellyfins/Images/logo.svg",
|
"imageUrl": "https://www.git.quarantinedstudio.com/mvezina/CinemaTrailers4Jellyfins/raw/branch/main/Jellyfin.Plugin.CinemaTrailers4Jellyfins/Images/logo.svg",
|
||||||
"versions": [
|
"versions": [
|
||||||
|
{
|
||||||
|
"checksum": "211f58d992857f9e91263293306fbd0d",
|
||||||
|
"changelog": "- Trailer Languages now also checks the original language of the movie or show. Before, only the trailer's own language tag was checked, and TMDB often tags subtitled foreign trailers as English, so Korean, Chinese or Japanese trailers got through\n",
|
||||||
|
"targetAbi": "10.11.0.0",
|
||||||
|
"sourceUrl": "https://www.git.quarantinedstudio.com/mvezina/CinemaTrailers4Jellyfins/releases/download/v1.0.0.15/cinematrailers4jellyfins_1.0.0.15.zip",
|
||||||
|
"timestamp": "2026-10-05T22:28:03Z",
|
||||||
|
"version": "1.0.0.15"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"checksum": "10ecbc35b84e98bade61576bbfc41864",
|
"checksum": "10ecbc35b84e98bade61576bbfc41864",
|
||||||
"changelog": "- When yt-dlp fails part-way, its partial download files (.part, .ytdl, separate video/audio) are now deleted instead of being left in the trailer folder\n",
|
"changelog": "- When yt-dlp fails part-way, its partial download files (.part, .ytdl, separate video/audio) are now deleted instead of being left in the trailer folder\n",
|
||||||
|
|||||||
Reference in New Issue
Block a user