Files
tbd-station-14/Content.Shared/Sericulture/SericultureSystem.cs
Centronias 6b99493e80 Reduce network burden of the hunger system (#32986)
* reduce network burden of the hunger system

* explicit start + last updated

* remove auto reformat changes to otherwise untouched code

add clamp helper

* imagine making breaking changes, documenting them, and then not thinking to check the yaml

* comments

* Remove unused net manager in hunger system
Remove lastAuthoritativeHungerValue from prototypes
2024-12-18 14:06:02 +01:00

117 lines
4.2 KiB
C#

using Content.Shared.Actions;
using Content.Shared.DoAfter;
using Content.Shared.Nutrition.EntitySystems;
using Robust.Shared.Serialization;
using Content.Shared.Popups;
using Robust.Shared.Network;
using Content.Shared.Nutrition.Components;
using Content.Shared.Stacks;
namespace Content.Shared.Sericulture;
/// <summary>
/// Allows mobs to produce materials with <see cref="SericultureComponent"/>.
/// </summary>
public abstract partial class SharedSericultureSystem : EntitySystem
{
// Managers
[Dependency] private readonly INetManager _netManager = default!;
// Systems
[Dependency] private readonly SharedActionsSystem _actionsSystem = default!;
[Dependency] private readonly SharedDoAfterSystem _doAfterSystem = default!;
[Dependency] private readonly HungerSystem _hungerSystem = default!;
[Dependency] private readonly SharedPopupSystem _popupSystem = default!;
[Dependency] private readonly SharedStackSystem _stackSystem = default!;
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<SericultureComponent, MapInitEvent>(OnMapInit);
SubscribeLocalEvent<SericultureComponent, ComponentShutdown>(OnCompRemove);
SubscribeLocalEvent<SericultureComponent, SericultureActionEvent>(OnSericultureStart);
SubscribeLocalEvent<SericultureComponent, SericultureDoAfterEvent>(OnSericultureDoAfter);
}
/// <summary>
/// Giveths the action to preform sericulture on the entity
/// </summary>
private void OnMapInit(EntityUid uid, SericultureComponent comp, MapInitEvent args)
{
_actionsSystem.AddAction(uid, ref comp.ActionEntity, comp.Action);
}
/// <summary>
/// Takeths away the action to preform sericulture from the entity.
/// </summary>
private void OnCompRemove(EntityUid uid, SericultureComponent comp, ComponentShutdown args)
{
_actionsSystem.RemoveAction(uid, comp.ActionEntity);
}
private void OnSericultureStart(EntityUid uid, SericultureComponent comp, SericultureActionEvent args)
{
if (TryComp<HungerComponent>(uid, out var hungerComp)
&& _hungerSystem.IsHungerBelowState(uid,
comp.MinHungerThreshold,
_hungerSystem.GetHunger(hungerComp) - comp.HungerCost,
hungerComp))
{
_popupSystem.PopupClient(Loc.GetString(comp.PopupText), uid, uid);
return;
}
var doAfter = new DoAfterArgs(EntityManager, uid, comp.ProductionLength, new SericultureDoAfterEvent(), uid)
{ // I'm not sure if more things should be put here, but imo ideally it should probably be set in the component/YAML. Not sure if this is currently possible.
BreakOnMove = true,
BlockDuplicate = true,
BreakOnDamage = true,
CancelDuplicate = true,
};
_doAfterSystem.TryStartDoAfter(doAfter);
}
private void OnSericultureDoAfter(EntityUid uid, SericultureComponent comp, SericultureDoAfterEvent args)
{
if (args.Cancelled || args.Handled || comp.Deleted)
return;
if (TryComp<HungerComponent>(uid,
out var hungerComp) // A check, just incase the doafter is somehow performed when the entity is not in the right hunger state.
&& _hungerSystem.IsHungerBelowState(uid,
comp.MinHungerThreshold,
_hungerSystem.GetHunger(hungerComp) - comp.HungerCost,
hungerComp))
{
_popupSystem.PopupClient(Loc.GetString(comp.PopupText), uid, uid);
return;
}
_hungerSystem.ModifyHunger(uid, -comp.HungerCost);
if (!_netManager.IsClient) // Have to do this because spawning stuff in shared is CBT.
{
var newEntity = Spawn(comp.EntityProduced, Transform(uid).Coordinates);
_stackSystem.TryMergeToHands(newEntity, uid);
}
args.Repeat = true;
}
}
/// <summary>
/// Should be relayed upon using the action.
/// </summary>
public sealed partial class SericultureActionEvent : InstantActionEvent { }
/// <summary>
/// Is relayed at the end of the sericulturing doafter.
/// </summary>
[Serializable, NetSerializable]
public sealed partial class SericultureDoAfterEvent : SimpleDoAfterEvent { }