// Fill out your copyright notice in the Description page of Project Settings. #include "cppGI.h" #include "Kismet/GameplayStatics.h" #include "Misc/paths.h" #include "Engine/levelstreamingdynamic.h" #include "cppFuncLibrary.h" /*for working tarray::Contains*/ bool operator==(const Fcppcoords& c1, const Fcppcoords& c2) { return c1.flat == c2.flat && c1.floor == c2.floor && c1.house == c2.house && c1.section == c2.section && c1.type == c2.type && c1.zone == c2.zone; } /*for working tarray::Contains*/ bool operator==(const FcppLevelStruct& c1, const FcppLevelStruct& c2) { return c1.anotherLvl == c2.anotherLvl && c1.coords == c2.coords && c1.dontUnload == c2.dontUnload && c1.path == c2.path && c1.uniqName == c2.uniqName && c1.Z == c2.Z; } TArray UcppGI::cppLvlManage(UObject* WorldContextObject, Fcppcoords currentCoords, uint8 currentState) { TArray outStruct; bool loadthis; /*for 3Dtour only*/ if(currentState==11) { auto temp = Fcppcoords(); temp.house = -2; temp.section = -2; temp.floor = 1; cppLoadList.AddUnique(temp); } cppLoadList.AddUnique(currentCoords); for (const auto& lvl : cppLevels) { loadthis = 0; if (cppBlackList.Contains(lvl)); else if (cppWhiteList.Contains(lvl)) loadthis = true; else { bool ceq[7]; for (const auto& crd : cppLoadList) // here is filter code { cppCoordsEq(crd, lvl.coords, true, false, ceq[0], ceq[1], ceq[2], ceq[3], ceq[4], ceq[5], ceq[6]); if (ceq[3] && ceq[4] && ceq[5] && !lvl.uniqName.ToString().EndsWith(L"refl")) loadthis = true; //reflections setup separately, load all on floor if (ceq[6] && lvl.uniqName.ToString().EndsWith(L"refl")) loadthis = true; //if (ceq[6]) loadthis = true; //classic load with parallax } } if (loadthis) { if (cppCreatedList.Contains(lvl.uniqName)) { /*if already created level*/ ULevelStreaming* outlvl_ = nullptr; if ((outlvl_ = UGameplayStatics::GetStreamingLevel(WorldContextObject, lvl.uniqName)) != nullptr) { outlvl_->SetShouldBeLoaded(true); outlvl_->SetShouldBeVisible(true); cpploadedList.Add(lvl.uniqName); outStruct.Add(outlvl_); } } else { /*load new level instance*/ bool b; if (ULevelStreamingDynamic* newlvl = ULevelStreamingDynamic::LoadLevelInstance(WorldContextObject, lvl.path, FVector(0, 0, lvl.Z), FRotator(0), b, lvl.uniqName.ToString())) { newlvl->SetPriority(lvl.coords.flat == -1 ? 1 : 0); newlvl->bShouldBlockOnLoad = lvl.dontUnload; cppCreatedList.Add(lvl.uniqName); cpploadedList.Add(lvl.uniqName); outStruct.Add(newlvl); } } } else if (cppCreatedList.Contains(lvl.uniqName)) { ULevelStreaming* outlvl_ = nullptr; if ((outlvl_ = UGameplayStatics::GetStreamingLevel(WorldContextObject, lvl.uniqName)) != nullptr) { //if (lvl.path.EndsWith("refl")) outlvl_->bShouldBlockOnUnload = true; outlvl_->SetShouldBeLoaded(lvl.dontUnload); outlvl_->SetShouldBeVisible(false); cpploadedList.Remove(lvl.uniqName); outStruct.Add(outlvl_); } } } cppWhiteList.Empty(); cppBlackList.Empty(); cppLoadList.Empty(); return outStruct; } void UcppGI::cppCoordsEq(Fcppcoords coords, Fcppcoords coords1, bool relevantMinus2, bool fastEq, bool& flat_, bool& type_, bool& zone_, bool& house_, bool& section_, bool& floor_, bool& fullEq) { bool* outLvl[6] = { &flat_, &type_, &zone_, &house_, §ion_, &floor_ }; int32 c1[6] = { coords.flat,coords.type, coords.zone, coords.house, coords.section, coords.floor }; int32 c2[6] = { coords1.flat,coords1.type, coords1.zone, coords1.house, coords1.section, coords1.floor }; int32 mins[6] = { 0,0,1,1,1,0 }; if (fastEq) { for (int8 i = 0; i < 6; i++) { *outLvl[i] = (c1[i] == c2[i]); } } else { for (int8 i = 0; i < 6; i++) { *outLvl[i] = ((c1[i] < mins[i]) && (c2[i] < mins[i])) || (c1[i] == c2[i]) || ((c1[i] == -2) && relevantMinus2) || ((c2[i] == -2) && relevantMinus2); } } fullEq = true; for (const auto var : outLvl) { if (!*var)fullEq = false; } }