예제 #1
0
        /// <summary>
        /// Find a paramater's target in code (methods)
        /// </summary>
        /// <param name="commandType">the system type of the command</param>
        /// <param name="currentNeededParm">the paramater we are after</param>
        public void SeekInCode(Type commandType, CommandParameterAttribute currentNeededParm)
        {
            var validTargetTypes      = commandsAssembly.GetTypes().Where(t => t.GetInterfaces().Contains(currentNeededParm.ParameterType));
            var internalCommandString = CommandStringRemainder.ToList();

            var  parmWords = internalCommandString.Count();
            Type parm      = null;

            while (parmWords > 0)
            {
                var currentParmString = string.Join(" ", RemoveGrammaticalNiceities(internalCommandString.Take(parmWords))).ToLower();

                if (!currentNeededParm.MatchesPattern(currentParmString))
                {
                    parmWords--;
                    continue;
                }

                var validParms = validTargetTypes.Where(comm => comm.GetCustomAttributes <CommandKeywordAttribute>()
                                                        .Any(att => att.Keyword.Equals(currentParmString)));

                if (validParms.Count() > 1)
                {
                    AccessErrors.Add(string.Format("There are {0} potential targets with that name for the {1} command.", validParms.Count(), commandType.Name));

                    AccessErrors.AddRange(validParms.Select(typ => typ.Name));

                    break;
                }
                else if (validParms.Count() == 1)
                {
                    parm = validParms.First();

                    if (parm != null)
                    {
                        switch (currentNeededParm.Usage)
                        {
                        case CommandUsage.Supporting:
                            Supporting = Activator.CreateInstance(parm);
                            break;

                        case CommandUsage.Subject:
                            Subject = Activator.CreateInstance(parm);
                            break;

                        case CommandUsage.Target:
                            Target = Activator.CreateInstance(parm);
                            break;
                        }
                    }

                    CommandStringRemainder = CommandStringRemainder.Skip(parmWords);
                    return;
                }

                parmWords--;
            }
        }
예제 #2
0
        /// <summary>
        /// Find a parameter target in backing data
        /// </summary>
        /// <typeparam name="T">the system type of the data</typeparam>
        /// <param name="commandType">the system type of the command</param>
        /// <param name="currentNeededParm">the conditions for the parameter we're after</param>
        public void SeekInBackingData <T>(Type commandType, CommandParameterAttribute currentNeededParm) where T : IData
        {
            var internalCommandString = CommandStringRemainder.ToList();

            var parmWords = internalCommandString.Count();

            while (parmWords > 0)
            {
                var currentParmString = string.Join(" ", internalCommandString.Take(parmWords));

                if (!currentNeededParm.MatchesPattern(currentParmString))
                {
                    parmWords--;
                    continue;
                }

                var validObject = default(T);

                long parmID = -1;
                if (!long.TryParse(currentParmString, out parmID))
                {
                    validObject = DataWrapper.GetOneBySharedKey <T>("Name", currentParmString);
                }
                else
                {
                    validObject = DataWrapper.GetOne <T>(parmID);
                }

                if (validObject != null && !validObject.Equals(default(T)))
                {
                    switch (currentNeededParm.Usage)
                    {
                    case CommandUsage.Supporting:
                        Supporting = validObject;
                        break;

                    case CommandUsage.Subject:
                        Subject = validObject;
                        break;

                    case CommandUsage.Target:
                        Target = validObject;
                        break;
                    }

                    CommandStringRemainder = CommandStringRemainder.Skip(parmWords);
                    return;
                }

                parmWords--;
            }
        }
예제 #3
0
        /// <summary>
        /// Find a parameter target in reference data
        /// </summary>
        /// <typeparam name="T">the system type of the data</typeparam>
        /// <param name="commandType">the system type of the command</param>
        /// <param name="currentNeededParm">the conditions for the parameter we're after</param>
        public void SeekInReferenceData <T>(Type commandType, CommandParameterAttribute currentNeededParm) where T : IReferenceData
        {
            var internalCommandString = CommandStringRemainder.ToList();

            var parmWords = internalCommandString.Count();

            while (parmWords > 0)
            {
                var currentParmString = string.Join(" ", RemoveGrammaticalNiceities(internalCommandString.Take(parmWords)));

                if (!currentNeededParm.MatchesPattern(currentParmString))
                {
                    parmWords--;
                    continue;
                }

                var validObject = ReferenceWrapper.GetOne <T>(currentParmString);

                if (validObject != null && !validObject.Equals(default(T)))
                {
                    switch (currentNeededParm.Usage)
                    {
                    case CommandUsage.Supporting:
                        Supporting = validObject;
                        break;

                    case CommandUsage.Subject:
                        Subject = validObject;
                        break;

                    case CommandUsage.Target:
                        Target = validObject;
                        break;
                    }

                    CommandStringRemainder = CommandStringRemainder.Skip(parmWords);
                    return;
                }

                parmWords--;
            }
        }
