예제 #1
0
 public static void AIMovement(StateSpaceComponents spaceComponents, DungeonTile[,] dungeonGrid, Vector2 dungeonDimensions, DijkstraMapTile[,] mapToPlayer)
 {
     if (spaceComponents.PlayerComponent.PlayerTookTurn)
     {
         // Handle Combat ready AI entities
         foreach (Guid id in spaceComponents.Entities.Where(c => ((c.ComponentFlags & ComponentMasks.CombatReadyAI) == ComponentMasks.CombatReadyAI)).Select(c => c.Id))
         {
             AIAlignment alignment = spaceComponents.AIAlignmentComponents[id];
             AIState state = spaceComponents.AIStateComponents[id];
             PositionComponent position = spaceComponents.PositionComponents[id];
             switch(state.State)
             {
                 case AIStates.STATE_ROAMING:
                     position = AISystem.AIRoam(id, position, dungeonGrid, dungeonDimensions, spaceComponents.random);
                     break;
                 case AIStates.STATE_ATTACKING:
                     position = AISystem.AIAttack(id, position, dungeonDimensions, mapToPlayer, spaceComponents.random);
                     break;
                 case AIStates.STATE_FLEEING:
                     position = AISystem.AIFlee(id, position, dungeonDimensions, mapToPlayer, spaceComponents.random);
                     break;
             }
             CollisionSystem.TryToMove(spaceComponents, dungeonGrid, position, id);
         }
     }
 }
예제 #2
0
 public static void ShouldPlayerMapRecalc(StateSpaceComponents spaceComponents, DungeonTile[,] dungeonGrid, Vector2 dungeonDimensions, ref DijkstraMapTile[,] playerMap)
 {
     if(spaceComponents.PlayerComponent.PlayerTookTurn || spaceComponents.PlayerComponent.PlayerJustLoaded)
     {
         CreateDijkstraMapToPlayers(dungeonGrid, dungeonDimensions, spaceComponents, ref playerMap);
     }
 }
예제 #3
0
 private static PositionComponent AIFlee(Guid entity, PositionComponent position, Vector2 dungeonDimensions, DijkstraMapTile[,] mapToPlayer, Random random)
 {
     int lowestGridTile = 1;
     List<Vector2> validSpots = new List<Vector2>();
     for (int i = (int)position.Position.X - 1; i <= (int)position.Position.X + 1; i++)
     {
         for (int j = (int)position.Position.Y - 1; j <= (int)position.Position.Y + 1; j++)
         {
             if (i >= 0 && j >= 0 && i < (int)dungeonDimensions.X && j < (int)dungeonDimensions.Y)
             {
                 if (mapToPlayer[i, j].Weight < DevConstants.Grid.WallWeight)
                 {
                     lowestGridTile = (mapToPlayer[i, j].Weight * -1 < lowestGridTile * -1) ? mapToPlayer[i, j].Weight : lowestGridTile;
                 }
             }
         }
     }
     for (int i = (int)position.Position.X - 1; i <= (int)position.Position.X + 1; i++)
     {
         for (int j = (int)position.Position.Y - 1; j <= (int)position.Position.Y + 1; j++)
         {
             if (i >= 0 && j >= 0 && i < (int)dungeonDimensions.X && j < (int)dungeonDimensions.Y && mapToPlayer[i, j].Weight == lowestGridTile)
             {
                 validSpots.Add(new Vector2(i, j));
             }
         }
     }
     return new PositionComponent() { Position = validSpots[random.Next(0, validSpots.Count)] };
 }
