diff --git a/Content.Server/Containers/ThrowInsertContainerComponent.cs b/Content.Server/Containers/ThrowInsertContainerComponent.cs new file mode 100644 index 0000000000..8aa2927773 --- /dev/null +++ b/Content.Server/Containers/ThrowInsertContainerComponent.cs @@ -0,0 +1,35 @@ +using Robust.Shared.Audio; + +namespace Content.Server.Containers; + +/// +/// Allows objects to fall inside the Container when thrown +/// +[RegisterComponent] +[Access(typeof(ThrowInsertContainerSystem))] +public sealed partial class ThrowInsertContainerComponent : Component +{ + [DataField(required: true)] + public string? ContainerId; + + /// + /// Throw chance of hitting into the container + /// + [DataField] + public float Probability = 0.75f; + + /// + /// Sound played when an object is throw into the container. + /// + [DataField] + public SoundSpecifier? InsertSound = new SoundPathSpecifier("/Audio/Effects/trashbag1.ogg"); + + /// + /// Sound played when an item is thrown and misses the container. + /// + [DataField] + public SoundSpecifier? MissSound = new SoundPathSpecifier("/Audio/Effects/thudswoosh.ogg"); + + [DataField] + public LocId MissLocString = "container-thrown-missed"; +} diff --git a/Content.Server/Containers/ThrowInsertContainerSystem.cs b/Content.Server/Containers/ThrowInsertContainerSystem.cs new file mode 100644 index 0000000000..781b808ef9 --- /dev/null +++ b/Content.Server/Containers/ThrowInsertContainerSystem.cs @@ -0,0 +1,53 @@ +using Content.Server.Administration.Logs; +using Content.Shared.Database; +using Content.Shared.Popups; +using Content.Shared.Throwing; +using Robust.Shared.Audio.Systems; +using Robust.Shared.Containers; +using Robust.Shared.Random; + +namespace Content.Server.Containers; + +public sealed class ThrowInsertContainerSystem : EntitySystem +{ + [Dependency] private readonly IAdminLogManager _adminLogger = default!; + [Dependency] private readonly SharedAudioSystem _audio = default!; + [Dependency] private readonly SharedContainerSystem _containerSystem = default!; + [Dependency] private readonly SharedPopupSystem _popup = default!; + [Dependency] private readonly IRobustRandom _random = default!; + + public override void Initialize() + { + base.Initialize(); + + SubscribeLocalEvent(OnThrowCollide); + } + + private void OnThrowCollide(Entity ent, ref ThrowHitByEvent args) + { + if (ent.Comp.ContainerId == null) + return; + + var container = _containerSystem.GetContainer(ent, ent.Comp.ContainerId); + + if (!_containerSystem.CanInsert(args.Thrown, container)) + return; + + + var rand = _random.NextFloat(); + if (rand > ent.Comp.Probability) + { + _audio.PlayPvs(ent.Comp.MissSound, ent); + _popup.PopupEntity(Loc.GetString(ent.Comp.MissLocString), ent); + return; + } + + if (_containerSystem.Insert(args.Thrown, container)) + _audio.PlayPvs(ent.Comp.InsertSound, ent); + else + throw new InvalidOperationException("Container insertion failed but CanInsert returned true"); + + if (args.Component.Thrower != null) + _adminLogger.Add(LogType.Landed, LogImpact.Low, $"{ToPrettyString(args.Thrown)} thrown by {ToPrettyString(args.Component.Thrower.Value):player} landed in {ToPrettyString(ent)}"); + } +} diff --git a/Content.Server/Disposal/Unit/EntitySystems/DisposalUnitSystem.cs b/Content.Server/Disposal/Unit/EntitySystems/DisposalUnitSystem.cs index 416e0744b5..b970ae4b0d 100644 --- a/Content.Server/Disposal/Unit/EntitySystems/DisposalUnitSystem.cs +++ b/Content.Server/Disposal/Unit/EntitySystems/DisposalUnitSystem.cs @@ -73,8 +73,6 @@ public sealed class DisposalUnitSystem : SharedDisposalUnitSystem SubscribeLocalEvent(OnPowerChange); SubscribeLocalEvent(OnDisposalInit); - SubscribeLocalEvent(OnThrowCollide); - SubscribeLocalEvent(OnActivate); SubscribeLocalEvent(OnAfterInteractUsing); SubscribeLocalEvent(OnDragDropOn); @@ -294,40 +292,6 @@ public sealed class DisposalUnitSystem : SharedDisposalUnitSystem args.Handled = true; } - /// - /// Thrown items have a chance of bouncing off the unit and not going in. - /// - private void OnThrowCollide(EntityUid uid, SharedDisposalUnitComponent component, ThrowHitByEvent args) - { - var canInsert = CanInsert(uid, component, args.Thrown); - var randDouble = _robustRandom.NextDouble(); - - if (!canInsert) - { - return; - } - - if (randDouble > 0.75) - { - _audioSystem.PlayPvs(component.MissSound, uid); - - _popupSystem.PopupEntity(Loc.GetString("disposal-unit-thrown-missed"), uid); - return; - } - - var inserted = _containerSystem.Insert(args.Thrown, component.Container); - - if (!inserted) - { - throw new InvalidOperationException("Container insertion failed but CanInsert returned true"); - } - - if (args.Component.Thrower != null) - _adminLogger.Add(LogType.Landed, LogImpact.Low, $"{ToPrettyString(args.Thrown)} thrown by {ToPrettyString(args.Component.Thrower.Value):player} landed in {ToPrettyString(uid)}"); - - AfterInsert(uid, component, args.Thrown); - } - private void OnDisposalInit(EntityUid uid, SharedDisposalUnitComponent component, ComponentInit args) { component.Container = _containerSystem.EnsureContainer(uid, SharedDisposalUnitComponent.ContainerId); diff --git a/Content.Shared/Disposal/Components/SharedDisposalUnitComponent.cs b/Content.Shared/Disposal/Components/SharedDisposalUnitComponent.cs index 4948cb6640..36dd14f9b2 100644 --- a/Content.Shared/Disposal/Components/SharedDisposalUnitComponent.cs +++ b/Content.Shared/Disposal/Components/SharedDisposalUnitComponent.cs @@ -36,13 +36,6 @@ public abstract partial class SharedDisposalUnitComponent : Component [ViewVariables(VVAccess.ReadWrite), DataField("soundInsert")] public SoundSpecifier? InsertSound = new SoundPathSpecifier("/Audio/Effects/trashbag1.ogg"); - /// - /// Sound played when an item is thrown and misses the disposal unit. - /// - [ViewVariables(VVAccess.ReadWrite), DataField("soundMiss")] - public SoundSpecifier? MissSound = new SoundPathSpecifier("/Audio/Effects/thudswoosh.ogg"); - - /// /// State for this disposals unit. /// diff --git a/Resources/Locale/en-US/containers/containers.ftl b/Resources/Locale/en-US/containers/containers.ftl index ab011f64f8..d96383305a 100644 --- a/Resources/Locale/en-US/containers/containers.ftl +++ b/Resources/Locale/en-US/containers/containers.ftl @@ -1,2 +1,5 @@ container-verb-text-enter = Enter container-verb-text-empty = Empty + +## missed +container-thrown-missed = Missed! \ No newline at end of file diff --git a/Resources/Locale/en-US/disposal/unit/components/disposal-unit-component.ftl b/Resources/Locale/en-US/disposal/unit/components/disposal-unit-component.ftl index 288db53668..2b23ee9a4a 100644 --- a/Resources/Locale/en-US/disposal/unit/components/disposal-unit-component.ftl +++ b/Resources/Locale/en-US/disposal/unit/components/disposal-unit-component.ftl @@ -18,9 +18,6 @@ disposal-eject-verb-get-data-text = Eject contents ## No hands disposal-unit-no-hands = You don't have hands! -## missed -disposal-unit-thrown-missed = Missed! - # state disposal-unit-state-Ready = Ready # Yes I want it to always say Pressurizing diff --git a/Resources/Prototypes/Entities/Structures/Piping/Disposal/units.yml b/Resources/Prototypes/Entities/Structures/Piping/Disposal/units.yml index b4a5f61ffa..2198c854a0 100644 --- a/Resources/Prototypes/Entities/Structures/Piping/Disposal/units.yml +++ b/Resources/Prototypes/Entities/Structures/Piping/Disposal/units.yml @@ -77,6 +77,8 @@ graph: DisposalMachine node: disposal_unit - type: DisposalUnit + - type: ThrowInsertContainer + containerId: disposals - type: UserInterface interfaces: enum.DisposalUnitUiKey.Key: