public List<Vector> FindPath(Vector s, Vector e, Entity o)
        {
            start = s;
            end = e;
            entity = o;

            int w = map.blocks.GetLength(0);
            int h = map.blocks.GetLength(1);
            gScore = new int[w, h];
            hScore = new int[w, h];
            fScore = new int[w, h];
            cameFrom = new Vector[w, h];

            List<Vector> open = new List<Vector>();
            List<Vector> closed = new List<Vector>();

            open.Add(start);
            gScore[start.x, start.y] = 0;
            hScore[start.x, start.y] = calculateHeuristic(start);
            fScore[start.x, start.y] = hScore[start.x, start.y];

            while(open.Count > 0) {
                Vector point = getLowestPointIn(open);
                if(point == end) return reconstructPath(cameFrom[point.x, point.y]);
                open.Remove(point);
                closed.Add(point);

                List<Vector> neighbours = getNeighbourPoints(point);
                foreach(Vector p in neighbours) {
                    if(closed.Contains(p)) continue;

                    int gPossible = gScore[point.x, point.y] + distanceBetween(p, point);

                    if(!open.Contains(p) || (open.Contains(p) && gPossible < gScore[p.x, p.y])) {
                        if(!open.Contains(p)) open.Add(p);
                        cameFrom[p.x, p.y] = point;
                        gScore[p.x, p.y] = gPossible;
                        hScore[p.x, p.y] = calculateHeuristic(p);
                        fScore[p.x, p.y] = gPossible + hScore[p.x, p.y];
                    }
                }
            }
            return null;
        }
예제 #2
0
 public bool canMoveTo(Vector to, Vector from, Entity e)
 {
     if(to.x < 0 || to.y < 0 || to.x > 20 || to.y > 20) return false;
     if(e != player && player.getMovingTo() == to) return false;
     foreach(Entity ai in ais)
         if(e != ai && ai.getMovingTo() == to) return false;
     foreach(Entity crate in crates)
         if(e != null && e.canPushCrates && crate.pos / 32 == to) {
             Vector diff = crate.pos / 32 - from;
             return canMoveTo(to + diff, crate.pos / 32, crate);
         }
         else if(e != crate && crate.getMovingTo() == to) return false;
     foreach(Entity n in noCrates)
         if(n.pos / 32 == to && crates.Contains(e))
             return false;
     foreach(Entity s in safe)
         if(s.pos / 32 == to)
             return e == player;
     return !blocks[to.x, to.y];
 }
예제 #3
0
 public Trail(Vector p, Color c)
 {
     pos = p;
     color = c;
 }
예제 #4
0
        public void loadTestLevel(char[,] map)
        {
            levelLoaded = false;
            isTest = true;
            isCustom = false;

            trails.Clear();
            ais.Clear();
            crates.Clear();
            noCrates.Clear();
            safe.Clear();

            blocks = new bool[21, 21];
            for(int i = 0; i < 21; i++)
                for(int j = 0; j < 21; j++) {
                    blocks[i, j] = false;
                    switch(map[i, j]) {
                        case '#':
                            blocks[i, j] = true;
                            break;
                        case 'S':
                            player.pos = new Vector(32 * i, 32 * j);
                            break;
                        case 'E':
                            end = new Vector(i, j);
                            break;
                        case 'A':
                            Entity ai = new Entity();
                            ai.pos = new Vector(32 * i, 32 * j);
                            ai.color = Color.Red;
                            ai.canPushCrates = true;
                            ais.Add(ai);
                            break;
                        case 'C':
                            Entity crate = new Entity();
                            crate.pos = new Vector(32 * i, 32 * j);
                            crate.color = Color.Blue;
                            crates.Add(crate);
                            break;
                        case 'N':
                            Entity noCrate = new Entity();
                            noCrate.pos = new Vector(32 * i, 32 * j);
                            noCrate.color = Color.LightBlue;
                            noCrates.Add(noCrate);
                            break;
                        case 'G':
                            Entity s = new Entity();
                            s.pos = new Vector(32 * i, 32 * j);
                            s.color = Color.LightGray;
                            safe.Add(s);
                            break;
                    }
                }

            moving = false;
            levelLoaded = true;
        }
