private void ExtractFileImages(ILocalFsResourceAccessor lfsra, Guid?albumMediaItemId, string albumTitle)
        {
            if (!albumMediaItemId.HasValue)
            {
                return;
            }

            string mediaItemId = albumMediaItemId.Value.ToString().ToUpperInvariant();

            TagLib.File tag;
            try
            {
                ByteVector.UseBrokenLatin1Behavior = true; // Otherwise we have problems retrieving non-latin1 chars
                tag = TagLib.File.Create(new AudioMetadataExtractor.ResourceProviderFileAbstraction(lfsra));
            }
            catch (CorruptFileException)
            {
                // Only log at the info level here - And simply return false. This makes the importer know that we
                // couldn't perform our task here.
                Logger.Info("AudioFanArtHandler: Audio file '{0}' seems to be broken", lfsra.CanonicalLocalResourcePath);
                return;
            }

            using (tag)
            {
                IPicture[] pics = tag.Tag.Pictures;
                if (pics.Length > 0)
                {
                    try
                    {
                        string fanArtType = FanArtTypes.Cover;
                        using (FanArtCache.FanArtCountLock countLock = FanArtCache.GetFanArtCountLock(mediaItemId, fanArtType))
                        {
                            if (countLock.Count >= FanArtCache.MAX_FANART_IMAGES[fanArtType])
                            {
                                return;
                            }

                            FanArtCache.InitFanArtCache(mediaItemId, albumTitle);
                            string cacheFile = GetCacheFileName(mediaItemId, fanArtType, "File." + Path.GetFileNameWithoutExtension(lfsra.LocalFileSystemPath) + ".jpg");
                            if (!System.IO.File.Exists(cacheFile))
                            {
                                using (MemoryStream ms = new MemoryStream(pics[0].Data.Data))
                                {
                                    using (Image img = Image.FromStream(ms, true, true))
                                    {
                                        img.Save(cacheFile, System.Drawing.Imaging.ImageFormat.Jpeg);
                                        countLock.Count++;
                                    }
                                }
                            }
                        }
                    }
                    // Decoding of invalid image data can fail, but main MediaItem is correct.
                    catch { }
                }
            }
        }
Пример #2
0
        private void SaveFolderFile(IResourceLocator mediaItemLocater, ResourcePath file, string fanartType, Guid parentId, string title)
        {
            string mediaItemId = parentId.ToString().ToUpperInvariant();

            using (FanArtCache.FanArtCountLock countLock = FanArtCache.GetFanArtCountLock(mediaItemId, fanartType))
            {
                if (countLock.Count >= FanArtCache.MAX_FANART_IMAGES[fanartType])
                {
                    return;
                }

                if ((MovieMetadataExtractor.CacheOfflineFanArt && mediaItemLocater.NativeResourcePath.IsNetworkResource) ||
                    (MovieMetadataExtractor.CacheLocalFanArt && !mediaItemLocater.NativeResourcePath.IsNetworkResource && mediaItemLocater.NativeResourcePath.IsValidLocalPath))
                {
                    FanArtCache.InitFanArtCache(mediaItemId, title);
                    string cacheFile = GetCacheFileName(mediaItemId, fanartType, "Folder." + ResourcePathHelper.GetFileName(file.ToString()));
                    if (!File.Exists(cacheFile))
                    {
                        using (var fileRa = new ResourceLocator(mediaItemLocater.NativeSystemId, file).CreateAccessor())
                        {
                            var fileFsra = fileRa as IFileSystemResourceAccessor;
                            if (fileFsra != null)
                            {
                                using (Stream ms = fileFsra.OpenRead())
                                {
                                    using (Image img = Image.FromStream(ms, true, true))
                                    {
                                        img.Save(cacheFile);
                                        countLock.Count++;
                                    }
                                }
                            }
                        }
                    }
                }
                else
                {
                    //Also count local FanArt
                    countLock.Count++;
                }
            }
        }
Пример #3
0
 public void DeleteFanArt(Guid mediaItemId)
 {
     Task.Run(() => FanArtCache.DeleteFanArtFiles(mediaItemId.ToString()));
 }
