Add entity prototype save test (#10274)

This commit is contained in:
Leon Friedrich
2022-08-17 12:47:58 +12:00
committed by GitHub
parent ad67a8508a
commit 93584f21db
104 changed files with 813 additions and 144 deletions

View File

@@ -21,6 +21,7 @@ namespace Content.IntegrationTests.Tests
public async Task SpawnTest() public async Task SpawnTest()
{ {
//TODO: Run this test in a for loop, and figure out why garbage is ending up in the Entities list on cleanup. //TODO: Run this test in a for loop, and figure out why garbage is ending up in the Entities list on cleanup.
//If this gets fixed, see also UninitializedSaveTest.
await using var pairTracker = await PoolManager.GetServerClient(new PoolSettings{NoClient = true, Dirty = true, Destructive = true}); await using var pairTracker = await PoolManager.GetServerClient(new PoolSettings{NoClient = true, Dirty = true, Destructive = true});
var server = pairTracker.Pair.Server; var server = pairTracker.Pair.Server;

View File

@@ -0,0 +1,350 @@
#nullable enable
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Content.Shared.Coordinates;
using NUnit.Framework;
using Robust.Shared.GameObjects;
using Robust.Shared.IoC;
using Robust.Shared.Map;
using Robust.Shared.Prototypes;
using Robust.Shared.Serialization.Manager;
using Robust.Shared.Serialization.Markdown;
using Robust.Shared.Serialization.Markdown.Mapping;
using Robust.Shared.Serialization.Markdown.Validation;
using Robust.Shared.Serialization.Markdown.Value;
using Robust.Shared.Serialization.TypeSerializers.Interfaces;
namespace Content.IntegrationTests.Tests;
/// <summary>
/// This test ensure that when an entity prototype is spawned into an un-initialized map, its component data is not
/// modified during init. I.e., when the entity is saved to the map, its data is simply the default prototype data (ignoring transform component).
/// </summary>
/// <remarks>
/// If you are here becaus your test is failing, one easy way of figuring out how to fix the prototype is to just
/// spawn it into a new empty map and seeing what the map yml looks like.
/// </remarks>
[TestFixture]
public sealed class PrototypeSaveTest
{
private readonly HashSet<string> _ignoredPrototypes = new()
{
"Singularity", // physics collision uses "AllMask" (-1). The flag serializer currently fails to save this because this features un-named bits.
"constructionghost",
// TODO fix more prototypes
// The rest of these prototypes (probably) shouldn't be getting ignored.
// There should be an issue up tracking all of these prototypes, indicating that still need to get fixed.
"C4",
"WeaponProtoKineticAccelerator",
"WeaponStaffHealing",
"WeaponStaffPolymorphDoor",
"WeaponWandPolymorphCarp",
"WeaponWandPolymorphMonkey",
"WeaponWandFireball",
"WeaponWandDeath",
"WeaponWandPolymorphDoor",
"GlowstickBase",
"GlowstickRed",
"GlowstickPurple",
"GlowstickYellow",
"GlowstickBlue",
"Thruster",
"Gyroscope",
"RemoteSignaller",
"filingCabinet",
"filingCabinetTall",
"filingCabinetDrawer",
"WeaponLauncherChinaLake",
"WeaponLauncherRocket",
"WeaponLauncherMultipleRocket",
"Crematorium",
"JawsOfLife",
"SyndicateJawsOfLife",
"LightReplacer",
"ComputerCloningConsole",
"PowerDrill",
"Omnitool",
"GasPressurePump",
"GasVolumePump",
"GasDualPortVentPump",
"PortableScrubber",
"ParticleAcceleratorControlBox",
"GasFilter",
"GasFilterFlipped",
"GasMixer",
"GasMixerFlipped",
"HospitalCurtainsOpen",
"CargoPallet",
"DisposalHolder",
"ParticlesProjectile",
"AMEController",
"AMEControllerUnanchored",
"MopBucket",
"JanitorialTrolley",
"FloorDrain",
"OrganHumanLungs",
"SprayBottle",
"OrganRatLungs",
"SentientSlimeCore",
"OrganSlimeLungs",
"OrganVoxLungs",
"OrganAnimalLungs",
"Floodlight",
"EmergencyMedipen",
"AntiPoisonMedipen",
"SpaceMedipen",
"HolosignWetFloor",
"HeadSkeleton",
"PoweredlightEmpty",
"Poweredlight",
"PoweredlightLED",
"PoweredlightExterior",
"PoweredlightSodium",
"PoweredSmallLightEmpty",
"PoweredSmallLight",
"PoweredLightPostSmallEmpty",
"PoweredLightPostSmall",
"DeployableBarrier",
"CrateArtifactContainer",
"CloningPod",
"DrinkColaCan",
"FoodBowlBig",
"FoodBowlFancy",
"MachineFrame",
"WeaponImprovisedPneumaticCannon",
"LauncherCreamPie",
"GravityGenerator",
"GravityGeneratorMini",
"FoodCondimentPacket",
"FoodCondimentBottle",
"FoodCondimentBottleSmall",
"Autolathe",
"Protolathe",
"CircuitImprinter",
"SecurityTechFab",
"MedicalTechFab",
"UniformPrinter",
"OreProcessor",
"MedicalScanner",
"KitchenMicrowave",
"MagazinePistolSubMachineGunTopMounted",
"Recycler",
"EpinephrineChemistryBottle",
"RobustHarvestChemistryBottle",
"NocturineChemistryBottle",
"EphedrineChemistryBottle",
"OmnizineChemistryBottle",
"Beaker",
"LargeBeaker",
"CryostasisBeaker",
"BluespaceBeaker",
"Syringe",
"ClusterBang",
"ClusterBangFull",
"CargoTelepad",
"ClothingHeadHatHardhatBlue",
"ClothingHeadHatHardhatOrange",
"ClothingHeadHatHardhatRed",
"ClothingHeadHatHardhatWhite",
"ClothingHeadHatHardhatYellow",
"Vaccinator",
"AirlockExternalShuttleLocked",
"AirlockExternalGlassShuttleLocked",
"AirlockExternalGlassShuttleEmergencyLocked",
"ConveyorBelt",
"ClothingHeadHatChef",
"ClothingHeadHelmetFire",
"ClothingHeadHelmetAtmosFire",
"Bucket",
"CableTerminal",
"AirlockShuttle",
"AirlockGlassShuttle"
};
[Test]
public async Task UninitializedSaveTest()
{
// Apparently SpawnTest fails to clean up properly. Due to the similarities, I'll assume this also fails.
await using var pairTracker = await PoolManager.GetServerClient(new PoolSettings { NoClient = true, Dirty = true, Destructive = true });
var server = pairTracker.Pair.Server;
var mapManager = server.ResolveDependency<IMapManager>();
var entityMan = server.ResolveDependency<IEntityManager>();
var prototypeMan = server.ResolveDependency<IPrototypeManager>();
var tileDefinitionManager = server.ResolveDependency<ITileDefinitionManager>();
var seriMan = server.ResolveDependency<ISerializationManager>();
var compFact = server.ResolveDependency<IComponentFactory>();
var prototypes = new List<EntityPrototype>();
IMapGrid grid = default!;
EntityUid uid;
MapId mapId = default;
//Build up test environment
await server.WaitPost(() =>
{
// Create a one tile grid to stave off the grid 0 monsters
mapId = mapManager.CreateMap();
mapManager.AddUninitializedMap(mapId);
grid = mapManager.CreateGrid(mapId);
var tileDefinition = tileDefinitionManager["UnderPlating"];
var tile = new Tile(tileDefinition.TileId);
var coordinates = grid.ToCoordinates();
grid.SetTile(coordinates, tile);
});
await server.WaitRunTicks(5);
//Generate list of non-abstract prototypes to test
foreach (var prototype in prototypeMan.EnumeratePrototypes<EntityPrototype>())
{
if (prototype.Abstract)
continue;
// Currently mobs and such can't be serialized, but they aren't flagged as serializable anyways.
if (!prototype.MapSavable)
continue;
if (_ignoredPrototypes.Contains(prototype.ID))
continue;
if (prototype.SetSuffix == "DEBUG")
continue;
prototypes.Add(prototype);
}
var context = new TestEntityUidContext();
await server.WaitAssertion(() =>
{
Assert.That(!mapManager.IsMapInitialized(mapId));
var testLocation = grid.ToCoordinates();
Assert.Multiple(() =>
{
//Iterate list of prototypes to spawn
foreach (var prototype in prototypes)
{
uid = entityMan.SpawnEntity(prototype.ID, testLocation);
server.RunTicks(1);
// get default prototype data
Dictionary<string, MappingDataNode> protoData = new();
try
{
foreach (var (compType, comp) in prototype.Components)
{
protoData.Add(compType, seriMan.WriteValueAs<MappingDataNode>(comp.Component.GetType(), comp.Component, context: context));
}
}
catch (Exception e)
{
Assert.Fail($"Failed to convert prototype {prototype.ID} into yaml. Exception: {e.Message}");
continue;
}
var comps = new HashSet<IComponent>(entityMan.GetComponents(uid));
var compNames = new HashSet<string>(comps.Count);
foreach (var component in comps)
{
var compType = component.GetType();
var compName = compFact.GetComponentName(compType);
compNames.Add(compName);
if (compType == typeof(MetaDataComponent) || compType == typeof(TransformComponent))
continue;
MappingDataNode compMapping;
try
{
compMapping = seriMan.WriteValueAs<MappingDataNode>(compType, component, context: context);
}
catch (Exception e)
{
Assert.Fail($"Failed to serialize {compName} component of entity prototype {prototype.ID}. Exception: {e.Message}");
continue;
}
if (protoData.TryGetValue(compName, out var protoMapping))
{
var diff = compMapping.Except(protoMapping);
if (diff != null && diff.Children.Count != 0)
{
var modComps = string.Join(",", diff.Keys.Select(x => x.ToString()));
Assert.Fail($"Prototype {prototype.ID} modifies component on spawn: {compName}. Modified fields: {modComps}");
}
}
else
{
Assert.Fail($"Prototype {prototype.ID} gains a component on spawn: {compName}");
}
}
// An entity may also remove components on init -> check no components are missing.
foreach (var (compType, comp) in prototype.Components)
{
Assert.That(compNames.Contains(compType), $"Prototype {prototype.ID} removes component {compType} on spawn.");
}
if (!entityMan.Deleted(uid))
entityMan.DeleteEntity(uid);
}
});
});
await pairTracker.CleanReturnAsync();
}
private sealed class TestEntityUidContext : ISerializationContext,
ITypeSerializer<EntityUid, ValueDataNode>,
ITypeReaderWriter<EntityUid, ValueDataNode>
{
public Dictionary<(Type, Type), object> TypeReaders { get; }
public Dictionary<Type, object> TypeWriters { get; }
public Dictionary<Type, object> TypeCopiers => TypeWriters;
public Dictionary<(Type, Type), object> TypeValidators => TypeReaders;
public TestEntityUidContext()
{
TypeReaders = new() { { (typeof(EntityUid), typeof(ValueDataNode)), this } };
TypeWriters = new() { { typeof(EntityUid), this } };
}
ValidationNode ITypeValidator<EntityUid, ValueDataNode>.Validate(ISerializationManager serializationManager,
ValueDataNode node, IDependencyCollection dependencies, ISerializationContext? context)
{
return new ValidatedValueNode(node);
}
public DataNode Write(ISerializationManager serializationManager, EntityUid value, bool alwaysWrite = false,
ISerializationContext? context = null)
{
// EntityUids should be nullable and have no initial value.
throw new InvalidOperationException("Serializing prototypes should not attempt to write entity Uids");
}
EntityUid ITypeReader<EntityUid, ValueDataNode>.Read(ISerializationManager serializationManager,
ValueDataNode node,
IDependencyCollection dependencies,
bool skipHook,
ISerializationContext? context, EntityUid _)
{
return EntityUid.Invalid;
}
public EntityUid Copy(ISerializationManager serializationManager, EntityUid source, EntityUid target,
bool skipHook,
ISerializationContext? context = null)
{
return new((int) source);
}
}
}

View File

@@ -1,7 +1,3 @@
using Content.Shared.Hands.Components;
using Content.Shared.Inventory;
using System.Diagnostics.CodeAnalysis;
using System.Linq;
using Content.Server.Administration.Logs; using Content.Server.Administration.Logs;
using Content.Server.Kitchen.Components; using Content.Server.Kitchen.Components;
using Content.Server.Popups; using Content.Server.Popups;
@@ -9,11 +5,11 @@ using Content.Shared.Access;
using Content.Shared.Access.Components; using Content.Shared.Access.Components;
using Content.Shared.Access.Systems; using Content.Shared.Access.Systems;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.PDA;
using Content.Shared.Popups; using Content.Shared.Popups;
using Robust.Shared.Player; using Robust.Shared.Player;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
using Robust.Shared.Random; using Robust.Shared.Random;
using System.Linq;
namespace Content.Server.Access.Systems namespace Content.Server.Access.Systems
{ {
@@ -27,13 +23,15 @@ namespace Content.Server.Access.Systems
public override void Initialize() public override void Initialize()
{ {
base.Initialize(); base.Initialize();
SubscribeLocalEvent<IdCardComponent, ComponentInit>(OnInit); SubscribeLocalEvent<IdCardComponent, MapInitEvent>(OnMapInit);
SubscribeLocalEvent<IdCardComponent, BeingMicrowavedEvent>(OnMicrowaved); SubscribeLocalEvent<IdCardComponent, BeingMicrowavedEvent>(OnMicrowaved);
} }
private void OnInit(EntityUid uid, IdCardComponent id, ComponentInit args) private void OnMapInit(EntityUid uid, IdCardComponent id, MapInitEvent args)
{ {
id.OriginalOwnerName ??= EntityManager.GetComponent<MetaDataComponent>(id.Owner).EntityName; // On one hand, these prototypes should default to having the correct name. On the other hand, id cards are
// rarely ever spawned in on their own without an owner, so this is fine.
id.OriginalEntityName ??= EntityManager.GetComponent<MetaDataComponent>(id.Owner).EntityName;
UpdateEntityName(uid, id); UpdateEntityName(uid, id);
} }
@@ -139,7 +137,7 @@ namespace Content.Server.Access.Systems
if (string.IsNullOrWhiteSpace(id.FullName) && string.IsNullOrWhiteSpace(id.JobTitle)) if (string.IsNullOrWhiteSpace(id.FullName) && string.IsNullOrWhiteSpace(id.JobTitle))
{ {
EntityManager.GetComponent<MetaDataComponent>(id.Owner).EntityName = id.OriginalOwnerName; EntityManager.GetComponent<MetaDataComponent>(id.Owner).EntityName = id.OriginalEntityName;
return; return;
} }
@@ -147,7 +145,7 @@ namespace Content.Server.Access.Systems
var val = string.IsNullOrWhiteSpace(id.FullName) var val = string.IsNullOrWhiteSpace(id.FullName)
? Loc.GetString("access-id-card-component-owner-name-job-title-text", ? Loc.GetString("access-id-card-component-owner-name-job-title-text",
("originalOwnerName", id.OriginalOwnerName), ("originalOwnerName", id.OriginalEntityName),
("jobSuffix", jobSuffix)) ("jobSuffix", jobSuffix))
: Loc.GetString("access-id-card-component-owner-full-name-job-title-text", : Loc.GetString("access-id-card-component-owner-full-name-job-title-text",
("fullName", id.FullName), ("fullName", id.FullName),

View File

@@ -1,4 +1,4 @@
using Content.Server.Access.Components; using Content.Server.Access.Components;
using Content.Shared.Access.Components; using Content.Shared.Access.Components;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.Inventory; using Content.Shared.Inventory;
@@ -66,7 +66,7 @@ public sealed class IdExaminableSystem : EntitySystem
var val = string.IsNullOrWhiteSpace(id.FullName) var val = string.IsNullOrWhiteSpace(id.FullName)
? Loc.GetString("access-id-card-component-owner-name-job-title-text", ? Loc.GetString("access-id-card-component-owner-name-job-title-text",
("originalOwnerName", id.OriginalOwnerName), ("originalOwnerName", id.OriginalEntityName),
("jobSuffix", jobSuffix)) ("jobSuffix", jobSuffix))
: Loc.GetString("access-id-card-component-owner-full-name-job-title-text", : Loc.GetString("access-id-card-component-owner-full-name-job-title-text",
("fullName", id.FullName), ("fullName", id.FullName),

View File

@@ -33,11 +33,11 @@ namespace Content.Server.Body.Components
mechanism.Owner.RandomOffset(0.25f); mechanism.Owner.RandomOffset(0.25f);
} }
protected override void Initialize() public void MapInitialize()
{ {
base.Initialize(); base.Initialize();
_mechanismContainer = Owner.EnsureContainer<Container>($"{Name}-{nameof(BodyPartComponent)}"); _mechanismContainer = Owner.EnsureContainer<Container>(ContainerId);
// This is ran in Startup as entities spawned in Initialize // This is ran in Startup as entities spawned in Initialize
// are not synced to the client since they are assumed to be // are not synced to the client since they are assumed to be

View File

@@ -21,6 +21,7 @@ namespace Content.Server.Body.Systems
SubscribeLocalEvent<BodyComponent, MoveInputEvent>(OnRelayMoveInput); SubscribeLocalEvent<BodyComponent, MoveInputEvent>(OnRelayMoveInput);
SubscribeLocalEvent<BodyComponent, ApplyMetabolicMultiplierEvent>(OnApplyMetabolicMultiplier); SubscribeLocalEvent<BodyComponent, ApplyMetabolicMultiplierEvent>(OnApplyMetabolicMultiplier);
SubscribeLocalEvent<BodyComponent, BeingMicrowavedEvent>(OnBeingMicrowaved); SubscribeLocalEvent<BodyComponent, BeingMicrowavedEvent>(OnBeingMicrowaved);
SubscribeLocalEvent<BodyPartComponent, MapInitEvent>((_, c, _) => c.MapInitialize());
} }
private void OnRelayMoveInput(EntityUid uid, BodyComponent component, ref MoveInputEvent args) private void OnRelayMoveInput(EntityUid uid, BodyComponent component, ref MoveInputEvent args)

View File

@@ -12,6 +12,8 @@ namespace Content.Server.Disposal.Tube.Components
{ {
public abstract class DisposalTubeComponent : Component, IDisposalTubeComponent public abstract class DisposalTubeComponent : Component, IDisposalTubeComponent
{ {
public const string ContainerId = "disposal-tube";
[Dependency] private readonly IEntityManager _entMan = default!; [Dependency] private readonly IEntityManager _entMan = default!;
public static readonly TimeSpan ClangDelay = TimeSpan.FromSeconds(0.5); public static readonly TimeSpan ClangDelay = TimeSpan.FromSeconds(0.5);
@@ -135,7 +137,7 @@ namespace Content.Server.Disposal.Tube.Components
{ {
base.Initialize(); base.Initialize();
Contents = ContainerHelpers.EnsureContainer<Container>(Owner, Name); Contents = ContainerHelpers.EnsureContainer<Container>(Owner, ContainerId);
Owner.EnsureComponent<AnchorableComponent>(); Owner.EnsureComponent<AnchorableComponent>();
} }

View File

@@ -46,6 +46,7 @@ namespace Content.Server.Disposal.Unit.EntitySystems
[Dependency] private readonly SharedHandsSystem _handsSystem = default!; [Dependency] private readonly SharedHandsSystem _handsSystem = default!;
[Dependency] private readonly DumpableSystem _dumpableSystem = default!; [Dependency] private readonly DumpableSystem _dumpableSystem = default!;
[Dependency] private readonly TransformSystem _transformSystem = default!; [Dependency] private readonly TransformSystem _transformSystem = default!;
[Dependency] private readonly SharedContainerSystem _containerSystem = default!;
private readonly List<DisposalUnitComponent> _activeDisposals = new(); private readonly List<DisposalUnitComponent> _activeDisposals = new();
@@ -293,7 +294,7 @@ namespace Content.Server.Disposal.Unit.EntitySystems
private void HandleDisposalInit(EntityUid uid, DisposalUnitComponent component, ComponentInit args) private void HandleDisposalInit(EntityUid uid, DisposalUnitComponent component, ComponentInit args)
{ {
component.Container = component.Owner.EnsureContainer<Container>(component.Name); component.Container = _containerSystem.EnsureContainer<Container>(uid, SharedDisposalUnitComponent.ContainerId);
UpdateInterface(component, component.Powered); UpdateInterface(component, component.Powered);

View File

@@ -62,7 +62,7 @@ public sealed class RenameCommand : IConsoleCommand
{ {
foreach (var idCardComponent in entMan.EntityQuery<IdCardComponent>()) foreach (var idCardComponent in entMan.EntityQuery<IdCardComponent>())
{ {
if (idCardComponent.OriginalOwnerName != oldName) if (idCardComponent.OriginalEntityName != oldName)
continue; continue;
idCardSystem.TryChangeFullName(idCardComponent.Owner, name, idCardComponent); idCardSystem.TryChangeFullName(idCardComponent.Owner, name, idCardComponent);
} }

View File

@@ -182,9 +182,11 @@ namespace Content.Server.Nutrition.EntitySystems
UpdateAppearance(component); UpdateAppearance(component);
// Synchronize solution in drink if (TryComp(uid, out RefillableSolutionComponent? refillComp))
EnsureComp<RefillableSolutionComponent>(uid).Solution = component.SolutionName; refillComp.Solution = component.SolutionName;
EnsureComp<DrainableSolutionComponent>(uid).Solution = component.SolutionName;
if (TryComp(uid, out DrainableSolutionComponent? drainComp))
drainComp.Solution = component.SolutionName;
} }
private void OnSolutionChange(EntityUid uid, DrinkComponent component, SolutionChangedEvent args) private void OnSolutionChange(EntityUid uid, DrinkComponent component, SolutionChangedEvent args)

View File

@@ -30,8 +30,6 @@ namespace Content.Server.Nutrition.EntitySystems
public void CheckSolutions(TrashOnEmptyComponent component) public void CheckSolutions(TrashOnEmptyComponent component)
{ {
EntityManager.EnsureComponent<TagComponent>(component.Owner);
if (!EntityManager.HasComponent<SolutionContainerManagerComponent>((component).Owner)) if (!EntityManager.HasComponent<SolutionContainerManagerComponent>((component).Owner))
return; return;

View File

@@ -18,7 +18,7 @@ namespace Content.Server.PDA.Ringer
base.Initialize(); base.Initialize();
// General Event Subscriptions // General Event Subscriptions
SubscribeLocalEvent<RingerComponent, ComponentInit>(RandomizeRingtone); SubscribeLocalEvent<RingerComponent, MapInitEvent>(RandomizeRingtone);
// RingerBoundUserInterface Subscriptions // RingerBoundUserInterface Subscriptions
SubscribeLocalEvent<RingerComponent, RingerSetRingtoneMessage>(OnSetRingtone); SubscribeLocalEvent<RingerComponent, RingerSetRingtoneMessage>(OnSetRingtone);
SubscribeLocalEvent<RingerComponent, RingerPlayRingtoneMessage>(RingerPlayRingtone); SubscribeLocalEvent<RingerComponent, RingerPlayRingtoneMessage>(RingerPlayRingtone);
@@ -46,7 +46,7 @@ namespace Content.Server.PDA.Ringer
UpdateRingerRingtone(ringer, args.Ringtone); UpdateRingerRingtone(ringer, args.Ringtone);
} }
public void RandomizeRingtone(EntityUid uid, RingerComponent ringer, ComponentInit args) public void RandomizeRingtone(EntityUid uid, RingerComponent ringer, MapInitEvent args)
{ {
// Default to using C pentatonic so it at least sounds not terrible. // Default to using C pentatonic so it at least sounds not terrible.
var notes = new[] var notes = new[]

View File

@@ -50,7 +50,7 @@ public sealed class EntityStorageSystem : EntitySystem
component.Contents.OccludesLight = component.OccludesLight; component.Contents.OccludesLight = component.OccludesLight;
if (TryComp<ConstructionComponent>(uid, out var construction)) if (TryComp<ConstructionComponent>(uid, out var construction))
_construction.AddContainer(uid, nameof(EntityStorageComponent), construction); _construction.AddContainer(uid, ContainerName, construction);
if (TryComp<PlaceableSurfaceComponent>(uid, out var placeable)) if (TryComp<PlaceableSurfaceComponent>(uid, out var placeable))
_placeableSurface.SetPlaceable(uid, component.Open, placeable); _placeableSurface.SetPlaceable(uid, component.Open, placeable);

View File

@@ -13,6 +13,7 @@ namespace Content.Server.Storage.EntitySystems
{ {
[Dependency] private readonly PopupSystem _popupSystem = default!; [Dependency] private readonly PopupSystem _popupSystem = default!;
[Dependency] private readonly SharedHandsSystem _handsSystem = default!; [Dependency] private readonly SharedHandsSystem _handsSystem = default!;
[Dependency] private readonly SharedContainerSystem _containerSystem = default!;
public override void Initialize() public override void Initialize()
{ {
@@ -31,7 +32,7 @@ namespace Content.Server.Storage.EntitySystems
component.SecretPartName = entityName; component.SecretPartName = entityName;
} }
component.ItemContainer = ContainerHelpers.EnsureContainer<ContainerSlot>(uid, "stash", out _); component.ItemContainer = _containerSystem.EnsureContainer<ContainerSlot>(uid, "stash", out _);
} }
private void OnDestroyed(EntityUid uid, SecretStashComponent component, DestructionEventArgs args) private void OnDestroyed(EntityUid uid, SecretStashComponent component, DestructionEventArgs args)

View File

@@ -14,7 +14,10 @@ namespace Content.Shared.Access.Components
[Access(typeof(AccessSystem), Other = AccessPermissions.ReadExecute)] // FIXME Friends [Access(typeof(AccessSystem), Other = AccessPermissions.ReadExecute)] // FIXME Friends
public HashSet<string> Tags = new(); public HashSet<string> Tags = new();
[DataField("groups", customTypeSerializer: typeof(PrototypeIdHashSetSerializer<AccessGroupPrototype>))] /// <summary>
public HashSet<string> Groups = new(); /// Access Groups. These are added to the tags during map init. After map init this will have no effect.
/// </summary>
[DataField("groups", readOnly: true, customTypeSerializer: typeof(PrototypeIdHashSetSerializer<AccessGroupPrototype>))]
public readonly HashSet<string> Groups = new();
} }
} }

View File

@@ -9,8 +9,8 @@ namespace Content.Shared.Access.Components
[Access(typeof(SharedIdCardSystem), typeof(SharedPDASystem), typeof(SharedAgentIdCardSystem))] [Access(typeof(SharedIdCardSystem), typeof(SharedPDASystem), typeof(SharedAgentIdCardSystem))]
public sealed class IdCardComponent : Component public sealed class IdCardComponent : Component
{ {
[DataField("originalOwnerName")] [DataField("originalEntityName")]
public string OriginalOwnerName = default!; public string OriginalEntityName = string.Empty;
[DataField("fullName")] [DataField("fullName")]
[Access(typeof(SharedIdCardSystem), typeof(SharedPDASystem), typeof(SharedAgentIdCardSystem), [Access(typeof(SharedIdCardSystem), typeof(SharedPDASystem), typeof(SharedAgentIdCardSystem),

View File

@@ -12,10 +12,10 @@ namespace Content.Shared.Access.Systems
{ {
base.Initialize(); base.Initialize();
SubscribeLocalEvent<AccessComponent, ComponentInit>(OnAccessInit); SubscribeLocalEvent<AccessComponent, MapInitEvent>(OnAccessInit);
} }
private void OnAccessInit(EntityUid uid, AccessComponent component, ComponentInit args) private void OnAccessInit(EntityUid uid, AccessComponent component, MapInitEvent args)
{ {
// Add all tags in groups to the list of tags. // Add all tags in groups to the list of tags.
foreach (var group in component.Groups) foreach (var group in component.Groups)

View File

@@ -11,6 +11,8 @@ namespace Content.Shared.Body.Components
[NetworkedComponent()] [NetworkedComponent()]
public abstract class SharedBodyPartComponent : Component public abstract class SharedBodyPartComponent : Component
{ {
public const string ContainerId = "bodypart";
[Dependency] private readonly IEntityManager _entMan = default!; [Dependency] private readonly IEntityManager _entMan = default!;
private SharedBodyComponent? _body; private SharedBodyComponent? _body;

View File

@@ -6,6 +6,8 @@ namespace Content.Shared.Disposal.Components
[NetworkedComponent] [NetworkedComponent]
public abstract class SharedDisposalUnitComponent : Component public abstract class SharedDisposalUnitComponent : Component
{ {
public const string ContainerId = "disposal-unit";
// TODO: Could maybe turn the contact off instead far more cheaply as farseer (though not box2d) had support for it? // TODO: Could maybe turn the contact off instead far more cheaply as farseer (though not box2d) had support for it?
// Need to suss it out. // Need to suss it out.
/// <summary> /// <summary>

View File

@@ -16,6 +16,7 @@ public abstract partial class SharedGunSystem
protected virtual void InitializeBallistic() protected virtual void InitializeBallistic()
{ {
SubscribeLocalEvent<BallisticAmmoProviderComponent, ComponentInit>(OnBallisticInit); SubscribeLocalEvent<BallisticAmmoProviderComponent, ComponentInit>(OnBallisticInit);
SubscribeLocalEvent<BallisticAmmoProviderComponent, MapInitEvent>(OnBallisticMapInit);
SubscribeLocalEvent<BallisticAmmoProviderComponent, TakeAmmoEvent>(OnBallisticTakeAmmo); SubscribeLocalEvent<BallisticAmmoProviderComponent, TakeAmmoEvent>(OnBallisticTakeAmmo);
SubscribeLocalEvent<BallisticAmmoProviderComponent, GetAmmoCountEvent>(OnBallisticAmmoCount); SubscribeLocalEvent<BallisticAmmoProviderComponent, GetAmmoCountEvent>(OnBallisticAmmoCount);
SubscribeLocalEvent<BallisticAmmoProviderComponent, ComponentGetState>(OnBallisticGetState); SubscribeLocalEvent<BallisticAmmoProviderComponent, ComponentGetState>(OnBallisticGetState);
@@ -122,17 +123,13 @@ public abstract partial class SharedGunSystem
private void OnBallisticInit(EntityUid uid, BallisticAmmoProviderComponent component, ComponentInit args) private void OnBallisticInit(EntityUid uid, BallisticAmmoProviderComponent component, ComponentInit args)
{ {
component.Container = Containers.EnsureContainer<Container>(uid, "ballistic-ammo"); component.Container = Containers.EnsureContainer<Container>(uid, "ballistic-ammo");
component.UnspawnedCount = component.Capacity; }
private void OnBallisticMapInit(EntityUid uid, BallisticAmmoProviderComponent component, MapInitEvent args)
{
if (component.FillProto != null) if (component.FillProto != null)
{
component.UnspawnedCount -= Math.Min(component.UnspawnedCount, component.Container.ContainedEntities.Count); component.UnspawnedCount -= Math.Min(component.UnspawnedCount, component.Container.ContainedEntities.Count);
} }
else
{
component.UnspawnedCount = 0;
}
}
protected int GetBallisticShots(BallisticAmmoProviderComponent component) protected int GetBallisticShots(BallisticAmmoProviderComponent component)
{ {

View File

@@ -10,6 +10,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
# For primates mainly # For primates mainly
- type: entity - type: entity

View File

@@ -8,6 +8,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: TorsoHuman id: TorsoHuman

View File

@@ -8,6 +8,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: TorsoReptilian id: TorsoReptilian

View File

@@ -6,6 +6,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Inorganic damageContainer: Inorganic
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: LeftArmBorg id: LeftArmBorg

View File

@@ -7,6 +7,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: TorsoSkeleton id: TorsoSkeleton

View File

@@ -7,6 +7,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: TorsoSlime id: TorsoSlime

View File

@@ -8,6 +8,11 @@
components: components:
- type: Damageable - type: Damageable
damageContainer: Biological damageContainer: Biological
- type: BodyPart
- type: ContainerContainer
containers:
bodypart: !type:Container
ents: []
- type: entity - type: entity
id: TorsoVox id: TorsoVox

View File

@@ -367,10 +367,22 @@
- id: MagazineShotgunIncendiary - id: MagazineShotgunIncendiary
amount: 6 amount: 6
# base BallisticAmmoProvider boxes
- type: entity
parent: BoxCardboard
id: BoxAmmoProvider
abstract: true
components:
- type: BallisticAmmoProvider
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
storagebase: !type:Container
# Shotgun Shells # Shotgun Shells
- type: entity - type: entity
name: box of shotgun beanbag cartridges name: box of shotgun beanbag cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxBeanbag id: BoxBeanbag
description: A box full of beanbag shots, designed for riot shotguns. description: A box full of beanbag shots, designed for riot shotguns.
components: components:
@@ -384,7 +396,7 @@
- type: entity - type: entity
name: box of shotgun lethal cartridges name: box of shotgun lethal cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxLethalshot id: BoxLethalshot
description: A box full of lethal pellet shots, designed for riot shotguns. description: A box full of lethal pellet shots, designed for riot shotguns.
components: components:
@@ -398,7 +410,7 @@
- type: entity - type: entity
name: box of shotgun slug cartridges name: box of shotgun slug cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxShotgunSlug id: BoxShotgunSlug
description: A box full of shotgun slugs, designed for riot shotguns. description: A box full of shotgun slugs, designed for riot shotguns.
components: components:
@@ -412,7 +424,7 @@
- type: entity - type: entity
name: box of shotgun flare cartridges name: box of shotgun flare cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxShotgunFlare id: BoxShotgunFlare
description: A box full of shotgun flare cartridges, designed for riot shotguns. description: A box full of shotgun flare cartridges, designed for riot shotguns.
components: components:
@@ -426,7 +438,7 @@
- type: entity - type: entity
name: box of shotgun incendiary cartridges name: box of shotgun incendiary cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxShotgunIncendiary id: BoxShotgunIncendiary
description: A box full of shotgun incendiary cartridges, designed for riot shotguns. description: A box full of shotgun incendiary cartridges, designed for riot shotguns.
components: components:
@@ -440,7 +452,7 @@
- type: entity - type: entity
name: box of shotgun practice cartridges name: box of shotgun practice cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxShotgunPractice id: BoxShotgunPractice
description: A box full of shotgun practice cartridges, designed for riot shotguns. description: A box full of shotgun practice cartridges, designed for riot shotguns.
components: components:
@@ -454,7 +466,7 @@
- type: entity - type: entity
name: box of tranquilizer cartridges name: box of tranquilizer cartridges
parent: BoxCardboard parent: BoxAmmoProvider
id: BoxShellTranquilizer id: BoxShellTranquilizer
description: A box full of tranquilizer cartridges, designed for riot shotguns. description: A box full of tranquilizer cartridges, designed for riot shotguns.
components: components:

View File

@@ -15,6 +15,10 @@
- back - back
- type: Storage - type: Storage
capacity: 100 capacity: 100
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.StorageUiKey.Key - key: enum.StorageUiKey.Key

View File

@@ -15,6 +15,10 @@
- back - back
- type: Storage - type: Storage
capacity: 120 capacity: 120
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []
- type: ClothingSpeedModifier - type: ClothingSpeedModifier
walkModifier: 1 walkModifier: 1
sprintModifier: 0.9 sprintModifier: 0.9

View File

@@ -15,6 +15,10 @@
- back - back
- type: Storage - type: Storage
capacity: 100 capacity: 100
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.StorageUiKey.Key - key: enum.StorageUiKey.Key

View File

@@ -20,6 +20,10 @@
capacity: 40 capacity: 40
equipSound: equipSound:
path: /Audio/Items/belt_equip.ogg path: /Audio/Items/belt_equip.ogg
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.StorageUiKey.Key - key: enum.StorageUiKey.Key

View File

@@ -221,6 +221,10 @@
Heat: 0.65 Heat: 0.65
Radiation: 1 Radiation: 1
- type: IdentityBlocker - type: IdentityBlocker
- type: ItemSlots
- type: ContainerContainer
containers:
cell_slot: !type:ContainerSlot {}
- type: entity - type: entity
parent: ClothingHeadLightBase parent: ClothingHeadLightBase

View File

@@ -30,6 +30,10 @@
components: components:
- type: Storage - type: Storage
capacity: 10 capacity: 10
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.StorageUiKey.Key - key: enum.StorageUiKey.Key
@@ -62,6 +66,9 @@
- type: DiseaseProtection - type: DiseaseProtection
protection: 0.05 protection: 0.05
- type: ToggleableClothing - type: ToggleableClothing
- type: ContainerContainer
containers:
toggleable-clothing: !type:ContainerSlot {}
- type: entity - type: entity
abstract: true abstract: true

View File

@@ -35,6 +35,9 @@
coefficient: 0.5 coefficient: 0.5
- type: ToggleableClothing - type: ToggleableClothing
clothingPrototype: ClothingHeadHelmetEVA clothingPrototype: ClothingHeadHelmetEVA
- type: ContainerContainer
containers:
toggleable-clothing: !type:ContainerSlot {}
- type: entity - type: entity
parent: ClothingOuterBaseLarge parent: ClothingOuterBaseLarge

View File

@@ -8,6 +8,8 @@
- type: Sprite - type: Sprite
drawdepth: FloorObjects drawdepth: FloorObjects
- type: SolutionContainerManager - type: SolutionContainerManager
solutions:
puddle: {}
- type: Puddle - type: Puddle
spillSound: spillSound:
path: /Audio/Effects/Fluids/splat.ogg path: /Audio/Effects/Fluids/splat.ogg

View File

@@ -8,6 +8,7 @@
- state: blue - state: blue
- texture: Mobs/Species/Human/parts.rsi/full.png - texture: Mobs/Species/Human/parts.rsi/full.png
- state: ai - state: ai
- type: Timer
- type: TimedSpawner - type: TimedSpawner
prototypes: prototypes:
- MobSpirate - MobSpirate
@@ -27,6 +28,7 @@
- state: blue - state: blue
- texture: Mobs/Aliens/Xenos/burrower.rsi/crit.png - texture: Mobs/Aliens/Xenos/burrower.rsi/crit.png
- state: ai - state: ai
- type: Timer
- type: TimedSpawner - type: TimedSpawner
prototypes: prototypes:
- MobXeno - MobXeno
@@ -45,6 +47,7 @@
- state: blue - state: blue
- texture: Mobs/Animals/mouse.rsi/icon-2.png - texture: Mobs/Animals/mouse.rsi/icon-2.png
- state: timed - state: timed
- type: Timer
- type: TimedSpawner - type: TimedSpawner
prototypes: prototypes:
- MobMouse - MobMouse

View File

@@ -51,7 +51,7 @@
- type: entity - type: entity
parent: BaseMobHuman parent: BaseMobHuman
suffix: Dead suffix: Dead
save: true save: false # mobs are currently not saveable.
id: SalvageHumanCorpse id: SalvageHumanCorpse
name: unidentified human name: unidentified human
description: We barely knew ye. description: We barely knew ye.

View File

@@ -4,6 +4,7 @@
name: GuardianBase name: GuardianBase
id: MobGuardianBase id: MobGuardianBase
description: guardian description: guardian
save: false
components: components:
- type: GhostTakeoverAvailable - type: GhostTakeoverAvailable
makeSentient: true makeSentient: true

View File

@@ -22,6 +22,8 @@
solution: drink solution: drink
- type: RefillableSolution - type: RefillableSolution
solution: drink solution: drink
- type: DrainableSolution
solution: drink
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.TransferAmountUiKey.Key - key: enum.TransferAmountUiKey.Key

View File

@@ -27,6 +27,12 @@
- state: icon - state: icon
map: ["enum.DrinkCanVisualLayers.Icon"] map: ["enum.DrinkCanVisualLayers.Icon"]
netsync: false netsync: false
- type: FitsInDispenser
solution: drink
- type: DrawableSolution
solution: drink
- type: RefillableSolution
solution: drink
- type: DrainableSolution - type: DrainableSolution
solution: drink solution: drink
- type: Appearance - type: Appearance

View File

@@ -15,6 +15,8 @@
solution: drink solution: drink
- type: RefillableSolution - type: RefillableSolution
solution: drink solution: drink
- type: DrainableSolution
solution: drink
- type: SolutionTransfer - type: SolutionTransfer
canChangeTransferAmount: true canChangeTransferAmount: true
maxTransferAmount: 10 maxTransferAmount: 10

View File

@@ -16,6 +16,8 @@
solution: drink solution: drink
- type: RefillableSolution - type: RefillableSolution
solution: drink solution: drink
- type: DrainableSolution
solution: drink
- type: SolutionTransfer - type: SolutionTransfer
canChangeTransferAmount: true canChangeTransferAmount: true
- type: Spillable - type: Spillable

View File

@@ -19,6 +19,14 @@
isOpen: true isOpen: true
- type: Spillable - type: Spillable
solution: drink solution: drink
- type: FitsInDispenser
solution: drink
- type: DrawableSolution
solution: drink
- type: RefillableSolution
solution: drink
- type: DrainableSolution
solution: drink
- type: UserInterface - type: UserInterface
interfaces: interfaces:
- key: enum.TransferAmountUiKey.Key - key: enum.TransferAmountUiKey.Key

View File

@@ -11,6 +11,7 @@
components: components:
- type: Drink - type: Drink
solution: food solution: food
refillable: false
openSounds: openSounds:
collection: packetOpenSounds collection: packetOpenSounds
- type: DrawableSolution - type: DrawableSolution
@@ -19,7 +20,9 @@
solution: food solution: food
- type: DrainableSolution - type: DrainableSolution
solution: food solution: food
# Note NOT refillable # Note NOT refillable.
# It be a shame if it turned out ALL drinks were ALWAYS refillable.... ffs.
# Well its fixed now, but I want to share my pain.
- type: SolutionContainerManager - type: SolutionContainerManager
solutions: solutions:
food: food:
@@ -331,6 +334,10 @@
solution: food solution: food
openSounds: openSounds:
collection: pop collection: pop
- type: RefillableSolution
solution: food
- type: DrainableSolution
solution: food
- type: SolutionContainerManager - type: SolutionContainerManager
solutions: solutions:
food: food:
@@ -478,6 +485,10 @@
solution: food solution: food
openSounds: openSounds:
collection: pop collection: pop
- type: RefillableSolution
solution: food
- type: DrainableSolution
solution: food
- type: SolutionContainerManager - type: SolutionContainerManager
solutions: solutions:
food: food:

View File

@@ -8,6 +8,10 @@
- type: ItemCooldown - type: ItemCooldown
- type: UseDelay - type: UseDelay
delay: 1.0 delay: 1.0
- type: ItemSlots
- type: ContainerContainer
containers:
cell_slot: !type:ContainerSlot {}
- type: PowerCellSlot - type: PowerCellSlot
cellSlot: cellSlot:
startingItem: PowerCellMedium startingItem: PowerCellMedium

View File

@@ -48,6 +48,10 @@
- type: StaticPrice - type: StaticPrice
price: 50000 # YOU STOLE A NUCLEAR FISSION EXPLOSIVE?! price: 50000 # YOU STOLE A NUCLEAR FISSION EXPLOSIVE?!
- type: CargoSellBlacklist - type: CargoSellBlacklist
- type: ItemSlots
- type: ContainerContainer
containers:
Nuke: !type:ContainerSlot
- type: entity - type: entity
parent: NuclearBomb parent: NuclearBomb

View File

@@ -76,6 +76,11 @@
enum.ChemicalPayloadFilledSlots.Left: payload-chemical-left enum.ChemicalPayloadFilledSlots.Left: payload-chemical-left
enum.ChemicalPayloadFilledSlots.Right: payload-chemical-right enum.ChemicalPayloadFilledSlots.Right: payload-chemical-right
enum.ChemicalPayloadFilledSlots.Both: payload-chemical-armed enum.ChemicalPayloadFilledSlots.Both: payload-chemical-armed
- type: ItemSlots
- type: ContainerContainer
containers:
BeakerSlotA: !type:ContainerSlot
BeakerSlotB: !type:ContainerSlot
- type: entity - type: entity
name: flash payload name: flash payload

View File

@@ -17,6 +17,11 @@
state: pda state: pda
- type: Item - type: Item
size: 10 size: 10
- type: ContainerContainer
containers:
PDA-id: !type:ContainerSlot {}
PDA-pen: !type:ContainerSlot {}
- type: ItemSlots
- type: Clothing - type: Clothing
quickEquip: false quickEquip: false
slots: slots:

View File

@@ -147,7 +147,7 @@
state: toms state: toms
- type: entity - type: entity
parent: BasePlaceableInstrument parent: [ BasePlaceableInstrument, ConstructibleMachine]
id: DawInstrument id: DawInstrument
name: digital audio workstation name: digital audio workstation
description: Cutting edge music technology, straight from the 90s. description: Cutting edge music technology, straight from the 90s.
@@ -161,9 +161,6 @@
map: ["enum.WiresVisualLayers.MaintenancePanel"] map: ["enum.WiresVisualLayers.MaintenancePanel"]
- type: Appearance - type: Appearance
- type: WiresVisuals - type: WiresVisuals
- type: Construction
graph: Machine
node: machine
- type: Wires - type: Wires
BoardName: "DawInstrument" BoardName: "DawInstrument"
LayoutId: DawInstrument LayoutId: DawInstrument

View File

@@ -491,6 +491,10 @@
capacity: 1 capacity: 1
soundInsert: soundInsert:
path: /Audio/Weapons/drawbow2.ogg path: /Audio/Weapons/drawbow2.ogg
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
parent: BaseItem parent: BaseItem
@@ -530,6 +534,10 @@
autoCycle: true autoCycle: true
soundInsert: soundInsert:
path: /Audio/Weapons/Guns/MagIn/revolver_magin.ogg path: /Audio/Weapons/Guns/MagIn/revolver_magin.ogg
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
parent: BaseItem parent: BaseItem

View File

@@ -12,3 +12,6 @@
- type: Storage - type: Storage
capacity: 30 capacity: 30
size: 10 size: 10
- type: ContainerContainer
containers:
storagebase: !type:Container

View File

@@ -7,6 +7,7 @@
- type: HandheldLight - type: HandheldLight
addPrefix: true addPrefix: true
- type: PowerCellSlot - type: PowerCellSlot
- type: ItemSlots
- type: ContainerContainer - type: ContainerContainer
containers: containers:
cell_slot: !type:ContainerSlot cell_slot: !type:ContainerSlot
@@ -16,6 +17,7 @@
- type: Item - type: Item
sprite: Objects/Misc/Lights/lights.rsi sprite: Objects/Misc/Lights/lights.rsi
size: 20 size: 20
heldPrefix: off
- type: PointLight - type: PointLight
netsync: false netsync: false
enabled: false enabled: false

View File

@@ -67,6 +67,11 @@
False: {visible: false} False: {visible: false}
- type: Pullable - type: Pullable
- type: AntiRottingContainer - type: AntiRottingContainer
- type: ItemSlots
- type: ContainerContainer
containers:
entity_storage: !type:Container
paper_label: !type:ContainerSlot
- type: entity - type: entity
id: BodyBag_Folded id: BodyBag_Folded

View File

@@ -67,3 +67,8 @@
- type: StorageVisualizer - type: StorageVisualizer
state_open: artifact_container_open state_open: artifact_container_open
state_closed: artifact_container_door state_closed: artifact_container_door
- type: ItemSlots
- type: ContainerContainer
containers:
entity_storage: !type:Container
paper_label: !type:ContainerSlot

View File

@@ -31,6 +31,7 @@
- type: ContainerContainer - type: ContainerContainer
containers: containers:
cell_slot: !type:ContainerSlot cell_slot: !type:ContainerSlot
- type: ItemSlots
- type: Sprite - type: Sprite
sprite: Objects/Tools/flashlight.rsi sprite: Objects/Tools/flashlight.rsi
netsync: false netsync: false

View File

@@ -30,6 +30,10 @@
- type: PowerCellSlot - type: PowerCellSlot
cellSlot: cellSlot:
startingItem: PowerCellMedium startingItem: PowerCellMedium
- type: ItemSlots
- type: ContainerContainer
containers:
cell_slot: !type:ContainerSlot {}
- type: entity - type: entity
name: extra-bright lantern name: extra-bright lantern

View File

@@ -19,3 +19,7 @@
steps: 2 steps: 2
zeroVisible: false zeroVisible: false
- type: Appearance - type: Appearance
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []

View File

@@ -11,6 +11,10 @@
capacity: 30 capacity: 30
- type: Sprite - type: Sprite
netsync: false netsync: false
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
# Boxes # Boxes
- type: entity - type: entity

View File

@@ -11,6 +11,10 @@
capacity: 6 capacity: 6
- type: Sprite - type: Sprite
netsync: false netsync: false
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
id: SpeedLoaderMagnum id: SpeedLoaderMagnum

View File

@@ -12,6 +12,10 @@
- type: Sprite - type: Sprite
netsync: false netsync: false
sprite: Objects/Weapons/Guns/Ammunition/SpeedLoaders/Pistol/pistol_speed_loader.rsi sprite: Objects/Weapons/Guns/Ammunition/SpeedLoaders/Pistol/pistol_speed_loader.rsi
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
id: SpeedLoaderPistol id: SpeedLoaderPistol

View File

@@ -22,3 +22,7 @@
steps: 6 steps: 6
zeroVisible: false zeroVisible: false
- type: Appearance - type: Appearance
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []

View File

@@ -21,6 +21,10 @@
steps: 7 steps: 7
zeroVisible: false zeroVisible: false
- type: Appearance - type: Appearance
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
id: SpeedLoaderCap id: SpeedLoaderCap

View File

@@ -44,3 +44,7 @@
steps: 4 steps: 4
zeroVisible: true zeroVisible: true
- type: Appearance - type: Appearance
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []

View File

@@ -37,14 +37,24 @@
angularDamping: 0 angularDamping: 0
- type: Fixtures - type: Fixtures
fixtures: fixtures:
- shape: - id: projectile
shape:
!type:PhysShapeAabb !type:PhysShapeAabb
bounds: "-0.1,-0.1,0.1,0.1" bounds: "-0.1,-0.1,0.1,0.1"
hard: false hard: false
id: projectile
mask: mask:
- Impassable - Impassable
- BulletImpassable - BulletImpassable
- &flybyfixture
id: fly-by
shape: !type:PhysShapeCircle
radius: 1.5
layer:
- Impassable
- MidImpassable
- HighImpassable
- LowImpassable
hard: False
- type: Projectile - type: Projectile
impactEffect: BulletImpactEffect impactEffect: BulletImpactEffect
damage: damage:
@@ -76,6 +86,7 @@
mask: mask:
- Impassable - Impassable
- BulletImpassable - BulletImpassable
- *flybyfixture
- type: entity - type: entity
id: BaseBulletHighVelocity id: BaseBulletHighVelocity
@@ -142,6 +153,7 @@
mask: mask:
- Impassable - Impassable
- BulletImpassable - BulletImpassable
- *flybyfixture
- type: Ammo - type: Ammo
- type: StaminaDamageOnCollide - type: StaminaDamageOnCollide
damage: 30 damage: 30
@@ -178,6 +190,7 @@
mask: mask:
- Impassable - Impassable
- Opaque - Opaque
- *flybyfixture
- type: Projectile - type: Projectile
# soundHit: Waiting on serv3 # soundHit: Waiting on serv3
damage: damage:

View File

@@ -17,12 +17,17 @@
- SemiAuto - SemiAuto
soundGunshot: soundGunshot:
path: /Audio/Weapons/Guns/Gunshots/revolver.ogg path: /Audio/Weapons/Guns/Gunshots/revolver.ogg
- type: ContainerContainer
containers:
revolver-ammo: !type:Container
- type: RevolverAmmoProvider - type: RevolverAmmoProvider
whitelist: whitelist:
tags: tags:
- CartridgeMagnum - CartridgeMagnum
proto: CartridgeMagnum proto: CartridgeMagnum
capacity: 7 capacity: 7
chambers: [ True, True, True, True, True, True, True ]
ammoSlots: [ null, null, null, null, null, null, null ]
soundEject: soundEject:
path: /Audio/Weapons/Guns/MagOut/revolver_magout.ogg path: /Audio/Weapons/Guns/MagOut/revolver_magout.ogg
soundInsert: soundInsert:
@@ -46,6 +51,8 @@
sprite: Objects/Weapons/Guns/Revolvers/deckard.rsi sprite: Objects/Weapons/Guns/Revolvers/deckard.rsi
- type: RevolverAmmoProvider - type: RevolverAmmoProvider
capacity: 5 capacity: 5
chambers: [ True, True, True, True, True ]
ammoSlots: [ null, null, null, null, null ]
- type: MagazineVisuals - type: MagazineVisuals
magState: mag magState: mag
steps: 4 steps: 4
@@ -64,6 +71,8 @@
sprite: Objects/Weapons/Guns/Revolvers/inspector.rsi sprite: Objects/Weapons/Guns/Revolvers/inspector.rsi
- type: RevolverAmmoProvider - type: RevolverAmmoProvider
capacity: 6 capacity: 6
chambers: [ True, True, True, True, True, True ]
ammoSlots: [ null, null, null, null, null, null ]
- type: entity - type: entity
name: Mateba name: Mateba
@@ -75,8 +84,6 @@
sprite: Objects/Weapons/Guns/Revolvers/mateba.rsi sprite: Objects/Weapons/Guns/Revolvers/mateba.rsi
- type: Item - type: Item
sprite: Objects/Weapons/Guns/Revolvers/mateba.rsi sprite: Objects/Weapons/Guns/Revolvers/mateba.rsi
- type: RevolverAmmoProvider
capacity: 7
- type: Gun - type: Gun
soundGunshot: soundGunshot:
path: /Audio/Weapons/Guns/Gunshots/mateba.ogg path: /Audio/Weapons/Guns/Gunshots/mateba.ogg
@@ -104,5 +111,10 @@
sprite: Objects/Weapons/Guns/Revolvers/pirate_revolver.rsi sprite: Objects/Weapons/Guns/Revolvers/pirate_revolver.rsi
- type: Gun - type: Gun
fireRate: 1 fireRate: 1
- type: ContainerContainer
containers:
revolver-ammo: !type:Container
- type: RevolverAmmoProvider - type: RevolverAmmoProvider
capacity: 5 capacity: 5
chambers: [ True, True, True, True, True ]
ammoSlots: [ null, null, null, null, null ]

View File

@@ -31,6 +31,10 @@
proto: ShellShotgun proto: ShellShotgun
soundInsert: soundInsert:
path: /Audio/Weapons/Guns/MagIn/shotgun_insert.ogg path: /Audio/Weapons/Guns/MagIn/shotgun_insert.ogg
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
name: Bulldog name: Bulldog

View File

@@ -27,6 +27,10 @@
whitelist: whitelist:
tags: tags:
- CartridgeLightRifle - CartridgeLightRifle
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []
- type: entity - type: entity
name: Kardashev-Mosin name: Kardashev-Mosin

View File

@@ -27,3 +27,7 @@
capacity: 1 capacity: 1
soundInsert: soundInsert:
path: /Audio/Weapons/Guns/MagIn/shotgun_insert.ogg path: /Audio/Weapons/Guns/MagIn/shotgun_insert.ogg
- type: ContainerContainer
containers:
ballistic-ammo: !type:Container
ents: []

View File

@@ -22,6 +22,7 @@
- type: Physics - type: Physics
bodyType: Dynamic bodyType: Dynamic
fixedRotation: false fixedRotation: false
canCollide: false # most entities start asleep.
- type: Fixtures - type: Fixtures
fixtures: fixtures:
- shape: - shape:
@@ -48,4 +49,8 @@
interfaces: interfaces:
- key: enum.StorageUiKey.Key - key: enum.StorageUiKey.Key
type: StorageBoundUserInterface type: StorageBoundUserInterface
- type: ContainerContainer
containers:
storagebase: !type:Container
ents: []

View File

@@ -1,6 +1,7 @@
- type: entity - type: entity
abstract: true abstract: true
id: ReagentDispenserBase id: ReagentDispenserBase
parent: ConstructibleMachine
placement: placement:
mode: SnapgridCenter mode: SnapgridCenter
components: components:
@@ -52,3 +53,9 @@
whitelist: whitelist:
components: components:
- FitsInDispenser - FitsInDispenser
- type: ItemSlots
- type: ContainerContainer
containers:
machine_board: !type:Container
machine_parts: !type:Container
ReagentDispenser-beaker: !type:ContainerSlot

View File

@@ -12,9 +12,6 @@
emagPack: ChemDispenserEmaggedInventory emagPack: ChemDispenserEmaggedInventory
- type: ApcPowerReceiver - type: ApcPowerReceiver
- type: ExtensionCableReceiver - type: ExtensionCableReceiver
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:

View File

@@ -85,10 +85,14 @@
interfaces: interfaces:
- key: enum.WiresUiKey.Key - key: enum.WiresUiKey.Key
type: WiresBoundUserInterface type: WiresBoundUserInterface
- type: Physics
canCollide: false
- type: Airtight - type: Airtight
fixVacuum: true fixVacuum: true
airBlocked: false
noAirWhenFullyAirBlocked: true noAirWhenFullyAirBlocked: true
- type: Occluder - type: Occluder
enabled: false
- type: Construction - type: Construction
graph: Firelock graph: Firelock
node: Firelock node: Firelock
@@ -126,6 +130,7 @@
sprite: Structures/Doors/edge_door_hazard.rsi sprite: Structures/Doors/edge_door_hazard.rsi
- type: Airtight - type: Airtight
fixVacuum: true fixVacuum: true
airBlocked: false
noAirWhenFullyAirBlocked: false noAirWhenFullyAirBlocked: false
airBlockedDirection: airBlockedDirection:
- South - South
@@ -143,3 +148,5 @@
enabled: false enabled: false
- type: Door - type: Door
occludes: false occludes: false
- type: Physics
canCollide: false

View File

@@ -33,3 +33,9 @@
components: components:
- type: Door - type: Door
state: Open state: Open
- type: Occluder
enabled: false
- type: Physics
canCollide: false
- type: Airtight
airBlocked: false

View File

@@ -66,6 +66,11 @@
key: walls key: walls
mode: NoSprite mode: NoSprite
- type: DoorSignalControl - type: DoorSignalControl
- type: SignalReceiver
inputs:
Open: []
Close: []
Toggle: []
- type: InteractionPopup - type: InteractionPopup
interactSuccessString: comp-window-knock interactSuccessString: comp-window-knock
messagePerceivedByOthers: comp-window-knock messagePerceivedByOthers: comp-window-knock
@@ -127,6 +132,12 @@
- type: Construction - type: Construction
graph: Shutters graph: Shutters
node: ShuttersRadiation node: ShuttersRadiation
- type: Occluder
enabled: false
- type: Physics
canCollide: false
- type: Airtight
airBlocked: false
- type: entity - type: entity
id: ShuttersWindow id: ShuttersWindow
@@ -154,6 +165,10 @@
- type: Construction - type: Construction
graph: Shutters graph: Shutters
node: ShuttersWindow node: ShuttersWindow
- type: Physics
canCollide: false
- type: Airtight
airBlocked: false
# Frame for construction # Frame for construction
- type: entity - type: entity

View File

@@ -25,6 +25,9 @@
- type: PottedPlantHide - type: PottedPlantHide
- type: SecretStash - type: SecretStash
secretPartName: the plant secretPartName: the plant
- type: ContainerContainer
containers:
stash: !type:ContainerSlot {}
- type: Pullable - type: Pullable
- type: Damageable - type: Damageable
damageContainer: Inorganic # The pot. Not the plant. Or is it plastic? damageContainer: Inorganic # The pot. Not the plant. Or is it plastic?

View File

@@ -18,6 +18,9 @@
- type: Toilet - type: Toilet
- type: SecretStash - type: SecretStash
secretPartName: the toilet cistern secretPartName: the toilet cistern
- type: ContainerContainer
containers:
stash: !type:ContainerSlot {}
- type: SolutionContainerManager - type: SolutionContainerManager
solutions: solutions:
toilet: toilet:
@@ -28,6 +31,7 @@
graph: Toilet graph: Toilet
node: toilet node: toilet
- type: Appearance - type: Appearance
- type: entity - type: entity
id: ToiletDirtyWater id: ToiletDirtyWater
parent: ToiletEmpty parent: ToiletEmpty

View File

@@ -49,3 +49,7 @@
- type: EmitSoundOnUIOpen - type: EmitSoundOnUIOpen
sound: sound:
collection: Keyboard collection: Keyboard
- type: ContainerContainer
containers:
board: !type:Container
ents: []

View File

@@ -382,6 +382,12 @@
- type: Tag - type: Tag
tags: tags:
- EmagImmune - EmagImmune
- type: ItemSlots
- type: ContainerContainer
containers:
board: !type:Container
IdCardConsole-privilegedId: !type:ContainerSlot
IdCardConsole-targetId: !type:ContainerSlot
- type: entity - type: entity
parent: BaseComputer parent: BaseComputer

View File

@@ -43,3 +43,19 @@
- type: ApcPowerReceiver - type: ApcPowerReceiver
powerLoad: 1000 powerLoad: 1000
- type: ExtensionCableReceiver - type: ExtensionCableReceiver
- type: entity
abstract: true
id: ConstructibleMachine
components:
- type: Machine
- type: ContainerContainer
containers:
machine_board: !type:Container
machine_parts: !type:Container
- type: Construction
graph: Machine
node: machine
containers:
- machine_parts
- machine_board

View File

@@ -1,6 +1,6 @@
- type: entity - type: entity
id: chem_master id: chem_master
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
name: ChemMaster 4000 name: ChemMaster 4000
description: An industrial grade chemical manipulator with pill and bottle production included. description: An industrial grade chemical manipulator with pill and bottle production included.
placement: placement:
@@ -60,7 +60,12 @@
- type: Machine - type: Machine
board: ChemMasterMachineCircuitboard board: ChemMasterMachineCircuitboard
- type: MaterialStorage - type: MaterialStorage
- type: Construction - type: ContainerContainer
graph: Machine containers:
node: machine machine_board: !type:Container
machine_parts: !type:Container
ChemMaster-beaker: !type:ContainerSlot
- type: ItemSlots
- type: SolutionContainerManager
solutions:
buffer: {}

View File

@@ -1,6 +1,6 @@
- type: entity - type: entity
id: CloningPod id: CloningPod
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
name: cloning pod name: cloning pod
description: A Cloning Pod. 50% reliable. description: A Cloning Pod. 50% reliable.
components: components:
@@ -25,9 +25,6 @@
- MachineMask - MachineMask
layer: layer:
- MachineLayer - MachineLayer
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:

View File

@@ -1,5 +1,5 @@
- type: entity - type: entity
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
id: Autolathe id: Autolathe
name: autolathe name: autolathe
description: It produces items using metal and glass. description: It produces items using metal and glass.
@@ -34,9 +34,6 @@
- MachineMask - MachineMask
layer: layer:
- MachineLayer - MachineLayer
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:
@@ -86,7 +83,7 @@
- Ingot - Ingot
- type: entity - type: entity
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
id: Protolathe id: Protolathe
name: protolathe name: protolathe
description: Converts raw materials into useful objects. description: Converts raw materials into useful objects.
@@ -122,9 +119,6 @@
layer: layer:
- MachineLayer - MachineLayer
- type: ResearchClient - type: ResearchClient
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:

View File

@@ -1,6 +1,6 @@
- type: entity - type: entity
id: MedicalScanner id: MedicalScanner
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
name: medical scanner name: medical scanner
description: A bulky medical scanner. description: A bulky medical scanner.
components: components:
@@ -28,9 +28,6 @@
- MachineMask - MachineMask
layer: layer:
- MachineLayer - MachineLayer
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:

View File

@@ -42,3 +42,8 @@
drawdepth: SmallObjects drawdepth: SmallObjects
- type: ApcPowerReceiver - type: ApcPowerReceiver
powerLoad: 300 powerLoad: 300
- type: ItemSlots
- type: ContainerContainer
containers:
ReagentGrinder-reagentContainerContainer: !type:ContainerSlot
ReagentGrinder-entityContainerContainer: !type:Container

View File

@@ -1,6 +1,6 @@
- type: entity - type: entity
abstract: true abstract: true
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
id: SurveillanceCameraRouterBase id: SurveillanceCameraRouterBase
name: camera router name: camera router
description: A surveillance camera router. It routes. Perhaps. description: A surveillance camera router. It routes. Perhaps.
@@ -14,9 +14,6 @@
interfaces: interfaces:
- key: enum.SurveillanceCameraSetupUiKey.Router - key: enum.SurveillanceCameraSetupUiKey.Router
type: SurveillanceCameraSetupBoundUi type: SurveillanceCameraSetupBoundUi
- type: Construction
graph: Machine
node: machine
- type: Machine - type: Machine
board: SurveillanceCameraRouterCircuitboard board: SurveillanceCameraRouterCircuitboard
- type: Sprite - type: Sprite
@@ -105,7 +102,7 @@
subnetFrequency: SurveillanceCameraGeneral subnetFrequency: SurveillanceCameraGeneral
- type: entity - type: entity
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
id: SurveillanceCameraWirelessRouterBase id: SurveillanceCameraWirelessRouterBase
name: wireless camera router name: wireless camera router
description: A wireless surveillance camera router. It routes. Perhaps. description: A wireless surveillance camera router. It routes. Perhaps.
@@ -120,9 +117,6 @@
interfaces: interfaces:
- key: enum.SurveillanceCameraSetupUiKey.Router - key: enum.SurveillanceCameraSetupUiKey.Router
type: SurveillanceCameraSetupBoundUi type: SurveillanceCameraSetupBoundUi
- type: Construction
graph: Machine
node: machine
- type: Machine - type: Machine
board: SurveillanceCameraWirelessRouterCircuitboard board: SurveillanceCameraWirelessRouterCircuitboard
- type: Sprite - type: Sprite

View File

@@ -1,13 +1,10 @@
- type: entity - type: entity
abstract: true abstract: true
parent: BaseStructureDynamic parent: [ BaseStructureDynamic, ConstructibleMachine ]
id: SurveillanceWirelessCameraBase id: SurveillanceWirelessCameraBase
name: wireless camera name: wireless camera
description: A camera. It's watching you. Kinda. description: A camera. It's watching you. Kinda.
components: components:
- type: Construction
graph: Machine
node: machine
- type: InteractionOutline - type: InteractionOutline
- type: Eye - type: Eye
- type: WirelessNetworkConnection - type: WirelessNetworkConnection

View File

@@ -9,6 +9,7 @@
- type: Clickable - type: Clickable
- type: InteractionOutline - type: InteractionOutline
- type: Physics - type: Physics
- type: Fixtures
- type: Transform - type: Transform
anchored: true anchored: true
- type: Damageable - type: Damageable

View File

@@ -15,6 +15,7 @@
damageContainer: Inorganic damageContainer: Inorganic
damageModifierSet: Metallic damageModifierSet: Metallic
- type: SubFloorHide - type: SubFloorHide
- type: CollideOnAnchor
- type: PipeAppearance - type: PipeAppearance
- type: Anchorable - type: Anchorable
- type: Rotatable - type: Rotatable

View File

@@ -15,6 +15,7 @@
!type:PipeNode !type:PipeNode
nodeGroupID: Pipe nodeGroupID: Pipe
pipeDirection: South pipeDirection: South
- type: CollideOnAnchor
- type: entity - type: entity
parent: GasUnaryBase parent: GasUnaryBase
@@ -184,7 +185,7 @@
- enum.LightLayers.Unshaded - enum.LightLayers.Unshaded
- type: entity - type: entity
parent: BaseMachinePowered parent: [ BaseMachinePowered, ConstructibleMachine ]
id: BaseGasThermoMachine id: BaseGasThermoMachine
name: thermomachine name: thermomachine
abstract: true abstract: true
@@ -207,9 +208,6 @@
- type: ActivatableUI - type: ActivatableUI
inHandsOnly: false inHandsOnly: false
key: enum.ThermomachineUiKey.Key key: enum.ThermomachineUiKey.Key
- type: Construction
graph: Machine
node: machine
- type: Wires - type: Wires
BoardName: "Thermomachine" BoardName: "Thermomachine"
LayoutId: Thermomachine LayoutId: Thermomachine
@@ -244,10 +242,6 @@
mode: Freezer mode: Freezer
- type: Machine - type: Machine
board: ThermomachineFreezerMachineCircuitBoard board: ThermomachineFreezerMachineCircuitBoard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container
- type: entity - type: entity
parent: BaseGasThermoMachine parent: BaseGasThermoMachine
@@ -273,7 +267,3 @@
mode: Heater mode: Heater
- type: Machine - type: Machine
board: ThermomachineHeaterMachineCircuitBoard board: ThermomachineHeaterMachineCircuitBoard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container

View File

@@ -49,6 +49,11 @@
node: broken node: broken
- type: Rotatable - type: Rotatable
- type: Pullable - type: Pullable
- type: CollideOnAnchor
- type: ContainerContainer
containers:
disposal-tube: !type:Container
ents: []
- type: entity - type: entity
id: DisposalHolder id: DisposalHolder

View File

@@ -70,6 +70,10 @@
interfaces: interfaces:
- key: enum.DisposalUnitUiKey.Key - key: enum.DisposalUnitUiKey.Key
type: DisposalUnitBoundUserInterface type: DisposalUnitBoundUserInterface
- type: ContainerContainer
containers:
disposal-unit: !type:Container
ents: []
- type: entity - type: entity
id: DisposalUnit id: DisposalUnit

View File

@@ -1,6 +1,7 @@
- type: entity - type: entity
id: Emitter id: Emitter
name: emitter name: emitter
parent: ConstructibleMachine
description: A heavy duty industrial laser. Shoots non-stop when turned on. description: A heavy duty industrial laser. Shoots non-stop when turned on.
placement: placement:
mode: SnapgridCenter mode: SnapgridCenter
@@ -70,8 +71,5 @@
locked: false locked: false
- type: AccessReader - type: AccessReader
access: [[ "Engineering" ]] access: [[ "Engineering" ]]
- type: Construction
graph: Machine
node: machine
- type: Machine - type: Machine
board: EmitterCircuitboard board: EmitterCircuitboard

View File

@@ -151,7 +151,7 @@
supplyRate: 3000 supplyRate: 3000
- type: entity - type: entity
parent: BaseGenerator parent: [ BaseGenerator, ConstructibleMachine ]
id: GeneratorPlasma id: GeneratorPlasma
suffix: Plasma, 5kW suffix: Plasma, 5kW
components: components:
@@ -160,21 +160,14 @@
- type: Sprite - type: Sprite
sprite: Structures/Power/Generation/portable_generator.rsi sprite: Structures/Power/Generation/portable_generator.rsi
state: portgen0_1 state: portgen0_1
- type: Construction
graph: Machine
node: machine
- type: Wires - type: Wires
BoardName: "GeneratorPlasma" BoardName: "GeneratorPlasma"
LayoutId: GeneratorPlasma LayoutId: GeneratorPlasma
- type: Machine - type: Machine
board: GeneratorPlasmaMachineCircuitboard board: GeneratorPlasmaMachineCircuitboard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container
- type: entity - type: entity
parent: BaseGenerator parent: [ BaseGenerator, ConstructibleMachine ]
id: GeneratorUranium id: GeneratorUranium
suffix: Uranium, 15kW suffix: Uranium, 15kW
components: components:
@@ -183,18 +176,11 @@
- type: Sprite - type: Sprite
sprite: Structures/Power/Generation/portable_generator.rsi sprite: Structures/Power/Generation/portable_generator.rsi
state: portgen1_1 state: portgen1_1
- type: Construction
graph: Machine
node: machine
- type: Wires - type: Wires
BoardName: "GeneratorUranium" BoardName: "GeneratorUranium"
LayoutId: GeneratorUranium LayoutId: GeneratorUranium
- type: Machine - type: Machine
board: GeneratorUraniumMachineCircuitboard board: GeneratorUraniumMachineCircuitboard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container
- type: entity - type: entity
parent: BaseGeneratorWallmount parent: BaseGeneratorWallmount

View File

@@ -26,6 +26,7 @@
- !type:DoActsBehavior - !type:DoActsBehavior
acts: ["Destruction"] acts: ["Destruction"]
- type: SubFloorHide - type: SubFloorHide
- type: CollideOnAnchor
- type: AmbientSound - type: AmbientSound
enabled: false # Leaving as false because 90% of them are set to this. enabled: false # Leaving as false because 90% of them are set to this.
- type: Appearance - type: Appearance

View File

@@ -38,6 +38,10 @@
- MachineMask - MachineMask
layer: layer:
- HighImpassable - HighImpassable
- type: ItemSlots
- type: ContainerContainer
containers:
charger-slot: !type:ContainerSlot
- type: entity - type: entity
name: recharger name: recharger

View File

@@ -2,7 +2,7 @@
- type: entity - type: entity
abstract: true abstract: true
id: BaseSMES id: BaseSMES
parent: BaseMachine parent: [ BaseMachine, ConstructibleMachine ]
name: SMES name: SMES
description: A high-capacity superconducting magnetic energy storage (SMES) unit. description: A high-capacity superconducting magnetic energy storage (SMES) unit.
placement: placement:
@@ -51,18 +51,11 @@
energy: 1.6 energy: 1.6
color: "#c9c042" color: "#c9c042"
castShadows: false castShadows: false
- type: Construction
graph: Machine
node: machine
- type: Wires - type: Wires
BoardName: "SMES" BoardName: "SMES"
LayoutId: SMES LayoutId: SMES
- type: Machine - type: Machine
board: SMESMachineCircuitboard board: SMESMachineCircuitboard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container
- type: StationInfiniteBatteryTarget - type: StationInfiniteBatteryTarget
# SMES' in use # SMES' in use

View File

@@ -2,7 +2,7 @@
- type: entity - type: entity
abstract: true abstract: true
id: BaseSubstation id: BaseSubstation
parent: BaseMachine parent: [ BaseMachine, ConstructibleMachine ]
name: substation name: substation
description: Reduces the voltage of electricity put into it. description: Reduces the voltage of electricity put into it.
placement: placement:
@@ -43,9 +43,6 @@
maxChargeRate: 5000 maxChargeRate: 5000
supplyRampTolerance: 5000 supplyRampTolerance: 5000
supplyRampRate: 1000 supplyRampRate: 1000
- type: Construction
graph: Machine
node: machine
- type: Destructible - type: Destructible
thresholds: thresholds:
- trigger: - trigger:
@@ -73,10 +70,6 @@
LayoutId: Substation LayoutId: Substation
- type: Machine - type: Machine
board: SubstationMachineCircuitboard board: SubstationMachineCircuitboard
- type: ContainerContainer
containers:
machine_parts: !type:Container
machine_board: !type:Container
- type: StationInfiniteBatteryTarget - type: StationInfiniteBatteryTarget
# Compact Wall Substation Base # Compact Wall Substation Base

View File

@@ -34,6 +34,7 @@
capacity: 500 capacity: 500
- type: Weldable - type: Weldable
- type: PlaceableSurface - type: PlaceableSurface
isPlaceable: false # defaults to closed.
- type: Damageable - type: Damageable
damageContainer: Inorganic damageContainer: Inorganic
damageModifierSet: Metallic damageModifierSet: Metallic
@@ -61,6 +62,7 @@
containers: containers:
entity_storage: !type:Container entity_storage: !type:Container
paper_label: !type:ContainerSlot paper_label: !type:ContainerSlot
- type: ItemSlots
- type: entity - type: entity
id: CrateBaseSecure id: CrateBaseSecure
@@ -97,6 +99,7 @@
capacity: 500 capacity: 500
- type: Weldable - type: Weldable
- type: PlaceableSurface - type: PlaceableSurface
isPlaceable: false # defaults to closed.
- type: Damageable - type: Damageable
damageContainer: Inorganic damageContainer: Inorganic
damageModifierSet: StrongMetallic damageModifierSet: StrongMetallic
@@ -123,3 +126,10 @@
- type: Construction - type: Construction
graph: CrateSecure graph: CrateSecure
node: cratesecure node: cratesecure
containers:
- entity_storage
- type: ContainerContainer
containers:
entity_storage: !type:Container
paper_label: !type:ContainerSlot
- type: ItemSlots

View File

@@ -23,7 +23,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CratePlastic id: CratePlastic
@@ -50,6 +51,8 @@
- type: Construction - type: Construction
graph: CratePlastic graph: CratePlastic
node: crateplastic node: crateplastic
containers:
- entity_storage
- type: entity - type: entity
id: CrateFreezer id: CrateFreezer
@@ -76,6 +79,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: AntiRottingContainer - type: AntiRottingContainer
- type: entity - type: entity
@@ -103,6 +108,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateMedical id: CrateMedical
@@ -129,6 +136,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateRadiation id: CrateRadiation
@@ -156,6 +165,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateInternals id: CrateInternals
@@ -182,6 +193,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateElectrical id: CrateElectrical
@@ -208,6 +221,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateEngineering id: CrateEngineering
@@ -234,6 +249,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateScience id: CrateScience
@@ -260,6 +277,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
- type: entity - type: entity
id: CrateSurgery id: CrateSurgery
@@ -286,6 +305,8 @@
- type: Construction - type: Construction
graph: CrateGenericSteel graph: CrateGenericSteel
node: crategenericsteel node: crategenericsteel
containers:
- entity_storage
# Secure Crates # Secure Crates
@@ -629,4 +650,6 @@
- type: Construction - type: Construction
graph: CrateLivestock graph: CrateLivestock
node: cratelivestock node: cratelivestock
containers:
- entity_storage

Some files were not shown because too many files have changed in this diff Show More