using Content.Server.Worldgen.Components; using Robust.Server.GameObjects; namespace Content.Server.Worldgen.Systems; /// /// This handles loading in objects based on distance from player, using some metadata on chunks. /// public sealed class LocalityLoaderSystem : BaseWorldSystem { [Dependency] private readonly TransformSystem _xformSys = default!; /// public override void Update(float frameTime) { var e = EntityQueryEnumerator(); var loadedQuery = GetEntityQuery(); var xformQuery = GetEntityQuery(); var controllerQuery = GetEntityQuery(); while (e.MoveNext(out var uid, out var loadable, out var xform)) { if (!controllerQuery.TryGetComponent(xform.MapUid, out var controller)) { RaiseLocalEvent(uid, new LocalStructureLoadedEvent()); RemCompDeferred(uid); continue; } var coords = GetChunkCoords(uid, xform); var done = false; for (var i = -1; i < 2 && !done; i++) { for (var j = -1; j < 2 && !done; j++) { var chunk = GetOrCreateChunk(coords + (i, j), xform.MapUid!.Value, controller); if (!loadedQuery.TryGetComponent(chunk, out var loaded) || loaded.Loaders is null) continue; foreach (var loader in loaded.Loaders) { if (!xformQuery.TryGetComponent(loader, out var loaderXform)) continue; if ((_xformSys.GetWorldPosition(loaderXform) - _xformSys.GetWorldPosition(xform)).Length() > loadable.LoadingDistance) continue; RaiseLocalEvent(uid, new LocalStructureLoadedEvent()); RemCompDeferred(uid); done = true; break; } } } } } } /// /// A directed fired on a loadable entity when a local loader enters it's vicinity. /// public record struct LocalStructureLoadedEvent;