Beispiel #1
0
        public Module(ModuleConfig config)
        {
            m_eventManager = config.GetEventManager();
            m_dependencies = config.GetDependencies();
            m_sName        = config.GetName();
            m_iUid         = config.GetUid();

            m_iModuleAvailableEventUid = config.GetEngineEvents().
                                         GetEventTypeUid(EngineEvents.Types.MODULE_AVAILABLE);
            m_iModuleUnavailableEventUid = config.GetEngineEvents().
                                           GetEventTypeUid(EngineEvents.Types.MODULE_UNAVAILABLE);
            m_iDependencyRequestEventUid = config.GetEngineEvents().
                                           GetEventTypeUid(EngineEvents.Types.DEPENDENCY_REQUEST);

            m_eventManager.AddEventListener(this, m_iModuleAvailableEventUid);
            m_eventManager.AddEventListener(this, m_iModuleUnavailableEventUid);

            foreach (string sDependencyName in config.GetDependencies())
            {
                m_eventManager.LaunchEvent(m_iDependencyRequestEventUid, sDependencyName);
            }
        }
Beispiel #2
0
        /// <summary>
        /// Adds a module of the given type. Modules must have unique names. Modules must provide a public
        /// constructor that takes a ModuleConfig and at most one other parameter whose type must be specified
        /// as the second type parameter to this function.
        /// </summary>
        /// <typeparam name="ModuleType">The type of module to create. Must inherit from Framework.Module</typeparam>
        /// <typeparam name="ConfigType">The type of configuration object to forward to the module constructor</typeparam>
        /// <param name="sName">The name by which to refer to the module</param>
        /// <param name="dependencies">A list of module names that this module requires access to</param>
        /// <returns>True if the module was successfully added, false otherwise</returns>
        /// <exception cref="ModuleException">Thrown when no valid module constructor could be found</throws>
        public bool AddModule <ModuleType, ConfigType>(ConfigType config, string sName, List <string> dependencies) where ModuleType : Module
        {
            if (string.IsNullOrEmpty(sName))
            {
                return(false);
            }

            // Dont allow modules to specify themselves as dependencies. Also filter out duplicates and
            // invalid values.
            if (dependencies == null)
            {
                dependencies = new List <string>();
            }

            dependencies.Remove(sName);
            SortedSet <string> dependencyFilter = new SortedSet <string>();

            foreach (string sDependencyName in dependencies)
            {
                if (!string.IsNullOrWhiteSpace(sDependencyName))
                {
                    dependencyFilter.Add(sDependencyName);
                }
            }

            dependencies = new List <string>();
            foreach (string sDependencyName in dependencyFilter)
            {
                dependencies.Add(sDependencyName);
            }

            // Module names must be unique
            foreach (Module m in m_modules)
            {
                if (m.GetName() == sName)
                {
                    return(false);
                }
            }

            ModuleConfig moduleConfig = new ModuleConfig(m_iNextModuleUid++, sName, m_eventManager, m_engineEvents, dependencies);
            ModuleType   module       = null;

            // Locate a constructor with the correct parameters. The first viable constructor will be used. Valid
            // formats are:
            // 1) ConfigType, ModuleConfig
            // 2) ModuleConfig, ConfigType
            // 3) ModuleConfig

            ConstructorInfo[] constructors = typeof(ModuleType).GetConstructors();
            foreach (ConstructorInfo constructor in constructors)
            {
                ParameterInfo[] parameters = constructor.GetParameters();
                if (parameters.Length == 1)
                {
                    if (parameters[0].ParameterType == typeof(ModuleConfig))
                    {
                        module = (ModuleType)Activator.CreateInstance(typeof(ModuleType), moduleConfig);
                        break;
                    }
                }
                else if (parameters.Length == 2)
                {
                    if (parameters[0].ParameterType == typeof(ModuleConfig) && parameters[1].ParameterType == typeof(ConfigType))
                    {
                        module = (ModuleType)Activator.CreateInstance(typeof(ModuleType), moduleConfig, config);
                        break;
                    }
                    else if (parameters[0].ParameterType == typeof(ConfigType) && parameters[1].ParameterType == typeof(ModuleConfig))
                    {
                        module = (ModuleType)Activator.CreateInstance(typeof(ModuleType), config, moduleConfig);
                        break;
                    }
                }
                else
                {
                    continue;
                }
            }

            if (module == null)
            {
                throw new ModuleException("Failed to construct module of type " + typeof(ModuleType).Name +
                                          " with name '" + sName + "'. A constructor accepting one of the following is required: " +
                                          "(ModuleConfig), (ModuleConfig, CustomParameter) or (CustomParameter, ModuleConfig).");
            }

            m_modules.Add(module);
            m_eventManager.LaunchEvent(m_iModuleAvailableEventUid, module);
            return(true);
        }