Skip to content
Open
6 changes: 4 additions & 2 deletions EXILED/Exiled.API/Features/Items/Firearm.cs
Original file line number Diff line number Diff line change
Expand Up @@ -360,9 +360,11 @@ public static Firearm Create(FirearmType type)
/// <param name="identifier">The <see cref="AttachmentIdentifier"/> to add.</param>
public void AddAttachment(AttachmentIdentifier identifier)
{
uint fallbackCode = AvailableAttachments[FirearmType].FirstOrDefault(attId => attId.Name == identifier.Name).Code;

// Fallback addedCode onto AvailableAttachments' code in case it's 0
uint addedCode = identifier.Code == 0
? AvailableAttachments[FirearmType].FirstOrDefault(attId => attId.Name == identifier.Name).Code
uint addedCode = identifier.Code == 0 || fallbackCode != identifier.Code
? fallbackCode
: identifier.Code;

// Look for conflicting attachment (attachment that occupies the same slot)
Expand Down
195 changes: 149 additions & 46 deletions EXILED/Exiled.API/Features/Player.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2871,7 +2871,7 @@ public Item AddItem(ItemType itemType)
{
if (itemType.GetFirearmType() is not FirearmType.None)
{
return AddItem(itemType.GetFirearmType(), null);
return AddItem(itemType.GetFirearmType(), new List<AttachmentIdentifier>());
}

Item item = Item.Create(itemType, this);
Expand All @@ -2881,6 +2881,39 @@ public Item AddItem(ItemType itemType)
return item;
}

/// <summary>
/// Adds the amount of items of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="itemType">The item to be added.</param>
/// <param name="amount">The amount of items to be added.</param>
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(ItemType itemType, int amount)
{
List<Item> items = new(amount > 0 ? amount : 0);
if (amount > 0)
{
for (int i = 0; i < amount; i++)
items.Add(AddItem(itemType));
}

return items;
}

/// <summary>
/// Adds the list of items of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="items">The list of items to be added.</param>
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(IEnumerable<ItemType> items)
{
List<Item> returnedItems = new(items.Count());

foreach (ItemType type in items)
returnedItems.Add(AddItem(type));

return returnedItems;
}

/// <summary>
/// Adds a firearm of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
Expand All @@ -2905,18 +2938,43 @@ public Item AddItem(FirearmType firearmType, IEnumerable<AttachmentIdentifier> i
}

/// <summary>
/// Adds the amount of items of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// Adds a firearm of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="itemType">The item to be added.</param>
/// <param name="firearmType">The firearm to be added.</param>
/// <param name="identifiers">The attachments to be added to the item.</param>
/// <returns>The <see cref="Item"/> given to the player.</returns>
public Item AddItem(FirearmType firearmType, IEnumerable<AttachmentName> identifiers)
{
Item item = Item.Create(firearmType.GetItemType());

if (item is Firearm firearm)
{
if (identifiers is not null)
firearm.AddAttachment(identifiers);
else if (Preferences is not null && Preferences.TryGetValue(firearmType, out AttachmentIdentifier[] attachments))
firearm.Base.ApplyAttachmentsCode(attachments.GetAttachmentsCode(), true);
}

AddItem(item);

return item;
}

/// <summary>
/// Adds the amount of firearms of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="firearmType">The item to be added.</param>
/// <param name="amount">The amount of items to be added.</param>
/// <returns>An <see cref="IEnumerable{Item}"/> containing the items given.</returns>
public IEnumerable<Item> AddItem(ItemType itemType, int amount)
/// <param name="identifiers">The attachments to be added to the item.</param>
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(FirearmType firearmType, int amount, IEnumerable<AttachmentIdentifier> identifiers)
{
List<Item> items = new(amount > 0 ? amount : 0);

if (amount > 0)
{
for (int i = 0; i < amount; i++)
items.Add(AddItem(itemType));
items.Add(AddItem(firearmType, identifiers));
}

return items;
Expand All @@ -2928,17 +2986,15 @@ public IEnumerable<Item> AddItem(ItemType itemType, int amount)
/// <param name="firearmType">The item to be added.</param>
/// <param name="amount">The amount of items to be added.</param>
/// <param name="identifiers">The attachments to be added to the item.</param>
/// <returns>An <see cref="IEnumerable{Item}"/> containing the items given.</returns>
public IEnumerable<Item> AddItem(FirearmType firearmType, int amount, IEnumerable<AttachmentIdentifier> identifiers)
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(FirearmType firearmType, int amount, IEnumerable<AttachmentName> identifiers)
{
List<Item> items = new(amount > 0 ? amount : 0);

if (amount > 0)
{
IEnumerable<AttachmentIdentifier> attachmentIdentifiers = identifiers.ToList();

for (int i = 0; i < amount; i++)
items.Add(AddItem(firearmType, attachmentIdentifiers));
items.Add(AddItem(firearmType, identifiers));
}

return items;
Expand All @@ -2947,48 +3003,76 @@ public IEnumerable<Item> AddItem(FirearmType firearmType, int amount, IEnumerabl
/// <summary>
/// Adds the list of items of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="items">The list of items to be added.</param>
/// <returns>An <see cref="IEnumerable{Item}"/> containing the items given.</returns>
public IEnumerable<Item> AddItem(IEnumerable<ItemType> items)
/// <param name="items">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="ItemType"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentIdentifier"/> to be added.</param>
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(Dictionary<FirearmType, IEnumerable<AttachmentIdentifier>> items)
{
List<ItemType> enumeratedItems = ListPool<ItemType>.Pool.Get(items);
List<Item> returnedItems = new(enumeratedItems.Count);
List<Item> returnedItems = new(items.Count);

foreach (ItemType type in enumeratedItems)
returnedItems.Add(AddItem(type));
foreach (KeyValuePair<FirearmType, IEnumerable<AttachmentIdentifier>> item in items)
returnedItems.Add(AddItem(item.Key, item.Value));

ListPool<ItemType>.Pool.Return(enumeratedItems);
return returnedItems;
}

/// <summary>
/// Adds the list of items of the specified type with default durability(ammo/charge) and no mods to the player's inventory.
/// </summary>
/// <param name="items">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="ItemType"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentIdentifier"/> to be added.</param>
/// <returns>An <see cref="IEnumerable{Item}"/> containing the items given.</returns>
public IEnumerable<Item> AddItem(Dictionary<FirearmType, IEnumerable<AttachmentIdentifier>> items)
/// <param name="items">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="ItemType"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentName"/> to be added.</param>
/// <returns>An <see cref="List{Item}"/> containing the items given.</returns>
public List<Item> AddItem(Dictionary<FirearmType, IEnumerable<AttachmentName>> items)
{
List<Item> returnedItems = new(items.Count);

foreach (KeyValuePair<FirearmType, IEnumerable<AttachmentIdentifier>> item in items)
returnedItems.Add(AddItem(item.Key, item.Value));
foreach (KeyValuePair<FirearmType, IEnumerable<AttachmentName>> item in items)
returnedItems.Add(AddItem(item.Key, AttachmentIdentifier.Get(item.Key, item.Value)));

return returnedItems;
}

/// <summary>
/// Adds the list of items to the player's inventory.
/// </summary>
/// <param name="firearms">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="Firearm"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentIdentifier"/> to be added.</param>
public void AddItem(Dictionary<Firearm, IEnumerable<AttachmentIdentifier>> firearms)
{
if (firearms.Count > 0)
{
foreach (KeyValuePair<Firearm, IEnumerable<AttachmentIdentifier>> item in firearms)
AddItem(item.Key, item.Value);
}
}

/// <summary>
/// Adds the list of items to the player's inventory.
/// </summary>
/// <param name="firearms">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="Firearm"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentName"/> to be added.</param>
public void AddItem(Dictionary<Firearm, IEnumerable<AttachmentName>> firearms)
{
if (firearms.Count > 0)
{
foreach (KeyValuePair<Firearm, IEnumerable<AttachmentName>> item in firearms)
AddItem(item.Key, item.Value);
}
}

/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
/// <param name="item">The item to be added.</param>
public void AddItem(Item item)
/// <param name="identifiers">The attachments to be added to the item.</param>
public void AddItem(Firearm item, IEnumerable<AttachmentIdentifier> identifiers)
{
try
{
if (identifiers is not null)
item.AddAttachment(identifiers);

AddItem(item.Base, item);
}
catch (Exception e)
catch (Exception exception)
{
Log.Error($"{nameof(Player)}.{nameof(AddItem)}(Item): {e}");
Log.Error($"{nameof(Player)}.{nameof(AddItem)}(Item): {exception}");
}
}

Expand All @@ -2997,7 +3081,7 @@ public void AddItem(Item item)
/// </summary>
/// <param name="item">The item to be added.</param>
/// <param name="identifiers">The attachments to be added to the item.</param>
public void AddItem(Firearm item, IEnumerable<AttachmentIdentifier> identifiers)
public void AddItem(Firearm item, IEnumerable<AttachmentName> identifiers)
{
try
{
Expand All @@ -3015,27 +3099,59 @@ public void AddItem(Firearm item, IEnumerable<AttachmentIdentifier> identifiers)
/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
/// <param name="pickup">The <see cref="Pickup"/> of the item to be added.</param>
/// <param name="addReason">The reason the item was added.</param>
/// <param name="pickup">The <see cref="FirearmPickup"/> of the item to be added.</param>
/// <param name="identifiers">The attachments to be added to <see cref="Pickup"/> of the item.</param>
/// <returns>The <see cref="Item"/> that was added.</returns>
public Item AddItem(Pickup pickup, ItemAddReason addReason = ItemAddReason.AdminCommand) => Item.Get(Inventory.ServerAddItem(pickup.Type, addReason, pickup.Serial, pickup.Base));
public Item AddItem(FirearmPickup pickup, IEnumerable<AttachmentIdentifier> identifiers)
{
Firearm firearm = Item.Get<Firearm>(Inventory.ServerAddItem(pickup.Type, ItemAddReason.PickedUp, pickup.Serial, pickup.Base));

if (identifiers is not null)
firearm.AddAttachment(identifiers);

return firearm;
}

/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
/// <param name="pickup">The <see cref="FirearmPickup"/> of the item to be added.</param>
/// <param name="identifiers">The attachments to be added to <see cref="Pickup"/> of the item.</param>
/// <returns>The <see cref="Item"/> that was added.</returns>
public Item AddItem(FirearmPickup pickup, IEnumerable<AttachmentIdentifier> identifiers)
public Item AddItem(FirearmPickup pickup, IEnumerable<AttachmentName> identifiers)
{
Firearm firearm = Item.Get<Firearm>(Inventory.ServerAddItem(pickup.Type, ItemAddReason.PickedUp, pickup.Serial, pickup.Base));
Firearm firearm = Item.Get<Firearm>(Inventory.ServerAddItem(pickup.Type, ItemAddReason.AdminCommand, pickup.Serial, pickup.Base));

if (identifiers is not null)
firearm.AddAttachment(identifiers);

return firearm;
}

/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
/// <param name="item">The item to be added.</param>
public void AddItem(Item item)
{
try
{
AddItem(item.Base, item);
}
catch (Exception e)
{
Log.Error($"{nameof(Player)}.{nameof(AddItem)}(Item): {e}");
}
}

/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
/// <param name="pickup">The <see cref="Pickup"/> of the item to be added.</param>
/// <param name="addReason">The reason the item was added.</param>
/// <returns>The <see cref="Item"/> that was added.</returns>
public Item AddItem(Pickup pickup, ItemAddReason addReason = ItemAddReason.AdminCommand) => Item.Get(Inventory.ServerAddItem(pickup.Type, addReason, pickup.Serial, pickup.Base));

/// <summary>
/// Adds an item to the player's inventory.
/// </summary>
Expand Down Expand Up @@ -3082,19 +3198,6 @@ public void AddItem(IEnumerable<Item> items)
AddItem(item);
}

/// <summary>
/// Adds the list of items to the player's inventory.
/// </summary>
/// <param name="firearms">The <see cref="Dictionary{TKey, TValue}"/> of <see cref="Firearm"/> and <see cref="IEnumerable{T}"/> of <see cref="AttachmentIdentifier"/> to be added.</param>
public void AddItem(Dictionary<Firearm, IEnumerable<AttachmentIdentifier>> firearms)
{
if (firearms.Count > 0)
{
foreach (KeyValuePair<Firearm, IEnumerable<AttachmentIdentifier>> item in firearms)
AddItem(item.Key, item.Value);
}
}

/// <summary>
/// Gives the player a specific candy. Will give the player a bag if they do not already have one.
/// </summary>
Expand Down
Loading
Loading