diff --git a/Content.Server/_DV/Speech/Components/DrunkardAccentComponent.cs b/Content.Server/_DV/Speech/Components/DrunkardAccentComponent.cs new file mode 100644 index 00000000000..b96bc931a12 --- /dev/null +++ b/Content.Server/_DV/Speech/Components/DrunkardAccentComponent.cs @@ -0,0 +1,4 @@ +namespace Content.Server._DV.Speech.Components; + +[RegisterComponent] +public sealed partial class DrunkardAccentComponent : Component; diff --git a/Content.Server/_DV/Speech/EntitySystems/DrunkardAccentSystem.cs b/Content.Server/_DV/Speech/EntitySystems/DrunkardAccentSystem.cs new file mode 100644 index 00000000000..7262bec88e5 --- /dev/null +++ b/Content.Server/_DV/Speech/EntitySystems/DrunkardAccentSystem.cs @@ -0,0 +1,83 @@ +using System.Text; +using Content.Server._DV.Speech.Components; +using Content.Server.Speech; +using Content.Shared.Drunk; +using Content.Shared.StatusEffect; +using Robust.Shared.Random; +using Robust.Shared.Timing; + +namespace Content.Server._DV.Speech.EntitySystems; + + +public sealed class DrunkardAccentSystem : EntitySystem +{ + [Dependency] private readonly StatusEffectsSystem _statusEffectsSystem = default!; + [Dependency] private readonly IRobustRandom _random = default!; + [Dependency] private readonly IGameTiming _timing = default!; + + public override void Initialize() + { + base.Initialize(); + + SubscribeLocalEvent(OnAccent); + } + + // A modified copy of SlurredSystem's Accentuate. + public string Accentuate(string message, float scale) + { + var sb = new StringBuilder(); + + foreach (var character in message) + { + if (_random.Prob(scale / 3)) + { + var lower = char.ToLowerInvariant(character); + var newString = lower switch + { + 'o' => "u", + 's' => "ch", + 'a' => "ah", + 'u' => "oo", + 'c' => "k", + _ => $"{character}", + }; + + sb.Append(newString); + } + + if (!_random.Prob(scale * 3 / 20)) + { + sb.Append(character); + continue; + } + + var next = _random.Next(1, 3) switch + { + 1 => "'", + 2 => $"{character}{character}", + _ => $"{character}{character}{character}", + }; + + sb.Append(next); + } + + return sb.ToString(); + } + + private void OnAccent(EntityUid uid, DrunkardAccentComponent component, AccentGetEvent args) + { + // Drunk status effect calculations, ripped directly from SlurredSystem B) + if (!_statusEffectsSystem.TryGetTime(uid, SharedDrunkSystem.DrunkKey, out var time)) + { + args.Message = Accentuate(args.Message, 0.25f); + } + else + { + var curTime = _timing.CurTime; + var timeLeft = (float) (time.Value.Item2 - curTime).TotalSeconds; + var drunkScale = Math.Clamp((timeLeft - 80) / 1100, 0f, 1f); + + args.Message = Accentuate(args.Message, Math.Max(0.25f, drunkScale)); + } + } +} diff --git a/Resources/Locale/en-US/_DV/traits/traits.ftl b/Resources/Locale/en-US/_DV/traits/traits.ftl index 024fcd50a5f..70500b916ae 100644 --- a/Resources/Locale/en-US/_DV/traits/traits.ftl +++ b/Resources/Locale/en-US/_DV/traits/traits.ftl @@ -38,3 +38,6 @@ trait-unborgable-desc = Your brain cannot be put into a man-machine interface. trait-depression-name = Depression trait-depression-desc = No mechanical effect. The world is dark but there is a light somewhere, calling to you. + +trait-drunkard-accent-name = Drunkard accent +trait-drunkard-accent-desc = You always sound like you're drunk. diff --git a/Resources/Prototypes/_DV/Traits/neutral.yml b/Resources/Prototypes/_DV/Traits/neutral.yml index 3d4333529b9..8aaa161af3e 100644 --- a/Resources/Prototypes/_DV/Traits/neutral.yml +++ b/Resources/Prototypes/_DV/Traits/neutral.yml @@ -45,3 +45,12 @@ cost: 2 # Changed weight to 2 in accordance with other accents components: - type: IrishAccent + +- type: trait + id: DrunkardAccent + name: trait-drunkard-accent-name + description: trait-drunkard-accent-desc + category: SpeechTraits + cost: 2 + components: + - type: DrunkardAccent