| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217 |
- using System.Diagnostics.CodeAnalysis;
- using System.Linq;
- using Content.Shared.Actions.Events;
- using Robust.Shared.Prototypes;
- using Robust.Shared.Utility;
- namespace Content.Shared.Actions;
- public sealed class ActionUpgradeSystem : EntitySystem
- {
- [Dependency] private readonly SharedActionsSystem _actions = default!;
- [Dependency] private readonly ActionContainerSystem _actionContainer = default!;
- [Dependency] private readonly EntityManager _entityManager = default!;
- public override void Initialize()
- {
- base.Initialize();
- SubscribeLocalEvent<ActionUpgradeComponent, ActionUpgradeEvent>(OnActionUpgradeEvent);
- }
- private void OnActionUpgradeEvent(EntityUid uid, ActionUpgradeComponent component, ActionUpgradeEvent args)
- {
- if (!CanUpgrade(args.NewLevel, component.EffectedLevels, out var newActionProto)
- || !_actions.TryGetActionData(uid, out var actionComp))
- return;
- var originalContainer = actionComp.Container;
- var originalAttachedEntity = actionComp.AttachedEntity;
- _actionContainer.RemoveAction(uid, actionComp);
- EntityUid? upgradedActionId = null;
- if (originalContainer != null
- && TryComp<ActionsContainerComponent>(originalContainer.Value, out var actionContainerComp))
- {
- upgradedActionId = _actionContainer.AddAction(originalContainer.Value, newActionProto, actionContainerComp);
- if (originalAttachedEntity != null)
- _actions.GrantContainedActions(originalAttachedEntity.Value, originalContainer.Value);
- else
- _actions.GrantContainedActions(originalContainer.Value, originalContainer.Value);
- }
- else if (originalAttachedEntity != null)
- {
- upgradedActionId = _actionContainer.AddAction(originalAttachedEntity.Value, newActionProto);
- }
- if (!TryComp<ActionUpgradeComponent>(upgradedActionId, out var upgradeComp))
- return;
- upgradeComp.Level = args.NewLevel;
- // TODO: Preserve ordering of actions
- _entityManager.DeleteEntity(uid);
- }
- public bool TryUpgradeAction(EntityUid? actionId, out EntityUid? upgradeActionId, ActionUpgradeComponent? actionUpgradeComponent = null, int newLevel = 0)
- {
- upgradeActionId = null;
- if (!TryGetActionUpgrade(actionId, out var actionUpgradeComp))
- return false;
- actionUpgradeComponent ??= actionUpgradeComp;
- DebugTools.AssertNotNull(actionUpgradeComponent);
- DebugTools.AssertNotNull(actionId);
- if (newLevel < 1)
- newLevel = actionUpgradeComponent.Level + 1;
- if (!CanLevelUp(newLevel, actionUpgradeComponent.EffectedLevels))
- return false;
- actionUpgradeComponent.Level = newLevel;
- // If it can level up but can't upgrade, still return true and return current actionId as the upgradeId.
- if (!CanUpgrade(newLevel, actionUpgradeComponent.EffectedLevels, out var newActionProto))
- {
- upgradeActionId = actionId;
- DebugTools.AssertNotNull(upgradeActionId);
- return true;
- }
- upgradeActionId = UpgradeAction(actionId, actionUpgradeComp, newActionProto, newLevel);
- DebugTools.AssertNotNull(upgradeActionId);
- return true;
- }
- private bool CanLevelUp(int newLevel, Dictionary<int, EntProtoId> levelDict)
- {
- if (levelDict.Count < 1)
- return false;
- var canLevel = false;
- var finalLevel = levelDict.Keys.ToList()[levelDict.Keys.Count - 1];
- foreach (var (level, proto) in levelDict)
- {
- if (newLevel > finalLevel)
- continue;
- if ((newLevel <= finalLevel && newLevel != level) || newLevel == level)
- {
- canLevel = true;
- break;
- }
- }
- return canLevel;
- }
- private bool CanUpgrade(int newLevel, Dictionary<int, EntProtoId> levelDict, [NotNullWhen(true)]out EntProtoId? newLevelProto)
- {
- var canUpgrade = false;
- newLevelProto = null;
- var finalLevel = levelDict.Keys.ToList()[levelDict.Keys.Count - 1];
- foreach (var (level, proto) in levelDict)
- {
- if (newLevel != level || newLevel > finalLevel)
- continue;
- canUpgrade = true;
- newLevelProto = proto;
- DebugTools.AssertNotNull(newLevelProto);
- break;
- }
- return canUpgrade;
- }
- /// <summary>
- /// Raises a level by one
- /// </summary>
- public EntityUid? UpgradeAction(EntityUid? actionId, ActionUpgradeComponent? actionUpgradeComponent = null, EntProtoId? newActionProto = null, int newLevel = 0)
- {
- if (!TryGetActionUpgrade(actionId, out var actionUpgradeComp))
- return null;
- actionUpgradeComponent ??= actionUpgradeComp;
- DebugTools.AssertNotNull(actionUpgradeComponent);
- DebugTools.AssertNotNull(actionId);
- if (newLevel < 1)
- newLevel = actionUpgradeComponent.Level + 1;
- actionUpgradeComponent.Level = newLevel;
- // RaiseActionUpgradeEvent(newLevel, actionId.Value);
- if (!CanUpgrade(newLevel, actionUpgradeComponent.EffectedLevels, out var newActionPrototype)
- || !_actions.TryGetActionData(actionId, out var actionComp))
- return null;
- newActionProto ??= newActionPrototype;
- DebugTools.AssertNotNull(newActionProto);
- var originalContainer = actionComp.Container;
- var originalAttachedEntity = actionComp.AttachedEntity;
- _actionContainer.RemoveAction(actionId.Value, actionComp);
- EntityUid? upgradedActionId = null;
- if (originalContainer != null
- && TryComp<ActionsContainerComponent>(originalContainer.Value, out var actionContainerComp))
- {
- upgradedActionId = _actionContainer.AddAction(originalContainer.Value, newActionProto, actionContainerComp);
- if (originalAttachedEntity != null)
- _actions.GrantContainedActions(originalAttachedEntity.Value, originalContainer.Value);
- else
- _actions.GrantContainedActions(originalContainer.Value, originalContainer.Value);
- }
- else if (originalAttachedEntity != null)
- {
- upgradedActionId = _actionContainer.AddAction(originalAttachedEntity.Value, newActionProto);
- }
- if (!TryComp<ActionUpgradeComponent>(upgradedActionId, out var upgradeComp))
- return null;
- upgradeComp.Level = newLevel;
- // TODO: Preserve ordering of actions
- _entityManager.DeleteEntity(actionId);
- return upgradedActionId.Value;
- }
- private void RaiseActionUpgradeEvent(int level, EntityUid actionId)
- {
- var ev = new ActionUpgradeEvent(level, actionId);
- RaiseLocalEvent(actionId, ev);
- }
- public bool TryGetActionUpgrade(
- [NotNullWhen(true)] EntityUid? uid,
- [NotNullWhen(true)] out ActionUpgradeComponent? result,
- bool logError = true)
- {
- result = null;
- if (!Exists(uid))
- return false;
- if (!TryComp<ActionUpgradeComponent>(uid, out var actionUpgradeComponent))
- {
- Log.Error($"Failed to get action upgrade from action entity: {ToPrettyString(uid.Value)}");
- return false;
- }
- result = actionUpgradeComponent;
- DebugTools.AssertOwner(uid, result);
- return true;
- }
- }
|