Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
d941552
Add RTSFormationsPlugin
Ji-Rath Jul 14, 2022
2bb9800
Some small discoveries about LOD Processors
Ji-Rath Jul 14, 2022
8aba178
Fix crash on endplay
Ji-Rath Jul 18, 2022
d7998fc
Second pass on unit formations. While it is more organized than previ…
Ji-Rath Jul 19, 2022
2111c5c
Begin optimizing new formation system
Ji-Rath Jul 21, 2022
1fbb7f8
Add simple variable tick rate to rts movement processor
Ji-Rath Jul 22, 2022
562bbf8
Performance refactoring
Ji-Rath Jul 22, 2022
1af4c82
Fix single entity not moving when changing position occasionally
Ji-Rath Jul 22, 2022
cf9bdb0
Fix entity creation/destruction not properly updating unit
Ji-Rath Jul 22, 2022
eaadfd2
Implement entity offset so that unit position doesnt have to be recal…
Ji-Rath Jul 23, 2022
d1a0acd
Refactor position logic for units to support hollow formation
Ji-Rath Jul 23, 2022
1bd4286
Implement basic circle formation
Ji-Rath Aug 8, 2022
e27e63e
Add formation presets
Ji-Rath Aug 8, 2022
c28ff6f
Add circle formation variables
Ji-Rath Aug 8, 2022
f3853a2
Attempt to resolve incorrect order while smooth rotating unit
Ji-Rath Aug 16, 2022
ed66d86
Refactor formation rotation logic to use FRotator since the logic for…
Ji-Rath Aug 23, 2022
20a1627
Refactor UpdateUnitPosition and implement CalculateNewPositions() to …
Ji-Rath Aug 27, 2022
a9d3b12
Cleanup RTSFormationSubsystem
Ji-Rath Aug 29, 2022
5eb1eda
Extend the Gameplay Debuggger to enable RTS Unit debugging
Ji-Rath Aug 29, 2022
ec3ab60
Add RTSAgentSubsystem for agent position tracking and communication t…
Ji-Rath Sep 2, 2022
a316107
Add LaunchEntityProcessor to handle launching entities
Ji-Rath Sep 2, 2022
e95a2fc
Begin implementing HashGrid to entities for querying positions
Ji-Rath Sep 2, 2022
e401d35
Implement basic hashgrid processors to update and set location of ent…
Ji-Rath Sep 2, 2022
4e3c93c
Clean up Signaling entities and ensure that there are entities to sig…
Ji-Rath Sep 8, 2022
8f5b90b
Fix entities not updating their index due to legacy code
Ji-Rath Sep 8, 2022
c931510
Add RTSAgentProcessors to handle hash grid positions of RTS agents
Ji-Rath Sep 8, 2022
4b1b2b9
Change LaunchEntityProcessor to a Signal Processor since I couldnt ge…
Ji-Rath Sep 8, 2022
971de22
Add BP_RTSPlayer for birds-eye view of map
Ji-Rath Sep 8, 2022
7e65b59
Modify BP_SpawnUnit and BP_SpawnEntity to use new base class BP_Pad
Ji-Rath Sep 8, 2022
0b34daa
Cleanup BP_FormationGameMode and re-enable randomized position genera…
Ji-Rath Sep 8, 2022
dfc1367
Modify DA_AgentFormation so LODSimulation is no longer included by de…
Ji-Rath Sep 8, 2022
f9eea66
Adjust LaunchEntities function to use QuerySmall and Signal processin…
Ji-Rath Sep 8, 2022
5ec694b
Update RTSFormationExample map so that updated gamemode and character…
Ji-Rath Sep 8, 2022
7256e5c
Fix header files being in wrong folder location
Ji-Rath Sep 8, 2022
7ed49cc
Merge branch 'Megafunk:main' into RTSFormations
Ji-Rath Aug 21, 2024
60ac80f
Update to 5.4
Ji-Rath Aug 21, 2024
4688504
Update how subsystems are retrieved so they are more inline with nati…
Ji-Rath Aug 22, 2024
fc1332b
Push RTSGameMode to support simple top down view
Ji-Rath Aug 22, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_FormationUnit.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_Pad.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_RTSGameMode.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_RTSPlayer.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_SpawnEntity.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/BP_SpawnUnit.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/DA_AgentFormation.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/DA_Circle.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/DA_Hollow.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/DA_Rectangle.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/DA_Spear.uasset
Git LFS file not shown
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Content/RTSFormationsExample.umap
Git LFS file not shown
46 changes: 46 additions & 0 deletions Plugins/RTSFormations/RTSFormations.uplugin
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
{
"FileVersion": 3,
"Version": 1,
"VersionName": "1.0",
"FriendlyName": "RTSFormations",
"Description": "",
"Category": "Other",
"CreatedBy": "JiRath",
"CreatedByURL": "",
"DocsURL": "",
"MarketplaceURL": "",
"SupportURL": "",
"CanContainContent": true,
"IsBetaVersion": true,
"IsExperimentalVersion": false,
"Installed": false,
"Modules": [
{
"Name": "RTSFormations",
"Type": "Runtime",
"LoadingPhase": "Default"
}
],
"Plugins": [
{
"Name": "MassGameplay",
"Enabled": true
},
{
"Name": "MassEntity",
"Enabled": true
},
{
"Name": "MassAI",
"Enabled": true
},
{
"Name": "StructUtils",
"Enabled": true
},
{
"Name": "MassCommunitySample",
"Enabled": true
}
]
}
3 changes: 3 additions & 0 deletions Plugins/RTSFormations/Resources/Icon128.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
// Fill out your copyright notice in the Description page of Project Settings.


