Skip to content

Commit

Permalink
Small corrections and fix map full loading percentage
Browse files Browse the repository at this point in the history
  • Loading branch information
tornac1234 committed Jan 8, 2025
1 parent c529216 commit eb02f01
Show file tree
Hide file tree
Showing 4 changed files with 39 additions and 30 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
using AssetsTools.NET.Extra;
using Newtonsoft.Json;
using NitroxModel.DataStructures.Unity;
using NitroxModel.Helper;
using NitroxServer.GameLogic.Entities;
using NitroxServer.Resources;
using NitroxServer_Subnautica.Resources.Parsers.Helper;
Expand Down Expand Up @@ -59,11 +60,8 @@ public Dictionary<string, PrefabPlaceholdersGroupAsset> ParseFile()
// Loading all prefabs by their classId and file paths (first the path to the prefab then the dependencies)
LoadAddressableCatalog(prefabDatabase);

string nitroxCachePath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "Nitrox", "Cache");
if (!Directory.Exists(nitroxCachePath))
{
Directory.CreateDirectory(nitroxCachePath);
}
string nitroxCachePath = Path.Combine(NitroxUser.AppDataPath, "Cache");
Directory.CreateDirectory(nitroxCachePath);

Dictionary<string, PrefabPlaceholdersGroupAsset> prefabPlaceholdersGroupPaths = null;
string prefabPlaceholdersGroupAssetCachePath = Path.Combine(nitroxCachePath, "PrefabPlaceholdersGroupAssetsCache.json");
Expand Down Expand Up @@ -93,24 +91,25 @@ public Dictionary<string, PrefabPlaceholdersGroupAsset> ParseFile()
return prefabPlaceholdersGroupPaths;
}

private Dictionary<string, PrefabPlaceholdersGroupAsset> MakeAndSerializeCache(string path)
private Dictionary<string, PrefabPlaceholdersGroupAsset> MakeAndSerializeCache(string filePath)
{
ConcurrentDictionary<string, string[]> prefabPlaceholdersGroupPaths = GetAllPrefabPlaceholdersGroupsFast();
Dictionary<string, PrefabPlaceholdersGroupAsset> prefabPlaceholdersGroupAssets = new(GetPrefabPlaceholderGroupAssetsByGroupClassId(prefabPlaceholdersGroupPaths));
using StreamWriter stream = File.CreateText(path);
using StreamWriter stream = File.CreateText(filePath);
serializer.Serialize(stream, new Cache(prefabPlaceholdersGroupAssets, RandomPossibilitiesByClassId));

return prefabPlaceholdersGroupAssets;
}

