From fbaafa8366f9be09b8bb44ed017c32794f2ac99e Mon Sep 17 00:00:00 2001 From: Hugal31 Date: Tue, 5 May 2020 00:39:15 +0200 Subject: [PATCH] Add smart equip shortcuts (#873) --- Content.Client/Input/ContentContexts.cs | 2 + .../UserInterface/TutorialWindow.cs | 6 +- .../Components/GUI/ServerHandsComponent.cs | 6 ++ .../Items/Storage/ServerStorageComponent.cs | 7 ++- .../GameObjects/EntitySystems/HandsSystem.cs | 57 +++++++++++++++++++ Content.Shared/Input/ContentKeyFunctions.cs | 2 + .../Entities/Items/Clothing/belts.yml | 1 + Resources/keybinds.yml | 8 +++ 8 files changed, 86 insertions(+), 3 deletions(-) diff --git a/Content.Client/Input/ContentContexts.cs b/Content.Client/Input/ContentContexts.cs index 4249ef2704..279b238217 100644 --- a/Content.Client/Input/ContentContexts.cs +++ b/Content.Client/Input/ContentContexts.cs @@ -28,6 +28,8 @@ namespace Content.Client.Input human.AddFunction(ContentKeyFunctions.OpenContextMenu); human.AddFunction(ContentKeyFunctions.OpenCraftingMenu); human.AddFunction(ContentKeyFunctions.OpenInventoryMenu); + human.AddFunction(ContentKeyFunctions.SmartEquipBackpack); + human.AddFunction(ContentKeyFunctions.SmartEquipBelt); human.AddFunction(ContentKeyFunctions.MouseMiddle); human.AddFunction(ContentKeyFunctions.ToggleCombatMode); human.AddFunction(ContentKeyFunctions.WideAttack); diff --git a/Content.Client/UserInterface/TutorialWindow.cs b/Content.Client/UserInterface/TutorialWindow.cs index ffdfc2a2b0..af54907d57 100644 --- a/Content.Client/UserInterface/TutorialWindow.cs +++ b/Content.Client/UserInterface/TutorialWindow.cs @@ -69,6 +69,8 @@ namespace Content.Client.UserInterface Switch hands: [color=#a4885c]{4}[/color] Use held item: [color=#a4885c]{5}[/color] Drop held item: [color=#a4885c]{6}[/color] +Smart equip from backpack: [color=#a4885c]{24}[/color] +Smart equip from belt: [color=#a4885c]{25}[/color] Open inventory: [color=#a4885c]{7}[/color] Open character window: [color=#a4885c]{8}[/color] Open crafting window: [color=#a4885c]{9}[/color] @@ -106,7 +108,9 @@ Toggle sandbox window: [color=#a4885c]{21}[/color]", Key(OpenTileSpawnWindow), Key(OpenSandboxWindow), Key(Use), - Key(WideAttack))); + Key(WideAttack), + Key(SmartEquipBackpack), + Key(SmartEquipBelt))); //Gameplay VBox.AddChild(new Label { FontOverride = headerFont, Text = "\nGameplay" }); diff --git a/Content.Server/GameObjects/Components/GUI/ServerHandsComponent.cs b/Content.Server/GameObjects/Components/GUI/ServerHandsComponent.cs index 5375c3b783..ab265e3693 100644 --- a/Content.Server/GameObjects/Components/GUI/ServerHandsComponent.cs +++ b/Content.Server/GameObjects/Components/GUI/ServerHandsComponent.cs @@ -151,6 +151,12 @@ namespace Content.Server.GameObjects return success; } + public void PutInHandOrDrop(ItemComponent item) + { + if (!PutInHand(item)) + item.Owner.Transform.GridPosition = Owner.Transform.GridPosition; + } + public bool CanPutInHand(ItemComponent item) { foreach (var hand in ActivePriorityEnumerable()) diff --git a/Content.Server/GameObjects/Components/Items/Storage/ServerStorageComponent.cs b/Content.Server/GameObjects/Components/Items/Storage/ServerStorageComponent.cs index 3f451a2ce4..f0bdb1a615 100644 --- a/Content.Server/GameObjects/Components/Items/Storage/ServerStorageComponent.cs +++ b/Content.Server/GameObjects/Components/Items/Storage/ServerStorageComponent.cs @@ -45,6 +45,8 @@ namespace Content.Server.GameObjects private int StorageCapacityMax = 10000; public HashSet SubscribedSessions = new HashSet(); + public IReadOnlyCollection StoredEntities => storage.ContainedEntities; + public override void Initialize() { base.Initialize(); @@ -140,7 +142,6 @@ namespace Content.Server.GameObjects /// public bool AttackBy(AttackByEventArgs eventArgs) { - _ensureInitialCalculated(); Logger.DebugS("Storage", "Storage (UID {0}) attacked by user (UID {1}) with entity (UID {2}).", Owner.Uid, eventArgs.User.Uid, eventArgs.AttackWith.Uid); if(Owner.TryGetComponent(out var placeableSurfaceComponent)) @@ -363,8 +364,10 @@ namespace Content.Server.GameObjects /// /// Inserts an entity into the storage component from the players active hand. /// - private bool PlayerInsertEntity(IEntity player) + public bool PlayerInsertEntity(IEntity player) { + _ensureInitialCalculated(); + if (!player.TryGetComponent(out IHandsComponent hands) || hands.GetActiveHand == null) return false; diff --git a/Content.Server/GameObjects/EntitySystems/HandsSystem.cs b/Content.Server/GameObjects/EntitySystems/HandsSystem.cs index cc70bc6d07..855084abba 100644 --- a/Content.Server/GameObjects/EntitySystems/HandsSystem.cs +++ b/Content.Server/GameObjects/EntitySystems/HandsSystem.cs @@ -1,9 +1,14 @@ using System; +using System.Linq; +using Content.Server.GameObjects; using Content.Server.GameObjects.Components; using Content.Server.GameObjects.Components.Stack; +using Content.Server.Interfaces; using Content.Server.Interfaces.GameObjects; using Content.Server.Throw; +using Content.Shared.GameObjects.Components.Inventory; using Content.Shared.Input; +using Content.Shared.Interfaces; using Content.Shared.Physics; using JetBrains.Annotations; using Robust.Server.GameObjects; @@ -19,6 +24,7 @@ using Robust.Shared.Interfaces.Map; using Robust.Shared.Interfaces.Physics; using Robust.Shared.Interfaces.Timing; using Robust.Shared.IoC; +using Robust.Shared.Localization; using Robust.Shared.Log; using Robust.Shared.Map; using Robust.Shared.Maths; @@ -33,6 +39,7 @@ namespace Content.Server.GameObjects.EntitySystems #pragma warning disable 649 [Dependency] private readonly IMapManager _mapManager; [Dependency] private readonly IEntitySystemManager _entitySystemManager; + [Dependency] private readonly IServerNotifyManager _notifyManager; #pragma warning restore 649 private const float ThrowForce = 1.5f; // Throwing force of mobs in Newtons @@ -50,6 +57,8 @@ namespace Content.Server.GameObjects.EntitySystems input.BindMap.BindFunction(ContentKeyFunctions.Drop, new PointerInputCmdHandler(HandleDrop)); input.BindMap.BindFunction(ContentKeyFunctions.ActivateItemInHand, InputCmdHandler.FromDelegate(HandleActivateItem)); input.BindMap.BindFunction(ContentKeyFunctions.ThrowItemInHand, new PointerInputCmdHandler(HandleThrowItem)); + input.BindMap.BindFunction(ContentKeyFunctions.SmartEquipBackpack, InputCmdHandler.FromDelegate(HandleSmartEquipBackpack)); + input.BindMap.BindFunction(ContentKeyFunctions.SmartEquipBelt, InputCmdHandler.FromDelegate(HandleSmartEquipBelt)); } /// @@ -190,5 +199,53 @@ namespace Content.Server.GameObjects.EntitySystems return true; } + + private void HandleSmartEquipBackpack(ICommonSession session) + { + HandleSmartEquip(session, EquipmentSlotDefines.Slots.BACKPACK); + } + + private void HandleSmartEquipBelt(ICommonSession session) + { + HandleSmartEquip(session, EquipmentSlotDefines.Slots.BELT); + } + + private void HandleSmartEquip(ICommonSession session, EquipmentSlotDefines.Slots equipementSlot) + { + var plyEnt = ((IPlayerSession) session).AttachedEntity; + + if (plyEnt == null || !plyEnt.IsValid()) + return; + + if (!plyEnt.TryGetComponent(out HandsComponent handsComp) || !plyEnt.TryGetComponent(out InventoryComponent inventoryComp)) + return; + + if (!inventoryComp.TryGetSlotItem(equipementSlot, out ItemComponent equipmentItem) + || !equipmentItem.Owner.TryGetComponent(out var storageComponent)) + { + _notifyManager.PopupMessage(plyEnt, plyEnt, Loc.GetString("You have no {0} to take something out of!", EquipmentSlotDefines.SlotNames[equipementSlot].ToLower())); + return; + } + + var heldItem = handsComp.GetHand(handsComp.ActiveIndex)?.Owner; + + if (heldItem != null) + { + storageComponent.PlayerInsertEntity(plyEnt); + } + else + { + if (storageComponent.StoredEntities.Count == 0) + { + _notifyManager.PopupMessage(plyEnt, plyEnt, Loc.GetString("There's nothing in your {0} to take out!", EquipmentSlotDefines.SlotNames[equipementSlot].ToLower())); + } + else + { + var lastStoredEntity = Enumerable.Last(storageComponent.StoredEntities); + if (storageComponent.Remove(lastStoredEntity)) + handsComp.PutInHandOrDrop(lastStoredEntity.GetComponent()); + } + } + } } } diff --git a/Content.Shared/Input/ContentKeyFunctions.cs b/Content.Shared/Input/ContentKeyFunctions.cs index f2a17daa5d..d44cb1d64d 100644 --- a/Content.Shared/Input/ContentKeyFunctions.cs +++ b/Content.Shared/Input/ContentKeyFunctions.cs @@ -15,6 +15,8 @@ namespace Content.Shared.Input public static readonly BoundKeyFunction OpenContextMenu = "OpenContextMenu"; public static readonly BoundKeyFunction OpenCraftingMenu = "OpenCraftingMenu"; public static readonly BoundKeyFunction OpenInventoryMenu = "OpenInventoryMenu"; + public static readonly BoundKeyFunction SmartEquipBackpack = "SmartEquipBackpack"; + public static readonly BoundKeyFunction SmartEquipBelt = "SmartEquipBelt"; public static readonly BoundKeyFunction OpenTutorial = "OpenTutorial"; public static readonly BoundKeyFunction SwapHands = "SwapHands"; public static readonly BoundKeyFunction ThrowItemInHand = "ThrowItemInHand"; diff --git a/Resources/Prototypes/Entities/Items/Clothing/belts.yml b/Resources/Prototypes/Entities/Items/Clothing/belts.yml index b2423d740e..2994275e00 100644 --- a/Resources/Prototypes/Entities/Items/Clothing/belts.yml +++ b/Resources/Prototypes/Entities/Items/Clothing/belts.yml @@ -21,6 +21,7 @@ state: utilitybelt - type: Clothing Size: 50 + QuickEquip: false sprite: Clothing/belt_utility.rsi - type: Storage Capacity: 40 # Full tool loadout is 35, plus an extra diff --git a/Resources/keybinds.yml b/Resources/keybinds.yml index 10ed5a7826..05cf30d140 100644 --- a/Resources/keybinds.yml +++ b/Resources/keybinds.yml @@ -105,6 +105,14 @@ binds: - function: OpenInventoryMenu type: state key: I +- function: SmartEquipBackpack + type: State + key: B + mod1: Shift +- function: SmartEquipBelt + type: State + key: E + mod1: Shift - function: ShowDebugConsole type: state key: Tilde