예제 #4
0
        public static void DrawTiles(Camera camera, SpriteBatch spriteBatch, DungeonTile[,] dungeonGrid, Vector2 dungeonDimensions, int cellSize, Texture2D spriteSheet, DungeonColorInfo colorInfo, DijkstraMapTile[,] mapToPlayer, SpriteFont font, StateSpaceComponents spaceComponents)
        {
            Entity player = spaceComponents.Entities.Where(c => (c.ComponentFlags & ComponentMasks.Player) == ComponentMasks.Player).FirstOrDefault();
            bool inWater = false;
            bool inFire = false;
            if (player != null)
            {
                Vector2 playerPos = spaceComponents.PositionComponents[spaceComponents.Entities.Where(c => (c.ComponentFlags & ComponentMasks.Player) == ComponentMasks.Player).First().Id].Position;
                inWater = dungeonGrid[(int)playerPos.X, (int)playerPos.Y].Type == TileType.TILE_WATER;
                inFire = dungeonGrid[(int)playerPos.X, (int)playerPos.Y].Type == TileType.TILE_FIRE || (player.ComponentFlags & ComponentMasks.BurningStatus) == ComponentMasks.BurningStatus;
            }

            Matrix cameraMatrix = camera.GetMatrix();
            Vector2 origin = new Vector2(DevConstants.Grid.TileBorderSize, DevConstants.Grid.TileBorderSize);
            for (int i = 0; i < (int)dungeonDimensions.X; i++)
            {
                for (int j = 0; j < (int)dungeonDimensions.Y; j++)
                {
                    bool tintFire = inFire || dungeonGrid[i, j].FireIllumination;
                    Vector2 tile = new Vector2((int)i * cellSize, (int)j * cellSize);
                    Rectangle floor = new Rectangle(0 * cellSize, 0 * cellSize, cellSize, cellSize); //Need to be moved eventually
                    Rectangle wall = new Rectangle(0 * cellSize, 0 * cellSize, cellSize, cellSize); //Need to be moved eventually

                    Vector2 bottomRight = Vector2.Transform(new Vector2((i * cellSize) + cellSize, (j * cellSize) + cellSize), cameraMatrix);
                    Vector2 topLeft = Vector2.Transform(new Vector2(i * cellSize, j * cellSize), cameraMatrix);
                    Rectangle cameraBounds = new Rectangle((int)topLeft.X, (int)topLeft.Y, (int)bottomRight.X - (int)topLeft.X, (int)bottomRight.Y - (int)topLeft.Y);


                    if (camera.IsInView(cameraMatrix, cameraBounds)) // check if in view
                    {

                        if (dungeonGrid[i, j].Found && !dungeonGrid[i, j].InRange)
                        {

                            Color colorToLerp = tintFire ? colorInfo.Fire : colorInfo.Water; //Default to water, if fire then change it.
                            switch (dungeonGrid[i, j].Type)
                            {
                                case TileType.TILE_FLATTENEDGRASS:
                                case TileType.TILE_FLOOR:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.Floor, colorToLerp, .3f) : colorInfo.Floor) * .3f, origin: origin);
                                    break;
                                case TileType.TILE_ROCK:
                                case TileType.TILE_WALL:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.Wall, colorToLerp, .3f) : colorInfo.Wall) * .3f, origin: origin);
                                    break;
                                case TileType.TILE_TALLGRASS:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.TallGrass, colorToLerp, .3f) : colorInfo.TallGrass) * .3f, origin: origin);
                                    break;
                                case TileType.TILE_ASH:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.Ash, colorToLerp, .3f) : colorInfo.Ash) * .3f, origin: origin);
                                    break;
                                case TileType.TILE_WATER:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (tintFire ? Color.Lerp(colorInfo.Water, colorToLerp, .3f) : colorInfo.Water) * .3f, origin: origin);
                                    break;
                                case TileType.TILE_FIRE:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater ? Color.Lerp(colorInfo.Fire, colorToLerp, .3f) : colorInfo.Fire) * .3f, origin: origin);
                                    break;
                            }
                            if (!string.IsNullOrEmpty(dungeonGrid[i, j].Symbol))
                            {
                                Vector2 size = font.MeasureString(dungeonGrid[i, j].Symbol);
                                spriteBatch.DrawString(font, dungeonGrid[i, j].Symbol, new Vector2(i * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2),
                                    (j * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2))),
                                    dungeonGrid[i, j].SymbolColor * .5f, 0f, new Vector2((int)(size.X / 2), (int)(size.Y / 2)), 1f, SpriteEffects.None, 0f);
                            }
                        }
                        else if (dungeonGrid[i, j].InRange && !dungeonGrid[i, j].NewlyFound)
                        {
                            int weight = mapToPlayer[i, j].Weight;
                            double opacity = 1 - (.035 * weight);
                            opacity = (opacity < .4) ? .4 : opacity;
                            opacity = dungeonGrid[i, j].FireIllumination ? .85f : opacity;
                            bool isWall = false;

                            Color colorToLerp = tintFire ? colorInfo.FireInRange : colorInfo.WaterInRange; //Default to water, if fire then change it.
                            switch (dungeonGrid[i, j].Type)
                            {
                                case TileType.TILE_FLATTENEDGRASS:
                                case TileType.TILE_FLOOR:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.FloorInRange, colorToLerp, .55f) : colorInfo.FloorInRange) * (float)opacity, origin: origin);
                                    break;
                                case TileType.TILE_ROCK:
                                case TileType.TILE_WALL:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.WallInRange, colorToLerp, .55f) : colorInfo.WallInRange) * .85f, origin: origin);
                                    isWall = true;
                                    break;
                                case TileType.TILE_TALLGRASS:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.TallGrassInRange, colorToLerp, .55f) : colorInfo.TallGrassInRange) * (float)opacity, origin: origin);
                                    break;
                                case TileType.TILE_WATER:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (tintFire ? Color.Lerp(colorInfo.WaterInRange, colorToLerp, .55f) : colorInfo.WaterInRange) * (float)opacity, origin: origin);
                                    break;
                                case TileType.TILE_ASH:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.AshInRange, colorToLerp, .55f) : colorInfo.AshInRange) * (float)opacity, origin: origin);
                                    break;
                                case TileType.TILE_FIRE:
                                    opacity = 0f + (.1f * dungeonGrid[i, j].TurnsToBurn);
                                    opacity = (opacity > 1f) ? 1f : opacity;
                                    opacity = (opacity < .3f) ? .3f : opacity;
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater ? Color.Lerp(colorInfo.FireInRange, colorToLerp, .55f) : colorInfo.FireInRange) * (float)opacity, origin: origin);
                                    break;
                            }
                            if (!isWall)
                            {
                                if (!string.IsNullOrEmpty(dungeonGrid[i, j].Symbol))
                                {
                                    Vector2 size = font.MeasureString(dungeonGrid[i, j].Symbol);
                                    spriteBatch.DrawString(font, dungeonGrid[i, j].Symbol, new Vector2(i * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2),
                                        (j * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2))),
                                        dungeonGrid[i, j].SymbolColor * (float)opacity, 0f, new Vector2((int)(size.X / 2), (int)(size.Y / 2)), 1f, SpriteEffects.None, 0f);
                                }
                            }
                            else
                            {
                                if (!string.IsNullOrEmpty(dungeonGrid[i, j].Symbol))
                                {
                                    Vector2 size = font.MeasureString(dungeonGrid[i, j].Symbol);
                                    spriteBatch.DrawString(font, dungeonGrid[i, j].Symbol, new Vector2(i * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2),
                                        (j * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2))),
                                        dungeonGrid[i, j].SymbolColor * .85f, 0f, new Vector2((int)(size.X / 2), (int)(size.Y / 2)), 1f, SpriteEffects.None, 0f);
                                }
                            }
                        }
                        else if (dungeonGrid[i, j].NewlyFound)
                        {
                            float opacity = dungeonGrid[i, j].Opacity;
                            Color colorToLerp = tintFire ? colorInfo.FireInRange : colorInfo.WaterInRange; //Default to water, if fire then change it.
                            switch (dungeonGrid[i, j].Type)
                            {
                                case TileType.TILE_FLATTENEDGRASS:
                                case TileType.TILE_FLOOR:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.FloorInRange, colorToLerp, .55f) : colorInfo.FloorInRange) * opacity, origin: origin);
                                    break;
                                case TileType.TILE_ROCK:
                                case TileType.TILE_WALL:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.WallInRange, colorToLerp, .55f) : colorInfo.WallInRange) * opacity, origin: origin);
                                    break;
                                case TileType.TILE_TALLGRASS:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.TallGrassInRange, colorToLerp, .55f) : colorInfo.TallGrassInRange) * opacity, origin: origin);
                                    break;
                                case TileType.TILE_ASH:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater || tintFire ? Color.Lerp(colorInfo.AshInRange, colorToLerp, .55f) : colorInfo.AshInRange) * opacity, origin: origin);
                                    break;
                                case TileType.TILE_WATER:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (tintFire ? Color.Lerp(colorInfo.WaterInRange, colorToLerp, .55f) : colorInfo.WaterInRange) * opacity, origin: origin);
                                    break;
                                case TileType.TILE_FIRE:
                                    spriteBatch.Draw(spriteSheet, position: tile, color: (inWater ? Color.Lerp(colorInfo.FireInRange, colorToLerp, .55f) : colorInfo.FireInRange), origin: origin);
                                    break;
                            }
                            if (!string.IsNullOrEmpty(dungeonGrid[i, j].Symbol))
                            {
                                Vector2 size = font.MeasureString(dungeonGrid[i, j].Symbol);
                                spriteBatch.DrawString(font, dungeonGrid[i, j].Symbol, new Vector2(i * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2),
                                    (j * DevConstants.Grid.CellSize + (int)(DevConstants.Grid.CellSize / 2))),
                                    dungeonGrid[i, j].SymbolColor * opacity, 0f, new Vector2((int)(size.X / 2), (int)(size.Y / 2)), 1f, SpriteEffects.None, 0f);
                            }
                            if (dungeonGrid[i, j].Opacity > .5)
                            {
                                dungeonGrid[i, j].NewlyFound = false;
                                dungeonGrid[i, j].Found = true;
                            }
                        }
                    }


                }
            }


        }
