* upgrade sdk * fix warnings in ersatztv.ffmpeg * fix warnings in ersatztv.core * fix warnings in ersatztv.infrastructure * fix warnings in ersatztv.application * disable analysis for migrations projects * fix warnings in ersatztv.scanner * fix warnings in ersatztv * upgrade project framework * update github actions and dockerfiles
80 lines
2.5 KiB
C#
80 lines
2.5 KiB
C#
namespace ErsatzTV.Core.FFmpeg;
|
|
|
|
public static class WatermarkCalculator
|
|
{
|
|
public static List<FadePoint> CalculateFadePoints(
|
|
DateTimeOffset itemStartTime,
|
|
TimeSpan inPoint,
|
|
TimeSpan outPoint,
|
|
Option<TimeSpan> streamSeek,
|
|
int frequencyMinutes,
|
|
int durationSeconds)
|
|
{
|
|
var result = new List<FadePoint>();
|
|
|
|
TimeSpan duration = outPoint - inPoint;
|
|
DateTimeOffset itemFinishTime = itemStartTime + duration;
|
|
|
|
DateTimeOffset start = itemStartTime.AddMinutes(-16);
|
|
|
|
// find the next whole minute
|
|
if (start.Second > 0 || start.Millisecond > 0)
|
|
{
|
|
start = start.AddMinutes(1);
|
|
start = start.AddSeconds(-start.Second);
|
|
start = start.AddMilliseconds(-start.Millisecond);
|
|
}
|
|
|
|
DateTimeOffset finish = itemFinishTime;
|
|
|
|
// find the previous whole minute
|
|
if (finish.Second > 0 || finish.Millisecond > 0)
|
|
{
|
|
finish = finish.AddSeconds(-finish.Second);
|
|
finish = finish.AddMilliseconds(-finish.Millisecond);
|
|
}
|
|
|
|
DateTimeOffset current = start;
|
|
while (current <= finish)
|
|
{
|
|
current = current.AddMinutes(1);
|
|
if (current.Minute % frequencyMinutes == 0)
|
|
{
|
|
TimeSpan fadeInTime = inPoint + (current - itemStartTime);
|
|
|
|
result.Add(new FadeInPoint(fadeInTime));
|
|
result.Add(new FadeOutPoint(fadeInTime.Add(TimeSpan.FromSeconds(durationSeconds))));
|
|
}
|
|
}
|
|
|
|
// if we're seeking, subtract the seek from each item and return that
|
|
foreach (TimeSpan ss in streamSeek)
|
|
{
|
|
result = result.Map(fp => fp with { Time = fp.Time - ss }).ToList();
|
|
}
|
|
|
|
// trim points that have already passed
|
|
result.RemoveAll(fp => fp.Time < TimeSpan.Zero);
|
|
|
|
// trim points that are past the end
|
|
result.RemoveAll(fp => fp.Time >= outPoint);
|
|
|
|
if (result.Count != 0)
|
|
{
|
|
for (var i = 0; i < result.Count; i++)
|
|
{
|
|
result[i].EnableStart = i == 0 ? TimeSpan.Zero : result[i - 1].Time.Add(TimeSpan.FromSeconds(1));
|
|
}
|
|
|
|
for (var i = 0; i < result.Count; i++)
|
|
{
|
|
result[i].EnableFinish = i == result.Count - 1
|
|
? outPoint
|
|
: result[i + 1].Time.Subtract(TimeSpan.FromSeconds(1));
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
}
|