예제 #5
0
        public void loadLevel(int n)
        {
            levelLoaded = false;
            level = n;
            isTest = false;
            isCustom = false;
            if(n >= mapstore.maps.GetLength(0) || n < 0)
                return;

            trails.Clear();
            ais.Clear();
            crates.Clear();
            noCrates.Clear();
            safe.Clear();

            blocks = new bool[21, 21];
            bool foundStart = false;
            bool foundEnd = false;
            for(int i = 0; i < 21; i++)
                for(int j = 0; j < 21; j++) {
                    blocks[i, j] = false;
                    switch(mapstore.maps[n, j][i]) {
                        case '#':
                            blocks[i, j] = true;
                            break;
                        case 'S':
                            player.pos = new Vector(32 * i, 32 * j);
                            foundStart = true;
                            break;
                        case 'E':
                            end = new Vector(i, j);
                            foundEnd = true;
                            break;
                        case 'A':
                            Entity ai = new Entity();
                            ai.pos = new Vector(32 * i, 32 * j);
                            ai.color = Color.Red;
                            ai.canPushCrates = true;
                            ais.Add(ai);
                            break;
                        case 'C':
                            Entity crate = new Entity();
                            crate.pos = new Vector(32 * i, 32 * j);
                            crate.color = Color.Blue;
                            crates.Add(crate);
                            break;
                        case 'N':
                            Entity noCrate = new Entity();
                            noCrate.pos = new Vector(32 * i, 32 * j);
                            noCrate.color = Color.LightBlue;
                            noCrates.Add(noCrate);
                            break;
                        case 'G':
                            Entity s = new Entity();
                            s.pos = new Vector(32 * i, 32 * j);
                            s.color = Color.LightGray;
                            safe.Add(s);
                            break;
                    }
                }
            if(!foundStart || !foundEnd) {
                levelLoaded = false;
                Console.WriteLine("INVALID LEVEL MISSING A START OR END. OH GOD WHAT DO I DO");
                return;
            }

            moving = false;
            levelLoaded = true;
        }
예제 #6
0
        public void loadCustomLevel()
        {
            FileStream stream = File.Open("mapeditor.xml", FileMode.OpenOrCreate, FileAccess.Read);
            XmlSerializer serializer = new XmlSerializer(typeof(string[]));
            string[] map = (string[]) serializer.Deserialize(stream);
            levelLoaded = false;
            isTest = false;
            isCustom = true;

            trails.Clear();
            ais.Clear();
            crates.Clear();
            noCrates.Clear();
            safe.Clear();

            blocks = new bool[21, 21];
            for(int i = 0; i < 21; i++)
                for(int j = 0; j < 21; j++) {
                    blocks[i, j] = false;
                    if(map[j].Length == 0) continue;
                    switch(map[j][i]) {
                        case '#':
                            blocks[i, j] = true;
                            break;
                        case 'S':
                            player.pos = new Vector(32 * i, 32 * j);
                            break;
                        case 'E':
                            end = new Vector(i, j);
                            break;
                        case 'A':
                            Entity ai = new Entity();
                            ai.pos = new Vector(32 * i, 32 * j);
                            ai.color = Color.Red;
                            ai.canPushCrates = true;
                            ais.Add(ai);
                            break;
                        case 'C':
                            Entity crate = new Entity();
                            crate.pos = new Vector(32 * i, 32 * j);
                            crate.color = Color.Blue;
                            crates.Add(crate);
                            break;
                        case 'N':
                            Entity noCrate = new Entity();
                            noCrate.pos = new Vector(32 * i, 32 * j);
                            noCrate.color = Color.LightBlue;
                            noCrates.Add(noCrate);
                            break;
                        case 'G':
                            Entity s = new Entity();
                            s.pos = new Vector(32 * i, 32 * j);
                            s.color = Color.LightGray;
                            safe.Add(s);
                            break;
                    }
                }

            moving = false;
            levelLoaded = true;
            stream.Close();
        }
 private Vector getLowestPointIn(List<Vector> list)
 {
     int lowest = -1;
     Vector found = new Vector(-1, -1);
     foreach(Vector p in list) {
         Vector c = cameFrom[p.x, p.y];
         int dist = c == new Vector(-1, -1) ? 0 : gScore[c.x, c.y] + distanceBetween(p, c) + calculateHeuristic(p);
         if(dist <= lowest || lowest == -1) {
             lowest = dist;
             found = p;
         }
     }
     return found;
 }
 private int distanceBetween(Vector pos1, Vector pos2)
 {
     return (int) Math.Round(10 * Math.Sqrt(Math.Pow(pos1.x - pos2.x, 2) + Math.Pow(pos1.y - pos2.y, 2)));
 }
 private int calculateHeuristic(Vector pos)
 {
     return 10 * (Math.Abs(pos.x - end.x) + Math.Abs(pos.y - end.y));
 }
 private List<Vector> reconstructPath(Vector p)
 {
     if(p != start) {
         List<Vector> path = reconstructPath(cameFrom[p.x, p.y]);
         path.Add(p);
         return path;
     }
     else
         return new List<Vector>();
 }
 private List<Vector> getNeighbourPoints(Vector p)
 {
     List<Vector> found = new List<Vector>();
     if(canMoveTo(p.x + 1, p.y, p.x, p.y)) found.Add(new Vector(p.x + 1, p.y));
     if(canMoveTo(p.x - 1, p.y, p.x, p.y)) found.Add(new Vector(p.x - 1, p.y));
     if(canMoveTo(p.x, p.y + 1, p.x, p.y)) found.Add(new Vector(p.x, p.y + 1));
     if(canMoveTo(p.x, p.y - 1, p.x, p.y)) found.Add(new Vector(p.x, p.y - 1));
     return found;
 }