private Cache? DeserializeCache(string path)
private Cache? DeserializeCache(string filePath)
{
try
{
using StreamReader reader = File.OpenText(path);
using StreamReader reader = File.OpenText(filePath);

return (Cache)serializer.Deserialize(reader, typeof(Cache));
} catch (Exception exception)
}
catch (Exception exception)
{
Log.Error(exception, "An error occurred while deserializing the game Cache. Re-creating it.");
}
Expand Down Expand Up @@ -143,7 +142,7 @@ private void LoadAddressableCatalog(Dictionary<string, string> prefabDatabase)
{
ContentCatalogData ccd = AddressablesJsonParser.FromString(File.ReadAllText(Path.Combine(aaRootPath, "catalog.json")));
Dictionary<string, string> classIdByPath = prefabDatabase.ToDictionary(m => m.Value, m => m.Key);

foreach (KeyValuePair<object, List<ResourceLocation>> entry in ccd.Resources)
{
if (entry.Key is string primaryKey && primaryKey.Length == 32 &&
Expand Down Expand Up @@ -230,19 +229,25 @@ private ConcurrentDictionary<string, string[]> GetAllPrefabPlaceholdersGroupsFas
AssetsBundleManager bundleManagerInst = am.Clone();
AssetsFileInstance assetFileInstance = bundleManagerInst.LoadBundleWithDependencies(assetPaths);

if (assetFileInstance.file.Metadata.TypeTreeTypes.Any(typeTree => typeTree.TypeId == (int)AssetClassID.MonoBehaviour && typeTree.TypeHash.data.SequenceEqual(prefabPlaceholdersGroupHash)))
foreach (TypeTreeType typeTreeType in assetFileInstance.file.Metadata.TypeTreeTypes)
{
prefabPlaceholdersGroupPaths.TryAdd(keyValuePair.Key, keyValuePair.Value);
}
else if (assetFileInstance.file.Metadata.TypeTreeTypes.Any(typeTree => typeTree.TypeId == (int)AssetClassID.MonoBehaviour && typeTree.TypeHash.data.SequenceEqual(spawnRandomHash)))
{
AssetsFileInstance assetFileInst = am.LoadBundleWithDependencies(assetPaths);

GetPrefabGameObjectInfoFromBundle(am, assetFileInst, out AssetFileInfo prefabGameObjectInfo);
if (typeTreeType.TypeId != (int)AssetClassID.MonoBehaviour)
{
continue;
}

AssetFileInfo spawnRandomInfo = am.GetMonoBehaviourFromGameObject(assetFileInst, prefabGameObjectInfo, "SpawnRandom");
if (spawnRandomInfo != null)
if (typeTreeType.TypeHash.data.SequenceEqual(prefabPlaceholdersGroupHash))
{
prefabPlaceholdersGroupPaths.TryAdd(keyValuePair.Key, keyValuePair.Value);
break;
}
else if (typeTreeType.TypeHash.data.SequenceEqual(spawnRandomHash))
{
AssetsFileInstance assetFileInst = am.LoadBundleWithDependencies(assetPaths);

GetPrefabGameObjectInfoFromBundle(am, assetFileInst, out AssetFileInfo prefabGameObjectInfo);

AssetFileInfo spawnRandomInfo = am.GetMonoBehaviourFromGameObject(assetFileInst, prefabGameObjectInfo, "SpawnRandom");
// See SpawnRandom.Start
AssetTypeValueField spawnRandom = am.GetBaseField(assetFileInst, spawnRandomInfo);
List<string> classIds = [];
Expand All @@ -252,6 +257,7 @@ private ConcurrentDictionary<string, string[]> GetAllPrefabPlaceholdersGroupsFas
}

RandomPossibilitiesByClassId.TryAdd(keyValuePair.Key, [.. classIds]);
break;
}
}

Expand Down Expand Up @@ -380,7 +386,7 @@ private IPrefabAsset GetAndCacheAsset(AssetsBundleManager amInst, string classId
{
classIds.Add(classIdByRuntimeKey[assetReference["m_AssetGUID"].AsString]);
}

return new PrefabPlaceholderRandomAsset(classIds);
}

Expand Down
4 changes: 2 additions & 2 deletions NitroxServer-Subnautica/Resources/ResourceAssets.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,16 @@ public class ResourceAssets
public Dictionary<string, WorldEntityInfo> WorldEntitiesByClassId { get; init; } = new();
public string LootDistributionsJson { get; init; } = "";
public Dictionary<string, PrefabPlaceholdersGroupAsset> PrefabPlaceholdersGroupsByGroupClassId { get; init; } = new();
public RandomStartGenerator NitroxRandom { get; init; }
public Dictionary<string, string[]> RandomPossibilitiesByClassId { get; init; }
public RandomStartGenerator NitroxRandom { get; init; }

public static void ValidateMembers(ResourceAssets resourceAssets)
{
Validate.NotNull(resourceAssets);
Validate.IsTrue(resourceAssets.WorldEntitiesByClassId.Count > 0);
Validate.IsTrue(resourceAssets.LootDistributionsJson != "");
Validate.IsTrue(resourceAssets.PrefabPlaceholdersGroupsByGroupClassId.Count > 0);
Validate.NotNull(resourceAssets.NitroxRandom);
Validate.IsTrue(resourceAssets.RandomPossibilitiesByClassId.Count > 0);
Validate.NotNull(resourceAssets.NitroxRandom);
}
}
6 changes: 4 additions & 2 deletions NitroxServer/GameLogic/Bases/BuildingManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,9 @@ public bool ModifyConstructedAmount(ModifyConstructedAmount modifyConstructedAmo
Log.Error($"Trying to modify the constructed amount of a non-registered object (GhostId: {modifyConstructedAmount.GhostId})");
return false;
}
// Certain entities are just "regular" WorldEntities and for simplicity we'll just ignore the

// Certain entities with a Constructable are just "regular" WorldEntities (e.g. starship boxes) and for simplicity we'll just not persist their progress
// since their only use is to be deconstructed to give materials to players
if (entity is not GhostEntity && entity is not ModuleEntity)
{
// In case the entity was fully deconstructed
Expand Down Expand Up @@ -275,7 +277,7 @@ public bool ReplacePieceByGhost(Player player, PieceDeconstructed pieceDeconstru

removedEntity = worldEntityManager.RemoveGlobalRootEntity(pieceDeconstructed.PieceId).Value;
GhostEntity ghostEntity = pieceDeconstructed.ReplacerGhost;

worldEntityManager.AddOrUpdateGlobalRootEntity(ghostEntity);
buildEntity.BaseData = pieceDeconstructed.BaseData;
buildEntity.OperationId++;
Expand Down
9 changes: 5 additions & 4 deletions NitroxServer/GameLogic/Entities/WorldEntityManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,8 @@ public void LoadAllUnspawnedEntities(System.Threading.CancellationToken token)
{
IMap map = NitroxServiceLocator.LocateService<IMap>();

int totalEntites = 0;
int totalBatches = map.DimensionsInBatches.X * map.DimensionsInBatches.Y * map.DimensionsInBatches.Z;
int batchesLoaded = 0;

for (int x = 0; x < map.DimensionsInBatches.X; x++)
{
Expand All @@ -230,13 +231,13 @@ public void LoadAllUnspawnedEntities(System.Threading.CancellationToken token)

Log.Debug($"Loaded {spawned} entities from batch ({x}, {y}, {z})");

totalEntites += spawned;
batchesLoaded++;
}
}

if (totalEntites > 0)
if (batchesLoaded > 0)
{
Log.Info($"Loading : {(int)((totalEntites/ 709531) * 100)}%");
Log.Info($"Loading : {(int)(100f * batchesLoaded / totalBatches)}%");
}
}
}
Expand Down

0 comments on commit eb02f01

Please sign in to comment.