// Fill out your copyright notice in the Description page of Project Settings. #include "DTFluxCoreSubsystem.h" #include "DTFluxCoreSubsystemModule.h" #include "DTFluxGeneralSettings.h" #include "FileHelpers.h" #include "Assets/DTFluxModelAsset.h" #include "Subsystems/DTFluxNetworkSubsystem.h" #include "UObject/SavePackage.h" void UDTFluxCoreSubsystem::Initialize(FSubsystemCollectionBase& Collection) { Super::Initialize(Collection); UE_LOG(logDTFluxCoreSubsystem, Log, TEXT("[UDTFluxCoreSubsystem] Initializing...")); if(!DataStorage) { const UDTFluxGeneralSettings* GeneralSettings = GetDefault(); TSoftObjectPtr ModelAsset = GeneralSettings->ModelAsset; DataStorage = ModelAsset.LoadSynchronous(); if(!DataStorage) { UE_LOG(logDTFluxCore, Error, TEXT("DataStorage Not Valid")); } } //TODO REMOVE This as it's only for testing purpose NetworkSubsystem = GEngine->GetEngineSubsystem(); if(NetworkSubsystem->WsStatus != EDTFluxConnectionStatus::Connected) { RegisterDelegates(); } } void UDTFluxCoreSubsystem::Deinitialize() { Super::Deinitialize(); } void UDTFluxCoreSubsystem::SaveDataStorage() { if(!DataStorage->MarkPackageDirty()) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Unable to make package dirty !!!")) } if(DataStorage) { UEditorLoadingAndSavingUtils::SavePackages({DataStorage->GetPackage()}, true); } } void UDTFluxCoreSubsystem::RegisterDelegates() { if(NetworkSubsystem) { NetworkSubsystem->OnReceivedRaceData().BindUFunction(this, "ProcessRaceData"); NetworkSubsystem->OnReceivedTeamList().BindUFunction(this, "ProcessTeamList"); NetworkSubsystem->OnReceivedContestRanking().BindUFunction(this, "ProcessContestRanking"); NetworkSubsystem->OnReceivedStageRanking().BindUFunction(this, "ProcessStageRanking"); NetworkSubsystem->OnReceivedSplitRanking().BindUFunction(this, "ProcessSplitRanking"); NetworkSubsystem->OnReceivedTeamUpdate().BindUFunction(this, "ProcessTeamList"); NetworkSubsystem->OnReceivedTeamStatusUpdate().BindUFunction(this, "ProcessTeamStatusUpdate"); NetworkSubsystem->OnReceivedTeamUpdate().BindUFunction(this, "ProcessTeamUpdate"); NetworkSubsystem->OnReceivedSplitSensor().BindUFunction(this, "ProcessSplitSensor"); } } void UDTFluxCoreSubsystem::ProcessRaceData(const FDTFluxRaceData& RaceDataDefinition) { if( RaceDataDefinition.Datas.Num() > 0 ) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Receiving RaceDataDefinition [%s]"), *RaceDataDefinition.Datas[0].Name); if(DataStorage != nullptr) { UE_LOG(logDTFluxCoreSubsystem, Error, TEXT("DataStorage Name %s"), *DataStorage->EventName); for(auto Contest : RaceDataDefinition.Datas) { DataStorage->AddContest(Contest); } } else { UE_LOG(logDTFluxCoreSubsystem, Error, TEXT("DataStorage is null")); } SaveDataStorage(); return; } UE_LOG(logDTFluxCoreSubsystem, Error, TEXT("RaceDataDefinition is empty !!!")); } void UDTFluxCoreSubsystem::ProcessTeamList(const FDTFluxTeamListDefinition& TeamListDefinition) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Received TeamList with %i Items"), TeamListDefinition.Participants.Num()); for(const auto& Participant : TeamListDefinition.Participants) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Add Participant %i in %i ContestId"), Participant.Bib, Participant.ContestId ); DataStorage->AddParticipant(Participant, Participant.ContestId); } } void UDTFluxCoreSubsystem::ProcessContestRanking(const FDTFluxContestRankings& ContestRankings) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Received ContestRankings with %i Items"), ContestRankings.Rankings.Num()); FDTFluxContestRankings NewContestRankings = ContestRankings; NewContestRankings.SetName( DataStorage->GetContestNameForId(ContestRankings.ContestId)); DataStorage->AddContestRanking(NewContestRankings); UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("ContestRankings added for Contest %s"), *NewContestRankings.ContestName); SaveDataStorage(); } void UDTFluxCoreSubsystem::ProcessStageRanking(const FDTFluxStageRankings& StageRankings) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Received StageRankings with %i Items"), StageRankings.Rankings.Num()); DataStorage->UpdateOrCreateStageRanking(StageRankings); SaveDataStorage(); } void UDTFluxCoreSubsystem::ProcessSplitRanking(const FDTFluxSplitRankings& SplitRankings) { UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Received SplitRanking with %i Items"), SplitRankings.Rankings.Num()); DataStorage->UpdateOrCreateSplitRanking(SplitRankings); SaveDataStorage(); } void UDTFluxCoreSubsystem::ProcessTeamStatusUpdate(const FDTFluxTeamStatusUpdate& NewParticipantStatus) { DataStorage->UpdateParticipantStatus(NewParticipantStatus); } void UDTFluxCoreSubsystem::ProcessTeamUpdate(const FDTFluxParticipant& Participant) { DataStorage->UpdateParticipant(Participant); } void UDTFluxCoreSubsystem::ProcessSplitSensor(const FDTFluxSplitSensorInfo& SplitSensorInfo) { FDTFluxContest Contest; FDTFluxStageKey StageKey(SplitSensorInfo.ContestId, SplitSensorInfo.StageId); DataStorage->GetContestById(SplitSensorInfo.ContestId, Contest); UE_LOG(logDTFluxCoreSubsystem, Log, TEXT("%s %s Split %i Sensor for Participant [Bib] %i "), *Contest.Name, *Contest.Stages[SplitSensorInfo.StageId].Name, SplitSensorInfo.SplitId , SplitSensorInfo.Bib); } void UDTFluxCoreSubsystem::SendRequest(const FString& Message) { if(NetworkSubsystem) { NetworkSubsystem->SendMessage(Message); } } void UDTFluxCoreSubsystem::SendTeamListRequest() { if (NetworkSubsystem) { NetworkSubsystem->SendRequest(EDTFluxRequestType::TeamList); } } void UDTFluxCoreSubsystem::SendRaceDataRequest() { if (NetworkSubsystem) { NetworkSubsystem->SendRequest(EDTFluxRequestType::RaceData); } } void UDTFluxCoreSubsystem::SendContestRankingRequest(int InContestId) { if (NetworkSubsystem) { NetworkSubsystem->SendRequest(EDTFluxRequestType::ContestRanking, InContestId); } } void UDTFluxCoreSubsystem::SendStageRankingRequest(int InContestId, int InStageId, bool bShouldIncludeSplitRanking) { // TODO Implement this } void UDTFluxCoreSubsystem::RequestAllStageRankingOfContest(int InContestId, int InStageId, bool bShouldIncludeSplitRanking) { // TODO Implement this } void UDTFluxCoreSubsystem::SendSplitRankingRequest(int InContestId, int InStageId, int InSplitId) { // TODO Implement this } void UDTFluxCoreSubsystem::RequestAllSplitRankingOfContest(int InContestId, int InStageId) { // TODO Implement this } FDTFluxStageRankings UDTFluxCoreSubsystem::GetStageRankings(FDTFluxStageKey StageKey) { if(DataStorage->StageRankings.Contains(StageKey)) { return DataStorage->StageRankings[StageKey]; } UE_LOG(logDTFluxCoreSubsystem, Warning, TEXT("Cannot find StageRankings for key [%s]"), *StageKey.GetDisplayName()); return FDTFluxStageRankings(); } void UDTFluxCoreSubsystem::RequestAllSplitRankingOfStage(int InContestId, int InStageId, int InSplitId) { // TODO Implement this } void UDTFluxCoreSubsystem::RefreshStorage() { // TODO Implement this } TArray UDTFluxCoreSubsystem::GetCurrentContestsId() { return GetContestsIdForTime(FDateTime::Now()); } TArray UDTFluxCoreSubsystem::GetCurrentContests() { return GetContestsForTime(FDateTime::Now()); } TArray UDTFluxCoreSubsystem::GetContestsIdForTime(const FDateTime Time) { TArray Contests; for(const auto& Pair : DataStorage->Contests) { FDTFluxContest Contest = Pair.Value; int ContestId = Contest.ContestId; if(Contest.Date < Time && Contest.EndTime > Time) { Contests.Add(ContestId); } } return Contests; } TArray UDTFluxCoreSubsystem::GetContestsForTime(const FDateTime Time) { TArray Contests; for(const auto& Pair : DataStorage->Contests) { FDTFluxContest Contest = Pair.Value; int ContestId = Contest.ContestId; if(Contest.Date < Time && Contest.EndTime > Time) { Contests.Add(Contest); } } return Contests; }