예제 #5
0
        private static void CreateDijkstraMapToPlayers(DungeonTile[,] dungeonGrid, Vector2 dungeonDimensions, StateSpaceComponents spaceComponents, ref DijkstraMapTile[,] dijkstraMap)
        {
            List<Vector2> targets = new List<Vector2>();
            //targets are any entities with friendly AI and players
            foreach(Guid id in spaceComponents.Entities.Where(x => (x.ComponentFlags & Component.COMPONENT_PLAYER) == Component.COMPONENT_PLAYER).Select(x => x.Id))
            {
                targets.Add(spaceComponents.PositionComponents[id].Position);
            }
            foreach (Guid id in spaceComponents.Entities.Where(x => (x.ComponentFlags & Component.COMPONENT_AI_ALIGNMENT) == Component.COMPONENT_AI_ALIGNMENT).Select(x => x.Id))
            {
                if(spaceComponents.AIAlignmentComponents[id].Alignment == AIAlignments.ALIGNMENT_FRIENDLY)
                {
                    targets.Add(spaceComponents.PositionComponents[id].Position);
                }
            }

            //Set up map
            for (int i = 0; i < dungeonDimensions.X; i++)
            {
                for (int j = 0; j < dungeonDimensions.Y; j++)
                {
                    if (dungeonGrid[i, j].Occupiable)
                    {
                        dijkstraMap[i, j].Weight = DevConstants.Grid.WallWeight -1;
                    }
                    else
                    {
                        dijkstraMap[i, j].Weight = DevConstants.Grid.WallWeight;
                    }
                    if (targets.Contains(new Vector2(i, j)))
                    {
                        dijkstraMap[i, j].Weight = 0;
                    }
                    dijkstraMap[i, j].Checked = false;
                }
            }

            Queue<Vector2> floodQueue = new Queue<Vector2>();
            foreach(Vector2 item in targets)
            {
                floodQueue.Enqueue(item);
            }

            while (floodQueue.Count > 0)
            {
                Vector2 pos = floodQueue.Dequeue();

                int x = (int)pos.X;
                int y = (int)pos.Y;
                int lowestNeighbor = DevConstants.Grid.WallWeight;
                HashSet<Vector2> toAdd = new HashSet<Vector2>();
                for (int k = x - 1; k <= x + 1; k++)
                {
                    for (int l = y - 1; l <= y + 1; l++)
                    {
                        if (l >= 0 && k >= 0 && l < (int)dungeonDimensions.Y && k < (int)dungeonDimensions.X && dijkstraMap[(int)pos.X, (int)pos.Y].Weight != DevConstants.Grid.WallWeight)
                        {
                            lowestNeighbor = (lowestNeighbor < dijkstraMap[k, l].Weight) ? lowestNeighbor : dijkstraMap[k, l].Weight;
                            if(!dijkstraMap[k,l].Checked)
                            {
                                dijkstraMap[k, l].Checked = true;
                                floodQueue.Enqueue(new Vector2(k, l));
                            }
                        }
                    }
                }
                if (dijkstraMap[x,y].Weight >= lowestNeighbor + 2)
                {
                    dijkstraMap[x,y].Weight = lowestNeighbor + 1;
                }
            }




        }