Click here to Skip to main content
15,886,018 members
Articles / Desktop Programming / WPF

Replacing TreeView with ListBox

Rate me:
Please Sign up or sign in to vote.
4.83/5 (18 votes)
6 Oct 2011BSD4 min read 70.8K   5.2K   66  
TreeView is not good enough to support millions of nodes. Simulating using a ListBox might help.
using System;
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.IO;
using System.Linq;
using MediaAssistant.Constants;
using MediaAssistant.DAL;
using MediaAssistant.Data;
using MediaAssistant.Helper;
using MefBasic.Helper;

namespace MediaAssistant.Management
{
    [Export]
    public class MediaFileScanner : BackgroundScanner
    {
        private List<string> ExistingFiles { get; set; }

        private Queue<string> ScanFolderQueue { get; set; }

        public MediaFileScanner()
        {
            ExistingFiles=new List<string>();
            Name = "Media File Scanner";
            ScanFolderQueue=new Queue<string>();
        }
        protected override void TryToScan()
        {
            ScanFolderQueue.Clear();
            switch (RegistryHelper.ScanOption)
            {
                case ScanOption.SpecificFolder:
                    QueueSpecificFolders();
                    break;
                case ScanOption.MyComputer:
                    foreach (var driveInfo in DriveInfo.GetDrives().Where(driveInfo => driveInfo.IsReady))
                    {
                        ScanFolderQueue.Enqueue(driveInfo.RootDirectory.FullName);
                    }
                    break;
                case ScanOption.None:
                    return;
                case ScanOption.MyDocument:
                    ScanFolderQueue.Enqueue(Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments));
                    ScanFolderQueue.Enqueue(Environment.GetFolderPath(Environment.SpecialFolder.MyMusic));
                    ScanFolderQueue.Enqueue(Environment.GetFolderPath(Environment.SpecialFolder.MyVideos));
                    break;
            }
            GetExistingFiles();
            ScanQueuedFolder();
            SetStatusMessage(StatusMessages.Ready);
        }

        private void QueueSpecificFolders()
        {
            foreach (var scannedDirectory in DatabaseManager.Instance.GetScanDirectories())
            {
                if (scannedDirectory.KeepEye == false && scannedDirectory.LastScanned != null)
                {
                    continue;
                }
                if (!Directory.Exists(scannedDirectory.FullPath))
                {
                    continue;
                }
                ScanFolderQueue.Enqueue(scannedDirectory.FullPath);
            }  
        }


        private void ScanQueuedFolder()
        {
            while(ScanFolderQueue.Count>0)
            {
                var folderPath = ScanFolderQueue.Dequeue();
                if (!Directory.Exists(folderPath))
                {
                    continue;
                }
                if (Scan(folderPath))
                {
                    var scannedDirectory = DatabaseManager.Instance.GetScanDirectories().FirstOrDefault(d => d.FullPath == folderPath);
                    if(scannedDirectory!=null)
                        DatabaseManager.Instance.MarkAsScanned(scannedDirectory);
                }
                if (ShallReturn())
                    return;
                PauseIfRequested();
            }
        }

        private void GetExistingFiles()
        {
            ExistingFiles=new List<string>();
            ExistingFiles.AddRange(DatabaseManager.Instance.GetImportedFileNames().Where(f => ExistingFiles.Contains(f) == false));
        }

        private bool Scan(string folderPath)
        {
            try
            {
                if (Directory.Exists(folderPath) == false)
                    return false;
                SetStatusMessage(string.Format("Scanning {0}", folderPath));
                if (ShallReturn())
                    return false;
                PauseIfRequested();
                AddFiles(Directory.GetFiles(folderPath, "*.mp3"));
                if (ShallReturn())
                    return false;
                PauseIfRequested();
                AddFiles(Directory.GetFiles(folderPath, "*.wma"));
                foreach (var extension in Utility.SupportedMovieFileExtension)
                {
                    if (ShallReturn())
                        return false;
                    PauseIfRequested();
                    AddFiles(Directory.GetFiles(folderPath, "*" + extension));
                }
                foreach (var directory in Directory.GetDirectories(folderPath))
                {
                    if (Scan(directory) == false)
                        return false;
                    if (ShallReturn())
                        return false;
                    PauseIfRequested();
                }
                return true;
            }
            catch (Exception)
            {
                return false;
            }
            
        }

        private void AddFiles(IEnumerable<string> files)
        {
            foreach (var file in files)
            {
                AddFile(file);
                if (ShallReturn())
                    return;
                PauseIfRequested();
            }
        }

        private void AddFile(string fileName)
        {
            if (ExistingFiles.Contains(fileName))
                return;
            ExistingFiles.Add(fileName);
            if (Utility.IsMusicFile(fileName))
            {
                SetStatusMessage(string.Format("Adding music file {0}", fileName));
                DatabaseManager.Instance.AddMusicFile(fileName);
            }
            else if (Utility.IsMovieFile(fileName))
            {
                var fileInfo = new FileInfo(fileName);
                if (fileInfo.Length < Utility.MinMovieFileSize)
                    return;
                SetStatusMessage(string.Format("Adding movie file {0}", fileName));
                DatabaseManager.Instance.AddMovieFile(fileName);
                DatabaseManager.Instance.UpdateNewMovieTitle(DataSource.Value.ShowDrivesMoviesOnly, DataSource.Value.SelectedProfile);
                DatabaseManager.Instance.UpdateProcessingTitle(DataSource.Value.ShowDrivesMoviesOnly);
            }
        }
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The BSD License


Written By
Software Developer (Senior) KAZ Software Limited
Bangladesh Bangladesh
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions