Explorar o código

Merge branch 'dev' of https://github.com/MediaBrowser/MediaBrowser into dev

Tavares André %!s(int64=10) %!d(string=hai) anos
pai
achega
428dfd183d

+ 2 - 2
MediaBrowser.Api/Playback/BaseStreamingService.cs

@@ -148,7 +148,7 @@ namespace MediaBrowser.Api.Playback
         }
 
         protected readonly CultureInfo UsCulture = new CultureInfo("en-US");
-        private readonly long _slowSeekTicks = TimeSpan.FromSeconds(2).Ticks;
+        private readonly long _slowSeekTicks = TimeSpan.FromSeconds(0).Ticks;
 
         /// <summary>
         /// Gets the fast seek command line parameter.
@@ -177,7 +177,7 @@ namespace MediaBrowser.Api.Playback
         {
             var time = request.StartTimeTicks ?? 0;
 
-            if (time > _slowSeekTicks)
+            if (time > _slowSeekTicks && _slowSeekTicks > 0)
             {
                 return string.Format("-ss {0}", MediaEncoder.GetTimeParameter(_slowSeekTicks));
             }

+ 71 - 5
MediaBrowser.Api/Playback/Hls/DynamicHlsService.cs

@@ -13,6 +13,7 @@ using MediaBrowser.Model.IO;
 using MediaBrowser.Model.Serialization;
 using ServiceStack;
 using System;
+using System.Collections.Concurrent;
 using System.Collections.Generic;
 using System.Globalization;
 using System.IO;
@@ -156,12 +157,14 @@ namespace MediaBrowser.Api.Playback.Hls
                         {
                             ApiEntryPoint.Instance.KillTranscodingJobs(request.DeviceId, request.PlaySessionId, p => false);
 
+                            await ReadSegmentLengths(playlistPath).ConfigureAwait(false);
+
                             if (currentTranscodingIndex.HasValue)
                             {
                                 DeleteLastFile(playlistPath, segmentExtension, 0);
                             }
 
-                            request.StartTimeTicks = GetSeekPositionTicks(state, requestedIndex);
+                            request.StartTimeTicks = GetSeekPositionTicks(state, playlistPath, requestedIndex);
 
                             job = await StartFfMpeg(state, playlistPath, cancellationTokenSource).ConfigureAwait(false);
                         }
@@ -199,11 +202,73 @@ namespace MediaBrowser.Api.Playback.Hls
             return await GetSegmentResult(playlistPath, segmentPath, requestedIndex, segmentLength, job, cancellationToken).ConfigureAwait(false);
         }
 
-        private long GetSeekPositionTicks(StreamState state, int requestedIndex)
+        private static readonly ConcurrentDictionary<string, double> SegmentLengths = new ConcurrentDictionary<string, double>(StringComparer.OrdinalIgnoreCase);
+        private async Task ReadSegmentLengths(string playlist)
         {
-            var startSeconds = requestedIndex * state.SegmentLength;
-            var position = TimeSpan.FromSeconds(startSeconds).Ticks;
+            try
+            {
+                using (var fileStream = GetPlaylistFileStream(playlist))
+                {
+                    using (var reader = new StreamReader(fileStream))
+                    {
+                        double duration = -1;
+
+                        while (!reader.EndOfStream)
+                        {
+                            var text = await reader.ReadLineAsync().ConfigureAwait(false);
+
+                            if (text.StartsWith("#EXTINF", StringComparison.OrdinalIgnoreCase))
+                            {
+                                var parts = text.Split(new[] { ':' }, 2);
+                                if (parts.Length == 2)
+                                {
+                                    var time = parts[1].Trim(new[] { ',' }).Trim();
+                                    double timeValue;
+                                    if (double.TryParse(time, NumberStyles.Any, CultureInfo.InvariantCulture, out timeValue))
+                                    {
+                                        duration = timeValue;
+                                        continue;
+                                    }
+                                }
+                            }
+                            else if (duration != -1)
+                            {
+                                SegmentLengths.AddOrUpdate(text, duration, (k, v) => duration);
+                                Logger.Debug("Added segment length of {0} for {1}", duration, text);
+                            }
+
+                            duration = -1;
+                        }
+                    }
+                }
+            }
+            catch (FileNotFoundException)
+            {
+                
+            }
+        }
 
+        private long GetSeekPositionTicks(StreamState state, string playlist, int requestedIndex)
+        {
+            double startSeconds = 0;
+
+            for (var i = 0; i < requestedIndex; i++)
+            {
+                var segmentPath = GetSegmentPath(playlist, i);
+
+                double length;
+                if (SegmentLengths.TryGetValue(Path.GetFileName(segmentPath), out length))
+                {
+                    Logger.Debug("Found segment length of {0} for index {1}", length, i);
+                    startSeconds += length;
+                }
+                else
+                {
+                    startSeconds += state.SegmentLength;
+                }
+            }
+
+            var position = TimeSpan.FromSeconds(startSeconds).Ticks;
             return position;
         }
 
@@ -693,7 +758,7 @@ namespace MediaBrowser.Api.Playback.Hls
             }
 
             var keyFrameArg = string.Format(" -force_key_frames expr:gte(t,n_forced*{0})",
-                state.SegmentLength.ToString(UsCulture));
+                1.ToString(UsCulture));
 
             var hasGraphicalSubs = state.SubtitleStream != null && !state.SubtitleStream.IsTextSubtitleStream;
 
@@ -728,6 +793,7 @@ namespace MediaBrowser.Api.Playback.Hls
             {
                 var startTime = state.Request.StartTimeTicks ?? 0;
                 var durationSeconds = ApiEntryPoint.Instance.GetEncodingOptions().ThrottleThresholdInSeconds;
+
                 var endTime = startTime + TimeSpan.FromSeconds(durationSeconds).Ticks;
                 endTime = Math.Min(endTime, state.RunTimeTicks.Value);
 

+ 0 - 1
MediaBrowser.WebDashboard/Api/PackageCreator.cs

@@ -619,7 +619,6 @@ namespace MediaBrowser.WebDashboard.Api
                                 "scheduledtaskpage.js",
                                 "scheduledtaskspage.js",
                                 "search.js",
-                                "supporterkeypage.js",
                                 "syncactivity.js",
                                 "syncsettings.js",
                                 "thememediaplayer.js",