示例#1
0
        public void Test_EntityPathThrowsErrorOnInvalidConstruct()
        {
            EntityPath entityPath;

            Assert.ThrowsException <ArgumentException>(() =>
            {
                // only types derived from Entity can use entity path.
                entityPath = new EntityPath(typeof(string));
            });

            Assert.ThrowsException <ArgumentNullException>(() =>
            {
                entityPath = new EntityPath((Type)null);
            });

            Assert.ThrowsException <ArgumentNullException>(() =>
            {
                entityPath = new EntityPath("", typeof(Event));
            });

            Assert.ThrowsException <ArgumentNullException>(() =>
            {
                entityPath = new EntityPath((Entity)null);
            });

            Assert.ThrowsException <ArgumentNullException>(() =>
            {
                entityPath = new EntityPath(new Event());
            });
        }
示例#2
0
        public NestedCommand Select(string requestPath)
        {
            var _requestPath = new EntityPath(from.root.Entity.ID, requestPath).Path;
            var p            = SelectCommandHelper.ValidatePath(_requestPath);

            (string[], string)item;

            if (p.Count() > 1)
            {
                throw new ArgumentException("Only one field should be returned by sub queries");
            }
            else if (p.Count() == 0)
            {
                throw new ArgumentException("At least one field should be returned by sub queries");
            }
            else
            {
                item = p.First();
            }

            if (item.Item2 == "*")
            {
                throw new ArgumentException("Select all not allowed in sub queries.");
            }

            outputField = SelectCommandHelper.GenerateSingleSelectNode(item, from);

            return(this);
        }
示例#3
0
        /// <summary>
        /// Return sub entity path.
        /// </summary>
        /// <param name="subEntity">Sub entity.</param>
        /// <returns></returns>
        public override string GetSubEntityFullPath(EntityPath subEntity)
        {
            // if it works with User graph object then just forward
            // actual entity path.
            subEntity.ThrowIfNull(nameof(subEntity));
            if (subEntity.Path.StartsWith("users", StringComparison.OrdinalIgnoreCase))
            {
                if (subEntity.Id.Equals("") ||
                    this.Id.Equals(subEntity.Id, StringComparison.OrdinalIgnoreCase))
                {
                    return($"{this.EntityPath.Path}");
                }

                if (Guid.TryParse(subEntity.Id, out Guid id))
                {
                    // navigation property case, return subEntity path as
                    // correct path will be there.
                    return($"{subEntity.Path}");
                }

                return($"{this.EntityPath.Path}/{subEntity.Id}");
            }

            return(base.GetSubEntityFullPath(subEntity));
        }
