/// <summary>
        /// Initializes a new instance of the <see cref="Project"/> class.
        /// </summary>
        public Project(
			ProjectProcessingState initialProcessingState =
				ProjectProcessingState.Interactive)
        {
            // Set up the initial states.
            ProcessingState = initialProcessingState;

            // We need the settings set up first since it may contribute
            // to the loading of other components of the project.
            Settings = new ProjectSettings();
            Properties = new PropertiesDictionary();
            BlockTypes = new BlockTypeSupervisor(this);
            Blocks = new ProjectBlockCollection(this);
            Commands = new BlockCommandSupervisor(this);
            Plugins = new PluginSupervisor(this);
            Macros = new ProjectMacros();
        }
        /// <summary>
        /// Configures the environment to load the plugin manager and verify we
        /// have access to our plugin and projectPlugin.
        /// </summary>
        private void SetupPlugin(
			out BlockCommandContext context,
			out ProjectBlockCollection blocks,
			out BlockCommandSupervisor commands,
			out PluginSupervisor plugins,
			out SpellEngineSpellingProjectPlugin projectPlugin)
        {
            // Start getting us a simple plugin manager.
            var spelling = new SpellingFrameworkPlugin();
            var nhunspell = new HunspellSpellingPlugin();
            var pluginManager = new PluginManager(spelling, nhunspell);

            PluginManager.Instance = pluginManager;

            // Create a project and pull out the useful properties we'll use to
            // make changes.
            var project = new Project();

            context = new BlockCommandContext(project);
            blocks = project.Blocks;
            commands = project.Commands;
            plugins = project.Plugins;

            // Load in the immediate correction editor.
            if (!plugins.Add("Spelling Framework"))
            {
                // We couldn't load it for some reason.
                throw new ApplicationException("Cannot load 'Spelling' plugin.");
            }

            if (!plugins.Add("NHunspell"))
            {
                // We couldn't load it for some reason.
                throw new ApplicationException("Cannot load 'NHunspell' plugin.");
            }

            // Pull out the projectPlugin for the correction and cast it (since we know
            // what type it is).
            ProjectPluginController pluginController = plugins.Controllers[1];
            projectPlugin =
                (SpellEngineSpellingProjectPlugin) pluginController.ProjectPlugin;
        }
        /// <summary>
        /// Configures the environment to load the plugin manager and verify we
        /// have access to our plugin and projectPlugin.
        /// </summary>
        private void SetupPlugin(
			out ProjectBlockCollection blocks,
			out BlockCommandSupervisor commands,
			out PluginSupervisor plugins,
			out FilesystemPersistenceProjectPlugin projectPlugin)
        {
            // Start getting us a simple plugin manager.
            var persistencePlugin = new PersistenceFrameworkPlugin();
            var filesystemPlugin = new FilesystemPersistencePlugin();
            var spellingPlugin = new SpellingFrameworkPlugin();
            var nhunspellPlugin = new HunspellSpellingPlugin();
            var localWordsPlugin = new LocalWordsPlugin();
            var immediateCorrectionPlugin = new ImmediateCorrectionPlugin();
            var immediateBlockTypesPlugin = new ImmediateBlockTypesPlugin();
            var blockStructurePlugin = new BlockStructurePlugin();

            var pluginManager = new PluginManager(
                persistencePlugin,
                filesystemPlugin,
                spellingPlugin,
                nhunspellPlugin,
                localWordsPlugin,
                immediateCorrectionPlugin,
                immediateBlockTypesPlugin,
                blockStructurePlugin);

            PluginManager.Instance = pluginManager;
            PersistenceManager.Instance = new PersistenceManager(persistencePlugin);

            // Create a project and pull out the useful properties we'll use to
            // make changes.
            var project = new Project();

            blocks = project.Blocks;
            commands = project.Commands;
            plugins = project.Plugins;

            // Load in the plugins we'll be using in these tests.
            foreach (IPlugin plugin in pluginManager.Plugins)
            {
                plugins.Add(plugin.Key);
            }

            // Set up the local words lookup.
            var localWordsProjectPlugin =
                (LocalWordsProjectPlugin) plugins["Local Words"];

            localWordsProjectPlugin.ReadSettings();
            localWordsProjectPlugin.CaseInsensitiveDictionary.Add("teig");
            localWordsProjectPlugin.CaseSensitiveDictionary.Add("Moonfire");
            localWordsProjectPlugin.WriteSettings();

            // Set up the immediate correction plugin.
            var immediateCorrectionProjectPlugin =
                (ImmediateCorrectionProjectPlugin) plugins["Immediate Correction"];

            immediateCorrectionProjectPlugin.AddSubstitution(
                "Grey", "Gray", SubstitutionOptions.WholeWord);
            immediateCorrectionProjectPlugin.AddSubstitution(
                "GWG", "Great Waryoni Garèo", SubstitutionOptions.None);
            immediateCorrectionProjectPlugin.AddSubstitution(
                "GWB", "Great Waryoni Bob", SubstitutionOptions.None);

            // Set up the immediate block types.
            var immediateBlockTypesProjectPlugin =
                (ImmediateBlockTypesProjectPlugin) plugins["Immediate Block Types"];

            foreach (BlockType blockType in project.BlockTypes.BlockTypes.Values)
            {
                string prefix = string.Format("{0}: ", blockType.Name);

                immediateBlockTypesProjectPlugin.Settings.Replacements[prefix] =
                    blockType.Name;
            }

            // Pull out the projectPlugin for the correction and cast it (since we know
            // what type it is).
            ProjectPluginController pluginController = plugins.Controllers[1];
            projectPlugin =
                (FilesystemPersistenceProjectPlugin) pluginController.ProjectPlugin;
        }
        /// <summary>
        /// Configures the environment to load the plugin manager and verify we
        /// have access to our plugin and projectPlugin.
        /// </summary>
        private void SetupPlugin(
			out ProjectBlockCollection blocks,
			out BlockCommandSupervisor commands,
			out PluginSupervisor plugins,
			out FilesystemPersistenceProjectPlugin projectPlugin)
        {
            // Start getting us a simple plugin manager.
            var persistencePlugin = new PersistenceFrameworkPlugin();
            var filesystemPlugin = new FilesystemPersistencePlugin();

            var pluginManager = new PluginManager(persistencePlugin, filesystemPlugin);

            PluginManager.Instance = pluginManager;
            PersistenceManager.Instance = new PersistenceManager(persistencePlugin);

            // Create a project and pull out the useful properties we'll use to
            // make changes.
            var project = new Project();

            blocks = project.Blocks;
            commands = project.Commands;
            plugins = project.Plugins;

            // Load in the plugins we'll be using in these tests.
            plugins.Add("Persistence Framework");
            plugins.Add("Filesystem Persistence");
            plugins.Add("Spelling Framework");
            plugins.Add("NHunspell");
            plugins.Add("Local Words");
            plugins.Add("Immediate Correction");

            // Pull out the projectPlugin for the correction and cast it (since we know
            // what type it is).
            ProjectPluginController pluginController = plugins.Controllers[1];
            projectPlugin =
                (FilesystemPersistenceProjectPlugin) pluginController.ProjectPlugin;
        }