Skip to content

Commit

Permalink
Фикс движения в вентиляции и комбез уплотнения для атмоса
Browse files Browse the repository at this point in the history
  • Loading branch information
VigersRay committed Feb 10, 2025
1 parent 5d86bf0 commit 08ff9c2
Show file tree
Hide file tree
Showing 7 changed files with 467 additions and 0 deletions.
106 changes: 106 additions & 0 deletions Content.Server/_Sunrise/VentCraw/BeingVentCrawSystem.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
using Content.Server.Atmos.EntitySystems;
using Content.Server.Body.Systems;
using Content.Server.Ghost;
using Content.Server.NodeContainer;
using Content.Server.NodeContainer.EntitySystems;
using Content.Server.NodeContainer.Nodes;
using Content.Shared._Sunrise.VentCraw.Components;
using Content.Shared.Mind;
using Content.Shared.Mobs;
using Robust.Shared.Player;

namespace Content.Server._Sunrise.VentCraw;

public sealed class BeingVentCrawSystem : EntitySystem
{
[Dependency] private readonly NodeContainerSystem _nodeContainer = default!;
[Dependency] private readonly IEntityManager _entities = default!;

public override void Initialize()
{
base.Initialize();

SubscribeLocalEvent<BeingVentCrawComponent, InhaleLocationEvent>(OnInhaleLocation);
SubscribeLocalEvent<BeingVentCrawComponent, ExhaleLocationEvent>(OnExhaleLocation);
SubscribeLocalEvent<BeingVentCrawComponent, AtmosExposedGetAirEvent>(OnGetAir);
SubscribeLocalEvent<BeingVentCrawComponent, MobStateChangedEvent>(OnMobStateChanged);
}

private void OnMobStateChanged(EntityUid uid, BeingVentCrawComponent component, MobStateChangedEvent args)
{
if (args.NewMobState != MobState.Dead || args.OldMobState != MobState.Critical)
return;

if (TryComp<ActorComponent>(uid, out var actor))
{
var session = actor.PlayerSession;

var minds = _entities.System<SharedMindSystem>();
if (!minds.TryGetMind(session, out var mindId, out var mind))
{
mindId = minds.CreateMind(session.UserId);
mind = _entities.GetComponent<MindComponent>(mindId);
}

_entities.System<GhostSystem>().OnGhostAttempt(mindId, true, true, mind);
}
}

private void OnGetAir(EntityUid uid, BeingVentCrawComponent component, ref AtmosExposedGetAirEvent args)
{
if (!TryComp<VentCrawHolderComponent>(component.Holder, out var holder))
return;

if (holder.CurrentTube == null)
return;

if (!TryComp(holder.CurrentTube.Value, out NodeContainerComponent? nodeContainer))
return;
foreach (var nodeContainerNode in nodeContainer.Nodes)
{
if (!_nodeContainer.TryGetNode(nodeContainer, nodeContainerNode.Key, out PipeNode? pipe))
continue;
args.Gas = pipe.Air;
args.Handled = true;
return;
}
}

private void OnInhaleLocation(EntityUid uid, BeingVentCrawComponent component, InhaleLocationEvent args)
{
if (!TryComp<VentCrawHolderComponent>(component.Holder, out var holder))
return;

if (holder.CurrentTube == null)
return;

if (!TryComp(holder.CurrentTube.Value, out NodeContainerComponent? nodeContainer))
return;
foreach (var nodeContainerNode in nodeContainer.Nodes)
{
if (!_nodeContainer.TryGetNode(nodeContainer, nodeContainerNode.Key, out PipeNode? pipe))
continue;
args.Gas = pipe.Air;
return;
}
}

private void OnExhaleLocation(EntityUid uid, BeingVentCrawComponent component, ExhaleLocationEvent args)
{
if (!TryComp<VentCrawHolderComponent>(component.Holder, out var holder))
return;

if (holder.CurrentTube == null)
return;

if (!TryComp(holder.CurrentTube.Value, out NodeContainerComponent? nodeContainer))
return;
foreach (var nodeContainerNode in nodeContainer.Nodes)
{
if (!_nodeContainer.TryGetNode(nodeContainer, nodeContainerNode.Key, out PipeNode? pipe))
continue;
args.Gas = pipe.Air;
return;
}
}
}
26 changes: 26 additions & 0 deletions Content.Server/_Sunrise/VentCraw/VentCrawClothingSystem.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
using Content.Shared._Sunrise.VentCraw;
using Content.Shared._Sunrise.VentCraw.Components;
using Content.Shared.Clothing;

namespace Content.Server._Sunrise.VentCraw;

