lower gop size and keyframe interval (#2832)
* lower gop size and keyframe interval * update changelog * fix build using latest dotnet sdk * fixes
This commit is contained in:
6
.github/workflows/artifacts.yml
vendored
6
.github/workflows/artifacts.yml
vendored
@@ -57,7 +57,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
@@ -172,7 +172,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
@@ -229,7 +229,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
|
||||
8
.github/workflows/pr.yml
vendored
8
.github/workflows/pr.yml
vendored
@@ -14,7 +14,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
@@ -36,7 +36,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
@@ -72,7 +72,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
@@ -100,7 +100,7 @@ jobs:
|
||||
- name: Setup dotnet
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: '10.0.102'
|
||||
dotnet-version: '10.0.x'
|
||||
|
||||
- name: Clean
|
||||
run: dotnet clean --configuration Release && dotnet nuget locals all --clear
|
||||
|
||||
@@ -20,11 +20,13 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
||||
- If this feature turns out to be popular, methods to correct the drift may be investigated
|
||||
- Add `ETV_INSTANCE_ID` environment variable to disambiguate EPG data from multiple ErsatzTV instances
|
||||
- When set, the value will be used in channel identifiers before the final `.ersatztv.org`
|
||||
- Show warning message when selecting audio format `aac (latm)` for general streaming use when it is only intended for DVB-C
|
||||
|
||||
### Changed
|
||||
- Move dark/light mode toggle to **Settings** > **UI**
|
||||
- Use latest (non-deprecated) authorization method with Jellyfin API
|
||||
- Replace direct Discord links with new contact page https://ersatztv.org/contact which also includes other options like Matrix
|
||||
- Lower GOP size and keyframe interval from four seconds to two seconds in accordance with HLS2 draft spec recommendations
|
||||
|
||||
### Fixed
|
||||
- Improve stability of playback orders `Shuffle` and `Shuffle in Order` over time
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<AnalysisLevel>latest-Recommended</AnalysisLevel>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
|
||||
@@ -498,7 +498,7 @@ public class GetPlayoutItemProcessByChannelNumberHandler : FFmpegProcessHandler<
|
||||
Option<TimeSpan> maybeDuration = maybeNextStart.Map(s => s - now);
|
||||
|
||||
// limit working ahead on errors to 1 minute
|
||||
if (!request.HlsRealtime && maybeDuration.IfNone(TimeSpan.FromMinutes(2)) > TimeSpan.FromMinutes(1))
|
||||
if (!request.HlsRealtime && await maybeDuration.IfNoneAsync(TimeSpan.FromMinutes(2)) > TimeSpan.FromMinutes(1))
|
||||
{
|
||||
maybeNextStart = now.AddMinutes(1);
|
||||
maybeDuration = TimeSpan.FromMinutes(1);
|
||||
@@ -766,7 +766,7 @@ public class GetPlayoutItemProcessByChannelNumberHandler : FFmpegProcessHandler<
|
||||
.ToListAsync(cancellationToken);
|
||||
|
||||
// always play min(duration to next item, version.Duration)
|
||||
TimeSpan duration = maybeDuration.IfNone(version.Duration);
|
||||
TimeSpan duration = await maybeDuration.IfNoneAsync(version.Duration);
|
||||
if (version.Duration < duration)
|
||||
{
|
||||
duration = version.Duration;
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<AnalysisLevel>latest-Recommended</AnalysisLevel>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
|
||||
@@ -893,7 +893,7 @@ public class FFmpegLibraryProcessService : IFFmpegProcessService
|
||||
playbackSettings.NormalizeColors,
|
||||
playbackSettings.Deinterlace);
|
||||
|
||||
var frameRate = playbackSettings.FrameRate.IfNone(new FrameRate("24"));
|
||||
var frameRate = await playbackSettings.FrameRate.IfNoneAsync(new FrameRate("24"));
|
||||
|
||||
var ffmpegVideoStream = new VideoStream(
|
||||
0,
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
<AnalysisLevel>latest-Recommended</AnalysisLevel>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
||||
@@ -32,8 +32,8 @@ public class OutputFormatConcatHls : IPipelineStep
|
||||
|
||||
return
|
||||
[
|
||||
"-g", $"{OutputFormatHls.SegmentSeconds}/2",
|
||||
"-force_key_frames", $"expr:gte(t,n_forced*{OutputFormatHls.SegmentSeconds}/2)",
|
||||
"-g", $"{OutputFormatHls.KeyframeIntervalSeconds}",
|
||||
"-force_key_frames", $"expr:gte(t,n_forced*{OutputFormatHls.KeyframeIntervalSeconds})",
|
||||
"-f", "hls",
|
||||
"-hls_segment_type", segmentType,
|
||||
//"-hls_init_time", "2",
|
||||
|
||||
@@ -6,6 +6,7 @@ namespace ErsatzTV.FFmpeg.OutputFormat;
|
||||
public class OutputFormatHls : IPipelineStep
|
||||
{
|
||||
public const int SegmentSeconds = 4;
|
||||
public const int KeyframeIntervalSeconds = 2;
|
||||
|
||||
private readonly FrameState _desiredState;
|
||||
private readonly bool _isFirstTranscode;
|
||||
@@ -55,7 +56,7 @@ public class OutputFormatHls : IPipelineStep
|
||||
|
||||
int gop = _oneSecondGop
|
||||
? (int)Math.Round(frameRate.ParsedFrameRate)
|
||||
: (int)Math.Round(frameRate.ParsedFrameRate * SegmentSeconds);
|
||||
: (int)Math.Round(frameRate.ParsedFrameRate * KeyframeIntervalSeconds);
|
||||
|
||||
List<string> result = [];
|
||||
|
||||
@@ -64,8 +65,8 @@ public class OutputFormatHls : IPipelineStep
|
||||
result.AddRange(
|
||||
[
|
||||
"-g", $"{gop}",
|
||||
"-keyint_min", $"{(int)Math.Round(frameRate.ParsedFrameRate * SegmentSeconds)}",
|
||||
"-force_key_frames", $"expr:gte(t,n_forced*{SegmentSeconds})"
|
||||
"-keyint_min", $"{(int)Math.Round(frameRate.ParsedFrameRate * KeyframeIntervalSeconds)}",
|
||||
"-force_key_frames", $"expr:gte(t,n_forced*{KeyframeIntervalSeconds})"
|
||||
]);
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<IsPackable>false</IsPackable>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
@@ -48,25 +48,22 @@ public static class DbInitializer
|
||||
if (resource != null)
|
||||
{
|
||||
using var reader = new StreamReader(resource);
|
||||
while (!reader.EndOfStream)
|
||||
string line;
|
||||
while ((line = await reader.ReadLineAsync(cancellationToken)) is not null)
|
||||
{
|
||||
string line = await reader.ReadLineAsync(cancellationToken);
|
||||
if (line != null)
|
||||
string[] split = line.Split("|");
|
||||
if (split.Length == 5)
|
||||
{
|
||||
string[] split = line.Split("|");
|
||||
if (split.Length == 5)
|
||||
var languageCode = new LanguageCode
|
||||
{
|
||||
var languageCode = new LanguageCode
|
||||
{
|
||||
ThreeCode1 = split[0],
|
||||
ThreeCode2 = split[1],
|
||||
TwoCode = split[2],
|
||||
EnglishName = split[3],
|
||||
FrenchName = split[4]
|
||||
};
|
||||
ThreeCode1 = split[0],
|
||||
ThreeCode2 = split[1],
|
||||
TwoCode = split[2],
|
||||
EnglishName = split[3],
|
||||
FrenchName = split[4]
|
||||
};
|
||||
|
||||
await context.LanguageCodes.AddAsync(languageCode, cancellationToken);
|
||||
}
|
||||
await context.LanguageCodes.AddAsync(languageCode, cancellationToken);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<AnalysisLevel>latest-Recommended</AnalysisLevel>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
|
||||
@@ -21,9 +21,9 @@ public class LanguageCodeCache : ILanguageCodeCache
|
||||
if (resource != null)
|
||||
{
|
||||
using var reader = new StreamReader(resource);
|
||||
while (!reader.EndOfStream)
|
||||
string line;
|
||||
while ((line = await reader.ReadLineAsync(cancellationToken)) is not null)
|
||||
{
|
||||
string line = await reader.ReadLineAsync(cancellationToken);
|
||||
if (string.IsNullOrWhiteSpace(line))
|
||||
{
|
||||
continue;
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
<TargetFramework>net10.0</TargetFramework>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<IsPackable>false</IsPackable>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
<UserSecretsId>729e6271-c307-43c8-8e36-1b36c39f6de2</UserSecretsId>
|
||||
<AnalysisLevel>latest-Recommended</AnalysisLevel>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
<TypeScriptToolsVersion>Latest</TypeScriptToolsVersion>
|
||||
<IsPackable>false</IsPackable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<NoWarn>VSTHRD200</NoWarn>
|
||||
<NoWarn>VSTHRD200,CA1873</NoWarn>
|
||||
<IncludeAllContentForSelfExtract>true</IncludeAllContentForSelfExtract>
|
||||
<Configurations>Debug;Release;Debug No Sync</Configurations>
|
||||
<Platforms>AnyCPU</Platforms>
|
||||
|
||||
@@ -282,8 +282,7 @@
|
||||
<div class="d-flex">
|
||||
<MudText>Format</MudText>
|
||||
</div>
|
||||
<MudSelect @bind-Value="_model.AudioFormat" For="@(() => _model.AudioFormat)">
|
||||
<MudSelectItem Value="@FFmpegProfileAudioFormat.Aac">aac</MudSelectItem>
|
||||
<MudSelect @bind-Value="_model.AudioFormat" For="@(() => _model.AudioFormat)" HelperText="@(_model.AudioFormat is FFmpegProfileAudioFormat.AacLatm ? "aac (latm) is ONLY intended for DVB-C; anything else should use aac instead which uses ADTS" : string.Empty)"> <MudSelectItem Value="@FFmpegProfileAudioFormat.Aac">aac</MudSelectItem>
|
||||
<MudSelectItem Value="@FFmpegProfileAudioFormat.Ac3">ac3</MudSelectItem>
|
||||
<MudSelectItem Value="@FFmpegProfileAudioFormat.AacLatm">aac (latm)</MudSelectItem>
|
||||
</MudSelect>
|
||||
|
||||
@@ -9,7 +9,7 @@ RUN apt-get update && \
|
||||
rm -rf /var/lib/apt/lists/*
|
||||
|
||||
# https://hub.docker.com/_/microsoft-dotnet
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0.102-noble-amd64 AS build
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0-noble-amd64 AS build
|
||||
RUN apt-get update && apt-get install -y ca-certificates gnupg default-jre-headless python3-pip
|
||||
WORKDIR /source
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ FROM --platform=linux/arm/v7 ghcr.io/ersatztv/ersatztv-ffmpeg:7.1.1 AS runtime-b
|
||||
COPY --from=dotnet-runtime /usr/share/dotnet /usr/share/dotnet
|
||||
|
||||
# https://hub.docker.com/_/microsoft-dotnet
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0.102-noble-amd64 AS build
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0-noble-amd64 AS build
|
||||
RUN apt-get update && apt-get install -y ca-certificates gnupg
|
||||
WORKDIR /source
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ FROM --platform=linux/arm64 ghcr.io/ersatztv/ersatztv-ffmpeg:7.1.1 AS runtime-ba
|
||||
COPY --from=dotnet-runtime /usr/share/dotnet /usr/share/dotnet
|
||||
|
||||
# https://hub.docker.com/_/microsoft-dotnet
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0.102-noble-arm64v8 AS build
|
||||
FROM mcr.microsoft.com/dotnet/sdk:10.0-noble-arm64v8 AS build
|
||||
RUN apt-get update && apt-get install -y ca-certificates gnupg
|
||||
WORKDIR /source
|
||||
|
||||
|
||||
Reference in New Issue
Block a user