diff --git a/.DS_Store b/.DS_Store deleted file mode 100644 index 8139cef01..000000000 Binary files a/.DS_Store and /dev/null differ diff --git a/src/.DS_Store b/src/.DS_Store deleted file mode 100644 index cbd549c7f..000000000 Binary files a/src/.DS_Store and /dev/null differ diff --git a/src/NzbDrone.Api/Config/NamingConfigModule.cs b/src/NzbDrone.Api/Config/NamingConfigModule.cs index 0b72e0b0c..04a67856e 100644 --- a/src/NzbDrone.Api/Config/NamingConfigModule.cs +++ b/src/NzbDrone.Api/Config/NamingConfigModule.cs @@ -39,6 +39,8 @@ public NamingConfigModule(INamingConfigService namingConfigService, SharedValidator.RuleFor(c => c.AnimeEpisodeFormat).ValidAnimeEpisodeFormat(); SharedValidator.RuleFor(c => c.SeriesFolderFormat).ValidSeriesFolderFormat(); SharedValidator.RuleFor(c => c.SeasonFolderFormat).ValidSeasonFolderFormat(); + SharedValidator.RuleFor(c => c.StandardMovieFormat).ValidMovieFormat(); + SharedValidator.RuleFor(c => c.MovieFolderFormat).ValidMovieFolderFormat(); } private void UpdateNamingConfig(NamingConfigResource resource) @@ -54,7 +56,13 @@ private NamingConfigResource GetNamingConfig() var nameSpec = _namingConfigService.GetConfig(); var resource = nameSpec.ToResource(); - if (resource.StandardEpisodeFormat.IsNotNullOrWhiteSpace()) + //if (resource.StandardEpisodeFormat.IsNotNullOrWhiteSpace()) + //{ + // var basicConfig = _filenameBuilder.GetBasicNamingConfig(nameSpec); + // basicConfig.AddToResource(resource); + //} + + if (resource.StandardMovieFormat.IsNotNullOrWhiteSpace()) { var basicConfig = _filenameBuilder.GetBasicNamingConfig(nameSpec); basicConfig.AddToResource(resource); @@ -73,39 +81,50 @@ private JsonResponse GetExamples(NamingConfigResource conf var nameSpec = config.ToModel(); var sampleResource = new NamingSampleResource(); - var singleEpisodeSampleResult = _filenameSampleService.GetStandardSample(nameSpec); - var multiEpisodeSampleResult = _filenameSampleService.GetMultiEpisodeSample(nameSpec); - var dailyEpisodeSampleResult = _filenameSampleService.GetDailySample(nameSpec); - var animeEpisodeSampleResult = _filenameSampleService.GetAnimeSample(nameSpec); - var animeMultiEpisodeSampleResult = _filenameSampleService.GetAnimeMultiEpisodeSample(nameSpec); + //var singleEpisodeSampleResult = _filenameSampleService.GetStandardSample(nameSpec); + //var multiEpisodeSampleResult = _filenameSampleService.GetMultiEpisodeSample(nameSpec); + //var dailyEpisodeSampleResult = _filenameSampleService.GetDailySample(nameSpec); + //var animeEpisodeSampleResult = _filenameSampleService.GetAnimeSample(nameSpec); + //var animeMultiEpisodeSampleResult = _filenameSampleService.GetAnimeMultiEpisodeSample(nameSpec); - sampleResource.SingleEpisodeExample = _filenameValidationService.ValidateStandardFilename(singleEpisodeSampleResult) != null - ? "Invalid format" - : singleEpisodeSampleResult.FileName; + var movieSampleResult = _filenameSampleService.GetMovieSample(nameSpec); + - sampleResource.MultiEpisodeExample = _filenameValidationService.ValidateStandardFilename(multiEpisodeSampleResult) != null - ? "Invalid format" - : multiEpisodeSampleResult.FileName; + //sampleResource.SingleEpisodeExample = _filenameValidationService.ValidateStandardFilename(singleEpisodeSampleResult) != null + // ? "Invalid format" + // : singleEpisodeSampleResult.FileName; - sampleResource.DailyEpisodeExample = _filenameValidationService.ValidateDailyFilename(dailyEpisodeSampleResult) != null - ? "Invalid format" - : dailyEpisodeSampleResult.FileName; + //sampleResource.MultiEpisodeExample = _filenameValidationService.ValidateStandardFilename(multiEpisodeSampleResult) != null + // ? "Invalid format" + // : multiEpisodeSampleResult.FileName; - sampleResource.AnimeEpisodeExample = _filenameValidationService.ValidateAnimeFilename(animeEpisodeSampleResult) != null - ? "Invalid format" - : animeEpisodeSampleResult.FileName; + //sampleResource.DailyEpisodeExample = _filenameValidationService.ValidateDailyFilename(dailyEpisodeSampleResult) != null + // ? "Invalid format" + // : dailyEpisodeSampleResult.FileName; - sampleResource.AnimeMultiEpisodeExample = _filenameValidationService.ValidateAnimeFilename(animeMultiEpisodeSampleResult) != null - ? "Invalid format" - : animeMultiEpisodeSampleResult.FileName; + //sampleResource.AnimeEpisodeExample = _filenameValidationService.ValidateAnimeFilename(animeEpisodeSampleResult) != null + // ? "Invalid format" + // : animeEpisodeSampleResult.FileName; - sampleResource.SeriesFolderExample = nameSpec.SeriesFolderFormat.IsNullOrWhiteSpace() + //sampleResource.AnimeMultiEpisodeExample = _filenameValidationService.ValidateAnimeFilename(animeMultiEpisodeSampleResult) != null + // ? "Invalid format" + // : animeMultiEpisodeSampleResult.FileName; + + sampleResource.MovieExample = nameSpec.StandardMovieFormat.IsNullOrWhiteSpace() + ? "Invalid Format" + : movieSampleResult.FileName; + + //sampleResource.SeriesFolderExample = nameSpec.SeriesFolderFormat.IsNullOrWhiteSpace() + // ? "Invalid format" + // : _filenameSampleService.GetSeriesFolderSample(nameSpec); + + //sampleResource.SeasonFolderExample = nameSpec.SeasonFolderFormat.IsNullOrWhiteSpace() + // ? "Invalid format" + // : _filenameSampleService.GetSeasonFolderSample(nameSpec); + + sampleResource.MovieFolderExample = nameSpec.MovieFolderFormat.IsNullOrWhiteSpace() ? "Invalid format" - : _filenameSampleService.GetSeriesFolderSample(nameSpec); - - sampleResource.SeasonFolderExample = nameSpec.SeasonFolderFormat.IsNullOrWhiteSpace() - ? "Invalid format" - : _filenameSampleService.GetSeasonFolderSample(nameSpec); + : _filenameSampleService.GetMovieFolderSample(nameSpec); return sampleResource.AsResponse(); } @@ -118,19 +137,25 @@ private void ValidateFormatResult(NamingConfig nameSpec) var animeEpisodeSampleResult = _filenameSampleService.GetAnimeSample(nameSpec); var animeMultiEpisodeSampleResult = _filenameSampleService.GetAnimeMultiEpisodeSample(nameSpec); + var movieSampleResult = _filenameSampleService.GetMovieSample(nameSpec); + var singleEpisodeValidationResult = _filenameValidationService.ValidateStandardFilename(singleEpisodeSampleResult); var multiEpisodeValidationResult = _filenameValidationService.ValidateStandardFilename(multiEpisodeSampleResult); var dailyEpisodeValidationResult = _filenameValidationService.ValidateDailyFilename(dailyEpisodeSampleResult); var animeEpisodeValidationResult = _filenameValidationService.ValidateAnimeFilename(animeEpisodeSampleResult); var animeMultiEpisodeValidationResult = _filenameValidationService.ValidateAnimeFilename(animeMultiEpisodeSampleResult); + //var standardMovieValidationResult = _filenameValidationService.ValidateMovieFilename(movieSampleResult); For now, let's hope the user is not stupid enough :/ + var validationFailures = new List(); - validationFailures.AddIfNotNull(singleEpisodeValidationResult); - validationFailures.AddIfNotNull(multiEpisodeValidationResult); - validationFailures.AddIfNotNull(dailyEpisodeValidationResult); - validationFailures.AddIfNotNull(animeEpisodeValidationResult); - validationFailures.AddIfNotNull(animeMultiEpisodeValidationResult); + //validationFailures.AddIfNotNull(singleEpisodeValidationResult); + //validationFailures.AddIfNotNull(multiEpisodeValidationResult); + //validationFailures.AddIfNotNull(dailyEpisodeValidationResult); + //validationFailures.AddIfNotNull(animeEpisodeValidationResult); + //validationFailures.AddIfNotNull(animeMultiEpisodeValidationResult); + + //validationFailures.AddIfNotNull(standardMovieValidationResult); if (validationFailures.Any()) { diff --git a/src/NzbDrone.Api/Config/NamingConfigResource.cs b/src/NzbDrone.Api/Config/NamingConfigResource.cs index 39147b993..f65d90e48 100644 --- a/src/NzbDrone.Api/Config/NamingConfigResource.cs +++ b/src/NzbDrone.Api/Config/NamingConfigResource.cs @@ -7,6 +7,8 @@ public class NamingConfigResource : RestResource { public bool RenameEpisodes { get; set; } public bool ReplaceIllegalCharacters { get; set; } + public string StandardMovieFormat { get; set; } + public string MovieFolderFormat { get; set; } public int MultiEpisodeStyle { get; set; } public string StandardEpisodeFormat { get; set; } public string DailyEpisodeFormat { get; set; } @@ -36,7 +38,9 @@ public static NamingConfigResource ToResource(this NamingConfig model) DailyEpisodeFormat = model.DailyEpisodeFormat, AnimeEpisodeFormat = model.AnimeEpisodeFormat, SeriesFolderFormat = model.SeriesFolderFormat, - SeasonFolderFormat = model.SeasonFolderFormat + SeasonFolderFormat = model.SeasonFolderFormat, + StandardMovieFormat = model.StandardMovieFormat, + MovieFolderFormat = model.MovieFolderFormat //IncludeSeriesTitle //IncludeEpisodeTitle //IncludeQuality @@ -64,12 +68,14 @@ public static NamingConfig ToModel(this NamingConfigResource resource) RenameEpisodes = resource.RenameEpisodes, ReplaceIllegalCharacters = resource.ReplaceIllegalCharacters, - MultiEpisodeStyle = resource.MultiEpisodeStyle, - StandardEpisodeFormat = resource.StandardEpisodeFormat, - DailyEpisodeFormat = resource.DailyEpisodeFormat, - AnimeEpisodeFormat = resource.AnimeEpisodeFormat, - SeriesFolderFormat = resource.SeriesFolderFormat, - SeasonFolderFormat = resource.SeasonFolderFormat + //MultiEpisodeStyle = resource.MultiEpisodeStyle, + //StandardEpisodeFormat = resource.StandardEpisodeFormat, + //DailyEpisodeFormat = resource.DailyEpisodeFormat, + //AnimeEpisodeFormat = resource.AnimeEpisodeFormat, + //SeriesFolderFormat = resource.SeriesFolderFormat, + //SeasonFolderFormat = resource.SeasonFolderFormat, + StandardMovieFormat = resource.StandardMovieFormat, + MovieFolderFormat = resource.MovieFolderFormat }; } } diff --git a/src/NzbDrone.Api/Config/NamingSampleResource.cs b/src/NzbDrone.Api/Config/NamingSampleResource.cs index 1f9c7f066..3430050e0 100644 --- a/src/NzbDrone.Api/Config/NamingSampleResource.cs +++ b/src/NzbDrone.Api/Config/NamingSampleResource.cs @@ -9,5 +9,8 @@ public class NamingSampleResource public string AnimeMultiEpisodeExample { get; set; } public string SeriesFolderExample { get; set; } public string SeasonFolderExample { get; set; } + + public string MovieExample { get; set; } + public string MovieFolderExample { get; set; } } } \ No newline at end of file diff --git a/src/NzbDrone.Common/Cloud/SonarrCloudRequestBuilder.cs b/src/NzbDrone.Common/Cloud/SonarrCloudRequestBuilder.cs index bcf03c4ee..653c5794a 100644 --- a/src/NzbDrone.Common/Cloud/SonarrCloudRequestBuilder.cs +++ b/src/NzbDrone.Common/Cloud/SonarrCloudRequestBuilder.cs @@ -14,7 +14,7 @@ public class SonarrCloudRequestBuilder : ISonarrCloudRequestBuilder { public SonarrCloudRequestBuilder() { - Services = new HttpRequestBuilder("http://services.sonarr.tv/v1/") + Services = new HttpRequestBuilder("https://radarr.aeonlucid.com/v1/") .CreateFactory(); SkyHookTvdb = new HttpRequestBuilder("http://skyhook.sonarr.tv/v1/tvdb/{route}/{language}/") @@ -26,12 +26,11 @@ public SonarrCloudRequestBuilder() .CreateFactory(); TMDBSingle = new HttpRequestBuilder("https://api.themoviedb.org/3/{route}") - .AddQueryParam("api_key", "1a7373301961d03f97f853a876dd1212") - .CreateFactory(); + .AddQueryParam("api_key", "1a7373301961d03f97f853a876dd1212") + .CreateFactory(); } public IHttpRequestBuilderFactory Services { get; private set; } - public IHttpRequestBuilderFactory SkyHookTvdb { get; private set; } public IHttpRequestBuilderFactory TMDB { get; private set; } public IHttpRequestBuilderFactory TMDBSingle { get; private set; } diff --git a/src/NzbDrone.Core/Datastore/Migration/109_add_movie_formats_to_naming_config.cs b/src/NzbDrone.Core/Datastore/Migration/109_add_movie_formats_to_naming_config.cs new file mode 100644 index 000000000..c36d3f094 --- /dev/null +++ b/src/NzbDrone.Core/Datastore/Migration/109_add_movie_formats_to_naming_config.cs @@ -0,0 +1,65 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using FluentMigrator; +using NzbDrone.Core.Datastore.Migration.Framework; +using System.Data; + +namespace NzbDrone.Core.Datastore.Migration +{ + [Migration(109)] + public class add_movie_formats_to_naming_config : NzbDroneMigrationBase + { + protected override void MainDbUpgrade() + { + Alter.Table("NamingConfig").AddColumn("StandardMovieFormat").AsString().Nullable(); + Alter.Table("NamingConfig").AddColumn("MovieFolderFormat").AsString().Nullable(); + + Execute.WithConnection(ConvertConfig); + } + + private void ConvertConfig(IDbConnection conn, IDbTransaction tran) + { + + using (IDbCommand namingConfigCmd = conn.CreateCommand()) + { + namingConfigCmd.Transaction = tran; + namingConfigCmd.CommandText = @"SELECT * FROM NamingConfig LIMIT 1"; + using (IDataReader namingConfigReader = namingConfigCmd.ExecuteReader()) + { + + while (namingConfigReader.Read()) + { + // Output Settings + var movieTitlePattern = ""; + var movieYearPattern = "({Release Year})"; + var qualityFormat = "[{Quality Title}]"; + + movieTitlePattern = "{Movie Title}"; + + var standardMovieFormat = string.Format("{0} {1} {2}", movieTitlePattern, + movieYearPattern, + qualityFormat); + + var movieFolderFormat = string.Format("{0} {1}", movieTitlePattern, movieYearPattern); + + + using (IDbCommand updateCmd = conn.CreateCommand()) + { + var text = string.Format("UPDATE NamingConfig " + + "SET StandardMovieFormat = '{0}', " + + "MovieFolderFormat = '{1}'", + standardMovieFormat, + movieFolderFormat); + + updateCmd.Transaction = tran; + updateCmd.CommandText = text; + updateCmd.ExecuteNonQuery(); + } + } + } + } + } + } +} diff --git a/src/NzbDrone.Core/Indexers/Newznab/NewznabRequestGenerator.cs b/src/NzbDrone.Core/Indexers/Newznab/NewznabRequestGenerator.cs index 518494923..b9b5103f3 100644 --- a/src/NzbDrone.Core/Indexers/Newznab/NewznabRequestGenerator.cs +++ b/src/NzbDrone.Core/Indexers/Newznab/NewznabRequestGenerator.cs @@ -112,9 +112,9 @@ public virtual IndexerPageableRequestChain GetRecentRequests() var capabilities = _capabilitiesProvider.GetCapabilities(Settings); - if (capabilities.SupportedTvSearchParameters != null) + if (capabilities.SupportedMovieSearchParamters != null) { - pageableRequests.Add(GetPagedRequests(MaxPages, Settings.Categories.Concat(Settings.AnimeCategories), "tvsearch", "")); + pageableRequests.Add(GetPagedRequests(MaxPages, Settings.Categories.Concat(Settings.AnimeCategories), "movie", "")); } return pageableRequests; diff --git a/src/NzbDrone.Core/MetadataSource/SkyHook/SkyHookProxy.cs b/src/NzbDrone.Core/MetadataSource/SkyHook/SkyHookProxy.cs index e0014a728..14957c0ef 100644 --- a/src/NzbDrone.Core/MetadataSource/SkyHook/SkyHookProxy.cs +++ b/src/NzbDrone.Core/MetadataSource/SkyHook/SkyHookProxy.cs @@ -12,6 +12,7 @@ using NzbDrone.Core.MetadataSource; using NzbDrone.Core.Tv; using Newtonsoft.Json; +using System.Text.RegularExpressions; namespace NzbDrone.Core.MetadataSource.SkyHook { @@ -175,9 +176,41 @@ public Movie GetMovieInfo(string ImdbId) return movie; } + private string[] SeparateYearFromTitle(string title) + { + var yearPattern = @"((?:19|20)\d{2})"; + var newTitle = title; + var substrings = Regex.Split(title, yearPattern); + var year = ""; + if (substrings.Length > 1) { + newTitle = substrings[0].TrimEnd("("); + year = substrings[1]; + } + + return new[] { newTitle.Trim(), year.Trim() }; + } + + private string StripTrailingTheFromTitle(string title) + { + if(title.EndsWith(",the")) + { + title = title.Substring(title.Length - 4); + } else if(title.EndsWith(", the")) + { + title = title.Substring(title.Length - 5); + } + return title; + } + public List SearchForNewMovie(string title) { var lowerTitle = title.ToLower(); + var yearCheck = SeparateYearFromTitle(lowerTitle); // TODO: Make this much less hacky! + + lowerTitle = yearCheck[0]; + var yearTerm = yearCheck[1]; + + lowerTitle = StripTrailingTheFromTitle(lowerTitle); if (lowerTitle.StartsWith("imdb:") || lowerTitle.StartsWith("imdbid:")) { @@ -209,6 +242,7 @@ public List SearchForNewMovie(string title) .SetSegment("id", "movie") .SetSegment("secondaryRoute", "") .AddQueryParam("query", searchTerm) + .AddQueryParam("year", yearTerm) .AddQueryParam("include_adult", false) .Build(); diff --git a/src/NzbDrone.Core/NzbDrone.Core.csproj b/src/NzbDrone.Core/NzbDrone.Core.csproj index 14d74a9e5..8720a43ff 100644 --- a/src/NzbDrone.Core/NzbDrone.Core.csproj +++ b/src/NzbDrone.Core/NzbDrone.Core.csproj @@ -286,6 +286,7 @@ Code + diff --git a/src/NzbDrone.Core/Organizer/FileNameBuilder.cs b/src/NzbDrone.Core/Organizer/FileNameBuilder.cs index 17d1f4c57..25399e6de 100644 --- a/src/NzbDrone.Core/Organizer/FileNameBuilder.cs +++ b/src/NzbDrone.Core/Organizer/FileNameBuilder.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections.Generic; using System.Globalization; using System.IO; @@ -24,7 +24,7 @@ public interface IBuildFileNames BasicNamingConfig GetBasicNamingConfig(NamingConfig nameSpec); string GetSeriesFolder(Series series, NamingConfig namingConfig = null); string GetSeasonFolder(Series series, int seasonNumber, NamingConfig namingConfig = null); - string GetMovieFolder(Movie movie); + string GetMovieFolder(Movie movie, NamingConfig namingConfig = null); } public class FileNameBuilder : IBuildFileNames @@ -58,6 +58,9 @@ public class FileNameBuilder : IBuildFileNames public static readonly Regex SeriesTitleRegex = new Regex(@"(?\{(?:Series)(?[- ._])(Clean)?Title\})", RegexOptions.Compiled | RegexOptions.IgnoreCase); + public static readonly Regex MovieTitleRegex = new Regex(@"(?\{(?:Movie)(?[- ._])(Clean)?Title\})", + RegexOptions.Compiled | RegexOptions.IgnoreCase); + private static readonly Regex FileNameCleanupRegex = new Regex(@"([- ._])(\1)+", RegexOptions.Compiled); private static readonly Regex TrimSeparatorsRegex = new Regex(@"[- ._]$", RegexOptions.Compiled); @@ -76,6 +79,7 @@ public FileNameBuilder(INamingConfigService namingConfigService, { _namingConfigService = namingConfigService; _qualityDefinitionService = qualityDefinitionService; + //_movieFormatCache = cacheManager.GetCache(GetType(), "movieFormat"); _episodeFormatCache = cacheManager.GetCache(GetType(), "episodeFormat"); _absoluteEpisodeFormatCache = cacheManager.GetCache(GetType(), "absoluteEpisodeFormat"); _logger = logger; @@ -151,52 +155,20 @@ public string BuildFileName(Movie movie, MovieFile movieFile, NamingConfig namin return GetOriginalTitle(movieFile); } - /*if (namingConfig.StandardEpisodeFormat.IsNullOrWhiteSpace() && series.SeriesType == SeriesTypes.Standard) - { - throw new NamingFormatException("Standard episode format cannot be empty"); - } - - if (namingConfig.DailyEpisodeFormat.IsNullOrWhiteSpace() && series.SeriesType == SeriesTypes.Daily) - { - throw new NamingFormatException("Daily episode format cannot be empty"); - } - - if (namingConfig.AnimeEpisodeFormat.IsNullOrWhiteSpace() && series.SeriesType == SeriesTypes.Anime) - { - throw new NamingFormatException("Anime episode format cannot be empty"); - }*/ - - /*var pattern = namingConfig.StandardEpisodeFormat; + //TODO: Update namingConfig for Movies! + var pattern = namingConfig.StandardMovieFormat; var tokenHandlers = new Dictionary>(FileNameBuilderTokenEqualityComparer.Instance); - episodes = episodes.OrderBy(e => e.SeasonNumber).ThenBy(e => e.EpisodeNumber).ToList(); - - if (series.SeriesType == SeriesTypes.Daily) - { - pattern = namingConfig.DailyEpisodeFormat; - } - - if (series.SeriesType == SeriesTypes.Anime && episodes.All(e => e.AbsoluteEpisodeNumber.HasValue)) - { - pattern = namingConfig.AnimeEpisodeFormat; - } - - pattern = AddSeasonEpisodeNumberingTokens(pattern, tokenHandlers, episodes, namingConfig); - pattern = AddAbsoluteNumberingTokens(pattern, tokenHandlers, series, episodes, namingConfig); - - AddSeriesTokens(tokenHandlers, series); - AddEpisodeTokens(tokenHandlers, episodes); - AddEpisodeFileTokens(tokenHandlers, episodeFile); - AddQualityTokens(tokenHandlers, series, episodeFile); - AddMediaInfoTokens(tokenHandlers, episodeFile); + AddMovieTokens(tokenHandlers, movie); + AddReleaseDateTokens(tokenHandlers, movie.Year); //In case we want to separate the year + AddQualityTokens(tokenHandlers, movie, movieFile); + AddMediaInfoTokens(tokenHandlers, movieFile); var fileName = ReplaceTokens(pattern, tokenHandlers, namingConfig).Trim(); fileName = FileNameCleanupRegex.Replace(fileName, match => match.Captures[0].Value[0].ToString()); - fileName = TrimSeparatorsRegex.Replace(fileName, string.Empty);*/ + fileName = TrimSeparatorsRegex.Replace(fileName, string.Empty); - //TODO: Update namingConfig for Movies! - - return GetOriginalTitle(movieFile); + return fileName; } public string BuildFilePath(Series series, int seasonNumber, string fileName, string extension) @@ -242,6 +214,8 @@ public string BuildSeasonPath(Series series, int seasonNumber) public BasicNamingConfig GetBasicNamingConfig(NamingConfig nameSpec) { + return new BasicNamingConfig(); //For now let's be lazy + var episodeFormat = GetEpisodeFormat(nameSpec.StandardEpisodeFormat).LastOrDefault(); if (episodeFormat == null) @@ -315,9 +289,19 @@ public string GetSeasonFolder(Series series, int seasonNumber, NamingConfig nami return CleanFolderName(ReplaceTokens(namingConfig.SeasonFolderFormat, tokenHandlers, namingConfig)); } - public string GetMovieFolder(Movie movie) + public string GetMovieFolder(Movie movie, NamingConfig namingConfig = null) { - return CleanFolderName(movie.Title); + if(namingConfig == null) + { + namingConfig = _namingConfigService.GetConfig(); + } + + var tokenHandlers = new Dictionary>(FileNameBuilderTokenEqualityComparer.Instance); + + AddMovieTokens(tokenHandlers, movie); + AddReleaseDateTokens(tokenHandlers, movie.Year); + + return CleanFolderName(ReplaceTokens(namingConfig.MovieFolderFormat, tokenHandlers, namingConfig)); } public static string CleanTitle(string title) @@ -481,6 +465,17 @@ private string AddAbsoluteNumberingTokens(string pattern, Dictionary> tokenHandlers, Movie movie) + { + tokenHandlers["{Movie Title}"] = m => movie.Title; + tokenHandlers["{Movie CleanTitle}"] = m => CleanTitle(movie.Title); + } + + private void AddReleaseDateTokens(Dictionary> tokenHandlers, int releaseYear) + { + tokenHandlers["{Release Year}"] = m => string.Format("{0}", releaseYear.ToString()); //Do I need m.CustomFormat? + } + private void AddSeasonTokens(Dictionary> tokenHandlers, int seasonNumber) { tokenHandlers["{Season}"] = m => seasonNumber.ToString(m.CustomFormat); @@ -520,6 +515,18 @@ private void AddQualityTokens(Dictionary> token tokenHandlers["{Quality Real}"] = m => qualityReal; } + private void AddQualityTokens(Dictionary> tokenHandlers, Movie movie, MovieFile movieFile) + { + var qualityTitle = _qualityDefinitionService.Get(movieFile.Quality.Quality).Title; + var qualityProper = GetQualityProper(movie, movieFile.Quality); + var qualityReal = GetQualityReal(movie, movieFile.Quality); + + tokenHandlers["{Quality Full}"] = m => String.Format("{0} {1} {2}", qualityTitle, qualityProper, qualityReal); + tokenHandlers["{Quality Title}"] = m => qualityTitle; + tokenHandlers["{Quality Proper}"] = m => qualityProper; + tokenHandlers["{Quality Real}"] = m => qualityReal; + } + private void AddMediaInfoTokens(Dictionary> tokenHandlers, EpisodeFile episodeFile) { if (episodeFile.MediaInfo == null) return; @@ -624,6 +631,110 @@ private void AddMediaInfoTokens(Dictionary> tok tokenHandlers["{MediaInfo Full}"] = m => string.Format("{0} {1}{2} {3}", videoCodec, audioCodec, mediaInfoAudioLanguages, mediaInfoSubtitleLanguages); } + private void AddMediaInfoTokens(Dictionary> tokenHandlers, MovieFile movieFile) + { + if (movieFile.MediaInfo == null) return; + + string videoCodec; + switch (movieFile.MediaInfo.VideoCodec) + { + case "AVC": + if (movieFile.SceneName.IsNotNullOrWhiteSpace() && Path.GetFileNameWithoutExtension(movieFile.SceneName).Contains("h264")) + { + videoCodec = "h264"; + } + else + { + videoCodec = "x264"; + } + break; + + case "V_MPEGH/ISO/HEVC": + if (movieFile.SceneName.IsNotNullOrWhiteSpace() && Path.GetFileNameWithoutExtension(movieFile.SceneName).Contains("h265")) + { + videoCodec = "h265"; + } + else + { + videoCodec = "x265"; + } + break; + + case "MPEG-2 Video": + videoCodec = "MPEG2"; + break; + + default: + videoCodec = movieFile.MediaInfo.VideoCodec; + break; + } + + string audioCodec; + switch (movieFile.MediaInfo.AudioFormat) + { + case "AC-3": + audioCodec = "AC3"; + break; + + case "E-AC-3": + audioCodec = "EAC3"; + break; + + case "MPEG Audio": + if (movieFile.MediaInfo.AudioProfile == "Layer 3") + { + audioCodec = "MP3"; + } + else + { + audioCodec = movieFile.MediaInfo.AudioFormat; + } + break; + + case "DTS": + audioCodec = movieFile.MediaInfo.AudioFormat; + break; + + default: + audioCodec = movieFile.MediaInfo.AudioFormat; + break; + } + + var mediaInfoAudioLanguages = GetLanguagesToken(movieFile.MediaInfo.AudioLanguages); + if (!mediaInfoAudioLanguages.IsNullOrWhiteSpace()) + { + mediaInfoAudioLanguages = string.Format("[{0}]", mediaInfoAudioLanguages); + } + + if (mediaInfoAudioLanguages == "[EN]") + { + mediaInfoAudioLanguages = string.Empty; + } + + var mediaInfoSubtitleLanguages = GetLanguagesToken(movieFile.MediaInfo.Subtitles); + if (!mediaInfoSubtitleLanguages.IsNullOrWhiteSpace()) + { + mediaInfoSubtitleLanguages = string.Format("[{0}]", mediaInfoSubtitleLanguages); + } + + var videoBitDepth = movieFile.MediaInfo.VideoBitDepth > 0 ? movieFile.MediaInfo.VideoBitDepth.ToString() : string.Empty; + var audioChannels = movieFile.MediaInfo.FormattedAudioChannels > 0 ? + movieFile.MediaInfo.FormattedAudioChannels.ToString("F1", CultureInfo.InvariantCulture) : + string.Empty; + + tokenHandlers["{MediaInfo Video}"] = m => videoCodec; + tokenHandlers["{MediaInfo VideoCodec}"] = m => videoCodec; + tokenHandlers["{MediaInfo VideoBitDepth}"] = m => videoBitDepth; + + tokenHandlers["{MediaInfo Audio}"] = m => audioCodec; + tokenHandlers["{MediaInfo AudioCodec}"] = m => audioCodec; + tokenHandlers["{MediaInfo AudioChannels}"] = m => audioChannels; + + tokenHandlers["{MediaInfo Simple}"] = m => string.Format("{0} {1}", videoCodec, audioCodec); + + tokenHandlers["{MediaInfo Full}"] = m => string.Format("{0} {1}{2} {3}", videoCodec, audioCodec, mediaInfoAudioLanguages, mediaInfoSubtitleLanguages); + } + private string GetLanguagesToken(string mediaInfoLanguages) { List tokens = new List(); @@ -803,6 +914,16 @@ private string CleanupEpisodeTitle(string title) return MultiPartCleanupRegex.Replace(title, string.Empty).Trim(); } + private string GetQualityProper(Movie movie, QualityModel quality) + { + if (quality.Revision.Version > 1) + { + return "Proper"; + } + + return String.Empty; + } + private string GetQualityProper(Series series, QualityModel quality) { if (quality.Revision.Version > 1) @@ -828,6 +949,16 @@ private string GetQualityReal(Series series, QualityModel quality) return string.Empty; } + private string GetQualityReal(Movie movie, QualityModel quality) + { + if (quality.Revision.Real > 0) + { + return "REAL"; + } + + return string.Empty; + } + private string GetOriginalTitle(EpisodeFile episodeFile) { if (episodeFile.SceneName.IsNullOrWhiteSpace()) diff --git a/src/NzbDrone.Core/Organizer/FileNameSampleService.cs b/src/NzbDrone.Core/Organizer/FileNameSampleService.cs index 966061fb3..654179b52 100644 --- a/src/NzbDrone.Core/Organizer/FileNameSampleService.cs +++ b/src/NzbDrone.Core/Organizer/FileNameSampleService.cs @@ -3,6 +3,7 @@ using NzbDrone.Core.Qualities; using NzbDrone.Core.Tv; using NzbDrone.Core.MediaFiles.MediaInfo; +using System; namespace NzbDrone.Core.Organizer { @@ -13,8 +14,10 @@ public interface IFilenameSampleService SampleResult GetDailySample(NamingConfig nameSpec); SampleResult GetAnimeSample(NamingConfig nameSpec); SampleResult GetAnimeMultiEpisodeSample(NamingConfig nameSpec); + SampleResult GetMovieSample(NamingConfig nameSpec); string GetSeriesFolderSample(NamingConfig nameSpec); string GetSeasonFolderSample(NamingConfig nameSpec); + string GetMovieFolderSample(NamingConfig nameSpec); } public class FileNameSampleService : IFilenameSampleService @@ -34,10 +37,19 @@ public class FileNameSampleService : IFilenameSampleService private static EpisodeFile _animeEpisodeFile; private static EpisodeFile _animeMultiEpisodeFile; + private static MovieFile _movieFile; + private static Movie _movie; + public FileNameSampleService(IBuildFileNames buildFileNames) { _buildFileNames = buildFileNames; + _movie = new Movie + { + Title = "Movie Title", + Year = 2010 + }; + _standardSeries = new Series { SeriesType = SeriesTypes.Standard, @@ -106,6 +118,15 @@ public FileNameSampleService(IBuildFileNames buildFileNames) Subtitles = "Japanese/English" }; + _movieFile = new MovieFile + { + Quality = new QualityModel(Quality.Bluray1080p, new Revision(2)), + RelativePath = "Movie.Title.2010.1080p.BluRay.DTS.x264-EVOLVE.mkv", + SceneName = "Movie.Title.2010.1080p.BluRay.DTS.x264-EVOLVE", + ReleaseGroup = "RlsGrp", + MediaInfo = mediaInfo + }; + _singleEpisodeFile = new EpisodeFile { Quality = new QualityModel(Quality.HDTV720p, new Revision(2)), @@ -217,6 +238,16 @@ public SampleResult GetAnimeMultiEpisodeSample(NamingConfig nameSpec) return result; } + public SampleResult GetMovieSample(NamingConfig nameSpec) + { + var result = new SampleResult + { + FileName = BuildSample(_movie, _movieFile, nameSpec), + }; + + return result; + } + public string GetSeriesFolderSample(NamingConfig nameSpec) { return _buildFileNames.GetSeriesFolder(_standardSeries, nameSpec); @@ -227,6 +258,11 @@ public string GetSeasonFolderSample(NamingConfig nameSpec) return _buildFileNames.GetSeasonFolder(_standardSeries, _episode1.SeasonNumber, nameSpec); } + public string GetMovieFolderSample(NamingConfig nameSpec) + { + return _buildFileNames.GetMovieFolder(_movie, nameSpec); + } + private string BuildSample(List episodes, Series series, EpisodeFile episodeFile, NamingConfig nameSpec) { try @@ -238,5 +274,17 @@ private string BuildSample(List episodes, Series series, EpisodeFile ep return string.Empty; } } + + private string BuildSample(Movie movie, MovieFile movieFile, NamingConfig nameSpec) + { + try + { + return _buildFileNames.BuildFileName(movie, movieFile, nameSpec); + } + catch (NamingFormatException) + { + return string.Empty; + } + } } } diff --git a/src/NzbDrone.Core/Organizer/FileNameValidation.cs b/src/NzbDrone.Core/Organizer/FileNameValidation.cs index 930b8a044..c1f4ac776 100644 --- a/src/NzbDrone.Core/Organizer/FileNameValidation.cs +++ b/src/NzbDrone.Core/Organizer/FileNameValidation.cs @@ -41,6 +41,18 @@ public static IRuleBuilderOptions ValidSeasonFolderFormat(this IRu ruleBuilder.SetValidator(new NotEmptyValidator(null)); return ruleBuilder.SetValidator(new RegularExpressionValidator(SeasonFolderRegex)).WithMessage("Must contain season number"); } + + public static IRuleBuilderOptions ValidMovieFolderFormat(this IRuleBuilder ruleBuilder) + { + ruleBuilder.SetValidator(new NotEmptyValidator(null)); + return ruleBuilder.SetValidator(new RegularExpressionValidator(FileNameBuilder.MovieTitleRegex)).WithMessage("Must contain movie title"); + } + + public static IRuleBuilderOptions ValidMovieFormat(this IRuleBuilder ruleBuilder) + { + ruleBuilder.SetValidator(new NotEmptyValidator(null)); + return ruleBuilder.SetValidator(new RegularExpressionValidator(FileNameBuilder.MovieTitleRegex)).WithMessage("Must contain movie title"); + } } public class ValidStandardEpisodeFormatValidator : PropertyValidator diff --git a/src/NzbDrone.Core/Organizer/FileNameValidationService.cs b/src/NzbDrone.Core/Organizer/FileNameValidationService.cs index 9367c11d8..697f72bbb 100644 --- a/src/NzbDrone.Core/Organizer/FileNameValidationService.cs +++ b/src/NzbDrone.Core/Organizer/FileNameValidationService.cs @@ -11,12 +11,26 @@ public interface IFilenameValidationService ValidationFailure ValidateStandardFilename(SampleResult sampleResult); ValidationFailure ValidateDailyFilename(SampleResult sampleResult); ValidationFailure ValidateAnimeFilename(SampleResult sampleResult); + ValidationFailure ValidateMovieFilename(SampleResult sampleResult); } public class FileNameValidationService : IFilenameValidationService { private const string ERROR_MESSAGE = "Produces invalid file names"; + public ValidationFailure ValidateMovieFilename(SampleResult sampleResult) + { + var validationFailure = new ValidationFailure("MovieFormat", ERROR_MESSAGE); + var parsedMovieInfo = Parser.Parser.ParseMovieTitle(sampleResult.FileName); + + if(parsedMovieInfo == null) + { + return validationFailure; + } + + return null; + } + public ValidationFailure ValidateStandardFilename(SampleResult sampleResult) { var validationFailure = new ValidationFailure("StandardEpisodeFormat", ERROR_MESSAGE); diff --git a/src/NzbDrone.Core/Organizer/NamingConfig.cs b/src/NzbDrone.Core/Organizer/NamingConfig.cs index 5de62a090..a617d5e61 100644 --- a/src/NzbDrone.Core/Organizer/NamingConfig.cs +++ b/src/NzbDrone.Core/Organizer/NamingConfig.cs @@ -1,4 +1,4 @@ -using NzbDrone.Core.Datastore; +using NzbDrone.Core.Datastore; namespace NzbDrone.Core.Organizer { @@ -13,7 +13,9 @@ public class NamingConfig : ModelBase DailyEpisodeFormat = "{Series Title} - {Air-Date} - {Episode Title} {Quality Full}", AnimeEpisodeFormat = "{Series Title} - S{season:00}E{episode:00} - {Episode Title} {Quality Full}", SeriesFolderFormat = "{Series Title}", - SeasonFolderFormat = "Season {season}" + SeasonFolderFormat = "Season {season}", + MovieFolderFormat = "{Movie Title} ({Release Year})", + StandardMovieFormat = "{Movie Title} ({Release Year}) {Quality Full}", }; public bool RenameEpisodes { get; set; } @@ -24,5 +26,7 @@ public class NamingConfig : ModelBase public string AnimeEpisodeFormat { get; set; } public string SeriesFolderFormat { get; set; } public string SeasonFolderFormat { get; set; } + public string StandardMovieFormat { get; set; } + public string MovieFolderFormat { get; set; } } } diff --git a/src/UI/.DS_Store b/src/UI/.DS_Store deleted file mode 100644 index 6cf6f2ffc..000000000 Binary files a/src/UI/.DS_Store and /dev/null differ diff --git a/src/UI/AddMovies/AddMoviesLayout.js b/src/UI/AddMovies/AddMoviesLayout.js index 904d3f179..3dd299959 100644 --- a/src/UI/AddMovies/AddMoviesLayout.js +++ b/src/UI/AddMovies/AddMoviesLayout.js @@ -2,7 +2,7 @@ var vent = require('vent'); var AppLayout = require('../AppLayout'); var Marionette = require('marionette'); var RootFolderLayout = require('./RootFolders/RootFolderLayout'); -//var ExistingMoviesCollectionView = require('./Existing/AddExistingSeriesCollectionView'); +var ExistingMoviesCollectionView = require('./Existing/AddExistingMovieCollectionView'); var AddMoviesView = require('./AddMoviesView'); var ProfileCollection = require('../Profile/ProfileCollection'); var RootFolderCollection = require('./RootFolders/RootFolderCollection'); @@ -36,9 +36,9 @@ module.exports = Marionette.Layout.extend({ }, _folderSelected : function(options) { - //vent.trigger(vent.Commands.CloseModalCommand); + vent.trigger(vent.Commands.CloseModalCommand); //TODO: Fix this shit. - //this.workspace.show(new ExistingMoviesCollectionView({ model : options.model })); + this.workspace.show(new ExistingMoviesCollectionView({ model : options.model })); }, _importMovies : function() { diff --git a/src/UI/AddMovies/AddMoviesView.js b/src/UI/AddMovies/AddMoviesView.js index ed4c5e2e8..ca47d5368 100644 --- a/src/UI/AddMovies/AddMoviesView.js +++ b/src/UI/AddMovies/AddMoviesView.js @@ -26,7 +26,7 @@ module.exports = Marionette.Layout.extend({ }, initialize : function(options) { - console.log(options) + console.log(options); this.isExisting = options.isExisting; this.collection = new AddMoviesCollection(); @@ -125,7 +125,7 @@ module.exports = Marionette.Layout.extend({ } else if (!this.isExisting) { - this.resultCollectionView.setExisting(options.movie.get('tmdbId')) + this.resultCollectionView.setExisting(options.movie.get('tmdbId')); /*this.collection.term = ''; this.collection.reset(); this._clearResults(); diff --git a/src/UI/AddMovies/Existing/AddExistingSeriesCollectionView.js b/src/UI/AddMovies/Existing/AddExistingMovieCollectionView.js similarity index 88% rename from src/UI/AddMovies/Existing/AddExistingSeriesCollectionView.js rename to src/UI/AddMovies/Existing/AddExistingMovieCollectionView.js index 5c5eddc64..1e3d38b6a 100644 --- a/src/UI/AddMovies/Existing/AddExistingSeriesCollectionView.js +++ b/src/UI/AddMovies/Existing/AddExistingMovieCollectionView.js @@ -1,11 +1,11 @@ var Marionette = require('marionette'); -var AddSeriesView = require('../AddSeriesView'); +var AddMoviesView = require('../AddMoviesView'); var UnmappedFolderCollection = require('./UnmappedFolderCollection'); module.exports = Marionette.CompositeView.extend({ - itemView : AddSeriesView, + itemView : AddMoviesView, itemViewContainer : '.x-loading-folders', - template : 'AddSeries/Existing/AddExistingSeriesCollectionViewTemplate', + template : 'AddMovies/Existing/AddExistingMovieCollectionViewTemplate', ui : { loadingFolders : '.x-loading-folders' diff --git a/src/UI/AddMovies/Existing/AddExistingSeriesCollectionViewTemplate.hbs b/src/UI/AddMovies/Existing/AddExistingMovieCollectionViewTemplate.hbs similarity index 100% rename from src/UI/AddMovies/Existing/AddExistingSeriesCollectionViewTemplate.hbs rename to src/UI/AddMovies/Existing/AddExistingMovieCollectionViewTemplate.hbs diff --git a/src/UI/AddMovies/SearchResultCollectionView.js b/src/UI/AddMovies/SearchResultCollectionView.js index 1d8c2df89..02fe1fa41 100644 --- a/src/UI/AddMovies/SearchResultCollectionView.js +++ b/src/UI/AddMovies/SearchResultCollectionView.js @@ -23,7 +23,7 @@ module.exports = Marionette.CollectionView.extend({ setExisting : function(tmdbid) { var movies = this.collection.where({ tmdbId : tmdbid }); - console.warn(movies) + console.warn(movies); //debugger; if (movies.length > 0) { this.children.findByModel(movies[0])._configureTemplateHelpers(); diff --git a/src/UI/AddMovies/SearchResultView.js b/src/UI/AddMovies/SearchResultView.js index 7a2a4a6ac..3d50e1030 100644 --- a/src/UI/AddMovies/SearchResultView.js +++ b/src/UI/AddMovies/SearchResultView.js @@ -92,14 +92,14 @@ var view = Marionette.ItemView.extend({ _configureTemplateHelpers : function() { var existingMovies = MoviesCollection.where({ tmdbId : this.model.get('tmdbId') }); - console.log(existingMovies) + console.log(existingMovies); if (existingMovies.length > 0) { this.templateHelpers.existing = existingMovies[0].toJSON(); } this.templateHelpers.profiles = Profiles.toJSON(); - console.log(this.model) - console.log(this.templateHelpers.existing) + console.log(this.model); + console.log(this.templateHelpers.existing); if (!this.model.get('isExisting')) { this.templateHelpers.rootFolders = RootFolders.toJSON(); } @@ -245,14 +245,14 @@ var view = Marionette.ItemView.extend({ options.ignoreEpisodesWithoutFiles = true; } - else if (monitor === 'latest') { - this.model.setSeasonPass(lastSeason.seasonNumber); - } + // else if (monitor === 'latest') { + // this.model.setSeasonPass(lastSeason.seasonNumber); + // } - else if (monitor === 'first') { - this.model.setSeasonPass(lastSeason.seasonNumber + 1); - this.model.setSeasonMonitored(firstSeason.seasonNumber); - } + // else if (monitor === 'first') { + // this.model.setSeasonPass(lastSeason.seasonNumber + 1); + // this.model.setSeasonMonitored(firstSeason.seasonNumber); + // } else if (monitor === 'missing') { options.ignoreEpisodesWithFiles = true; @@ -262,9 +262,9 @@ var view = Marionette.ItemView.extend({ options.ignoreEpisodesWithoutFiles = true; } - else if (monitor === 'none') { - this.model.setSeasonPass(lastSeason.seasonNumber + 1); - } + // else if (monitor === 'none') { + // this.model.setSeasonPass(lastSeason.seasonNumber + 1); + // } return options; } diff --git a/src/UI/Settings/MediaManagement/FileManagement/FileManagementViewTemplate.hbs b/src/UI/Settings/MediaManagement/FileManagement/FileManagementViewTemplate.hbs index 2a3dd5d51..9fd640ec0 100644 --- a/src/UI/Settings/MediaManagement/FileManagement/FileManagementViewTemplate.hbs +++ b/src/UI/Settings/MediaManagement/FileManagement/FileManagementViewTemplate.hbs @@ -2,7 +2,7 @@ File Management
- +
@@ -17,7 +17,7 @@ - +
@@ -39,7 +39,7 @@ - +
diff --git a/src/UI/Settings/MediaManagement/Naming/Basic/BasicNamingView.js b/src/UI/Settings/MediaManagement/Naming/Basic/BasicNamingView.js index 916a15aed..2f6320ac8 100644 --- a/src/UI/Settings/MediaManagement/Naming/Basic/BasicNamingView.js +++ b/src/UI/Settings/MediaManagement/Naming/Basic/BasicNamingView.js @@ -26,10 +26,10 @@ var view = Marionette.ItemView.extend({ }, _parseNamingModel : function() { - var standardFormat = this.namingModel.get('standardEpisodeFormat'); + var standardFormat = this.namingModel.get('standardMovieFormat'); - var includeSeriesTitle = standardFormat.match(/\{Series[-_. ]Title\}/i); - var includeEpisodeTitle = standardFormat.match(/\{Episode[-_. ]Title\}/i); + var includeSeriesTitle = false;//standardFormat.match(/\{Series[-_. ]Title\}/i); + var includeEpisodeTitle = false;//standardFormat.match(/\{Episode[-_. ]Title\}/i); var includeQuality = standardFormat.match(/\{Quality[-_. ]Title\}/i); var numberStyle = standardFormat.match(/s?\{season(?:\:0+)?\}[ex]\{episode(?:\:0+)?\}/i); var replaceSpaces = standardFormat.indexOf(' ') === -1; @@ -115,4 +115,4 @@ var view = Marionette.ItemView.extend({ } }); -module.exports = AsModelBoundView.call(view); \ No newline at end of file +module.exports = AsModelBoundView.call(view); diff --git a/src/UI/Settings/MediaManagement/Naming/NamingView.js b/src/UI/Settings/MediaManagement/Naming/NamingView.js index 71e4df4f8..5496fb784 100644 --- a/src/UI/Settings/MediaManagement/Naming/NamingView.js +++ b/src/UI/Settings/MediaManagement/Naming/NamingView.js @@ -19,7 +19,9 @@ module.exports = (function() { namingTokenHelper : '.x-naming-token-helper', multiEpisodeStyle : '.x-multi-episode-style', seriesFolderExample : '.x-series-folder-example', - seasonFolderExample : '.x-season-folder-example' + seasonFolderExample : '.x-season-folder-example', + movieExample : '.x-movie-example', + movieFolderExample : '.x-movie-folder-example' }, events : { "change .x-rename-episodes" : '_setFailedDownloadOptionsVisibility', @@ -58,6 +60,8 @@ module.exports = (function() { this.ui.animeMultiEpisodeExample.html(this.namingSampleModel.get('animeMultiEpisodeExample')); this.ui.seriesFolderExample.html(this.namingSampleModel.get('seriesFolderExample')); this.ui.seasonFolderExample.html(this.namingSampleModel.get('seasonFolderExample')); + this.ui.movieExample.html(this.namingSampleModel.get('movieExample')); + this.ui.movieFolderExample.html(this.namingSampleModel.get('movieFolderExample')); }, _addToken : function(e) { e.preventDefault(); diff --git a/src/UI/Settings/MediaManagement/Naming/NamingViewTemplate.hbs b/src/UI/Settings/MediaManagement/Naming/NamingViewTemplate.hbs index 361954d70..615f95b1a 100644 --- a/src/UI/Settings/MediaManagement/Naming/NamingViewTemplate.hbs +++ b/src/UI/Settings/MediaManagement/Naming/NamingViewTemplate.hbs @@ -1,8 +1,8 @@
- Episode Naming + Movie Naming
- +
@@ -18,7 +18,7 @@ - +
@@ -51,25 +51,23 @@
- +
- +
- +
-
+ {{!--
@@ -111,9 +109,9 @@
-
+
--}} -
+ {{!--
@@ -144,31 +142,32 @@
-
+ --}}
- +
- +
- +
-
+ {{!--
@@ -186,9 +185,9 @@
- + --}} -
+ {{!--
@@ -203,17 +202,17 @@
-
+ --}}
- +
-

+

-
+ {{!--
@@ -242,21 +241,21 @@

-
+
--}}
- +
-

+

-
+ {{!--

-
+
--}}
diff --git a/src/UI/Settings/MediaManagement/Naming/Partials/MovieTitleNamingPartial.hbs b/src/UI/Settings/MediaManagement/Naming/Partials/MovieTitleNamingPartial.hbs new file mode 100644 index 000000000..916416fdb --- /dev/null +++ b/src/UI/Settings/MediaManagement/Naming/Partials/MovieTitleNamingPartial.hbs @@ -0,0 +1,11 @@ + diff --git a/src/UI/Settings/MediaManagement/Naming/Partials/ReleaseYearNamingPartial.hbs b/src/UI/Settings/MediaManagement/Naming/Partials/ReleaseYearNamingPartial.hbs new file mode 100644 index 000000000..0a4153d66 --- /dev/null +++ b/src/UI/Settings/MediaManagement/Naming/Partials/ReleaseYearNamingPartial.hbs @@ -0,0 +1 @@ +
  • Release Year
  • \ No newline at end of file diff --git a/src/UI/Settings/MediaManagement/Sorting/SortingViewTemplate.hbs b/src/UI/Settings/MediaManagement/Sorting/SortingViewTemplate.hbs index c78c7393a..c0784c942 100644 --- a/src/UI/Settings/MediaManagement/Sorting/SortingViewTemplate.hbs +++ b/src/UI/Settings/MediaManagement/Sorting/SortingViewTemplate.hbs @@ -2,7 +2,7 @@ Folders
    - +
    @@ -18,7 +18,7 @@ - +
    @@ -46,7 +46,7 @@ - +
    @@ -71,7 +71,7 @@ - +