public sealed class VentCrawClothingSystem : EntitySystem
{
public override void Initialize()
{
base.Initialize();

SubscribeLocalEvent<VentCrawClothingComponent, ClothingGotEquippedEvent>(OnClothingEquip);
SubscribeLocalEvent<VentCrawClothingComponent, ClothingGotUnequippedEvent>(OnClothingUnequip);
}

private void OnClothingEquip(Entity<VentCrawClothingComponent> ent, ref ClothingGotEquippedEvent args)
{
AddComp<VentCrawlerComponent>(args.Wearer);
}

private void OnClothingUnequip(Entity<VentCrawClothingComponent> ent, ref ClothingGotUnequippedEvent args)
{
RemComp<VentCrawlerComponent>(args.Wearer);
}
}
220 changes: 220 additions & 0 deletions Content.Server/_Sunrise/VentCraw/VentCrawTubeSystem.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,220 @@
using System.Linq;
using Content.Server.Construction.Completions;
using Content.Server.Popups;
using Content.Shared._Sunrise.VentCraw;
using Content.Shared._Sunrise.VentCraw.Components;
using Content.Shared.Destructible;
using Content.Shared.DoAfter;
using Content.Shared.Movement.Systems;
using Content.Shared.Tools.Components;
using Content.Shared.Verbs;
using Robust.Shared.Containers;

