KillCalloutRuleSystem.cs 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. using Content.Server.Chat.Managers;
  2. using Content.Server.GameTicking.Rules.Components;
  3. using Content.Server.KillTracking;
  4. using Content.Shared.Chat;
  5. using Content.Shared.GameTicking.Components;
  6. using Robust.Server.Player;
  7. using Robust.Shared.Player;
  8. using Robust.Shared.Random;
  9. namespace Content.Server.GameTicking.Rules;
  10. /// <summary>
  11. /// This handles calling out kills from <see cref="KillTrackingSystem"/>
  12. /// </summary>
  13. public sealed class KillCalloutRuleSystem : GameRuleSystem<KillCalloutRuleComponent>
  14. {
  15. [Dependency] private readonly IChatManager _chatManager = default!;
  16. [Dependency] private readonly IPlayerManager _playerManager = default!;
  17. [Dependency] private readonly IRobustRandom _random = default!;
  18. /// <inheritdoc/>
  19. public override void Initialize()
  20. {
  21. base.Initialize();
  22. SubscribeLocalEvent<KillReportedEvent>(OnKillReported);
  23. }
  24. private void OnKillReported(ref KillReportedEvent ev)
  25. {
  26. var query = EntityQueryEnumerator<KillCalloutRuleComponent, GameRuleComponent>();
  27. while (query.MoveNext(out var uid, out var kill, out var rule))
  28. {
  29. if (!GameTicker.IsGameRuleActive(uid, rule))
  30. continue;
  31. var callout = GetCallout(kill, ev);
  32. _chatManager.ChatMessageToAll(ChatChannel.Server, callout, callout, uid, false, true, Color.OrangeRed);
  33. }
  34. }
  35. private string GetCallout(KillCalloutRuleComponent component, KillReportedEvent ev)
  36. {
  37. // Do the humiliation callouts if you kill yourself or die from bleeding out or something lame.
  38. if (ev.Primary is KillEnvironmentSource || ev.Suicide)
  39. {
  40. var selfCallout = $"{component.SelfKillCalloutPrefix}{_random.Next(component.SelfKillCalloutAmount)}";
  41. return Loc.GetString(selfCallout,
  42. ("victim", GetCalloutName(ev.Entity)));
  43. }
  44. var primary = GetCalloutName(ev.Primary);
  45. var killerString = primary;
  46. if (ev.Assist != null)
  47. {
  48. var secondary = GetCalloutName(ev.Assist);
  49. killerString = Loc.GetString("death-match-assist",
  50. ("primary", primary), ("secondary", secondary));
  51. }
  52. var callout = $"{component.KillCalloutPrefix}{_random.Next(component.KillCalloutAmount)}";
  53. return Loc.GetString(callout, ("killer", killerString),
  54. ("victim", GetCalloutName(ev.Entity)));
  55. }
  56. private string GetCalloutName(KillSource source)
  57. {
  58. switch (source)
  59. {
  60. case KillPlayerSource player:
  61. if (!_playerManager.TryGetSessionById(player.PlayerId, out var session))
  62. break;
  63. if (session.AttachedEntity == null)
  64. break;
  65. return Loc.GetString("death-match-name-player",
  66. ("name", MetaData(session.AttachedEntity.Value).EntityName),
  67. ("username", session.Name));
  68. case KillNpcSource npc:
  69. if (Deleted(npc.NpcEnt))
  70. return string.Empty;
  71. return Loc.GetString("death-match-name-npc", ("name", MetaData(npc.NpcEnt).EntityName));
  72. }
  73. return string.Empty;
  74. }
  75. private string GetCalloutName(EntityUid source)
  76. {
  77. if (TryComp<ActorComponent>(source, out var actorComp))
  78. {
  79. return Loc.GetString("death-match-name-player",
  80. ("name", MetaData(source).EntityName),
  81. ("username", actorComp.PlayerSession.Name));
  82. }
  83. return Loc.GetString("death-match-name-npc", ("name", MetaData(source).EntityName));
  84. }
  85. }