예제 #4
0
        /// <summary>
        /// Find a parameter target in the live world (entity)
        /// </summary>
        /// <typeparam name="T">the system type of the entity</typeparam>
        /// <param name="commandType">the system type of the command</param>
        /// <param name="currentNeededParm">the conditions for the parameter we're after</param>
        public void SeekInLiveWorldContainer <T>(Type commandType, CommandParameterAttribute currentNeededParm, Type subjectType)
        {
            //Borked it here, we found nothing viable earlier
            if (Subject == null || !((ICollection <IEntity>)Subject).Any())
            {
                return;
            }

            var subjectCollection = (ICollection <IEntity>)Subject;

            //Containers are touch range only
            var internalCommandString = CommandStringRemainder.ToList();
            var disambiguator         = -1;
            var parmWords             = internalCommandString.Count();

            while (parmWords > 0)
            {
                var currentParmString = string.Join(" ", RemoveGrammaticalNiceities(internalCommandString.Take(parmWords))).ToLower();

                //We have disambiguation here, we need to pick the first object we get back in the list
                if (Regex.IsMatch(currentParmString, LiveWorldDisambiguationSyntax))
                {
                    disambiguator     = int.Parse(currentParmString.Substring(0, currentParmString.IndexOf(".")));
                    currentParmString = currentParmString.Substring(currentParmString.IndexOf(".") + 1);
                }

                if (!currentNeededParm.MatchesPattern(currentParmString))
                {
                    parmWords--;
                    continue;
                }

                var validObjects = new List <T>();

                validObjects.AddRange(subjectCollection.Select(sbj => sbj.CurrentLocation)
                                      .Where(cl => cl.Keywords.Any(key => key.Contains(currentParmString))).Select(ent => (T)ent));

                if (validObjects.Count() > 0)
                {
                    //Skip everything up to the right guy and then take the one we want so we don't have to horribly alter the following logic flows
                    if (disambiguator > -1 && validObjects.Count() > 1)
                    {
                        validObjects = validObjects.Skip(disambiguator - 1).Take(1).ToList();
                    }

                    if (validObjects.Count() > 1)
                    {
                        AccessErrors.Add(string.Format("There are {0} potential containers with that name for the {1} command. Try using one of the following disambiguators:", validObjects.Count(), commandType.Name));

                        int iterator = 1;
                        foreach (var obj in validObjects)
                        {
                            var entityObject = (IEntity)obj;

                            AccessErrors.Add(string.Format("{0}.{1}", iterator++, entityObject.DataTemplate.Name));
                        }

                        break;
                    }
                    else if (validObjects.Count() == 1)
                    {
                        var parm = validObjects.First();

                        if (parm != null)
                        {
                            switch (currentNeededParm.Usage)
                            {
                            case CommandUsage.Supporting:
                                Supporting = parm;
                                break;

                            case CommandUsage.Subject:
                                Subject = parm;
                                break;

                            case CommandUsage.Target:
                                Target = parm;
                                break;
                            }
                        }

                        CommandStringRemainder = CommandStringRemainder.Skip(parmWords);

                        //Now try to set the subject
                        var container = (IContains)parm;

                        var validSubjects = new List <IEntity>();

                        validSubjects.AddRange(subjectCollection.Where(sbj => sbj.CurrentLocation.Equals(container)));

                        if (validSubjects.Count() > 1)
                        {
                            AccessErrors.Add(string.Format("There are {0} potential targets with that name inside {1} for the {2} command. Try using one of the following disambiguators:"
                                                           , validObjects.Count(), parmWords, commandType.Name));

                            int iterator = 1;
                            foreach (var obj in validSubjects)
                            {
                                AccessErrors.Add(string.Format("{0}.{1}", iterator++, obj.DataTemplate.Name));
                            }
                        }
                        else if (validObjects.Count() == 1)
                        {
                            Subject = validSubjects.First();
                        }

                        return;
                    }
                }

                parmWords--;
            }
        }