#include "FormationPresets.h"

Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
// Fill out your copyright notice in the Description page of Project Settings.


#include "GameplayDebuggerCategory_RTSAgents.h"

#include "DrawDebugHelpers.h"
#include "MassEntitySubsystem.h"
#include "MassNavigationFragments.h"
#include "Engine/World.h"

#if WITH_GAMEPLAY_DEBUGGER

#include "GameFramework/PlayerController.h"

FGameplayDebuggerCategory_RTSAgents::FGameplayDebuggerCategory_RTSAgents()
{
bShowOnlyWithDebugActor = false;
SetDataPackReplication<FRepData>(&DataPack);
}

void FGameplayDebuggerCategory_RTSAgents::CollectData(APlayerController* OwnerPC, AActor* DebugActor)
{
if (OwnerPC)
{
//DataPack.ActorName = OwnerPC->GetPawn()->GetName();
URTSFormationSubsystem* FormationSubsystem = UWorld::GetSubsystem<URTSFormationSubsystem>(OwnerPC->GetWorld());
UMassEntitySubsystem* EntitySubsystem = UWorld::GetSubsystem<UMassEntitySubsystem>(OwnerPC->GetWorld());
DataPack.NumUnits = FormationSubsystem->Units.Num();

DataPack.Positions.Empty();
DataPack.Positions.Reserve(FormationSubsystem->Units[0].Entities.Num());

for(auto& Entity : FormationSubsystem->Units[0].Entities)
{
const FVector& Pos = EntitySubsystem->GetEntityManager().GetFragmentDataChecked<FMassMoveTargetFragment>(Entity).Center;
DataPack.Positions.Add(Pos);
}
}
}

void FGameplayDebuggerCategory_RTSAgents::DrawData(APlayerController* OwnerPC, FGameplayDebuggerCanvasContext& CanvasContext)
{
CanvasContext.Printf(TEXT("{yellow}Units: {white}%d"), DataPack.NumUnits);
CanvasContext.Printf(TEXT("{yellow}Entities in Unit 0: {white}%d"), DataPack.Positions.Num());
for(FVector& Pos : DataPack.Positions)
{
DrawDebugCanvasWireSphere(CanvasContext.Canvas.Get(), Pos, FColor::Yellow, 20.f, 5);
}
}

TSharedRef<FGameplayDebuggerCategory> FGameplayDebuggerCategory_RTSAgents::MakeInstance()
{
return MakeShareable(new FGameplayDebuggerCategory_RTSAgents());
}

void FGameplayDebuggerCategory_RTSAgents::FRepData::Serialize(FArchive& Ar)
{
Ar << Positions;
Ar << NumUnits;
}

#endif // WITH_GAMEPLAY_DEBUGGER
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
// Fill out your copyright notice in the Description page of Project Settings.
#include "LaunchEntityProcessor.h"

#include "DrawDebugHelpers.h"
#include "MassCommonFragments.h"
#include "MassExecutionContext.h"
#include "MassMovementFragments.h"
#include "MassNavigationFragments.h"
#include "TimerManager.h"
#include "Engine/World.h"

//----------------------------------------------------------------------//
// ULaunchEntityProcessor
//----------------------------------------------------------------------//

void ULaunchEntityProcessor::ConfigureQueries()
{
EntityQuery.AddRequirement<FLaunchEntityFragment>(EMassFragmentAccess::ReadWrite);
EntityQuery.AddRequirement<FMassMoveTargetFragment>(EMassFragmentAccess::ReadWrite);
EntityQuery.AddRequirement<FTransformFragment>(EMassFragmentAccess::ReadOnly);
EntityQuery.AddTagRequirement<FInitLaunchFragment>(EMassFragmentPresence::None);
}

void ULaunchEntityProcessor::Initialize(UObject& Owner)
{
Super::Initialize(Owner);
SignalSubsystem = UWorld::GetSubsystem<UMassSignalSubsystem>(Owner.GetWorld());
FormationSubsystem = UWorld::GetSubsystem<URTSFormationSubsystem>(Owner.GetWorld());
SubscribeToSignal(*SignalSubsystem, LaunchEntity);
}

