This project implements an A* search algorithm to find the shortest path between two points on an OpenStreetMap. The route is visualized using SFML (Simple and Fast Multimedia Library) with rich map rendering including roads, buildings, water bodies, parks, and more.
- A Path Finding Algorithm*: Efficient route planning using the A* search algorithm with heuristic optimization
- Rich Map Visualization:
- Roads with accurate widths and colors based on type (motorways, residential, etc.)
- Buildings with outlines
- Water bodies (lakes, rivers)
- Landuse areas (forests, parks, commercial, residential zones)
- Leisure areas (parks, playgrounds)
- Railways with proper styling
- Interactive Route Display:
- Orange path line showing your calculated route
- Green marker at start position
- Red marker at end position
- Real-time distance calculation in meters
- Prerequisites
- Dependencies Installation
- Building the Project
- Running the Application
- Testing
- Project Structure
- Troubleshooting
Before building this project, ensure you have the following installed:
- CMake >= 3.11.3
- Make >= 4.1 (Linux, Mac), 3.81 (Windows)
- C++ Compiler with C++17 support (gcc/g++ >= 7.4.0 or clang)
- Xcode Command Line Tools
- Homebrew package manager
- Build essentials package
- Standard development tools
- MinGW or Visual Studio 2017+ with C++17 support
- Or use WSL (Windows Subsystem for Linux)
SFML is used for graphics rendering and window management. This project uses SFML 3.0+ which has native Apple Silicon support.
# Install Homebrew if you haven't already
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
# Install SFML
brew install sfml# Update package list
sudo apt update
# Install dependencies
sudo apt install build-essential cmake
# Install SFML 3.0 (if available in your distro)
sudo apt install libsfml-dev
# If SFML 3.0 is not available, build from source:
git clone https://github.com/SFML/SFML.git
cd SFML
git checkout 3.0.0
mkdir build && cd build
cmake ..
make
sudo make install# Using vcpkg (recommended)
vcpkg install sfml
# Or download pre-built binaries from:
# https://www.sfml-dev.org/download.php# Check CMake version
cmake --version
# Check compiler version
g++ --version # or clang++ --version
# Verify SFML installation (the output should show SFML 3.x)
pkg-config --modversion sfml-all # Linux/MacWhen cloning this project, use the --recurse-submodules flag to include dependencies:
# Using HTTPS
git clone https://github.com/Bootcamp-AI/CppND-Route-Planning-Project.git --recurse-submodules
# Or using SSH
git clone git@github.com:Bootcamp-AI/CppND-Route-Planning-Project.git --recurse-submodulesIf you already cloned without submodules:
cd CppND-Route-Planning-Project
git submodule update --init --recursivecd CppND-Route-Planning-Project
mkdir build
cd buildcmake ..Expected output should show:
-- Found SFML 3.x.x in /path/to/sfml
-- Configuring done
-- Generating done
# On Linux/Mac
make
# On Windows with Visual Studio
cmake --build . --config Release
# Or with multiple cores (faster)
make -j$(nproc) # Linux
make -j$(sysctl -n hw.ncpu) # MacThe build creates two executables:
OSM_A_star_search- Main applicationtest- Unit tests
From the build directory:
./OSM_A_star_searchYou'll be prompted to enter coordinates:
Reading OpenStreetMap data from the following file: ../map.osm
The map coordinates begin at (0,0) in the lower left corner and end at (100,100) in the upper right.
Enter a start x between 0 and 100
10
Enter a start y between 0 and 100
10
Enter an end x between 0 and 100
90
Enter an end y between 0 and 100
90
Path found with 33 nodes.
Distance: 873.416 meters.
A window will open displaying:
- The OpenStreetMap with all features (roads, buildings, water, parks)
- Your calculated route as an orange line
- Green circle at the start position
- Red circle at the end position
./OSM_A_star_search -f ../map.osm
# Or use your own OSM file
./OSM_A_star_search -f /path/to/your/custom_map.osm# Diagonal route (long distance)
Start: (10, 10)
End: (90, 90)
# Short route
Start: (25, 25)
End: (35, 35)
# Horizontal route
Start: (10, 50)
End: (90, 50)
# Vertical route
Start: (50, 10)
End: (50, 90)- Click the window's close button (×)
- The window will close automatically when you're done viewing the route
The project includes comprehensive unit tests for the A* algorithm implementation.
From the build directory:
./testExpected output:
Running main() from .../gtest_main.cc
[==========] Running 4 tests from 1 test suite.
[----------] Global test environment set-up.
[----------] 4 tests from RoutePlannerTest
[ RUN ] RoutePlannerTest.TestCalculateHValue
[ OK ] RoutePlannerTest.TestCalculateHValue (X ms)
[ RUN ] RoutePlannerTest.TestAddNeighbors
[ OK ] RoutePlannerTest.TestAddNeighbors (X ms)
[ RUN ] RoutePlannerTest.TestConstructFinalPath
[ OK ] RoutePlannerTest.TestConstructFinalPath (X ms)
[ RUN ] RoutePlannerTest.TestAStarSearch
Path found with 33 nodes.
[ OK ] RoutePlannerTest.TestAStarSearch (X ms)
[----------] 4 tests from RoutePlannerTest (XXX ms total)
[----------] Global test environment tear-down
[==========] 4 tests from 1 test suite ran. (XXX ms total)
[ PASSED ] 4 tests.
- TestCalculateHValue: Validates the heuristic function (Euclidean distance)
- TestAddNeighbors: Ensures neighbors are correctly added to the open list
- TestConstructFinalPath: Verifies the path is built correctly from goal to start
- TestAStarSearch: End-to-end test of the complete A* algorithm
All tests must pass for the implementation to be considered correct.
CppND-Route-Planning-Project/
├── src/
│ ├── main.cpp # Application entry point
│ ├── model.cpp/h # OpenStreetMap data model
│ ├── route_model.cpp/h # Route-specific model extensions
│ ├── route_planner.cpp/h # A* algorithm implementation
│ └── sfml_render.cpp/h # SFML-based visualization
├── test/
│ └── utest_rp_a_star_search.cpp # Unit tests
├── thirdparty/
│ ├── pugixml/ # XML parsing library
│ └── googletest/ # Testing framework
├── build/ # Build directory (created by you)
├── map.osm # Default OpenStreetMap data
└── CMakeLists.txt # Build configuration
The project implements the A* pathfinding algorithm with these key components:
- Heuristic Function (h-value): Euclidean distance to the goal
- Cost Function (g-value): Actual distance traveled from start
- f-value: g-value + h-value (total estimated cost)
The algorithm:
- Starts at the user-specified start node
- Explores neighbors, calculating f-values
- Always expands the node with lowest f-value next
- Continues until reaching the goal
- Reconstructs the path by following parent pointers
The SFML renderer draws map elements in layers:
- Background: Light beige
- Landuses: Colored zones (forests, parks, commercial, etc.)
- Leisure areas: Light green parks
- Water bodies: Blue water features
- Railways: Grey tracks with white center lines
- Roads: Color and width based on road type
- Buildings: Tan rectangles with outlines
- Path: Orange line showing your route
- Markers: Green (start) and Red (end) circles
# Linux: Ensure pkg-config is installed
sudo apt install pkg-config
# Mac: Ensure Homebrew SFML is properly linked
brew link sfml
# All platforms: Check that SFML 3.x is installed
pkg-config --modversion sfml-allEnsure your compiler supports C++17:
# Check compiler version
g++ --version # Should be >= 7.4.0
clang++ --version # Should be >= 5.0
# Explicitly set compiler (if needed)
cmake -DCMAKE_CXX_COMPILER=g++-9 ..If you see errors about missing pugixml or googletest:
# From project root
git submodule update --init --recursive- Ensure SFML is correctly installed
- Try rebuilding from scratch:
cd build rm -rf * cmake .. make
- Ensure you're running from the
builddirectory - Check that
../map.osmexists relative tobuild/ - Use absolute path:
./OSM_A_star_search -f /absolute/path/to/map.osm
- Verify coordinates are between 0 and 100
- Ensure the map file is valid OpenStreetMap XML format
- Check that all dependencies built correctly
This project fully supports Apple Silicon Macs thanks to SFML 3.0:
- No Rosetta 2 translation needed
- Native ARM64 performance
- If you have issues, ensure you installed the ARM version of Homebrew:
# Check architecture arch # Should output: arm64 # If needed, install ARM Homebrew /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
If you encounter issues not covered here:
- Check that all prerequisites are correctly installed
- Verify you're using compatible versions (SFML 3.x, CMake 3.11+)
- Try a clean rebuild (
rm -rf build && mkdir build && cd build && cmake .. && make) - Check the GitHub Issues page for similar problems
- First run may take a few seconds to parse the OSM file
- Typical A* search completes in < 100ms
- Rendering is smooth at 60 FPS
- Path finding time depends on distance between start/end points
This project is part of the Udacity C++ Nanodegree program.
- OpenStreetMap for map data
- SFML for cross-platform graphics
- Google Test for unit testing framework
- pugixml for XML parsing
