private void SetGalleryCacheSize()
        {
            // gallery
            long thumbnailCachesize = MyFile.DirectorySize(@"cache\gallery", "poster*.jpg");

            labelForGalleryCacheSize.Text = MyFile.FormatSize(thumbnailCachesize);
        }
Example #2
0
        private void SetListItem(VideoInfo videoInfo, VideoItemFile videoItemFile, string fileType)
        {
            VideoItemFileInfo videoItemFileInfo = new VideoItemFileInfo();

            videoItemFileInfo.videoInfo     = videoInfo;
            videoItemFileInfo.videoItemFile = videoItemFile;

            // if not already in image list, add to it
            if (!smallImageList.Images.ContainsKey(videoItemFile.Extension))
            {
                Icon icon = MyFileTypeIcon.Get(videoItemFileInfo.GetFullName());
                if (icon != null)
                {
                    smallImageList.Images.Add(videoItemFile.Extension, icon);
                }
            }

            ListViewItem listViewItem = new ListViewItem(videoItemFile.Name);

            listViewItem.ImageKey = videoItemFile.Extension;
            listViewItem.SubItems.Add(fileType);
            string fileSize = Convert.ToString(MyFile.FormatSize(videoItemFile.Length));

            listViewItem.SubItems.Add(fileSize);


            listViewItem.Tag = videoItemFileInfo;

            listView.Items.Add(listViewItem);
        }
Example #3
0
        public static bool Save()
        {
            if (listVideoInfos == null)
            {
                return(false);
            }

            Stopwatch stopWatch = new Stopwatch();

            stopWatch.Start();
            MyLog.Add("Saving VideoItems -->");

            foreach (ConfigSettings.Source settingsSource in Config.settings.sources)
            {
                string dataFile = MyFile.EnsureDataFile("videos", Config.settings.exportExt, "data", settingsSource.alias);
                if (dataFile == null)
                {
                    continue;
                }

                List <VideoInfo> saveVideoInfos = new List <VideoInfo>(listVideoInfos.Count());
                saveVideoInfos = listVideoInfos.Where(x => x.sourceAlias == settingsSource.alias && x.videoItem != null && x.videoItem.title != null).OrderBy(x => x.videoItem.title).ToList();


                if (saveVideoInfos == null)
                {
                    continue;
                }
                int nbrVideoInfos = saveVideoInfos.Count();
                if (nbrVideoInfos == 0)
                {
                    continue;
                }

                MyLog.RotateFiles(dataFile);
                MySerialize.ToFile(Config.settings.exportFormat, dataFile, saveVideoInfos);


                FileInfo fileInfo = MyFile.FileInfo(dataFile);
                string   toFile   = "to " + dataFile.Replace(MyFile.exeDirectory, "");
                if (fileInfo != null)
                {
                    toFile += " " + MyFile.FormatSize(fileInfo.Length);
                }
                MyLog.Add("Saved " + nbrVideoInfos + " VideoItems " + toFile);
            }

            stopWatch.Stop();
            MyLog.AddElapsed("<-- in ", stopWatch.Elapsed);

            return(true);
        }
        public static bool Load()
        {
            bool      ret       = false;
            Stopwatch stopWatch = new Stopwatch();

            stopWatch.Start();

            // MyLog.Add("Loading VideoItemStats");

            string dataFile = MyFile.EnsureDataFile("stats", Config.settings.exportExt, "stats");

            if (dataFile == null)
            {
                return(false);
            }

            // keep a backup of settings
            if (File.Exists(dataFile))
            {
                videoInfoStats = new VideoInfoStats();
                videoInfoStats = (VideoInfoStats)MyDeserialize.FromFile(Config.settings.exportFormat, dataFile, videoInfoStats);

                string   fromFIle = "from " + dataFile.Replace(MyFile.exeDirectory, "");
                FileInfo fileInfo = MyFile.FileInfo(dataFile);
                if (fileInfo != null)
                {
                    fromFIle += " " + MyFile.FormatSize(fileInfo.Length);
                }
                MyLog.Add("Loaded VideoInfoStats " + fromFIle);

                if (videoInfoStats != null && videoInfoStats.year != null && videoInfoStats.year.Count() > 0)
                {
                    ret = true;
                }
            }
            else
            {
                // MyLog.Add("No VideoInfoStats to load ");
            }

            stopWatch.Stop();

            if (ret)
            {
                MyLog.AddElapsed(stopWatch.Elapsed);
            }

            return(ret);
        }
