Exemplo n.º 1
0
 private void InitializeSubMap(int islandId)
 {
     if (islandId > 0 && islandId <= numberOfIslands)
     {
         if (SubMaps.ContainsKey(islandId) == false)
         {
             Console.WriteLine($"Creating submap with island id: {islandId}");
             SubMaps[islandId] = new SubMap(processedFullSizeMapDataForPathFinding, processedFullSizeMapDataForExploration, islandProcessedMapDataForPathFinding, islandId);
         }
     }
 }
Exemplo n.º 2
0
        public SubMap GetSubMap(Vector2 gridPosition, bool initializeIfNotPresent = false)
        {
            int islandId = TryGetIslandId((int)gridPosition.X, (int)gridPosition.Y);

            if (islandId == 0 || islandId == -1)
            {
                Console.WriteLine($"Unable to find any valid island id near pos: {gridPosition}.");
                return(null);
            }
            if (initializeIfNotPresent == true)
            {
                //InitializeSubMap(islandId);
            }
            SubMap subMap;
            bool   gotSubMap = SubMaps.TryGetValue(islandId, out subMap);

            if (gotSubMap)
            {
                return(subMap);
            }
            return(null);
        }
Exemplo n.º 3
0
        private void IdIslands(byte[] rawMapData, int bytesPerRow, long cols, long rows)
        {
            var       startTime = DateTime.Now;
            const int OutsideIslandsUnwalkable = -1;

            var baseMapArray = new byte[cols * Terrain.MapCellSizeI, rows *Terrain.MapCellSizeI];

            Terrain.PopulatePathfindingGrid(rawMapData, bytesPerRow, cols, rows, baseMapArray);

            islandProcessedMapDataForPathFinding = new int[cols * Terrain.MapCellSizeI, rows *Terrain.MapCellSizeI];
            var markArray = new int[cols * Terrain.MapCellSizeI, rows *Terrain.MapCellSizeI];

            var floodSpiller = new FloodSpiller();
            Predicate <int, int> positionQualifier = (x, y) => baseMapArray[x, y] == 0;
            var floodParameters = new FloodParameters(startX: 0, startY: 0)
            {
                ProcessStartAsFirstNeighbour = true,
                NeighbourhoodType            = NeighbourhoodType.Eight,
                Qualifier          = positionQualifier,
                NeighbourProcessor = (x, y, mark) =>
                {
                    islandProcessedMapDataForPathFinding[x, y] = OutsideIslandsUnwalkable;
                }
            };

            floodSpiller.SpillFlood(floodParameters, markArray);
            int currentIslandId           = 1;
            int currentStartX             = 0;
            int currentStartY             = 0;
            int sumOfCellsInCurrentIsland = 0;

            while (true)
            {
                var ret = GetPositionOfFirstMatchingValue(islandProcessedMapDataForPathFinding, 0);
                if (ret.Item1 == -1)
                {
                    // done. No more islands
                    break;
                }
                // add new submap

                SubMaps[currentIslandId] = new SubMap(currentIslandId, (int)cols * Terrain.MapCellSizeI, (int)rows * Terrain.MapCellSizeI);

                currentStartX = ret.Item1;
                currentStartY = ret.Item2;
                Predicate <int, int> positionQualifierIslands = (x, y) => islandProcessedMapDataForPathFinding[x, y] == 0;
                floodParameters = new FloodParameters(startX: currentStartX, startY: currentStartY)
                {
                    ProcessStartAsFirstNeighbour = true,
                    NeighbourhoodType            = NeighbourhoodType.Eight,
                    Qualifier          = positionQualifierIslands,
                    NeighbourProcessor = (x, y, mark) =>
                    {
                        islandProcessedMapDataForPathFinding[x, y] = currentIslandId;
                        if (processedFullSizeMapDataForPathFinding[x, y] == 1)
                        {
                            SubMaps[currentIslandId].SetExplorationGridValue(x, y, 1);
                            SubMaps[currentIslandId].AddNodeWithPosition(x, y);
                        }
                        sumOfCellsInCurrentIsland += 1;
                    }
                };
                floodSpiller.SpillFlood(floodParameters, markArray);
                Console.WriteLine("Sum of current cells: {0}", sumOfCellsInCurrentIsland);
                if (sumOfCellsInCurrentIsland < 50)
                {
                    SubMaps.Remove(currentIslandId);
                    // erase the area. F.ex sarn ramparts has a few rogue walkable pixels in the middle of nowhere
                    Predicate <int, int> eraseQualifier = (x, y) => islandProcessedMapDataForPathFinding[x, y] == currentIslandId;
                    floodParameters = new FloodParameters(startX: currentStartX, startY: currentStartY)
                    {
                        ProcessStartAsFirstNeighbour = true,
                        NeighbourhoodType            = NeighbourhoodType.Eight,
                        Qualifier          = eraseQualifier,
                        NeighbourProcessor = (x, y, mark) =>
                        {
                            islandProcessedMapDataForPathFinding[x, y] = OutsideIslandsUnwalkable;
                        }
                    };
                }
                else
                {
                    SubMaps[currentIslandId].InitializeExploration();
                    currentIslandId += 1;
                }
                sumOfCellsInCurrentIsland = 0;
            }
            numberOfIslands = currentIslandId - 1;
            //SaveArrayAsImage(islandProcessedMapDataForPathFinding);
            Console.WriteLine($"Id islands took: {DateTime.Now.Subtract(startTime).TotalMilliseconds} milliseconds");
        }