More storage tweaks (#25970)
- Fix some prediction stuff. - Fix some jank. - UseDelay. - Cap.
This commit is contained in:
@@ -26,7 +26,7 @@ public sealed class StorageSystem : SharedStorageSystem
|
|||||||
|
|
||||||
SubscribeLocalEvent<StorageComponent, ComponentShutdown>(OnShutdown);
|
SubscribeLocalEvent<StorageComponent, ComponentShutdown>(OnShutdown);
|
||||||
SubscribeNetworkEvent<PickupAnimationEvent>(HandlePickupAnimation);
|
SubscribeNetworkEvent<PickupAnimationEvent>(HandlePickupAnimation);
|
||||||
SubscribeNetworkEvent<AnimateInsertingEntitiesEvent>(HandleAnimatingInsertingEntities);
|
SubscribeAllEvent<AnimateInsertingEntitiesEvent>(HandleAnimatingInsertingEntities);
|
||||||
}
|
}
|
||||||
|
|
||||||
public override void UpdateUI(Entity<StorageComponent?> entity)
|
public override void UpdateUI(Entity<StorageComponent?> entity)
|
||||||
|
|||||||
@@ -61,6 +61,9 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
|
|
||||||
public bool CheckingCanInsert;
|
public bool CheckingCanInsert;
|
||||||
|
|
||||||
|
private List<EntityUid> _entList = new();
|
||||||
|
private HashSet<EntityUid> _entSet = new();
|
||||||
|
|
||||||
private readonly List<ItemSizePrototype> _sortedSizes = new();
|
private readonly List<ItemSizePrototype> _sortedSizes = new();
|
||||||
private FrozenDictionary<string, ItemSizePrototype> _nextSmallest = FrozenDictionary<string, ItemSizePrototype>.Empty;
|
private FrozenDictionary<string, ItemSizePrototype> _nextSmallest = FrozenDictionary<string, ItemSizePrototype>.Empty;
|
||||||
|
|
||||||
@@ -262,36 +265,40 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
private void AfterInteract(EntityUid uid, StorageComponent storageComp, AfterInteractEvent args)
|
private void AfterInteract(EntityUid uid, StorageComponent storageComp, AfterInteractEvent args)
|
||||||
{
|
{
|
||||||
if (args.Handled || !args.CanReach)
|
if (args.Handled || !args.CanReach || !UseDelay.TryResetDelay(uid, checkDelayed: true))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// Pick up all entities in a radius around the clicked location.
|
// Pick up all entities in a radius around the clicked location.
|
||||||
// The last half of the if is because carpets exist and this is terrible
|
// The last half of the if is because carpets exist and this is terrible
|
||||||
if (storageComp.AreaInsert && (args.Target == null || !HasComp<ItemComponent>(args.Target.Value)))
|
if (storageComp.AreaInsert && (args.Target == null || !HasComp<ItemComponent>(args.Target.Value)))
|
||||||
{
|
{
|
||||||
var validStorables = new List<EntityUid>();
|
_entList.Clear();
|
||||||
|
_entSet.Clear();
|
||||||
|
_entityLookupSystem.GetEntitiesInRange(args.ClickLocation, storageComp.AreaInsertRadius, _entSet, LookupFlags.Dynamic | LookupFlags.Sundries);
|
||||||
var delay = 0f;
|
var delay = 0f;
|
||||||
|
|
||||||
foreach (var entity in _entityLookupSystem.GetEntitiesInRange(args.ClickLocation, storageComp.AreaInsertRadius, LookupFlags.Dynamic | LookupFlags.Sundries))
|
foreach (var entity in _entSet)
|
||||||
{
|
{
|
||||||
if (entity == args.User
|
if (entity == args.User
|
||||||
// || !_itemQuery.HasComponent(entity)
|
|| !_itemQuery.TryGetComponent(entity, out var itemComp) // Need comp to get item size to get weight
|
||||||
|| !TryComp<ItemComponent>(entity, out var itemComp) // Need comp to get item size to get weight
|
|
||||||
|| !_prototype.TryIndex(itemComp.Size, out var itemSize)
|
|| !_prototype.TryIndex(itemComp.Size, out var itemSize)
|
||||||
|| !CanInsert(uid, entity, out _, storageComp)
|
|| !CanInsert(uid, entity, out _, storageComp, item: itemComp)
|
||||||
|| !_interactionSystem.InRangeUnobstructed(args.User, entity))
|
|| !_interactionSystem.InRangeUnobstructed(args.User, entity))
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
validStorables.Add(entity);
|
_entList.Add(entity);
|
||||||
delay += itemSize.Weight * AreaInsertDelayPerItem;
|
delay += itemSize.Weight * AreaInsertDelayPerItem;
|
||||||
|
|
||||||
|
if (_entList.Count >= StorageComponent.AreaPickupLimit)
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
//If there's only one then let's be generous
|
//If there's only one then let's be generous
|
||||||
if (validStorables.Count > 1)
|
if (_entList.Count > 1)
|
||||||
{
|
{
|
||||||
var doAfterArgs = new DoAfterArgs(EntityManager, args.User, delay, new AreaPickupDoAfterEvent(GetNetEntityList(validStorables)), uid, target: uid)
|
var doAfterArgs = new DoAfterArgs(EntityManager, args.User, delay, new AreaPickupDoAfterEvent(GetNetEntityList(_entList)), uid, target: uid)
|
||||||
{
|
{
|
||||||
BreakOnDamage = true,
|
BreakOnDamage = true,
|
||||||
BreakOnMove = true,
|
BreakOnMove = true,
|
||||||
@@ -313,7 +320,7 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
|
|
||||||
if (_containerSystem.IsEntityInContainer(target)
|
if (_containerSystem.IsEntityInContainer(target)
|
||||||
|| target == args.User
|
|| target == args.User
|
||||||
|| !HasComp<ItemComponent>(target))
|
|| !_itemQuery.HasComponent(target))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -331,10 +338,10 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
args.Handled = true;
|
args.Handled = true;
|
||||||
if (PlayerInsertEntityInWorld((uid, storageComp), args.User, target))
|
if (PlayerInsertEntityInWorld((uid, storageComp), args.User, target))
|
||||||
{
|
{
|
||||||
RaiseNetworkEvent(new AnimateInsertingEntitiesEvent(GetNetEntity(uid),
|
EntityManager.RaiseSharedEvent(new AnimateInsertingEntitiesEvent(GetNetEntity(uid),
|
||||||
new List<NetEntity> { GetNetEntity(target) },
|
new List<NetEntity> { GetNetEntity(target) },
|
||||||
new List<NetCoordinates> { GetNetCoordinates(position) },
|
new List<NetCoordinates> { GetNetCoordinates(position) },
|
||||||
new List<Angle> { transformOwner.LocalRotation }));
|
new List<Angle> { transformOwner.LocalRotation }), args.User);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -349,20 +356,27 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
var successfullyInserted = new List<EntityUid>();
|
var successfullyInserted = new List<EntityUid>();
|
||||||
var successfullyInsertedPositions = new List<EntityCoordinates>();
|
var successfullyInsertedPositions = new List<EntityCoordinates>();
|
||||||
var successfullyInsertedAngles = new List<Angle>();
|
var successfullyInsertedAngles = new List<Angle>();
|
||||||
_xformQuery.TryGetComponent(uid, out var xform);
|
|
||||||
|
|
||||||
foreach (var netEntity in args.Entities)
|
if (!_xformQuery.TryGetComponent(uid, out var xform))
|
||||||
{
|
{
|
||||||
var entity = GetEntity(netEntity);
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
var entCount = Math.Min(StorageComponent.AreaPickupLimit, args.Entities.Count);
|
||||||
|
|
||||||
|
for (var i = 0; i < entCount; i++)
|
||||||
|
{
|
||||||
|
var entity = GetEntity(args.Entities[i]);
|
||||||
|
|
||||||
// Check again, situation may have changed for some entities, but we'll still pick up any that are valid
|
// Check again, situation may have changed for some entities, but we'll still pick up any that are valid
|
||||||
if (_containerSystem.IsEntityInContainer(entity)
|
if (_containerSystem.IsEntityInContainer(entity)
|
||||||
|| entity == args.Args.User
|
|| entity == args.Args.User
|
||||||
|| !_itemQuery.HasComponent(entity))
|
|| !_itemQuery.HasComponent(entity))
|
||||||
|
{
|
||||||
continue;
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (xform == null ||
|
if (!_xformQuery.TryGetComponent(entity, out var targetXform) ||
|
||||||
!_xformQuery.TryGetComponent(entity, out var targetXform) ||
|
|
||||||
targetXform.MapID != xform.MapID)
|
targetXform.MapID != xform.MapID)
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
@@ -387,12 +401,12 @@ public abstract class SharedStorageSystem : EntitySystem
|
|||||||
// If we picked up at least one thing, play a sound and do a cool animation!
|
// If we picked up at least one thing, play a sound and do a cool animation!
|
||||||
if (successfullyInserted.Count > 0)
|
if (successfullyInserted.Count > 0)
|
||||||
{
|
{
|
||||||
Audio.PlayPvs(component.StorageInsertSound, uid);
|
Audio.PlayPredicted(component.StorageInsertSound, uid, args.User);
|
||||||
RaiseNetworkEvent(new AnimateInsertingEntitiesEvent(
|
EntityManager.RaiseSharedEvent(new AnimateInsertingEntitiesEvent(
|
||||||
GetNetEntity(uid),
|
GetNetEntity(uid),
|
||||||
GetNetEntityList(successfullyInserted),
|
GetNetEntityList(successfullyInserted),
|
||||||
GetNetCoordinatesList(successfullyInsertedPositions),
|
GetNetCoordinatesList(successfullyInsertedPositions),
|
||||||
successfullyInsertedAngles));
|
successfullyInsertedAngles), args.User);
|
||||||
}
|
}
|
||||||
|
|
||||||
args.Handled = true;
|
args.Handled = true;
|
||||||
|
|||||||
@@ -60,6 +60,11 @@ namespace Content.Shared.Storage
|
|||||||
[DataField]
|
[DataField]
|
||||||
public bool ClickInsert = true; // Can insert stuff by clicking the storage entity with it
|
public bool ClickInsert = true; // Can insert stuff by clicking the storage entity with it
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// How many entities area pickup can pickup at once.
|
||||||
|
/// </summary>
|
||||||
|
public const int AreaPickupLimit = 10;
|
||||||
|
|
||||||
[DataField]
|
[DataField]
|
||||||
public bool AreaInsert; // Clicking with the storage entity causes it to insert all nearby storables after a delay
|
public bool AreaInsert; // Clicking with the storage entity causes it to insert all nearby storables after a delay
|
||||||
|
|
||||||
|
|||||||
@@ -22,6 +22,8 @@
|
|||||||
tags:
|
tags:
|
||||||
- Cartridge
|
- Cartridge
|
||||||
- Trash
|
- Trash
|
||||||
|
- type: UseDelay
|
||||||
|
delay: 0.5
|
||||||
- type: Tag
|
- type: Tag
|
||||||
tags:
|
tags:
|
||||||
- TrashBag
|
- TrashBag
|
||||||
|
|||||||
Reference in New Issue
Block a user