Migrate all mechs to PartAssembly and remove legacy MechAssemblySystem (#39027)

* Removed the old MechAssembly system and component.
Converted all mechs to use the unified PartAssembly system.
Removed dismantling mechs during assembly logic to simplify the code.

* Delete Chassis via migration
This commit is contained in:
AndrewFenriz
2025-08-31 15:54:45 +03:00
committed by GitHub
parent 487c280f1c
commit 0e23e4537f
9 changed files with 71 additions and 220 deletions

View File

@@ -1,50 +0,0 @@
using Content.Shared.Storage.Components;
using Content.Shared.Tag;
using Content.Shared.Tools;
using Robust.Shared.Containers;
using Robust.Shared.Prototypes;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype.Dictionary;
namespace Content.Server.Mech.Components;
/// <summary>
/// A component used to create a mech chassis
/// after the correct parts have been placed inside
/// of it.
/// </summary>
/// <remarks>
/// The actual visualization of the parts being inserted is
/// done via <see cref="ItemMapperComponent"/>
/// </remarks>
[RegisterComponent]
public sealed partial class MechAssemblyComponent : Component
{
/// <summary>
/// The parts needed to be placed within the assembly,
/// stored as a tag and a bool tracking whether or not
/// they're present.
/// </summary>
[DataField("requiredParts", required: true, customTypeSerializer: typeof(PrototypeIdDictionarySerializer<bool, TagPrototype>))]
public Dictionary<string, bool> RequiredParts = new();
/// <summary>
/// The prototype spawned when the assembly is finished
/// </summary>
[DataField("finishedPrototype", required: true, customTypeSerializer: typeof(PrototypeIdSerializer<EntityPrototype>))]
public string FinishedPrototype = default!;
/// <summary>
/// The container that stores all of the parts when
/// they're being assembled.
/// </summary>
[ViewVariables]
public Container PartsContainer = default!;
/// <summary>
/// The quality of tool needed to remove all the parts
/// from the parts container.
/// </summary>
[DataField("qualityNeeded", customTypeSerializer: typeof(PrototypeIdSerializer<ToolQualityPrototype>))]
public string QualityNeeded = "Prying";
}

View File

@@ -1,67 +0,0 @@
using Content.Server.Mech.Components;
using Content.Shared.Interaction;
using Content.Shared.Tag;
using Content.Shared.Tools.Components;
using Content.Shared.Tools.Systems;
using Robust.Server.Containers;
using Robust.Shared.Containers;
namespace Content.Server.Mech.Systems;
/// <summary>
/// Handles <see cref="MechAssemblyComponent"/> and the insertion
/// and removal of parts from the assembly.
/// </summary>
public sealed class MechAssemblySystem : EntitySystem
{
[Dependency] private readonly ContainerSystem _container = default!;
[Dependency] private readonly TagSystem _tag = default!;
[Dependency] private readonly SharedToolSystem _toolSystem = default!;
/// <inheritdoc/>
public override void Initialize()
{
SubscribeLocalEvent<MechAssemblyComponent, ComponentInit>(OnInit);
SubscribeLocalEvent<MechAssemblyComponent, InteractUsingEvent>(OnInteractUsing);
}
private void OnInit(EntityUid uid, MechAssemblyComponent component, ComponentInit args)
{
component.PartsContainer = _container.EnsureContainer<Container>(uid, "mech-assembly-container");
}
private void OnInteractUsing(EntityUid uid, MechAssemblyComponent component, InteractUsingEvent args)
{
if (_toolSystem.HasQuality(args.Used, component.QualityNeeded))
{
foreach (var tag in component.RequiredParts.Keys)
{
component.RequiredParts[tag] = false;
}
_container.EmptyContainer(component.PartsContainer);
return;
}
if (!TryComp<TagComponent>(args.Used, out var tagComp))
return;
foreach (var (tag, val) in component.RequiredParts)
{
if (!val && _tag.HasTag(tagComp, tag))
{
component.RequiredParts[tag] = true;
_container.Insert(args.Used, component.PartsContainer);
break;
}
}
//check to see if we have all the parts
foreach (var val in component.RequiredParts.Values)
{
if (!val)
return;
}
Spawn(component.FinishedPrototype, Transform(uid).Coordinates);
Del(uid);
}
}

View File

@@ -18,4 +18,6 @@ mech-slot-display = Open Slots: {$amount}
mech-no-enter = You cannot pilot this.
mech-eject-pilot-alert = {$user} is pulling the pilot out of the {$item}!
mech-eject-pilot-alert = {$user} is pulling the pilot out of the {$item}!
mech-construction-guide-string = All mech parts must be attached to the harness.

View File

@@ -75,16 +75,23 @@
- type: ContainerContainer
containers:
mech-assembly-container: !type:Container
- type: MechAssembly
finishedPrototype: RipleyChassis
requiredParts:
RipleyLArm: false
RipleyRArm: false
RipleyLLeg: false
RipleyRLeg: false
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: ripley
- type: Sprite
state: ripley_harness+o
noRot: true
- type: PartAssembly
parts:
Ripley:
- RipleyLArm
- RipleyRArm
- RipleyLLeg
- RipleyRLeg
containerId: mech-assembly-container
- type: Construction
graph: Ripley
node: start
- type: entity
parent: BaseRipleyPartItem
@@ -134,26 +141,6 @@
tags:
- RipleyRArm
- type: entity
id: RipleyChassis
parent: BaseRipleyPart
name: ripley chassis
description: An in-progress construction of the Ripley APLU mech.
components:
- type: Appearance
- type: ContainerContainer
containers:
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: ripley
- type: Sprite
noRot: true
state: ripley0
- type: Construction
graph: Ripley
node: start
defaultTarget: ripley
# H.O.N.K.
- type: entity
@@ -203,16 +190,23 @@
- type: ContainerContainer
containers:
mech-assembly-container: !type:Container
- type: MechAssembly
finishedPrototype: HonkerChassis
requiredParts:
HonkerLArm: false
HonkerRArm: false
HonkerLLeg: false
HonkerRLeg: false
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: honker
- type: Sprite
state: honker_harness+o
noRot: true
- type: PartAssembly
parts:
Honker:
- HonkerLArm
- HonkerRArm
- HonkerLLeg
- HonkerRLeg
containerId: mech-assembly-container
- type: Construction
graph: Honker
node: start
- type: entity
parent: BaseHonkerPartItem
@@ -262,26 +256,6 @@
tags:
- HonkerRArm
- type: entity
id: HonkerChassis
parent: BaseHonkerPart
name: H.O.N.K. chassis
description: An in-progress construction of a H.O.N.K. mech. Contains chuckle unit, bananium core and honk support systems.
components:
- type: Appearance
- type: ContainerContainer
containers:
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: honker
- type: Sprite
noRot: true
state: honker0
- type: Construction
graph: Honker
node: start
defaultTarget: honker
# H.A.M.T.R.
- type: entity
@@ -331,16 +305,23 @@
- type: ContainerContainer
containers:
mech-assembly-container: !type:Container
- type: MechAssembly
finishedPrototype: HamtrChassis
requiredParts:
HamtrLArm: false
HamtrRArm: false
HamtrLLeg: false
HamtrRLeg: false
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: hamtr
- type: Sprite
state: hamtr_harness+o
noRot: true
- type: PartAssembly
parts:
Hamtr:
- HamtrLArm
- HamtrRArm
- HamtrLLeg
- HamtrRLeg
containerId: mech-assembly-container
- type: Construction
graph: Hamtr
node: start
- type: entity
parent: BaseHamtrPartItem
@@ -390,26 +371,6 @@
tags:
- HamtrRArm
- type: entity
id: HamtrChassis
parent: BaseHamtrPart
name: HAMTR chassis
description: An in-progress construction of the HAMTR mech.
components:
- type: Appearance
- type: ContainerContainer
containers:
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: hamtr
- type: Sprite
noRot: true
state: hamtr0
- type: Construction
graph: Hamtr
node: start
defaultTarget: hamtr
# Vim!!!!!!
- type: entity
@@ -455,30 +416,17 @@
- type: ContainerContainer
containers:
mech-assembly-container: !type:Container
- type: MechAssembly
finishedPrototype: VimChassis
requiredParts:
HelmetEVA: false
BorgLeg: false
battery-container: !type:Container
- type: PartAssembly
parts:
Vim:
- HelmetEVA
- BorgLeg
- BorgLeg
containerId: mech-assembly-container
- type: Sprite
state: harness
noRot: true
- type: entity
id: VimChassis
parent: BaseVimPart
name: vim chassis
description: An in-progress construction of the Vim exosuit.
components:
- type: Appearance
- type: ContainerContainer
containers:
battery-container: !type:Container
- type: MechAssemblyVisuals
statePrefix: vim
- type: Sprite
noRot: true
state: vim0
- type: Construction
graph: Vim
node: start

View File

@@ -6,6 +6,9 @@
edges:
- to: hamtr
steps:
- assemblyId: Hamtr
guideString: mech-construction-guide-string
- tool: Anchoring
doAfter: 1
completed:

View File

@@ -6,6 +6,9 @@
edges:
- to: honker
steps:
- assemblyId: Honker
guideString: mech-construction-guide-string
- tool: Honking
doAfter: 1
completed:

View File

@@ -6,6 +6,9 @@
edges:
- to: ripley
steps:
- assemblyId: Ripley
guideString: mech-construction-guide-string
- tool: Anchoring
doAfter: 1
completed:

View File

@@ -6,6 +6,9 @@
edges:
- to: vim
steps:
- assemblyId: Vim
guideString: mech-construction-guide-string
- tag: VoiceTrigger
name: construction-graph-tag-voice-trigger
icon:

View File

@@ -701,6 +701,12 @@ BarSignWhiskeyEchoesAlignTile: BarSignWhiskeyEchoes
# 2025-06-21
ClothingNeckHeadphones: ClothingMultipleHeadphones
# 2025-07-17
RipleyChassis: null
HonkerChassis: null
HamtrChassis: null
VimChassis: null
# 2025-08-01
FoodDonutJellySlugcat: FoodDonutJellyScurret