--- /dev/null
+using Robust.Shared.Audio;
+using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom;
+
+namespace Content.Server.IgnitionSource;
+
+/// <summary>
+/// Ignites for a certain length of time when triggered.
+/// Requires <see cref="IgnitionSourceComponent"/> along with triggering components.
+/// </summary>
+[RegisterComponent, Access(typeof(IgniteOnTriggerSystem))]
+public sealed partial class IgniteOnTriggerComponent : Component
+{
+ /// <summary>
+ /// Once ignited, the time it will unignite at.
+ /// </summary>
+ [DataField(customTypeSerializer: typeof(TimeOffsetSerializer)), ViewVariables(VVAccess.ReadWrite)]
+ public TimeSpan IgnitedUntil = TimeSpan.Zero;
+
+ /// <summary>
+ /// How long the ignition source is active for after triggering.
+ /// </summary>
+ [DataField, ViewVariables(VVAccess.ReadWrite)]
+ public TimeSpan IgnitedTime = TimeSpan.FromSeconds(0.5);
+
+ /// <summary>
+ /// Sound to play when igniting.
+ /// </summary>
+ [DataField]
+ public SoundSpecifier IgniteSound = new SoundCollectionSpecifier("WelderOn");
+}
--- /dev/null
+using Content.Server.Explosion.EntitySystems;
+using Content.Shared.Timing;
+using Robust.Shared.Audio;
+using Robust.Shared.Timing;
+
+namespace Content.Server.IgnitionSource;
+
+/// <summary>
+/// Handles igniting when triggered and stopping ignition after the delay.
+/// </summary>
+public sealed class IgniteOnTriggerSystem : EntitySystem
+{
+ [Dependency] private readonly IGameTiming _timing = default!;
+ [Dependency] private readonly IgnitionSourceSystem _source = default!;
+ [Dependency] private readonly SharedAudioSystem _audio = default!;
+ [Dependency] private readonly UseDelaySystem _useDelay = default!;
+
+ public override void Initialize()
+ {
+ base.Initialize();
+
+ SubscribeLocalEvent<IgniteOnTriggerComponent, TriggerEvent>(OnTrigger);
+ }
+
+ public override void Update(float deltaTime)
+ {
+ base.Update(deltaTime);
+
+ var query = EntityQueryEnumerator<IgniteOnTriggerComponent, IgnitionSourceComponent>();
+ while (query.MoveNext(out var uid, out var comp, out var source))
+ {
+ if (!source.Ignited)
+ continue;
+
+ if (_timing.CurTime < comp.IgnitedUntil)
+ continue;
+
+ _source.SetIgnited(uid, false, source);
+ }
+ }
+
+ private void OnTrigger(EntityUid uid, IgniteOnTriggerComponent comp, TriggerEvent args)
+ {
+ // prevent spamming sound and ignition
+ TryComp<UseDelayComponent>(uid, out var delay);
+ if (_useDelay.ActiveDelay(uid, delay))
+ return;
+
+ _source.SetIgnited(uid);
+ _audio.PlayPvs(comp.IgniteSound, uid);
+
+ _useDelay.BeginDelay(uid, delay);
+ comp.IgnitedUntil = _timing.CurTime + comp.IgnitedTime;
+ }
+}
private void OnIsHot(EntityUid uid, IgnitionSourceComponent component, IsHotEvent args)
{
- SetIgnited(uid,component,args.IsHot);
+ SetIgnited(uid, args.IsHot, component);
}
- private void SetIgnited(EntityUid uid, IgnitionSourceComponent component, bool newState)
+ /// <summary>
+ /// Simply sets the ignited field to the ignited param.
+ /// </summary>
+ public void SetIgnited(EntityUid uid, bool ignited = true, IgnitionSourceComponent? comp = null)
{
- component.Ignited = newState;
+ if (!Resolve(uid, ref comp))
+ return;
+
+ comp.Ignited = ignited;
}
public override void Update(float frameTime)
Flash: 4
ProximitySensor: 3
RemoteSignaller: 3
+ Igniter: 3 # its more ordnance but yeah
HandheldHealthAnalyzer: 3
Scalpel: 2
SawElectric: 2
id: VendomatInventory
startingInventory:
RemoteSignaller: 1
+ Igniter: 2
Wirecutter: 1
CableApcStack: 2
FlashlightLantern: 2
PowerCellSmallPrinted: 3
MatterBinStockPart: 4
CapacitorStockPart: 4
- MicroManipulatorStockPart: 4
\ No newline at end of file
+ MicroManipulatorStockPart: 4
--- /dev/null
+- type: entity
+ parent: BaseItem
+ id: Igniter
+ name: igniter
+ description: Creates a spark when activated by a signal.
+ components:
+ - type: Sprite
+ sprite: Objects/Devices/igniter.rsi
+ state: icon
+ - type: IgnitionSource
+ temperature: 800
+ - type: IgniteOnTrigger
+ - type: TriggerOnSignal
+ - type: DeviceNetwork
+ deviceNetId: Wireless
+ receiveFrequencyId: BasicDevice
+ - type: WirelessNetworkConnection
+ range: 200
+ - type: DeviceLinkSink
+ ports:
+ - Trigger
+ - type: UseDelay # prevent sound spam
+ - type: Tag
+ tags:
+ - Igniter
- Signaller
- SignalTrigger
- VoiceTrigger
+ - Igniter
- PowerCellMedium
- PowerCellHigh
- WeaponPistolCHIMP
Steel: 300
Plastic: 200
+- type: latheRecipe
+ id: Igniter
+ result: Igniter
+ completetime: 2
+ materials:
+ Steel: 300
+ Plastic: 100
+ Glass: 100
+
- type: latheRecipe
id: ChemicalPayload
result: ChemicalPayload
- TimerTrigger
- FlashPayload
- ExplosivePayload
+ - Igniter
- type: technology
id: WeaponizedLaserManipulation
- type: Tag
id: Hotsauce
+- type: Tag
+ id: Igniter
+
- type: Tag #Drop this innate tool instead of deleting it.
id: InnateDontDelete
--- /dev/null
+{
+ "version": 1,
+ "license": "CC-BY-SA-3.0",
+ "copyright": "Taken from tgstation at https://github.com/tgstation/tgstation/blob/9a401d19045574f3ea7f2cf3feebf65989903ccc/icons/obj/assemblies/new_assemblies.dmi",
+ "size": {
+ "x": 32,
+ "y": 32
+ },
+ "states": [
+ {
+ "name": "icon"
+ }
+ ]
+}