public static FloorPlanLocation Generate(FloorPlan fp)
 {
     return new FloorPlanLocation
     {
         Id = ++_idCount,
         XPos = RandomGenerator.Integer(),
         YPos = RandomGenerator.Integer(),
         FloorPlan = fp
     };
 }
 /// <summary>
 /// Generates a FloorPlan object with random values. Blueprint and FloorPlanData values are null.
 /// Has empty lists for Beacons and points of interest.
 /// </summary>
 /// <returns></returns>
 public static FloorPlan Generate()
 {
     var fp = new FloorPlan
     {
         Blueprint = null,
         Floor = RandomGenerator.Integer(50),
         Id = ++_idCount,
         ImageDataWidth = RandomGenerator.Integer(50),
         CalibrationImagePath = RandomGenerator.String(10),
         UserImagePath = RandomGenerator.String(10),
         Beacons = new List<Beacon>(),
         PointsOfInterest = new List<PointOfInterest>(),
     };
     fp.FloorDesc = fp.Floor.ToString();
     return fp;
 }
 private void Equals(FloorPlan expected, BeaconDto actual)
 {
     Assert.AreEqual(expected.Id, actual.Location.FloorPlanId);
     Assert.AreEqual(expected.Floor, actual.Location.Floor);
     Assert.AreEqual(expected.FloorDesc, actual.Location.FloorDesc);
 }
 private static bool IsFloorplanOwner(FloorPlan floorPlan, int userId)
 {
     return floorPlan != null
            && floorPlan.Blueprint.UserId == userId;
 }
        /// <summary>
        /// Fullfills pathfinding requests by returning a Route object.
        /// </summary>
        /// <param name="startX"></param>
        /// <param name="endX"></param>
        /// <param name="startY"></param>
        /// <param name="endY"></param>
        /// <param name="startFloor"></param>
        /// <param name="endFloor"></param>
        /// <returns></returns>
        public RouteDto getPath(int startX, int startY, int endX, int endY, FloorPlan startFloorPlan, FloorPlan endFloorPlan)
        {
            int startFloor = startFloorPlan.Floor;
            int endFloor = endFloorPlan.Floor;

            // The route object will contain the final route, if one exists
            RouteDto route = new RouteDto();

            if(_bluePrint == null)
            {
                return route.pathfindingError();
            }

            // Get map of start floor through api.
            // If something goes wrong, return a fail-code route
            bool[,] startFloorMap = getFloorMap(startFloor, _bluePrint);
            if (startFloorMap == null)
            {
                return route.pathfindingError();
            }

            // API call for endFloor map
            // (needed in places of different scope below)
            bool[,] endFloorMap = null;
            if (startFloor != endFloor)
            {
                endFloorMap = getFloorMap(endFloor, _bluePrint);

                if (endFloorMap == null)
                {
                    return route.pathfindingError();
                }
            }

            // BEGIN PATHFINDING /////////////////

            if (startFloor == endFloor)
            {
                AStarSearch searchPath = new AStarSearch(startFloorMap).run(startX, startY, endX, endY);

                if (searchPath.hasSolution())
                {
                    // Create the event for the path and add it to our route
                    lastFloorGridWidth = searchPath.gridLengthX;
                    lastFloorGridHeight = searchPath.gridLengthY;
                    return route.addPath(startFloor, searchPath.Solution.ToList());
                }

                // falls out to third-tier search
            }
            else
            {
                if (endFloorMap == null)
                {
                    return route.pathfindingError();
                }

                // API call searching for all "vertical paths" (VPs) from startFloor directly to endFloor
                var directPois = _bluePrint.NavigationalPois
                    .Where(v => v.Locations.Any(l => l.FloorPlan.Floor == startFloor) && v.Locations.Any(asd => asd.FloorPlan.Floor == endFloor))
                    .ToList();

                if (directPois != null && directPois.Count > 0)
                {
                    // Create the search objs here to be reused. Prevents duplicatoin of weighted-grid work.
                    AStarSearch search1 = new AStarSearch(startFloorMap);
                    AStarSearch search2 = new AStarSearch(endFloorMap);

                    // Here we are looking for a valid path using only one stairs, elevator, etc.
                    foreach (NavigationalPoi v in directPois)
                    {
                        // start floor
                        FloorPlanLocation fp1 = v.Locations.Where(x => x.FloorPlan.Floor == startFloor).FirstOrDefault();
                        int vertX1 = (int) (fp1.XPos * startFloorPlan.ImageDataWidth);
                        int vertY1 = (int) (fp1.YPos * startFloorPlan.ImageDataHeight);

                        // find path from user position to the "stairs"
                        search1.run(startX, startY, vertX1, vertY1);

                        // if we can't get to the "stairs" from here, lets try the next way up
                        if (!search1.hasSolution())
                        {
                            continue;
                        }

                        // end floor
                        FloorPlanLocation fp2 = v.Locations.Where(x => x.FloorPlan.Floor == endFloor).FirstOrDefault();
                        int vertX2 = (int) (fp2.XPos * endFloorPlan.ImageDataWidth);
                        int vertY2 = (int) (fp2.YPos * endFloorPlan.ImageDataHeight);

                        // find path from "stairs" to the ending position
                        search2.run(vertX2, vertY2, endX, endY);

                        // if we can't get to the "stairs" from here, we do not want to get to the return statement
                        if (!search2.hasSolution())
                        {
                            continue;
                        }

                        lastFloorGridWidth = search2.gridLengthX;
                        lastFloorGridHeight = search2.gridLengthY;

                        // Create solution
                        return route
                            .addPath(startFloor, search1.Solution.ToList())
                            .addVerticalTransisiton(v.Type, new CoordinateDto(vertX1, vertY1, search1.gridLengthX, search1.gridLengthY), startFloor,endFloor)
                            .addPath(endFloor, search2.Solution.ToList());

                    }

                    // falls out to third-tier search
                }
            }

            // the infamous third-tier search

            return route;
        }
 private void Equal(FloorPlan expected, FloorPlanDto actual)
 {
     Assert.AreEqual(expected.Floor, actual.Floor);
     Assert.AreEqual(expected.FloorDesc, actual.FloorDesc);
     Assert.AreEqual(expected.Id, actual.Id);
 }