예제 #5
0
        /// <summary>
        /// Find a parameter target in the live world (entity)
        /// </summary>
        /// <typeparam name="T">the system type of the entity</typeparam>
        /// <param name="commandType">the system type of the command</param>
        /// <param name="currentNeededParm">the conditions for the parameter we're after</param>
        /// <param name="hasContainer">does the command need a container to look for things in</param>
        /// <param name="seekRange">how far we can look</param>
        public void SeekInLiveWorld <T>(Type commandType, CommandParameterAttribute currentNeededParm, CommandRangeAttribute seekRange, bool hasContainer)
        {
            var internalCommandString = CommandStringRemainder.ToList();
            var disambiguator         = -1;
            var parmWords             = internalCommandString.Count();

            while (parmWords > 0)
            {
                var currentParmString = string.Join(" ", RemoveGrammaticalNiceities(internalCommandString.Take(parmWords))).ToLower();

                //We have disambiguation here, we need to pick the first object we get back in the list
                if (Regex.IsMatch(currentParmString, LiveWorldDisambiguationSyntax))
                {
                    disambiguator     = int.Parse(currentParmString.Substring(0, currentParmString.IndexOf(".")));
                    currentParmString = currentParmString.Substring(currentParmString.IndexOf(".") + 1);
                }

                if (!currentNeededParm.MatchesPattern(currentParmString))
                {
                    parmWords--;
                    continue;
                }

                var validObjects = new List <T>();

                switch (seekRange.Type)
                {
                case CommandRangeType.Self:
                    validObjects.Add((T)Actor);
                    break;

                case CommandRangeType.Touch:
                    validObjects.AddRange(Location.GetContents <T>().Where(ent => ((IEntity)ent).Keywords.Any(key => key.Contains(currentParmString))));

                    if (Actor.GetType().GetInterfaces().Any(typ => typ == typeof(IContains)))
                    {
                        validObjects.AddRange(((IContains)Actor).GetContents <T>().Where(ent => ((IEntity)ent).Keywords.Any(key => key.Contains(currentParmString))));
                    }

                    //Containers only matter for touch usage subject paramaters, actor's inventory is already handled
                    //Don't sift through another intelligence's stuff
                    //TODO: write "does entity have permission to another entity's inventories" function on IEntity
                    if (hasContainer && currentNeededParm.Usage == CommandUsage.Subject)
                    {
                        foreach (IContains thing in Location.GetContents <T>().Where(ent => ent.GetType().GetInterfaces().Any(intf => intf == typeof(IContains)) &&
                                                                                     !ent.GetType().GetInterfaces().Any(intf => intf == typeof(IMobile)) &&
                                                                                     !ent.Equals(Actor)))
                        {
                            validObjects.AddRange(thing.GetContents <T>().Where(ent => ((IEntity)ent).Keywords.Any(key => key.Contains(currentParmString))));
                        }
                    }
                    break;

                case CommandRangeType.Local:     //requires Range to be working
                    break;

                case CommandRangeType.Regional:     //requires range to be working
                    break;

                case CommandRangeType.Global:
                    validObjects.AddRange(LiveCache.GetAll <T>().Where(ent => ((IEntity)ent).Keywords.Any(key => key.Contains(currentParmString))));
                    break;
                }

                if (hasContainer && currentNeededParm.Usage == CommandUsage.Subject && validObjects.Count() > 0)
                {
                    Subject = validObjects;
                    CommandStringRemainder = CommandStringRemainder.Skip(parmWords);
                    return;
                }
                else if (validObjects.Count() > 0)
                {
                    //Skip everything up to the right guy and then take the one we want so we don't have to horribly alter the following logic flows
                    if (disambiguator > -1 && validObjects.Count() > 1)
                    {
                        validObjects = validObjects.Skip(disambiguator - 1).Take(1).ToList();
                    }

                    if (validObjects.Count() > 1)
                    {
                        AccessErrors.Add(string.Format("There are {0} potential targets with that name for the {1} command. Try using one of the following disambiguators:", validObjects.Count(), commandType.Name));

                        int iterator = 1;
                        foreach (var obj in validObjects)
                        {
                            var entityObject = (IEntity)obj;

                            AccessErrors.Add(string.Format("{0}.{1}", iterator++, entityObject.DataTemplate.Name));
                        }

                        break;
                    }
                    else if (validObjects.Count() == 1)
                    {
                        var parm = validObjects.First();

                        if (parm != null)
                        {
                            switch (currentNeededParm.Usage)
                            {
                            case CommandUsage.Supporting:
                                Supporting = parm;
                                break;

                            case CommandUsage.Subject:
                                Subject = parm;
                                break;

                            case CommandUsage.Target:
                                Target = parm;
                                break;
                            }
                        }

                        CommandStringRemainder = CommandStringRemainder.Skip(parmWords);
                        return;
                    }
                }

                parmWords--;
            }
        }