using Content.Server.Explosion.EntitySystems; using Content.Server.Interaction.Components; using Content.Server.Sound.Components; using Content.Server.Throwing; using Content.Server.UserInterface; using Content.Server.Popups; using Content.Shared.Interaction; using Content.Shared.Interaction.Events; using Content.Shared.Maps; using Content.Shared.Throwing; using JetBrains.Annotations; using Robust.Shared.Map; using Robust.Shared.Player; using Robust.Shared.Random; namespace Content.Server.Sound { /// /// Will play a sound on various events if the affected entity has a component derived from BaseEmitSoundComponent /// [UsedImplicitly] public sealed class EmitSoundSystem : EntitySystem { [Dependency] private readonly IMapManager _mapManager = default!; [Dependency] private readonly ITileDefinitionManager _tileDefMan = default!; [Dependency] private readonly IRobustRandom _random = default!; [Dependency] private readonly SharedAudioSystem _audioSystem = default!; [Dependency] private readonly PopupSystem _popupSystem = default!; /// public override void Update(float frameTime) { base.Update(frameTime); foreach (var soundSpammer in EntityQuery()) { soundSpammer.Accumulator += frameTime; if (soundSpammer.Accumulator < soundSpammer.RollInterval) { continue; } soundSpammer.Accumulator -= soundSpammer.RollInterval; if (_random.Prob(soundSpammer.PlayChance)) { if (soundSpammer.PopUp != null) _popupSystem.PopupEntity(Loc.GetString(soundSpammer.PopUp), soundSpammer.Owner, Filter.Pvs(soundSpammer.Owner)); TryEmitSound(soundSpammer); } } } public override void Initialize() { base.Initialize(); SubscribeLocalEvent(HandleEmitSoundOnLand); SubscribeLocalEvent(HandleEmitSoundOnUseInHand); SubscribeLocalEvent(HandleEmitSoundOnThrown); SubscribeLocalEvent(HandleEmitSoundOnActivateInWorld); SubscribeLocalEvent(HandleEmitSoundOnTrigger); SubscribeLocalEvent(HandleEmitSoundOnUIOpen); } private void HandleEmitSoundOnTrigger(EntityUid uid, EmitSoundOnTriggerComponent component, TriggerEvent args) { TryEmitSound(component); args.Handled = true; } private void HandleEmitSoundOnLand(EntityUid eUI, BaseEmitSoundComponent component, LandEvent arg) { if (!TryComp(eUI, out var xform) || !_mapManager.TryGetGrid(xform.GridUid, out var grid)) return; var tile = grid.GetTileRef(xform.Coordinates); if (tile.IsSpace(_tileDefMan)) return; TryEmitSound(component); } private void HandleEmitSoundOnUseInHand(EntityUid eUI, EmitSoundOnUseComponent component, UseInHandEvent arg) { // Intentionally not checking whether the interaction has already been handled. TryEmitSound(component); if (component.Handle) arg.Handled = true; } private void HandleEmitSoundOnThrown(EntityUid eUI, BaseEmitSoundComponent component, ThrownEvent arg) { TryEmitSound(component); } private void HandleEmitSoundOnActivateInWorld(EntityUid eUI, EmitSoundOnActivateComponent component, ActivateInWorldEvent arg) { // Intentionally not checking whether the interaction has already been handled. TryEmitSound(component); if (component.Handle) arg.Handled = true; } private void HandleEmitSoundOnUIOpen(EntityUid eUI, BaseEmitSoundComponent component, AfterActivatableUIOpenEvent arg) { TryEmitSound(component); } private void TryEmitSound(BaseEmitSoundComponent component) { _audioSystem.PlayPvs(component.Sound, component.Owner, component.Sound.Params.AddVolume(-2f)); } } }