2022-01-22 05:52:35 -07:00
|
|
|
using System;
|
2021-10-05 14:29:03 +11:00
|
|
|
using System.Collections.Generic;
|
2021-03-08 04:09:59 +11:00
|
|
|
using System.Linq;
|
2021-06-09 22:19:39 +02:00
|
|
|
using Content.Server.Climbing.Components;
|
2022-01-22 05:52:35 -07:00
|
|
|
using Content.Server.Popups;
|
|
|
|
|
using Content.Server.Stunnable;
|
2021-10-05 14:29:03 +11:00
|
|
|
using Content.Shared.ActionBlocker;
|
2022-02-15 20:04:33 -07:00
|
|
|
using Content.Shared.Buckle.Components;
|
2021-08-10 10:34:01 +10:00
|
|
|
using Content.Shared.Climbing;
|
2022-01-22 05:52:35 -07:00
|
|
|
using Content.Shared.Damage;
|
2021-03-08 04:09:59 +11:00
|
|
|
using Content.Shared.GameTicking;
|
2021-10-05 14:29:03 +11:00
|
|
|
using Content.Shared.Verbs;
|
2020-08-19 18:13:22 -04:00
|
|
|
using JetBrains.Annotations;
|
2021-02-11 01:13:03 -08:00
|
|
|
using Robust.Shared.GameObjects;
|
2021-10-05 14:29:03 +11:00
|
|
|
using Robust.Shared.IoC;
|
|
|
|
|
using Robust.Shared.Localization;
|
2022-01-22 05:52:35 -07:00
|
|
|
using Robust.Shared.Player;
|
2020-08-19 18:13:22 -04:00
|
|
|
|
2021-06-09 22:19:39 +02:00
|
|
|
namespace Content.Server.Climbing
|
2020-08-19 18:13:22 -04:00
|
|
|
{
|
|
|
|
|
[UsedImplicitly]
|
2021-08-10 10:34:01 +10:00
|
|
|
internal sealed class ClimbSystem : SharedClimbSystem
|
2020-08-19 18:13:22 -04:00
|
|
|
{
|
2021-03-08 04:09:59 +11:00
|
|
|
private readonly HashSet<ClimbingComponent> _activeClimbers = new();
|
|
|
|
|
|
2021-10-05 14:29:03 +11:00
|
|
|
[Dependency] private readonly ActionBlockerSystem _actionBlockerSystem = default!;
|
2022-01-22 05:52:35 -07:00
|
|
|
[Dependency] private readonly StunSystem _stunSystem = default!;
|
|
|
|
|
[Dependency] private readonly DamageableSystem _damageableSystem = default!;
|
|
|
|
|
[Dependency] private readonly PopupSystem _popupSystem = default!;
|
2021-10-05 14:29:03 +11:00
|
|
|
|
2021-06-29 15:56:07 +02:00
|
|
|
public override void Initialize()
|
|
|
|
|
{
|
|
|
|
|
base.Initialize();
|
|
|
|
|
|
|
|
|
|
SubscribeLocalEvent<RoundRestartCleanupEvent>(Reset);
|
2022-02-10 15:30:59 +13:00
|
|
|
SubscribeLocalEvent<ClimbableComponent, GetVerbsEvent<AlternativeVerb>>(AddClimbVerb);
|
2022-02-15 20:04:33 -07:00
|
|
|
SubscribeLocalEvent<ClimbingComponent, BuckleChangeEvent>(OnBuckleChange);
|
2022-01-22 05:52:35 -07:00
|
|
|
SubscribeLocalEvent<GlassTableComponent, ClimbedOnEvent>(OnGlassClimbed);
|
2021-10-05 14:29:03 +11:00
|
|
|
}
|
|
|
|
|
|
2021-11-20 01:03:09 +00:00
|
|
|
public void ForciblySetClimbing(EntityUid uid, ClimbingComponent? component = null)
|
|
|
|
|
{
|
|
|
|
|
if (!Resolve(uid, ref component, false))
|
|
|
|
|
return;
|
|
|
|
|
component.IsClimbing = true;
|
|
|
|
|
UnsetTransitionBoolAfterBufferTime(uid, component);
|
|
|
|
|
}
|
|
|
|
|
|
2022-02-10 15:30:59 +13:00
|
|
|
private void AddClimbVerb(EntityUid uid, ClimbableComponent component, GetVerbsEvent<AlternativeVerb> args)
|
2021-10-05 14:29:03 +11:00
|
|
|
{
|
2021-12-03 15:53:09 +01:00
|
|
|
if (!args.CanAccess || !args.CanInteract || !_actionBlockerSystem.CanMove(args.User))
|
2021-10-05 14:29:03 +11:00
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
// Check that the user climb.
|
2021-12-08 13:00:43 +01:00
|
|
|
if (!EntityManager.TryGetComponent(args.User, out ClimbingComponent? climbingComponent) ||
|
2021-10-05 14:29:03 +11:00
|
|
|
climbingComponent.IsClimbing)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
// Add a climb verb
|
2022-02-10 15:30:59 +13:00
|
|
|
AlternativeVerb verb = new();
|
2022-01-22 05:52:35 -07:00
|
|
|
verb.Act = () => component.TryClimb(args.User, args.Target);
|
2021-10-05 14:29:03 +11:00
|
|
|
verb.Text = Loc.GetString("comp-climbable-verb-climb");
|
|
|
|
|
// TODO VERBS ICON add a climbing icon?
|
|
|
|
|
args.Verbs.Add(verb);
|
2021-06-29 15:56:07 +02:00
|
|
|
}
|
|
|
|
|
|
2022-02-15 20:04:33 -07:00
|
|
|
private void OnBuckleChange(EntityUid uid, ClimbingComponent component, BuckleChangeEvent args)
|
|
|
|
|
{
|
|
|
|
|
if (args.Buckling)
|
|
|
|
|
component.IsClimbing = false;
|
|
|
|
|
}
|
|
|
|
|
|
2022-01-22 05:52:35 -07:00
|
|
|
private void OnGlassClimbed(EntityUid uid, GlassTableComponent component, ClimbedOnEvent args)
|
|
|
|
|
{
|
2022-03-02 06:07:48 -08:00
|
|
|
if (TryComp<PhysicsComponent>(args.Climber, out var physics) && physics.Mass <= component.MassLimit)
|
|
|
|
|
return;
|
2022-01-22 05:52:35 -07:00
|
|
|
_damageableSystem.TryChangeDamage(args.Climber, component.ClimberDamage);
|
|
|
|
|
_damageableSystem.TryChangeDamage(uid, component.TableDamage);
|
|
|
|
|
_stunSystem.TryParalyze(args.Climber, TimeSpan.FromSeconds(component.StunTime), true);
|
|
|
|
|
|
|
|
|
|
// Not shown to the user, since they already get a 'you climb on the glass table' popup
|
|
|
|
|
_popupSystem.PopupEntity(Loc.GetString("glass-table-shattered-others",
|
|
|
|
|
("table", uid), ("climber", args.Climber)), args.Climber,
|
|
|
|
|
Filter.Pvs(uid).RemoveWhereAttachedEntity(puid => puid == args.Climber));
|
|
|
|
|
}
|
|
|
|
|
|
2021-03-08 04:09:59 +11:00
|
|
|
public void AddActiveClimber(ClimbingComponent climbingComponent)
|
|
|
|
|
{
|
|
|
|
|
_activeClimbers.Add(climbingComponent);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public void RemoveActiveClimber(ClimbingComponent climbingComponent)
|
|
|
|
|
{
|
|
|
|
|
_activeClimbers.Remove(climbingComponent);
|
|
|
|
|
}
|
|
|
|
|
|
2021-11-20 01:03:09 +00:00
|
|
|
public void UnsetTransitionBoolAfterBufferTime(EntityUid uid, ClimbingComponent? component = null)
|
|
|
|
|
{
|
|
|
|
|
if (!Resolve(uid, ref component, false))
|
|
|
|
|
return;
|
|
|
|
|
component.Owner.SpawnTimer((int) (SharedClimbingComponent.BufferTime * 1000), () =>
|
|
|
|
|
{
|
|
|
|
|
if (component.Deleted) return;
|
|
|
|
|
component.OwnerIsTransitioning = false;
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
|
2020-08-19 18:13:22 -04:00
|
|
|
public override void Update(float frameTime)
|
|
|
|
|
{
|
2021-03-08 04:09:59 +11:00
|
|
|
foreach (var climber in _activeClimbers.ToArray())
|
2020-08-19 18:13:22 -04:00
|
|
|
{
|
2021-03-08 04:09:59 +11:00
|
|
|
climber.Update();
|
2020-08-19 18:13:22 -04:00
|
|
|
}
|
|
|
|
|
}
|
2021-03-08 04:09:59 +11:00
|
|
|
|
2021-06-29 15:56:07 +02:00
|
|
|
public void Reset(RoundRestartCleanupEvent ev)
|
2021-03-08 04:09:59 +11:00
|
|
|
{
|
|
|
|
|
_activeClimbers.Clear();
|
|
|
|
|
}
|
2020-08-19 18:13:22 -04:00
|
|
|
}
|
|
|
|
|
}
|