using System; using System.Collections.Generic; namespace ConfusedPolarBear.Plugin.IntroSkipper; /// /// Range of contiguous time. /// public class TimeRange : IComparable { /// /// Initializes a new instance of the class. /// public TimeRange() { Start = 0; End = 0; } /// /// Initializes a new instance of the class. /// /// Time range start. /// Time range end. public TimeRange(double start, double end) { Start = start; End = end; } /// /// Initializes a new instance of the class. /// /// Original TimeRange. public TimeRange(TimeRange original) { Start = original.Start; End = original.End; } /// /// Gets or sets the time range start (in seconds). /// public double Start { get; set; } /// /// Gets or sets the time range end (in seconds). /// public double End { get; set; } /// /// Gets the duration of this time range (in seconds). /// public double Duration => End - Start; /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator ==(TimeRange left, TimeRange right) { return left.Equals(right); } /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator !=(TimeRange left, TimeRange right) { return !left.Equals(right); } /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator <=(TimeRange left, TimeRange right) { return left.CompareTo(right) <= 0; } /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator <(TimeRange left, TimeRange right) { return left.CompareTo(right) < 0; } /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator >=(TimeRange left, TimeRange right) { return left.CompareTo(right) >= 0; } /// /// Comparison operator. /// /// Left TimeRange. /// Right TimeRange. public static bool operator >(TimeRange left, TimeRange right) { return left.CompareTo(right) > 0; } /// /// Compares this TimeRange to another TimeRange. /// /// Other object to compare against. /// A signed integer that indicates whether this instance precedes, follows, or appears in the same position in the sort order as the obj parameter. public int CompareTo(object? obj) { if (obj is not TimeRange tr) { return 0; } return this.Duration.CompareTo(tr.Duration); } /// public override bool Equals(object? obj) { if (obj is null || obj is not TimeRange tr) { return false; } return this.Start == tr.Start && this.Duration == tr.Duration; } /// public override int GetHashCode() { return this.Start.GetHashCode() + this.Duration.GetHashCode(); } } /// /// Time range helpers. /// public static class TimeRangeHelpers { /// /// Finds the longest contiguous time range. /// /// Sorted timestamps to search. /// Maximum distance permitted between contiguous timestamps. /// The longest contiguous time range (if one was found), or null (if none was found). public static TimeRange? FindContiguous(double[] times, double maximumDistance) { if (times.Length == 0) { return null; } Array.Sort(times); var ranges = new List(); var currentRange = new TimeRange(times[0], 0); // For all provided timestamps, check if it is contiguous with its neighbor. for (var i = 0; i < times.Length - 1; i++) { var current = times[i]; var next = times[i + 1]; if (next - current <= maximumDistance) { currentRange.End = next; continue; } ranges.Add(new TimeRange(currentRange)); currentRange.Start = next; } // Find and return the longest contiguous range. ranges.Sort(); return (ranges.Count > 0) ? ranges[0] : null; } }