Example #5
0
        /// <summary>
        /// log message to the log file
        /// always log exceptions e.ToString() so can debug/fix
        /// </summary>
        /// <param name="message"></param>
        public static void Add(string message)
        {
            if (logFile == null)
            {
                logFile = MyFile.EnsureDataFile("mve", "log", "logs");
            }

            try
            {
                string privateMemorySize;
                using (Process currentProcess = Process.GetCurrentProcess())
                {
                    privateMemorySize = MyFile.FormatSize(currentProcess.PrivateMemorySize64);
                }

                using (StreamWriter streamWriter = File.AppendText(logFile))
                {
                    streamWriter.WriteLine("{0} | {1} | {2} | ", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.ff"), privateMemorySize, message);
                }
            }
            catch (Exception e)
            {
                if (Application.OpenForms.Count > 0)
                {
                    MessageBox.Show("Unable to write to log [" + e.Message + "]");
                }
            }

            // check if should rotate logs; but only check occasionaly, to reduce io checks
            Random random = new Random();

            if (random.Next(1, 100) < 20)
            {
                RotateLogs(logFile);
            }
        }
Example #6
0
        public static bool Load()
        {
            Stopwatch stopWatch = new Stopwatch();

            stopWatch.Start();

            MyLog.Add("Loading VideoItems -->");

            int      nbrVideoInfos;
            FileInfo fileInfo;

            CreateList();
            foreach (ConfigSettings.Source source in Config.settings.sources)
            {
                string dataFile = MyFile.EnsureDataFile("videos", Config.settings.exportExt, "data", source.alias);
                if (dataFile == null)
                {
                    continue;
                }

                // keep a backup of settings
                if (File.Exists(dataFile))
                {
                    fileInfo = MyFile.FileInfo(dataFile);
                    List <VideoInfo> loadVideoInfos = (List <VideoInfo>)MyDeserialize.FromFile(Config.settings.exportFormat, dataFile, listVideoInfos);
                    if (loadVideoInfos == null)
                    {
                        MyLog.Add("Unable to load VideoInfos from " + dataFile);
                        continue;
                    }
                    AddItems(loadVideoInfos);

                    string fromFile = "from " + dataFile.Replace(MyFile.exeDirectory, "");
                    if (fileInfo != null)
                    {
                        fromFile += " " + MyFile.FormatSize(fileInfo.Length);
                    }

                    if (loadVideoInfos == null)
                    {
                        nbrVideoInfos = 0;
                    }
                    else
                    {
                        nbrVideoInfos = loadVideoInfos.Count();
                    }
                    MyLog.Add("Loaded " + nbrVideoInfos + " VideoItems " + fromFile);
                }
            }

            EnsureVideoInfos();

            stopWatch.Stop();


            if (listVideoInfos == null)
            {
                nbrVideoInfos = 0;
            }
            else
            {
                nbrVideoInfos = listVideoInfos.Count();
            }

            MyLog.AddElapsed("<-- in ", stopWatch.Elapsed);

            bool loaded = nbrVideoInfos > 0 ? true : false;

            return(loaded);
        }
Example #7
0
        public bool SetImages(VideoInfo videoInfo)
        {
            // nothing to see
            if (videoInfo.files == null || videoInfo.files.images == null)
            {
                return(false);
            }

            // set big picture box to poster, if avail
            if (videoInfo.files != null && videoInfo.files.poster != null)
            {
                Image posterImage = MyImage.GetImageFromFile(videoInfo.GetFullName(videoInfo.files.poster));
                pictureBoxImage.Image = posterImage;
            }
            else
            {
                if (pictureBoxImage.Image != null)
                {
                    pictureBoxImage.Image.Dispose();
                }
                pictureBoxImage.Image = null;
            }


            flowLayoutPanelImages.SuspendLayout();

            // remove prior images, for memory management funz

            /*
             * http://msdn.microsoft.com/en-us/library/system.windows.forms.control.controlcollection.clear%28v=vs.110%29.aspx
             * Calling the Clear method does not remove control handles from memory.
             */
            // flowLayoutPanelImages.Controls.Clear();
            foreach (PictureBox priorPictureImage in flowLayoutPanelImages.Controls.OfType <PictureBox>())
            {
                if (priorPictureImage.Image != null)
                {
                    priorPictureImage.Image.Dispose();
                }
                priorPictureImage.Image = null;
            }
            while (flowLayoutPanelImages.Controls.Count > 0)
            {
                flowLayoutPanelImages.Controls.RemoveAt(0);
            }



            PictureBox pictureBox;

            foreach (VideoItemFile videoItemFile in videoInfo.files.images)
            {
                string imageFullName = videoInfo.GetFullName(videoItemFile);
                // skip images smaller than y or larger than x
                if (videoItemFile.Length < 100)
                {
                    MyLog.Add("SetImages: Skipping " + imageFullName + " " + MyFile.FormatSize(videoItemFile.Length));
                    continue;
                }
                if (videoItemFile.Length > 5 * 1048576)
                {
                    MyLog.Add("SetImages: Skipping " + imageFullName + " " + MyFile.FormatSize(videoItemFile.Length));
                    continue;
                }

                Image image = MyImage.GetImageFromFile(imageFullName);

                try
                {
                    pictureBox          = new PictureBox();
                    pictureBox.Size     = new Size(75, 75);
                    pictureBox.Image    = image;
                    pictureBox.SizeMode = PictureBoxSizeMode.Zoom; // keep aspect ratio
                    pictureBox.Cursor   = Cursors.Hand;
                    pictureBox.Click   += this.imageList_Click;

                    flowLayoutPanelImages.Controls.Add(pictureBox);
                }
                catch (Exception e)
                {
                    // skip
                    MyLog.Add("SetImages: " + imageFullName + "\n" + e.ToString());
                }
            }

            flowLayoutPanelImages.ResumeLayout();

            return(true);
        }
Example #8
0
        public static bool Decompress(string source)
        {
            FileInfo sourceFileInfo = MyFile.FileInfo(source);

            if (sourceFileInfo == null)
            {
                return(false);
            }
            try
            {
                using (FileStream originalFileStream = sourceFileInfo.OpenRead())
                {
                    string currentFileName = sourceFileInfo.FullName;
                    string newFileName     = currentFileName.Remove(currentFileName.Length - sourceFileInfo.Extension.Length);

                    using (FileStream decompressedFileStream = File.Create(newFileName))
                    {
                        using (GZipStream decompressionStream = new GZipStream(originalFileStream, CompressionMode.Decompress))
                        {
                            decompressionStream.CopyTo(decompressedFileStream);
                            MyLog.Add(String.Format("Decompressed {0} from {1} to {2}", sourceFileInfo.Name, MyFile.FormatSize(sourceFileInfo.Length), MyFile.FormatSize(decompressionStream.Length)));
                        }
                    }
                }
            }
            catch (Exception e)
            {
                MyLog.Add(e.ToString());
                return(false);
            }
            return(true);
        }
Example #9
0
        public static bool Compress(string source, string target, string targetExt)
        {
            FileInfo sourceFileInfo = MyFile.FileInfo(source);

            if (sourceFileInfo == null)
            {
                return(false);
            }
            try
            {
                using (FileStream originalFileStream = sourceFileInfo.OpenRead())
                {
                    using (FileStream compressedFileStream = File.Create(target + targetExt))
                    {
                        using (GZipStream compressionStream = new GZipStream(compressedFileStream, CompressionMode.Compress))
                        {
                            originalFileStream.CopyTo(compressionStream);
                            MyLog.Add(String.Format("Compressed {0} from {1} to {2}", sourceFileInfo.Name, MyFile.FormatSize(sourceFileInfo.Length), MyFile.FormatSize(compressedFileStream.Length)));
                        }
                    }
                }
            }
            catch (Exception e)
            {
                MyLog.Add(e.ToString());
                return(false);
            }
            return(true);
        }
Example #10
0
        public void SetForm(VideoInfo videoInfo)
        {
            this.selectedVideoInfo = videoInfo;
            VideoItem videoItem = videoInfo.videoItem;

            try
            {
                // set search title
                MyFormField.SetTextBoxText(textBoxTitle, videoItem.title);

                // set movie set
                MyFormField.SetTextBoxText(textBoxMovieSet, videoItem.movieset);

                // set plot
                MyFormField.SetRichTextBoxText(richTextBoxPlot, videoItem.plot);

                // set runtime
                MyFormField.SetTextBoxText(textBoxRunTime, videoItem.runtime.ToString());

                // set tagline
                // MyFormField.SetTextBoxText(textBoxTagLine, videoItem.tagline); // not yet

                // set notes
                MyFormField.SetRichTextBoxText(richTextBoxNotes, videoItem.notes);

                if (videoItem.encoding != null)
                {
                    // set width
                    if (videoItem.encoding.width > 0)
                    {
                        MyFormField.SetTextBoxText(textBoxWidth, videoItem.encoding.width.ToString());
                    }
                    else
                    {
                        MyFormField.SetTextBoxText(textBoxWidth, "");
                    }

                    // set height
                    if (videoItem.encoding.height > 0)
                    {
                        MyFormField.SetTextBoxText(textBoxHeight, videoItem.encoding.height.ToString());
                    }
                    else
                    {
                        MyFormField.SetTextBoxText(textBoxHeight, "");
                    }

                    // set bitrate
                    if (videoItem.encoding.bitrate > 0)
                    {
                        MyFormField.SetTextBoxText(textBoxBitrate, videoItem.encoding.bitrate.ToString());
                        string bitrateFormatted = MyFile.FormatSize(videoItem.encoding.bitrate, 2);
                        bitrateFormatted = bitrateFormatted.Replace(" ", "\n");
                        MyFormField.SetLabelText(labelForBitrateFormatted, bitrateFormatted);
                    }
                    else
                    {
                        MyFormField.SetTextBoxText(textBoxBitrate, "");
                        MyFormField.SetLabelText(labelForBitrateFormatted, "");
                    }

                    // set codec
                    if (!String.IsNullOrEmpty(videoItem.encoding.codec))
                    {
                        MyFormField.SetComboBoxValue(comboBoxCodec, videoItem.encoding.codec);
                    }
                    else
                    {
                        MyFormField.SetComboBoxValue(comboBoxCodec, "");
                    }
                }


                // set tag
                for (int index = dataGridViewTags.Rows.Count - 1; index >= 0; index--)
                {
                    if (dataGridViewTags.Rows[index].IsNewRow)
                    {
                        continue;
                    }
                    dataGridViewTags.Rows.RemoveAt(index);
                }
                if (videoItem.tags != null)
                {
                    IComparer <VideoItemTag <string> > sortVideoItemTag = new SortVideoItemTag();
                    videoItem.tags.Sort(sortVideoItemTag);
                    foreach (VideoItemTag <string> tag in videoItem.tags)
                    {
                        dataGridViewTags.Rows.Add(new object[] { tag.name });
                    }
                    // prevent add row from being auto selected
                    if (dataGridViewTags.CurrentCell != null)
                    {
                        dataGridViewTags.CurrentCell.Selected = false;
                    }
                }

                // set genre
                for (int index = dataGridViewGenres.Rows.Count - 1; index >= 0; index--)
                {
                    if (dataGridViewGenres.Rows[index].IsNewRow)
                    {
                        continue;
                    }
                    dataGridViewGenres.Rows.RemoveAt(index);
                }
                if (videoItem.genres != null)
                {
                    IComparer <VideoItemGenre <string> > sortVideoItemGenre = new SortVideoItemGenre();
                    videoItem.genres.Sort(sortVideoItemGenre);
                    foreach (VideoItemGenre <string> genre in videoItem.genres)
                    {
                        dataGridViewGenres.Rows.Add(new object[] { genre.name });
                    }
                    // prevent add row from being auto selected
                    if (dataGridViewGenres.CurrentCell != null)
                    {
                        dataGridViewGenres.CurrentCell.Selected = false;
                    }
                }

                // set bing link
                SetLinkLabelFromTitle(linkLabelBing, "https://www.bing.com/search?q=");

                // set google link
                SetLinkLabelFromTitle(linkLabelGoogle, "https://www.google.com/search?q=");

                // set google link
                SetLinkLabelFromTitle(linkLabelRT, "https://www.rottentomatoes.com/search/?search=");

                // set upc
                MyFormField.SetTextBoxText(textBoxUPC, videoItem.upc);

                // set tmdbId link
                MyFormField.SetTextBoxText(textBoxTMDB, videoItem.tmdbId);
                MyFormField.SetLinkLabel(linkLabelTMDB, "http://www.themoviedb.org/movie/", videoItem.tmdbId);

                // set imdbId link
                MyFormField.SetTextBoxText(textBoxIMDB, videoItem.imdbId);
                MyFormField.SetLinkLabel(linkLabelIMDB, "http://www.imdb.com/title/", videoItem.imdbId);


                // set year
                MyFormField.SetComboBoxValue(comboBoxYear, videoItem.year);

                // set imdbRating
                MyFormField.SetComboBoxValue(comboBoxIMDBRating, Convert.ToInt32(videoItem.imdbRating));

                // set mpaa
                MyFormField.SetComboBoxValue(comboBoxMPAA, videoItem.mpaa);

                // set playCount
                MyFormField.SetComboBoxValue(comboBoxPlayCount, videoItem.playCount);

                // set rating
                MyFormField.SetComboBoxValue(comboBoxRating, videoItem.rating);

                // set source
                MyFormField.SetComboBoxValue(comboBoxSource, videoItem.source);

                // set version
                MyFormField.SetComboBoxValue(comboBoxVersion, videoItem.version);

                // set lastPlayed
                MyFormField.SetLabelText(labelLastPlayed, videoItem.lastPlayed);

                // set labelUpdated
                MyFormField.SetLabelText(labelUpdated, videoInfo.updated);


                // set watched
                MyFormField.SetCheckBoxChecked(checkBoxWatched, ((videoItem.watched != "NO") ? true : false));

                // set actor/director
                for (int index = dataGridViewActors.Rows.Count - 1; index >= 0; index--)
                {
                    if (dataGridViewActors.Rows[index].IsNewRow)
                    {
                        continue;
                    }
                    dataGridViewActors.Rows.RemoveAt(index);
                }
                if (videoItem.directors != null)
                {
                    IComparer <VideoItemDirector <string> > sortVideoItemDirector = new SortVideoItemDirector();
                    videoItem.directors.Sort(sortVideoItemDirector);
                    foreach (VideoItemDirector <string> director in videoItem.directors)
                    {
                        dataGridViewActors.Rows.Add(new object[] { director.name, "Director" });
                    }
                }
                if (videoItem.actors != null)
                {
                    IComparer <VideoItemActor <string, string> > sortVideoItemActor = new SortVideoItemActor();
                    videoItem.actors.Sort(sortVideoItemActor);
                    foreach (VideoItemActor <string, string> actor in videoItem.actors)
                    {
                        dataGridViewActors.Rows.Add(new object[] { actor.name, actor.role });
                    }
                }
                // prevent add row from being auto selected
                if (dataGridViewActors.CurrentCell != null)
                {
                    dataGridViewActors.CurrentCell.Selected = false;
                }
            }
            catch (Exception e)
            {
                MyLog.Add(e.ToString());
            }

            this.Parent.Focus();
        }
Example #11
0
        public bool SyncUpVideoSource(FileInfo sourceFileInfo)
        {
            // clean up old uploads
            IEnumerable <string> files = MyFile.EnumerateFiles(@"sync", "*.gz");

            foreach (string file in files)
            {
                MyFile.DeleteFile(file);
            }

            // compress file, video source
            string compressedFile = @"sync\" + MyFile.SafeFileName(sourceFileInfo.Name);

            if (!MyFile.Compress(sourceFileInfo.FullName, compressedFile))
            {
                return(false);
            }

            // rename file so has 'rand' key/iv
            Random random     = new Random();
            int    rand       = random.Next(0, MyEncrypt.sharedKeys.Length - 1);
            string uploadFile = compressedFile.Replace("." + Config.settings.exportExt, "-" + rand + "." + Config.settings.exportExt);

            File.Move(compressedFile + ".gz", uploadFile + ".gz");



            string key       = MyEncrypt.sharedKeys[rand];
            string iv        = MyEncrypt.GenerateIV();
            string delimiter = "#";

            // now encrypt compressed file contents
            string fileContents = MyFile.ReadAllBinaryToString(uploadFile + ".gz");

            string contentsHeader = "{";

            contentsHeader += "\"apiKey\":\"" + this.apiKey + "\", ";
            contentsHeader += "\"iv\":\"" + iv + "\", ";
            contentsHeader += "\"sync\":" + MySerialize.ToJSON(Sync.syncSettings);
            contentsHeader += "}";

            contentsHeader = Convert.ToBase64String(Encoding.UTF8.GetBytes(contentsHeader));



            fileContents = MyEncrypt.EncryptRJ256(key, iv, fileContents);
            if (fileContents == null)
            {
                return(false);
            }

            contentsHeader = MyEncrypt.EncryptRJ256(key, iv, contentsHeader);

            string contentsToEncode = contentsHeader + delimiter + fileContents;

            // write base64 encoded file
            File.WriteAllText(uploadFile + ".enc", contentsToEncode);


            // log it
            FileInfo encodedFileInfo = MyFile.FileInfo(uploadFile + ".enc");

            if (encodedFileInfo == null)
            {
                return(false);
            }
            MyLog.Add(String.Format("Encrypted {0} to {1}", encodedFileInfo.Name, MyFile.FormatSize(encodedFileInfo.Length)));


            // test decrypt

            fileContents = MyFile.ReadAllText(uploadFile + ".enc");

            string[] fileParts = fileContents.Split(new string[] { delimiter }, StringSplitOptions.None);

            fileContents = MyEncrypt.DecryptRJ256(key, iv, fileParts[1]);



            MyFile.DeleteFile(uploadFile + ".gz");
            MyFile.WriteAllBinaryFromString(uploadFile + ".gz", fileContents);



            // post encoded file to website

            string url = apiURL;
            List <KeyValuePair <string, string> > headers = new List <KeyValuePair <string, string> > {
            };

            headers.Add(new KeyValuePair <string, string>("api-key", apiKey));
            headers.Add(new KeyValuePair <string, string>("access-token", iv));
            Upload(url, uploadFile + ".enc", headers);



            return(true);
        }
Example #12
0
        public bool SetList()
        {
            listViewSyncUp.SuspendLayout();

            listViewSyncUp.Items.Clear();

            // string syncFile;
            string       fileSize;
            FileInfo     fileInfo;
            ListViewItem listViewItem;

            /*
             * // get sync info
             * syncFile = @"sync\sync." + Config.settings.exportExt;
             * fileInfo = MyFile.FileInfo(syncFile);
             * if (fileInfo == null)
             * {
             *  Sync.Save();
             *  fileInfo = MyFile.FileInfo(syncFile);
             *  if (fileInfo == null)
             *  {
             *      MessageBox.Show("Unable to create [" + syncFile + "]");
             *      MyLog.Add("Unable to create [" + syncFile + "]");
             *      return false;
             *  }
             * }
             * listViewItem = new ListViewItem("Sync");
             * listViewItem.SubItems.Add("-");
             * fileSize = Convert.ToString(MyFile.FormatSize(fileInfo.Length));
             * listViewItem.SubItems.Add(fileSize);
             * listViewItem.Tag = fileInfo;
             *
             * listViewSyncUp.Items.Add(listViewItem);
             */

            // get all sources
            IEnumerable <string> files = MyFile.EnumerateFiles("data", "videos_*." + Config.settings.exportExt);
            Regex regexIgnoreBackups   = new Regex(@"\.[0-9]\." + Config.settings.exportExt);

            foreach (string file in files)
            {
                if (regexIgnoreBackups.IsMatch(file))
                {
                    continue;
                }
                fileInfo = MyFile.FileInfo(file);
                if (fileInfo == null)
                {
                    continue;
                }
                string source = file.Replace(@"data\videos_", "").Replace("." + Config.settings.exportExt, "");
                int    qty    = CalcStatsForSource(source);
                if (qty == 0)
                {
                    MyLog.Add("Source [" + source + "] seems to have 0 videos, skipping");
                    continue;
                }
                listViewItem = new ListViewItem(source);
                listViewItem.SubItems.Add(qty.ToString());
                fileSize = Convert.ToString(MyFile.FormatSize(fileInfo.Length));
                listViewItem.SubItems.Add(fileSize);
                listViewItem.Tag = fileInfo;

                listViewSyncUp.Items.Add(listViewItem);
            }


            ResizeColumns();


            listViewSyncUp.ResumeLayout();

            return(true);
        }
Example #13
0
        public static GalleryImageThumbnailInfo GetCachedThumbnail(VideoInfo videoInfo)
        {
            GalleryImageThumbnailInfo galleryImageThumbnailInfo = new GalleryImageThumbnailInfo();

            galleryImageThumbnailInfo.fromCache    = false;
            galleryImageThumbnailInfo.createdCache = false;
            galleryImageThumbnailInfo.thumbnail    = null;

            Image  thumbnail = null;
            string cachedThumbnailFullName = MyFile.EnsureDataFile("poster_" + videoInfo.hash, "jpg", @"cache\gallery");

            if (Config.settings.gallery.cachePosterThumbnails && File.Exists(cachedThumbnailFullName))
            {
                // use file stream so files not locked
                FileStream fileStream = new FileStream(cachedThumbnailFullName, FileMode.Open, FileAccess.Read);
                thumbnail = Image.FromStream(fileStream);
                fileStream.Close();
                // thumbnail = Image.FromFile(cachedThumbnailFile); // locks file

                galleryImageThumbnailInfo.fromCache = true;
            }
            else if (videoInfo.files.poster == null)
            {
                thumbnail = null;
            }
            else
            {
                VideoItemFile videoItemFile  = videoInfo.files.poster;
                string        posterFullName = videoInfo.GetFullName(videoItemFile);

                // skip images smaller than y or larger than x
                if (videoItemFile.Length < 100)
                {
                    MyLog.Add("Get Thumbnail: Skipping " + posterFullName + " " + MyFile.FormatSize(videoItemFile.Length));
                    thumbnail = null;
                }
                if (videoItemFile.Length > 5 * 1048576)
                {
                    MyLog.Add("Get Thumbnail: Skipping " + posterFullName + " " + MyFile.FormatSize(videoItemFile.Length));
                    thumbnail = null;
                }

                try
                {
                    if (!File.Exists(posterFullName))
                    {
                        thumbnail = null;
                    }
                    else
                    {
                        // size of thumbails .. TODO make a config setting
                        thumbnail = MyImage.GetThumbnail(posterFullName, 165, 250, Color.Black);
                        if (Config.settings.gallery.cachePosterThumbnails && thumbnail != null)
                        {
                            // clone image so files not locked
                            if (MyImage.SaveJpgImage((Image)thumbnail.Clone(), cachedThumbnailFullName))
                            {
                                galleryImageThumbnailInfo.createdCache = true;
                            }
                        }
                    }
                }
                catch (OutOfMemoryException)
                {
                    // Image.FromFile will throw this if file is invalid/corrupted; Don't ask me why
                    MyLog.Add("Invalid Image; Unable to read " + posterFullName + " " + MyFile.FormatSize(videoItemFile.Length));
                    thumbnail = null;
                }
                catch (Exception ei)
                {
                    MyLog.Add(ei.ToString());
                    thumbnail = null;
                }
            }

            galleryImageThumbnailInfo.thumbnail = thumbnail;
            return(galleryImageThumbnailInfo);
        }