示例#4
0
            static bool match(World world, ref SmallList <EntityQueryPart> queryParts, string entityPath)
            {
                var pathParts = new EntityQuery(entityPath).EnumerateParts();
                ReadOnlySpan <EntityQueryPart> remainingQueryParts = queryParts.AsSpan();
                bool matches = false;

                foreach (EntityQueryPart pathPart in pathParts)
                {
                    if (remainingQueryParts.IsEmpty)
                    {
                        return(false);
                    }
                    EntityQueryPart queryPart = remainingQueryParts[0];
                    if (!queryPart.SearchInAliases && !matchParts(queryPart, pathPart))
                    {
                        return(false);
                    }
                    if (queryPart.SearchInAliases && queryPart.IsLast)
                    {
                        var path = new EntityPath(queryPart.Value.ToString());
                        return(world._aliases.TryGetValue(path, out EntityId id) &&
                               id.Path.Equals(entityPath, StringComparison.Ordinal));
                    }

                    remainingQueryParts = remainingQueryParts[1..];
示例#5
0
        public void Test_MessageEntityPath()
        {
            EntityPath entityPath = new EntityPath(typeof(Message));

            Assert.IsTrue(entityPath.IsRootContainer);
            Assert.AreEqual("", entityPath.Id);
            Assert.AreEqual("Messages", entityPath.Path);
            Assert.AreEqual("Messages", entityPath.RootContainer);
            Assert.IsNull(entityPath.SubEntity);

            entityPath = new EntityPath("Abc", typeof(MailFolder));
            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("Abc", entityPath.Id);
            Assert.AreEqual("MailFolders/Abc", entityPath.Path);
            Assert.AreEqual("MailFolders", entityPath.RootContainer);
            Assert.IsNull(entityPath.SubEntity);

            entityPath           = new EntityPath("Abc", typeof(MailFolder));
            entityPath.SubEntity = new EntityPath(typeof(Message));
            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("Abc", entityPath.Id);
            Assert.AreEqual("MailFolders/Abc/Messages", entityPath.Path);
            Assert.AreEqual("MailFolders", entityPath.RootContainer);

            Assert.IsTrue(entityPath.SubEntity.IsRootContainer);
            Assert.AreEqual("", entityPath.SubEntity.Id);
            Assert.AreEqual("Messages", entityPath.SubEntity.Path);
            Assert.AreEqual("Messages", entityPath.SubEntity.RootContainer);
        }
示例#6
0
 private static void WriteEntityPath(TextWriter writer, EntityPath entityPath)
 {
     foreach (var entity in entityPath.GenerateEntities())
     {
         WriteEntity(writer, entity);
     }
 }
示例#7
0
        public bool MoveMob(
            Point3d targetPosition)
        {
            bool success = false;

            if (path == null)
            {
                PathComputer pathComputer = new PathComputer();

                success =
                    pathComputer.BlockingPathRequest(
                        moveRequest.Room.runtime_nav_mesh,
                        moveRequest.Room.room_key,
                        new Point3d(mob.Position),
                        new Point3d(targetPosition));

                if (success)
                {
                    RoomKey  roomKey            = moveRequest.Room.room_key;
                    PathStep lastPathStep       = pathComputer.FinalPath[pathComputer.FinalPath.Count - 1];
                    PathStep secondLastPathStep = pathComputer.FinalPath[pathComputer.FinalPath.Count - 2];
                    Vector3d lastPathHeading    = lastPathStep.StepPoint - secondLastPathStep.StepPoint;
                    float    targetAngle        = MathConstants.GetAngleForVector(lastPathHeading);

                    path =
                        new EntityPath()
                    {
                        entity_id = mob.ID,
                        path      = pathComputer.FinalPath
                    };

                    // Post an event that we moved
                    output_game_events.Add(
                        new GameEvent_MobMoved()
                    {
                        mob_id     = mob.ID,
                        room_x     = roomKey.x,
                        room_y     = roomKey.y,
                        room_z     = roomKey.z,
                        from_x     = mob.Position.x,
                        from_y     = mob.Position.y,
                        from_z     = mob.Position.z,
                        from_angle = mob.Angle,
                        to_x       = targetPosition.x,
                        to_y       = targetPosition.y,
                        to_z       = targetPosition.z,
                        to_angle   = targetAngle
                    });

                    // Update the mob position and facing
                    mob.Position = targetPosition;
                    mob.Angle    = targetAngle;

                    // TODO: Update the mob energy based on the distance traveled
                }
            }

            return(success);
        }
示例#8
0
 public SmallList <Entity> Query(uint contextId, EntityQuery query)
 {
     if (EntityPath.IsValidPath(query, out EntityPath simplePath) &&
         Get(contextId, simplePath) is Entity result)
     {
         return(new SmallList <Entity>(result));
     }
     return(QuerySlow(contextId, query));
 }
示例#9
0
        public void Test_EventMessageEntityPath()
        {
            EntityPath entityPath = new EntityPath(typeof(EventMessage));

            Assert.IsTrue(entityPath.IsRootContainer);
            Assert.AreEqual("", entityPath.Id);
            Assert.AreEqual("Messages", entityPath.Path);
            Assert.AreEqual("Messages", entityPath.RootContainer);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#10
0
        /// <summary>
        /// Create new instance of <see cref="GraphUri"/>
        /// </summary>
        /// <param name="identity">Identity.</param>
        /// <param name="subEntity">Sub entity.</param>
        /// <param name="beta">Connect to beta endpoint.</param>
        internal GraphUri(IGraphIdentity identity, EntityPath subEntity, bool beta)
        {
            identity.ThrowIfNull(nameof(identity));
            subEntity.ThrowIfNull(nameof(subEntity));

            this.IsBeta   = beta;
            this.Identity = identity;
            this.restUri  = new HttpRestUri(
                $"{GraphUri.baseGraphUri}/{this.GetServiceInstance()}/{this.Identity.GetSubEntityFullPath(subEntity)}");
        }
示例#11
0
        public MobUpdateContext(
            AIMoveRequestProcessor moveRequest,
            Mob mob)
        {
            this.moveRequest = moveRequest;
            this.otherMobs   = moveRequest.MobContexts.Where(c => c.mob.ID != mob.ID).Select(c => c.mob).ToList();
            this.mob         = mob;
            this.path        = null;

            output_game_events = new List <GameEventParameters>();
        }
 /// <summary>
 /// Determines if the entity at the given path requires a new Guid value when it's imported
 /// onto the target system. On import, if an entity of that type and Guid already exists then
 /// it is not imported and a reference to the existing entity is used instead.
 /// </summary>
 /// <param name="path">The path to the queued entity object that is being checked.</param>
 /// <returns>
 ///   <c>true</c> if the path requires a new Guid value; otherwise, <c>false</c>
 /// </returns>
 public bool DoesPathNeedNewGuid(EntityPath path)
 {
     return(path == "" ||
            path == "AttributeTypes" ||
            path == "AttributeTypes.AttributeQualifiers" ||
            path == "ActivityTypes" ||
            path == "ActivityTypes.AttributeTypes" ||
            path == "ActivityTypes.AttributeTypes.AttributeQualifiers" ||
            path == "ActivityTypes.ActionTypes" ||
            path == "ActivityTypes.ActionTypes.AttributeValues" ||
            path == "ActivityTypes.ActionTypes.WorkflowFormId" ||
            path == "ActivityTypes.ActionTypes.WorkflowFormId.FormAttributes");
 }
示例#13
0
        public void Test_MessageRuleEntityPath()
        {
            MessageRule rule = new MessageRule()
            {
                Id = "abc"
            };

            EntityPath entityPath = new EntityPath(rule);

            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("MailFolders/Inbox/MessageRules", entityPath.RootContainer);
            Assert.AreEqual("abc", entityPath.Id);
            Assert.AreEqual("MailFolders/Inbox/MessageRules/abc", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#14
0
        public void Test_OutlookTaskEntityPath()
        {
            EntityPath entityPath = new EntityPath(typeof(OutlookTask));

            Assert.IsTrue(entityPath.IsRootContainer);
            Assert.AreEqual("Outlook/Tasks", entityPath.RootContainer);
            Assert.AreEqual("Outlook/Tasks", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);

            entityPath = new EntityPath("abcd", typeof(OutlookTask));
            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("Outlook/Tasks", entityPath.RootContainer);
            Assert.AreEqual("Outlook/Tasks/abcd", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#15
0
        public void Test_OutlookCategoryEntityPath()
        {
            EntityPath entityPath = new EntityPath(typeof(OutlookCategory));

            Assert.IsTrue(entityPath.IsRootContainer);
            Assert.AreEqual("Outlook/MasterCategories", entityPath.RootContainer);
            Assert.AreEqual("Outlook/MasterCategories", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);

            entityPath = new EntityPath("abcd", typeof(OutlookCategory));
            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("Outlook/MasterCategories", entityPath.RootContainer);
            Assert.AreEqual("Outlook/MasterCategories/abcd", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#16
0
        public void Test_ContactEntityPath()
        {
            Contact contact = new Contact()
            {
                Id = "cId"
            };

            EntityPath entityPath = new EntityPath(contact);

            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("Contacts", entityPath.RootContainer);
            Assert.AreEqual("Contacts/cId", entityPath.Path);
            Assert.AreEqual("cId", entityPath.Id);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#17
0
        private static EntityPath ReadPath(Stream stream)
        {
            var entityPath = new EntityPath();

            entityPath.Name      = stream.ReadString(128);
            entityPath.ClassName = stream.ReadString(128);
            entityPath.Type      = (PathType)stream.ReadInt();

            var nodeCount = stream.ReadInt();

            for (int i = 0; i < nodeCount; i++)
            {
                entityPath.Nodes.Add(ReadPathNode(stream));
            }

            return(entityPath);
        }
        /// <summary>
        /// Determines if the property at the given path should be followed to it's referenced entity.
        /// This is called for both referenced entities and child entities.
        /// </summary>
        /// <param name="path">The path.</param>
        /// <returns></returns>
        public bool ShouldFollowPathProperty(EntityPath path)
        {
            if (path == "CategoryId")
            {
                return(false);
            }

            if (path.Count > 0)
            {
                var lastComponent = path.Last();

                if (lastComponent.Entity.TypeName == "Rock.Model.DefinedType" && lastComponent.PropertyName == "DefinedValues")
                {
                    return(false);
                }
            }

            return(true);
        }
示例#19
0
        private static EntityPath ReadEntityPath(Stream stream)
        {
            var path = new EntityPath();

            path.ClassName = stream.ReadLengthPrefixedString();
            path.Name      = stream.ReadLengthPrefixedString();
            path.Type      = (PathType)stream.ReadInt();
            var unknown1 = stream.ReadBytes(4);
            var color    = ReadColor(stream);

            var nodeCount = stream.ReadInt();

            for (int i = 0; i < nodeCount; i++)
            {
                path.Nodes.Add(ReadPathNode(stream));
            }

            return(path);
        }
示例#20
0
        public SelectCommand Select(string requestPath)
        {
            var _requestPath = new EntityPath(from.root.Entity.ID, requestPath).Path;
            var p            = SelectCommandHelper.ValidatePath(_requestPath);

            foreach (var item in p)
            {
                var x = from.Resolve(item.Item1);
                IEnumerable <SelectNode> fields;
                if (item.Item2 != "*")
                {
                    fields = x.Entity.entityFields
                             .Where(ef => ef.CodeName == item.Item2)
                             .Select(ef => {
                        return(new SelectNode()
                        {
                            FullPath = new FieldPath(x.FullPath.Root, x.FullPath.Path, ef.CodeName),
                            EntityField = ef,
                            FromNode = x
                        });
                    });
                }
                else //wildcard = select all
                {
                    fields = x.Entity.entityFields
                             .Select(ef => {
                        return(new SelectNode()
                        {
                            FullPath = new FieldPath(x.FullPath.Root, x.FullPath.Path, ef.CodeName),
                            EntityField = ef,
                            FromNode = x
                        });
                    });
                }
                selectFields.AddRange(fields);
            }

            ((BaseCommand)this).CommandLog(LogLevel.Info, "SelectCommand", $"{{\"Action\":\"Select\", \"Path\":\"{requestPath}\"}}");
            return(this);
        }
示例#21
0
        /// <summary>
        /// Get next page.
        /// </summary>
        /// <returns></returns>
        public async Task <FindEntityResults <T> > GetNextPage()
        {
            this.propertyBag.TryGetKey(
                nameof(Entity.EntityService),
                out PropertyDefinition entityServicePropDef);
            entityServicePropDef.ThrowIfNull(nameof(entityServicePropDef));

            this.propertyBag.TryGetKey(
                nameof(Entity.EntityPath),
                out PropertyDefinition entityPathPropDef);
            entityPathPropDef.ThrowIfNull(nameof(entityPathPropDef));

            IEntityService entityService = (IEntityService)this.propertyBag[entityServicePropDef];
            EntityPath     entityPath    = (EntityPath)this.propertyBag[entityPathPropDef];

            entityPath.SubEntity = new EntityPath(typeof(T));
            FindEntityResults <T> result = await entityService.Navigate <T>(entityPath, this.pageQuery);

            this.pageQuery.Offset += this.pageQuery.PageSize;

            return(result);
        }
示例#22
0
        public void Test_NonTypedEntityPath()
        {
            EntityPath entityPath = new EntityPath(
                "abc==",
                "calCheck");

            Assert.IsFalse(entityPath.IsRootContainer);
            Assert.AreEqual("calCheck/abc==", entityPath.Path);
            Assert.AreEqual("abc==", entityPath.Id);
            Assert.AreEqual("calCheck", entityPath.RootContainer);
            Assert.IsNull(entityPath.SubEntity);

            entityPath.SubEntity = new EntityPath(typeof(MailFolder));
            Assert.AreEqual("calCheck/abc==/MailFolders", entityPath.Path);
            Assert.IsNotNull(entityPath.SubEntity);

            entityPath = new EntityPath(nameof(AutomaticRepliesSetting));
            Assert.IsTrue(entityPath.IsRootContainer);
            Assert.AreEqual("AutomaticRepliesSetting", entityPath.RootContainer);
            Assert.AreEqual("AutomaticRepliesSetting", entityPath.Path);
            Assert.IsNull(entityPath.SubEntity);
        }
示例#23
0
        public WorldTests()
        {
            var levels = new List <EntityPath> [3];

            for (int i = 0; i < 3; i++)
            {
                levels[i] = new List <EntityPath>();
            }

            void entity(string name)
            {
                var path = new EntityPath(name);
                ResolvedEntityPath resolvedPath = _world.ResolvePath(0, path);

                _world.Add(new BasicEntity(resolvedPath));
                int level = name.Count(c => c == '/');

                levels[level].Add(path);
            }

            _world = new World();
            entity("root");
            entity("root1");
            entity("root/e11");
            entity("root/e12");
            entity("root/e11/e21");
            entity("root/e11/e22");
            entity("root/e11/e23");
            entity("root/e12/e21");
            entity("root/e12/e22");
            entity("root/e12/e23");
            entity("root/MouseOver/img");

            _treeLevels = new EntityPath[3][];
            for (int i = 0; i < 3; i++)
            {
                _treeLevels[i] = levels[i].ToArray();
            }
        }
示例#24
0
        public EntityId(ref MessagePackReader reader)
        {
            reader.ReadArrayHeader();
            Context = reader.ReadUInt32();
            string?value = reader.ReadString();

            if (value is not null)
            {
                var path = new EntityPath(value);
                _nameStart = 0;
                MouseState = path.MouseState;
                Path       = path.Value;
                _hashCode  = HashCode.Combine(Path.GetHashCode(), Context);
            }
            else
            {
                Path       = null !;
                _nameStart = 0;
                Context    = 0;
                _hashCode  = 0;
                MouseState = default;
            }
        }
 private IEnumerable <IDbEntity> GetCollection(IDbEntity entity)
 {
     return((entity.Eval(EntityPath.Substring(1, EntityPath.LastIndexOf("[") - 1)) as IEnumerable).Cast <IDbEntity>());
 }
示例#26
0
 /// <summary>
 /// Create sub entity path.
 /// </summary>
 /// <param name="subEntity">Sub entity.</param>
 /// <returns></returns>
 public virtual string GetSubEntityFullPath(EntityPath subEntity)
 {
     subEntity.ThrowIfNull(nameof(subEntity));
     return($"{this.EntityPath.Path}/{subEntity.Path}");
 }
        /// <summary>
        /// Gets any custom references for the entity at the given path.
        /// </summary>
        /// <param name="parentEntity">The entity that will later be encoded.</param>
        /// <param name="path">The path to the parent entity.</param>
        /// <returns>
        /// A collection of references that should be applied to the encoded entity.
        /// </returns>
        public ICollection <Reference> GetUserReferencesForPath(IEntity parentEntity, EntityPath path)
        {
            if (path == "")
            {
                return(new List <Reference>
                {
                    Reference.UserDefinedReference("CategoryId", "WorkflowCategory")
                });
            }

            return(null);
        }
 /// <summary>
 /// Determines whether the path to an entity should be considered critical. A critical
 /// entity is one that MUST exist on the target system in order for the export/import to
 /// succeed, as such a critical entity is always included.
 /// </summary>
 /// <param name="path">The path to the queued entity object that is being checked.</param>
 /// <returns>
 ///   <c>true</c> if the path is critical; otherwise, <c>false</c>.
 /// </returns>
 public bool IsPathCritical(EntityPath path)
 {
     return(DoesPathNeedNewGuid(path));
 }
示例#29
0
        public static IEnumerable <Entity> GenerateEntities(this EntityPath path)
        {
            // NOTE: This always yields the previous entity, because its target may have been updated by the current entity,
            //       and it may be too late to update an entity after it has already been yielded.

            var    index          = 0;
            Entity previousEntity = null;

            foreach (var node in path.Nodes)
            {
                var entity = CreateEntityForNode(node);

                if (previousEntity != null)
                {
                    yield return(previousEntity);
                }

                previousEntity = entity;
                index         += 1;
            }

            if (path.Type == PathType.Circular)
            {
                // Point the last node back at the first:
                previousEntity.Properties[Attributes.Target] = path.Name;
            }
            else if (path.Type == PathType.PingPong)
            {
                // Generate additional nodes for the way back (in reverse order, excluding the first and last corner):
                foreach (var node in path.Nodes.Skip(1).Take(path.Nodes.Count - 2).Reverse())
                {
                    var entity = CreateEntityForNode(node);

                    if (previousEntity != null)
                    {
                        yield return(previousEntity);
                    }

                    previousEntity = entity;
                    index         += 1;
                }
                previousEntity.Properties[Attributes.Target] = path.Name;
            }

            if (previousEntity != null)
            {
                yield return(previousEntity);
            }

            Entity CreateEntityForNode(EntityPathNode node)
            {
                var entity = new Entity();

                foreach (var property in node.Properties)
                {
                    entity.Properties[property.Key] = property.Value;
                }

                entity.ClassName = path.ClassName;
                entity.Origin    = node.Position;

                var targetname = node.NameOverride;

                if (string.IsNullOrEmpty(targetname))
                {
                    targetname = (index == 0) ? path.Name : FormattableString.Invariant($"{path.Name}{index:00}");
                }
                entity.Properties[Attributes.Targetname] = targetname;

                if (previousEntity != null)
                {
                    previousEntity.Properties[Attributes.Target] = targetname;
                }

                return(entity);
            }
        }
示例#30
0
        private void UpdateAIPropVisibility(
            MobUpdateContext context)
        {
            Mob     ownerMob = context.mob;
            NavMesh navMesh  = context.moveRequest.Room.runtime_nav_mesh;

            foreach (EntityProp prop in ai_props)
            {
                Point3d oldPropPosition = prop.GetPosition();

                // Find the player associated with the player id
                MobUpdateContext otherMobContext = context.moveRequest.MobContexts.Find(m => m.mob.ID == prop.target_object_id);
                Mob otherMob = otherMobContext.mob;

                // Can the mob see the other mob at their current location
                bool canSee = CanMobSeePoint(navMesh, ownerMob, otherMob.Position);

                TypedFlags <EntityProp.ePropVisibilityFlags> oldVisibilityFlags =
                    new TypedFlags <EntityProp.ePropVisibilityFlags>(prop.visibilityFlags);

                prop.visibilityFlags.Set(EntityProp.ePropVisibilityFlags.canSee, canSee);
                prop.visibilityFlags.Set(EntityProp.ePropVisibilityFlags.caughtGlimpse, canSee);

                if (canSee)
                {
                    // If so, we get to pull the entity properties
                    prop.RefeshEntityProperties(ownerMob, otherMob);
                    prop.visibilityFlags.Set(EntityProp.ePropVisibilityFlags.seenAtLeastOnce, true);
                }
                else
                {
                    EntityPath entityPath = otherMobContext.path;

                    if (entityPath != null)
                    {
                        // Find the last place we saw the player along their path, if at all
                        for (int pathStepIndex = entityPath.path.Count - 1; pathStepIndex >= 0; pathStepIndex--)
                        {
                            PathStep pathStep = entityPath.path[pathStepIndex];

                            if (CanMobSeePoint(navMesh, ownerMob, pathStep.StepPoint))
                            {
                                prop.position_x = pathStep.StepPoint.x;
                                prop.position_y = pathStep.StepPoint.y;
                                prop.position_z = pathStep.StepPoint.z;
                                prop.visibilityFlags.Set(EntityProp.ePropVisibilityFlags.caughtGlimpse, true);
                                prop.visibilityFlags.Set(EntityProp.ePropVisibilityFlags.seenAtLeastOnce, true);
                                break;
                            }
                        }
                    }
                }

                // Post an event if we just spotted another mob that we've never seen before
                if (!oldVisibilityFlags.Test(EntityProp.ePropVisibilityFlags.canSee) &&
                    !oldVisibilityFlags.Test(EntityProp.ePropVisibilityFlags.seenAtLeastOnce) &&
                    (prop.visibilityFlags.Test(EntityProp.ePropVisibilityFlags.canSee) ||
                     prop.visibilityFlags.Test(EntityProp.ePropVisibilityFlags.caughtGlimpse)))
                {
                    context.output_game_events.Add(
                        new GameEvent_MobAIPropSpotted()
                    {
                        mob_id         = ownerMob.ID,
                        spotted_mob_id = prop.target_object_id,
                        x = prop.position_x,
                        y = prop.position_y,
                        z = prop.position_z
                    });
                }
            }
        }