A* algorithm now working as intended
This commit is contained in:
parent
5c1535da32
commit
80e990c432
@ -78,39 +78,39 @@ void AAdventureCameraPawn::EdgeScrollSide(float AxisValue)
|
|||||||
|
|
||||||
if (mousePosX <= ESASize) // if in LEFT area
|
if (mousePosX <= ESASize) // if in LEFT area
|
||||||
{
|
{
|
||||||
////// Scroll LEFT with Vert Accelleration
|
////// Scroll LEFT
|
||||||
float SpeedX = (mousePosX * ESAMinBoundSlope + ESAMinBoundIntercept) * BaseScrollSpeed;
|
float SpeedX = (mousePosX * ESAMinBoundSlope + ESAMinBoundIntercept) * BaseScrollSpeed;
|
||||||
AddActorLocalOffset(FVector(0, -SpeedX, 0));
|
AddActorLocalOffset(FVector(-SpeedX, 0, 0));
|
||||||
|
|
||||||
if (mousePosY > .005) // if not touching EDGE
|
if (mousePosY > .005) // if not touching TOP EDGE
|
||||||
{
|
{
|
||||||
AddActorLocalOffset(FVector(VertAccelleration, 0, 0));
|
AddActorLocalOffset(FVector(0, -VertAccelleration, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (AxisValue < .0 && mousePosX <= .005) // if mouse moving LEFT and touching EDGE
|
if (AxisValue < .0 && mousePosX <= .005) // if mouse moving LEFT and touching EDGE
|
||||||
{
|
{
|
||||||
////// Add LEFT accelleration
|
////// Add LEFT accelleration
|
||||||
SpeedX = AxisValue * ScrollAccelleration;
|
SpeedX = AxisValue * ScrollAccelleration;
|
||||||
AddActorLocalOffset(FVector(0, SpeedX, 0));
|
AddActorLocalOffset(FVector(SpeedX, 0, 0));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mousePosX >= 1-ESASize) // if in RIGHT area
|
if (mousePosX >= 1-ESASize) // if in RIGHT area
|
||||||
{
|
{
|
||||||
////// Scroll RIGHT with Vert Accelleration
|
////// Scroll RIGHT
|
||||||
float SpeedX = (mousePosX * ESAMaxBoundSlope + ESAMaxBoundIntercept) * BaseScrollSpeed;
|
float SpeedX = (mousePosX * ESAMaxBoundSlope + ESAMaxBoundIntercept) * BaseScrollSpeed;
|
||||||
AddActorLocalOffset(FVector(0, SpeedX, 0));
|
AddActorLocalOffset(FVector(SpeedX, 0, 0));
|
||||||
|
|
||||||
if (mousePosY < .995) // if not touching EDGE
|
if (mousePosY < .995) // if not touching BOT EDGE
|
||||||
{
|
{
|
||||||
AddActorLocalOffset(FVector(VertAccelleration, 0, 0));
|
AddActorLocalOffset(FVector(0, -VertAccelleration, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (AxisValue > .0 && mousePosX >= .995) // if mouse moving RIGHT and touching EDGE
|
if (AxisValue > .0 && mousePosX >= .995) // if mouse moving RIGHT and touching EDGE
|
||||||
{
|
{
|
||||||
////// Add RIGHT accelleration
|
////// Add RIGHT accelleration
|
||||||
SpeedX = AxisValue * ScrollAccelleration;
|
SpeedX = AxisValue * ScrollAccelleration;
|
||||||
AddActorLocalOffset(FVector(0, SpeedX, 0));
|
AddActorLocalOffset(FVector(SpeedX, 0, 0));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -126,39 +126,39 @@ void AAdventureCameraPawn::EdgeScrollVert(float AxisValue)
|
|||||||
|
|
||||||
if (mousePosY <= ESASize) // if in TOP area
|
if (mousePosY <= ESASize) // if in TOP area
|
||||||
{
|
{
|
||||||
////// Scroll TOP with Side Accelleration
|
////// Scroll TOP
|
||||||
float SpeedY = (mousePosY * ESAMinBoundSlope + ESAMinBoundIntercept) * BaseScrollSpeed;
|
float SpeedY = (mousePosY * ESAMinBoundSlope + ESAMinBoundIntercept) * BaseScrollSpeed;
|
||||||
AddActorLocalOffset(FVector(SpeedY, SideAccelleration, 0));
|
AddActorLocalOffset(FVector(0, -SpeedY, 0));
|
||||||
|
|
||||||
if (mousePosX > .005) // if not touching EDGE
|
if (mousePosX > .005) // if not touching EDGE
|
||||||
{
|
{
|
||||||
AddActorLocalOffset(FVector(0, SideAccelleration, 0));
|
AddActorLocalOffset(FVector(SideAccelleration, 0, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (AxisValue > .0 && mousePosY <= .005) // if mouse moving TOP and touching EDGE
|
if (AxisValue > .0 && mousePosY <= .005) // if mouse moving TOP and touching EDGE
|
||||||
{
|
{
|
||||||
////// Add TOP accelleration
|
////// Add TOP accelleration
|
||||||
SpeedY = AxisValue * ScrollAccelleration;
|
SpeedY = AxisValue * ScrollAccelleration;
|
||||||
AddActorLocalOffset(FVector(SpeedY, 0, 0));
|
AddActorLocalOffset(FVector(0, -SpeedY, 0));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mousePosY >= 1-ESASize) // if in BOTTOM area
|
if (mousePosY >= 1-ESASize) // if in BOTTOM area
|
||||||
{
|
{
|
||||||
////// Scroll BOTTOM with Side Accelleration
|
////// Scroll BOTTOM
|
||||||
float SpeedY = (mousePosY * ESAMaxBoundSlope + ESAMaxBoundIntercept) * BaseScrollSpeed;
|
float SpeedY = (mousePosY * ESAMaxBoundSlope + ESAMaxBoundIntercept) * BaseScrollSpeed;
|
||||||
AddActorLocalOffset(FVector(-SpeedY, SideAccelleration, 0));
|
AddActorLocalOffset(FVector(0, SpeedY, 0));
|
||||||
|
|
||||||
if (mousePosX < .995) // if not touching EDGE
|
if (mousePosX < .995) // if not touching BOT EDGE
|
||||||
{
|
{
|
||||||
AddActorLocalOffset(FVector(0, SideAccelleration, 0));
|
AddActorLocalOffset(FVector(SideAccelleration, 0, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (AxisValue < .0 && mousePosY >= .995) // if mouse moving BOTTOM and touching EDGE
|
if (AxisValue < .0 && mousePosY >= .995) // if mouse moving BOTTOM and touching EDGE
|
||||||
{
|
{
|
||||||
////// add BOTTOM accelleration
|
////// add BOTTOM accelleration
|
||||||
SpeedY = AxisValue * ScrollAccelleration;
|
SpeedY = AxisValue * ScrollAccelleration;
|
||||||
AddActorLocalOffset(FVector(SpeedY, 0, 0));
|
AddActorLocalOffset(FVector(0, -SpeedY, 0));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -82,57 +82,43 @@ int32 AAdventureMap::GridIndex(int32 qAxial, int32 rAxial)
|
|||||||
|
|
||||||
AHexTile* AAdventureMap::RandomHex()
|
AHexTile* AAdventureMap::RandomHex()
|
||||||
{
|
{
|
||||||
int32 RandHex = GridIndex(FMath::RandRange(0, GridSize-1), FMath::RandRange(0, GridSize-1));
|
int32 RandHex = FMath::RandRange(0, GridSize*GridSize-1);
|
||||||
return Grid[RandHex];
|
return Grid[RandHex];
|
||||||
}
|
}
|
||||||
|
|
||||||
TArray<AHexTile*> AAdventureMap::Neighbors(AHexTile* OfHex)
|
TArray<AHexTile*> AAdventureMap::Neighbors(AHexTile* OfHex)
|
||||||
{
|
{
|
||||||
TArray<AHexTile*> Neighbors;
|
TArray<AHexTile*> Neighbors;
|
||||||
int32 I;
|
int32 Arr[] = { GridIndex(OfHex->Q+1, OfHex->R), GridIndex(OfHex->Q+1, OfHex->R-1),
|
||||||
|
GridIndex(OfHex->Q, OfHex->R-1), GridIndex(OfHex->Q-1, OfHex->R),
|
||||||
I = GridIndex(OfHex->Q + 1 , OfHex->R + 0 );
|
GridIndex(OfHex->Q-1, OfHex->R+1), GridIndex(OfHex->Q, OfHex->R+1) };
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
TArray<int32> Indeces;
|
||||||
|
Indeces.Append(Arr, UE_ARRAY_COUNT(Arr));
|
||||||
I = GridIndex(OfHex->Q + 1 , OfHex->R - 1 );
|
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
|
||||||
|
|
||||||
I = GridIndex(OfHex->Q + 0 , OfHex->R - 1 );
|
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
|
||||||
|
|
||||||
I = GridIndex(OfHex->Q - 1 , OfHex->R + 0 );
|
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
|
||||||
|
|
||||||
I = GridIndex(OfHex->Q - 1 , OfHex->R + 1 );
|
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
|
||||||
|
|
||||||
I = GridIndex(OfHex->Q + 0 , OfHex->R + 1 );
|
|
||||||
if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); }
|
|
||||||
|
|
||||||
|
Neighbors.Add(RandomHex());
|
||||||
|
for (auto& I : Indeces) { if (Grid.IsValidIndex(I) && OfHex->Distance(Grid[I]) == 1) { Neighbors.Add(Grid[I]); } }
|
||||||
return Neighbors;
|
return Neighbors;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Massive memory leak when Goal is more than 2 distance away from Start (leading to the Editor freezing)
|
|
||||||
// Also freezes when the Goal is on the Edge of the map (i.e. has only 3 Neighbors)
|
|
||||||
TArray<AHexTile*> AAdventureMap::FindPathAStar(AHexTile* Start, AHexTile* Goal)
|
TArray<AHexTile*> AAdventureMap::FindPathAStar(AHexTile* Start, AHexTile* Goal)
|
||||||
{
|
{
|
||||||
TArray<AHexTile*> PQ; // Makeshift Priority Queue. (High value = Low priority)
|
TArray<AHexTile*> PQ; // Makeshift Priority Queue. (High value = Low priority)
|
||||||
PQ.Init(Start, 1);
|
PQ.Add(Start);
|
||||||
|
|
||||||
// The goal of this loop is to edit the Hex->CameFrom pointers, So as to chain Hexes from Goal to Start
|
// The goal of this loop is to edit the Hex->CameFrom pointers, So as to chain Hexes from Goal to Start
|
||||||
while (!PQ.IsEmpty())
|
while (!PQ.IsEmpty())
|
||||||
{
|
{
|
||||||
AHexTile* Current = PQ[0];
|
AHexTile* Current = PQ[0];
|
||||||
PQ.RemoveAt(0);
|
PQ.RemoveAt(0);
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Popping top priority Hex Q:%d|R:%d"), Current->Q, Current->R);
|
// UE_LOG(LogTemp, Warning, TEXT("Popping top priority Hex %d:%d"), Current->Q, Current->R); // debug
|
||||||
|
|
||||||
if (Current == Goal) // early exit
|
if (Current == Goal) // early exit
|
||||||
{
|
{
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Goal found!!!")); // debug
|
// UE_LOG(LogTemp, Warning, TEXT("Goal found!!!")); // debug
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Expanding the frontier...")); // debug
|
// UE_LOG(LogTemp, Warning, TEXT("Expanding the frontier...")); // debug
|
||||||
for (AHexTile* Next : Neighbors(Current))
|
for (AHexTile* Next : Neighbors(Current))
|
||||||
{
|
{
|
||||||
int32 NewCost = Current->CostSoFar + Next->MoveCost;
|
int32 NewCost = Current->CostSoFar + Next->MoveCost;
|
||||||
@ -143,33 +129,36 @@ TArray<AHexTile*> AAdventureMap::FindPathAStar(AHexTile* Start, AHexTile* Goal)
|
|||||||
PQ.Remove(Next);
|
PQ.Remove(Next);
|
||||||
int32 NewPrio = NewCost + Next->Distance(Goal); // Higher value = Lower priority
|
int32 NewPrio = NewCost + Next->Distance(Goal); // Higher value = Lower priority
|
||||||
|
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Hex Q:%d|R:%d pathing updated. Readjusting priorities..."), Next->Q, Next->R); // debug
|
// no crash up to this point
|
||||||
|
|
||||||
|
// UE_LOG(LogTemp, Warning, TEXT("Hex %d:%d path info updated. Readjusting priorities..."), Next->Q, Next->R); // debug
|
||||||
if (!PQ.IsEmpty())
|
if (!PQ.IsEmpty())
|
||||||
{
|
{
|
||||||
int32 OldPrio;
|
int32 OldPrio;
|
||||||
int32 OldIndex = PQ.Num() - 1; // To be inserted as lowest priority by default
|
int32 OldIndex = PQ.Num() - 1; // default to lowest priority
|
||||||
|
|
||||||
for (AHexTile* Hex : PQ)
|
for (auto& Hex : PQ)
|
||||||
{
|
{
|
||||||
OldPrio = Hex->CostSoFar + Hex->Distance(Goal);
|
OldPrio = Hex->CostSoFar + Hex->Distance(Goal);
|
||||||
if (NewPrio <= OldPrio) // looking for 1. Hex in "PQ" with a lower priority than that of "Next"
|
if (NewPrio <= OldPrio) // looking for 1. Hex in "PQ" with a lower priority than that of "Next"
|
||||||
{
|
{
|
||||||
PQ.Find(Hex, OldIndex); // redefining of "OldIndex"
|
PQ.Find(Hex, OldIndex); // redefine OldIndex
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Inserting Hex at priority %d"), OldIndex); // debug
|
// UE_LOG(LogTemp, Warning, TEXT("Saving at PQ index %d"), OldIndex); // debug
|
||||||
PQ.Insert(Next, OldIndex);
|
PQ.Insert(Next, OldIndex);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
PQ.Add(Next);
|
PQ.Add(Next);
|
||||||
UE_LOG(LogTemp, Warning, TEXT("Adding one last Candidate.")); // debug
|
// UE_LOG(LogTemp, Warning, TEXT("Adding (PQ was empty)")); // debug
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TArray<AHexTile*> Path;
|
TArray<AHexTile*> Path;
|
||||||
|
/*
|
||||||
AHexTile* Hex = Goal;
|
AHexTile* Hex = Goal;
|
||||||
while (Hex != Start)
|
while (Hex != Start)
|
||||||
{
|
{
|
||||||
@ -177,5 +166,6 @@ TArray<AHexTile*> AAdventureMap::FindPathAStar(AHexTile* Start, AHexTile* Goal)
|
|||||||
Hex = Hex->CameFrom;
|
Hex = Hex->CameFrom;
|
||||||
}
|
}
|
||||||
Algo::Reverse(Path);
|
Algo::Reverse(Path);
|
||||||
|
*/
|
||||||
return Path;
|
return Path;
|
||||||
}
|
}
|
Loading…
Reference in New Issue
Block a user