Skip to content

Commit 6053149

Browse files
committed
fix(pathfinder): Implement new robust forward insertion sort code
1 parent 7600a5c commit 6053149

2 files changed

Lines changed: 55 additions & 0 deletions

File tree

Core/GameEngine/Include/GameLogic/AIPathfind.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -331,6 +331,9 @@ class PathfindCell
331331
void forwardInsertionSortRetailCompatible(PathfindCellList& list);
332332
#endif
333333

334+
// Forward insertion sort, in ascending cost order
335+
void forwardInsertionSort(PathfindCellList& list);
336+
334337
/// put self on "open" list in ascending cost order
335338
void putOnSortedOpenList( PathfindCellList &list );
336339

Core/GameEngine/Source/GameLogic/AI/AIPathfind.cpp

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1680,6 +1680,7 @@ Bool PathfindCell::removeObstacle( Object *obstacle )
16801680
return true;
16811681
}
16821682

1683+
#if RETAIL_COMPATIBLE_PATHFINDING
16831684
// Retail compatible insertion sort
16841685
void PathfindCell::forwardInsertionSortRetailCompatible(PathfindCellList& list)
16851686
{
@@ -1734,11 +1735,62 @@ void PathfindCell::forwardInsertionSortRetailCompatible(PathfindCellList& list)
17341735
m_info->m_nextOpen = nullptr;
17351736
}
17361737
}
1738+
#endif
1739+
1740+
// Forward insertion sort, returns early if the list is being initialised or we are prepending the list
1741+
void PathfindCell::forwardInsertionSort(PathfindCellList& list)
1742+
{
1743+
DEBUG_ASSERTCRASH(m_info, ("Has to have info."));
1744+
DEBUG_ASSERTCRASH(m_info->m_closed == FALSE && m_info->m_open == FALSE, ("Serious error - Invalid flags. jba"));
1745+
1746+
// mark the new cell as being on the open list
1747+
m_info->m_open = true;
1748+
m_info->m_closed = false;
1749+
1750+
if (list.m_head == nullptr) {
1751+
m_info->m_prevOpen = nullptr;
1752+
m_info->m_nextOpen = nullptr;
1753+
list.m_head = this;
1754+
return;
1755+
}
1756+
1757+
// If the node needs inserting before the current list head
1758+
if (m_info->m_totalCost < list.m_head->m_info->m_totalCost) {
1759+
m_info->m_prevOpen = nullptr;
1760+
list.m_head->m_info->m_prevOpen = this->m_info;
1761+
m_info->m_nextOpen = list.m_head->m_info;
1762+
list.m_head = this;
1763+
return;
1764+
}
1765+
1766+
// Traverse the list to find correct position
1767+
PathfindCell* current = list.m_head;
1768+
while (current->m_info->m_nextOpen && current->m_info->m_nextOpen->m_totalCost <= m_info->m_totalCost) {
1769+
current = current->getNextOpen();
1770+
}
1771+
1772+
// Insert the new node in the correct position
1773+
m_info->m_nextOpen = current->m_info->m_nextOpen;
1774+
if (current->m_info->m_nextOpen != nullptr) {
1775+
current->m_info->m_nextOpen->m_prevOpen = this->m_info;
1776+
}
1777+
current->m_info->m_nextOpen = this->m_info;
1778+
m_info->m_prevOpen = current->m_info;
1779+
1780+
}
17371781

17381782
/// put self on "open" list in ascending cost order, return new list
17391783
void PathfindCell::putOnSortedOpenList( PathfindCellList &list )
17401784
{
1785+
#if RETAIL_COMPATIBLE_PATHFINDING
1786+
if (!s_useFixedPathfinding) {
17411787
forwardInsertionSortRetailCompatible(list);
1788+
return;
1789+
}
1790+
#endif
1791+
1792+
forwardInsertionSort(list);
1793+
17421794
}
17431795

17441796
/// remove self from "open" list

0 commit comments

Comments
 (0)