New patch with ammo skills.
Index: java/org/l2jmobius/gameserver/data/ItemTable.java
===================================================================
--- java/org/l2jmobius/gameserver/data/ItemTable.java (revision 8502)
+++ java/org/l2jmobius/gameserver/data/ItemTable.java (working copy)
@@ -47,11 +47,14 @@
import org.l2jmobius.gameserver.model.actor.instance.PlayerInstance;
import org.l2jmobius.gameserver.model.events.EventDispatcher;
import org.l2jmobius.gameserver.model.events.impl.item.OnItemCreate;
+import org.l2jmobius.gameserver.model.holders.ItemSkillHolder;
import org.l2jmobius.gameserver.model.items.Armor;
import org.l2jmobius.gameserver.model.items.EtcItem;
import org.l2jmobius.gameserver.model.items.Item;
import org.l2jmobius.gameserver.model.items.Weapon;
import org.l2jmobius.gameserver.model.items.instance.ItemInstance;
+import org.l2jmobius.gameserver.model.items.type.EtcItemType;
+import org.l2jmobius.gameserver.model.skills.AmmunitionSkillList;
import org.l2jmobius.gameserver.util.DocumentItem;
import org.l2jmobius.gameserver.util.GMAudit;
@@ -194,6 +197,15 @@
if (item instanceof EtcItem)
{
_etcItems.put(item.getId(), (EtcItem) item);
+
+ if ((item.getItemType() == EtcItemType.ARROW) || (item.getItemType() == EtcItemType.BOLT))
+ {
+ final List<ItemSkillHolder> skills = item.getAllSkills();
+ if (skills != null)
+ {
+ AmmunitionSkillList.add(skills);
+ }
+ }
}
else if (item instanceof Armor)
{
Index: java/org/l2jmobius/gameserver/model/actor/Creature.java
===================================================================
--- java/org/l2jmobius/gameserver/model/actor/Creature.java (revision 8527)
+++ java/org/l2jmobius/gameserver/model/actor/Creature.java (working copy)
@@ -1154,11 +1154,11 @@
// Try to do what is expected by having more attack speed.
// final int reuse = (int) (Formulas.calculateReuseTime(this, weaponItem) / (Math.max(1, _stat.getAttackSpeedMultiplier() - 1)));
- // Consume arrows
+ // Consume ammunition.
final Inventory inventory = getInventory();
if (inventory != null)
{
- inventory.reduceArrowCount(crossbow ? EtcItemType.BOLT : EtcItemType.ARROW);
+ inventory.reduceAmmunitionCount(crossbow ? EtcItemType.BOLT : EtcItemType.ARROW);
}
// Check if the Creature is a PlayerInstance
Index: java/org/l2jmobius/gameserver/model/actor/instance/PlayerInstance.java
===================================================================
--- java/org/l2jmobius/gameserver/model/actor/instance/PlayerInstance.java (revision 8533)
+++ java/org/l2jmobius/gameserver/model/actor/instance/PlayerInstance.java (working copy)
@@ -220,6 +220,7 @@
import org.l2jmobius.gameserver.model.holders.AutoUseSettingsHolder;
import org.l2jmobius.gameserver.model.holders.DamageTakenHolder;
import org.l2jmobius.gameserver.model.holders.ItemHolder;
+import org.l2jmobius.gameserver.model.holders.ItemSkillHolder;
import org.l2jmobius.gameserver.model.holders.MovieHolder;
import org.l2jmobius.gameserver.model.holders.PlayerEventHolder;
import org.l2jmobius.gameserver.model.holders.PreparedMultisellListHolder;
@@ -261,6 +262,7 @@
import org.l2jmobius.gameserver.model.siege.Fort;
import org.l2jmobius.gameserver.model.siege.Siege;
import org.l2jmobius.gameserver.model.skills.AbnormalType;
+import org.l2jmobius.gameserver.model.skills.AmmunitionSkillList;
import org.l2jmobius.gameserver.model.skills.BuffInfo;
import org.l2jmobius.gameserver.model.skills.CommonSkill;
import org.l2jmobius.gameserver.model.skills.Skill;
@@ -725,6 +727,8 @@
private BroochJewel _activeRubyJewel = null;
private BroochJewel _activeShappireJewel = null;
+ private int _lastAmmunitionId = 0;
+
/** Event parameters */
private PlayerEventHolder eventStatus = null;
@@ -853,7 +857,7 @@
// Shared dualclass skills.
private static final String KNOWN_DUAL_SKILLS_VAR = "KNOWN_DUAL_SKILLS";
- private static final int[] DUAL_CLASS_SKILLS = new int[]
+ private static final int[] DUAL_CLASS_SKILLS =
{
19222, // Dignity of the Exalted
19223, // Belief of the Exalted
@@ -4439,20 +4443,6 @@
else
{
addItem("Pickup", target, null, true);
- // Auto-Equip arrows/bolts if player has a bow/crossbow and player picks up arrows/bolts.
- final ItemInstance weapon = _inventory.getPaperdollItem(Inventory.PAPERDOLL_RHAND);
- if (weapon != null)
- {
- final EtcItem etcItem = target.getEtcItem();
- if (etcItem != null)
- {
- final EtcItemType itemType = etcItem.getItemType();
- if (((weapon.getItemType() == WeaponType.BOW) && (itemType == EtcItemType.ARROW)) || (((weapon.getItemType() == WeaponType.CROSSBOW) || (weapon.getItemType() == WeaponType.TWOHANDCROSSBOW)) && (itemType == EtcItemType.BOLT)))
- {
- checkAndEquipAmmunition(itemType);
- }
- }
- }
}
}
}
@@ -5772,31 +5762,81 @@
@Override
protected boolean checkAndEquipAmmunition(EtcItemType type)
{
- ItemInstance arrows = _inventory.getPaperdollItem(Inventory.PAPERDOLL_LHAND);
- if (arrows == null)
+ ItemInstance ammunition = null;
+ final Weapon weapon = getActiveWeaponItem();
+ if (type == EtcItemType.ARROW)
{
- final Weapon weapon = getActiveWeaponItem();
- if (type == EtcItemType.ARROW)
+ ammunition = _inventory.findArrowForBow(weapon);
+ }
+ else if (type == EtcItemType.BOLT)
+ {
+ ammunition = _inventory.findBoltForCrossBow(weapon);
+ }
+
+ if (ammunition != null)
+ {
+ addAmmunitionSkills(ammunition);
+ sendItemList();
+ return true;
+ }
+
+ removeAmmunitionSkills();
+ return false;
+ }
+
+ private void addAmmunitionSkills(ItemInstance ammunition)
+ {
+ final int currentAmmunitionId = ammunition.getId();
+ if (_lastAmmunitionId == currentAmmunitionId)
+ {
+ return;
+ }
+ removeAmmunitionSkills();
+ _lastAmmunitionId = currentAmmunitionId;
+
+ final List<ItemSkillHolder> skills = ammunition.getItem().getAllSkills();
+ if (skills == null)
+ {
+ return;
+ }
+
+ boolean sendSkillList = false;
+ for (ItemSkillHolder holder : skills)
+ {
+ if (!isAffectedBySkill(holder))
{
- arrows = _inventory.findArrowForBow(weapon);
+ final Skill skill = holder.getSkill();
+ if (skill.isPassive())
+ {
+ addSkill(skill);
+ sendSkillList = true;
+ }
}
- else if (type == EtcItemType.BOLT)
+ }
+ if (sendSkillList)
+ {
+ sendSkillList();
+ }
+ }
+
+ public void removeAmmunitionSkills()
+ {
+ if (_lastAmmunitionId != 0)
+ {
+ boolean sendSkillList = false;
+ for (Integer skillId : AmmunitionSkillList.values())
{
- arrows = _inventory.findBoltForCrossBow(weapon);
+ if (removeSkill(skillId.intValue(), true) != null)
+ {
+ sendSkillList = true;
+ }
}
- if (arrows != null)
+ if (sendSkillList)
{
- // Equip arrows needed in left hand
- _inventory.setPaperdollItem(Inventory.PAPERDOLL_LHAND, arrows);
- sendItemList();
- return true;
+ sendSkillList();
}
}
- else
- {
- return true;
- }
- return false;
+ _lastAmmunitionId = 0;
}
/**
Index: java/org/l2jmobius/gameserver/model/itemcontainer/Inventory.java
===================================================================
--- java/org/l2jmobius/gameserver/model/itemcontainer/Inventory.java (revision 8502)
+++ java/org/l2jmobius/gameserver/model/itemcontainer/Inventory.java (working copy)
@@ -231,33 +231,50 @@
@Override
public void notifyUnequiped(int slot, ItemInstance item, Inventory inventory)
{
- if (slot != PAPERDOLL_RHAND)
+ if ((slot != PAPERDOLL_RHAND) || !item.isWeapon())
{
return;
}
- if (item.getItemType() == WeaponType.BOW)
+ switch (item.getWeaponItem().getItemType())
{
- final ItemInstance arrow = inventory.getPaperdollItem(PAPERDOLL_LHAND);
- if (arrow != null)
+ case BOW:
{
- inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ final ItemInstance leftHandItem = inventory.getPaperdollItem(PAPERDOLL_LHAND);
+ if (((leftHandItem != null) && ((leftHandItem.getItemType()) != ArmorType.SIGIL)))
+ {
+ inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ }
+ final PlayerInstance owner = inventory.getOwner().getActingPlayer();
+ if (owner != null)
+ {
+ owner.removeAmmunitionSkills();
+ }
+ break;
}
- }
- else if ((item.getItemType() == WeaponType.CROSSBOW) || (item.getItemType() == WeaponType.TWOHANDCROSSBOW))
- {
- final ItemInstance bolts = inventory.getPaperdollItem(PAPERDOLL_LHAND);
- if (bolts != null)
+ case CROSSBOW:
+ case TWOHANDCROSSBOW:
{
- inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ final ItemInstance leftHandItem = inventory.getPaperdollItem(PAPERDOLL_LHAND);
+ if (((leftHandItem != null) && ((leftHandItem.getItemType()) != ArmorType.SIGIL)))
+ {
+ inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ }
+ final PlayerInstance owner = inventory.getOwner().getActingPlayer();
+ if (owner != null)
+ {
+ owner.removeAmmunitionSkills();
+ }
+ break;
}
- }
- else if (item.getItemType() == WeaponType.FISHINGROD)
- {
- final ItemInstance lure = inventory.getPaperdollItem(PAPERDOLL_LHAND);
- if (lure != null)
+ case FISHINGROD:
{
- inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ final ItemInstance leftHandItem = inventory.getPaperdollItem(PAPERDOLL_LHAND);
+ if (leftHandItem != null)
+ {
+ inventory.setPaperdollItem(PAPERDOLL_LHAND, null);
+ }
+ break;
}
}
}
@@ -265,27 +282,6 @@
@Override
public void notifyEquiped(int slot, ItemInstance item, Inventory inventory)
{
- if (slot != PAPERDOLL_RHAND)
- {
- return;
- }
-
- if (item.getItemType() == WeaponType.BOW)
- {
- final ItemInstance arrow = inventory.findArrowForBow(item.getItem());
- if (arrow != null)
- {
- inventory.setPaperdollItem(PAPERDOLL_LHAND, arrow);
- }
- }
- else if ((item.getItemType() == WeaponType.CROSSBOW) || (item.getItemType() == WeaponType.TWOHANDCROSSBOW))
- {
- final ItemInstance bolts = inventory.findBoltForCrossBow(item.getItem());
- if (bolts != null)
- {
- inventory.setPaperdollItem(PAPERDOLL_LHAND, bolts);
- }
- }
}
}
@@ -2097,6 +2093,18 @@
}
/**
+ * Reduce the arrow number of the Creature.<br>
+ * <br>
+ * <b><u>Overridden in</u>:</b>
+ * <li>PlayerInstance</li><br>
+ * @param type
+ */
+ public void reduceAmmunitionCount(EtcItemType type)
+ {
+ // Default is to do nothing.
+ }
+
+ /**
* Return the ItemInstance of the arrows needed for this bow.
* @param bow : Item designating the bow
* @return ItemInstance pointing out arrows for bow
@@ -2463,18 +2471,6 @@
}
/**
- * Reduce the arrow number of the Creature.<br>
- * <br>
- * <b><u>Overridden in</u>:</b>
- * <li>PlayerInstance</li><br>
- * @param type
- */
- public void reduceArrowCount(EtcItemType type)
- {
- // default is to do nothing
- }
-
- /**
* Gets the items in paperdoll slots filtered by filter.
* @param filters multiple filters
* @return the filtered items in inventory
Index: java/org/l2jmobius/gameserver/model/itemcontainer/PlayerInventory.java
===================================================================
--- java/org/l2jmobius/gameserver/model/itemcontainer/PlayerInventory.java (revision 8502)
+++ java/org/l2jmobius/gameserver/model/itemcontainer/PlayerInventory.java (working copy)
@@ -42,6 +42,7 @@
import org.l2jmobius.gameserver.model.events.impl.creature.player.OnPlayerItemDrop;
import org.l2jmobius.gameserver.model.events.impl.creature.player.OnPlayerItemTransfer;
import org.l2jmobius.gameserver.model.items.Item;
+import org.l2jmobius.gameserver.model.items.Weapon;
import org.l2jmobius.gameserver.model.items.instance.ItemInstance;
import org.l2jmobius.gameserver.model.items.type.EtcItemType;
import org.l2jmobius.gameserver.model.variables.ItemVariables;
@@ -955,26 +956,52 @@
* @param type
*/
@Override
- public void reduceArrowCount(EtcItemType type)
+ public void reduceAmmunitionCount(EtcItemType type)
{
if ((type != EtcItemType.ARROW) && (type != EtcItemType.BOLT))
{
- LOGGER.log(Level.WARNING, type.toString(), " which is not arrow type passed to PlayerInstance.reduceArrowCount()");
+ LOGGER.log(Level.WARNING, type.toString(), " which is not ammo type.");
return;
}
- final ItemInstance arrows = getPaperdollItem(Inventory.PAPERDOLL_LHAND);
- if ((arrows == null) || (arrows.getItemType() != type))
+ final Weapon weapon = _owner.getActiveWeaponItem();
+ if (weapon == null)
{
return;
}
- if (arrows.getEtcItem().isInfinite()) // Null-safe due to type checks above
+ ItemInstance ammunition = null;
+ switch (weapon.getItemType())
{
+ case BOW:
+ {
+ ammunition = findArrowForBow(weapon);
+ break;
+ }
+ case CROSSBOW:
+ case TWOHANDCROSSBOW:
+ {
+ ammunition = findBoltForCrossBow(weapon);
+ break;
+ }
+ default:
+ {
+ return;
+ }
+ }
+
+ if ((ammunition == null) || (ammunition.getItemType() != type))
+ {
return;
}
- updateItemCountNoDbUpdate(null, arrows, -1, _owner, null);
+ if (ammunition.getEtcItem().isInfinite())
+ {
+ return;
+ }
+
+ // Reduce item count.
+ updateItemCountNoDbUpdate(null, ammunition, -1, _owner, null);
}
/**
Index: java/org/l2jmobius/gameserver/model/skills/AmmunitionSkillList.java
===================================================================
--- java/org/l2jmobius/gameserver/model/skills/AmmunitionSkillList.java (nonexistent)
+++ java/org/l2jmobius/gameserver/model/skills/AmmunitionSkillList.java (working copy)
@@ -0,0 +1,44 @@
+/*
+ * This file is part of the L2J Mobius project.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+package org.l2jmobius.gameserver.model.skills;
+
+import java.util.List;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+
+import org.l2jmobius.gameserver.model.holders.ItemSkillHolder;
+
+/**
+ * @author Mobius
+ */
+public class AmmunitionSkillList
+{
+ private static final Set<Integer> SKILLS = ConcurrentHashMap.newKeySet();
+
+ public static void add(List<ItemSkillHolder> skills)
+ {
+ for (ItemSkillHolder skill : skills)
+ {
+ SKILLS.add(skill.getSkillId());
+ }
+ }
+
+ public static Set<Integer> values()
+ {
+ return SKILLS;
+ }
+}