void ULaunchEntityProcessor::SignalEntities(FMassEntityManager& EntityManager,
FMassExecutionContext& Context, FMassSignalNameLookup& EntitySignals)
{
EntityQuery.ParallelForEachEntityChunk(EntityManager, Context, [this, &EntityManager](FMassExecutionContext& Context)
{
TArrayView<FLaunchEntityFragment> LaunchEntityFragments = Context.GetMutableFragmentView<FLaunchEntityFragment>();
TArrayView<FMassMoveTargetFragment> MoveTargetFragments = Context.GetMutableFragmentView<FMassMoveTargetFragment>();
TConstArrayView<FTransformFragment> TransformFragments = Context.GetFragmentView<FTransformFragment>();

for (int32 EntityIndex = 0; EntityIndex < Context.GetNumEntities(); ++EntityIndex)
{
const FLaunchEntityFragment& LaunchEntityFragment = LaunchEntityFragments[EntityIndex];
FMassMoveTargetFragment& MoveTargetFragment = MoveTargetFragments[EntityIndex];
const FTransformFragment& TransformFragment = TransformFragments[EntityIndex];

MoveTargetFragment.CreateNewAction(EMassMovementAction::Move, *GetWorld());
MoveTargetFragment.Center = TransformFragment.GetTransform().GetLocation()+(TransformFragment.GetTransform().GetTranslation()-LaunchEntityFragment.Origin).GetSafeNormal()*LaunchEntityFragment.Magnitude;
MoveTargetFragment.Center.Z = 0.f;
MoveTargetFragment.Forward = (TransformFragment.GetTransform().GetTranslation()-LaunchEntityFragment.Origin).GetSafeNormal();
MoveTargetFragment.DistanceToGoal = (TransformFragment.GetTransform().GetTranslation()-LaunchEntityFragment.Origin).Length();
//DrawDebugPoint(GetWorld(), MoveTargetFragment.Center+(FVector::UpVector*200.f), 40.f, FColor::Green, false, 10.f);
//UE_LOG(LogTemp, Error, TEXT("MoveTarget: "), *MoveTargetFragment.Center.ToString());
Context.Defer().AddTag<FInitLaunchFragment>(Context.GetEntity(EntityIndex));
}
});
}

//----------------------------------------------------------------------//
// UMoveForceProcessor
//----------------------------------------------------------------------//

void UMoveForceProcessor::ConfigureQueries()
{
EntityQuery.AddRequirement<FLaunchEntityFragment>(EMassFragmentAccess::ReadOnly);
EntityQuery.AddRequirement<FMassForceFragment>(EMassFragmentAccess::ReadWrite);
EntityQuery.AddRequirement<FTransformFragment>(EMassFragmentAccess::ReadWrite);
EntityQuery.AddRequirement<FMassMoveTargetFragment>(EMassFragmentAccess::ReadWrite);
EntityQuery.AddTagRequirement<FInitLaunchFragment>(EMassFragmentPresence::All);

}

void UMoveForceProcessor::Execute(FMassEntityManager& EntityManager, FMassExecutionContext& Context)
{
EntityQuery.ParallelForEachEntityChunk(EntityManager, Context, [this, &EntityManager](FMassExecutionContext& Context)
{
TConstArrayView<FLaunchEntityFragment> LaunchEntityFragments = Context.GetFragmentView<FLaunchEntityFragment>();
TArrayView<FMassMoveTargetFragment> MoveTargetFragments = Context.GetMutableFragmentView<FMassMoveTargetFragment>();
TArrayView<FMassForceFragment> ForceFragments = Context.GetMutableFragmentView<FMassForceFragment>();
TArrayView<FTransformFragment> TransformFragments = Context.GetMutableFragmentView<FTransformFragment>();

for (int32 EntityIndex = 0; EntityIndex < Context.GetNumEntities(); ++EntityIndex)
{
const FLaunchEntityFragment& LaunchEntityFragment = LaunchEntityFragments[EntityIndex];
FMassMoveTargetFragment& MoveTargetFragment = MoveTargetFragments[EntityIndex];
FMassForceFragment& ForceFragment = ForceFragments[EntityIndex];
FTransformFragment& TransformFragment = TransformFragments[EntityIndex];

MoveTargetFragment.DistanceToGoal = (TransformFragment.GetTransform().GetTranslation()-MoveTargetFragment.Center).Length();

if(MoveTargetFragment.DistanceToGoal < 50.f)
{
if (MoveTargetFragment.GetCurrentAction() == EMassMovementAction::Move)
{
//Context.Defer().RemoveFragment<FLaunchEntityFragment>(Context.GetEntity(EntityIndex));
//Context.Defer().RemoveTag<FInitLaunchFragment>(Context.GetEntity(EntityIndex));
Context.Defer().DestroyEntity(Context.GetEntity(EntityIndex));
MoveTargetFragment.CreateNewAction(EMassMovementAction::Stand, *GetWorld());
}
}
else
{
DrawDebugSphere(GetWorld(), TransformFragment.GetTransform().GetLocation(), 40.f, 5, FColor::Red);
}
}
});
}
Loading