namespace Content.Server._Sunrise.VentCraw
{
public sealed class VentCrawTubeSystem : EntitySystem
{
[Dependency] private readonly SharedVentCrawableSystem _ventCrawableSystem = default!;
[Dependency] private readonly SharedContainerSystem _containerSystem = default!;
[Dependency] private readonly SharedDoAfterSystem _doAfterSystem = default!;
[Dependency] private readonly PopupSystem _popup = default!;
[Dependency] private readonly SharedMoverController _mover = default!;
[Dependency] private readonly SharedTransformSystem _transform = default!;

public override void Initialize()
{
base.Initialize();

SubscribeLocalEvent<VentCrawTubeComponent, ComponentInit>(OnComponentInit);
SubscribeLocalEvent<VentCrawTubeComponent, ComponentRemove>(OnComponentRemove);

SubscribeLocalEvent<VentCrawTubeComponent, AnchorStateChangedEvent>(OnAnchorChange);
SubscribeLocalEvent<VentCrawTubeComponent, BreakageEventArgs>(OnBreak);
SubscribeLocalEvent<VentCrawTubeComponent, ComponentShutdown>(OnShutdown);
SubscribeLocalEvent<VentCrawTubeComponent, ComponentStartup>(OnStartup);
SubscribeLocalEvent<VentCrawTubeComponent, ConstructionBeforeDeleteEvent>(OnDeconstruct);
SubscribeLocalEvent<VentCrawBendComponent, GetVentCrawsConnectableDirectionsEvent>(OnGetBendConnectableDirections);
SubscribeLocalEvent<VentCrawEntryComponent, GetVentCrawsConnectableDirectionsEvent>(OnGetEntryConnectableDirections);
SubscribeLocalEvent<VentCrawJunctionComponent, GetVentCrawsConnectableDirectionsEvent>(OnGetJunctionConnectableDirections);
SubscribeLocalEvent<VentCrawTransitComponent, GetVentCrawsConnectableDirectionsEvent>(OnGetTransitConnectableDirections);
SubscribeLocalEvent<VentCrawEntryComponent, GetVerbsEvent<AlternativeVerb>>(AddClimbedVerb);
SubscribeLocalEvent<VentCrawlerComponent, EnterVentDoAfterEvent>(OnDoAfterEnterTube);
}

private void AddClimbedVerb(EntityUid uid, VentCrawEntryComponent component, GetVerbsEvent<AlternativeVerb> args)
{
if (!TryComp<VentCrawlerComponent>(args.User, out var ventCrawlerComponent) || HasComp<BeingVentCrawComponent>(args.User))
return;

var xform = Transform(uid);

if (!xform.Anchored)
return;

AlternativeVerb verb = new()
{
Act = () => TryEnter(uid, args.User, ventCrawlerComponent),
Text = Loc.GetString("comp-climbable-verb-climb")
};
args.Verbs.Add(verb);
}

private void OnDoAfterEnterTube(EntityUid uid, VentCrawlerComponent component, EnterVentDoAfterEvent args)
{
if (args.Handled || args.Cancelled || args.Args.Target == null || args.Args.Used == null)
return;

TryInsert(args.Args.Target.Value, args.Args.Used.Value);

args.Handled = true;
}

private void TryEnter(EntityUid uid, EntityUid user, VentCrawlerComponent crawler)
{
if (TryComp<WeldableComponent>(uid, out var weldableComponent))
{
if (weldableComponent.IsWelded)
{
_popup.PopupEntity(Loc.GetString("entity-storage-component-welded-shut-message"), user);
return;
}
}

var args = new DoAfterArgs(EntityManager, user, crawler.EnterDelay, new EnterVentDoAfterEvent(), user, uid, user)
{
BreakOnMove = true,
BreakOnDamage = false
};

_doAfterSystem.TryStartDoAfter(args);
}

private void OnComponentInit(EntityUid uid, VentCrawTubeComponent tube, ComponentInit args)
{
tube.Contents = _containerSystem.EnsureContainer<Container>(uid, tube.ContainerId);
}

private void OnComponentRemove(EntityUid uid, VentCrawTubeComponent tube, ComponentRemove args)
{
DisconnectTube(uid, tube);
}

private void OnShutdown(EntityUid uid, VentCrawTubeComponent tube, ComponentShutdown args)
{
DisconnectTube(uid, tube);
}

private void OnGetBendConnectableDirections(EntityUid uid, VentCrawBendComponent component, ref GetVentCrawsConnectableDirectionsEvent args)
{
var direction = Transform(uid).LocalRotation;
var side = new Angle(MathHelper.DegreesToRadians(direction.Degrees - 90));

args.Connectable = new[] { direction.GetDir(), side.GetDir() };
}

private void OnGetEntryConnectableDirections(EntityUid uid, VentCrawEntryComponent component, ref GetVentCrawsConnectableDirectionsEvent args)
{
args.Connectable = new[] { Transform(uid).LocalRotation.GetDir() };
}

private void OnGetJunctionConnectableDirections(EntityUid uid, VentCrawJunctionComponent component, ref GetVentCrawsConnectableDirectionsEvent args)
{
var direction = Transform(uid).LocalRotation;

args.Connectable = component.Degrees
.Select(degree => new Angle(degree.Theta + direction.Theta).GetDir())
.ToArray();
}

private void OnGetTransitConnectableDirections(EntityUid uid, VentCrawTransitComponent component, ref GetVentCrawsConnectableDirectionsEvent args)
{
var rotation = Transform(uid).LocalRotation;
var opposite = new Angle(rotation.Theta + Math.PI);

args.Connectable = new[] { rotation.GetDir(), opposite.GetDir() };
}

private void OnDeconstruct(EntityUid uid, VentCrawTubeComponent component, ConstructionBeforeDeleteEvent args)
{
DisconnectTube(uid, component);
}

private void OnStartup(EntityUid uid, VentCrawTubeComponent component, ComponentStartup args)
{
UpdateAnchored(uid, component, Transform(uid).Anchored);
}

private void OnBreak(EntityUid uid, VentCrawTubeComponent component, BreakageEventArgs args)
{
DisconnectTube(uid, component);
}

private void OnAnchorChange(EntityUid uid, VentCrawTubeComponent component, ref AnchorStateChangedEvent args)
{
UpdateAnchored(uid, component, args.Anchored);
}

private void UpdateAnchored(EntityUid uid, VentCrawTubeComponent component, bool anchored)
{
if (anchored)
{
ConnectTube(uid, component);
}
else
{
DisconnectTube(uid, component);
}
}

private static void ConnectTube(EntityUid _, VentCrawTubeComponent tube)
{
if (tube.Connected)
{
return;
}

tube.Connected = true;
}


private void DisconnectTube(EntityUid _, VentCrawTubeComponent tube)
{
if (!tube.Connected)
{
return;
}

tube.Connected = false;

var query = GetEntityQuery<VentCrawHolderComponent>();
foreach (var entity in tube.Contents.ContainedEntities.ToArray())
{
if (query.TryGetComponent(entity, out var holder))
{
var Exitev = new VentCrawExitEvent();
RaiseLocalEvent(entity, ref Exitev);
}
}
}

private bool TryInsert(EntityUid uid, EntityUid entity, VentCrawEntryComponent? entry = null)
{
if (!Resolve(uid, ref entry))
return false;

if (!TryComp<VentCrawlerComponent>(entity, out var ventCrawlerComponent))
return false;

var holder = Spawn(VentCrawEntryComponent.HolderPrototypeId, _transform.GetMapCoordinates(uid));
var holderComponent = Comp<VentCrawHolderComponent>(holder);

_ventCrawableSystem.TryInsert(holder, entity, holderComponent);

_mover.SetRelay(entity, holder);
ventCrawlerComponent.InTube = true;
Dirty(entity, ventCrawlerComponent);

return _ventCrawableSystem.EnterTube(holder, uid, holderComponent);
}
}
}
Loading

0 comments on commit 08ff9c2

Please sign in to comment.