Пример #4
0
        private void ExtractMkvImages(ILocalFsResourceAccessor lfsra, Guid?movieMediaItemId, string movieTitle)
        {
            if (!movieMediaItemId.HasValue)
            {
                return;
            }

            string mediaItemId    = movieMediaItemId.Value.ToString().ToUpperInvariant();
            string fileSystemPath = string.Empty;
            IDictionary <string, string> patterns = new Dictionary <string, string>()
            {
                { "banner.", FanArtTypes.Banner },
                { "clearart.", FanArtTypes.ClearArt },
                { "cover.", FanArtTypes.Cover },
                { "poster.", FanArtTypes.Poster },
                { "folder.", FanArtTypes.Poster },
                { "backdrop.", FanArtTypes.FanArt },
                { "fanart.", FanArtTypes.FanArt },
            };

            // File based access
            try
            {
                if (lfsra != null)
                {
                    fileSystemPath = lfsra.LocalFileSystemPath;
                    var ext = ResourcePathHelper.GetExtension(lfsra.LocalFileSystemPath);
                    if (!MKV_EXTENSIONS.Contains(ext))
                    {
                        return;
                    }

                    MatroskaInfoReader mkvReader = new MatroskaInfoReader(lfsra);
                    foreach (string pattern in patterns.Keys)
                    {
                        byte[] binaryData;
                        if (mkvReader.GetAttachmentByName(pattern, out binaryData))
                        {
                            string fanArtType = patterns[pattern];
                            using (FanArtCache.FanArtCountLock countLock = FanArtCache.GetFanArtCountLock(mediaItemId, fanArtType))
                            {
                                if (countLock.Count >= FanArtCache.MAX_FANART_IMAGES[fanArtType])
                                {
                                    return;
                                }

                                FanArtCache.InitFanArtCache(mediaItemId, movieTitle);
                                string cacheFile = GetCacheFileName(mediaItemId, fanArtType, "File." + pattern + Path.GetFileNameWithoutExtension(lfsra.LocalFileSystemPath) + ".jpg");
                                if (!File.Exists(cacheFile))
                                {
                                    using (MemoryStream ms = new MemoryStream(binaryData))
                                    {
                                        using (Image img = Image.FromStream(ms, true, true))
                                        {
                                            img.Save(cacheFile, System.Drawing.Imaging.ImageFormat.Jpeg);
                                            countLock.Count++;
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                Logger.Warn("MovieFanArtHandler: Exception while reading mkv attachments from '{0}'", ex, fileSystemPath);
            }
        }
Пример #5
0
        /// <summary>
        /// Gets a list of <see cref="FanArtImage"/>s for a requested <paramref name="mediaType"/>, <paramref name="fanArtType"/> and <paramref name="name"/>.
        /// The name can be: Series name, Actor name, Artist name depending on the <paramref name="mediaType"/>.
        /// </summary>
        /// <param name="mediaType">Requested FanArtMediaType</param>
        /// <param name="fanArtType">Requested FanArtType</param>
        /// <param name="name">Requested name of Series, Actor, Artist...</param>
        /// <param name="maxWidth">Maximum width for image. <c>0</c> returns image in original size.</param>
        /// <param name="maxHeight">Maximum height for image. <c>0</c> returns image in original size.</param>
        /// <param name="singleRandom">If <c>true</c> only one random image URI will be returned</param>
        /// <param name="result">Result if return code is <c>true</c>.</param>
        /// <returns><c>true</c> if at least one match was found.</returns>
        public bool TryGetFanArt(string mediaType, string fanArtType, string name, int maxWidth, int maxHeight, bool singleRandom, out IList <IResourceLocator> result)
        {
            result = null;

            if (!VALID_MEDIA_TYPES.Contains(mediaType) || !VALID_FANART_TYPES.Contains(fanArtType))
            {
                return(false);
            }

            if (string.IsNullOrWhiteSpace(name))
            {
                return(false);
            }

            Guid mediaItemId;

            if (Guid.TryParse(name, out mediaItemId) == false)
            {
                return(false);
            }

            List <string> fanArtFiles = new List <string>();

            fanArtFiles.AddRange(FanArtCache.GetFanArtFiles(mediaItemId.ToString().ToUpperInvariant(), fanArtType));

            // Try fallback
            if (fanArtFiles.Count == 0 &&
                (mediaType == FanArtMediaTypes.SeriesSeason ||
                 mediaType == FanArtMediaTypes.Character ||
                 (mediaType == FanArtMediaTypes.Episode && fanArtType == FanArtTypes.FanArt)))
            {
                IMediaLibrary mediaLibrary = ServiceRegistration.Get <IMediaLibrary>(false);
                if (mediaLibrary == null)
                {
                    return(false);
                }

                IFilter           filter = new MediaItemIdFilter(mediaItemId);
                IList <MediaItem> items  = mediaLibrary.Search(new MediaItemQuery(NECESSARY_MIAS, OPTIONAL_MIAS, filter), false, null, true);
                if (items == null || items.Count == 0)
                {
                    return(false);
                }

                MediaItem mediaItem = items.First();

                if (mediaType == FanArtMediaTypes.Episode && fanArtType == FanArtTypes.FanArt)
                {
                    if (mediaItem.Aspects.ContainsKey(EpisodeAspect.ASPECT_ID))
                    {
                        IList <MultipleMediaItemAspect> relationAspects;
                        if (MediaItemAspect.TryGetAspects(mediaItem.Aspects, RelationshipAspect.Metadata, out relationAspects))
                        {
                            //Season fallback
                            foreach (MultipleMediaItemAspect relation in relationAspects)
                            {
                                if ((Guid?)relation[RelationshipAspect.ATTR_LINKED_ROLE] == SeasonAspect.ROLE_SEASON)
                                {
                                    fanArtFiles.AddRange(FanArtCache.GetFanArtFiles(relation[RelationshipAspect.ATTR_LINKED_ID].ToString().ToUpperInvariant(), fanArtType));
                                    if (fanArtFiles.Count > 0)
                                    {
                                        break;
                                    }
                                }
                            }

                            //Series fallback
                            if (fanArtFiles.Count == 0)
                            {
                                foreach (MultipleMediaItemAspect relation in relationAspects)
                                {
                                    if ((Guid?)relation[RelationshipAspect.ATTR_LINKED_ROLE] == SeriesAspect.ROLE_SERIES)
                                    {
                                        fanArtFiles.AddRange(FanArtCache.GetFanArtFiles(relation[RelationshipAspect.ATTR_LINKED_ID].ToString().ToUpperInvariant(), fanArtType));
                                        if (fanArtFiles.Count > 0)
                                        {
                                            break;
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
                else if (mediaType == FanArtMediaTypes.SeriesSeason)
                {
                    if (mediaItem.Aspects.ContainsKey(SeasonAspect.ASPECT_ID))
                    {
                        IList <MultipleMediaItemAspect> relationAspects;
                        if (MediaItemAspect.TryGetAspects(mediaItem.Aspects, RelationshipAspect.Metadata, out relationAspects))
                        {
                            foreach (MultipleMediaItemAspect relation in relationAspects)
                            {
                                if ((Guid?)relation[RelationshipAspect.ATTR_LINKED_ROLE] == SeriesAspect.ROLE_SERIES)
                                {
                                    fanArtFiles.AddRange(FanArtCache.GetFanArtFiles(relation[RelationshipAspect.ATTR_LINKED_ID].ToString().ToUpperInvariant(), fanArtType));
                                    if (fanArtFiles.Count > 0)
                                    {
                                        break;
                                    }
                                }
                            }
                        }
                    }
                }
                else if (mediaType == FanArtMediaTypes.Character)
                {
                    if (mediaItem.Aspects.ContainsKey(CharacterAspect.ASPECT_ID))
                    {
                        IList <MultipleMediaItemAspect> relationAspects;
                        if (MediaItemAspect.TryGetAspects(mediaItem.Aspects, RelationshipAspect.Metadata, out relationAspects))
                        {
                            foreach (MultipleMediaItemAspect relation in relationAspects)
                            {
                                if ((Guid?)relation[RelationshipAspect.ATTR_LINKED_ROLE] == PersonAspect.ROLE_ACTOR)
                                {
                                    fanArtFiles.AddRange(FanArtCache.GetFanArtFiles(relation[RelationshipAspect.ATTR_LINKED_ID].ToString().ToUpperInvariant(), fanArtType));
                                    if (fanArtFiles.Count > 0)
                                    {
                                        break;
                                    }
                                }
                            }
                        }
                    }
                }
            }

            List <IResourceLocator> files = new List <IResourceLocator>();

            try
            {
                files.AddRange(fanArtFiles
                               .Select(fileName => new ResourceLocator(ResourcePath.BuildBaseProviderPath(LocalFsResourceProviderBase.LOCAL_FS_RESOURCE_PROVIDER_ID, fileName)))
                               );
                result = files;
                return(result.Count > 0);
            }
            catch (Exception) { }
            return(false);
        }
Пример #6
0
        protected override int SaveFanArtImages(string id, IEnumerable <TrackImage> images, string language, string mediaItemId, string name, string fanartType)
        {
            try
            {
                if (images == null)
                {
                    return(0);
                }

                string imgType = null;
                if (fanartType == FanArtTypes.Cover)
                {
                    imgType = "Front";
                }
                else if (fanartType == FanArtTypes.DiscArt)
                {
                    imgType = "Medium";
                }

                if (imgType == null)
                {
                    return(0);
                }

                int idx = 0;
                foreach (TrackImage img in images)
                {
                    using (FanArtCache.FanArtCountLock countLock = FanArtCache.GetFanArtCountLock(mediaItemId, fanartType))
                    {
                        if (countLock.Count >= FanArtCache.MAX_FANART_IMAGES[fanartType])
                        {
                            break;
                        }
                        if (idx >= FanArtCache.MAX_FANART_IMAGES[fanartType])
                        {
                            break;
                        }

                        foreach (string imageType in img.Types)
                        {
                            if (imageType.Equals(imgType, StringComparison.InvariantCultureIgnoreCase))
                            {
                                FanArtCache.InitFanArtCache(mediaItemId, name);
                                if (_wrapper.DownloadFanArt(id, img, Path.Combine(FANART_CACHE_PATH, mediaItemId, fanartType)))
                                {
                                    countLock.Count++;
                                    idx++;
                                }
                                break;
                            }
                        }
                    }
                }
                Logger.Debug(GetType().Name + @" Download: Saved {0} for media item {1} ({2}) of type {3}", idx, mediaItemId, name, fanartType);
                return(idx);
            }
            catch (Exception ex)
            {
                Logger.Debug(GetType().Name + " Download: Exception downloading images for ID {0} [{1} ({2})]", ex, id, mediaItemId, name);
                return(0);
            }
        }
Пример #7
0
        private int SaveBanners(IEnumerable <TvdbBanner> banners, TvdbLanguage language, string mediaItemId, string name, string fanartType)
        {
            int idx = 0;

            foreach (TvdbBanner tvdbBanner in banners)
            {
                if (tvdbBanner.Language != TvdbLanguage.UniversalLanguage && tvdbBanner.Language != language && language != null && tvdbBanner.Language != null)
                {
                    continue;
                }

                using (FanArtCache.FanArtCountLock countLock = FanArtCache.GetFanArtCountLock(mediaItemId, fanartType))
                {
                    if (countLock.Count >= FanArtCache.MAX_FANART_IMAGES[fanartType])
                    {
                        break;
                    }

                    if (idx >= FanArtCache.MAX_FANART_IMAGES[fanartType])
                    {
                        break;
                    }

                    if (fanartType == FanArtTypes.Banner)
                    {
                        if (!tvdbBanner.BannerPath.Contains("wide") && !tvdbBanner.BannerPath.Contains("graphical"))
                        {
                            continue;
                        }
                    }

                    if (!tvdbBanner.IsLoaded)
                    {
                        // We need the image only loaded once, later we will access the cache directly
                        try
                        {
                            FanArtCache.InitFanArtCache(mediaItemId, name);
                            tvdbBanner.CachePath = Path.Combine(FANART_CACHE_PATH, mediaItemId, fanartType);
                            tvdbBanner.LoadBanner();
                            tvdbBanner.UnloadBanner(true);
                            idx++;
                            countLock.Count++;
                        }
                        catch (Exception ex)
                        {
                            Logger.Debug(GetType().Name + " Download: Exception saving images for ID {0} [{1} ({2})]", ex, tvdbBanner.Id, mediaItemId, name);
                        }
                    }
                }
            }
            if (idx > 0)
            {
                Logger.Debug(GetType().Name + @" Download: Saved {0} for media item {1} ({2}) of type {3}", idx, mediaItemId, name, fanartType);
                return(idx);
            }

            // Try fallback languages if no images found for preferred
            if (language != TvdbLanguage.UniversalLanguage && language != TvdbLanguage.DefaultLanguage)
            {
                if (_useUniversalLanguage)
                {
                    idx = SaveBanners(banners, TvdbLanguage.UniversalLanguage, mediaItemId, name, fanartType);
                    if (idx > 0)
                    {
                        return(idx);
                    }
                }

                idx = SaveBanners(banners, TvdbLanguage.DefaultLanguage, mediaItemId, name, fanartType);
            }
            Logger.Debug(GetType().Name + @" Download: Saved {0} for media item {1} ({2}) of type {3}", idx, mediaItemId, name, fanartType);
            return(idx);
        }