diff --git a/MediaBrowser.Controller/Chapters/ChapterResponse.cs b/MediaBrowser.Controller/Chapters/ChapterResponse.cs
new file mode 100644
index 000000000..3c1b8ed07
--- /dev/null
+++ b/MediaBrowser.Controller/Chapters/ChapterResponse.cs
@@ -0,0 +1,19 @@
+using MediaBrowser.Model.Chapters;
+using System.Collections.Generic;
+
+namespace MediaBrowser.Controller.Chapters
+{
+ public class ChapterResponse
+ {
+ ///
+ /// Gets or sets the chapters.
+ ///
+ /// The chapters.
+ public List Chapters { get; set; }
+
+ public ChapterResponse()
+ {
+ Chapters = new List();
+ }
+ }
+}
\ No newline at end of file
diff --git a/MediaBrowser.Controller/Chapters/ChapterSearchRequest.cs b/MediaBrowser.Controller/Chapters/ChapterSearchRequest.cs
new file mode 100644
index 000000000..9a53d68ea
--- /dev/null
+++ b/MediaBrowser.Controller/Chapters/ChapterSearchRequest.cs
@@ -0,0 +1,29 @@
+using MediaBrowser.Controller.Providers;
+using MediaBrowser.Model.Entities;
+using System;
+using System.Collections.Generic;
+
+namespace MediaBrowser.Controller.Chapters
+{
+ public class ChapterSearchRequest : IHasProviderIds
+ {
+ public string Language { get; set; }
+
+ public VideoContentType ContentType { get; set; }
+
+ public string MediaPath { get; set; }
+ public string SeriesName { get; set; }
+ public string Name { get; set; }
+ public int? IndexNumber { get; set; }
+ public int? IndexNumberEnd { get; set; }
+ public int? ParentIndexNumber { get; set; }
+ public int? ProductionYear { get; set; }
+ public long? RuntimeTicks { get; set; }
+ public Dictionary ProviderIds { get; set; }
+
+ public ChapterSearchRequest()
+ {
+ ProviderIds = new Dictionary(StringComparer.OrdinalIgnoreCase);
+ }
+ }
+}
\ No newline at end of file
diff --git a/MediaBrowser.Controller/Chapters/IChapterProvider.cs b/MediaBrowser.Controller/Chapters/IChapterProvider.cs
new file mode 100644
index 000000000..a7505347b
--- /dev/null
+++ b/MediaBrowser.Controller/Chapters/IChapterProvider.cs
@@ -0,0 +1,39 @@
+using MediaBrowser.Controller.Providers;
+using MediaBrowser.Model.Chapters;
+using System.Collections.Generic;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace MediaBrowser.Controller.Chapters
+{
+ public interface IChapterProvider
+ {
+ ///
+ /// Gets the name.
+ ///
+ /// The name.
+ string Name { get; }
+
+ ///
+ /// Gets the supported media types.
+ ///
+ /// The supported media types.
+ IEnumerable SupportedMediaTypes { get; }
+
+ ///
+ /// Searches the specified request.
+ ///
+ /// The request.
+ /// The cancellation token.
+ /// Task{IEnumerable{RemoteChapterResult}}.
+ Task> Search(ChapterSearchRequest request, CancellationToken cancellationToken);
+
+ ///
+ /// Gets the chapters.
+ ///
+ /// The identifier.
+ /// The cancellation token.
+ /// Task{ChapterResponse}.
+ Task GetChapters(string id, CancellationToken cancellationToken);
+ }
+}
diff --git a/MediaBrowser.Controller/MediaBrowser.Controller.csproj b/MediaBrowser.Controller/MediaBrowser.Controller.csproj
index 6a7557e3a..c7c4c5b5f 100644
--- a/MediaBrowser.Controller/MediaBrowser.Controller.csproj
+++ b/MediaBrowser.Controller/MediaBrowser.Controller.csproj
@@ -77,6 +77,9 @@
+
+
+
@@ -191,6 +194,7 @@
+
@@ -269,6 +273,8 @@
+
+
diff --git a/MediaBrowser.Controller/Providers/VideoContentType.cs b/MediaBrowser.Controller/Providers/VideoContentType.cs
new file mode 100644
index 000000000..903c77612
--- /dev/null
+++ b/MediaBrowser.Controller/Providers/VideoContentType.cs
@@ -0,0 +1,19 @@
+
+namespace MediaBrowser.Controller.Providers
+{
+ ///
+ /// Enum VideoContentType
+ ///
+ public enum VideoContentType
+ {
+ ///
+ /// The episode
+ ///
+ Episode = 0,
+
+ ///
+ /// The movie
+ ///
+ Movie = 1
+ }
+}
diff --git a/MediaBrowser.Controller/Subtitles/ISubtitleProvider.cs b/MediaBrowser.Controller/Subtitles/ISubtitleProvider.cs
index 1409b7d50..dceea0cc6 100644
--- a/MediaBrowser.Controller/Subtitles/ISubtitleProvider.cs
+++ b/MediaBrowser.Controller/Subtitles/ISubtitleProvider.cs
@@ -1,8 +1,6 @@
-using MediaBrowser.Model.Entities;
+using MediaBrowser.Controller.Providers;
using MediaBrowser.Model.Providers;
-using System;
using System.Collections.Generic;
-using System.IO;
using System.Threading;
using System.Threading.Tasks;
@@ -20,7 +18,7 @@ namespace MediaBrowser.Controller.Subtitles
/// Gets the supported media types.
///
/// The supported media types.
- IEnumerable SupportedMediaTypes { get; }
+ IEnumerable SupportedMediaTypes { get; }
///
/// Searches the subtitles.
@@ -28,7 +26,7 @@ namespace MediaBrowser.Controller.Subtitles
/// The request.
/// The cancellation token.
/// Task{IEnumerable{RemoteSubtitleInfo}}.
- Task> SearchSubtitles(SubtitleSearchRequest request, CancellationToken cancellationToken);
+ Task> Search(SubtitleSearchRequest request, CancellationToken cancellationToken);
///
/// Gets the subtitles.
@@ -38,38 +36,4 @@ namespace MediaBrowser.Controller.Subtitles
/// Task{SubtitleResponse}.
Task GetSubtitles(string id, CancellationToken cancellationToken);
}
-
- public enum SubtitleMediaType
- {
- Episode = 0,
- Movie = 1
- }
-
- public class SubtitleResponse
- {
- public string Language { get; set; }
- public string Format { get; set; }
- public Stream Stream { get; set; }
- }
-
- public class SubtitleSearchRequest : IHasProviderIds
- {
- public string Language { get; set; }
-
- public SubtitleMediaType ContentType { get; set; }
-
- public string MediaPath { get; set; }
- public string SeriesName { get; set; }
- public string Name { get; set; }
- public int? IndexNumber { get; set; }
- public int? IndexNumberEnd { get; set; }
- public int? ParentIndexNumber { get; set; }
- public int? ProductionYear { get; set; }
- public Dictionary ProviderIds { get; set; }
-
- public SubtitleSearchRequest()
- {
- ProviderIds = new Dictionary(StringComparer.OrdinalIgnoreCase);
- }
- }
}
diff --git a/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs b/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs
new file mode 100644
index 000000000..69e92c1f5
--- /dev/null
+++ b/MediaBrowser.Controller/Subtitles/SubtitleResponse.cs
@@ -0,0 +1,11 @@
+using System.IO;
+
+namespace MediaBrowser.Controller.Subtitles
+{
+ public class SubtitleResponse
+ {
+ public string Language { get; set; }
+ public string Format { get; set; }
+ public Stream Stream { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs b/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs
new file mode 100644
index 000000000..e83387129
--- /dev/null
+++ b/MediaBrowser.Controller/Subtitles/SubtitleSearchRequest.cs
@@ -0,0 +1,29 @@
+using MediaBrowser.Controller.Providers;
+using MediaBrowser.Model.Entities;
+using System;
+using System.Collections.Generic;
+
+namespace MediaBrowser.Controller.Subtitles
+{
+ public class SubtitleSearchRequest : IHasProviderIds
+ {
+ public string Language { get; set; }
+
+ public VideoContentType ContentType { get; set; }
+
+ public string MediaPath { get; set; }
+ public string SeriesName { get; set; }
+ public string Name { get; set; }
+ public int? IndexNumber { get; set; }
+ public int? IndexNumberEnd { get; set; }
+ public int? ParentIndexNumber { get; set; }
+ public int? ProductionYear { get; set; }
+ public long? RuntimeTicks { get; set; }
+ public Dictionary ProviderIds { get; set; }
+
+ public SubtitleSearchRequest()
+ {
+ ProviderIds = new Dictionary(StringComparer.OrdinalIgnoreCase);
+ }
+ }
+}
\ No newline at end of file
diff --git a/MediaBrowser.Model.Portable/MediaBrowser.Model.Portable.csproj b/MediaBrowser.Model.Portable/MediaBrowser.Model.Portable.csproj
index 57d265796..ef59f8878 100644
--- a/MediaBrowser.Model.Portable/MediaBrowser.Model.Portable.csproj
+++ b/MediaBrowser.Model.Portable/MediaBrowser.Model.Portable.csproj
@@ -83,6 +83,12 @@
Channels\ChannelQuery.cs
+
+ Chapters\RemoteChapterInfo.cs
+
+
+ Chapters\RemoteChapterResult.cs
+
Configuration\BaseApplicationConfiguration.cs
diff --git a/MediaBrowser.Model.net35/MediaBrowser.Model.net35.csproj b/MediaBrowser.Model.net35/MediaBrowser.Model.net35.csproj
index 318a26b7c..38ca64019 100644
--- a/MediaBrowser.Model.net35/MediaBrowser.Model.net35.csproj
+++ b/MediaBrowser.Model.net35/MediaBrowser.Model.net35.csproj
@@ -70,6 +70,12 @@
Channels\ChannelQuery.cs
+
+ Chapters\RemoteChapterInfo.cs
+
+
+ Chapters\RemoteChapterResult.cs
+
Configuration\BaseApplicationConfiguration.cs
diff --git a/MediaBrowser.Model/Chapters/RemoteChapterInfo.cs b/MediaBrowser.Model/Chapters/RemoteChapterInfo.cs
new file mode 100644
index 000000000..f2674c842
--- /dev/null
+++ b/MediaBrowser.Model/Chapters/RemoteChapterInfo.cs
@@ -0,0 +1,18 @@
+
+namespace MediaBrowser.Model.Chapters
+{
+ public class RemoteChapterInfo
+ {
+ ///
+ /// Gets or sets the start position ticks.
+ ///
+ /// The start position ticks.
+ public long StartPositionTicks { get; set; }
+
+ ///
+ /// Gets or sets the name.
+ ///
+ /// The name.
+ public string Name { get; set; }
+ }
+}
diff --git a/MediaBrowser.Model/Chapters/RemoteChapterResult.cs b/MediaBrowser.Model/Chapters/RemoteChapterResult.cs
new file mode 100644
index 000000000..5c58e5e7b
--- /dev/null
+++ b/MediaBrowser.Model/Chapters/RemoteChapterResult.cs
@@ -0,0 +1,36 @@
+
+namespace MediaBrowser.Model.Chapters
+{
+ public class RemoteChapterResult
+ {
+ ///
+ /// Gets or sets the identifier.
+ ///
+ /// The identifier.
+ public string Id { get; set; }
+
+ ///
+ /// Gets or sets the run time ticks.
+ ///
+ /// The run time ticks.
+ public long? RunTimeTicks { get; set; }
+
+ ///
+ /// Gets or sets the name.
+ ///
+ /// The name.
+ public string Name { get; set; }
+
+ ///
+ /// Gets or sets the community rating.
+ ///
+ /// The community rating.
+ public float? CommunityRating { get; set; }
+
+ ///
+ /// Gets or sets the chapter count.
+ ///
+ /// The chapter count.
+ public int? ChapterCount { get; set; }
+ }
+}
diff --git a/MediaBrowser.Model/Dto/BaseItemPerson.cs b/MediaBrowser.Model/Dto/BaseItemPerson.cs
index 376ba239d..b8393f444 100644
--- a/MediaBrowser.Model/Dto/BaseItemPerson.cs
+++ b/MediaBrowser.Model/Dto/BaseItemPerson.cs
@@ -1,5 +1,4 @@
-using System;
-using System.ComponentModel;
+using System.ComponentModel;
using System.Diagnostics;
using System.Runtime.Serialization;
@@ -17,6 +16,12 @@ namespace MediaBrowser.Model.Dto
/// The name.
public string Name { get; set; }
+ ///
+ /// Gets or sets the identifier.
+ ///
+ /// The identifier.
+ public string Id { get; set; }
+
///
/// Gets or sets the role.
///
diff --git a/MediaBrowser.Model/MediaBrowser.Model.csproj b/MediaBrowser.Model/MediaBrowser.Model.csproj
index 748e5f0a8..2c714f831 100644
--- a/MediaBrowser.Model/MediaBrowser.Model.csproj
+++ b/MediaBrowser.Model/MediaBrowser.Model.csproj
@@ -61,6 +61,8 @@
+
+
diff --git a/MediaBrowser.Providers/MediaInfo/SubtitleDownloader.cs b/MediaBrowser.Providers/MediaInfo/SubtitleDownloader.cs
index af0f91d0b..cf14cfadc 100644
--- a/MediaBrowser.Providers/MediaInfo/SubtitleDownloader.cs
+++ b/MediaBrowser.Providers/MediaInfo/SubtitleDownloader.cs
@@ -1,6 +1,7 @@
using MediaBrowser.Controller.Entities;
using MediaBrowser.Controller.Entities.Movies;
using MediaBrowser.Controller.Entities.TV;
+using MediaBrowser.Controller.Providers;
using MediaBrowser.Controller.Subtitles;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Logging;
@@ -37,15 +38,15 @@ namespace MediaBrowser.Providers.MediaInfo
return new List();
}
- SubtitleMediaType mediaType;
+ VideoContentType mediaType;
if (video is Episode)
{
- mediaType = SubtitleMediaType.Episode;
+ mediaType = VideoContentType.Episode;
}
else if (video is Movie)
{
- mediaType = SubtitleMediaType.Movie;
+ mediaType = VideoContentType.Movie;
}
else
{
@@ -82,7 +83,7 @@ namespace MediaBrowser.Providers.MediaInfo
bool skipIfGraphicalSubtitlesPresent,
bool skipIfAudioTrackMatches,
string language,
- SubtitleMediaType mediaType,
+ VideoContentType mediaType,
CancellationToken cancellationToken)
{
// There's already subtitles for this language
diff --git a/MediaBrowser.Providers/Subtitles/OpenSubtitleDownloader.cs b/MediaBrowser.Providers/Subtitles/OpenSubtitleDownloader.cs
index 79a301dd3..5b951e0c2 100644
--- a/MediaBrowser.Providers/Subtitles/OpenSubtitleDownloader.cs
+++ b/MediaBrowser.Providers/Subtitles/OpenSubtitleDownloader.cs
@@ -1,6 +1,7 @@
using MediaBrowser.Common.Extensions;
using MediaBrowser.Common.Net;
using MediaBrowser.Controller.Configuration;
+using MediaBrowser.Controller.Providers;
using MediaBrowser.Controller.Security;
using MediaBrowser.Controller.Subtitles;
using MediaBrowser.Model.Configuration;
@@ -72,17 +73,17 @@ namespace MediaBrowser.Providers.Subtitles
get { return "Open Subtitles"; }
}
- public IEnumerable SupportedMediaTypes
+ public IEnumerable SupportedMediaTypes
{
get
{
if (string.IsNullOrWhiteSpace(_config.Configuration.SubtitleOptions.OpenSubtitlesUsername) ||
string.IsNullOrWhiteSpace(_config.Configuration.SubtitleOptions.OpenSubtitlesPasswordHash))
{
- return new SubtitleMediaType[] { };
+ return new VideoContentType[] { };
}
- return new[] { SubtitleMediaType.Episode, SubtitleMediaType.Movie };
+ return new[] { VideoContentType.Episode, VideoContentType.Movie };
}
}
@@ -163,21 +164,21 @@ namespace MediaBrowser.Providers.Subtitles
_lastLogin = DateTime.UtcNow;
}
- public async Task> SearchSubtitles(SubtitleSearchRequest request, CancellationToken cancellationToken)
+ public async Task> Search(SubtitleSearchRequest request, CancellationToken cancellationToken)
{
var imdbIdText = request.GetProviderId(MetadataProviders.Imdb);
long imdbId = 0;
switch (request.ContentType)
{
- case SubtitleMediaType.Episode:
+ case VideoContentType.Episode:
if (!request.IndexNumber.HasValue || !request.ParentIndexNumber.HasValue || string.IsNullOrEmpty(request.SeriesName))
{
_logger.Debug("Episode information missing");
return new List();
}
break;
- case SubtitleMediaType.Movie:
+ case VideoContentType.Movie:
if (string.IsNullOrEmpty(request.Name))
{
_logger.Debug("Movie name missing");
@@ -206,8 +207,8 @@ namespace MediaBrowser.Providers.Subtitles
var hash = Utilities.ComputeHash(request.MediaPath);
var fileInfo = new FileInfo(request.MediaPath);
var movieByteSize = fileInfo.Length;
- var searchImdbId = request.ContentType == SubtitleMediaType.Movie ? imdbId.ToString(_usCulture) : "";
- var subtitleSearchParameters = request.ContentType == SubtitleMediaType.Episode
+ var searchImdbId = request.ContentType == VideoContentType.Movie ? imdbId.ToString(_usCulture) : "";
+ var subtitleSearchParameters = request.ContentType == VideoContentType.Episode
? new List {
new SubtitleSearchParameters(subLanguageId,
query: request.SeriesName,
@@ -234,7 +235,7 @@ namespace MediaBrowser.Providers.Subtitles
Predicate mediaFilter =
x =>
- request.ContentType == SubtitleMediaType.Episode
+ request.ContentType == VideoContentType.Episode
? !string.IsNullOrEmpty(x.SeriesSeason) && !string.IsNullOrEmpty(x.SeriesEpisode) &&
int.Parse(x.SeriesSeason, _usCulture) == request.ParentIndexNumber &&
int.Parse(x.SeriesEpisode, _usCulture) == request.IndexNumber
diff --git a/MediaBrowser.Providers/Subtitles/SubtitleManager.cs b/MediaBrowser.Providers/Subtitles/SubtitleManager.cs
index 6951e8bd0..2d5445653 100644
--- a/MediaBrowser.Providers/Subtitles/SubtitleManager.cs
+++ b/MediaBrowser.Providers/Subtitles/SubtitleManager.cs
@@ -3,6 +3,7 @@ using MediaBrowser.Controller.Entities;
using MediaBrowser.Controller.Entities.Movies;
using MediaBrowser.Controller.Entities.TV;
using MediaBrowser.Controller.Library;
+using MediaBrowser.Controller.Providers;
using MediaBrowser.Controller.Subtitles;
using MediaBrowser.Model.Entities;
using MediaBrowser.Model.Logging;
@@ -45,7 +46,7 @@ namespace MediaBrowser.Providers.Subtitles
{
try
{
- return await i.SearchSubtitles(request, cancellationToken).ConfigureAwait(false);
+ return await i.Search(request, cancellationToken).ConfigureAwait(false);
}
catch (Exception ex)
{
@@ -99,15 +100,15 @@ namespace MediaBrowser.Providers.Subtitles
return Task.FromResult>(new List());
}
- SubtitleMediaType mediaType;
+ VideoContentType mediaType;
if (video is Episode)
{
- mediaType = SubtitleMediaType.Episode;
+ mediaType = VideoContentType.Episode;
}
else if (video is Movie)
{
- mediaType = SubtitleMediaType.Movie;
+ mediaType = VideoContentType.Movie;
}
else
{
@@ -124,7 +125,8 @@ namespace MediaBrowser.Providers.Subtitles
Name = video.Name,
ParentIndexNumber = video.ParentIndexNumber,
ProductionYear = video.ProductionYear,
- ProviderIds = video.ProviderIds
+ ProviderIds = video.ProviderIds,
+ RuntimeTicks = video.RunTimeTicks
};
var episode = video as Episode;
diff --git a/MediaBrowser.Server.Implementations/Dto/DtoService.cs b/MediaBrowser.Server.Implementations/Dto/DtoService.cs
index 97a0ee703..4bcbfaf95 100644
--- a/MediaBrowser.Server.Implementations/Dto/DtoService.cs
+++ b/MediaBrowser.Server.Implementations/Dto/DtoService.cs
@@ -429,6 +429,7 @@ namespace MediaBrowser.Server.Implementations.Dto
if (dictionary.TryGetValue(person.Name, out entity))
{
baseItemPerson.PrimaryImageTag = GetImageCacheTag(entity, ImageType.Primary);
+ baseItemPerson.Id = entity.Id.ToString("N");
}
dto.People[i] = baseItemPerson;
diff --git a/MediaBrowser.WebDashboard/Api/DashboardService.cs b/MediaBrowser.WebDashboard/Api/DashboardService.cs
index e551a6e6b..047758f0d 100644
--- a/MediaBrowser.WebDashboard/Api/DashboardService.cs
+++ b/MediaBrowser.WebDashboard/Api/DashboardService.cs
@@ -517,7 +517,6 @@ namespace MediaBrowser.WebDashboard.Api
"librarymenu.js",
"mediacontroller.js",
"chromecast.js",
- "contextmenu.js",
"backdrops.js",
"mediaplayer.js",
diff --git a/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj b/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj
index 64ff1cf15..a6a9183e1 100644
--- a/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj
+++ b/MediaBrowser.WebDashboard/MediaBrowser.WebDashboard.csproj
@@ -592,9 +592,6 @@
PreserveNewest
-
- PreserveNewest
-
PreserveNewest