Skip to content

Commit 77b4a4d

Browse files
authored
feat: ecsact package subsystems (#15)
1 parent e454e94 commit 77b4a4d

17 files changed

+1181
-69
lines changed

Source/Ecsact/Ecsact.Build.cs

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,6 @@ public Ecsact(ReadOnlyTargetRules Target) : base(Target) {
2929
"Engine",
3030
"Slate",
3131
"SlateCore",
32-
"Kismet",
3332
});
3433

3534
DynamicallyLoadedModuleNames.AddRange(new string[] {
@@ -80,14 +79,14 @@ public Ecsact(ReadOnlyTargetRules Target) : base(Target) {
8079
"--plugin=cpp_systems_source"
8180
};
8281

83-
// if(!File.Exists(EcsactUnrealCodegenPluginPath)) {
84-
// Console.WriteLine(
85-
// "warning: EcsactUnrealCodegenPlugin was not built. It should have "
86-
// + "been shipped with the Ecsact Unreal integration plugin."
87-
// );
88-
// } else {
89-
// CodegenArgs.Add($"--plugin={EcsactUnrealCodegenPluginPath}");
90-
// }
82+
if(!File.Exists(EcsactUnrealCodegenPluginPath)) {
83+
Console.WriteLine(
84+
"warning: EcsactUnrealCodegenPlugin was not built. It should have " +
85+
"been shipped with the Ecsact Unreal integration plugin."
86+
);
87+
} else {
88+
CodegenArgs.Add($"--plugin={EcsactUnrealCodegenPluginPath}");
89+
}
9190

9291
CodegenArgs.AddRange(EcsactSources);
9392
ExecEcsactCli(CodegenArgs);

Source/Ecsact/Public/EcsactUnreal/Blueprint/EcsactAsyncConnectBlueprintAction.cpp

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,20 @@ auto UEcsactAsyncConnectBlueprintAction::Activate() -> void {
2323
TEXT("Cannot use Ecsact async blueprint api with runner that does not "
2424
"implement IEcsactAsyncRunnerEvents")
2525
);
26+
OnError.Broadcast(EAsyncConnectError::AsyncRunnerEventsUnavailable);
27+
OnDone.Broadcast({});
2628
return;
2729
}
2830

2931
auto req_id = ecsact_async_connect(Utf8ConnectionString.c_str());
32+
UE_LOG(Ecsact, Warning, TEXT("async connect request id=%i"), req_id);
33+
34+
if(req_id == ECSACT_INVALID_ID(async_request)) {
35+
UE_LOG(Ecsact, Error, TEXT("Invalid Request ID"));
36+
OnError.Broadcast(EAsyncConnectError::InvalidRequestId);
37+
OnDone.Broadcast({});
38+
return;
39+
}
3040

3141
async_events->OnRequestDone(
3242
req_id,
@@ -46,6 +56,7 @@ auto UEcsactAsyncConnectBlueprintAction::Activate() -> void {
4656
}
4757

4858
auto UEcsactAsyncConnectBlueprintAction::OnRequestDone() -> void {
59+
UE_LOG(Ecsact, Error, TEXT("OnRequestDone??"));
4960
if(!bConnectFailed) {
5061
OnSuccess.Broadcast({});
5162
}
@@ -55,12 +66,13 @@ auto UEcsactAsyncConnectBlueprintAction::OnRequestDone() -> void {
5566
auto UEcsactAsyncConnectBlueprintAction::OnRequestError( //
5667
ecsact_async_error Error
5768
) -> void {
69+
UE_LOG(Ecsact, Error, TEXT("OnRequestError??"));
5870
switch(Error) {
5971
case ECSACT_ASYNC_ERR_PERMISSION_DENIED:
6072
OnError.Broadcast(EAsyncConnectError::PermissionDenied);
6173
break;
6274
case ECSACT_ASYNC_INVALID_CONNECTION_STRING:
63-
OnError.Broadcast(EAsyncConnectError::PermissionDenied);
75+
OnError.Broadcast(EAsyncConnectError::InvalidConnectionString);
6476
break;
6577
}
6678

Source/Ecsact/Public/EcsactUnreal/Blueprint/EcsactAsyncConnectBlueprintAction.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
UENUM()
99
enum class EAsyncConnectError : uint8 {
1010
NoError,
11+
AsyncRunnerEventsUnavailable,
12+
InvalidRequestId,
1113
PermissionDenied,
1214
InvalidConnectionString,
1315
};
@@ -54,7 +56,7 @@ class ECSACT_API UEcsactAsyncConnectBlueprintAction
5456
FAsyncConnectDoneCallback OnDone;
5557

5658
/**
57-
* Async request is done and no errors occured.
59+
* Async request is done and no errors occurred.
5860
*/
5961
UPROPERTY(BlueprintAssignable)
6062
FAsyncConnectDoneCallback OnSuccess;

Source/Ecsact/Public/EcsactUnreal/Ecsact.cpp

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,12 @@ FOR_EACH_ECSACT_API_FN(INIT_ECSACT_API_FN, UNUSED_PARAM);
1818
FEcsactModule* FEcsactModule::Self = nullptr;
1919

2020
auto FEcsactModule::Get() -> FEcsactModule& {
21-
check(Self != nullptr);
22-
return *Self;
21+
if(GIsEditor) {
22+
return FModuleManager::Get().GetModuleChecked<FEcsactModule>("Ecsact");
23+
} else {
24+
check(Self != nullptr);
25+
return *Self;
26+
}
2327
}
2428

2529
auto FEcsactModule::Abort() -> void {
@@ -84,13 +88,14 @@ auto FEcsactModule::UnloadEcsactRuntime() -> void {
8488
}
8589

8690
auto FEcsactModule::StartupModule() -> void {
91+
UE_LOG(Ecsact, Warning, TEXT("Ecsact Startup Module"));
8792
Self = this;
8893
if(!GIsEditor) {
8994
LoadEcsactRuntime();
9095
}
9196
#if WITH_EDITOR
9297
FEditorDelegates::PreBeginPIE.AddRaw(this, &FEcsactModule::OnPreBeginPIE);
93-
FEditorDelegates::EndPIE.AddRaw(this, &FEcsactModule::OnEndPIE);
98+
FEditorDelegates::EndPIE.AddRaw(this, &FEcsactModule::OnPrePIEEnded);
9499
#endif
95100
}
96101

@@ -103,14 +108,15 @@ auto FEcsactModule::ShutdownModule() -> void {
103108
FEditorDelegates::PreBeginPIE.RemoveAll(this);
104109
FEditorDelegates::EndPIE.RemoveAll(this);
105110
#endif
111+
UE_LOG(Ecsact, Warning, TEXT("Ecsact Shutdown Module"));
106112
Self = nullptr;
107113
}
108114

109115
auto FEcsactModule::OnPreBeginPIE(bool _) -> void {
110116
LoadEcsactRuntime();
111117
}
112118

113-
auto FEcsactModule::OnEndPIE(bool _) -> void {
119+
auto FEcsactModule::OnPrePIEEnded(bool _) -> void {
114120
UnloadEcsactRuntime();
115121
}
116122

@@ -149,17 +155,26 @@ auto FEcsactModule::StartRunner() -> void {
149155
UE_LOG(
150156
Ecsact,
151157
Log,
152-
TEXT("Using ecsact runner: %s"),
158+
TEXT("Starting ecsact runner: %s"),
153159
*Runner->GetClass()->GetName()
154160
);
155161
Runner->AddToRoot();
162+
Runner->Start();
156163
}
157164
}
158165

159166
auto FEcsactModule::StopRunner() -> void {
160167
if(Runner != nullptr) {
168+
UE_LOG(
169+
Ecsact,
170+
Log,
171+
TEXT("Stopping ecsact runner: %s"),
172+
*Runner->GetClass()->GetName()
173+
);
174+
Runner->Stop();
161175
Runner->RemoveFromRoot();
162-
Runner = nullptr;
176+
Runner->MarkAsGarbage();
177+
Runner.Reset();
163178
}
164179
}
165180

Source/Ecsact/Public/EcsactUnreal/Ecsact.h

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,21 +2,22 @@
22

33
#include "CoreMinimal.h"
44
#include "Modules/ModuleManager.h"
5+
#include "UObject/WeakObjectPtr.h"
56

67
DECLARE_LOG_CATEGORY_EXTERN(Ecsact, Log, All);
78

89
class FEcsactModule : public IModuleInterface {
910
friend class EcsactUnrealExecution;
1011

11-
static FEcsactModule* Self;
12-
void* EcsactRuntimeHandle;
13-
class UEcsactRunner* Runner;
12+
static FEcsactModule* Self;
13+
void* EcsactRuntimeHandle;
14+
TWeakObjectPtr<class UEcsactRunner> Runner;
1415

1516
auto LoadEcsactRuntime() -> void;
1617
auto UnloadEcsactRuntime() -> void;
1718
auto Abort() -> void;
1819
auto OnPreBeginPIE(bool bIsSimulating) -> void;
19-
auto OnEndPIE(const bool bIsSimulating) -> void;
20+
auto OnPrePIEEnded(const bool bIsSimulating) -> void;
2021

2122
auto StartRunner() -> void;
2223
auto StopRunner() -> void;

Source/Ecsact/Public/EcsactUnreal/EcsactAsyncRunner.cpp

Lines changed: 67 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -28,10 +28,27 @@ auto UEcsactAsyncRunner::OnAsyncErrorRaw(
2828

2929
for(auto req_id : request_ids) {
3030
auto cbs = self->RequestErrorCallbacks.Find(req_id);
31-
if(cbs) {
31+
32+
UE_LOG(Ecsact, Warning, TEXT("async request error id=%i"), req_id);
33+
34+
if(cbs && !cbs->IsEmpty()) {
3235
for(auto& cb : *cbs) {
33-
cb.ExecuteIfBound(async_err);
36+
if(!cb.ExecuteIfBound(async_err)) {
37+
UE_LOG(
38+
Ecsact,
39+
Warning,
40+
TEXT("Unbound async error callback for request %i"),
41+
req_id
42+
);
43+
}
3444
}
45+
} else {
46+
UE_LOG(
47+
Ecsact,
48+
Warning,
49+
TEXT("No async error callbacks for request %i"),
50+
req_id
51+
);
3552
}
3653
}
3754
}
@@ -54,27 +71,46 @@ auto UEcsactAsyncRunner::OnAsyncRequestDoneRaw(
5471

5572
for(auto req_id : request_ids) {
5673
auto cbs = self->RequestDoneCallbacks.Find(req_id);
57-
if(cbs) {
74+
75+
UE_LOG(Ecsact, Warning, TEXT("async request done id=%i"), req_id);
76+
77+
if(cbs && !cbs->IsEmpty()) {
5878
for(auto& cb : *cbs) {
59-
cb.ExecuteIfBound();
79+
if(!cb.ExecuteIfBound()) {
80+
UE_LOG(
81+
Ecsact,
82+
Warning,
83+
TEXT("Unbound async done callback for request %i (self=%i)"),
84+
req_id,
85+
(intptr_t)self
86+
);
87+
}
6088
}
6189

6290
cbs->Empty();
91+
} else {
92+
UE_LOG(
93+
Ecsact,
94+
Warning,
95+
TEXT("No async done callbacks for request %i (self=%i)"),
96+
req_id,
97+
(intptr_t)self
98+
);
6399
}
64100
}
65101
}
66102

67103
auto UEcsactAsyncRunner::Tick(float DeltaTime) -> void {
104+
if(IsStopped()) {
105+
return;
106+
}
107+
68108
EnqueueExecutionOptions();
69109

70110
if(ecsact_async_flush_events == nullptr) {
71111
UE_LOG(Ecsact, Error, TEXT("ecsact_async_flush_events is unavailable"));
72112
} else {
73-
ecsact_execution_events_collector* evc_c = nullptr;
74-
if(EventsCollector != nullptr) {
75-
evc_c = EventsCollector->GetCEVC();
76-
}
77-
ecsact_async_flush_events(evc_c, &async_evc);
113+
ecsact_async_flush_events(GetEventsCollector(), &async_evc);
78114
}
79115
}
80116

@@ -92,7 +128,14 @@ auto UEcsactAsyncRunner::EnqueueExecutionOptions() -> void {
92128
}
93129

94130
if(ExecutionOptions->IsNotEmpty()) {
95-
ecsact_async_enqueue_execution_options(*ExecutionOptions->GetCPtr());
131+
auto req_id =
132+
ecsact_async_enqueue_execution_options(*ExecutionOptions->GetCPtr());
133+
UE_LOG(
134+
Ecsact,
135+
Warning,
136+
TEXT("Actually enqueueing some options! (req_id=%i)"),
137+
(int)req_id
138+
);
96139
ExecutionOptions->Clear();
97140
}
98141
}
@@ -109,6 +152,13 @@ auto UEcsactAsyncRunner::OnRequestDone(
109152
FAsyncRequestDoneCallback Callback
110153
) -> void {
111154
check(RequestId != ECSACT_INVALID_ID(async_request));
155+
UE_LOG(
156+
Ecsact,
157+
Error,
158+
TEXT("Adding on request done callback (req_id=%i self=%i)"),
159+
RequestId,
160+
(intptr_t)this
161+
);
112162

113163
RequestDoneCallbacks.FindOrAdd(RequestId).Add(Callback);
114164
}
@@ -118,6 +168,13 @@ auto UEcsactAsyncRunner::OnRequestError(
118168
FAsyncRequestErrorCallback Callback
119169
) -> void {
120170
check(RequestId != ECSACT_INVALID_ID(async_request));
171+
UE_LOG(
172+
Ecsact,
173+
Error,
174+
TEXT("Adding on request error callback (req_id=%i self=%i)"),
175+
RequestId,
176+
(intptr_t)this
177+
);
121178

122179
RequestErrorCallbacks.FindOrAdd(RequestId).Add(Callback);
123180
}

Source/Ecsact/Public/EcsactUnreal/EcsactExecution.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,6 @@ auto EcsactUnrealExecution::DeltaTime() -> float {
77
return DeltaTime_;
88
}
99

10-
auto EcsactUnrealExecution::Runner() -> class UEcsactRunner* {
10+
auto EcsactUnrealExecution::Runner() -> TWeakObjectPtr<class UEcsactRunner> {
1111
return FEcsactModule::Get().Runner;
1212
}

Source/Ecsact/Public/EcsactUnreal/EcsactExecution.h

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
#pragma once
22

3-
class EcsactUnrealExecution {
3+
#include "EcsactUnreal/Ecsact.h"
4+
#include "UObject/WeakObjectPtrTemplates.h"
5+
6+
class ECSACT_API EcsactUnrealExecution {
47
friend class UEcsactSyncRunner;
58
friend class UEcsactAsyncRunner;
69
static float DeltaTime_;
@@ -18,5 +21,5 @@ class EcsactUnrealExecution {
1821
/**
1922
*
2023
*/
21-
static auto Runner() -> class UEcsactRunner*;
24+
static auto Runner() -> TWeakObjectPtr<class UEcsactRunner>;
2225
};

0 commit comments

Comments
 (0)