2024-12-22 15:13:10 +13:00
|
|
|
using System.Linq;
|
2024-04-24 21:31:45 -04:00
|
|
|
using Content.Server.GameTicking.Rules.Components;
|
2024-05-10 14:35:59 +03:00
|
|
|
using Content.Server.GridPreloader;
|
2024-12-07 00:39:35 +03:00
|
|
|
using Content.Server.StationEvents.Events;
|
2024-06-04 11:53:24 +00:00
|
|
|
using Content.Shared.GameTicking.Components;
|
2024-04-24 21:31:45 -04:00
|
|
|
using Robust.Server.GameObjects;
|
2024-12-22 15:13:10 +13:00
|
|
|
using Robust.Shared.EntitySerialization;
|
|
|
|
|
using Robust.Shared.EntitySerialization.Systems;
|
|
|
|
|
using Robust.Shared.Map;
|
2024-04-24 21:31:45 -04:00
|
|
|
using Robust.Shared.Prototypes;
|
2024-12-22 15:13:10 +13:00
|
|
|
using Robust.Shared.Utility;
|
2024-04-24 21:31:45 -04:00
|
|
|
|
|
|
|
|
namespace Content.Server.GameTicking.Rules;
|
|
|
|
|
|
2024-12-07 00:39:35 +03:00
|
|
|
public sealed class LoadMapRuleSystem : StationEventSystem<LoadMapRuleComponent>
|
2024-04-24 21:31:45 -04:00
|
|
|
{
|
|
|
|
|
[Dependency] private readonly IPrototypeManager _prototypeManager = default!;
|
|
|
|
|
[Dependency] private readonly MapSystem _map = default!;
|
|
|
|
|
[Dependency] private readonly MapLoaderSystem _mapLoader = default!;
|
|
|
|
|
[Dependency] private readonly TransformSystem _transform = default!;
|
2024-05-10 14:35:59 +03:00
|
|
|
[Dependency] private readonly GridPreloaderSystem _gridPreloader = default!;
|
2024-04-24 21:31:45 -04:00
|
|
|
|
|
|
|
|
protected override void Added(EntityUid uid, LoadMapRuleComponent comp, GameRuleComponent rule, GameRuleAddedEvent args)
|
|
|
|
|
{
|
2024-06-04 00:04:19 +00:00
|
|
|
if (comp.PreloadedGrid != null && !_gridPreloader.PreloadingEnabled)
|
|
|
|
|
{
|
|
|
|
|
// Preloading will never work if it's disabled, duh
|
|
|
|
|
Log.Debug($"Immediately ending {ToPrettyString(uid):rule} as preloading grids is disabled by cvar.");
|
|
|
|
|
ForceEndSelf(uid, rule);
|
2024-04-24 21:31:45 -04:00
|
|
|
return;
|
2024-06-04 00:04:19 +00:00
|
|
|
}
|
2024-04-24 21:31:45 -04:00
|
|
|
|
2024-12-22 15:13:10 +13:00
|
|
|
MapId mapId;
|
2024-06-04 00:04:19 +00:00
|
|
|
IReadOnlyList<EntityUid> grids;
|
2024-04-24 21:31:45 -04:00
|
|
|
if (comp.GameMap != null)
|
|
|
|
|
{
|
2024-12-22 15:13:10 +13:00
|
|
|
// Component has one of three modes, only one of the three fields should ever be populated.
|
|
|
|
|
DebugTools.AssertNull(comp.MapPath);
|
|
|
|
|
DebugTools.AssertNull(comp.GridPath);
|
|
|
|
|
DebugTools.AssertNull(comp.PreloadedGrid);
|
|
|
|
|
|
2024-04-24 21:31:45 -04:00
|
|
|
var gameMap = _prototypeManager.Index(comp.GameMap.Value);
|
2024-12-22 15:13:10 +13:00
|
|
|
grids = GameTicker.LoadGameMap(gameMap, out mapId, null);
|
|
|
|
|
Log.Info($"Created map {mapId} for {ToPrettyString(uid):rule}");
|
2024-04-24 21:31:45 -04:00
|
|
|
}
|
2024-06-04 00:04:19 +00:00
|
|
|
else if (comp.MapPath is {} path)
|
2024-04-24 21:31:45 -04:00
|
|
|
{
|
2024-12-22 15:13:10 +13:00
|
|
|
DebugTools.AssertNull(comp.GridPath);
|
|
|
|
|
DebugTools.AssertNull(comp.PreloadedGrid);
|
|
|
|
|
|
|
|
|
|
var opts = DeserializationOptions.Default with {InitializeMaps = true};
|
|
|
|
|
if (!_mapLoader.TryLoadMap(path, out var map, out var gridSet, opts))
|
2024-05-10 14:35:59 +03:00
|
|
|
{
|
2024-06-04 00:04:19 +00:00
|
|
|
Log.Error($"Failed to load map from {path}!");
|
|
|
|
|
ForceEndSelf(uid, rule);
|
2024-05-10 14:35:59 +03:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
2024-12-22 15:13:10 +13:00
|
|
|
grids = gridSet.Select( x => x.Owner).ToList();
|
|
|
|
|
mapId = map.Value.Comp.MapId;
|
|
|
|
|
}
|
|
|
|
|
else if (comp.GridPath is { } gPath)
|
|
|
|
|
{
|
|
|
|
|
DebugTools.AssertNull(comp.PreloadedGrid);
|
|
|
|
|
|
|
|
|
|
// I fucking love it when "map paths" choses to ar
|
|
|
|
|
_map.CreateMap(out mapId);
|
|
|
|
|
var opts = DeserializationOptions.Default with {InitializeMaps = true};
|
|
|
|
|
if (!_mapLoader.TryLoadGrid(mapId, gPath, out var grid, opts))
|
|
|
|
|
{
|
|
|
|
|
Log.Error($"Failed to load grid from {gPath}!");
|
|
|
|
|
ForceEndSelf(uid, rule);
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
grids = new List<EntityUid> {grid.Value.Owner};
|
2024-05-10 14:35:59 +03:00
|
|
|
}
|
2024-06-04 00:04:19 +00:00
|
|
|
else if (comp.PreloadedGrid is {} preloaded)
|
2024-05-10 14:35:59 +03:00
|
|
|
{
|
|
|
|
|
// TODO: If there are no preloaded grids left, any rule announcements will still go off!
|
2024-06-04 00:04:19 +00:00
|
|
|
if (!_gridPreloader.TryGetPreloadedGrid(preloaded, out var loadedShuttle))
|
2024-05-10 14:35:59 +03:00
|
|
|
{
|
2024-06-04 00:04:19 +00:00
|
|
|
Log.Error($"Failed to get a preloaded grid with {preloaded}!");
|
|
|
|
|
ForceEndSelf(uid, rule);
|
2024-05-10 14:35:59 +03:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
2024-12-22 15:13:10 +13:00
|
|
|
var mapUid = _map.CreateMap(out mapId, runMapInit: false);
|
2024-05-10 14:35:59 +03:00
|
|
|
_transform.SetParent(loadedShuttle.Value, mapUid);
|
2024-06-04 00:04:19 +00:00
|
|
|
grids = new List<EntityUid>() { loadedShuttle.Value };
|
|
|
|
|
_map.InitializeMap(mapUid);
|
2024-04-24 21:31:45 -04:00
|
|
|
}
|
|
|
|
|
else
|
|
|
|
|
{
|
|
|
|
|
Log.Error($"No valid map prototype or map path associated with the rule {ToPrettyString(uid)}");
|
2024-06-04 00:04:19 +00:00
|
|
|
ForceEndSelf(uid, rule);
|
|
|
|
|
return;
|
2024-04-24 21:31:45 -04:00
|
|
|
}
|
|
|
|
|
|
2024-06-04 00:04:19 +00:00
|
|
|
var ev = new RuleLoadedGridsEvent(mapId, grids);
|
|
|
|
|
RaiseLocalEvent(uid, ref ev);
|
2024-12-07 00:39:35 +03:00
|
|
|
|
|
|
|
|
base.Added(uid, comp, rule, args);
|
2024-04-24 21:31:45 -04:00
|
|
|
}
|
|
|
|
|
}
|