From ee6ea3442d60c2aaa6428d77ee9e5c68c6127ef9 Mon Sep 17 00:00:00 2001 From: MitchellHansen Date: Sat, 22 Aug 2015 17:43:38 -0700 Subject: [PATCH] Prettied it up, comments, refactors --- aStar/App.cpp | 24 ++++-- aStar/App.h | 16 ++-- aStar/Explorer.cpp | 17 ++-- aStar/Explorer.h | 15 ++++ aStar/Map.cpp | 43 +++++++--- aStar/Map.h | 10 ++- aStar/Pather.cpp | 167 +++++++++--------------------------- aStar/Pather.h | 62 +++++++------ aStar/aStar.vcxproj | 4 + aStar/aStar.vcxproj.filters | 6 ++ aStar/node.cpp | 71 +++++++++------ aStar/node.h | 42 ++++++--- 12 files changed, 249 insertions(+), 228 deletions(-) diff --git a/aStar/App.cpp b/aStar/App.cpp index bed0fd0..5231a0d 100644 --- a/aStar/App.cpp +++ b/aStar/App.cpp @@ -16,12 +16,13 @@ void App::Init() { // Set up the background texture background_texture = new sf::Texture(); background_texture->loadFromFile("background.png"); - backgroundSprite.setTexture(*background_texture); + // Pixel array for drawing the tiles, explorer _pixelArray = new sf::Uint8[WINDOW_WIDTH * WINDOW_HEIGHT * 4]; pixel_array_texture.create(WINDOW_WIDTH, WINDOW_HEIGHT); + // Create the explorer, giving it a reference to the map data explorer = new Explorer(&map); } @@ -29,6 +30,8 @@ void App::Input() { while (window->pollEvent(event)) { if (event.type == sf::Event::Closed) window->close(); + + // Set the destination if (sf::Mouse::isButtonPressed(sf::Mouse::Left)) { sf::Vector2i mouse_position = sf::Mouse::getPosition(*window); explorer->setDestination(sf::Vector2i(mouse_position.x/ 5, mouse_position.y/ 5)); @@ -49,7 +52,10 @@ void App::Input() { } void App::Update(double step_size) { + Input(); + + // Have the explorer go one move forward explorer->move(); } @@ -57,6 +63,7 @@ void App::Render() { // HOUSEKEEPING + // Get the physics fps for the last render cycle physics_fps = physics_frame_count * render_fps; @@ -70,23 +77,28 @@ void App::Render() { // RENDERING + // Clear and draw a fresh background window->clear(sf::Color::Blue); window->draw(backgroundSprite); - sf::Vector2i pos; + // Clean up the pixel array and reset everything to 0's again for (int i = 0; i < WINDOW_WIDTH * WINDOW_HEIGHT * 4; i++) { _pixelArray[i] = 0; } - // Draw the tiles + // Color all the tiles for (int x = 0; x < Map::CELLS_WIDTH; x++) { for (int y = 0; y < Map::CELLS_HEIGHT; y++) { + // Get the current cell position + sf::Vector2i pos; pos.x = x; pos.y = y; + + // Use that to find the color of the tile at that position sf::Color thing = map.getTile(pos)->getColor(); - + // Fill the 4x4 pixel area taken up by the cell for (int x2 = 1; x2 < 5; x2++) { for (int y2 = 1; y2 < 5; y2++) { @@ -104,6 +116,7 @@ void App::Render() { } // Draw the explorer + // Basically the same as above, fills 4x4 area where the explorer is located for (int x2 = 1; x2 < 5; x2++) { for (int y2 = 1; y2 < 5; y2++) { @@ -120,11 +133,12 @@ void App::Render() { } } + // Update and draw the pixel array pixel_array_texture.update(_pixelArray); - pixel_array_sprite.setTexture(pixel_array_texture); window->draw(pixel_array_sprite); + // Finish! window->display(); } diff --git a/aStar/App.h b/aStar/App.h index d9754d8..aca04a2 100644 --- a/aStar/App.h +++ b/aStar/App.h @@ -3,6 +3,7 @@ #include "Map.h" #include "Explorer.h" +// 2d heap allocated array structure stolen off of stackOverflow template class MultiArray { private: @@ -13,8 +14,10 @@ public: MultiArray() { data = new cols[width]; } ~MultiArray() { delete[] data; } }; + class App { public: + // Constants static const int WINDOW_HEIGHT = 766; static const int WINDOW_WIDTH = 1596; @@ -28,18 +31,21 @@ public: private: + // Map and its data Map map; - sf::Uint8* _pixelArray; - sf::Sprite pixel_array_sprite; - sf::Texture pixel_array_texture; + // The explorer that will traverse the map Explorer* explorer; // Art assets sf::Texture* background_texture; - sf::Sprite backgroundSprite; + // Data required for hand drawing pixels + sf::Uint8* _pixelArray; + sf::Sprite pixel_array_sprite; + sf::Texture pixel_array_texture; + void Init(); void Input(); void Update(double step_size); @@ -50,7 +56,7 @@ private: // The events for the event handler sf::Event event; - // Loop management data, black magic, need to redo + // ============= Loop data ================== float time(); // Size of the physics steps to take diff --git a/aStar/Explorer.cpp b/aStar/Explorer.cpp index 27cab6a..d16a6a3 100644 --- a/aStar/Explorer.cpp +++ b/aStar/Explorer.cpp @@ -3,7 +3,7 @@ #include "Pather.h" Explorer::Explorer(Map* map_) { - color = sf::Color::Blue; + color = sf::Color::Yellow; position = sf::Vector2i(6, 10); map = map_; } @@ -22,12 +22,12 @@ sf::Color Explorer::getColor() { void Explorer::setDestination(sf::Vector2i destination_) { + // Call a* to get path plan(destination_); } bool Explorer::move() { - // While there are moves for us to take if (!movement_stack.empty()) { bool valid = false; // If the next move is valid, collision @@ -35,9 +35,9 @@ bool Explorer::move() { switch (x) { case 0: // North - if (!map->getTile(position.x, position.y - 1)->isSolid()) { - valid = true; - position = sf::Vector2i(position.x, position.y - 1); + if (!map->getTile(position.x, position.y - 1)->isSolid()) { // If the tile isn't solid + valid = true; // Set the move to valid + position = sf::Vector2i(position.x, position.y - 1); // Update the Explorers position } break; case 1: // East @@ -79,10 +79,13 @@ bool Explorer::move() { return false; } -// A* bool Explorer::plan(sf::Vector2i destination_) { + + // Create a new pather with the map data Pather pather(map); - movement_stack = pather.pathTo(position, destination_); + + // Get the movement list from the pather + movement_stack = pather.getPathTo(position, destination_); return true; } diff --git a/aStar/Explorer.h b/aStar/Explorer.h index ab60720..1a148dd 100644 --- a/aStar/Explorer.h +++ b/aStar/Explorer.h @@ -5,18 +5,33 @@ class Explorer { public: + // Constructors Explorer(Map* map_); ~Explorer(); + + // Getters sf::Vector2i getPosition(); sf::Color getColor(); + + // Move to the specified destination void setDestination(sf::Vector2i destination_); + + // Follow the pathlist for one move bool move(); + private: + // Color that will be drawn sf::Color color; + sf::Vector2i position; + + // Reference to the map data Map* map; + // Moves list that will be filled with plan(), and executed by move() std::deque movement_stack; + + // Fills the movement stack with moves bool plan(sf::Vector2i destination_); }; diff --git a/aStar/Map.cpp b/aStar/Map.cpp index e646991..963ec95 100644 --- a/aStar/Map.cpp +++ b/aStar/Map.cpp @@ -10,41 +10,64 @@ Map::Map() { Map::~Map() { } - - Tile* Map::getTile(sf::Vector2i position_) { + + // If the position is within bounds if (position_.x > CELLS_WIDTH || position_.x < 0 || position_.y > CELLS_HEIGHT || position_.y < 0) { return nullptr; } - - return tileArray[position_.x][position_.y]; + else + // Return the value specified + return tileArray[position_.x][position_.y]; } bool Map::isTileSolid(sf::Vector2i position_) { + + // If the position is within bounds if (position_.x >= CELLS_WIDTH || position_.x < 0 || position_.y >= CELLS_HEIGHT || position_.y < 0) { - return true; + return true; // If it isn't say that the tile is solid } else + // Return whether the tile is solid return tileArray[position_.x][position_.y]->isSolid(); } + Tile* Map::getTile(int x_, int y_) { - return tileArray[x_][y_]; + + // If the position is within bounds + if (x_ > CELLS_WIDTH || x_ < 0 + || y_ > CELLS_HEIGHT || y_ < 0) { + return nullptr; + } + else + // Return the value specified + return tileArray[x_][y_]; } -void Map::setTile(sf::Vector2i position, Tile* data) { - delete tileArray[position.x][position.y]; - tileArray[position.x][position.y] = data; +void Map::overwriteTile(sf::Vector2i position_, Tile* data) { + // If the position is within bounds + if (position_.x >= CELLS_WIDTH || position_.x < 0 + || position_.y >= CELLS_HEIGHT || position_.y < 0) { + return; // If it isn't just return + } + else { // If it is, then delete the old data, replace it with the new + delete tileArray[position_.x][position_.y]; + tileArray[position_.x][position_.y] = data; + } } void Map::Init() { + + // Fill up the map with a random scatter of solid and passable tiles + int q; for (int x = 0; x < CELLS_WIDTH; x++) { for (int y = 0; y < CELLS_HEIGHT; y++) { q = rand() % 100; - if (q > 90) { + if (q > 65) { tileArray[x][y] = new Tile(true, 100.0, sf::Color::Cyan); } else { diff --git a/aStar/Map.h b/aStar/Map.h index 4364cfc..a740240 100644 --- a/aStar/Map.h +++ b/aStar/Map.h @@ -4,21 +4,27 @@ class Map { public: + // Width and height of the map in individual cells static const int CELLS_HEIGHT = 153; static const int CELLS_WIDTH = 319; + // Constructors Map(); ~Map(); - + // Get the tile at the specified position, overloaded Tile* getTile(sf::Vector2i position); Tile* getTile(int x_, int y_); + bool isTileSolid(sf::Vector2i); - void setTile(sf::Vector2i position, Tile* data); + + // completely replaces the data at the specified position + void overwriteTile(sf::Vector2i position, Tile* data); private: void Init(); + // Data Tile* tileArray[319][153]; }; diff --git a/aStar/Pather.cpp b/aStar/Pather.cpp index 4cc4ff0..1c1eb0b 100644 --- a/aStar/Pather.cpp +++ b/aStar/Pather.cpp @@ -1,137 +1,46 @@ #include "Pather.h" #include -node::node(sf::Vector2i XY, double h, int cF, int cL, node* p, Pather* pather_) { - xy = XY; - hueristic = h; - cameFrom = cF; - closedList = cL; - parent = p; - pather = pather_; -} -node::node() { - -} -node::~node() { - -} - -void node::neighbors() { - - int x = pather->getEndNodePosition().x; - int y = pather->getEndNodePosition().y; - - sf::Vector2i dest0XY(xy.x, xy.y - 1); // North - if (!pather->map->isTileSolid(dest0XY) && pather->visitedMap(dest0XY.x, dest0XY.y) != 1) { - // If so, find the distance between this node and the end node, the hueristic - int tempx = (x - dest0XY.x); - int tempy = (y - dest0XY.y); - - // I think dv is the hueristic?? - double dv = sqrt((tempx * tempx) + (tempy * tempy)); - - double v = dv; - - // Take that value and create a new node - pather->openList.emplace(new node(dest0XY, v, 0, 1, pather->active_node, pather), v); - - // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap(dest0XY.x, dest0XY.y) = 1; - } - - sf::Vector2i dest1XY(xy.x + 1, xy.y); // East - if (!pather->map->isTileSolid(dest1XY) && pather->visitedMap(dest1XY.x, dest1XY.y) != 1) { - // If so, find the distance between this node and the end node, the hueristic - int tempx = (x - dest1XY.x); - int tempy = (y - dest1XY.y); - - // I think dv is the hueristic?? - double dv = sqrt((tempx * tempx) + (tempy * tempy)); - - double v = dv; - - // Take that value and create a new node - pather->openList.emplace(new node(dest1XY, v, 1, 1, pather->active_node, pather), v); - - // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap(dest1XY.x, dest1XY.y) = 1; - } - - sf::Vector2i dest2XY(xy.x, xy.y + 1); // South - if (!pather->map->isTileSolid(dest2XY) && pather->visitedMap(dest2XY.x, dest2XY.y) != 1) { - // If so, find the distance between this node and the end node, the hueristic - int tempx = (x - dest2XY.x); - int tempy = (y - dest2XY.y); - - // I think dv is the hueristic?? - double dv = sqrt((tempx * tempx) + (tempy * tempy)); - - double v = dv; - - // Take that value and create a new node - pather->openList.emplace(new node(dest2XY, v, 2, 1, pather->active_node, pather), v); - - // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap(dest2XY.x, dest2XY.y) = 1; - } - - sf::Vector2i dest3XY(xy.x - 1, xy.y); // West - if (!pather->map->isTileSolid(dest3XY) && pather->visitedMap(dest3XY.x, dest3XY.y) != 1) { - // If so, find the distance between this node and the end node, the hueristic - int tempx = (x - dest3XY.x); - int tempy = (y - dest3XY.y); - - // I think dv is the hueristic?? - double dv = sqrt((tempx * tempx) + (tempy * tempy)); - - double v = dv; - - // Take that value and create a new node - pather->openList.emplace(new node(dest3XY, v, 3, 1, pather->active_node, pather), v); - - // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap(dest3XY.x, dest3XY.y) = 1; - } -} Pather::Pather(Map* map_) { map = map_; - //visitedMap = new MultiArray(); } Pather::~Pather() { } sf::Vector2i Pather::getEndNodePosition() { - return end_node->xy; + return end_node->getPosition(); } -std::deque Pather::pathTo(sf::Vector2i start, sf::Vector2i end) { +node* Pather::getActiveNode() { + return active_node; +} - - // Clear the visited map for erroneous data +std::deque Pather::getPathTo(sf::Vector2i start, sf::Vector2i end) { + + // Clear the visited map of erroneous data for (int i = 0; i < Map::CELLS_WIDTH; i++) { for (int l = 0; l < Map::CELLS_HEIGHT; l++) { - visitedMap(i, l) = 0; + visited_map(i, l) = 0; } } - - std::cout << visitedMap(10, 163); // Place the start and end nodes - start_node = new node(start, 7000, 0, 0, nullptr, this); - end_node = new node(end, 0, 0, 0, nullptr, this); + start_node = new node(start, 7000, 0, nullptr, this); + end_node = new node(end, 0, 0, nullptr, this); // Set the entry point, clean up any stray data from last run active_node = start_node; - openList.clear(); - closedList.clear(); + open_list.clear(); + closed_list.clear(); - // Seed for the loop - openList.emplace(start_node, start_node->hueristic); + // Seed for the loop, hueristic is intentionally high + open_list.emplace(start_node, start_node->getHueristic()); + // Set up the early exit, and enter into the loop early_exit = false; path_list = loop(); @@ -141,26 +50,29 @@ std::deque Pather::pathTo(sf::Vector2i start, sf::Vector2i end) { std::deque Pather::loop() { - // Damn thing keeps falling out of scope - - - while (!openList.empty() && !early_exit) { - // Early exit jankyness, need to change this - if (closedList.size() > 1000) { - no_path = true; - early_exit = true; + while (!open_list.empty() && !early_exit) { + + if (closed_list.size() > 1000) { // Quits when the path gets to be over 1000 long, janky + no_path = true; // Signal no path was found + early_exit = true; // Break break; } - if (active_node->xy.x == end_node->xy.x && active_node->xy.y == end_node->xy.y) { + + // Check to see if we're at our destination, break if we are + if (active_node->getPosition().x == end_node->getPosition().x && active_node->getPosition().y == end_node->getPosition().y) { early_exit = true; break; } + + // If we didn't get held up before, do a round of a* else { + // Find the pair with the lowest hueristic - // 5/10 - std::pair bestMin(start_node, 10000); + std::pair bestMin(start_node, 10000); // Get a clean value for the comparison - for (auto testMin: openList) { + // Compare all the values in openList for the one with the smallest hueristic + // O(n) complexity so it can get verrrrryyyy slow + for (auto testMin: open_list) { if (bestMin.second >= testMin.second) bestMin = testMin; } @@ -169,22 +81,23 @@ std::deque Pather::loop() { active_node = bestMin.first; // Find the neighbors for that node - active_node->neighbors(); + active_node->getNewNeighbors(); // Remove the active node from the openlist as you have visited it and called its neighbors - openList.erase(active_node); + open_list.erase(active_node); // Check to see if the node has already been added to the closed list, if not, add it - if (closedList.count(active_node) == 0) { - closedList.emplace(active_node, active_node->hueristic); + if (closed_list.count(active_node) == 0) { + closed_list.emplace(active_node, active_node->getHueristic()); } } } + // When we're done, get the return path std::deque return_path = returnPath(); - if (no_path || return_path.empty()) { + if (no_path || return_path.empty()) { // If we had an error, display it return std::deque(); std::cout << " no return path " << std::endl; } @@ -193,12 +106,14 @@ std::deque Pather::loop() { } std::deque Pather::returnPath() { + // Deque that will be returned std::deque path; - while (active_node->parent != nullptr) { - path.push_back(active_node->cameFrom); + // Backtrack through the active_nodes, adding their cameFrom value to the deque + while (active_node->getParent() != nullptr) { + path.push_back(active_node->getCameFrom()); - node* parent = active_node->parent; + node* parent = active_node->getParent(); delete active_node; active_node = parent; } diff --git a/aStar/Pather.h b/aStar/Pather.h index 57141ef..7ed32ff 100644 --- a/aStar/Pather.h +++ b/aStar/Pather.h @@ -2,58 +2,54 @@ #include #include "App.h" #include - -class Pather; - -class node { -public: - - node(sf::Vector2i XY, double h, int cF, int cL, node* p, Pather* pather_); - node(); - ~node(); - - sf::Vector2i xy; - - // Ugh, pointers, ugh c++ - node* parent; - double hueristic; - int cameFrom; - int closedList; - Pather* pather; - - void neighbors(); -private: - -}; +#include "node.h" class Pather { + public: + // Constructor Pather(Map* map_); ~Pather(); + // Reference to the map data Map* map; - std::unordered_map openList; - std::unordered_map closedList; + // Containers for the loop, probably inefficient as hell + std::unordered_map open_list; + std::unordered_map closed_list; - MultiArray visitedMap; - //int visitedMap[App::WINDOW_HEIGHT][App::WINDOW_WIDTH]; + // A stack allocated 2d array from a template I stole from stackOverflow + MultiArray visited_map; - std::deque pathTo(sf::Vector2i start, sf::Vector2i end); - std::deque loop(); - std::deque returnPath(); + // Return a deque with the movement info to path to the end position from the start position + std::deque getPathTo(sf::Vector2i start, sf::Vector2i end); + // Returns the end node of the current path sf::Vector2i getEndNodePosition(); - node* start_node; - node* active_node; + // Returns the current active node + node* getActiveNode(); +private: + // Whether we couldn't find a path bool no_path = false; + // If we found the path and can exit early bool early_exit; + + // Calculate the return path from back tracing the active nodes + std::deque returnPath(); -private: + // The main iterative loop for a* + std::deque loop(); + // Movement list for the Explorer std::deque path_list; + + // Start positions node + node* start_node; + // Current positions node + node* active_node; + // End positions node node* end_node; }; diff --git a/aStar/aStar.vcxproj b/aStar/aStar.vcxproj index 779db3f..c1c8c2b 100644 --- a/aStar/aStar.vcxproj +++ b/aStar/aStar.vcxproj @@ -160,6 +160,7 @@ + @@ -170,6 +171,9 @@ + + + diff --git a/aStar/aStar.vcxproj.filters b/aStar/aStar.vcxproj.filters index 0e28dba..56ec0f8 100644 --- a/aStar/aStar.vcxproj.filters +++ b/aStar/aStar.vcxproj.filters @@ -33,6 +33,9 @@ Source Files + + Source Files + @@ -51,4 +54,7 @@ Header Files + + + \ No newline at end of file diff --git a/aStar/node.cpp b/aStar/node.cpp index 6a7e3f1..64b51ca 100644 --- a/aStar/node.cpp +++ b/aStar/node.cpp @@ -1,11 +1,9 @@ -#pragma once -#include "node.h" +#include "Pather.h" -node::node(sf::Vector2i XY, int h, int cF, int cL, node* p, Pather* pather_) { - xy = XY; +node::node(sf::Vector2i XY, double h, int cF, node* p, Pather* pather_) { + position = XY; hueristic = h; - cameFrom = cF; - closedList = cL; + came_from = cF; parent = p; pather = pather_; } @@ -16,13 +14,14 @@ node::~node() { } -void node::neighbors() { +void node::getNewNeighbors() { + // Get the end node position for calculating distance from end(hueristic) int x = pather->getEndNodePosition().x; int y = pather->getEndNodePosition().y; - sf::Vector2i dest0XY(xy.x, xy.y - 1); // North - if (!pather->map->isTileSolid(dest0XY) && pather->visitedMap[dest0XY.x][dest0XY.y] != 1) { + sf::Vector2i dest0XY(position.x, position.y - 1); // North + if (!pather->map->isTileSolid(dest0XY) && pather->visited_map(dest0XY.x, dest0XY.y) != 1) { // If so, find the distance between this node and the end node, the hueristic int tempx = (x - dest0XY.x); int tempy = (y - dest0XY.y); @@ -30,17 +29,17 @@ void node::neighbors() { // I think dv is the hueristic?? double dv = sqrt((tempx * tempx) + (tempy * tempy)); - int v = static_cast(dv); + double v = dv; // Take that value and create a new node - pather->openList.emplace(new node(dest0XY, v, 0, 1, pather->active_node, pather), v); + pather->open_list.emplace(new node(dest0XY, v, 0, pather->getActiveNode(), pather), v); // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap[dest0XY.x][dest0XY.y] = 1; + pather->visited_map(dest0XY.x, dest0XY.y) = 1; } - sf::Vector2i dest1XY(xy.x + 1, xy.y); // East - if (!pather->map->isTileSolid(dest1XY) && pather->visitedMap[dest1XY.x][dest1XY.y] != 1) { + sf::Vector2i dest1XY(position.x + 1, position.y); // East + if (!pather->map->isTileSolid(dest1XY) && pather->visited_map(dest1XY.x, dest1XY.y) != 1) { // If so, find the distance between this node and the end node, the hueristic int tempx = (x - dest1XY.x); int tempy = (y - dest1XY.y); @@ -48,17 +47,17 @@ void node::neighbors() { // I think dv is the hueristic?? double dv = sqrt((tempx * tempx) + (tempy * tempy)); - int v = static_cast(dv); + double v = dv; // Take that value and create a new node - pather->openList.emplace(new node(dest1XY, v, 0, 1, pather->active_node, pather), v); + pather->open_list.emplace(new node(dest1XY, v, 1, pather->getActiveNode(), pather), v); // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap[dest1XY.x][dest1XY.y] = 1; + pather->visited_map(dest1XY.x, dest1XY.y) = 1; } - sf::Vector2i dest2XY(xy.x, xy.y + 1); // South - if (!pather->map->isTileSolid(dest2XY) && pather->visitedMap[dest2XY.x][dest2XY.y] != 1) { + sf::Vector2i dest2XY(position.x, position.y + 1); // South + if (!pather->map->isTileSolid(dest2XY) && pather->visited_map(dest2XY.x, dest2XY.y) != 1) { // If so, find the distance between this node and the end node, the hueristic int tempx = (x - dest2XY.x); int tempy = (y - dest2XY.y); @@ -66,17 +65,17 @@ void node::neighbors() { // I think dv is the hueristic?? double dv = sqrt((tempx * tempx) + (tempy * tempy)); - int v = static_cast(dv); + double v = dv; // Take that value and create a new node - pather->openList.emplace(new node(dest2XY, v, 0, 1, pather->active_node, pather), v); + pather->open_list.emplace(new node(dest2XY, v, 2, pather->getActiveNode(), pather), v); // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap[dest2XY.x][dest2XY.y] = 1; + pather->visited_map(dest2XY.x, dest2XY.y) = 1; } - sf::Vector2i dest3XY(xy.x - 1, xy.y); // West - if (!pather->map->isTileSolid(dest3XY) && pather->visitedMap[dest3XY.x][dest3XY.y] != 1) { + sf::Vector2i dest3XY(position.x - 1, position.y); // West + if (!pather->map->isTileSolid(dest3XY) && pather->visited_map(dest3XY.x, dest3XY.y) != 1) { // If so, find the distance between this node and the end node, the hueristic int tempx = (x - dest3XY.x); int tempy = (y - dest3XY.y); @@ -84,12 +83,28 @@ void node::neighbors() { // I think dv is the hueristic?? double dv = sqrt((tempx * tempx) + (tempy * tempy)); - int v = static_cast(dv); + double v = dv; // Take that value and create a new node - pather->openList.emplace(new node(dest3XY, v, 0, 1, pather->active_node, pather), v); + pather->open_list.emplace(new node(dest3XY, v, 3, pather->getActiveNode(), pather), v); // Set that tile as visited so we don't get stuck in a loop - pather->visitedMap[dest3XY.x][dest3XY.y] = 1; + pather->visited_map(dest3XY.x, dest3XY.y) = 1; } -} \ No newline at end of file +} + +sf::Vector2i node::getPosition() { + return position; +} + +node* node::getParent() { + return parent; +} + +double node::getHueristic() { + return hueristic; +} + +int node::getCameFrom() { + return came_from; +} diff --git a/aStar/node.h b/aStar/node.h index 5a56aed..b3589e2 100644 --- a/aStar/node.h +++ b/aStar/node.h @@ -1,26 +1,44 @@ #pragma once -#include +#include #include "App.h" +#include + +class Pather; class node { public: - - node(sf::Vector2i XY, int h, int cF, int cL, node* p, Pather* pather_); + + // XY position, hueristic value, cameFrom direction, parent, ref to pather + node(sf::Vector2i position_, double hueristic_, int came_from_, node* parent_, Pather* pather_); node(); ~node(); - sf::Vector2i xy; + - // Ugh, pointers, ugh c++ - node* parent; - int hueristic; - int cameFrom; - int closedList; - Pather* pather; + // Populate the open_list with neighbors + void getNewNeighbors(); + + // HAS THE ABILITY TO DELETE THE PARENT!! + node* getParent(); + + sf::Vector2i getPosition(); + double getHueristic(); + int getCameFrom(); - void neighbors(); private: + // Position of the node + sf::Vector2i position; + + // The parent of the node, previous one visited + node* parent; -}; + // How close it is to the destination + double hueristic; + // What direction the parent was + int came_from; + + // Ref to pather + Pather* pather; +}; \ No newline at end of file