UseItem.java 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414
  1. /*
  2. * Copyright (C) 2004-2015 L2J Server
  3. *
  4. * This file is part of L2J Server.
  5. *
  6. * L2J Server is free software: you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation, either version 3 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * L2J Server is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  18. */
  19. package com.l2jserver.gameserver.network.clientpackets;
  20. import java.util.concurrent.TimeUnit;
  21. import java.util.logging.Level;
  22. import com.l2jserver.Config;
  23. import com.l2jserver.gameserver.ThreadPoolManager;
  24. import com.l2jserver.gameserver.ai.CtrlEvent;
  25. import com.l2jserver.gameserver.ai.CtrlIntention;
  26. import com.l2jserver.gameserver.ai.NextAction;
  27. import com.l2jserver.gameserver.enums.PrivateStoreType;
  28. import com.l2jserver.gameserver.enums.Race;
  29. import com.l2jserver.gameserver.handler.IItemHandler;
  30. import com.l2jserver.gameserver.handler.ItemHandler;
  31. import com.l2jserver.gameserver.instancemanager.FortSiegeManager;
  32. import com.l2jserver.gameserver.model.PcCondOverride;
  33. import com.l2jserver.gameserver.model.actor.instance.L2PcInstance;
  34. import com.l2jserver.gameserver.model.effects.L2EffectType;
  35. import com.l2jserver.gameserver.model.holders.SkillHolder;
  36. import com.l2jserver.gameserver.model.itemcontainer.Inventory;
  37. import com.l2jserver.gameserver.model.items.L2EtcItem;
  38. import com.l2jserver.gameserver.model.items.L2Item;
  39. import com.l2jserver.gameserver.model.items.L2Weapon;
  40. import com.l2jserver.gameserver.model.items.instance.L2ItemInstance;
  41. import com.l2jserver.gameserver.model.items.type.ArmorType;
  42. import com.l2jserver.gameserver.model.items.type.WeaponType;
  43. import com.l2jserver.gameserver.model.skills.Skill;
  44. import com.l2jserver.gameserver.network.SystemMessageId;
  45. import com.l2jserver.gameserver.network.serverpackets.ActionFailed;
  46. import com.l2jserver.gameserver.network.serverpackets.ExUseSharedGroupItem;
  47. import com.l2jserver.gameserver.network.serverpackets.ItemList;
  48. import com.l2jserver.gameserver.network.serverpackets.SystemMessage;
  49. public final class UseItem extends L2GameClientPacket
  50. {
  51. private static final String _C__19_USEITEM = "[C] 19 UseItem";
  52. private int _objectId;
  53. private boolean _ctrlPressed;
  54. private int _itemId;
  55. /** Weapon Equip Task */
  56. private static class WeaponEquipTask implements Runnable
  57. {
  58. private final L2ItemInstance item;
  59. private final L2PcInstance activeChar;
  60. protected WeaponEquipTask(L2ItemInstance it, L2PcInstance character)
  61. {
  62. item = it;
  63. activeChar = character;
  64. }
  65. @Override
  66. public void run()
  67. {
  68. // Equip or unEquip
  69. activeChar.useEquippableItem(item, false);
  70. }
  71. }
  72. @Override
  73. protected void readImpl()
  74. {
  75. _objectId = readD();
  76. _ctrlPressed = readD() != 0;
  77. }
  78. @Override
  79. protected void runImpl()
  80. {
  81. final L2PcInstance activeChar = getClient().getActiveChar();
  82. if (activeChar == null)
  83. {
  84. return;
  85. }
  86. if (Config.DEBUG)
  87. {
  88. _log.log(Level.INFO, activeChar + ": use item " + _objectId);
  89. }
  90. // Flood protect UseItem
  91. if (!getClient().getFloodProtectors().getUseItem().tryPerformAction("use item"))
  92. {
  93. return;
  94. }
  95. if (activeChar.getActiveTradeList() != null)
  96. {
  97. activeChar.cancelActiveTrade();
  98. }
  99. if (activeChar.getPrivateStoreType() != PrivateStoreType.NONE)
  100. {
  101. activeChar.sendPacket(SystemMessageId.CANNOT_TRADE_DISCARD_DROP_ITEM_WHILE_IN_SHOPMODE);
  102. activeChar.sendPacket(ActionFailed.STATIC_PACKET);
  103. return;
  104. }
  105. final L2ItemInstance item = activeChar.getInventory().getItemByObjectId(_objectId);
  106. if (item == null)
  107. {
  108. return;
  109. }
  110. if (item.getItem().getType2() == L2Item.TYPE2_QUEST)
  111. {
  112. activeChar.sendPacket(SystemMessageId.CANNOT_USE_QUEST_ITEMS);
  113. return;
  114. }
  115. // No UseItem is allowed while the player is in special conditions
  116. if (activeChar.isStunned() || activeChar.isParalyzed() || activeChar.isSleeping() || activeChar.isAfraid() || activeChar.isAlikeDead())
  117. {
  118. return;
  119. }
  120. _itemId = item.getId();
  121. // Char cannot use item when dead
  122. if (activeChar.isDead() || !activeChar.getInventory().canManipulateWithItemId(_itemId))
  123. {
  124. final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.S1_CANNOT_BE_USED);
  125. sm.addItemName(item);
  126. activeChar.sendPacket(sm);
  127. return;
  128. }
  129. if (!item.isEquipped() && !item.getItem().checkCondition(activeChar, activeChar, true))
  130. {
  131. return;
  132. }
  133. if (activeChar.isFishing() && ((_itemId < 6535) || (_itemId > 6540)))
  134. {
  135. // You cannot do anything else while fishing
  136. activeChar.sendPacket(SystemMessageId.CANNOT_DO_WHILE_FISHING_3);
  137. return;
  138. }
  139. if (!Config.ALT_GAME_KARMA_PLAYER_CAN_TELEPORT && (activeChar.getKarma() > 0))
  140. {
  141. SkillHolder[] skills = item.getItem().getSkills();
  142. if (skills != null)
  143. {
  144. for (SkillHolder sHolder : skills)
  145. {
  146. Skill skill = sHolder.getSkill();
  147. if ((skill != null) && skill.hasEffectType(L2EffectType.TELEPORT))
  148. {
  149. return;
  150. }
  151. }
  152. }
  153. }
  154. // If the item has reuse time and it has not passed.
  155. // Message from reuse delay must come from item.
  156. final int reuseDelay = item.getReuseDelay();
  157. final int sharedReuseGroup = item.getSharedReuseGroup();
  158. if (reuseDelay > 0)
  159. {
  160. final long reuse = activeChar.getItemRemainingReuseTime(item.getObjectId());
  161. if (reuse > 0)
  162. {
  163. reuseData(activeChar, item, reuse);
  164. sendSharedGroupUpdate(activeChar, sharedReuseGroup, reuse, reuseDelay);
  165. return;
  166. }
  167. final long reuseOnGroup = activeChar.getReuseDelayOnGroup(sharedReuseGroup);
  168. if (reuseOnGroup > 0)
  169. {
  170. reuseData(activeChar, item, reuseOnGroup);
  171. sendSharedGroupUpdate(activeChar, sharedReuseGroup, reuseOnGroup, reuseDelay);
  172. return;
  173. }
  174. }
  175. if (item.isEquipable())
  176. {
  177. // Don't allow to put formal wear while a cursed weapon is equipped.
  178. if (activeChar.isCursedWeaponEquipped() && (_itemId == 6408))
  179. {
  180. return;
  181. }
  182. // Equip or unEquip
  183. if (FortSiegeManager.getInstance().isCombat(_itemId))
  184. {
  185. return; // no message
  186. }
  187. if (activeChar.isCombatFlagEquipped())
  188. {
  189. return;
  190. }
  191. switch (item.getItem().getBodyPart())
  192. {
  193. case L2Item.SLOT_LR_HAND:
  194. case L2Item.SLOT_L_HAND:
  195. case L2Item.SLOT_R_HAND:
  196. {
  197. // Prevent players to equip weapon while wearing combat flag
  198. if ((activeChar.getActiveWeaponItem() != null) && (activeChar.getActiveWeaponItem().getId() == 9819))
  199. {
  200. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  201. return;
  202. }
  203. if (activeChar.isMounted())
  204. {
  205. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  206. return;
  207. }
  208. if (activeChar.isDisarmed())
  209. {
  210. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  211. return;
  212. }
  213. // Don't allow weapon/shield equipment if a cursed weapon is equipped.
  214. if (activeChar.isCursedWeaponEquipped())
  215. {
  216. return;
  217. }
  218. // Don't allow other Race to Wear Kamael exclusive Weapons.
  219. if (!item.isEquipped() && item.isWeapon() && !activeChar.canOverrideCond(PcCondOverride.ITEM_CONDITIONS))
  220. {
  221. L2Weapon wpn = (L2Weapon) item.getItem();
  222. switch (activeChar.getRace())
  223. {
  224. case KAMAEL:
  225. {
  226. switch (wpn.getItemType())
  227. {
  228. case NONE:
  229. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  230. return;
  231. }
  232. break;
  233. }
  234. case HUMAN:
  235. case DWARF:
  236. case ELF:
  237. case DARK_ELF:
  238. case ORC:
  239. {
  240. switch (wpn.getItemType())
  241. {
  242. case RAPIER:
  243. case CROSSBOW:
  244. case ANCIENTSWORD:
  245. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  246. return;
  247. }
  248. break;
  249. }
  250. }
  251. }
  252. break;
  253. }
  254. case L2Item.SLOT_CHEST:
  255. case L2Item.SLOT_BACK:
  256. case L2Item.SLOT_GLOVES:
  257. case L2Item.SLOT_FEET:
  258. case L2Item.SLOT_HEAD:
  259. case L2Item.SLOT_FULL_ARMOR:
  260. case L2Item.SLOT_LEGS:
  261. {
  262. if ((activeChar.getRace() == Race.KAMAEL) && ((item.getItem().getItemType() == ArmorType.HEAVY) || (item.getItem().getItemType() == ArmorType.MAGIC)))
  263. {
  264. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  265. return;
  266. }
  267. break;
  268. }
  269. case L2Item.SLOT_DECO:
  270. {
  271. if (!item.isEquipped() && (activeChar.getInventory().getTalismanSlots() == 0))
  272. {
  273. activeChar.sendPacket(SystemMessageId.CANNOT_EQUIP_ITEM_DUE_TO_BAD_CONDITION);
  274. return;
  275. }
  276. }
  277. }
  278. if (activeChar.isCastingNow() || activeChar.isCastingSimultaneouslyNow())
  279. {
  280. // Creating next action class.
  281. final NextAction nextAction = new NextAction(CtrlEvent.EVT_FINISH_CASTING, CtrlIntention.AI_INTENTION_CAST, () -> activeChar.useEquippableItem(item, true));
  282. // Binding next action to AI.
  283. activeChar.getAI().setNextAction(nextAction);
  284. }
  285. else if (activeChar.isAttackingNow())
  286. {
  287. ThreadPoolManager.getInstance().scheduleGeneral(new WeaponEquipTask(item, activeChar), TimeUnit.MILLISECONDS.convert(activeChar.getAttackEndTime() - System.nanoTime(), TimeUnit.NANOSECONDS));
  288. }
  289. else
  290. {
  291. activeChar.useEquippableItem(item, true);
  292. }
  293. }
  294. else
  295. {
  296. final L2Weapon weaponItem = activeChar.getActiveWeaponItem();
  297. if (((weaponItem != null) && (weaponItem.getItemType() == WeaponType.FISHINGROD)) && (((_itemId >= 6519) && (_itemId <= 6527)) || ((_itemId >= 7610) && (_itemId <= 7613)) || ((_itemId >= 7807) && (_itemId <= 7809)) || ((_itemId >= 8484) && (_itemId <= 8486)) || ((_itemId >= 8505) && (_itemId <= 8513))))
  298. {
  299. activeChar.getInventory().setPaperdollItem(Inventory.PAPERDOLL_LHAND, item);
  300. activeChar.broadcastUserInfo();
  301. // Send a Server->Client packet ItemList to this L2PcINstance to update left hand equipment.
  302. sendPacket(new ItemList(activeChar, false));
  303. return;
  304. }
  305. final L2EtcItem etcItem = item.getEtcItem();
  306. final IItemHandler handler = ItemHandler.getInstance().getHandler(etcItem);
  307. if (handler == null)
  308. {
  309. if ((etcItem != null) && (etcItem.getHandlerName() != null))
  310. {
  311. _log.log(Level.WARNING, "Unmanaged Item handler: " + etcItem.getHandlerName() + " for Item Id: " + _itemId + "!");
  312. }
  313. else if (Config.DEBUG)
  314. {
  315. _log.log(Level.WARNING, "No Item handler registered for Item Id: " + _itemId + "!");
  316. }
  317. return;
  318. }
  319. // Item reuse time should be added if the item is successfully used.
  320. // Skill reuse delay is done at handlers.itemhandlers.ItemSkillsTemplate;
  321. if (handler.useItem(activeChar, item, _ctrlPressed))
  322. {
  323. if (reuseDelay > 0)
  324. {
  325. activeChar.addTimeStampItem(item, reuseDelay);
  326. sendSharedGroupUpdate(activeChar, sharedReuseGroup, reuseDelay, reuseDelay);
  327. }
  328. }
  329. }
  330. }
  331. private void reuseData(L2PcInstance activeChar, L2ItemInstance item, long remainingTime)
  332. {
  333. final int hours = (int) (remainingTime / 3600000L);
  334. final int minutes = (int) (remainingTime % 3600000L) / 60000;
  335. final int seconds = (int) ((remainingTime / 1000) % 60);
  336. final SystemMessage sm;
  337. if (hours > 0)
  338. {
  339. sm = SystemMessage.getSystemMessage(SystemMessageId.S2_HOURS_S3_MINUTES_S4_SECONDS_REMAINING_FOR_REUSE_S1);
  340. sm.addItemName(item);
  341. sm.addInt(hours);
  342. sm.addInt(minutes);
  343. }
  344. else if (minutes > 0)
  345. {
  346. sm = SystemMessage.getSystemMessage(SystemMessageId.S2_MINUTES_S3_SECONDS_REMAINING_FOR_REUSE_S1);
  347. sm.addItemName(item);
  348. sm.addInt(minutes);
  349. }
  350. else
  351. {
  352. sm = SystemMessage.getSystemMessage(SystemMessageId.S2_SECONDS_REMAINING_FOR_REUSE_S1);
  353. sm.addItemName(item);
  354. }
  355. sm.addInt(seconds);
  356. activeChar.sendPacket(sm);
  357. }
  358. private void sendSharedGroupUpdate(L2PcInstance activeChar, int group, long remaining, int reuse)
  359. {
  360. if (group > 0)
  361. {
  362. activeChar.sendPacket(new ExUseSharedGroupItem(_itemId, group, remaining, reuse));
  363. }
  364. }
  365. @Override
  366. public String getType()
  367. {
  368. return _C__19_USEITEM;
  369. }
  370. @Override
  371. protected boolean triggersOnActionRequest()
  372. {
  373. return !Config.SPAWN_PROTECTION_ALLOWED_ITEMS.contains(_itemId);
  374. }
  375. }