Advertisement
Guest User

Untitled

a guest
Feb 20th, 2018
96
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 314.61 KB | None | 0 0
  1. #include "stdafx.h"
  2.  
  3. #include <stack>
  4.  
  5. #include "utils.h"
  6. #include "config.h"
  7. #include "char.h"
  8. #include "char_manager.h"
  9. #include "item_manager.h"
  10. #include "desc.h"
  11. #include "desc_client.h"
  12. #include "desc_manager.h"
  13. #include "packet.h"
  14. #include "affect.h"
  15. #include "skill.h"
  16. #include "start_position.h"
  17. #include "mob_manager.h"
  18. #include "db.h"
  19. #include "log.h"
  20. #include "vector.h"
  21. #include "buffer_manager.h"
  22. #include "questmanager.h"
  23. #include "fishing.h"
  24. #include "party.h"
  25. #include "dungeon.h"
  26. #include "refine.h"
  27. #include "unique_item.h"
  28. #include "war_map.h"
  29. #include "xmas_event.h"
  30. #include "marriage.h"
  31. #include "monarch.h"
  32. #include "polymorph.h"
  33. #include "blend_item.h"
  34. #include "castle.h"
  35. #include "BattleArena.h"
  36. #include "arena.h"
  37. #include "dev_log.h"
  38. #include "pcbang.h"
  39. #include "threeway_war.h"
  40.  
  41. #include "safebox.h"
  42. #include "shop.h"
  43.  
  44. #include "../../common/VnumHelper.h"
  45. #include "DragonSoul.h"
  46. #include "buff_on_attributes.h"
  47. #include "belt_inventory_helper.h"
  48.  
  49. //auction_temp
  50. #ifdef __AUCTION__
  51. #include "auction_manager.h"
  52. #endif
  53. const int ITEM_BROKEN_METIN_VNUM = 28960;
  54.  
  55. // CHANGE_ITEM_ATTRIBUTES
  56. const DWORD CHARACTER::msc_dwDefaultChangeItemAttrCycle = 10;
  57. const char CHARACTER::msc_szLastChangeItemAttrFlag[] = "Item.LastChangeItemAttr";
  58. const char CHARACTER::msc_szChangeItemAttrCycleFlag[] = "change_itemattr_cycle";
  59. // END_OF_CHANGE_ITEM_ATTRIBUTES
  60. const BYTE g_aBuffOnAttrPoints[] = { POINT_ENERGY, POINT_COSTUME_ATTR_BONUS };
  61.  
  62. struct FFindStone
  63. {
  64. std::map<DWORD, LPCHARACTER> m_mapStone;
  65.  
  66. void operator()(LPENTITY pEnt)
  67. {
  68. if (pEnt->IsType(ENTITY_CHARACTER) == true)
  69. {
  70. LPCHARACTER pChar = (LPCHARACTER)pEnt;
  71.  
  72. if (pChar->IsStone() == true)
  73. {
  74. m_mapStone[(DWORD)pChar->GetVID()] = pChar;
  75. }
  76. }
  77. }
  78. };
  79.  
  80.  
  81. //±ÍČŻşÎ, ±ÍČŻ±âľďşÎ, °áČĄąÝÁö
  82. static bool IS_SUMMON_ITEM(int vnum)
  83. {
  84. switch (vnum)
  85. {
  86. case 22000:
  87. case 22010:
  88. case 22011:
  89. case 22020:
  90. case ITEM_MARRIAGE_RING:
  91. return true;
  92. }
  93.  
  94. return false;
  95. }
  96.  
  97. static bool IS_MONKEY_DUNGEON(int map_index)
  98. {
  99. switch (map_index)
  100. {
  101. case 5:
  102. case 25:
  103. case 45:
  104. case 108:
  105. case 109:
  106. return true;;
  107. }
  108.  
  109. return false;
  110. }
  111.  
  112. bool IS_SUMMONABLE_ZONE(int map_index)
  113. {
  114. // ¸ůĹ°´řŔü
  115. if (IS_MONKEY_DUNGEON(map_index))
  116. return false;
  117. // Ľş
  118. if (IS_CASTLE_MAP(map_index))
  119. return false;
  120.  
  121. switch (map_index)
  122. {
  123. case 66 : // »ç±ÍŸżö
  124. case 71 : // °ĹąĚ ´řŔü 2Ăţ
  125. case 72 : // õŔÇ µż±Ľ
  126. case 73 : // õŔÇ µż±Ľ 2Ăţ
  127. case 193 : // °ĹąĚ ´řŔü 2-1Ăţ
  128. #if 0
  129. case 184 : // õŔÇ µż±Ľ(˝ĹĽö)
  130. case 185 : // õŔÇ µż±Ľ 2Ăţ(˝ĹĽö)
  131. case 186 : // õŔÇ µż±Ľ(õÁ¶)
  132. case 187 : // õŔÇ µż±Ľ 2Ăţ(õÁ¶)
  133. case 188 : // õŔÇ µż±Ľ(Ářłë)
  134. case 189 : // õŔÇ µż±Ľ 2Ăţ(Ářłë)
  135. #endif
  136. // case 206 : // ľĆ±Íµż±Ľ
  137. case 216 : // ľĆ±Íµż±Ľ
  138. case 217 : // °ĹąĚ ´řŔü 3Ăţ
  139. case 208 : // õŔÇ µż±Ľ (żëąć)
  140. return false;
  141. }
  142.  
  143. if (CBattleArena::IsBattleArenaMap(map_index)) return false;
  144.  
  145. // ¸đµç private ¸ĘŔ¸·Đ żöÇÁ şŇ°ˇ´É
  146. if (map_index > 10000) return false;
  147.  
  148. return true;
  149. }
  150.  
  151. bool IS_BOTARYABLE_ZONE(int nMapIndex)
  152. {
  153. if (LC_IsYMIR() == false && LC_IsKorea() == false) return true;
  154.  
  155. switch (nMapIndex)
  156. {
  157. case 1 :
  158. case 3 :
  159. case 21 :
  160. case 23 :
  161. case 41 :
  162. case 43 :
  163. return true;
  164. }
  165.  
  166. return false;
  167. }
  168.  
  169. // item socket ŔĚ ÇÁ·ÎĹäŸŔÔ°ú °°ŔşÁö ĂĽĹ© -- by mhh
  170. static bool FN_check_item_socket(LPITEM item)
  171. {
  172. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  173. {
  174. if (item->GetSocket(i) != item->GetProto()->alSockets[i])
  175. return false;
  176. }
  177.  
  178. return true;
  179. }
  180.  
  181. // item socket şą»ç -- by mhh
  182. static void FN_copy_item_socket(LPITEM dest, LPITEM src)
  183. {
  184. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  185. {
  186. dest->SetSocket(i, src->GetSocket(i));
  187. }
  188. }
  189. static bool FN_check_item_sex(LPCHARACTER ch, LPITEM item)
  190. {
  191. // ł˛ŔÚ ±ÝÁö
  192. if (IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_MALE))
  193. {
  194. if (SEX_MALE==GET_SEX(ch))
  195. return false;
  196. }
  197. // ż©ŔÚ±ÝÁö
  198. if (IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_FEMALE))
  199. {
  200. if (SEX_FEMALE==GET_SEX(ch))
  201. return false;
  202. }
  203.  
  204. return true;
  205. }
  206.  
  207.  
  208. /////////////////////////////////////////////////////////////////////////////
  209. // ITEM HANDLING
  210. /////////////////////////////////////////////////////////////////////////////
  211. bool CHARACTER::CanHandleItem(bool bSkipCheckRefine, bool bSkipObserver)
  212. {
  213. if (!bSkipObserver)
  214. if (m_bIsObserver)
  215. return false;
  216.  
  217. if (GetMyShop())
  218. return false;
  219.  
  220. if (!bSkipCheckRefine)
  221. if (m_bUnderRefine)
  222. return false;
  223.  
  224. if (IsCubeOpen() || NULL != DragonSoul_RefineWindow_GetOpener())
  225. return false;
  226.  
  227. if (IsWarping())
  228. return false;
  229.  
  230. return true;
  231. }
  232.  
  233. LPITEM CHARACTER::GetInventoryItem(WORD wCell) const
  234. {
  235. return GetItem(TItemPos(INVENTORY, wCell));
  236. }
  237. LPITEM CHARACTER::GetItem(TItemPos Cell) const
  238. {
  239. if (!IsValidItemPosition(Cell))
  240. return NULL;
  241. WORD wCell = Cell.cell;
  242. BYTE window_type = Cell.window_type;
  243. switch (window_type)
  244. {
  245. case INVENTORY:
  246. case EQUIPMENT:
  247. if (wCell >= INVENTORY_AND_EQUIP_SLOT_MAX)
  248. {
  249. sys_err("CHARACTER::GetInventoryItem: invalid item cell %d", wCell);
  250. return NULL;
  251. }
  252. return m_pointsInstant.pItems[wCell];
  253. case DRAGON_SOUL_INVENTORY:
  254. if (wCell >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  255. {
  256. sys_err("CHARACTER::GetInventoryItem: invalid DS item cell %d", wCell);
  257. return NULL;
  258. }
  259. return m_pointsInstant.pDSItems[wCell];
  260.  
  261. default:
  262. return NULL;
  263. }
  264. return NULL;
  265. }
  266.  
  267. void CHARACTER::SetItem(TItemPos Cell, LPITEM pItem)
  268. {
  269. WORD wCell = Cell.cell;
  270. BYTE window_type = Cell.window_type;
  271. if ((unsigned long)((CItem*)pItem) == 0xff || (unsigned long)((CItem*)pItem) == 0xffffffff)
  272. {
  273. sys_err("!!! FATAL ERROR !!! item == 0xff (char: %s cell: %u)", GetName(), wCell);
  274. core_dump();
  275. return;
  276. }
  277.  
  278. if (pItem && pItem->GetOwner())
  279. {
  280. assert(!"GetOwner exist");
  281. return;
  282. }
  283. // ±âş» ŔÎşĄĹ丮
  284. switch(window_type)
  285. {
  286. case INVENTORY:
  287. case EQUIPMENT:
  288. {
  289. if (wCell >= INVENTORY_AND_EQUIP_SLOT_MAX)
  290. {
  291. sys_err("CHARACTER::SetItem: invalid item cell %d", wCell);
  292. return;
  293. }
  294.  
  295. LPITEM pOld = m_pointsInstant.pItems[wCell];
  296.  
  297. if (pOld)
  298. {
  299. if (wCell < INVENTORY_MAX_NUM)
  300. {
  301. for (int i = 0; i < pOld->GetSize(); ++i)
  302. {
  303. int p = wCell + (i * 5);
  304.  
  305. if (p >= INVENTORY_MAX_NUM)
  306. continue;
  307.  
  308. if (m_pointsInstant.pItems[p] && m_pointsInstant.pItems[p] != pOld)
  309. continue;
  310.  
  311. m_pointsInstant.bItemGrid[p] = 0;
  312. }
  313. }
  314. else
  315. m_pointsInstant.bItemGrid[wCell] = 0;
  316. }
  317.  
  318. if (pItem)
  319. {
  320. if (wCell < INVENTORY_MAX_NUM)
  321. {
  322. for (int i = 0; i < pItem->GetSize(); ++i)
  323. {
  324. int p = wCell + (i * 5);
  325.  
  326. if (p >= INVENTORY_MAX_NUM)
  327. continue;
  328.  
  329. // wCell + 1 ·Î ÇĎ´Â °ÍŔş şó°÷Ŕ» ĂĽĹ©ÇŇ ¶§ °°Ŕş
  330. // ľĆŔĚĹŰŔş żążÜĂł¸®Çϱâ Ŕ§ÇÔ
  331. m_pointsInstant.bItemGrid[p] = wCell + 1;
  332. }
  333. }
  334. else
  335. m_pointsInstant.bItemGrid[wCell] = wCell + 1;
  336. }
  337.  
  338. m_pointsInstant.pItems[wCell] = pItem;
  339. }
  340. break;
  341. // żëČĄĽ® ŔÎşĄĹ丮
  342. case DRAGON_SOUL_INVENTORY:
  343. {
  344. LPITEM pOld = m_pointsInstant.pDSItems[wCell];
  345.  
  346. if (pOld)
  347. {
  348. if (wCell < DRAGON_SOUL_INVENTORY_MAX_NUM)
  349. {
  350. for (int i = 0; i < pOld->GetSize(); ++i)
  351. {
  352. int p = wCell + (i * DRAGON_SOUL_BOX_COLUMN_NUM);
  353.  
  354. if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  355. continue;
  356.  
  357. if (m_pointsInstant.pDSItems[p] && m_pointsInstant.pDSItems[p] != pOld)
  358. continue;
  359.  
  360. m_pointsInstant.wDSItemGrid[p] = 0;
  361. }
  362. }
  363. else
  364. m_pointsInstant.wDSItemGrid[wCell] = 0;
  365. }
  366.  
  367. if (pItem)
  368. {
  369. if (wCell >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  370. {
  371. sys_err("CHARACTER::SetItem: invalid DS item cell %d", wCell);
  372. return;
  373. }
  374.  
  375. if (wCell < DRAGON_SOUL_INVENTORY_MAX_NUM)
  376. {
  377. for (int i = 0; i < pItem->GetSize(); ++i)
  378. {
  379. int p = wCell + (i * DRAGON_SOUL_BOX_COLUMN_NUM);
  380.  
  381. if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  382. continue;
  383.  
  384. // wCell + 1 ·Î ÇĎ´Â °ÍŔş şó°÷Ŕ» ĂĽĹ©ÇŇ ¶§ °°Ŕş
  385. // ľĆŔĚĹŰŔş żążÜĂł¸®Çϱâ Ŕ§ÇÔ
  386. m_pointsInstant.wDSItemGrid[p] = wCell + 1;
  387. }
  388. }
  389. else
  390. m_pointsInstant.wDSItemGrid[wCell] = wCell + 1;
  391. }
  392.  
  393. m_pointsInstant.pDSItems[wCell] = pItem;
  394. }
  395. break;
  396. default:
  397. sys_err ("Invalid Inventory type %d", window_type);
  398. return;
  399. }
  400.  
  401. if (GetDesc())
  402. {
  403. // Č®Ŕĺ ľĆŔĚĹŰ: Ľ­ąöżˇĽ­ ľĆŔĚĹŰ ÇĂ·ˇ±× Á¤ş¸¸¦ ş¸ł˝´Ů
  404. if (pItem)
  405. {
  406. TPacketGCItemSet pack;
  407. pack.header = HEADER_GC_ITEM_SET;
  408. pack.Cell = Cell;
  409.  
  410. pack.count = pItem->GetCount();
  411. pack.vnum = pItem->GetVnum();
  412. pack.flags = pItem->GetFlag();
  413. pack.anti_flags = pItem->GetAntiFlag();
  414. pack.highlight = (Cell.window_type == DRAGON_SOUL_INVENTORY);
  415.  
  416.  
  417. thecore_memcpy(pack.alSockets, pItem->GetSockets(), sizeof(pack.alSockets));
  418. thecore_memcpy(pack.aAttr, pItem->GetAttributes(), sizeof(pack.aAttr));
  419.  
  420. GetDesc()->Packet(&pack, sizeof(TPacketGCItemSet));
  421. }
  422. else
  423. {
  424. TPacketGCItemDelDeprecated pack;
  425. pack.header = HEADER_GC_ITEM_DEL;
  426. pack.Cell = Cell;
  427. pack.count = 0;
  428. pack.vnum = 0;
  429. memset(pack.alSockets, 0, sizeof(pack.alSockets));
  430. memset(pack.aAttr, 0, sizeof(pack.aAttr));
  431.  
  432. GetDesc()->Packet(&pack, sizeof(TPacketGCItemDelDeprecated));
  433. }
  434. }
  435.  
  436. if (pItem)
  437. {
  438. pItem->SetCell(this, wCell);
  439. switch (window_type)
  440. {
  441. case INVENTORY:
  442. case EQUIPMENT:
  443. if ((wCell < INVENTORY_MAX_NUM) || (BELT_INVENTORY_SLOT_START <= wCell && BELT_INVENTORY_SLOT_END > wCell))
  444. pItem->SetWindow(INVENTORY);
  445. else
  446. pItem->SetWindow(EQUIPMENT);
  447. break;
  448. case DRAGON_SOUL_INVENTORY:
  449. pItem->SetWindow(DRAGON_SOUL_INVENTORY);
  450. break;
  451. }
  452. }
  453. }
  454.  
  455. LPITEM CHARACTER::GetWear(BYTE bCell) const
  456. {
  457. // > WEAR_MAX_NUM : żëČĄĽ® ˝˝·Ôµé.
  458. if (bCell >= WEAR_MAX_NUM + DRAGON_SOUL_DECK_MAX_NUM * DS_SLOT_MAX)
  459. {
  460. sys_err("CHARACTER::GetWear: invalid wear cell %d", bCell);
  461. return NULL;
  462. }
  463.  
  464. return m_pointsInstant.pItems[INVENTORY_MAX_NUM + bCell];
  465. }
  466.  
  467. void CHARACTER::SetWear(BYTE bCell, LPITEM item)
  468. {
  469. // > WEAR_MAX_NUM : żëČĄĽ® ˝˝·Ôµé.
  470. if (bCell >= WEAR_MAX_NUM + DRAGON_SOUL_DECK_MAX_NUM * DS_SLOT_MAX)
  471. {
  472. sys_err("CHARACTER::SetItem: invalid item cell %d", bCell);
  473. return;
  474. }
  475.  
  476. SetItem(TItemPos (INVENTORY, INVENTORY_MAX_NUM + bCell), item);
  477.  
  478. if (!item && bCell == WEAR_WEAPON)
  479. {
  480. // ±Í°Ë »çżë ˝Ă ąţ´Â °ÍŔ̶ó¸é Čż°ú¸¦ ľřľÖľß ÇŃ´Ů.
  481. if (IsAffectFlag(AFF_GWIGUM))
  482. RemoveAffect(SKILL_GWIGEOM);
  483.  
  484. if (IsAffectFlag(AFF_GEOMGYEONG))
  485. RemoveAffect(SKILL_GEOMKYUNG);
  486. }
  487. }
  488.  
  489. void CHARACTER::ClearItem()
  490. {
  491. int i;
  492. LPITEM item;
  493.  
  494. for (i = 0; i < INVENTORY_AND_EQUIP_SLOT_MAX; ++i)
  495. {
  496. if ((item = GetInventoryItem(i)))
  497. {
  498. item->SetSkipSave(true);
  499. ITEM_MANAGER::instance().FlushDelayedSave(item);
  500.  
  501. item->RemoveFromCharacter();
  502. M2_DESTROY_ITEM(item);
  503.  
  504. SyncQuickslot(QUICKSLOT_TYPE_ITEM, i, 255);
  505. }
  506. }
  507. for (i = 0; i < DRAGON_SOUL_INVENTORY_MAX_NUM; ++i)
  508. {
  509. if ((item = GetItem(TItemPos(DRAGON_SOUL_INVENTORY, i))))
  510. {
  511. item->SetSkipSave(true);
  512. ITEM_MANAGER::instance().FlushDelayedSave(item);
  513.  
  514. item->RemoveFromCharacter();
  515. M2_DESTROY_ITEM(item);
  516. }
  517. }
  518. }
  519.  
  520. bool CHARACTER::IsEmptyItemGrid(TItemPos Cell, BYTE bSize, int iExceptionCell) const
  521. {
  522. switch (Cell.window_type)
  523. {
  524. case INVENTORY:
  525. {
  526. BYTE bCell = Cell.cell;
  527.  
  528. // bItemCellŔş 0ŔĚ falseŔÓŔ» łŞĹ¸ł»±â Ŕ§ÇŘ + 1 ÇŘĽ­ Ăł¸®ÇŃ´Ů.
  529. // µű¶óĽ­ iExceptionCellżˇ 1Ŕ» ´őÇŘ şń±łÇŃ´Ů.
  530. ++iExceptionCell;
  531.  
  532. if (Cell.IsBeltInventoryPosition())
  533. {
  534. LPITEM beltItem = GetWear(WEAR_BELT);
  535.  
  536. if (NULL == beltItem)
  537. return false;
  538.  
  539. if (false == CBeltInventoryHelper::IsAvailableCell(bCell - BELT_INVENTORY_SLOT_START, beltItem->GetValue(0)))
  540. return false;
  541.  
  542. if (m_pointsInstant.bItemGrid[bCell])
  543. {
  544. if (m_pointsInstant.bItemGrid[bCell] == iExceptionCell)
  545. return true;
  546.  
  547. return false;
  548. }
  549.  
  550. if (bSize == 1)
  551. return true;
  552.  
  553. }
  554. else if (bCell >= INVENTORY_MAX_NUM)
  555. return false;
  556.  
  557. if (m_pointsInstant.bItemGrid[bCell])
  558. {
  559. if (m_pointsInstant.bItemGrid[bCell] == iExceptionCell)
  560. {
  561. if (bSize == 1)
  562. return true;
  563.  
  564. int j = 1;
  565. BYTE bPage = bCell / (INVENTORY_MAX_NUM / 2);
  566.  
  567. do
  568. {
  569. BYTE p = bCell + (5 * j);
  570.  
  571. if (p >= INVENTORY_MAX_NUM)
  572. return false;
  573.  
  574. if (p / (INVENTORY_MAX_NUM / 2) != bPage)
  575. return false;
  576.  
  577. if (m_pointsInstant.bItemGrid[p])
  578. if (m_pointsInstant.bItemGrid[p] != iExceptionCell)
  579. return false;
  580. }
  581. while (++j < bSize);
  582.  
  583. return true;
  584. }
  585. else
  586. return false;
  587. }
  588.  
  589. // Ĺ©±â°ˇ 1Ŕ̸é ÇŃÄ­Ŕ» Â÷ÁöÇĎ´Â °ÍŔ̹ǷΠ±×łÉ ¸®ĹĎ
  590. if (1 == bSize)
  591. return true;
  592. else
  593. {
  594. int j = 1;
  595. BYTE bPage = bCell / (INVENTORY_MAX_NUM / 2);
  596.  
  597. do
  598. {
  599. BYTE p = bCell + (5 * j);
  600.  
  601. if (p >= INVENTORY_MAX_NUM)
  602. return false;
  603.  
  604. if (p / (INVENTORY_MAX_NUM / 2) != bPage)
  605. return false;
  606.  
  607. if (m_pointsInstant.bItemGrid[p])
  608. if (m_pointsInstant.bItemGrid[p] != iExceptionCell)
  609. return false;
  610. }
  611. while (++j < bSize);
  612.  
  613. return true;
  614. }
  615. }
  616. break;
  617. case DRAGON_SOUL_INVENTORY:
  618. {
  619. WORD wCell = Cell.cell;
  620. if (wCell >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  621. return false;
  622.  
  623. // bItemCellŔş 0ŔĚ falseŔÓŔ» łŞĹ¸ł»±â Ŕ§ÇŘ + 1 ÇŘĽ­ Ăł¸®ÇŃ´Ů.
  624. // µű¶óĽ­ iExceptionCellżˇ 1Ŕ» ´őÇŘ şń±łÇŃ´Ů.
  625. iExceptionCell++;
  626.  
  627. if (m_pointsInstant.wDSItemGrid[wCell])
  628. {
  629. if (m_pointsInstant.wDSItemGrid[wCell] == iExceptionCell)
  630. {
  631. if (bSize == 1)
  632. return true;
  633.  
  634. int j = 1;
  635.  
  636. do
  637. {
  638. BYTE p = wCell + (DRAGON_SOUL_BOX_COLUMN_NUM * j);
  639.  
  640. if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  641. return false;
  642.  
  643. if (m_pointsInstant.wDSItemGrid[p])
  644. if (m_pointsInstant.wDSItemGrid[p] != iExceptionCell)
  645. return false;
  646. }
  647. while (++j < bSize);
  648.  
  649. return true;
  650. }
  651. else
  652. return false;
  653. }
  654.  
  655. // Ĺ©±â°ˇ 1Ŕ̸é ÇŃÄ­Ŕ» Â÷ÁöÇĎ´Â °ÍŔ̹ǷΠ±×łÉ ¸®ĹĎ
  656. if (1 == bSize)
  657. return true;
  658. else
  659. {
  660. int j = 1;
  661.  
  662. do
  663. {
  664. BYTE p = wCell + (DRAGON_SOUL_BOX_COLUMN_NUM * j);
  665.  
  666. if (p >= DRAGON_SOUL_INVENTORY_MAX_NUM)
  667. return false;
  668.  
  669. if (m_pointsInstant.bItemGrid[p])
  670. if (m_pointsInstant.wDSItemGrid[p] != iExceptionCell)
  671. return false;
  672. }
  673. while (++j < bSize);
  674.  
  675. return true;
  676. }
  677. }
  678. }
  679. }
  680.  
  681. int CHARACTER::GetEmptyInventory(BYTE size) const
  682. {
  683. // NOTE: ÇöŔç ŔĚ ÇÔĽö´Â ľĆŔĚĹŰ Áö±Ţ, Čąµć µîŔÇ ÇŕŔ§¸¦ ÇŇ ¶§ ŔÎşĄĹ丮ŔÇ şó Ä­Ŕ» ĂŁ±â Ŕ§ÇŘ »çżëµÇ°í ŔִµĄ,
  684. // ş§Ć® ŔÎşĄĹ丮´Â ĆŻĽö ŔÎşĄĹ丮Ŕ̹ǷΠ°Ë»çÇĎÁö ľĘµµ·Ď ÇŃ´Ů. (±âş» ŔÎşĄĹ丮: INVENTORY_MAX_NUM ±îÁö¸¸ °Ë»ç)
  685. for ( int i = 0; i < INVENTORY_MAX_NUM; ++i)
  686. if (IsEmptyItemGrid(TItemPos (INVENTORY, i), size))
  687. return i;
  688. return -1;
  689. }
  690.  
  691. int CHARACTER::GetEmptyDragonSoulInventory(LPITEM pItem) const
  692. {
  693. if (NULL == pItem || !pItem->IsDragonSoul())
  694. return -1;
  695. if (!DragonSoul_IsQualified())
  696. {
  697. return -1;
  698. }
  699. BYTE bSize = pItem->GetSize();
  700. WORD wBaseCell = DSManager::instance().GetBasePosition(pItem);
  701.  
  702. if (WORD_MAX == wBaseCell)
  703. return -1;
  704.  
  705. for (int i = 0; i < DRAGON_SOUL_BOX_SIZE; ++i)
  706. if (IsEmptyItemGrid(TItemPos(DRAGON_SOUL_INVENTORY, i + wBaseCell), bSize))
  707. return i + wBaseCell;
  708.  
  709. return -1;
  710. }
  711.  
  712. void CHARACTER::CopyDragonSoulItemGrid(std::vector<WORD>& vDragonSoulItemGrid) const
  713. {
  714. vDragonSoulItemGrid.resize(DRAGON_SOUL_INVENTORY_MAX_NUM);
  715.  
  716. std::copy(m_pointsInstant.wDSItemGrid, m_pointsInstant.wDSItemGrid + DRAGON_SOUL_INVENTORY_MAX_NUM, vDragonSoulItemGrid.begin());
  717. }
  718.  
  719. int CHARACTER::CountEmptyInventory() const
  720. {
  721. int count = 0;
  722.  
  723. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  724. if (GetInventoryItem(i))
  725. count += GetInventoryItem(i)->GetSize();
  726.  
  727. return (INVENTORY_MAX_NUM - count);
  728. }
  729.  
  730. void TransformRefineItem(LPITEM pkOldItem, LPITEM pkNewItem)
  731. {
  732. // ACCESSORY_REFINE
  733. if (pkOldItem->IsAccessoryForSocket())
  734. {
  735. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  736. {
  737. pkNewItem->SetSocket(i, pkOldItem->GetSocket(i));
  738. }
  739. //pkNewItem->StartAccessorySocketExpireEvent();
  740. }
  741. // END_OF_ACCESSORY_REFINE
  742. else
  743. {
  744. // ż©±âĽ­ ±úÁřĽ®ŔĚ ŔÚµżŔűŔ¸·Î Ă»ĽŇ µĘ
  745. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  746. {
  747. if (!pkOldItem->GetSocket(i))
  748. break;
  749. else
  750. pkNewItem->SetSocket(i, 1);
  751. }
  752.  
  753. // ĽŇÄĎ ĽłÁ¤
  754. int slot = 0;
  755.  
  756. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  757. {
  758. long socket = pkOldItem->GetSocket(i);
  759.  
  760. if (socket > 2 && socket != ITEM_BROKEN_METIN_VNUM)
  761. pkNewItem->SetSocket(slot++, socket);
  762. }
  763.  
  764. }
  765.  
  766. // ¸ĹÁ÷ ľĆŔĚĹŰ ĽłÁ¤
  767. pkOldItem->CopyAttributeTo(pkNewItem);
  768. }
  769.  
  770. void NotifyRefineSuccess(LPCHARACTER ch, LPITEM item, const char* way)
  771. {
  772. if (NULL != ch && item != NULL)
  773. {
  774. ch->ChatPacket(CHAT_TYPE_COMMAND, "RefineSuceeded");
  775.  
  776. LogManager::instance().RefineLog(ch->GetPlayerID(), item->GetName(), item->GetID(), item->GetRefineLevel(), 1, way);
  777. }
  778. }
  779.  
  780. void NotifyRefineFail(LPCHARACTER ch, LPITEM item, const char* way, int success = 0)
  781. {
  782. if (NULL != ch && NULL != item)
  783. {
  784. ch->ChatPacket(CHAT_TYPE_COMMAND, "RefineFailed");
  785.  
  786. LogManager::instance().RefineLog(ch->GetPlayerID(), item->GetName(), item->GetID(), item->GetRefineLevel(), success, way);
  787. }
  788. }
  789.  
  790. void CHARACTER::SetRefineNPC(LPCHARACTER ch)
  791. {
  792. if ( ch != NULL )
  793. {
  794. m_dwRefineNPCVID = ch->GetVID();
  795. }
  796. else
  797. {
  798. m_dwRefineNPCVID = 0;
  799. }
  800. }
  801.  
  802. bool CHARACTER::DoRefine(LPITEM item, bool bMoneyOnly)
  803. {
  804. if (!CanHandleItem(true))
  805. {
  806. ClearRefineMode();
  807. return false;
  808. }
  809.  
  810. //°ł·® ˝Ă°ŁÁ¦ÇŃ : upgrade_refine_scroll.quest żˇĽ­ °ł·®ČÄ 5şĐŔĚł»żˇ ŔĎąÝ °ł·®Ŕ»
  811. //ÁřÇŕÇŇĽö ľřŔ˝
  812. if (quest::CQuestManager::instance().GetEventFlag("update_refine_time") != 0)
  813. {
  814. if (get_global_time() < quest::CQuestManager::instance().GetEventFlag("update_refine_time") + (60 * 5))
  815. {
  816. sys_log(0, "can't refine %d %s", GetPlayerID(), GetName());
  817. return false;
  818. }
  819. }
  820.  
  821. const TRefineTable * prt = CRefineManager::instance().GetRefineRecipe(item->GetRefineSet());
  822.  
  823. if (!prt)
  824. return false;
  825.  
  826. DWORD result_vnum = item->GetRefinedVnum();
  827.  
  828. // REFINE_COST
  829. int cost = ComputeRefineFee(prt->cost);
  830.  
  831. int RefineChance = GetQuestFlag("main_quest_lv7.refine_chance");
  832.  
  833. if (RefineChance > 0)
  834. {
  835. if (!item->CheckItemUseLevel(20) || item->GetType() != ITEM_WEAPON)
  836. {
  837. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą«·á °ł·® ±âȸ´Â 20 ŔĚÇĎŔÇ ą«±â¸¸ °ˇ´ÉÇŐ´Ď´Ů"));
  838. return false;
  839. }
  840.  
  841. cost = 0;
  842. SetQuestFlag("main_quest_lv7.refine_chance", RefineChance - 1);
  843. }
  844. // END_OF_REFINE_COST
  845.  
  846. if (result_vnum == 0)
  847. {
  848. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  849. return false;
  850. }
  851.  
  852. if (item->GetType() == ITEM_USE && item->GetSubType() == USE_TUNING)
  853. return false;
  854.  
  855. TItemTable * pProto = ITEM_MANAGER::instance().GetTable(item->GetRefinedVnum());
  856.  
  857. if (!pProto)
  858. {
  859. sys_err("DoRefine NOT GET ITEM PROTO %d", item->GetRefinedVnum());
  860. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  861. return false;
  862. }
  863.  
  864. // Check level limit in korea only
  865. if (!g_iUseLocale)
  866. {
  867. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  868. {
  869. long limit = pProto->aLimits[i].lValue;
  870.  
  871. switch (pProto->aLimits[i].bType)
  872. {
  873. case LIMIT_LEVEL:
  874. if (GetLevel() < limit)
  875. {
  876. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®µČ ČÄ ľĆŔĚĹŰŔÇ ·ąş§ Á¦ÇŃş¸´Ů ·ąş§ŔĚ ł·˝Ŕ´Ď´Ů."));
  877. return false;
  878. }
  879. break;
  880. }
  881. }
  882. }
  883.  
  884. // REFINE_COST
  885. if (GetGold() < cost)
  886. {
  887. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ µ·ŔĚ şÎÁ·ÇŐ´Ď´Ů."));
  888. return false;
  889. }
  890.  
  891. if (!bMoneyOnly && !RefineChance)
  892. {
  893. for (int i = 0; i < prt->material_count; ++i)
  894. {
  895. if (CountSpecifyItem(prt->materials[i].vnum) < prt->materials[i].count)
  896. {
  897. if (test_server)
  898. {
  899. ChatPacket(CHAT_TYPE_INFO, "Find %d, count %d, require %d", prt->materials[i].vnum, CountSpecifyItem(prt->materials[i].vnum), prt->materials[i].count);
  900. }
  901. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ Ŕç·á°ˇ şÎÁ·ÇŐ´Ď´Ů."));
  902. return false;
  903. }
  904. }
  905.  
  906. for (int i = 0; i < prt->material_count; ++i)
  907. RemoveSpecifyItem(prt->materials[i].vnum, prt->materials[i].count);
  908. }
  909.  
  910. int prob = number(1, 100);
  911.  
  912. if (IsRefineThroughGuild() || bMoneyOnly)
  913. prob -= 10;
  914.  
  915. // END_OF_REFINE_COST
  916.  
  917. if (prob <= prt->prob)
  918. {
  919. // Ľş°ř! ¸đµç ľĆŔĚĹŰŔĚ »ç¶óÁö°í, °°Ŕş ĽÓĽşŔÇ ´Ů¸Ą ľĆŔĚĹŰ Čąµć
  920. LPITEM pkNewItem = ITEM_MANAGER::instance().CreateItem(result_vnum, 1, 0, false);
  921.  
  922. if (pkNewItem)
  923. {
  924. ITEM_MANAGER::CopyAllAttrTo(item, pkNewItem);
  925. LogManager::instance().ItemLog(this, pkNewItem, "REFINE SUCCESS", pkNewItem->GetName());
  926.  
  927. BYTE bCell = item->GetCell();
  928.  
  929. // DETAIL_REFINE_LOG
  930. NotifyRefineSuccess(this, item, IsRefineThroughGuild() ? "GUILD" : "POWER");
  931. DBManager::instance().SendMoneyLog(MONEY_LOG_REFINE, item->GetVnum(), -cost);
  932. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (REFINE SUCCESS)");
  933. // END_OF_DETAIL_REFINE_LOG
  934.  
  935. pkNewItem->AddToCharacter(this, TItemPos(INVENTORY, bCell));
  936. ITEM_MANAGER::instance().FlushDelayedSave(pkNewItem);
  937.  
  938. sys_log(0, "Refine Success %d", cost);
  939. pkNewItem->AttrLog();
  940. //PointChange(POINT_GOLD, -cost);
  941. sys_log(0, "PayPee %d", cost);
  942. PayRefineFee(cost);
  943. sys_log(0, "PayPee End %d", cost);
  944. }
  945. else
  946. {
  947. // DETAIL_REFINE_LOG
  948. // ľĆŔĚĹŰ »ýĽşżˇ ˝ÇĆĐ -> °ł·® ˝ÇĆĐ·Î °ŁÁÖ
  949. sys_err("cannot create item %u", result_vnum);
  950. NotifyRefineFail(this, item, IsRefineThroughGuild() ? "GUILD" : "POWER");
  951. // END_OF_DETAIL_REFINE_LOG
  952. }
  953. }
  954. else
  955. {
  956. // ˝ÇĆĐ! ¸đµç ľĆŔĚĹŰŔĚ »ç¶óÁü.
  957. DBManager::instance().SendMoneyLog(MONEY_LOG_REFINE, item->GetVnum(), -cost);
  958. NotifyRefineFail(this, item, IsRefineThroughGuild() ? "GUILD" : "POWER");
  959. item->AttrLog();
  960. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (REFINE FAIL)");
  961.  
  962. //PointChange(POINT_GOLD, -cost);
  963. PayRefineFee(cost);
  964. }
  965.  
  966. return true;
  967. }
  968.  
  969. enum enum_RefineScrolls
  970. {
  971. CHUKBOK_SCROLL = 0,
  972. HYUNIRON_CHN = 1, // Áß±ążˇĽ­¸¸ »çżë
  973. YONGSIN_SCROLL = 2,
  974. MUSIN_SCROLL = 3,
  975. YAGONG_SCROLL = 4,
  976. MEMO_SCROLL = 5,
  977. BDRAGON_SCROLL = 6,
  978. };
  979.  
  980. bool CHARACTER::DoRefineWithScroll(LPITEM item)
  981. {
  982. if (!CanHandleItem(true))
  983. {
  984. ClearRefineMode();
  985. return false;
  986. }
  987.  
  988. ClearRefineMode();
  989.  
  990. //°ł·® ˝Ă°ŁÁ¦ÇŃ : upgrade_refine_scroll.quest żˇĽ­ °ł·®ČÄ 5şĐŔĚł»żˇ ŔĎąÝ °ł·®Ŕ»
  991. //ÁřÇŕÇŇĽö ľřŔ˝
  992. if (quest::CQuestManager::instance().GetEventFlag("update_refine_time") != 0)
  993. {
  994. if (get_global_time() < quest::CQuestManager::instance().GetEventFlag("update_refine_time") + (60 * 5))
  995. {
  996. sys_log(0, "can't refine %d %s", GetPlayerID(), GetName());
  997. return false;
  998. }
  999. }
  1000.  
  1001. const TRefineTable * prt = CRefineManager::instance().GetRefineRecipe(item->GetRefineSet());
  1002.  
  1003. if (!prt)
  1004. return false;
  1005.  
  1006. LPITEM pkItemScroll;
  1007.  
  1008. // °ł·®Ľ­ ĂĽĹ©
  1009. if (m_iRefineAdditionalCell < 0)
  1010. return false;
  1011.  
  1012. pkItemScroll = GetInventoryItem(m_iRefineAdditionalCell);
  1013.  
  1014. if (!pkItemScroll)
  1015. return false;
  1016.  
  1017. if (!(pkItemScroll->GetType() == ITEM_USE && pkItemScroll->GetSubType() == USE_TUNING))
  1018. return false;
  1019.  
  1020. if (pkItemScroll->GetVnum() == item->GetVnum())
  1021. return false;
  1022.  
  1023. DWORD result_vnum = item->GetRefinedVnum();
  1024. DWORD result_fail_vnum = item->GetRefineFromVnum();
  1025.  
  1026. if (result_vnum == 0)
  1027. {
  1028. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1029. return false;
  1030. }
  1031.  
  1032. // MUSIN_SCROLL
  1033. if (pkItemScroll->GetValue(0) == MUSIN_SCROLL)
  1034. {
  1035. if (item->GetRefineLevel() >= 4)
  1036. {
  1037. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ °ł·®Ľ­·Î ´ő ŔĚ»ó °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1038. return false;
  1039. }
  1040. }
  1041. // END_OF_MUSIC_SCROLL
  1042.  
  1043. else if (pkItemScroll->GetValue(0) == MEMO_SCROLL)
  1044. {
  1045. if (item->GetRefineLevel() != pkItemScroll->GetValue(1))
  1046. {
  1047. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ °ł·®Ľ­·Î °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1048. return false;
  1049. }
  1050. }
  1051. else if (pkItemScroll->GetValue(0) == BDRAGON_SCROLL)
  1052. {
  1053. if (item->GetType() != ITEM_METIN || item->GetRefineLevel() != 4)
  1054. {
  1055. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔ¸·Î °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1056. return false;
  1057. }
  1058. }
  1059.  
  1060. TItemTable * pProto = ITEM_MANAGER::instance().GetTable(item->GetRefinedVnum());
  1061.  
  1062. if (!pProto)
  1063. {
  1064. sys_err("DoRefineWithScroll NOT GET ITEM PROTO %d", item->GetRefinedVnum());
  1065. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1066. return false;
  1067. }
  1068.  
  1069. // Check level limit in korea only
  1070. if (!g_iUseLocale)
  1071. {
  1072. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  1073. {
  1074. long limit = pProto->aLimits[i].lValue;
  1075.  
  1076. switch (pProto->aLimits[i].bType)
  1077. {
  1078. case LIMIT_LEVEL:
  1079. if (GetLevel() < limit)
  1080. {
  1081. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®µČ ČÄ ľĆŔĚĹŰŔÇ ·ąş§ Á¦ÇŃş¸´Ů ·ąş§ŔĚ ł·˝Ŕ´Ď´Ů."));
  1082. return false;
  1083. }
  1084. break;
  1085. }
  1086. }
  1087. }
  1088.  
  1089. if (GetGold() < prt->cost)
  1090. {
  1091. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ µ·ŔĚ şÎÁ·ÇŐ´Ď´Ů."));
  1092. return false;
  1093. }
  1094.  
  1095. for (int i = 0; i < prt->material_count; ++i)
  1096. {
  1097. if (CountSpecifyItem(prt->materials[i].vnum) < prt->materials[i].count)
  1098. {
  1099. if (test_server)
  1100. {
  1101. ChatPacket(CHAT_TYPE_INFO, "Find %d, count %d, require %d", prt->materials[i].vnum, CountSpecifyItem(prt->materials[i].vnum), prt->materials[i].count);
  1102. }
  1103. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ Ŕç·á°ˇ şÎÁ·ÇŐ´Ď´Ů."));
  1104. return false;
  1105. }
  1106. }
  1107.  
  1108. for (int i = 0; i < prt->material_count; ++i)
  1109. RemoveSpecifyItem(prt->materials[i].vnum, prt->materials[i].count);
  1110.  
  1111. int prob = number(1, 100);
  1112. int success_prob = prt->prob;
  1113. bool bDestroyWhenFail = false;
  1114.  
  1115. const char* szRefineType = "SCROLL";
  1116.  
  1117. if (pkItemScroll->GetValue(0) == HYUNIRON_CHN ||
  1118. pkItemScroll->GetValue(0) == YONGSIN_SCROLL ||
  1119. pkItemScroll->GetValue(0) == YAGONG_SCROLL) // Çöö, żë˝ĹŔÇ ĂŕşąĽ­, ľß°řŔÇ şńŔüĽ­ Ăł¸®
  1120. {
  1121. const char hyuniron_prob[9] = { 100, 75, 65, 55, 45, 40, 35, 25, 20 };
  1122. const char hyuniron_prob_euckr[9] = { 100, 75, 65, 55, 45, 40, 35, 30, 25 };
  1123.  
  1124. const char yagong_prob[9] = { 100, 100, 90, 80, 70, 60, 50, 30, 20 };
  1125. const char yagong_prob_euckr[9] = { 100, 100, 90, 80, 70, 60, 50, 40, 30 };
  1126.  
  1127. if (pkItemScroll->GetValue(0) == YONGSIN_SCROLL)
  1128. {
  1129. if (LC_IsYMIR() == true || LC_IsKorea() == true)
  1130. success_prob = hyuniron_prob_euckr[MINMAX(0, item->GetRefineLevel(), 8)];
  1131. else
  1132. success_prob = hyuniron_prob[MINMAX(0, item->GetRefineLevel(), 8)];
  1133. }
  1134. else if (pkItemScroll->GetValue(0) == YAGONG_SCROLL)
  1135. {
  1136. if (LC_IsYMIR() == true || LC_IsKorea() == true)
  1137. success_prob = yagong_prob_euckr[MINMAX(0, item->GetRefineLevel(), 8)];
  1138. else
  1139. success_prob = yagong_prob[MINMAX(0, item->GetRefineLevel(), 8)];
  1140. }
  1141. else
  1142. {
  1143. sys_err("REFINE : Unknown refine scroll item. Value0: %d", pkItemScroll->GetValue(0));
  1144. }
  1145.  
  1146. if (test_server)
  1147. {
  1148. ChatPacket(CHAT_TYPE_INFO, "[Only Test] Success_Prob %d, RefineLevel %d ", success_prob, item->GetRefineLevel());
  1149. }
  1150. if (pkItemScroll->GetValue(0) == HYUNIRON_CHN) // ÇööŔş ľĆŔĚĹŰŔĚ şÎĽ­Á®ľß ÇŃ´Ů.
  1151. bDestroyWhenFail = true;
  1152.  
  1153. // DETAIL_REFINE_LOG
  1154. if (pkItemScroll->GetValue(0) == HYUNIRON_CHN)
  1155. {
  1156. szRefineType = "HYUNIRON";
  1157. }
  1158. else if (pkItemScroll->GetValue(0) == YONGSIN_SCROLL)
  1159. {
  1160. szRefineType = "GOD_SCROLL";
  1161. }
  1162. else if (pkItemScroll->GetValue(0) == YAGONG_SCROLL)
  1163. {
  1164. szRefineType = "YAGONG_SCROLL";
  1165. }
  1166. // END_OF_DETAIL_REFINE_LOG
  1167. }
  1168.  
  1169. // DETAIL_REFINE_LOG
  1170. if (pkItemScroll->GetValue(0) == MUSIN_SCROLL) // ą«˝ĹŔÇ ĂŕşąĽ­´Â 100% Ľş°ř (+4±îÁö¸¸)
  1171. {
  1172. success_prob = 100;
  1173.  
  1174. szRefineType = "MUSIN_SCROLL";
  1175. }
  1176. // END_OF_DETAIL_REFINE_LOG
  1177. else if (pkItemScroll->GetValue(0) == MEMO_SCROLL)
  1178. {
  1179. success_prob = 100;
  1180. szRefineType = "MEMO_SCROLL";
  1181. }
  1182. else if (pkItemScroll->GetValue(0) == BDRAGON_SCROLL)
  1183. {
  1184. success_prob = 80;
  1185. szRefineType = "BDRAGON_SCROLL";
  1186. }
  1187.  
  1188. pkItemScroll->SetCount(pkItemScroll->GetCount() - 1);
  1189.  
  1190. if (prob <= success_prob)
  1191. {
  1192. // Ľş°ř! ¸đµç ľĆŔĚĹŰŔĚ »ç¶óÁö°í, °°Ŕş ĽÓĽşŔÇ ´Ů¸Ą ľĆŔĚĹŰ Čąµć
  1193. LPITEM pkNewItem = ITEM_MANAGER::instance().CreateItem(result_vnum, 1, 0, false);
  1194.  
  1195. if (pkNewItem)
  1196. {
  1197. ITEM_MANAGER::CopyAllAttrTo(item, pkNewItem);
  1198. LogManager::instance().ItemLog(this, pkNewItem, "REFINE SUCCESS", pkNewItem->GetName());
  1199.  
  1200. BYTE bCell = item->GetCell();
  1201.  
  1202. NotifyRefineSuccess(this, item, szRefineType);
  1203. DBManager::instance().SendMoneyLog(MONEY_LOG_REFINE, item->GetVnum(), -prt->cost);
  1204. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (REFINE SUCCESS)");
  1205.  
  1206. pkNewItem->AddToCharacter(this, TItemPos(INVENTORY, bCell));
  1207. ITEM_MANAGER::instance().FlushDelayedSave(pkNewItem);
  1208. pkNewItem->AttrLog();
  1209. //PointChange(POINT_GOLD, -prt->cost);
  1210. PayRefineFee(prt->cost);
  1211. }
  1212. else
  1213. {
  1214. // ľĆŔĚĹŰ »ýĽşżˇ ˝ÇĆĐ -> °ł·® ˝ÇĆĐ·Î °ŁÁÖ
  1215. sys_err("cannot create item %u", result_vnum);
  1216. NotifyRefineFail(this, item, szRefineType);
  1217. }
  1218. }
  1219. else if (!bDestroyWhenFail && result_fail_vnum)
  1220. {
  1221. // ˝ÇĆĐ! ¸đµç ľĆŔĚĹŰŔĚ »ç¶óÁö°í, °°Ŕş ĽÓĽşŔÇ ł·Ŕş µî±ŢŔÇ ľĆŔĚĹŰ Čąµć
  1222. LPITEM pkNewItem = ITEM_MANAGER::instance().CreateItem(result_fail_vnum, 1, 0, false);
  1223.  
  1224. if (pkNewItem)
  1225. {
  1226. ITEM_MANAGER::CopyAllAttrTo(item, pkNewItem);
  1227. LogManager::instance().ItemLog(this, pkNewItem, "REFINE FAIL", pkNewItem->GetName());
  1228.  
  1229. BYTE bCell = item->GetCell();
  1230.  
  1231. DBManager::instance().SendMoneyLog(MONEY_LOG_REFINE, item->GetVnum(), -prt->cost);
  1232. NotifyRefineFail(this, item, szRefineType, -1);
  1233. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (REFINE FAIL)");
  1234.  
  1235. pkNewItem->AddToCharacter(this, TItemPos(INVENTORY, bCell));
  1236. ITEM_MANAGER::instance().FlushDelayedSave(pkNewItem);
  1237.  
  1238. pkNewItem->AttrLog();
  1239.  
  1240. //PointChange(POINT_GOLD, -prt->cost);
  1241. PayRefineFee(prt->cost);
  1242. }
  1243. else
  1244. {
  1245. // ľĆŔĚĹŰ »ýĽşżˇ ˝ÇĆĐ -> °ł·® ˝ÇĆĐ·Î °ŁÁÖ
  1246. sys_err("cannot create item %u", result_fail_vnum);
  1247. NotifyRefineFail(this, item, szRefineType);
  1248. }
  1249. }
  1250. else
  1251. {
  1252. NotifyRefineFail(this, item, szRefineType); // °ł·®˝Ă ľĆŔĚĹŰ »ç¶óÁöÁö ľĘŔ˝
  1253.  
  1254. PayRefineFee(prt->cost);
  1255. }
  1256.  
  1257. return true;
  1258. }
  1259.  
  1260. bool CHARACTER::RefineInformation(BYTE bCell, BYTE bType, int iAdditionalCell)
  1261. {
  1262. if (bCell > INVENTORY_MAX_NUM)
  1263. return false;
  1264.  
  1265. LPITEM item = GetInventoryItem(bCell);
  1266.  
  1267. if (!item)
  1268. return false;
  1269.  
  1270. // REFINE_COST
  1271. if (bType == REFINE_TYPE_MONEY_ONLY && !GetQuestFlag("deviltower_zone.can_refine"))
  1272. {
  1273. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»ç±Í Ÿżö żĎ·á ş¸»óŔş ÇŃąř±îÁö »çżë°ˇ´ÉÇŐ´Ď´Ů."));
  1274. return false;
  1275. }
  1276. // END_OF_REFINE_COST
  1277.  
  1278. TPacketGCRefineInformation p;
  1279.  
  1280. p.header = HEADER_GC_REFINE_INFORMATION;
  1281. p.pos = bCell;
  1282. p.src_vnum = item->GetVnum();
  1283. p.result_vnum = item->GetRefinedVnum();
  1284. p.type = bType;
  1285.  
  1286. if (p.result_vnum == 0)
  1287. {
  1288. sys_err("RefineInformation p.result_vnum == 0");
  1289. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1290. return false;
  1291. }
  1292.  
  1293. if (item->GetType() == ITEM_USE && item->GetSubType() == USE_TUNING)
  1294. {
  1295. if (bType == 0)
  1296. {
  1297. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş ŔĚ ąć˝ÄŔ¸·Î´Â °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1298. return false;
  1299. }
  1300. else
  1301. {
  1302. LPITEM itemScroll = GetInventoryItem(iAdditionalCell);
  1303. if (!itemScroll || item->GetVnum() == itemScroll->GetVnum())
  1304. {
  1305. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°°Ŕş °ł·®Ľ­¸¦ ÇŐÄĄ Ľö´Â ľř˝Ŕ´Ď´Ů."));
  1306. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĂŕşąŔÇ Ľ­żÍ ÇööŔ» ÇŐÄĄ Ľö ŔÖ˝Ŕ´Ď´Ů."));
  1307. return false;
  1308. }
  1309. }
  1310. }
  1311.  
  1312. CRefineManager & rm = CRefineManager::instance();
  1313.  
  1314. const TRefineTable* prt = rm.GetRefineRecipe(item->GetRefineSet());
  1315.  
  1316. if (!prt)
  1317. {
  1318. sys_err("RefineInformation NOT GET REFINE SET %d", item->GetRefineSet());
  1319. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1320. return false;
  1321. }
  1322.  
  1323. // REFINE_COST
  1324.  
  1325. //MAIN_QUEST_LV7
  1326. if (GetQuestFlag("main_quest_lv7.refine_chance") > 0)
  1327. {
  1328. // ŔĎş»Ŕş Á¦żÜ
  1329. if (!item->CheckItemUseLevel(20) || item->GetType() != ITEM_WEAPON)
  1330. {
  1331. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą«·á °ł·® ±âȸ´Â 20 ŔĚÇĎŔÇ ą«±â¸¸ °ˇ´ÉÇŐ´Ď´Ů"));
  1332. return false;
  1333. }
  1334. p.cost = 0;
  1335. }
  1336. else
  1337. p.cost = ComputeRefineFee(prt->cost);
  1338.  
  1339. //END_MAIN_QUEST_LV7
  1340. p.prob = prt->prob;
  1341. if (bType == REFINE_TYPE_MONEY_ONLY)
  1342. {
  1343. p.material_count = 0;
  1344. memset(p.materials, 0, sizeof(p.materials));
  1345. }
  1346. else
  1347. {
  1348. p.material_count = prt->material_count;
  1349. thecore_memcpy(&p.materials, prt->materials, sizeof(prt->materials));
  1350. }
  1351. // END_OF_REFINE_COST
  1352.  
  1353. GetDesc()->Packet(&p, sizeof(TPacketGCRefineInformation));
  1354.  
  1355. SetRefineMode(iAdditionalCell);
  1356. return true;
  1357. }
  1358.  
  1359. bool CHARACTER::RefineItem(LPITEM pkItem, LPITEM pkTarget)
  1360. {
  1361. if (!CanHandleItem())
  1362. return false;
  1363.  
  1364. if (pkItem->GetSubType() == USE_TUNING)
  1365. {
  1366. // XXX Ľş´É, ĽŇÄĎ °ł·®Ľ­´Â »ç¶óÁł˝Ŕ´Ď´Ů...
  1367. // XXX Ľş´É°ł·®Ľ­´Â ĂŕşąŔÇ Ľ­°ˇ µÇľú´Ů!
  1368. // MUSIN_SCROLL
  1369. if (pkItem->GetValue(0) == MUSIN_SCROLL)
  1370. RefineInformation(pkTarget->GetCell(), REFINE_TYPE_MUSIN, pkItem->GetCell());
  1371. // END_OF_MUSIN_SCROLL
  1372. else if (pkItem->GetValue(0) == HYUNIRON_CHN)
  1373. RefineInformation(pkTarget->GetCell(), REFINE_TYPE_HYUNIRON, pkItem->GetCell());
  1374. else if (pkItem->GetValue(0) == BDRAGON_SCROLL)
  1375. {
  1376. if (pkTarget->GetRefineSet() != 702) return false;
  1377. RefineInformation(pkTarget->GetCell(), REFINE_TYPE_BDRAGON, pkItem->GetCell());
  1378. }
  1379. else
  1380. {
  1381. if (pkTarget->GetRefineSet() == 501) return false;
  1382. RefineInformation(pkTarget->GetCell(), REFINE_TYPE_SCROLL, pkItem->GetCell());
  1383. }
  1384. }
  1385. else if (pkItem->GetSubType() == USE_DETACHMENT && IS_SET(pkTarget->GetFlag(), ITEM_FLAG_REFINEABLE))
  1386. {
  1387. LogManager::instance().ItemLog(this, pkTarget, "USE_DETACHMENT", pkTarget->GetName());
  1388.  
  1389. bool bHasMetinStone = false;
  1390.  
  1391. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; i++)
  1392. {
  1393. long socket = pkTarget->GetSocket(i);
  1394. if (socket > 2 && socket != ITEM_BROKEN_METIN_VNUM)
  1395. {
  1396. bHasMetinStone = true;
  1397. break;
  1398. }
  1399. }
  1400.  
  1401. if (bHasMetinStone)
  1402. {
  1403. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  1404. {
  1405. long socket = pkTarget->GetSocket(i);
  1406. if (socket > 2 && socket != ITEM_BROKEN_METIN_VNUM)
  1407. {
  1408. AutoGiveItem(socket);
  1409. //TItemTable* pTable = ITEM_MANAGER::instance().GetTable(pkTarget->GetSocket(i));
  1410. //pkTarget->SetSocket(i, pTable->alValues[2]);
  1411. // ±úÁřµą·Î ´ëĂĽÇŘÁŘ´Ů
  1412. pkTarget->SetSocket(i, ITEM_BROKEN_METIN_VNUM);
  1413. }
  1414. }
  1415. pkItem->SetCount(pkItem->GetCount() - 1);
  1416. return true;
  1417. }
  1418. else
  1419. {
  1420. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»©łľ Ľö ŔÖ´Â ¸ŢĆľĽ®ŔĚ ľř˝Ŕ´Ď´Ů."));
  1421. return false;
  1422. }
  1423. }
  1424.  
  1425. return false;
  1426. }
  1427.  
  1428. EVENTFUNC(kill_campfire_event)
  1429. {
  1430. char_event_info* info = dynamic_cast<char_event_info*>( event->info );
  1431.  
  1432. if ( info == NULL )
  1433. {
  1434. sys_err( "kill_campfire_event> <Factor> Null pointer" );
  1435. return 0;
  1436. }
  1437.  
  1438. LPCHARACTER ch = info->ch;
  1439.  
  1440. if (ch == NULL) { // <Factor>
  1441. return 0;
  1442. }
  1443. ch->m_pkMiningEvent = NULL;
  1444. M2_DESTROY_CHARACTER(ch);
  1445. return 0;
  1446. }
  1447.  
  1448. bool CHARACTER::GiveRecallItem(LPITEM item)
  1449. {
  1450. int idx = GetMapIndex();
  1451. int iEmpireByMapIndex = -1;
  1452.  
  1453. if (idx < 20)
  1454. iEmpireByMapIndex = 1;
  1455. else if (idx < 40)
  1456. iEmpireByMapIndex = 2;
  1457. else if (idx < 60)
  1458. iEmpireByMapIndex = 3;
  1459. else if (idx < 10000)
  1460. iEmpireByMapIndex = 0;
  1461.  
  1462. switch (idx)
  1463. {
  1464. case 66:
  1465. case 216:
  1466. iEmpireByMapIndex = -1;
  1467. break;
  1468. }
  1469.  
  1470. if (iEmpireByMapIndex && GetEmpire() != iEmpireByMapIndex)
  1471. {
  1472. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±âľďÇŘ µŃ Ľö ľř´Â Ŕ§Äˇ ŔÔ´Ď´Ů."));
  1473. return false;
  1474. }
  1475.  
  1476. int pos;
  1477.  
  1478. if (item->GetCount() == 1) // ľĆŔĚĹŰŔĚ ÇĎłŞ¶ó¸é ±×łÉ ĽÂĆĂ.
  1479. {
  1480. item->SetSocket(0, GetX());
  1481. item->SetSocket(1, GetY());
  1482. }
  1483. else if ((pos = GetEmptyInventory(item->GetSize())) != -1) // ±×·¸Áö ľĘ´Ů¸é ´Ů¸Ą ŔÎşĄĹ丮 ˝˝·ÔŔ» ĂŁ´Â´Ů.
  1484. {
  1485. LPITEM item2 = ITEM_MANAGER::instance().CreateItem(item->GetVnum(), 1);
  1486.  
  1487. if (NULL != item2)
  1488. {
  1489. item2->SetSocket(0, GetX());
  1490. item2->SetSocket(1, GetY());
  1491. item2->AddToCharacter(this, TItemPos(INVENTORY, pos));
  1492.  
  1493. item->SetCount(item->GetCount() - 1);
  1494. }
  1495. }
  1496. else
  1497. {
  1498. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇ°żˇ şó °ř°ŁŔĚ ľř˝Ŕ´Ď´Ů."));
  1499. return false;
  1500. }
  1501.  
  1502. return true;
  1503. }
  1504.  
  1505. void CHARACTER::ProcessRecallItem(LPITEM item)
  1506. {
  1507. int idx;
  1508.  
  1509. if ((idx = SECTREE_MANAGER::instance().GetMapIndex(item->GetSocket(0), item->GetSocket(1))) == 0)
  1510. return;
  1511.  
  1512. int iEmpireByMapIndex = -1;
  1513.  
  1514. if (idx < 20)
  1515. iEmpireByMapIndex = 1;
  1516. else if (idx < 40)
  1517. iEmpireByMapIndex = 2;
  1518. else if (idx < 60)
  1519. iEmpireByMapIndex = 3;
  1520. else if (idx < 10000)
  1521. iEmpireByMapIndex = 0;
  1522.  
  1523. switch (idx)
  1524. {
  1525. case 66:
  1526. case 216:
  1527. iEmpireByMapIndex = -1;
  1528. break;
  1529. // ľÇ·ć±şµµ Ŕ϶§
  1530. case 301:
  1531. case 302:
  1532. case 303:
  1533. case 304:
  1534. if( GetLevel() < 90 )
  1535. {
  1536. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰŔÇ ·ąş§ Á¦ÇŃş¸´Ů ·ąş§ŔĚ ł·˝Ŕ´Ď´Ů."));
  1537. return;
  1538. }
  1539. else
  1540. break;
  1541. }
  1542.  
  1543. if (iEmpireByMapIndex && GetEmpire() != iEmpireByMapIndex)
  1544. {
  1545. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±âľďµČ Ŕ§Äˇ°ˇ ŸÁ¦±ążˇ ĽÓÇŘ Ŕ־ ±ÍČŻÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1546. item->SetSocket(0, 0);
  1547. item->SetSocket(1, 0);
  1548. }
  1549. else
  1550. {
  1551. sys_log(1, "Recall: %s %d %d -> %d %d", GetName(), GetX(), GetY(), item->GetSocket(0), item->GetSocket(1));
  1552. WarpSet(item->GetSocket(0), item->GetSocket(1));
  1553. item->SetCount(item->GetCount() - 1);
  1554. }
  1555. }
  1556.  
  1557. void CHARACTER::__OpenPrivateShop()
  1558. {
  1559. unsigned bodyPart = GetPart(PART_MAIN);
  1560. switch (bodyPart)
  1561. {
  1562. case 0:
  1563. case 1:
  1564. case 2:
  1565. ChatPacket(CHAT_TYPE_COMMAND, "OpenPrivateShop");
  1566. break;
  1567. default:
  1568. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°©żĘŔ» ąţľîľß °łŔÎ »óÁˇŔ» ż­ Ľö ŔÖ˝Ŕ´Ď´Ů."));
  1569. break;
  1570. }
  1571. }
  1572.  
  1573. // MYSHOP_PRICE_LIST
  1574. void CHARACTER::SendMyShopPriceListCmd(DWORD dwItemVnum, long long dwItemPrice)
  1575. {
  1576. char szLine[256];
  1577. snprintf(szLine, sizeof(szLine), "MyShopPriceList %u %lld", dwItemVnum, dwItemPrice);
  1578. ChatPacket(CHAT_TYPE_COMMAND, szLine);
  1579. sys_log(0, szLine);
  1580. }
  1581.  
  1582. //
  1583. // DB Äł˝Ă·Î şÎĹÍ ąŢŔş ¸®˝şĆ®¸¦ User żˇ°Ô ŔüĽŰÇĎ°í »óÁˇŔ» ż­¶ó´Â Äż¸Çµĺ¸¦ ş¸ł˝´Ů.
  1584. //
  1585. void CHARACTER::UseSilkBotaryReal(const TPacketMyshopPricelistHeader* p)
  1586. {
  1587. const TItemPriceInfo* pInfo = (const TItemPriceInfo*)(p + 1);
  1588.  
  1589. if (!p->byCount)
  1590. // °ˇ°Ý ¸®˝şĆ®°ˇ ľř´Ů. dummy µĄŔĚĹ͸¦ łÖŔş Äż¸Çµĺ¸¦ ş¸ł»ÁŘ´Ů.
  1591. SendMyShopPriceListCmd(1, 0);
  1592. else {
  1593. for (int idx = 0; idx < p->byCount; idx++)
  1594. SendMyShopPriceListCmd(pInfo[ idx ].dwVnum, pInfo[ idx ].dwPrice);
  1595. }
  1596.  
  1597. __OpenPrivateShop();
  1598. }
  1599.  
  1600. //
  1601. // ŔĚąř Á˘ĽÓ ČÄ ĂłŔ˝ »óÁˇŔ» Open ÇĎ´Â °ćżě ¸®˝şĆ®¸¦ Load Çϱâ Ŕ§ÇŘ DB Äł˝Ăżˇ °ˇ°ÝÁ¤ş¸ ¸®˝şĆ® żäĂ» ĆĐŶŔ» ş¸ł˝´Ů.
  1602. // ŔĚČÄşÎĹÍ´Â ąŮ·Î »óÁˇŔ» ż­¶ó´Â ŔŔ´äŔ» ş¸ł˝´Ů.
  1603. //
  1604. void CHARACTER::UseSilkBotary(void)
  1605. {
  1606. if (m_bNoOpenedShop) {
  1607. DWORD dwPlayerID = GetPlayerID();
  1608. db_clientdesc->DBPacket(HEADER_GD_MYSHOP_PRICELIST_REQ, GetDesc()->GetHandle(), &dwPlayerID, sizeof(DWORD));
  1609. m_bNoOpenedShop = false;
  1610. } else {
  1611. __OpenPrivateShop();
  1612. }
  1613. }
  1614. // END_OF_MYSHOP_PRICE_LIST
  1615.  
  1616.  
  1617. int CalculateConsume(LPCHARACTER ch)
  1618. {
  1619. static const int WARP_NEED_LIFE_PERCENT = 30;
  1620. static const int WARP_MIN_LIFE_PERCENT = 10;
  1621. // CONSUME_LIFE_WHEN_USE_WARP_ITEM
  1622. int consumeLife = 0;
  1623. {
  1624. // CheckNeedLifeForWarp
  1625. const int curLife = ch->GetHP();
  1626. const int needPercent = WARP_NEED_LIFE_PERCENT;
  1627. const int needLife = ch->GetMaxHP() * needPercent / 100;
  1628. if (curLife < needLife)
  1629. {
  1630. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ł˛Ŕş »ý¸í·Â ľçŔĚ ¸đŔÚ¶ó »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1631. return -1;
  1632. }
  1633.  
  1634. consumeLife = needLife;
  1635.  
  1636.  
  1637. // CheckMinLifeForWarp: µ¶żˇ ŔÇÇŘĽ­ Á×Ŕ¸¸é ľČµÇąÇ·Î »ý¸í·Â ĂÖĽŇ·®´Â ł˛°ÜÁŘ´Ů
  1638. const int minPercent = WARP_MIN_LIFE_PERCENT;
  1639. const int minLife = ch->GetMaxHP() * minPercent / 100;
  1640. if (curLife - needLife < minLife)
  1641. consumeLife = curLife - minLife;
  1642.  
  1643. if (consumeLife < 0)
  1644. consumeLife = 0;
  1645. }
  1646. // END_OF_CONSUME_LIFE_WHEN_USE_WARP_ITEM
  1647. return consumeLife;
  1648. }
  1649.  
  1650. int CalculateConsumeSP(LPCHARACTER lpChar)
  1651. {
  1652. static const int NEED_WARP_SP_PERCENT = 30;
  1653.  
  1654. const int curSP = lpChar->GetSP();
  1655. const int needSP = lpChar->GetMaxSP() * NEED_WARP_SP_PERCENT / 100;
  1656.  
  1657. if (curSP < needSP)
  1658. {
  1659. lpChar->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ł˛Ŕş Á¤˝Ĺ·Â ľçŔĚ ¸đŔÚ¶ó »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  1660. return -1;
  1661. }
  1662.  
  1663. return needSP;
  1664. }
  1665.  
  1666. bool CHARACTER::UseItemEx(LPITEM item, TItemPos DestCell)
  1667. {
  1668. int iLimitRealtimeStartFirstUseFlagIndex = -1;
  1669. int iLimitTimerBasedOnWearFlagIndex = -1;
  1670.  
  1671. WORD wDestCell = DestCell.cell;
  1672. BYTE bDestInven = DestCell.window_type;
  1673. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  1674. {
  1675. long limitValue = item->GetProto()->aLimits[i].lValue;
  1676.  
  1677. switch (item->GetProto()->aLimits[i].bType)
  1678. {
  1679. case LIMIT_LEVEL:
  1680. if (GetLevel() < limitValue)
  1681. {
  1682. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰŔÇ ·ąş§ Á¦ÇŃş¸´Ů ·ąş§ŔĚ ł·˝Ŕ´Ď´Ů."));
  1683. return false;
  1684. }
  1685. break;
  1686.  
  1687. case LIMIT_REAL_TIME_START_FIRST_USE:
  1688. iLimitRealtimeStartFirstUseFlagIndex = i;
  1689. break;
  1690.  
  1691. case LIMIT_TIMER_BASED_ON_WEAR:
  1692. iLimitTimerBasedOnWearFlagIndex = i;
  1693. break;
  1694. }
  1695. }
  1696.  
  1697. if (test_server)
  1698. {
  1699. sys_log(0, "USE_ITEM %s, Inven %d, Cell %d, ItemType %d, SubType %d", item->GetName(), bDestInven, wDestCell, item->GetType(), item->GetSubType());
  1700. }
  1701.  
  1702. if ( CArenaManager::instance().IsLimitedItem( GetMapIndex(), item->GetVnum() ) == true )
  1703. {
  1704. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  1705. return false;
  1706. }
  1707.  
  1708. // ľĆŔĚĹŰ ĂÖĂĘ »çżë ŔĚČÄşÎĹÍ´Â »çżëÇĎÁö ľĘľĆµµ ˝Ă°ŁŔĚ Â÷°¨µÇ´Â ąć˝Ä Ăł¸®.
  1709. if (-1 != iLimitRealtimeStartFirstUseFlagIndex)
  1710. {
  1711. // ÇŃ ąřŔĚ¶óµµ »çżëÇŃ ľĆŔĚĹŰŔÎÁö ż©şÎ´Â Socket1Ŕ» ş¸°í ĆÇ´ÜÇŃ´Ů. (Socket1żˇ »çżëČ˝Ľö ±â·Ď)
  1712. if (0 == item->GetSocket(1))
  1713. {
  1714. // »çżë°ˇ´É˝Ă°ŁŔş Default °ŞŔ¸·Î Limit Value °ŞŔ» »çżëÇϵÇ, Socket0żˇ °ŞŔĚ ŔÖŔ¸¸é ±× °ŞŔ» »çżëÇϵµ·Ď ÇŃ´Ů. (´ÜŔ§´Â ĂĘ)
  1715. long duration = (0 != item->GetSocket(0)) ? item->GetSocket(0) : item->GetProto()->aLimits[iLimitRealtimeStartFirstUseFlagIndex].lValue;
  1716.  
  1717. if (0 == duration)
  1718. duration = 60 * 60 * 24 * 7;
  1719.  
  1720. item->SetSocket(0, time(0) + duration);
  1721. item->StartRealTimeExpireEvent();
  1722. }
  1723.  
  1724. if (false == item->IsEquipped())
  1725. item->SetSocket(1, item->GetSocket(1) + 1);
  1726. }
  1727.  
  1728. switch (item->GetType())
  1729. {
  1730. case ITEM_HAIR:
  1731. return ItemProcess_Hair(item, wDestCell);
  1732.  
  1733. case ITEM_POLYMORPH:
  1734. return ItemProcess_Polymorph(item);
  1735.  
  1736. case ITEM_QUEST:
  1737. if (GetArena() != NULL || IsObserverMode() == true)
  1738. {
  1739. if (item->GetVnum() == 50051 || item->GetVnum() == 50052 || item->GetVnum() == 50053)
  1740. {
  1741. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  1742. return false;
  1743. }
  1744. }
  1745.  
  1746. if (!IS_SET(item->GetFlag(), ITEM_FLAG_QUEST_USE | ITEM_FLAG_QUEST_USE_MULTIPLE))
  1747. {
  1748. if (item->GetSIGVnum() == 0)
  1749. {
  1750. quest::CQuestManager::instance().UseItem(GetPlayerID(), item, false);
  1751. }
  1752. else
  1753. {
  1754. quest::CQuestManager::instance().SIGUse(GetPlayerID(), item->GetSIGVnum(), item, false);
  1755. }
  1756. }
  1757. break;
  1758.  
  1759. case ITEM_CAMPFIRE:
  1760. {
  1761. float fx, fy;
  1762. GetDeltaByDegree(GetRotation(), 100.0f, &fx, &fy);
  1763.  
  1764. LPSECTREE tree = SECTREE_MANAGER::instance().Get(GetMapIndex(), (long)(GetX()+fx), (long)(GetY()+fy));
  1765.  
  1766. if (!tree)
  1767. {
  1768. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸đ´ÚşŇŔ» ÇÇżď Ľö ľř´Â ÁöÁˇŔÔ´Ď´Ů."));
  1769. return false;
  1770. }
  1771.  
  1772. if (tree->IsAttr((long)(GetX()+fx), (long)(GetY()+fy), ATTR_WATER))
  1773. {
  1774. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą° ĽÓżˇ ¸đ´ÚşŇŔ» ÇÇżď Ľö ľř˝Ŕ´Ď´Ů."));
  1775. return false;
  1776. }
  1777.  
  1778. LPCHARACTER campfire = CHARACTER_MANAGER::instance().SpawnMob(fishing::CAMPFIRE_MOB, GetMapIndex(), (long)(GetX()+fx), (long)(GetY()+fy), 0, false, number(0, 359));
  1779.  
  1780. char_event_info* info = AllocEventInfo<char_event_info>();
  1781.  
  1782. info->ch = campfire;
  1783.  
  1784. campfire->m_pkMiningEvent = event_create(kill_campfire_event, info, PASSES_PER_SEC(40));
  1785.  
  1786. item->SetCount(item->GetCount() - 1);
  1787. }
  1788. break;
  1789.  
  1790. case ITEM_UNIQUE:
  1791. {
  1792. switch (item->GetSubType())
  1793. {
  1794. case USE_ABILITY_UP:
  1795. {
  1796. switch (item->GetValue(0))
  1797. {
  1798. case APPLY_MOV_SPEED:
  1799. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_MOV_SPEED, item->GetValue(2), AFF_MOV_SPEED_POTION, item->GetValue(1), 0, true, true);
  1800. EffectPacket(SE_SPEEDUP_GREEN); // to pod att_speed (zielony efekt)
  1801. break;
  1802.  
  1803. case APPLY_ATT_SPEED:
  1804. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_ATT_SPEED, item->GetValue(2), AFF_ATT_SPEED_POTION, item->GetValue(1), 0, true, true);
  1805. EffectPacket(SE_SPEEDUP_GREEN); // to pod att_speed (zielony efekt)
  1806. break;
  1807.  
  1808. case APPLY_STR:
  1809. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_ST, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1810. break;
  1811.  
  1812. case APPLY_DEX:
  1813. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_DX, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1814. break;
  1815.  
  1816. case APPLY_CON:
  1817. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_HT, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1818. break;
  1819.  
  1820. case APPLY_INT:
  1821. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_IQ, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1822. break;
  1823.  
  1824. case APPLY_CAST_SPEED:
  1825. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_CASTING_SPEED, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1826. break;
  1827.  
  1828. case APPLY_RESIST_MAGIC:
  1829. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_RESIST_MAGIC, item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1830. break;
  1831.  
  1832. case APPLY_ATT_GRADE_BONUS:
  1833. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_ATT_GRADE_BONUS,
  1834. item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1835. break;
  1836.  
  1837. case APPLY_DEF_GRADE_BONUS:
  1838. AddAffect(AFFECT_UNIQUE_ABILITY, POINT_DEF_GRADE_BONUS,
  1839. item->GetValue(2), 0, item->GetValue(1), 0, true, true);
  1840. break;
  1841. }
  1842. }
  1843.  
  1844. if (GetDungeon())
  1845. GetDungeon()->UsePotion(this);
  1846.  
  1847. if (GetWarMap())
  1848. GetWarMap()->UsePotion(this, item);
  1849.  
  1850. item->SetCount(item->GetCount() - 1);
  1851. break;
  1852.  
  1853. default:
  1854. {
  1855. if (item->GetSubType() == USE_SPECIAL)
  1856. {
  1857. sys_log(0, "ITEM_UNIQUE: USE_SPECIAL %u", item->GetVnum());
  1858.  
  1859. switch (item->GetVnum())
  1860. {
  1861. case 71049: // şń´Üş¸µű¸®
  1862. if (LC_IsYMIR() == true || LC_IsKorea() == true)
  1863. {
  1864. if (IS_BOTARYABLE_ZONE(GetMapIndex()) == true)
  1865. {
  1866. UseSilkBotary();
  1867. }
  1868. else
  1869. {
  1870. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°łŔÎ »óÁˇŔ» ż­ Ľö ľř´Â ÁöżŞŔÔ´Ď´Ů"));
  1871. }
  1872. }
  1873. else
  1874. {
  1875. UseSilkBotary();
  1876. }
  1877. break;
  1878. }
  1879. }
  1880. else
  1881. {
  1882. if (!item->IsEquipped())
  1883. EquipItem(item);
  1884. else
  1885. UnequipItem(item);
  1886. }
  1887. }
  1888. break;
  1889. }
  1890. }
  1891. break;
  1892.  
  1893. case ITEM_COSTUME:
  1894. case ITEM_WEAPON:
  1895. case ITEM_ARMOR:
  1896. case ITEM_ROD:
  1897. case ITEM_RING: // ˝Ĺ±Ô ąÝÁö ľĆŔĚĹŰ
  1898. case ITEM_BELT: // ˝Ĺ±Ô ş§Ć® ľĆŔĚĹŰ
  1899. // MINING
  1900. case ITEM_PICK:
  1901. // END_OF_MINING
  1902. if (!item->IsEquipped())
  1903. EquipItem(item);
  1904. else
  1905. UnequipItem(item);
  1906. break;
  1907. // ÂřżëÇĎÁö ľĘŔş żëČĄĽ®Ŕş »çżëÇŇ Ľö ľř´Ů.
  1908. // Á¤»óŔűŔΠŬ¶ó¶ó¸é, żëČĄĽ®żˇ °üÇĎż© item use ĆĐŶŔ» ş¸łľ Ľö ľř´Ů.
  1909. // żëČĄĽ® ÂřżëŔş item move ĆĐŶŔ¸·Î ÇŃ´Ů.
  1910. // ÂřżëÇŃ żëČĄĽ®Ŕş ĂßĂâÇŃ´Ů.
  1911. case ITEM_DS:
  1912. {
  1913. if (!item->IsEquipped())
  1914. return false;
  1915. return DSManager::instance().PullOut(this, NPOS, item);
  1916. break;
  1917. }
  1918. case ITEM_SPECIAL_DS:
  1919. if (!item->IsEquipped())
  1920. EquipItem(item);
  1921. else
  1922. UnequipItem(item);
  1923. break;
  1924.  
  1925. case ITEM_FISH:
  1926. {
  1927. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  1928. {
  1929. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  1930. return false;
  1931. }
  1932.  
  1933. if (item->GetSubType() == FISH_ALIVE)
  1934. fishing::UseFish(this, item);
  1935. }
  1936. break;
  1937.  
  1938. case ITEM_TREASURE_BOX:
  1939. {
  1940. return false;
  1941. //ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ż­Ľč·Î Ŕá°Ü Ŕ־ ż­¸®Áö ľĘ´Â°Í °°´Ů. ż­Ľč¸¦ ±¸ÇŘş¸ŔÚ."));
  1942. }
  1943. break;
  1944.  
  1945. case ITEM_TREASURE_KEY:
  1946. {
  1947. LPITEM item2;
  1948.  
  1949. if (!GetItem(DestCell) || !(item2 = GetItem(DestCell)))
  1950. return false;
  1951.  
  1952. if (item2->IsExchanging())
  1953. return false;
  1954.  
  1955. if (item2->GetType() != ITEM_TREASURE_BOX)
  1956. {
  1957. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ż­Ľč·Î ż©´Â ą°°ÇŔĚ ľĆ´Ń°Í °°´Ů."));
  1958. return false;
  1959. }
  1960.  
  1961. if (item->GetValue(0) == item2->GetValue(0))
  1962. {
  1963. //ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ż­Ľč´Â ¸ÂŔ¸łŞ ľĆŔĚĹŰ ÁÖ´Â şÎşĐ ±¸ÇöŔĚ ľČµÇľú˝Ŕ´Ď´Ů."));
  1964. DWORD dwBoxVnum = item2->GetVnum();
  1965. std::vector <DWORD> dwVnums;
  1966. std::vector <DWORD> dwCounts;
  1967. std::vector <LPITEM> item_gets(NULL);
  1968. int count = 0;
  1969.  
  1970. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  1971. {
  1972. ITEM_MANAGER::instance().RemoveItem(item);
  1973. ITEM_MANAGER::instance().RemoveItem(item2);
  1974.  
  1975. for (int i = 0; i < count; i++){
  1976. switch (dwVnums[i])
  1977. {
  1978. case CSpecialItemGroup::GOLD:
  1979. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µ· %d łÉŔ» ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  1980. break;
  1981. case CSpecialItemGroup::EXP:
  1982. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ şÎĹÍ ˝ĹşńÇŃ şűŔĚ łŞżÉ´Ď´Ů."));
  1983. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%dŔÇ °ćÇčġ¸¦ ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  1984. break;
  1985. case CSpecialItemGroup::MOB:
  1986. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  1987. break;
  1988. case CSpecialItemGroup::SLOW:
  1989. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ »ˇ°Ł ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ żňÁ÷ŔĚ´Â ĽÓµµ°ˇ ´Ŕ·ÁÁł˝Ŕ´Ď´Ů!"));
  1990. break;
  1991. case CSpecialItemGroup::DRAIN_HP:
  1992. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚ°ˇ °©ŔÚ±â ĆřąßÇĎż´˝Ŕ´Ď´Ů! »ý¸í·ÂŔĚ °¨ĽŇÇß˝Ŕ´Ď´Ů."));
  1993. break;
  1994. case CSpecialItemGroup::POISON:
  1995. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ łě»ö ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ µ¶ŔĚ żÂ¸öŔ¸·Î ĆŰÁý´Ď´Ů!"));
  1996. break;
  1997. case CSpecialItemGroup::MOB_GROUP:
  1998. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  1999. break;
  2000. default:
  2001. if (item_gets[i])
  2002. {
  2003. if (dwCounts[i] > 1)
  2004. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ %d °ł łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName(), dwCounts[i]);
  2005. else
  2006. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName());
  2007.  
  2008. }
  2009. }
  2010. }
  2011. }
  2012. else
  2013. {
  2014. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ż­Ľč°ˇ ¸ÂÁö ľĘ´Â °Í °°´Ů."));
  2015. return false;
  2016. }
  2017. }
  2018. else
  2019. {
  2020. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ż­Ľč°ˇ ¸ÂÁö ľĘ´Â °Í °°´Ů."));
  2021. return false;
  2022. }
  2023. }
  2024. break;
  2025.  
  2026. case ITEM_GIFTBOX:
  2027. {
  2028. DWORD dwBoxVnum = item->GetVnum();
  2029. std::vector <DWORD> dwVnums;
  2030. std::vector <DWORD> dwCounts;
  2031. std::vector <LPITEM> item_gets(NULL);
  2032. int count = 0;
  2033.  
  2034. if (dwBoxVnum == 50033 && LC_IsYMIR()) // ľËĽöľř´Â »óŔÚ
  2035. {
  2036. if (GetLevel() < 15)
  2037. {
  2038. ChatPacket(CHAT_TYPE_INFO, "15·ąş§ ŔĚÇĎżˇĽ­´Â »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů.");
  2039. return false;
  2040. }
  2041. }
  2042.  
  2043. if( (dwBoxVnum > 51500 && dwBoxVnum < 52000) || (dwBoxVnum >= 50255 && dwBoxVnum <= 50260) ) // żëČĄżřĽ®µé
  2044. {
  2045. if( !(this->DragonSoul_IsQualified()) )
  2046. {
  2047. ChatPacket(CHAT_TYPE_INFO,LC_TEXT("¸ŐŔú żëČĄĽ® Äů˝şĆ®¸¦ żĎ·áÇĎĽĹľß ÇŐ´Ď´Ů."));
  2048. return false;
  2049. }
  2050. }
  2051.  
  2052. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  2053. {
  2054. item->SetCount(item->GetCount()-1);
  2055.  
  2056. for (int i = 0; i < count; i++){
  2057. switch (dwVnums[i])
  2058. {
  2059. case CSpecialItemGroup::GOLD:
  2060. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µ· %d łÉŔ» ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  2061. break;
  2062. case CSpecialItemGroup::EXP:
  2063. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ şÎĹÍ ˝ĹşńÇŃ şűŔĚ łŞżÉ´Ď´Ů."));
  2064. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%dŔÇ °ćÇčġ¸¦ ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  2065. break;
  2066. case CSpecialItemGroup::MOB:
  2067. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  2068. break;
  2069. case CSpecialItemGroup::SLOW:
  2070. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ »ˇ°Ł ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ żňÁ÷ŔĚ´Â ĽÓµµ°ˇ ´Ŕ·ÁÁł˝Ŕ´Ď´Ů!"));
  2071. break;
  2072. case CSpecialItemGroup::DRAIN_HP:
  2073. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚ°ˇ °©ŔÚ±â ĆřąßÇĎż´˝Ŕ´Ď´Ů! »ý¸í·ÂŔĚ °¨ĽŇÇß˝Ŕ´Ď´Ů."));
  2074. break;
  2075. case CSpecialItemGroup::POISON:
  2076. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ łě»ö ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ µ¶ŔĚ żÂ¸öŔ¸·Î ĆŰÁý´Ď´Ů!"));
  2077. break;
  2078. case CSpecialItemGroup::MOB_GROUP:
  2079. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  2080. break;
  2081. default:
  2082. if (item_gets[i])
  2083. {
  2084. if (dwCounts[i] > 1)
  2085. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ %d °ł łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName(), dwCounts[i]);
  2086. else
  2087. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName());
  2088. }
  2089. }
  2090. }
  2091. }
  2092. else
  2093. {
  2094. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ľĆą«°Íµµ ľňŔ» Ľö ľřľú˝Ŕ´Ď´Ů."));
  2095. return false;
  2096. }
  2097. }
  2098. break;
  2099.  
  2100. case ITEM_SKILLFORGET:
  2101. {
  2102. if (!item->GetSocket(0))
  2103. {
  2104. ITEM_MANAGER::instance().RemoveItem(item);
  2105. return false;
  2106. }
  2107.  
  2108. DWORD dwVnum = item->GetSocket(0);
  2109.  
  2110. if (SkillLevelDown(dwVnum))
  2111. {
  2112. ITEM_MANAGER::instance().RemoveItem(item);
  2113. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("˝şĹł ·ąş§Ŕ» ł»¸®´ÂµĄ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  2114. }
  2115. else
  2116. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("˝şĹł ·ąş§Ŕ» ł»¸± Ľö ľř˝Ŕ´Ď´Ů."));
  2117. }
  2118. break;
  2119.  
  2120. case ITEM_SKILLBOOK:
  2121. {
  2122. if (IsPolymorphed())
  2123. {
  2124. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  2125. return false;
  2126. }
  2127.  
  2128. DWORD dwVnum = 0;
  2129.  
  2130. if (item->GetVnum() == 50300)
  2131. {
  2132. dwVnum = item->GetSocket(0);
  2133. }
  2134. else
  2135. {
  2136. // »ő·Îżî Ľö·ĂĽ­´Â value 0 żˇ ˝şĹł ąřČŁ°ˇ ŔÖŔ¸ąÇ·Î ±×°ÍŔ» »çżë.
  2137. dwVnum = item->GetValue(0);
  2138. }
  2139.  
  2140. if (0 == dwVnum)
  2141. {
  2142. ITEM_MANAGER::instance().RemoveItem(item);
  2143.  
  2144. return false;
  2145. }
  2146.  
  2147. if (true == LearnSkillByBook(dwVnum))
  2148. {
  2149. ITEM_MANAGER::instance().RemoveItem(item);
  2150.  
  2151. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  2152.  
  2153. if (distribution_test_server)
  2154. iReadDelay /= 3;
  2155.  
  2156. //Çѱą ş»Ľ·ŔÇ °ćżěżˇ´Â ˝Ă°ŁŔ» 24˝Ă°Ł °íÁ¤
  2157. if (LC_IsKorea())
  2158. iReadDelay = 86400;
  2159.  
  2160. SetSkillNextReadTime(dwVnum, get_global_time() + iReadDelay);
  2161. }
  2162. }
  2163. break;
  2164.  
  2165. case ITEM_USE:
  2166. {
  2167. if (item->GetVnum() > 50800 && item->GetVnum() <= 50820)
  2168. {
  2169. if (test_server)
  2170. sys_log (0, "ADD addtional effect : vnum(%d) subtype(%d)", item->GetOriginalVnum(), item->GetSubType());
  2171.  
  2172. int affect_type = AFFECT_EXP_BONUS_EURO_FREE;
  2173. int apply_type = aApplyInfo[item->GetValue(0)].bPointType;
  2174. int apply_value = item->GetValue(2);
  2175. int apply_duration = item->GetValue(1);
  2176.  
  2177. switch (item->GetSubType())
  2178. {
  2179. case USE_ABILITY_UP:
  2180. if (FindAffect(affect_type, apply_type))
  2181. {
  2182. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  2183. return false;
  2184. }
  2185.  
  2186. {
  2187. switch (item->GetValue(0))
  2188. {
  2189. case APPLY_MOV_SPEED:
  2190. AddAffect(affect_type, apply_type, apply_value, AFF_MOV_SPEED_POTION, apply_duration, 0, true, true);
  2191. EffectPacket(SE_DXUP_PURPLE); // to pod mov_speed (fioletowy efekt)
  2192. break;
  2193.  
  2194. case APPLY_ATT_SPEED:
  2195. AddAffect(affect_type, apply_type, apply_value, AFF_ATT_SPEED_POTION, apply_duration, 0, true, true);
  2196. break;
  2197.  
  2198. case APPLY_STR:
  2199. case APPLY_DEX:
  2200. case APPLY_CON:
  2201. case APPLY_INT:
  2202. case APPLY_CAST_SPEED:
  2203. case APPLY_RESIST_MAGIC:
  2204. case APPLY_ATT_GRADE_BONUS:
  2205. case APPLY_DEF_GRADE_BONUS:
  2206. AddAffect(affect_type, apply_type, apply_value, 0, apply_duration, 0, true, true);
  2207. break;
  2208. }
  2209. }
  2210.  
  2211. if (GetDungeon())
  2212. GetDungeon()->UsePotion(this);
  2213.  
  2214. if (GetWarMap())
  2215. GetWarMap()->UsePotion(this, item);
  2216.  
  2217. item->SetCount(item->GetCount() - 1);
  2218. break;
  2219.  
  2220. case USE_AFFECT :
  2221. {
  2222. if (FindAffect(AFFECT_EXP_BONUS_EURO_FREE, aApplyInfo[item->GetValue(1)].bPointType))
  2223. {
  2224. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  2225. }
  2226. else
  2227. {
  2228. // PC_BANG_ITEM_ADD
  2229. if (item->IsPCBangItem() == true)
  2230. {
  2231. // PCąćŔÎÁö ĂĽĹ©ÇŘĽ­ Ăł¸®
  2232. if (CPCBangManager::instance().IsPCBangIP(GetDesc()->GetHostName()) == false)
  2233. {
  2234. // PCąćŔĚ ľĆ´Ô!
  2235. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş PCąćżˇĽ­¸¸ »çżëÇŇ Ľö ŔÖ˝Ŕ´Ď´Ů."));
  2236. return false;
  2237. }
  2238. }
  2239. // END_PC_BANG_ITEM_ADD
  2240.  
  2241. AddAffect(AFFECT_EXP_BONUS_EURO_FREE, aApplyInfo[item->GetValue(1)].bPointType, item->GetValue(2), 0, item->GetValue(3), 0, false, true);
  2242. item->SetCount(item->GetCount() - 1);
  2243. }
  2244. }
  2245. break;
  2246.  
  2247. case USE_POTION_NODELAY:
  2248. {
  2249. if (item->GetVnum() >= 71018 && item->GetVnum() <= 71020)
  2250. {
  2251. if ((GetMapIndex() == 110 || GetMapIndex() == 111 || GetMapIndex() == 212))
  2252. {
  2253. ChatPacket(CHAT_TYPE_INFO, "Nie możesz użyć tego przedmiotu podczas Wojny Gildyjnej.");
  2254. return false;
  2255. }
  2256. }
  2257.  
  2258. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  2259. {
  2260. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit") > 0)
  2261. {
  2262. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  2263. return false;
  2264. }
  2265.  
  2266. switch (item->GetVnum())
  2267. {
  2268. case 70020 :
  2269. case 71018 :
  2270. case 71019 :
  2271. case 71020 :
  2272. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit_count") < 10000)
  2273. {
  2274. if (m_nPotionLimit <= 0)
  2275. {
  2276. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»çżë Á¦ÇŃ·®Ŕ» ĂĘ°úÇĎż´˝Ŕ´Ď´Ů."));
  2277. return false;
  2278. }
  2279. }
  2280. break;
  2281.  
  2282. default :
  2283. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  2284. return false;
  2285. break;
  2286. }
  2287. }
  2288.  
  2289. bool used = false;
  2290.  
  2291. if (item->GetValue(0) != 0) // HP Ŕý´ë°Ş ȸşą
  2292. {
  2293. if (GetHP() < GetMaxHP())
  2294. {
  2295. PointChange(POINT_HP, item->GetValue(0) * (100 + GetPoint(POINT_POTION_BONUS)) / 100);
  2296. EffectPacket(SE_HPUP_RED);
  2297. used = TRUE;
  2298. }
  2299. }
  2300.  
  2301. if (item->GetValue(1) != 0) // SP Ŕý´ë°Ş ȸşą
  2302. {
  2303. if (GetSP() < GetMaxSP())
  2304. {
  2305. PointChange(POINT_SP, item->GetValue(1) * (100 + GetPoint(POINT_POTION_BONUS)) / 100);
  2306. EffectPacket(SE_SPUP_BLUE);
  2307. used = TRUE;
  2308. }
  2309. }
  2310.  
  2311. if (item->GetValue(3) != 0) // HP % ȸşą
  2312. {
  2313. if (GetHP() < GetMaxHP())
  2314. {
  2315. PointChange(POINT_HP, item->GetValue(3) * GetMaxHP() / 100);
  2316. EffectPacket(SE_HPUP_RED);
  2317. used = TRUE;
  2318. }
  2319. }
  2320.  
  2321. if (item->GetValue(4) != 0) // SP % ȸşą
  2322. {
  2323. if (GetSP() < GetMaxSP())
  2324. {
  2325. PointChange(POINT_SP, item->GetValue(4) * GetMaxSP() / 100);
  2326. EffectPacket(SE_SPUP_BLUE);
  2327. used = TRUE;
  2328. }
  2329. }
  2330.  
  2331. if (used)
  2332. {
  2333. if (item->GetVnum() == 50085 || item->GetVnum() == 50086)
  2334. {
  2335. if (test_server)
  2336. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żůş´ ¶Ç´Â ÁľŔÚ ¸¦ »çżëÇĎż´˝Ŕ´Ď´Ů"));
  2337. SetUseSeedOrMoonBottleTime();
  2338. }
  2339. if (GetDungeon())
  2340. GetDungeon()->UsePotion(this);
  2341.  
  2342. if (GetWarMap())
  2343. GetWarMap()->UsePotion(this, item);
  2344.  
  2345. m_nPotionLimit--;
  2346.  
  2347. //RESTRICT_USE_SEED_OR_MOONBOTTLE
  2348. item->SetCount(item->GetCount() - 1);
  2349. //END_RESTRICT_USE_SEED_OR_MOONBOTTLE
  2350. }
  2351. }
  2352. break;
  2353. }
  2354.  
  2355. return true;
  2356. }
  2357.  
  2358.  
  2359. if (item->GetVnum() >= 27863 && item->GetVnum() <= 27883)
  2360. {
  2361. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  2362. {
  2363. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  2364. return false;
  2365. }
  2366. }
  2367.  
  2368. if (test_server)
  2369. {
  2370. sys_log (0, "USE_ITEM %s Type %d SubType %d vnum %d", item->GetName(), item->GetType(), item->GetSubType(), item->GetOriginalVnum());
  2371. }
  2372.  
  2373. switch (item->GetSubType())
  2374. {
  2375. case USE_TIME_CHARGE_PER:
  2376. {
  2377. LPITEM pDestItem = GetItem(DestCell);
  2378. if (NULL == pDestItem)
  2379. {
  2380. return false;
  2381. }
  2382. // żěĽ± żëČĄĽ®żˇ °üÇŘĽ­¸¸ Çϵµ·Ď ÇŃ´Ů.
  2383. if (pDestItem->IsDragonSoul())
  2384. {
  2385. int ret;
  2386. char buf[128];
  2387. if (item->GetVnum() == DRAGON_HEART_VNUM)
  2388. {
  2389. ret = pDestItem->GiveMoreTime_Per((float)item->GetSocket(ITEM_SOCKET_CHARGING_AMOUNT_IDX));
  2390. }
  2391. else
  2392. {
  2393. ret = pDestItem->GiveMoreTime_Per((float)item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2394. }
  2395. if (ret > 0)
  2396. {
  2397. if (item->GetVnum() == DRAGON_HEART_VNUM)
  2398. {
  2399. sprintf(buf, "Inc %ds by item{VN:%d SOC%d:%d}", ret, item->GetVnum(), ITEM_SOCKET_CHARGING_AMOUNT_IDX, item->GetSocket(ITEM_SOCKET_CHARGING_AMOUNT_IDX));
  2400. }
  2401. else
  2402. {
  2403. sprintf(buf, "Inc %ds by item{VN:%d VAL%d:%d}", ret, item->GetVnum(), ITEM_VALUE_CHARGING_AMOUNT_IDX, item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2404. }
  2405.  
  2406. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%dĂĘ ¸¸Ĺ­ ĂćŔüµÇľú˝Ŕ´Ď´Ů."), ret);
  2407. item->SetCount(item->GetCount() - 1);
  2408. LogManager::instance().ItemLog(this, item, "DS_CHARGING_SUCCESS", buf);
  2409. return true;
  2410. }
  2411. else
  2412. {
  2413. if (item->GetVnum() == DRAGON_HEART_VNUM)
  2414. {
  2415. sprintf(buf, "No change by item{VN:%d SOC%d:%d}", item->GetVnum(), ITEM_SOCKET_CHARGING_AMOUNT_IDX, item->GetSocket(ITEM_SOCKET_CHARGING_AMOUNT_IDX));
  2416. }
  2417. else
  2418. {
  2419. sprintf(buf, "No change by item{VN:%d VAL%d:%d}", item->GetVnum(), ITEM_VALUE_CHARGING_AMOUNT_IDX, item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2420. }
  2421.  
  2422. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĂćŔüÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  2423. LogManager::instance().ItemLog(this, item, "DS_CHARGING_FAILED", buf);
  2424. return false;
  2425. }
  2426. }
  2427. else
  2428. return false;
  2429. }
  2430. break;
  2431. case USE_TIME_CHARGE_FIX:
  2432. {
  2433. LPITEM pDestItem = GetItem(DestCell);
  2434. if (NULL == pDestItem)
  2435. {
  2436. return false;
  2437. }
  2438. // żěĽ± żëČĄĽ®żˇ °üÇŘĽ­¸¸ Çϵµ·Ď ÇŃ´Ů.
  2439. if (pDestItem->IsDragonSoul())
  2440. {
  2441. int ret = pDestItem->GiveMoreTime_Fix(item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2442. char buf[128];
  2443. if (ret)
  2444. {
  2445. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%dĂĘ ¸¸Ĺ­ ĂćŔüµÇľú˝Ŕ´Ď´Ů."), ret);
  2446. sprintf(buf, "Increase %ds by item{VN:%d VAL%d:%d}", ret, item->GetVnum(), ITEM_VALUE_CHARGING_AMOUNT_IDX, item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2447. LogManager::instance().ItemLog(this, item, "DS_CHARGING_SUCCESS", buf);
  2448. item->SetCount(item->GetCount() - 1);
  2449. return true;
  2450. }
  2451. else
  2452. {
  2453. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĂćŔüÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  2454. sprintf(buf, "No change by item{VN:%d VAL%d:%d}", item->GetVnum(), ITEM_VALUE_CHARGING_AMOUNT_IDX, item->GetValue(ITEM_VALUE_CHARGING_AMOUNT_IDX));
  2455. LogManager::instance().ItemLog(this, item, "DS_CHARGING_FAILED", buf);
  2456. return false;
  2457. }
  2458. }
  2459. else
  2460. return false;
  2461. }
  2462. break;
  2463. case USE_SPECIAL:
  2464.  
  2465. switch (item->GetVnum())
  2466. {
  2467. //Ĺ©¸®˝ş¸¶˝ş ¶őÁÖ
  2468. case ITEM_NOG_POCKET:
  2469. {
  2470. /*
  2471. ¶őÁÖ´É·Âġ : item_proto value ŔÇąĚ
  2472. Ŕ̵żĽÓµµ value 1
  2473. °ř°Ý·Â value 2
  2474. °ćÇčġ value 3
  2475. ÁöĽÓ˝Ă°Ł value 0 (´ÜŔ§ ĂĘ)
  2476.  
  2477. */
  2478. if (FindAffect(AFFECT_NOG_ABILITY))
  2479. {
  2480. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  2481. return false;
  2482. }
  2483. long time = item->GetValue(0);
  2484. long moveSpeedPer = item->GetValue(1);
  2485. long attPer = item->GetValue(2);
  2486. long expPer = item->GetValue(3);
  2487. AddAffect(AFFECT_NOG_ABILITY, POINT_MOV_SPEED, moveSpeedPer, AFF_MOV_SPEED_POTION, time, 0, true, true);
  2488. EffectPacket(SE_DXUP_PURPLE);
  2489. AddAffect(AFFECT_NOG_ABILITY, POINT_MALL_ATTBONUS, attPer, AFF_NONE, time, 0, true, true);
  2490. AddAffect(AFFECT_NOG_ABILITY, POINT_MALL_EXPBONUS, expPer, AFF_NONE, time, 0, true, true);
  2491. item->SetCount(item->GetCount() - 1);
  2492. }
  2493. break;
  2494.  
  2495. //¶ó¸¶´Üżë »çĹÁ
  2496. case ITEM_RAMADAN_CANDY:
  2497. {
  2498. /*
  2499. »çĹÁ´É·Âġ : item_proto value ŔÇąĚ
  2500. Ŕ̵żĽÓµµ value 1
  2501. °ř°Ý·Â value 2
  2502. °ćÇčġ value 3
  2503. ÁöĽÓ˝Ă°Ł value 0 (´ÜŔ§ ĂĘ)
  2504.  
  2505. */
  2506. long time = item->GetValue(0);
  2507. long moveSpeedPer = item->GetValue(1);
  2508. long attPer = item->GetValue(2);
  2509. long expPer = item->GetValue(3);
  2510. AddAffect(AFFECT_RAMADAN_ABILITY, POINT_MOV_SPEED, moveSpeedPer, AFF_MOV_SPEED_POTION, time, 0, true, true);
  2511. AddAffect(AFFECT_RAMADAN_ABILITY, POINT_MALL_ATTBONUS, attPer, AFF_NONE, time, 0, true, true);
  2512. AddAffect(AFFECT_RAMADAN_ABILITY, POINT_MALL_EXPBONUS, expPer, AFF_NONE, time, 0, true, true);
  2513. item->SetCount(item->GetCount() - 1);
  2514. }
  2515. break;
  2516. case ITEM_MARRIAGE_RING:
  2517. {
  2518. marriage::TMarriage* pMarriage = marriage::CManager::instance().Get(GetPlayerID());
  2519. if (pMarriage)
  2520. {
  2521. if (pMarriage->ch1 != NULL)
  2522. {
  2523. if (CArenaManager::instance().IsArenaMap(pMarriage->ch1->GetMapIndex()) == true)
  2524. {
  2525. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  2526. break;
  2527. }
  2528. }
  2529.  
  2530. if (pMarriage->ch2 != NULL)
  2531. {
  2532. if (CArenaManager::instance().IsArenaMap(pMarriage->ch2->GetMapIndex()) == true)
  2533. {
  2534. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  2535. break;
  2536. }
  2537. }
  2538.  
  2539. int consumeSP = CalculateConsumeSP(this);
  2540.  
  2541. if (consumeSP < 0)
  2542. return false;
  2543.  
  2544. PointChange(POINT_SP, -consumeSP, false);
  2545.  
  2546. WarpToPID(pMarriage->GetOther(GetPlayerID()));
  2547. }
  2548. else
  2549. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°áČĄ »óĹ°ˇ ľĆ´Ď¸é °áČĄąÝÁö¸¦ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  2550. }
  2551. break;
  2552.  
  2553. //±âÁ¸ żë±âŔÇ ¸ÁĹä
  2554. case UNIQUE_ITEM_CAPE_OF_COURAGE:
  2555. //¶ó¸¶´Ü ş¸»óżë żë±âŔÇ ¸ÁĹä
  2556. case 70057:
  2557. case REWARD_BOX_UNIQUE_ITEM_CAPE_OF_COURAGE:
  2558. AggregateMonster();
  2559. item->SetCount(item->GetCount()-1);
  2560. break;
  2561.  
  2562. case UNIQUE_ITEM_WHITE_FLAG:
  2563. ForgetMyAttacker();
  2564. item->SetCount(item->GetCount()-1);
  2565. break;
  2566.  
  2567. case UNIQUE_ITEM_TREASURE_BOX:
  2568. break;
  2569.  
  2570. case 30093:
  2571. case 30094:
  2572. case 30095:
  2573. case 30096:
  2574. // şąÁÖ¸Ó´Ď
  2575. {
  2576. const int MAX_BAG_INFO = 26;
  2577. static struct LuckyBagInfo
  2578. {
  2579. DWORD count;
  2580. int prob;
  2581. DWORD vnum;
  2582. } b1[MAX_BAG_INFO] =
  2583. {
  2584. { 1000, 302, 1 },
  2585. { 10, 150, 27002 },
  2586. { 10, 75, 27003 },
  2587. { 10, 100, 27005 },
  2588. { 10, 50, 27006 },
  2589. { 10, 80, 27001 },
  2590. { 10, 50, 27002 },
  2591. { 10, 80, 27004 },
  2592. { 10, 50, 27005 },
  2593. { 1, 10, 50300 },
  2594. { 1, 6, 92 },
  2595. { 1, 2, 132 },
  2596. { 1, 6, 1052 },
  2597. { 1, 2, 1092 },
  2598. { 1, 6, 2082 },
  2599. { 1, 2, 2122 },
  2600. { 1, 6, 3082 },
  2601. { 1, 2, 3122 },
  2602. { 1, 6, 5052 },
  2603. { 1, 2, 5082 },
  2604. { 1, 6, 7082 },
  2605. { 1, 2, 7122 },
  2606. { 1, 1, 11282 },
  2607. { 1, 1, 11482 },
  2608. { 1, 1, 11682 },
  2609. { 1, 1, 11882 },
  2610. };
  2611.  
  2612. struct LuckyBagInfo b2[MAX_BAG_INFO] =
  2613. {
  2614. { 1000, 302, 1 },
  2615. { 10, 150, 27002 },
  2616. { 10, 75, 27002 },
  2617. { 10, 100, 27005 },
  2618. { 10, 50, 27005 },
  2619. { 10, 80, 27001 },
  2620. { 10, 50, 27002 },
  2621. { 10, 80, 27004 },
  2622. { 10, 50, 27005 },
  2623. { 1, 10, 50300 },
  2624. { 1, 6, 92 },
  2625. { 1, 2, 132 },
  2626. { 1, 6, 1052 },
  2627. { 1, 2, 1092 },
  2628. { 1, 6, 2082 },
  2629. { 1, 2, 2122 },
  2630. { 1, 6, 3082 },
  2631. { 1, 2, 3122 },
  2632. { 1, 6, 5052 },
  2633. { 1, 2, 5082 },
  2634. { 1, 6, 7082 },
  2635. { 1, 2, 7122 },
  2636. { 1, 1, 11282 },
  2637. { 1, 1, 11482 },
  2638. { 1, 1, 11682 },
  2639. { 1, 1, 11882 },
  2640. };
  2641.  
  2642. LuckyBagInfo * bi = NULL;
  2643. if (LC_IsHongKong())
  2644. bi = b2;
  2645. else
  2646. bi = b1;
  2647.  
  2648. int pct = number(1, 1000);
  2649.  
  2650. int i;
  2651. for (i=0;i<MAX_BAG_INFO;i++)
  2652. {
  2653. if (pct <= bi[i].prob)
  2654. break;
  2655. pct -= bi[i].prob;
  2656. }
  2657. if (i>=MAX_BAG_INFO)
  2658. return false;
  2659.  
  2660. if (bi[i].vnum == 50300)
  2661. {
  2662. // ˝şĹłĽö·ĂĽ­´Â ĆŻĽöÇĎ°Ô ÁŘ´Ů.
  2663. GiveRandomSkillBook();
  2664. }
  2665. else if (bi[i].vnum == 1)
  2666. {
  2667. PointChange(POINT_GOLD, 1000, true);
  2668. }
  2669. else
  2670. {
  2671. AutoGiveItem(bi[i].vnum, bi[i].count);
  2672. }
  2673. ITEM_MANAGER::instance().RemoveItem(item);
  2674. }
  2675. break;
  2676.  
  2677. case 50004: // ŔĚşĄĆ®żë °¨Áö±â
  2678. {
  2679. if (item->GetSocket(0))
  2680. {
  2681. item->SetSocket(0, item->GetSocket(0) + 1);
  2682. }
  2683. else
  2684. {
  2685. // ĂłŔ˝ »çżë˝Ă
  2686. int iMapIndex = GetMapIndex();
  2687.  
  2688. PIXEL_POSITION pos;
  2689.  
  2690. if (SECTREE_MANAGER::instance().GetRandomLocation(iMapIndex, pos, 700))
  2691. {
  2692. item->SetSocket(0, 1);
  2693. item->SetSocket(1, pos.x);
  2694. item->SetSocket(2, pos.y);
  2695. }
  2696. else
  2697. {
  2698. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ °÷żˇĽ± ŔĚşĄĆ®żë °¨Áö±â°ˇ µżŔŰÇĎÁö ľĘ´Â°Í °°˝Ŕ´Ď´Ů."));
  2699. return false;
  2700. }
  2701. }
  2702.  
  2703. int dist = 0;
  2704. float distance = (DISTANCE_SQRT(GetX()-item->GetSocket(1), GetY()-item->GetSocket(2)));
  2705.  
  2706. if (distance < 1000.0f)
  2707. {
  2708. // ąß°ß!
  2709. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚşĄĆ®żë °¨Áö±â°ˇ ˝Ĺşń·Îżî şűŔ» ł»¸ç »ç¶óÁý´Ď´Ů."));
  2710.  
  2711. // »çżëČ˝Ľöżˇ µű¶ó ÁÖ´Â ľĆŔĚĹŰŔ» ´Ů¸Ł°Ô ÇŃ´Ů.
  2712. struct TEventStoneInfo
  2713. {
  2714. DWORD dwVnum;
  2715. int count;
  2716. int prob;
  2717. };
  2718. const int EVENT_STONE_MAX_INFO = 15;
  2719. TEventStoneInfo info_10[EVENT_STONE_MAX_INFO] =
  2720. {
  2721. { 27001, 10, 8 },
  2722. { 27004, 10, 6 },
  2723. { 27002, 10, 12 },
  2724. { 27005, 10, 12 },
  2725. { 27100, 1, 9 },
  2726. { 27103, 1, 9 },
  2727. { 27101, 1, 10 },
  2728. { 27104, 1, 10 },
  2729. { 27999, 1, 12 },
  2730.  
  2731. { 25040, 1, 4 },
  2732.  
  2733. { 27410, 1, 0 },
  2734. { 27600, 1, 0 },
  2735. { 25100, 1, 0 },
  2736.  
  2737. { 50001, 1, 0 },
  2738. { 50003, 1, 1 },
  2739. };
  2740. TEventStoneInfo info_7[EVENT_STONE_MAX_INFO] =
  2741. {
  2742. { 27001, 10, 1 },
  2743. { 27004, 10, 1 },
  2744. { 27004, 10, 9 },
  2745. { 27005, 10, 9 },
  2746. { 27100, 1, 5 },
  2747. { 27103, 1, 5 },
  2748. { 27101, 1, 10 },
  2749. { 27104, 1, 10 },
  2750. { 27999, 1, 14 },
  2751.  
  2752. { 25040, 1, 5 },
  2753.  
  2754. { 27410, 1, 5 },
  2755. { 27600, 1, 5 },
  2756. { 25100, 1, 5 },
  2757.  
  2758. { 50001, 1, 0 },
  2759. { 50003, 1, 5 },
  2760.  
  2761. };
  2762. TEventStoneInfo info_4[EVENT_STONE_MAX_INFO] =
  2763. {
  2764. { 27001, 10, 0 },
  2765. { 27004, 10, 0 },
  2766. { 27002, 10, 0 },
  2767. { 27005, 10, 0 },
  2768. { 27100, 1, 0 },
  2769. { 27103, 1, 0 },
  2770. { 27101, 1, 0 },
  2771. { 27104, 1, 0 },
  2772. { 27999, 1, 25 },
  2773.  
  2774. { 25040, 1, 0 },
  2775.  
  2776. { 27410, 1, 0 },
  2777. { 27600, 1, 0 },
  2778. { 25100, 1, 15 },
  2779.  
  2780. { 50001, 1, 10 },
  2781. { 50003, 1, 50 },
  2782.  
  2783. };
  2784.  
  2785. {
  2786. TEventStoneInfo* info;
  2787. if (item->GetSocket(0) <= 4)
  2788. info = info_4;
  2789. else if (item->GetSocket(0) <= 7)
  2790. info = info_7;
  2791. else
  2792. info = info_10;
  2793.  
  2794. int prob = number(1, 100);
  2795.  
  2796. for (int i = 0; i < EVENT_STONE_MAX_INFO; ++i)
  2797. {
  2798. if (!info[i].prob)
  2799. continue;
  2800.  
  2801. if (prob <= info[i].prob)
  2802. {
  2803. if (info[i].dwVnum == 50001)
  2804. {
  2805. DWORD * pdw = M2_NEW DWORD[2];
  2806.  
  2807. pdw[0] = info[i].dwVnum;
  2808. pdw[1] = info[i].count;
  2809.  
  2810. // ĂßĂ·Ľ­´Â ĽŇÄĎŔ» ĽłÁ¤ÇŃ´Ů
  2811. DBManager::instance().ReturnQuery(QID_LOTTO, GetPlayerID(), pdw,
  2812. "INSERT INTO lotto_list VALUES(0, 'server%s', %u, NOW())",
  2813. get_table_postfix(), GetPlayerID());
  2814. }
  2815. else
  2816. AutoGiveItem(info[i].dwVnum, info[i].count);
  2817.  
  2818. break;
  2819. }
  2820. prob -= info[i].prob;
  2821. }
  2822. }
  2823.  
  2824. char chatbuf[CHAT_MAX_LEN + 1];
  2825. int len = snprintf(chatbuf, sizeof(chatbuf), "StoneDetect %u 0 0", (DWORD)GetVID());
  2826.  
  2827. if (len < 0 || len >= (int) sizeof(chatbuf))
  2828. len = sizeof(chatbuf) - 1;
  2829.  
  2830. ++len; // \0 ą®ŔÚ±îÁö ş¸ł»±â
  2831.  
  2832. TPacketGCChat pack_chat;
  2833. pack_chat.header = HEADER_GC_CHAT;
  2834. pack_chat.size = sizeof(TPacketGCChat) + len;
  2835. pack_chat.type = CHAT_TYPE_COMMAND;
  2836. pack_chat.id = 0;
  2837. pack_chat.bEmpire = GetDesc()->GetEmpire();
  2838. //pack_chat.id = vid;
  2839.  
  2840. TEMP_BUFFER buf;
  2841. buf.write(&pack_chat, sizeof(TPacketGCChat));
  2842. buf.write(chatbuf, len);
  2843.  
  2844. PacketAround(buf.read_peek(), buf.size());
  2845.  
  2846. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (DETECT_EVENT_STONE) 1");
  2847. return true;
  2848. }
  2849. else if (distance < 20000)
  2850. dist = 1;
  2851. else if (distance < 70000)
  2852. dist = 2;
  2853. else
  2854. dist = 3;
  2855.  
  2856. // ¸ąŔĚ »çżëÇßŔ¸¸é »ç¶óÁř´Ů.
  2857. const int STONE_DETECT_MAX_TRY = 10;
  2858. if (item->GetSocket(0) >= STONE_DETECT_MAX_TRY)
  2859. {
  2860. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚşĄĆ®żë °¨Áö±â°ˇ ČçŔűµµ ľřŔĚ »ç¶óÁý´Ď´Ů."));
  2861. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (DETECT_EVENT_STONE) 0");
  2862. AutoGiveItem(27002);
  2863. return true;
  2864. }
  2865.  
  2866. if (dist)
  2867. {
  2868. char chatbuf[CHAT_MAX_LEN + 1];
  2869. int len = snprintf(chatbuf, sizeof(chatbuf),
  2870. "StoneDetect %u %d %d",
  2871. (DWORD)GetVID(), dist, (int)GetDegreeFromPositionXY(GetX(), item->GetSocket(2), item->GetSocket(1), GetY()));
  2872.  
  2873. if (len < 0 || len >= (int) sizeof(chatbuf))
  2874. len = sizeof(chatbuf) - 1;
  2875.  
  2876. ++len; // \0 ą®ŔÚ±îÁö ş¸ł»±â
  2877.  
  2878. TPacketGCChat pack_chat;
  2879. pack_chat.header = HEADER_GC_CHAT;
  2880. pack_chat.size = sizeof(TPacketGCChat) + len;
  2881. pack_chat.type = CHAT_TYPE_COMMAND;
  2882. pack_chat.id = 0;
  2883. pack_chat.bEmpire = GetDesc()->GetEmpire();
  2884. //pack_chat.id = vid;
  2885.  
  2886. TEMP_BUFFER buf;
  2887. buf.write(&pack_chat, sizeof(TPacketGCChat));
  2888. buf.write(chatbuf, len);
  2889.  
  2890. PacketAround(buf.read_peek(), buf.size());
  2891. }
  2892.  
  2893. }
  2894. break;
  2895.  
  2896. case 27989: // żµĽ®°¨Áö±â
  2897. case 76006: // Ľ±ą°żë żµĽ®°¨Áö±â
  2898. {
  2899. LPSECTREE_MAP pMap = SECTREE_MANAGER::instance().GetMap(GetMapIndex());
  2900.  
  2901. if (pMap != NULL)
  2902. {
  2903. item->SetSocket(0, item->GetSocket(0) + 1);
  2904.  
  2905. FFindStone f;
  2906.  
  2907. // <Factor> SECTREE::for_each -> SECTREE::for_each_entity
  2908. pMap->for_each(f);
  2909.  
  2910. if (f.m_mapStone.size() > 0)
  2911. {
  2912. std::map<DWORD, LPCHARACTER>::iterator stone = f.m_mapStone.begin();
  2913.  
  2914. DWORD max = UINT_MAX;
  2915. LPCHARACTER pTarget = stone->second;
  2916.  
  2917. while (stone != f.m_mapStone.end())
  2918. {
  2919. DWORD dist = (DWORD)DISTANCE_SQRT(GetX()-stone->second->GetX(), GetY()-stone->second->GetY());
  2920.  
  2921. if (dist != 0 && max > dist)
  2922. {
  2923. max = dist;
  2924. pTarget = stone->second;
  2925. }
  2926. stone++;
  2927. }
  2928.  
  2929. if (pTarget != NULL)
  2930. {
  2931. int val = 3;
  2932.  
  2933. if (max < 10000) val = 2;
  2934. else if (max < 70000) val = 1;
  2935.  
  2936. ChatPacket(CHAT_TYPE_COMMAND, "StoneDetect %u %d %d", (DWORD)GetVID(), val,
  2937. (int)GetDegreeFromPositionXY(GetX(), pTarget->GetY(), pTarget->GetX(), GetY()));
  2938. }
  2939. else
  2940. {
  2941. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°¨Áö±â¸¦ ŔŰżëÇĎż´Ŕ¸łŞ °¨ÁöµÇ´Â żµĽ®ŔĚ ľř˝Ŕ´Ď´Ů."));
  2942. }
  2943. }
  2944. else
  2945. {
  2946. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°¨Áö±â¸¦ ŔŰżëÇĎż´Ŕ¸łŞ °¨ÁöµÇ´Â żµĽ®ŔĚ ľř˝Ŕ´Ď´Ů."));
  2947. }
  2948.  
  2949. if (item->GetSocket(0) >= 6)
  2950. {
  2951. ChatPacket(CHAT_TYPE_COMMAND, "StoneDetect %u 0 0", (DWORD)GetVID());
  2952. ITEM_MANAGER::instance().RemoveItem(item);
  2953. }
  2954. }
  2955. break;
  2956. }
  2957. break;
  2958.  
  2959. case 27996: // µ¶ş´
  2960. item->SetCount(item->GetCount() - 1);
  2961. /*if (GetSkillLevel(SKILL_CREATE_POISON))
  2962. AddAffect(AFFECT_ATT_GRADE, POINT_ATT_GRADE, 3, AFF_DRINK_POISON, 15*60, 0, true);
  2963. else
  2964. {
  2965. // µ¶´Ů·ç±â°ˇ ľřŔ¸¸é 50% Áď»ç 50% °ř°Ý·Â +2
  2966. if (number(0, 1))
  2967. {
  2968. if (GetHP() > 100)
  2969. PointChange(POINT_HP, -(GetHP() - 1));
  2970. else
  2971. Dead();
  2972. }
  2973. else
  2974. AddAffect(AFFECT_ATT_GRADE, POINT_ATT_GRADE, 2, AFF_DRINK_POISON, 15*60, 0, true);
  2975. }*/
  2976. break;
  2977.  
  2978. case 27987: // Á¶°ł
  2979. // 50 µąÁ¶°˘ 47990
  2980. // 30 ˛Î
  2981. // 10 ąéÁřÁÖ 47992
  2982. // 7 Ă»ÁřÁÖ 47993
  2983. // 3 ÇÇÁřÁÖ 47994
  2984. {
  2985. item->SetCount(item->GetCount() - 1);
  2986.  
  2987. int r = number(1, 100);
  2988.  
  2989. if (r <= 50)
  2990. {
  2991. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á¶°łżˇĽ­ µąÁ¶°˘ŔĚ łŞżÔ˝Ŕ´Ď´Ů."));
  2992. AutoGiveItem(27990);
  2993. }
  2994. else
  2995. {
  2996. const int prob_table_euckr[] =
  2997. {
  2998. 80, 90, 97
  2999. };
  3000.  
  3001. const int prob_table_gb2312[] =
  3002. {
  3003. 95, 97, 99
  3004. };
  3005.  
  3006. const int * prob_table = !g_iUseLocale ? prob_table_euckr : prob_table_gb2312;
  3007.  
  3008. if (r <= prob_table[0])
  3009. {
  3010. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á¶°ł°ˇ ČçŔűµµ ľřŔĚ »ç¶óÁý´Ď´Ů."));
  3011. }
  3012. else if (r <= prob_table[1])
  3013. {
  3014. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á¶°łżˇĽ­ ąéÁřÁÖ°ˇ łŞżÔ˝Ŕ´Ď´Ů."));
  3015. AutoGiveItem(27992);
  3016. }
  3017. else if (r <= prob_table[2])
  3018. {
  3019. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á¶°łżˇĽ­ Ă»ÁřÁÖ°ˇ łŞżÔ˝Ŕ´Ď´Ů."));
  3020. AutoGiveItem(27993);
  3021. }
  3022. else
  3023. {
  3024. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á¶°łżˇĽ­ ÇÇÁřÁÖ°ˇ łŞżÔ˝Ŕ´Ď´Ů."));
  3025. AutoGiveItem(27994);
  3026. }
  3027. }
  3028. }
  3029. break;
  3030.  
  3031. case 71013: // ĂŕÁ¦żëĆřÁ×
  3032. CreateFly(number(FLY_FIREWORK1, FLY_FIREWORK6), this);
  3033. item->SetCount(item->GetCount() - 1);
  3034. break;
  3035.  
  3036. case 50100: // ĆřÁ×
  3037. case 50101:
  3038. case 50102:
  3039. case 50103:
  3040. case 50104:
  3041. case 50105:
  3042. case 50106:
  3043. CreateFly(item->GetVnum() - 50100 + FLY_FIREWORK1, this);
  3044. item->SetCount(item->GetCount() - 1);
  3045. break;
  3046.  
  3047. case 50200: // ş¸µű¸®
  3048. if (LC_IsYMIR() == true || LC_IsKorea() == true)
  3049. {
  3050. if (IS_BOTARYABLE_ZONE(GetMapIndex()) == true)
  3051. {
  3052. __OpenPrivateShop();
  3053. }
  3054. else
  3055. {
  3056. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°łŔÎ »óÁˇŔ» ż­ Ľö ľř´Â ÁöżŞŔÔ´Ď´Ů"));
  3057. }
  3058. }
  3059. else
  3060. {
  3061. __OpenPrivateShop();
  3062. }
  3063. break;
  3064.  
  3065. case fishing::FISH_MIND_PILL_VNUM:
  3066. AddAffect(AFFECT_FISH_MIND_PILL, POINT_NONE, 0, AFF_FISH_MIND, 20*60, 0, true);
  3067. item->SetCount(item->GetCount() - 1);
  3068. break;
  3069.  
  3070. case 50301: // ĹëĽÖ·Â Ľö·ĂĽ­
  3071. case 50302:
  3072. case 50303:
  3073. {
  3074. if (IsPolymorphed() == true)
  3075. {
  3076. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µĐ°© Áßżˇ´Â ´É·ÂŔ» żĂ¸± Ľö ľř˝Ŕ´Ď´Ů."));
  3077. return false;
  3078. }
  3079.  
  3080. int lv = GetSkillLevel(SKILL_LEADERSHIP);
  3081.  
  3082. if (lv < item->GetValue(0))
  3083. {
  3084. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ĂĄŔş łĘą« ľî·Áżö ŔĚÇŘÇϱⰡ Čűµě´Ď´Ů."));
  3085. return false;
  3086. }
  3087.  
  3088. if (lv >= item->GetValue(1))
  3089. {
  3090. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ĂĄŔş ľĆą«¸® şÁµµ µµżňŔĚ µÉ °Í °°Áö ľĘ˝Ŕ´Ď´Ů."));
  3091. return false;
  3092. }
  3093.  
  3094. if (LearnSkillByBook(SKILL_LEADERSHIP))
  3095. {
  3096. ITEM_MANAGER::instance().RemoveItem(item);
  3097.  
  3098. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3099. if (distribution_test_server) iReadDelay /= 3;
  3100.  
  3101. SetSkillNextReadTime(SKILL_LEADERSHIP, get_global_time() + iReadDelay);
  3102. }
  3103. }
  3104. break;
  3105.  
  3106. case 50304: // ż¬°č±â Ľö·ĂĽ­
  3107. case 50305:
  3108. case 50306:
  3109. {
  3110. if (IsPolymorphed())
  3111. {
  3112. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3113. return false;
  3114.  
  3115. }
  3116. if (GetSkillLevel(SKILL_COMBO) == 0 && GetLevel() < 30)
  3117. {
  3118. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("·ąş§ 30ŔĚ µÇ±â Ŕüżˇ´Â ˝ŔµćÇŇ Ľö ŔÖŔ» °Í °°Áö ľĘ˝Ŕ´Ď´Ů."));
  3119. return false;
  3120. }
  3121.  
  3122. if (GetSkillLevel(SKILL_COMBO) == 1 && GetLevel() < 50)
  3123. {
  3124. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("·ąş§ 50ŔĚ µÇ±â Ŕüżˇ´Â ˝ŔµćÇŇ Ľö ŔÖŔ» °Í °°Áö ľĘ˝Ŕ´Ď´Ů."));
  3125. return false;
  3126. }
  3127.  
  3128. if (GetSkillLevel(SKILL_COMBO) >= 2)
  3129. {
  3130. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ż¬°č±â´Â ´őŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3131. return false;
  3132. }
  3133.  
  3134. int iPct = item->GetValue(0);
  3135.  
  3136. if (LearnSkillByBook(SKILL_COMBO, iPct))
  3137. {
  3138. ITEM_MANAGER::instance().RemoveItem(item);
  3139.  
  3140. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3141. if (distribution_test_server) iReadDelay /= 3;
  3142.  
  3143. SetSkillNextReadTime(SKILL_COMBO, get_global_time() + iReadDelay);
  3144. }
  3145. }
  3146. break;
  3147. case 50311: // ľđľî Ľö·ĂĽ­
  3148. case 50312:
  3149. case 50313:
  3150. {
  3151. if (IsPolymorphed())
  3152. {
  3153. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3154. return false;
  3155.  
  3156. }
  3157. DWORD dwSkillVnum = item->GetValue(0);
  3158. int iPct = MINMAX(0, item->GetValue(1), 100);
  3159. if (GetSkillLevel(dwSkillVnum)>=20 || dwSkillVnum-SKILL_LANGUAGE1+1 == GetEmpire())
  3160. {
  3161. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ żĎş®ÇĎ°Ô ľËľĆµéŔ» Ľö ŔÖ´Â ľđľîŔĚ´Ů."));
  3162. return false;
  3163. }
  3164.  
  3165. if (LearnSkillByBook(dwSkillVnum, iPct))
  3166. {
  3167. ITEM_MANAGER::instance().RemoveItem(item);
  3168.  
  3169. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3170. if (distribution_test_server) iReadDelay /= 3;
  3171.  
  3172. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3173. }
  3174. }
  3175. break;
  3176.  
  3177. case 50061 : // ŔĎş» ¸» ĽŇČŻ ˝şĹł Ľö·ĂĽ­
  3178. {
  3179. if (IsPolymorphed())
  3180. {
  3181. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3182. return false;
  3183.  
  3184. }
  3185. DWORD dwSkillVnum = item->GetValue(0);
  3186. int iPct = MINMAX(0, item->GetValue(1), 100);
  3187.  
  3188. if (GetSkillLevel(dwSkillVnum) >= 10)
  3189. {
  3190. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3191. return false;
  3192. }
  3193.  
  3194. if (LearnSkillByBook(dwSkillVnum, iPct))
  3195. {
  3196. ITEM_MANAGER::instance().RemoveItem(item);
  3197.  
  3198. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3199. if (distribution_test_server) iReadDelay /= 3;
  3200.  
  3201. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3202. }
  3203. }
  3204. break;
  3205.  
  3206. case 50314: case 50315: case 50316: // şŻ˝Ĺ Ľö·ĂĽ­
  3207. case 50323: case 50324: // ÁőÇ÷ Ľö·ĂĽ­
  3208. case 50325: case 50326: // öĹë Ľö·ĂĽ­
  3209. {
  3210. if (IsPolymorphed() == true)
  3211. {
  3212. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µĐ°© Áßżˇ´Â ´É·ÂŔ» żĂ¸± Ľö ľř˝Ŕ´Ď´Ů."));
  3213. return false;
  3214. }
  3215.  
  3216. int iSkillLevelLowLimit = item->GetValue(0);
  3217. int iSkillLevelHighLimit = item->GetValue(1);
  3218. int iPct = MINMAX(0, item->GetValue(2), 100);
  3219. int iLevelLimit = item->GetValue(3);
  3220. DWORD dwSkillVnum = 0;
  3221.  
  3222. switch (item->GetVnum())
  3223. {
  3224. case 50314: case 50315: case 50316:
  3225. dwSkillVnum = SKILL_POLYMORPH;
  3226. break;
  3227.  
  3228. case 50323: case 50324:
  3229. dwSkillVnum = SKILL_ADD_HP;
  3230. break;
  3231.  
  3232. case 50325: case 50326:
  3233. dwSkillVnum = SKILL_RESIST_PENETRATE;
  3234. break;
  3235.  
  3236. default:
  3237. return false;
  3238. }
  3239.  
  3240. if (0 == dwSkillVnum)
  3241. return false;
  3242.  
  3243. if (GetLevel() < iLevelLimit)
  3244. {
  3245. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ĂĄŔ» ŔĐŔ¸·Á¸é ·ąş§Ŕ» ´ő żĂ·Áľß ÇŐ´Ď´Ů."));
  3246. return false;
  3247. }
  3248.  
  3249. if (GetSkillLevel(dwSkillVnum) >= 40)
  3250. {
  3251. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3252. return false;
  3253. }
  3254.  
  3255. if (GetSkillLevel(dwSkillVnum) < iSkillLevelLowLimit)
  3256. {
  3257. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ĂĄŔş łĘą« ľî·Áżö ŔĚÇŘÇϱⰡ Čűµě´Ď´Ů."));
  3258. return false;
  3259. }
  3260.  
  3261. if (GetSkillLevel(dwSkillVnum) >= iSkillLevelHighLimit)
  3262. {
  3263. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ĂĄŔ¸·Î´Â ´ő ŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3264. return false;
  3265. }
  3266.  
  3267. if (LearnSkillByBook(dwSkillVnum, iPct))
  3268. {
  3269. ITEM_MANAGER::instance().RemoveItem(item);
  3270.  
  3271. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3272. if (distribution_test_server) iReadDelay /= 3;
  3273.  
  3274. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3275. }
  3276. }
  3277. break;
  3278.  
  3279. case 50902:
  3280. case 50903:
  3281. case 50904:
  3282. {
  3283. if (IsPolymorphed())
  3284. {
  3285. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3286. return false;
  3287.  
  3288. }
  3289. DWORD dwSkillVnum = SKILL_CREATE;
  3290. int iPct = MINMAX(0, item->GetValue(1), 100);
  3291.  
  3292. if (GetSkillLevel(dwSkillVnum)>=40)
  3293. {
  3294. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3295. return false;
  3296. }
  3297.  
  3298. if (LearnSkillByBook(dwSkillVnum, iPct))
  3299. {
  3300. ITEM_MANAGER::instance().RemoveItem(item);
  3301.  
  3302. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3303. if (distribution_test_server) iReadDelay /= 3;
  3304.  
  3305. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3306.  
  3307. if (test_server)
  3308. {
  3309. ChatPacket(CHAT_TYPE_INFO, "[TEST_SERVER] Success to learn skill ");
  3310. }
  3311. }
  3312. else
  3313. {
  3314. if (test_server)
  3315. {
  3316. ChatPacket(CHAT_TYPE_INFO, "[TEST_SERVER] Failed to learn skill ");
  3317. }
  3318. }
  3319. }
  3320. break;
  3321.  
  3322. // MINING
  3323. case ITEM_MINING_SKILL_TRAIN_BOOK:
  3324. {
  3325. if (IsPolymorphed())
  3326. {
  3327. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3328. return false;
  3329.  
  3330. }
  3331. DWORD dwSkillVnum = SKILL_MINING;
  3332. int iPct = MINMAX(0, item->GetValue(1), 100);
  3333.  
  3334. if (GetSkillLevel(dwSkillVnum)>=40)
  3335. {
  3336. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó Ľö·ĂÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3337. return false;
  3338. }
  3339.  
  3340. if (LearnSkillByBook(dwSkillVnum, iPct))
  3341. {
  3342. ITEM_MANAGER::instance().RemoveItem(item);
  3343.  
  3344. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3345. if (distribution_test_server) iReadDelay /= 3;
  3346.  
  3347. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3348. }
  3349. }
  3350. break;
  3351. // END_OF_MINING
  3352.  
  3353. case ITEM_HORSE_SKILL_TRAIN_BOOK:
  3354. {
  3355. if (IsPolymorphed())
  3356. {
  3357. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ˝ĹÁßżˇ´Â ĂĄŔ» ŔĐŔ»Ľö ľř˝Ŕ´Ď´Ů."));
  3358. return false;
  3359.  
  3360. }
  3361. DWORD dwSkillVnum = SKILL_HORSE;
  3362. int iPct = MINMAX(0, item->GetValue(1), 100);
  3363.  
  3364. if (GetLevel() < 50)
  3365. {
  3366. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆÁ÷ ˝Â¸¶ ˝şĹłŔ» Ľö·ĂÇŇ Ľö ŔÖ´Â ·ąş§ŔĚ ľĆ´Ő´Ď´Ů."));
  3367. return false;
  3368. }
  3369.  
  3370. if (!test_server && get_global_time() < GetSkillNextReadTime(dwSkillVnum))
  3371. {
  3372. if (FindAffect(AFFECT_SKILL_NO_BOOK_DELAY))
  3373. {
  3374. // Á־ȼúĽ­ »çżëÁßżˇ´Â ˝Ă°Ł Á¦ÇŃ ą«˝Ă
  3375. RemoveAffect(AFFECT_SKILL_NO_BOOK_DELAY);
  3376. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á־ȼúĽ­¸¦ ĹëÇŘ ÁÖČ­ŔÔ¸¶żˇĽ­ şüÁ®łŞżÔ˝Ŕ´Ď´Ů."));
  3377. }
  3378. else
  3379. {
  3380. SkillLearnWaitMoreTimeMessage(GetSkillNextReadTime(dwSkillVnum) - get_global_time());
  3381. return false;
  3382. }
  3383. }
  3384.  
  3385. if (GetPoint(POINT_HORSE_SKILL) >= 20 ||
  3386. GetSkillLevel(SKILL_HORSE_WILDATTACK) + GetSkillLevel(SKILL_HORSE_CHARGE) + GetSkillLevel(SKILL_HORSE_ESCAPE) >= 60 ||
  3387. GetSkillLevel(SKILL_HORSE_WILDATTACK_RANGE) + GetSkillLevel(SKILL_HORSE_CHARGE) + GetSkillLevel(SKILL_HORSE_ESCAPE) >= 60)
  3388. {
  3389. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó ˝Â¸¶ Ľö·ĂĽ­¸¦ ŔĐŔ» Ľö ľř˝Ŕ´Ď´Ů."));
  3390. return false;
  3391. }
  3392.  
  3393. if (number(1, 100) <= iPct)
  3394. {
  3395. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("˝Â¸¶ Ľö·ĂĽ­¸¦ ŔĐľî ˝Â¸¶ ˝şĹł Ć÷ŔÎĆ®¸¦ ľňľú˝Ŕ´Ď´Ů."));
  3396. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľňŔş Ć÷ŔÎĆ®·Î´Â ˝Â¸¶ ˝şĹłŔÇ ·ąş§Ŕ» żĂ¸± Ľö ŔÖ˝Ŕ´Ď´Ů."));
  3397. PointChange(POINT_HORSE_SKILL, 1);
  3398.  
  3399. int iReadDelay = number(SKILLBOOK_DELAY_MIN, SKILLBOOK_DELAY_MAX);
  3400. if (distribution_test_server) iReadDelay /= 3;
  3401.  
  3402. if (!test_server)
  3403. SetSkillNextReadTime(dwSkillVnum, get_global_time() + iReadDelay);
  3404. }
  3405. else
  3406. {
  3407. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("˝Â¸¶ Ľö·ĂĽ­ ŔĚÇŘżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  3408. }
  3409.  
  3410. ITEM_MANAGER::instance().RemoveItem(item);
  3411. }
  3412. break;
  3413.  
  3414. case 70102: // Ľ±µÎ
  3415. case 70103: // Ľ±µÎ
  3416. {
  3417. if (GetAlignment() >= 0)
  3418. return false;
  3419.  
  3420. int delta = MIN(-GetAlignment(), item->GetValue(0));
  3421.  
  3422. sys_log(0, "%s ALIGNMENT ITEM %d", GetName(), delta);
  3423.  
  3424. UpdateAlignment(delta);
  3425. item->SetCount(item->GetCount() - 1);
  3426.  
  3427. if (delta / 10 > 0)
  3428. {
  3429. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("¸¶Ŕ˝ŔĚ ¸ĽľĆÁö´Â±ş. °ˇ˝żŔ» Áţ´©¸Ł´ř ą«ľđ°ˇ°ˇ Á» °ˇş­żöÁř ´Ŕł¦ŔĚľß."));
  3430. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľ±ľÇġ°ˇ %d Áő°ˇÇĎż´˝Ŕ´Ď´Ů."), delta/10);
  3431. }
  3432. }
  3433. break;
  3434.  
  3435. case 71107: // õµµşąĽţľĆ
  3436. {
  3437. int val = item->GetValue(0);
  3438. int interval = item->GetValue(1);
  3439. quest::PC* pPC = quest::CQuestManager::instance().GetPC(GetPlayerID());
  3440. int last_use_time = pPC->GetFlag("mythical_peach.last_use_time");
  3441.  
  3442. if (get_global_time() - last_use_time < interval * 60 * 60)
  3443. {
  3444. if (test_server == false)
  3445. {
  3446. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆÁ÷ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  3447. return false;
  3448. }
  3449. else
  3450. {
  3451. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ĺ×˝şĆ® Ľ­ąö ˝Ă°ŁÁ¦ÇŃ Ĺë°ú"));
  3452. }
  3453. }
  3454.  
  3455. if (GetAlignment() == 200000)
  3456. {
  3457. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľ±ľÇġ¸¦ ´ő ŔĚ»ó żĂ¸± Ľö ľř˝Ŕ´Ď´Ů."));
  3458. return false;
  3459. }
  3460.  
  3461. if (200000 - GetAlignment() < val * 10)
  3462. {
  3463. val = (200000 - GetAlignment()) / 10;
  3464. }
  3465.  
  3466. int old_alignment = GetAlignment() / 10;
  3467.  
  3468. UpdateAlignment(val*10);
  3469.  
  3470. item->SetCount(item->GetCount()-1);
  3471. pPC->SetFlag("mythical_peach.last_use_time", get_global_time());
  3472.  
  3473. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("¸¶Ŕ˝ŔĚ ¸ĽľĆÁö´Â±ş. °ˇ˝żŔ» Áţ´©¸Ł´ř ą«ľđ°ˇ°ˇ Á» °ˇş­żöÁř ´Ŕł¦ŔĚľß."));
  3474. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľ±ľÇġ°ˇ %d Áő°ˇÇĎż´˝Ŕ´Ď´Ů."), val);
  3475.  
  3476. char buf[256 + 1];
  3477. snprintf(buf, sizeof(buf), "%d %d", old_alignment, GetAlignment() / 10);
  3478. LogManager::instance().CharLog(this, val, "MYTHICAL_PEACH", buf);
  3479. }
  3480. break;
  3481.  
  3482. case 71109: // Ĺ»Ľ®Ľ­
  3483. case 72719:
  3484. {
  3485. LPITEM item2;
  3486.  
  3487. if (!IsValidItemPosition(DestCell) || !(item2 = GetItem(DestCell)))
  3488. return false;
  3489.  
  3490. if (item2->IsExchanging() == true)
  3491. return false;
  3492.  
  3493. if (item2->GetSocketCount() == 0)
  3494. return false;
  3495.  
  3496. switch( item2->GetType() )
  3497. {
  3498. case ITEM_WEAPON:
  3499. break;
  3500. case ITEM_ARMOR:
  3501. switch (item2->GetSubType())
  3502. {
  3503. case ARMOR_EAR:
  3504. case ARMOR_WRIST:
  3505. case ARMOR_NECK:
  3506. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»©łľ żµĽ®ŔĚ ľř˝Ŕ´Ď´Ů"));
  3507. return false;
  3508. }
  3509. break;
  3510.  
  3511. default:
  3512. return false;
  3513. }
  3514.  
  3515. std::stack<long> socket;
  3516.  
  3517. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  3518. socket.push(item2->GetSocket(i));
  3519.  
  3520. int idx = ITEM_SOCKET_MAX_NUM - 1;
  3521.  
  3522. while (socket.size() > 0)
  3523. {
  3524. if (socket.top() > 2 && socket.top() != ITEM_BROKEN_METIN_VNUM)
  3525. break;
  3526.  
  3527. idx--;
  3528. socket.pop();
  3529. }
  3530.  
  3531. if (socket.size() == 0)
  3532. {
  3533. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»©łľ żµĽ®ŔĚ ľř˝Ŕ´Ď´Ů"));
  3534. return false;
  3535. }
  3536.  
  3537. LPITEM pItemReward = AutoGiveItem(socket.top());
  3538.  
  3539. if (pItemReward != NULL)
  3540. {
  3541. item2->SetSocket(idx, 1);
  3542.  
  3543. char buf[256+1];
  3544. snprintf(buf, sizeof(buf), "%s(%u) %s(%u)",
  3545. item2->GetName(), item2->GetID(), pItemReward->GetName(), pItemReward->GetID());
  3546. LogManager::instance().ItemLog(this, item, "USE_DETACHMENT_ONE", buf);
  3547.  
  3548. item->SetCount(item->GetCount() - 1);
  3549. }
  3550. }
  3551. break;
  3552.  
  3553. case 70201: // Ĺ»»öÁ¦
  3554. case 70202: // ż°»öľŕ(Čň»ö)
  3555. case 70203: // ż°»öľŕ(±Ý»ö)
  3556. case 70204: // ż°»öľŕ(»ˇ°Ł»ö)
  3557. case 70205: // ż°»öľŕ(°Ą»ö)
  3558. case 70206: // ż°»öľŕ(°ËŔş»ö)
  3559. {
  3560. // NEW_HAIR_STYLE_ADD
  3561. if (GetPart(PART_HAIR) >= 1001)
  3562. {
  3563. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ÇöŔç Çěľî˝şĹ¸ŔĎżˇĽ­´Â ż°»ö°ú Ĺ»»öŔĚ şŇ°ˇ´ÉÇŐ´Ď´Ů."));
  3564. }
  3565. // END_NEW_HAIR_STYLE_ADD
  3566. else
  3567. {
  3568. quest::CQuestManager& q = quest::CQuestManager::instance();
  3569. quest::PC* pPC = q.GetPC(GetPlayerID());
  3570.  
  3571. if (pPC)
  3572. {
  3573. int last_dye_level = pPC->GetFlag("dyeing_hair.last_dye_level");
  3574.  
  3575. if (last_dye_level == 0 ||
  3576. last_dye_level+3 <= GetLevel() ||
  3577. item->GetVnum() == 70201)
  3578. {
  3579. SetPart(PART_HAIR, item->GetVnum() - 70201);
  3580.  
  3581. if (item->GetVnum() == 70201)
  3582. pPC->SetFlag("dyeing_hair.last_dye_level", 0);
  3583. else
  3584. pPC->SetFlag("dyeing_hair.last_dye_level", GetLevel());
  3585.  
  3586. item->SetCount(item->GetCount() - 1);
  3587. UpdatePacket();
  3588. }
  3589. else
  3590. {
  3591. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%d ·ąş§ŔĚ µÇľîľß ´Ů˝Ă ż°»öÇĎ˝Ç Ľö ŔÖ˝Ŕ´Ď´Ů."), last_dye_level+3);
  3592. }
  3593. }
  3594. }
  3595. }
  3596. break;
  3597.  
  3598. case ITEM_NEW_YEAR_GREETING_VNUM:
  3599. {
  3600. DWORD dwBoxVnum = ITEM_NEW_YEAR_GREETING_VNUM;
  3601. std::vector <DWORD> dwVnums;
  3602. std::vector <DWORD> dwCounts;
  3603. std::vector <LPITEM> item_gets;
  3604. int count = 0;
  3605.  
  3606. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  3607. {
  3608. for (int i = 0; i < count; i++)
  3609. {
  3610. if (dwVnums[i] == CSpecialItemGroup::GOLD)
  3611. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µ· %d łÉŔ» ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  3612. }
  3613.  
  3614. item->SetCount(item->GetCount() - 1);
  3615. }
  3616. }
  3617. break;
  3618.  
  3619. case ITEM_VALENTINE_ROSE:
  3620. case ITEM_VALENTINE_CHOCOLATE:
  3621. {
  3622. DWORD dwBoxVnum = item->GetVnum();
  3623. std::vector <DWORD> dwVnums;
  3624. std::vector <DWORD> dwCounts;
  3625. std::vector <LPITEM> item_gets(NULL);
  3626. int count = 0;
  3627.  
  3628.  
  3629. if (item->GetVnum() == ITEM_VALENTINE_ROSE && SEX_MALE==GET_SEX(this) ||
  3630. item->GetVnum() == ITEM_VALENTINE_CHOCOLATE && SEX_FEMALE==GET_SEX(this))
  3631. {
  3632. // Ľşş°ŔĚ ¸ÂÁöľĘľĆ ľµ Ľö ľř´Ů.
  3633. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľşş°ŔĚ ¸ÂÁöľĘľĆ ŔĚ ľĆŔĚĹŰŔ» ż­ Ľö ľř˝Ŕ´Ď´Ů."));
  3634. return false;
  3635. }
  3636.  
  3637.  
  3638. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  3639. item->SetCount(item->GetCount()-1);
  3640. }
  3641. break;
  3642.  
  3643. case ITEM_WHITEDAY_CANDY:
  3644. case ITEM_WHITEDAY_ROSE:
  3645. {
  3646. DWORD dwBoxVnum = item->GetVnum();
  3647. std::vector <DWORD> dwVnums;
  3648. std::vector <DWORD> dwCounts;
  3649. std::vector <LPITEM> item_gets(NULL);
  3650. int count = 0;
  3651.  
  3652.  
  3653. if (item->GetVnum() == ITEM_WHITEDAY_CANDY && SEX_MALE==GET_SEX(this) ||
  3654. item->GetVnum() == ITEM_WHITEDAY_ROSE && SEX_FEMALE==GET_SEX(this))
  3655. {
  3656. // Ľşş°ŔĚ ¸ÂÁöľĘľĆ ľµ Ľö ľř´Ů.
  3657. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľşş°ŔĚ ¸ÂÁöľĘľĆ ŔĚ ľĆŔĚĹŰŔ» ż­ Ľö ľř˝Ŕ´Ď´Ů."));
  3658. return false;
  3659. }
  3660.  
  3661.  
  3662. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  3663. item->SetCount(item->GetCount()-1);
  3664. }
  3665. break;
  3666.  
  3667. case 50011: // żů±¤ş¸ÇŐ
  3668. {
  3669. DWORD dwBoxVnum = 50011;
  3670. std::vector <DWORD> dwVnums;
  3671. std::vector <DWORD> dwCounts;
  3672. std::vector <LPITEM> item_gets(NULL);
  3673. int count = 0;
  3674.  
  3675. if (GiveItemFromSpecialItemGroup(dwBoxVnum, dwVnums, dwCounts, item_gets, count))
  3676. {
  3677. for (int i = 0; i < count; i++)
  3678. {
  3679. char buf[50 + 1];
  3680. snprintf(buf, sizeof(buf), "%u %u", dwVnums[i], dwCounts[i]);
  3681. LogManager::instance().ItemLog(this, item, "MOONLIGHT_GET", buf);
  3682.  
  3683. //ITEM_MANAGER::instance().RemoveItem(item);
  3684. item->SetCount(item->GetCount() - 1);
  3685.  
  3686. switch (dwVnums[i])
  3687. {
  3688. case CSpecialItemGroup::GOLD:
  3689. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µ· %d łÉŔ» ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  3690. break;
  3691.  
  3692. case CSpecialItemGroup::EXP:
  3693. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ şÎĹÍ ˝ĹşńÇŃ şűŔĚ łŞżÉ´Ď´Ů."));
  3694. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("%dŔÇ °ćÇčġ¸¦ ČąµćÇß˝Ŕ´Ď´Ů."), dwCounts[i]);
  3695. break;
  3696.  
  3697. case CSpecialItemGroup::MOB:
  3698. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  3699. break;
  3700.  
  3701. case CSpecialItemGroup::SLOW:
  3702. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ »ˇ°Ł ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ żňÁ÷ŔĚ´Â ĽÓµµ°ˇ ´Ŕ·ÁÁł˝Ŕ´Ď´Ů!"));
  3703. break;
  3704.  
  3705. case CSpecialItemGroup::DRAIN_HP:
  3706. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚ°ˇ °©ŔÚ±â ĆřąßÇĎż´˝Ŕ´Ď´Ů! »ý¸í·ÂŔĚ °¨ĽŇÇß˝Ŕ´Ď´Ů."));
  3707. break;
  3708.  
  3709. case CSpecialItemGroup::POISON:
  3710. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ łŞżÂ łě»ö ż¬±â¸¦ µéŔ̸¶˝ĂŔÚ µ¶ŔĚ żÂ¸öŔ¸·Î ĆŰÁý´Ď´Ů!"));
  3711. break;
  3712.  
  3713. case CSpecialItemGroup::MOB_GROUP:
  3714. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ ¸ó˝şĹÍ°ˇ łŞĹ¸łµ˝Ŕ´Ď´Ů!"));
  3715. break;
  3716.  
  3717. default:
  3718. if (item_gets[i])
  3719. {
  3720. if (dwCounts[i] > 1)
  3721. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ %d °ł łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName(), dwCounts[i]);
  3722. else
  3723. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»óŔÚżˇĽ­ %s °ˇ łŞżÔ˝Ŕ´Ď´Ů."), item_gets[i]->GetName());
  3724. }
  3725. break;
  3726. }
  3727. }
  3728. }
  3729. else
  3730. {
  3731. ChatPacket(CHAT_TYPE_TALKING, LC_TEXT("ľĆą«°Íµµ ľňŔ» Ľö ľřľú˝Ŕ´Ď´Ů."));
  3732. return false;
  3733. }
  3734. }
  3735. break;
  3736.  
  3737. case ITEM_GIVE_STAT_RESET_COUNT_VNUM:
  3738. {
  3739. //PointChange(POINT_GOLD, -iCost);
  3740. PointChange(POINT_STAT_RESET_COUNT, 1);
  3741. item->SetCount(item->GetCount()-1);
  3742. }
  3743. break;
  3744.  
  3745. case 50107:
  3746. {
  3747. EffectPacket(SE_CHINA_FIREWORK);
  3748. // ˝şĹĎ °ř°ÝŔ» żĂ·ÁÁŘ´Ů
  3749. AddAffect(AFFECT_CHINA_FIREWORK, POINT_STUN_PCT, 30, AFF_CHINA_FIREWORK, 5*60, 0, true);
  3750. item->SetCount(item->GetCount()-1);
  3751. }
  3752. break;
  3753.  
  3754. case 50108:
  3755. {
  3756. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  3757. {
  3758. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  3759. return false;
  3760. }
  3761.  
  3762. EffectPacket(SE_SPIN_TOP);
  3763. // ˝şĹĎ °ř°ÝŔ» żĂ·ÁÁŘ´Ů
  3764. AddAffect(AFFECT_CHINA_FIREWORK, POINT_STUN_PCT, 30, AFF_CHINA_FIREWORK, 5*60, 0, true);
  3765. item->SetCount(item->GetCount()-1);
  3766. }
  3767. break;
  3768.  
  3769. case ITEM_WONSO_BEAN_VNUM:
  3770. PointChange(POINT_HP, GetMaxHP() - GetHP());
  3771. item->SetCount(item->GetCount()-1);
  3772. break;
  3773.  
  3774. case ITEM_WONSO_SUGAR_VNUM:
  3775. PointChange(POINT_SP, GetMaxSP() - GetSP());
  3776. item->SetCount(item->GetCount()-1);
  3777. break;
  3778.  
  3779. case ITEM_WONSO_FRUIT_VNUM:
  3780. PointChange(POINT_STAMINA, GetMaxStamina()-GetStamina());
  3781. item->SetCount(item->GetCount()-1);
  3782. break;
  3783.  
  3784. case 90008: // VCARD
  3785. case 90009: // VCARD
  3786. VCardUse(this, this, item);
  3787. break;
  3788.  
  3789. case ITEM_ELK_VNUM: // µ·˛Ů·ŻąĚ
  3790. {
  3791. int iGold = item->GetSocket(0);
  3792. ITEM_MANAGER::instance().RemoveItem(item);
  3793. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µ· %d łÉŔ» ČąµćÇß˝Ŕ´Ď´Ů."), iGold);
  3794. PointChange(POINT_GOLD, iGold);
  3795. }
  3796. break;
  3797.  
  3798. //±şÁÖŔÇ ÁőÇĄ
  3799. case 70021:
  3800. {
  3801. int HealPrice = quest::CQuestManager::instance().GetEventFlag("MonarchHealGold");
  3802. if (HealPrice == 0)
  3803. HealPrice = 2000000;
  3804.  
  3805. if (CMonarch::instance().HealMyEmpire(this, HealPrice))
  3806. {
  3807. char szNotice[256];
  3808. snprintf(szNotice, sizeof(szNotice), LC_TEXT("±şÁÖŔÇ ĂŕşąŔ¸·Î ŔĚÁöżŞ %s ŔŻŔú´Â HP,SP°ˇ ¸đµÎ äżöÁý´Ď´Ů."), EMPIRE_NAME(GetEmpire()));
  3809. SendNoticeMap(szNotice, GetMapIndex(), false);
  3810.  
  3811. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±şÁÖŔÇ ĂŕşąŔ» »çżëÇĎż´˝Ŕ´Ď´Ů."));
  3812. }
  3813. }
  3814. break;
  3815.  
  3816. case 27995:
  3817. {
  3818. }
  3819. break;
  3820.  
  3821. case 71092 : // şŻ˝Ĺ ÇŘĂĽşÎ ŔÓ˝Ă
  3822. {
  3823. if (m_pkChrTarget != NULL)
  3824. {
  3825. if (m_pkChrTarget->IsPolymorphed())
  3826. {
  3827. m_pkChrTarget->SetPolymorph(0);
  3828. m_pkChrTarget->RemoveAffect(AFFECT_POLYMORPH);
  3829. }
  3830. }
  3831. else
  3832. {
  3833. if (IsPolymorphed())
  3834. {
  3835. SetPolymorph(0);
  3836. RemoveAffect(AFFECT_POLYMORPH);
  3837. }
  3838. }
  3839. }
  3840. break;
  3841.  
  3842. case 71051 : // ÁřŔç°ˇ
  3843. {
  3844. // ŔŻ·´, ˝Ě°ˇĆú, şŁĆ®ł˛ ÁřŔç°ˇ »çżë±ÝÁö
  3845. if (LC_IsEurope() || LC_IsSingapore() || LC_IsVietnam())
  3846. return false;
  3847.  
  3848. LPITEM item2;
  3849.  
  3850. if (!IsValidItemPosition(DestCell) || !(item2 = GetInventoryItem(wDestCell)))
  3851. return false;
  3852.  
  3853. if (item2->IsExchanging() == true)
  3854. return false;
  3855.  
  3856. if (item2->GetAttributeSetIndex() == -1)
  3857. {
  3858. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  3859. return false;
  3860. }
  3861.  
  3862. if (item2->AddRareAttribute() == true)
  3863. {
  3864. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľş°řŔűŔ¸·Î ĽÓĽşŔĚ Ăß°ˇ µÇľú˝Ŕ´Ď´Ů"));
  3865.  
  3866. int iAddedIdx = item2->GetRareAttrCount() + 4;
  3867. char buf[21];
  3868. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  3869.  
  3870. LogManager::instance().ItemLog(
  3871. GetPlayerID(),
  3872. item2->GetAttributeType(iAddedIdx),
  3873. item2->GetAttributeValue(iAddedIdx),
  3874. item->GetID(),
  3875. "ADD_RARE_ATTR",
  3876. buf,
  3877. GetDesc()->GetHostName(),
  3878. item->GetOriginalVnum());
  3879.  
  3880. item->SetCount(item->GetCount() - 1);
  3881. }
  3882. else
  3883. {
  3884. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó ŔĚ ľĆŔĚĹŰŔ¸·Î ĽÓĽşŔ» Ăß°ˇÇŇ Ľö ľř˝Ŕ´Ď´Ů"));
  3885. }
  3886. }
  3887. break;
  3888.  
  3889. case 71052 : // ÁřŔç°ć
  3890. {
  3891. // ŔŻ·´, ˝Ě°ˇĆú, şŁĆ®ł˛ ÁřŔç°ˇ »çżë±ÝÁö
  3892. if (LC_IsEurope() || LC_IsSingapore() || LC_IsVietnam())
  3893. return false;
  3894.  
  3895. LPITEM item2;
  3896.  
  3897. if (!IsValidItemPosition(DestCell) || !(item2 = GetItem(DestCell)))
  3898. return false;
  3899.  
  3900. if (item2->IsExchanging() == true)
  3901. return false;
  3902.  
  3903. if (item2->GetAttributeSetIndex() == -1)
  3904. {
  3905. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  3906. return false;
  3907. }
  3908.  
  3909. if (item2->ChangeRareAttribute() == true)
  3910. {
  3911. char buf[21];
  3912. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  3913. LogManager::instance().ItemLog(this, item, "CHANGE_RARE_ATTR", buf);
  3914.  
  3915. item->SetCount(item->GetCount() - 1);
  3916. }
  3917. else
  3918. {
  3919. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ°ć ˝ĂĹł ĽÓĽşŔĚ ľř˝Ŕ´Ď´Ů"));
  3920. }
  3921. }
  3922. break;
  3923.  
  3924. case ITEM_AUTO_HP_RECOVERY_S:
  3925. case ITEM_AUTO_HP_RECOVERY_M:
  3926. case ITEM_AUTO_HP_RECOVERY_L:
  3927. case ITEM_AUTO_HP_RECOVERY_X:
  3928. case ITEM_AUTO_SP_RECOVERY_S:
  3929. case ITEM_AUTO_SP_RECOVERY_M:
  3930. case ITEM_AUTO_SP_RECOVERY_L:
  3931. case ITEM_AUTO_SP_RECOVERY_X:
  3932. // ą«˝Ăą«˝ĂÇĎÁö¸¸ ŔĚŔüżˇ ÇĎ´ř °É °íġ±â´Â ą«Ľ·°í...
  3933. // ±×·ˇĽ­ ±×łÉ Çϵĺ ÄÚµů. Ľ±ą° »óŔÚżë ŔÚµżą°ľŕ ľĆŔĚĹ۵é.
  3934. case REWARD_BOX_ITEM_AUTO_SP_RECOVERY_XS:
  3935. case REWARD_BOX_ITEM_AUTO_SP_RECOVERY_S:
  3936. case REWARD_BOX_ITEM_AUTO_HP_RECOVERY_XS:
  3937. case REWARD_BOX_ITEM_AUTO_HP_RECOVERY_S:
  3938. case FUCKING_BRAZIL_ITEM_AUTO_SP_RECOVERY_S:
  3939. case FUCKING_BRAZIL_ITEM_AUTO_HP_RECOVERY_S:
  3940. {
  3941. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  3942. {
  3943. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  3944. return false;
  3945. }
  3946.  
  3947. EAffectTypes type = AFFECT_NONE;
  3948. bool isSpecialPotion = false;
  3949.  
  3950. switch (item->GetVnum())
  3951. {
  3952. case ITEM_AUTO_HP_RECOVERY_X:
  3953. isSpecialPotion = true;
  3954.  
  3955. case ITEM_AUTO_HP_RECOVERY_S:
  3956. case ITEM_AUTO_HP_RECOVERY_M:
  3957. case ITEM_AUTO_HP_RECOVERY_L:
  3958. case REWARD_BOX_ITEM_AUTO_HP_RECOVERY_XS:
  3959. case REWARD_BOX_ITEM_AUTO_HP_RECOVERY_S:
  3960. case FUCKING_BRAZIL_ITEM_AUTO_HP_RECOVERY_S:
  3961. type = AFFECT_AUTO_HP_RECOVERY;
  3962. break;
  3963.  
  3964. case ITEM_AUTO_SP_RECOVERY_X:
  3965. isSpecialPotion = true;
  3966.  
  3967. case ITEM_AUTO_SP_RECOVERY_S:
  3968. case ITEM_AUTO_SP_RECOVERY_M:
  3969. case ITEM_AUTO_SP_RECOVERY_L:
  3970. case REWARD_BOX_ITEM_AUTO_SP_RECOVERY_XS:
  3971. case REWARD_BOX_ITEM_AUTO_SP_RECOVERY_S:
  3972. case FUCKING_BRAZIL_ITEM_AUTO_SP_RECOVERY_S:
  3973. type = AFFECT_AUTO_SP_RECOVERY;
  3974. break;
  3975. }
  3976.  
  3977. if (AFFECT_NONE == type)
  3978. break;
  3979.  
  3980. if (item->GetCount() > 1)
  3981. {
  3982. int pos = GetEmptyInventory(item->GetSize());
  3983.  
  3984. if (-1 == pos)
  3985. {
  3986. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇ°żˇ şó °ř°ŁŔĚ ľř˝Ŕ´Ď´Ů."));
  3987. break;
  3988. }
  3989.  
  3990. item->SetCount( item->GetCount() - 1 );
  3991.  
  3992. LPITEM item2 = ITEM_MANAGER::instance().CreateItem( item->GetVnum(), 1 );
  3993. item2->AddToCharacter(this, TItemPos(INVENTORY, pos));
  3994.  
  3995. if (item->GetSocket(1) != 0)
  3996. {
  3997. item2->SetSocket(1, item->GetSocket(1));
  3998. }
  3999.  
  4000. item = item2;
  4001. }
  4002.  
  4003. CAffect* pAffect = FindAffect( type );
  4004.  
  4005. if (NULL == pAffect)
  4006. {
  4007. EPointTypes bonus = POINT_NONE;
  4008.  
  4009. if (true == isSpecialPotion)
  4010. {
  4011. if (type == AFFECT_AUTO_HP_RECOVERY)
  4012. {
  4013. bonus = POINT_MAX_HP_PCT;
  4014. }
  4015. else if (type == AFFECT_AUTO_SP_RECOVERY)
  4016. {
  4017. bonus = POINT_MAX_SP_PCT;
  4018. }
  4019. }
  4020.  
  4021. AddAffect( type, bonus, 4, item->GetID(), INFINITE_AFFECT_DURATION, 0, true, false);
  4022.  
  4023. item->Lock(true);
  4024. item->SetSocket(0, true);
  4025.  
  4026. AutoRecoveryItemProcess( type );
  4027. }
  4028. else
  4029. {
  4030. if (item->GetID() == pAffect->dwFlag)
  4031. {
  4032. RemoveAffect( pAffect );
  4033.  
  4034. item->Lock(false);
  4035. item->SetSocket(0, false);
  4036. }
  4037. else
  4038. {
  4039. LPITEM old = FindItemByID( pAffect->dwFlag );
  4040.  
  4041. if (NULL != old)
  4042. {
  4043. old->Lock(false);
  4044. old->SetSocket(0, false);
  4045. }
  4046.  
  4047. RemoveAffect( pAffect );
  4048.  
  4049. EPointTypes bonus = POINT_NONE;
  4050.  
  4051. if (true == isSpecialPotion)
  4052. {
  4053. if (type == AFFECT_AUTO_HP_RECOVERY)
  4054. {
  4055. bonus = POINT_MAX_HP_PCT;
  4056. }
  4057. else if (type == AFFECT_AUTO_SP_RECOVERY)
  4058. {
  4059. bonus = POINT_MAX_SP_PCT;
  4060. }
  4061. }
  4062.  
  4063. AddAffect( type, bonus, 4, item->GetID(), INFINITE_AFFECT_DURATION, 0, true, false);
  4064.  
  4065. item->Lock(true);
  4066. item->SetSocket(0, true);
  4067.  
  4068. AutoRecoveryItemProcess( type );
  4069. }
  4070. }
  4071. }
  4072. break;
  4073. }
  4074. break;
  4075.  
  4076. case USE_CLEAR:
  4077. {
  4078. RemoveBadAffect();
  4079. item->SetCount(item->GetCount() - 1);
  4080. }
  4081. break;
  4082.  
  4083. case USE_INVISIBILITY:
  4084. {
  4085. if (item->GetVnum() == 70026)
  4086. {
  4087. quest::CQuestManager& q = quest::CQuestManager::instance();
  4088. quest::PC* pPC = q.GetPC(GetPlayerID());
  4089.  
  4090. if (pPC != NULL)
  4091. {
  4092. int last_use_time = pPC->GetFlag("mirror_of_disapper.last_use_time");
  4093.  
  4094. if (get_global_time() - last_use_time < 10*60)
  4095. {
  4096. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆÁ÷ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4097. return false;
  4098. }
  4099.  
  4100. pPC->SetFlag("mirror_of_disapper.last_use_time", get_global_time());
  4101. }
  4102. }
  4103.  
  4104. AddAffect(AFFECT_INVISIBILITY, POINT_NONE, 0, AFF_INVISIBILITY, 300, 0, true);
  4105. item->SetCount(item->GetCount() - 1);
  4106. }
  4107. break;
  4108.  
  4109. case USE_POTION_NODELAY:
  4110. {
  4111. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  4112. {
  4113. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit") > 0)
  4114. {
  4115. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  4116. return false;
  4117. }
  4118.  
  4119. switch (item->GetVnum())
  4120. {
  4121. case 70020 :
  4122. case 71018 :
  4123. case 71019 :
  4124. case 71020 :
  4125. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit_count") < 10000)
  4126. {
  4127. if (m_nPotionLimit <= 0)
  4128. {
  4129. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»çżë Á¦ÇŃ·®Ŕ» ĂĘ°úÇĎż´˝Ŕ´Ď´Ů."));
  4130. return false;
  4131. }
  4132. }
  4133. break;
  4134.  
  4135. default :
  4136. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  4137. return false;
  4138. }
  4139. }
  4140.  
  4141. bool used = false;
  4142.  
  4143. if (item->GetValue(0) != 0) // HP Ŕý´ë°Ş ȸşą
  4144. {
  4145. if (GetHP() < GetMaxHP())
  4146. {
  4147. PointChange(POINT_HP, item->GetValue(0) * (100 + GetPoint(POINT_POTION_BONUS)) / 100);
  4148. EffectPacket(SE_HPUP_RED);
  4149. used = TRUE;
  4150. }
  4151. }
  4152.  
  4153. if (item->GetValue(1) != 0) // SP Ŕý´ë°Ş ȸşą
  4154. {
  4155. if (GetSP() < GetMaxSP())
  4156. {
  4157. PointChange(POINT_SP, item->GetValue(1) * (100 + GetPoint(POINT_POTION_BONUS)) / 100);
  4158. EffectPacket(SE_SPUP_BLUE);
  4159. used = TRUE;
  4160. }
  4161. }
  4162.  
  4163. if (item->GetValue(3) != 0) // HP % ȸşą
  4164. {
  4165. if (GetHP() < GetMaxHP())
  4166. {
  4167. PointChange(POINT_HP, item->GetValue(3) * GetMaxHP() / 100);
  4168. EffectPacket(SE_HPUP_RED);
  4169. used = TRUE;
  4170. }
  4171. }
  4172.  
  4173. if (item->GetValue(4) != 0) // SP % ȸşą
  4174. {
  4175. if (GetSP() < GetMaxSP())
  4176. {
  4177. PointChange(POINT_SP, item->GetValue(4) * GetMaxSP() / 100);
  4178. EffectPacket(SE_SPUP_BLUE);
  4179. used = TRUE;
  4180. }
  4181. }
  4182.  
  4183. if (used)
  4184. {
  4185. if (item->GetVnum() == 50085 || item->GetVnum() == 50086)
  4186. {
  4187. if (test_server)
  4188. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żůş´ ¶Ç´Â ÁľŔÚ ¸¦ »çżëÇĎż´˝Ŕ´Ď´Ů"));
  4189. SetUseSeedOrMoonBottleTime();
  4190. }
  4191. if (GetDungeon())
  4192. GetDungeon()->UsePotion(this);
  4193.  
  4194. if (GetWarMap())
  4195. GetWarMap()->UsePotion(this, item);
  4196.  
  4197. m_nPotionLimit--;
  4198.  
  4199. //RESTRICT_USE_SEED_OR_MOONBOTTLE
  4200. item->SetCount(item->GetCount() - 1);
  4201. //END_RESTRICT_USE_SEED_OR_MOONBOTTLE
  4202. }
  4203. }
  4204. break;
  4205.  
  4206. case USE_POTION:
  4207. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  4208. {
  4209. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit") > 0)
  4210. {
  4211. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  4212. return false;
  4213. }
  4214.  
  4215. switch (item->GetVnum())
  4216. {
  4217. case 27001 :
  4218. case 27002 :
  4219. case 27003 :
  4220. case 27004 :
  4221. case 27005 :
  4222. case 27006 :
  4223. if (quest::CQuestManager::instance().GetEventFlag("arena_potion_limit_count") < 10000)
  4224. {
  4225. if (m_nPotionLimit <= 0)
  4226. {
  4227. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»çżë Á¦ÇŃ·®Ŕ» ĂĘ°úÇĎż´˝Ŕ´Ď´Ů."));
  4228. return false;
  4229. }
  4230. }
  4231. break;
  4232.  
  4233. default :
  4234. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·ĂŔ忡Ľ­ »çżëÇĎ˝Ç Ľö ľř˝Ŕ´Ď´Ů."));
  4235. return false;
  4236. }
  4237. }
  4238.  
  4239. if (item->GetValue(1) != 0)
  4240. {
  4241. if (GetPoint(POINT_SP_RECOVERY) + GetSP() >= GetMaxSP())
  4242. {
  4243. return false;
  4244. }
  4245.  
  4246. PointChange(POINT_SP_RECOVERY, item->GetValue(1) * MIN(200, (100 + GetPoint(POINT_POTION_BONUS))) / 100);
  4247. StartAffectEvent();
  4248. EffectPacket(SE_SPUP_BLUE);
  4249. }
  4250.  
  4251. if (item->GetValue(0) != 0)
  4252. {
  4253. if (GetPoint(POINT_HP_RECOVERY) + GetHP() >= GetMaxHP())
  4254. {
  4255. return false;
  4256. }
  4257.  
  4258. PointChange(POINT_HP_RECOVERY, item->GetValue(0) * MIN(200, (100 + GetPoint(POINT_POTION_BONUS))) / 100);
  4259. StartAffectEvent();
  4260. EffectPacket(SE_HPUP_RED);
  4261. }
  4262.  
  4263. if (GetDungeon())
  4264. GetDungeon()->UsePotion(this);
  4265.  
  4266. if (GetWarMap())
  4267. GetWarMap()->UsePotion(this, item);
  4268.  
  4269. item->SetCount(item->GetCount() - 1);
  4270. m_nPotionLimit--;
  4271. break;
  4272.  
  4273. case USE_POTION_CONTINUE:
  4274. {
  4275. if (item->GetValue(0) != 0)
  4276. {
  4277. AddAffect(AFFECT_HP_RECOVER_CONTINUE, POINT_HP_RECOVER_CONTINUE, item->GetValue(0), 0, item->GetValue(2), 0, true);
  4278. }
  4279. else if (item->GetValue(1) != 0)
  4280. {
  4281. AddAffect(AFFECT_SP_RECOVER_CONTINUE, POINT_SP_RECOVER_CONTINUE, item->GetValue(1), 0, item->GetValue(2), 0, true);
  4282. }
  4283. else
  4284. return false;
  4285. }
  4286.  
  4287. if (GetDungeon())
  4288. GetDungeon()->UsePotion(this);
  4289.  
  4290. if (GetWarMap())
  4291. GetWarMap()->UsePotion(this, item);
  4292.  
  4293. item->SetCount(item->GetCount() - 1);
  4294. break;
  4295.  
  4296. case USE_ABILITY_UP:
  4297. {
  4298. switch (item->GetValue(0))
  4299. {
  4300. case APPLY_MOV_SPEED:
  4301. AddAffect(AFFECT_MOV_SPEED, POINT_MOV_SPEED, item->GetValue(2), AFF_MOV_SPEED_POTION, item->GetValue(1), 0, true);
  4302. EffectPacket(SE_DXUP_PURPLE); // to pod mov_speed (fioletowy efekt)
  4303. break;
  4304.  
  4305. case APPLY_ATT_SPEED:
  4306. AddAffect(AFFECT_ATT_SPEED, POINT_ATT_SPEED, item->GetValue(2), AFF_ATT_SPEED_POTION, item->GetValue(1), 0, true);
  4307. EffectPacket(SE_SPEEDUP_GREEN); // to pod att_speed (zielony efekt)
  4308. break;
  4309.  
  4310. case APPLY_STR:
  4311. AddAffect(AFFECT_STR, POINT_ST, item->GetValue(2), 0, item->GetValue(1), 0, true);
  4312. break;
  4313.  
  4314. case APPLY_DEX:
  4315. AddAffect(AFFECT_DEX, POINT_DX, item->GetValue(2), 0, item->GetValue(1), 0, true);
  4316. break;
  4317.  
  4318. case APPLY_CON:
  4319. AddAffect(AFFECT_CON, POINT_HT, item->GetValue(2), 0, item->GetValue(1), 0, true);
  4320. break;
  4321.  
  4322. case APPLY_INT:
  4323. AddAffect(AFFECT_INT, POINT_IQ, item->GetValue(2), 0, item->GetValue(1), 0, true);
  4324. break;
  4325.  
  4326. case APPLY_CAST_SPEED:
  4327. AddAffect(AFFECT_CAST_SPEED, POINT_CASTING_SPEED, item->GetValue(2), 0, item->GetValue(1), 0, true);
  4328. break;
  4329.  
  4330. case APPLY_ATT_GRADE_BONUS:
  4331. AddAffect(AFFECT_ATT_GRADE, POINT_ATT_GRADE_BONUS,
  4332. item->GetValue(2), 0, item->GetValue(1), 0, true);
  4333. break;
  4334.  
  4335. case APPLY_DEF_GRADE_BONUS:
  4336. AddAffect(AFFECT_DEF_GRADE, POINT_DEF_GRADE_BONUS,
  4337. item->GetValue(2), 0, item->GetValue(1), 0, true);
  4338. break;
  4339. }
  4340. }
  4341.  
  4342. if (GetDungeon())
  4343. GetDungeon()->UsePotion(this);
  4344.  
  4345. if (GetWarMap())
  4346. GetWarMap()->UsePotion(this, item);
  4347.  
  4348. item->SetCount(item->GetCount() - 1);
  4349. break;
  4350.  
  4351. case USE_TALISMAN:
  4352. {
  4353. const int TOWN_PORTAL = 1;
  4354. const int MEMORY_PORTAL = 2;
  4355.  
  4356.  
  4357. // gm_guild_build, oxevent ¸ĘżˇĽ­ ±ÍČŻşÎ ±ÍČŻ±âľďşÎ ¸¦ »çżë¸řÇĎ°Ô ¸·Ŕ˝
  4358. if (GetMapIndex() == 200 || GetMapIndex() == 113)
  4359. {
  4360. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ÇöŔç Ŕ§ÄˇżˇĽ­ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4361. return false;
  4362. }
  4363.  
  4364. if (CArenaManager::instance().IsArenaMap(GetMapIndex()) == true)
  4365. {
  4366. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ë·Ă Áßżˇ´Â ŔĚżëÇŇ Ľö ľř´Â ą°Ç°ŔÔ´Ď´Ů."));
  4367. return false;
  4368. }
  4369.  
  4370. if (m_pkWarpEvent)
  4371. {
  4372. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕ̵żÇŇ ÁŘşń°ˇ µÇľîŔÖŔ˝Ŕ¸·Î ±ÍČŻşÎ¸¦ »çżëÇŇĽö ľř˝Ŕ´Ď´Ů"));
  4373. return false;
  4374. }
  4375.  
  4376. // CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4377. int consumeLife = CalculateConsume(this);
  4378.  
  4379. if (consumeLife < 0)
  4380. return false;
  4381. // END_OF_CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4382.  
  4383. if (item->GetValue(0) == TOWN_PORTAL) // ±ÍČŻşÎ
  4384. {
  4385. if (item->GetSocket(0) == 0)
  4386. {
  4387. if (!GetDungeon())
  4388. if (!GiveRecallItem(item))
  4389. return false;
  4390.  
  4391. PIXEL_POSITION posWarp;
  4392.  
  4393. if (SECTREE_MANAGER::instance().GetRecallPositionByEmpire(GetMapIndex(), GetEmpire(), posWarp))
  4394. {
  4395. // CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4396. PointChange(POINT_HP, -consumeLife, false);
  4397. // END_OF_CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4398.  
  4399. WarpSet(posWarp.x, posWarp.y);
  4400. }
  4401. else
  4402. {
  4403. sys_err("CHARACTER::UseItem : cannot find spawn position (name %s, %d x %d)", GetName(), GetX(), GetY());
  4404. }
  4405. }
  4406. else
  4407. {
  4408. if (test_server)
  4409. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żř·ˇ Ŕ§Äˇ·Î şą±Í"));
  4410.  
  4411. ProcessRecallItem(item);
  4412. }
  4413. }
  4414. else if (item->GetValue(0) == MEMORY_PORTAL) // ±ÍČŻ±âľďşÎ
  4415. {
  4416. if (item->GetSocket(0) == 0)
  4417. {
  4418. if (GetDungeon())
  4419. {
  4420. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´řŔü ľČżˇĽ­´Â %s%s »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."),
  4421. item->GetName(),
  4422. g_iUseLocale ? "" : (under_han(item->GetName()) ? LC_TEXT("Ŕ»") : LC_TEXT("¸¦")));
  4423. return false;
  4424. }
  4425.  
  4426. if (!GiveRecallItem(item))
  4427. return false;
  4428. }
  4429. else
  4430. {
  4431. // CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4432. PointChange(POINT_HP, -consumeLife, false);
  4433. // END_OF_CONSUME_LIFE_WHEN_USE_WARP_ITEM
  4434.  
  4435. ProcessRecallItem(item);
  4436. }
  4437. }
  4438. }
  4439. break;
  4440.  
  4441. case USE_TUNING:
  4442. case USE_DETACHMENT:
  4443. {
  4444. LPITEM item2;
  4445.  
  4446. if (!IsValidItemPosition(DestCell) || !(item2 = GetItem(DestCell)))
  4447. return false;
  4448.  
  4449. if (item2->IsExchanging())
  4450. return false;
  4451.  
  4452. if (item2->IsEquipped())
  4453. return false;
  4454.  
  4455. if (item2->GetVnum() >= 28330 && item2->GetVnum() <= 28343) // żµĽ®+3
  4456. {
  4457. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("+3 żµĽ®Ŕş ŔĚ ľĆŔĚĹŰŔ¸·Î °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů"));
  4458. return false;
  4459. }
  4460.  
  4461. if (item2->GetVnum() >= 28430 && item2->GetVnum() <= 28443) // żµĽ®+4
  4462. {
  4463. if (item->GetVnum() == 71056) // Ă»·ćŔÇĽű°á
  4464. {
  4465. RefineItem(item, item2);
  4466. }
  4467. else
  4468. {
  4469. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żµĽ®Ŕş ŔĚ ľĆŔĚĹŰŔ¸·Î °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů"));
  4470. }
  4471. }
  4472. else
  4473. {
  4474. RefineItem(item, item2);
  4475. }
  4476. }
  4477. break;
  4478.  
  4479. // ACCESSORY_REFINE & ADD/CHANGE_ATTRIBUTES
  4480. case USE_PUT_INTO_BELT_SOCKET:
  4481. case USE_PUT_INTO_RING_SOCKET:
  4482. case USE_PUT_INTO_ACCESSORY_SOCKET:
  4483. case USE_ADD_ACCESSORY_SOCKET:
  4484. case USE_CLEAN_SOCKET:
  4485. case USE_CHANGE_ATTRIBUTE:
  4486. case USE_CHANGE_ATTRIBUTE2 :
  4487. case USE_ADD_ATTRIBUTE:
  4488. case USE_ADD_ATTRIBUTE2:
  4489. {
  4490. LPITEM item2;
  4491. if (!IsValidItemPosition(DestCell) || !(item2 = GetItem(DestCell)))
  4492. return false;
  4493.  
  4494. if (item2->IsEquipped())
  4495. {
  4496. BuffOnAttr_RemoveBuffsFromItem(item2);
  4497. }
  4498.  
  4499. // [NOTE] ÄÚ˝şĆ¬ ľĆŔĚĹŰżˇ´Â ľĆŔĚĹŰ ĂÖĂĘ »ýĽş˝Ă ·Ł´ý ĽÓĽşŔ» şÎż©ÇϵÇ, Ŕç°ćŔç°ˇ µîµîŔş ¸·ľĆ´Ţ¶ó´Â żäĂ»ŔĚ ŔÖľúŔ˝.
  4500. // żř·ˇ ANTI_CHANGE_ATTRIBUTE °°Ŕş ľĆŔĚĹŰ Flag¸¦ Ăß°ˇÇĎż© ±âČą ·ąş§żˇĽ­ ŔŻż¬ÇĎ°Ô ÄÁĆ®·Ń ÇŇ Ľö ŔÖµµ·Ď ÇŇ żąÁ¤ŔĚľúŔ¸łŞ
  4501. // ±×µý°Ĺ ÇĘżäľřŔ¸´Ď ´Úġ°í »ˇ¸® ÇŘ´Ţ·ˇĽ­ ±×łÉ ż©±âĽ­ ¸·Ŕ˝... -_-
  4502. if (ITEM_COSTUME == item2->GetType())
  4503. {
  4504. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  4505. return false;
  4506. }
  4507.  
  4508. if (item2->IsExchanging())
  4509. return false;
  4510.  
  4511. if (item2->IsEquipped())
  4512. return false;
  4513.  
  4514. switch (item->GetSubType())
  4515. {
  4516. case USE_CLEAN_SOCKET:
  4517. {
  4518. int i;
  4519. for (i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  4520. {
  4521. if (item2->GetSocket(i) == ITEM_BROKEN_METIN_VNUM)
  4522. break;
  4523. }
  4524.  
  4525. if (i == ITEM_SOCKET_MAX_NUM)
  4526. {
  4527. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ă»ĽŇÇŇ Ľ®ŔĚ ąÚÇôŔÖÁö ľĘ˝Ŕ´Ď´Ů."));
  4528. return false;
  4529. }
  4530.  
  4531. int j = 0;
  4532.  
  4533. for (i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  4534. {
  4535. if (item2->GetSocket(i) != ITEM_BROKEN_METIN_VNUM && item2->GetSocket(i) != 0)
  4536. item2->SetSocket(j++, item2->GetSocket(i));
  4537. }
  4538.  
  4539. for (; j < ITEM_SOCKET_MAX_NUM; ++j)
  4540. {
  4541. if (item2->GetSocket(j) > 0)
  4542. item2->SetSocket(j, 1);
  4543. }
  4544.  
  4545. {
  4546. char buf[21];
  4547. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4548. LogManager::instance().ItemLog(this, item, "CLEAN_SOCKET", buf);
  4549. }
  4550.  
  4551. item->SetCount(item->GetCount() - 1);
  4552.  
  4553. }
  4554. break;
  4555.  
  4556. case USE_CHANGE_ATTRIBUTE :
  4557. if (item2->GetAttributeSetIndex() == -1)
  4558. {
  4559. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  4560. return false;
  4561. }
  4562.  
  4563. if (item2->GetAttributeCount() == 0)
  4564. {
  4565. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şŻ°ćÇŇ ĽÓĽşŔĚ ľř˝Ŕ´Ď´Ů."));
  4566. return false;
  4567. }
  4568.  
  4569. if (GM_PLAYER == GetGMLevel() && false == test_server)
  4570. {
  4571. //
  4572. // Event Flag ¸¦ ĹëÇŘ ŔĚŔüżˇ ľĆŔĚĹŰ ĽÓĽş şŻ°ćŔ» ÇŃ ˝Ă°ŁŔ¸·Î şÎĹÍ ĂćşĐÇŃ ˝Ă°ŁŔĚ Čę·¶´ÂÁö °Ë»çÇĎ°í
  4573. // ˝Ă°ŁŔĚ ĂćşĐČ÷ Čę·¶´Ů¸é ÇöŔç ĽÓĽşşŻ°ćżˇ ´ëÇŃ ˝Ă°ŁŔ» ĽłÁ¤ÇŘ ÁŘ´Ů.
  4574. //
  4575.  
  4576. DWORD dwChangeItemAttrCycle = quest::CQuestManager::instance().GetEventFlag(msc_szChangeItemAttrCycleFlag);
  4577. if (dwChangeItemAttrCycle < msc_dwDefaultChangeItemAttrCycle)
  4578. dwChangeItemAttrCycle = msc_dwDefaultChangeItemAttrCycle;
  4579.  
  4580. quest::PC* pPC = quest::CQuestManager::instance().GetPC(GetPlayerID());
  4581.  
  4582. if (pPC)
  4583. {
  4584. DWORD dwNowMin = get_global_time() / 60;
  4585.  
  4586. DWORD dwLastChangeItemAttrMin = pPC->GetFlag(msc_szLastChangeItemAttrFlag);
  4587.  
  4588. if (dwLastChangeItemAttrMin + dwChangeItemAttrCycle > dwNowMin)
  4589. {
  4590. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» ąŮ˛ŰÁö %dşĐ ŔĚł»żˇ´Â ´Ů˝Ă şŻ°ćÇŇ Ľö ľř˝Ŕ´Ď´Ů.(%d şĐ ł˛Ŕ˝)"),
  4591. dwChangeItemAttrCycle, dwChangeItemAttrCycle - (dwNowMin - dwLastChangeItemAttrMin));
  4592. return false;
  4593. }
  4594.  
  4595. pPC->SetFlag(msc_szLastChangeItemAttrFlag, dwNowMin);
  4596. }
  4597. }
  4598.  
  4599. if (item->GetSubType() == USE_CHANGE_ATTRIBUTE2)
  4600. {
  4601. int aiChangeProb[ITEM_ATTRIBUTE_MAX_LEVEL] =
  4602. {
  4603. 0, 0, 30, 40, 3
  4604. };
  4605.  
  4606. item2->ChangeAttribute(aiChangeProb);
  4607. }
  4608. else if (item->GetVnum() == 76014)
  4609. {
  4610. int aiChangeProb[ITEM_ATTRIBUTE_MAX_LEVEL] =
  4611. {
  4612. 0, 10, 50, 39, 1
  4613. };
  4614.  
  4615. item2->ChangeAttribute(aiChangeProb);
  4616. }
  4617.  
  4618. else
  4619. {
  4620. // ż¬Ŕç°ć ĆŻĽöĂł¸®
  4621. // Ŕý´ë·Î ż¬Ŕç°ˇ Ăß°ˇ ľČµÉ°Ĺ¶ó ÇĎż© Çϵĺ ÄÚµůÇÔ.
  4622. if (item->GetVnum() == 71151 || item->GetVnum() == 76023)
  4623. {
  4624. if ((item2->GetType() == ITEM_WEAPON)
  4625. || (item2->GetType() == ITEM_ARMOR && item2->GetSubType() == ARMOR_BODY))
  4626. {
  4627. bool bCanUse = true;
  4628. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  4629. {
  4630. if (item2->GetLimitType(i) == LIMIT_LEVEL && item2->GetLimitValue(i) > 40)
  4631. {
  4632. bCanUse = false;
  4633. break;
  4634. }
  4635. }
  4636. if (false == bCanUse)
  4637. {
  4638. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕűżë ·ąş§ş¸´Ů łôľĆ »çżëŔĚ şŇ°ˇ´ÉÇŐ´Ď´Ů."));
  4639. break;
  4640. }
  4641. }
  4642. else
  4643. {
  4644. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą«±âżÍ °©żĘżˇ¸¸ »çżë °ˇ´ÉÇŐ´Ď´Ů."));
  4645. break;
  4646. }
  4647. }
  4648. item2->ChangeAttribute();
  4649. }
  4650.  
  4651. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇĎż´˝Ŕ´Ď´Ů."));
  4652. {
  4653. char buf[21];
  4654. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4655. LogManager::instance().ItemLog(this, item, "CHANGE_ATTRIBUTE", buf);
  4656. }
  4657.  
  4658. item->SetCount(item->GetCount() - 1);
  4659. break;
  4660.  
  4661. case USE_ADD_ATTRIBUTE :
  4662. if (item2->GetAttributeSetIndex() == -1)
  4663. {
  4664. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  4665. return false;
  4666. }
  4667.  
  4668. if (item2->GetAttributeCount() < 5)
  4669. {
  4670. // ż¬Ŕç°ˇ ĆŻĽöĂł¸®
  4671. // Ŕý´ë·Î ż¬Ŕç°ˇ Ăß°ˇ ľČµÉ°Ĺ¶ó ÇĎż© Çϵĺ ÄÚµůÇÔ.
  4672. if (item->GetVnum() == 71152 || item->GetVnum() == 76024)
  4673. {
  4674. if ((item2->GetType() == ITEM_WEAPON)
  4675. || (item2->GetType() == ITEM_ARMOR && item2->GetSubType() == ARMOR_BODY))
  4676. {
  4677. bool bCanUse = true;
  4678. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  4679. {
  4680. if (item2->GetLimitType(i) == LIMIT_LEVEL && item2->GetLimitValue(i) > 40)
  4681. {
  4682. bCanUse = false;
  4683. break;
  4684. }
  4685. }
  4686. if (false == bCanUse)
  4687. {
  4688. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕűżë ·ąş§ş¸´Ů łôľĆ »çżëŔĚ şŇ°ˇ´ÉÇŐ´Ď´Ů."));
  4689. break;
  4690. }
  4691. }
  4692. else
  4693. {
  4694. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą«±âżÍ °©żĘżˇ¸¸ »çżë °ˇ´ÉÇŐ´Ď´Ů."));
  4695. break;
  4696. }
  4697. }
  4698. char buf[21];
  4699. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4700.  
  4701. if (number(1, 100) <= aiItemAttributeAddPercent[item2->GetAttributeCount()])
  4702. {
  4703. item2->AddAttribute();
  4704. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽş Ăß°ˇżˇ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  4705.  
  4706. int iAddedIdx = item2->GetAttributeCount() - 1;
  4707. LogManager::instance().ItemLog(
  4708. GetPlayerID(),
  4709. item2->GetAttributeType(iAddedIdx),
  4710. item2->GetAttributeValue(iAddedIdx),
  4711. item->GetID(),
  4712. "ADD_ATTRIBUTE_SUCCESS",
  4713. buf,
  4714. GetDesc()->GetHostName(),
  4715. item->GetOriginalVnum());
  4716. }
  4717. else
  4718. {
  4719. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽş Ăß°ˇżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  4720. LogManager::instance().ItemLog(this, item, "ADD_ATTRIBUTE_FAIL", buf);
  4721. }
  4722.  
  4723. item->SetCount(item->GetCount() - 1);
  4724. }
  4725. else
  4726. {
  4727. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´őŔĚ»ó ŔĚ ľĆŔĚĹŰŔ» ŔĚżëÇĎż© ĽÓĽşŔ» Ăß°ˇÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4728. }
  4729. break;
  4730.  
  4731. case USE_ADD_ATTRIBUTE2 :
  4732. // ĂŕşąŔÇ ±¸˝˝
  4733. // Ŕç°ˇşńĽ­¸¦ ĹëÇŘ ĽÓĽşŔ» 4°ł Ăß°ˇ ˝ĂŲ ľĆŔĚĹŰżˇ ´ëÇŘĽ­ ÇĎłŞŔÇ ĽÓĽşŔ» ´ő şŮż©ÁŘ´Ů.
  4734. if (item2->GetAttributeSetIndex() == -1)
  4735. {
  4736. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽşŔ» şŻ°ćÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  4737. return false;
  4738. }
  4739.  
  4740. // ĽÓĽşŔĚ ŔĚąĚ 4°ł Ăß°ˇ µÇľúŔ» ¶§¸¸ ĽÓĽşŔ» Ăß°ˇ °ˇ´ÉÇĎ´Ů.
  4741. if (item2->GetAttributeCount() == 4)
  4742. {
  4743. char buf[21];
  4744. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4745.  
  4746. if (number(1, 100) <= aiItemAttributeAddPercent[item2->GetAttributeCount()])
  4747. {
  4748. item2->AddAttribute();
  4749. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽş Ăß°ˇżˇ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  4750.  
  4751. int iAddedIdx = item2->GetAttributeCount() - 1;
  4752. LogManager::instance().ItemLog(
  4753. GetPlayerID(),
  4754. item2->GetAttributeType(iAddedIdx),
  4755. item2->GetAttributeValue(iAddedIdx),
  4756. item->GetID(),
  4757. "ADD_ATTRIBUTE2_SUCCESS",
  4758. buf,
  4759. GetDesc()->GetHostName(),
  4760. item->GetOriginalVnum());
  4761. }
  4762. else
  4763. {
  4764. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽÓĽş Ăß°ˇżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  4765. LogManager::instance().ItemLog(this, item, "ADD_ATTRIBUTE2_FAIL", buf);
  4766. }
  4767.  
  4768. item->SetCount(item->GetCount() - 1);
  4769. }
  4770. else if (item2->GetAttributeCount() == 5)
  4771. {
  4772. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ő ŔĚ»ó ŔĚ ľĆŔĚĹŰŔ» ŔĚżëÇĎż© ĽÓĽşŔ» Ăß°ˇÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4773. }
  4774. else if (item2->GetAttributeCount() < 4)
  4775. {
  4776. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸ŐŔú Ŕç°ˇşńĽ­¸¦ ŔĚżëÇĎż© ĽÓĽşŔ» Ăß°ˇ˝ĂÄŃ ÁÖĽĽżä."));
  4777. }
  4778. else
  4779. {
  4780. // wtf ?!
  4781. sys_err("ADD_ATTRIBUTE2 : Item has wrong AttributeCount(%d)", item2->GetAttributeCount());
  4782. }
  4783. break;
  4784.  
  4785. case USE_ADD_ACCESSORY_SOCKET:
  4786. {
  4787. char buf[21];
  4788. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4789.  
  4790. if (item2->IsAccessoryForSocket())
  4791. {
  4792. if (item2->GetAccessorySocketMaxGrade() < ITEM_ACCESSORY_SOCKET_MAX_NUM)
  4793. {
  4794. if (number(1, 100) <= 50)
  4795. {
  4796. item2->SetAccessorySocketMaxGrade(item2->GetAccessorySocketMaxGrade() + 1);
  4797. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÄĎŔĚ Ľş°řŔűŔ¸·Î Ăß°ˇµÇľú˝Ŕ´Ď´Ů."));
  4798. LogManager::instance().ItemLog(this, item, "ADD_SOCKET_SUCCESS", buf);
  4799. }
  4800. else
  4801. {
  4802. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÄĎ Ăß°ˇżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  4803. LogManager::instance().ItemLog(this, item, "ADD_SOCKET_FAIL", buf);
  4804. }
  4805.  
  4806. item->SetCount(item->GetCount() - 1);
  4807. }
  4808. else
  4809. {
  4810. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľ×ĽĽĽ­¸®żˇ´Â ´őŔĚ»ó ĽŇÄĎŔ» Ăß°ˇÇŇ °ř°ŁŔĚ ľř˝Ŕ´Ď´Ů."));
  4811. }
  4812. }
  4813. else
  4814. {
  4815. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔ¸·Î ĽŇÄĎŔ» Ăß°ˇÇŇ Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  4816. }
  4817. }
  4818. break;
  4819.  
  4820. case USE_PUT_INTO_BELT_SOCKET:
  4821. case USE_PUT_INTO_ACCESSORY_SOCKET:
  4822. if (item2->IsAccessoryForSocket() && item->CanPutInto(item2))
  4823. {
  4824. char buf[21];
  4825. snprintf(buf, sizeof(buf), "%u", item2->GetID());
  4826.  
  4827. if (item2->GetAccessorySocketGrade() < item2->GetAccessorySocketMaxGrade())
  4828. {
  4829. if (number(1, 100) <= aiAccessorySocketPutPct[item2->GetAccessorySocketGrade()])
  4830. {
  4831. item2->SetAccessorySocketGrade(item2->GetAccessorySocketGrade() + 1);
  4832. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĺÂřżˇ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  4833. LogManager::instance().ItemLog(this, item, "PUT_SOCKET_SUCCESS", buf);
  4834. }
  4835. else
  4836. {
  4837. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĺÂřżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  4838. LogManager::instance().ItemLog(this, item, "PUT_SOCKET_FAIL", buf);
  4839. }
  4840.  
  4841. item->SetCount(item->GetCount() - 1);
  4842. }
  4843. else
  4844. {
  4845. if (item2->GetAccessorySocketMaxGrade() == 0)
  4846. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸ŐŔú ´ŮŔ̾Ƹóµĺ·Î ľÇĽĽĽ­¸®żˇ ĽŇÄĎŔ» Ăß°ˇÇŘľßÇŐ´Ď´Ů."));
  4847. else if (item2->GetAccessorySocketMaxGrade() < ITEM_ACCESSORY_SOCKET_MAX_NUM)
  4848. {
  4849. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľ×ĽĽĽ­¸®żˇ´Â ´őŔĚ»ó ŔĺÂřÇŇ ĽŇÄĎŔĚ ľř˝Ŕ´Ď´Ů."));
  4850. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´ŮŔ̾Ƹóµĺ·Î ĽŇÄĎŔ» Ăß°ˇÇŘľßÇŐ´Ď´Ů."));
  4851. }
  4852. else
  4853. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľ×ĽĽĽ­¸®żˇ´Â ´őŔĚ»ó ş¸Ľ®Ŕ» ŔĺÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4854. }
  4855. }
  4856. else
  4857. {
  4858. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔ» ŔĺÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  4859. }
  4860. break;
  4861. }
  4862. if (item2->IsEquipped())
  4863. {
  4864. BuffOnAttr_AddBuffsFromItem(item2);
  4865. }
  4866. }
  4867. break;
  4868. // END_OF_ACCESSORY_REFINE & END_OF_ADD_ATTRIBUTES & END_OF_CHANGE_ATTRIBUTES
  4869.  
  4870. case USE_BAIT:
  4871. {
  4872.  
  4873. if (m_pkFishingEvent)
  4874. {
  4875. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ł¬˝Ă Áßżˇ ąĚł˘¸¦ °ĄľĆł˘żď Ľö ľř˝Ŕ´Ď´Ů."));
  4876. return false;
  4877. }
  4878.  
  4879. LPITEM weapon = GetWear(WEAR_WEAPON);
  4880.  
  4881. if (!weapon || weapon->GetType() != ITEM_ROD)
  4882. return false;
  4883.  
  4884. if (weapon->GetSocket(2))
  4885. {
  4886. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ ˛ČÇôŔÖ´ř ąĚł˘¸¦ »©°í %s¸¦ ł˘żó´Ď´Ů."), item->GetName());
  4887. }
  4888. else
  4889. {
  4890. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ł¬˝Ă´ëżˇ %s¸¦ ąĚł˘·Î ł˘żó´Ď´Ů."), item->GetName());
  4891. }
  4892.  
  4893. weapon->SetSocket(2, item->GetValue(0));
  4894. item->SetCount(item->GetCount() - 1);
  4895. }
  4896. break;
  4897.  
  4898. case USE_MOVE:
  4899. case USE_TREASURE_BOX:
  4900. case USE_MONEYBAG:
  4901. break;
  4902.  
  4903. case USE_AFFECT :
  4904. {
  4905. if (FindAffect(item->GetValue(0), aApplyInfo[item->GetValue(1)].bPointType))
  4906. {
  4907. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  4908. }
  4909. else
  4910. {
  4911. // PC_BANG_ITEM_ADD
  4912. if (item->IsPCBangItem() == true)
  4913. {
  4914. // PCąćŔÎÁö ĂĽĹ©ÇŘĽ­ Ăł¸®
  4915. if (CPCBangManager::instance().IsPCBangIP(GetDesc()->GetHostName()) == false)
  4916. {
  4917. // PCąćŔĚ ľĆ´Ô!
  4918. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş PCąćżˇĽ­¸¸ »çżëÇŇ Ľö ŔÖ˝Ŕ´Ď´Ů."));
  4919. return false;
  4920. }
  4921. }
  4922. // END_PC_BANG_ITEM_ADD
  4923.  
  4924. AddAffect(item->GetValue(0), aApplyInfo[item->GetValue(1)].bPointType, item->GetValue(2), 0, item->GetValue(3), 0, false);
  4925. item->SetCount(item->GetCount() - 1);
  4926. }
  4927. }
  4928. break;
  4929.  
  4930. case USE_CREATE_STONE:
  4931. AutoGiveItem(number(28000, 28013));
  4932. item->SetCount(item->GetCount() - 1);
  4933. break;
  4934.  
  4935. // ą°ľŕ Á¦Á¶ ˝şĹłżë ·ą˝ĂÇÇ Ăł¸®
  4936. case USE_RECIPE :
  4937. {
  4938. LPITEM pSource1 = FindSpecifyItem(item->GetValue(1));
  4939. DWORD dwSourceCount1 = item->GetValue(2);
  4940.  
  4941. LPITEM pSource2 = FindSpecifyItem(item->GetValue(3));
  4942. DWORD dwSourceCount2 = item->GetValue(4);
  4943.  
  4944. if (dwSourceCount1 != 0)
  4945. {
  4946. if (pSource1 == NULL)
  4947. {
  4948. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą°ľŕ Á¶ÇŐŔ» Ŕ§ÇŃ Ŕç·á°ˇ şÎÁ·ÇŐ´Ď´Ů."));
  4949. return false;
  4950. }
  4951. }
  4952.  
  4953. if (dwSourceCount2 != 0)
  4954. {
  4955. if (pSource2 == NULL)
  4956. {
  4957. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą°ľŕ Á¶ÇŐŔ» Ŕ§ÇŃ Ŕç·á°ˇ şÎÁ·ÇŐ´Ď´Ů."));
  4958. return false;
  4959. }
  4960. }
  4961.  
  4962. if (pSource1 != NULL)
  4963. {
  4964. if (pSource1->GetCount() < dwSourceCount1)
  4965. {
  4966. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕç·á(%s)°ˇ şÎÁ·ÇŐ´Ď´Ů."), pSource1->GetName());
  4967. return false;
  4968. }
  4969.  
  4970. pSource1->SetCount(pSource1->GetCount() - dwSourceCount1);
  4971. }
  4972.  
  4973. if (pSource2 != NULL)
  4974. {
  4975. if (pSource2->GetCount() < dwSourceCount2)
  4976. {
  4977. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕç·á(%s)°ˇ şÎÁ·ÇŐ´Ď´Ů."), pSource2->GetName());
  4978. return false;
  4979. }
  4980.  
  4981. pSource2->SetCount(pSource2->GetCount() - dwSourceCount2);
  4982. }
  4983.  
  4984. LPITEM pBottle = FindSpecifyItem(50901);
  4985.  
  4986. if (!pBottle || pBottle->GetCount() < 1)
  4987. {
  4988. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şó ş´ŔĚ ¸đŔÚ¸¨´Ď´Ů."));
  4989. return false;
  4990. }
  4991.  
  4992. pBottle->SetCount(pBottle->GetCount() - 1);
  4993.  
  4994. if (number(1, 100) > item->GetValue(5))
  4995. {
  4996. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ą°ľŕ Á¦Á¶żˇ ˝ÇĆĐÇß˝Ŕ´Ď´Ů."));
  4997. return false;
  4998. }
  4999.  
  5000. AutoGiveItem(item->GetValue(0));
  5001. }
  5002. break;
  5003. }
  5004. }
  5005. break;
  5006.  
  5007. case ITEM_METIN:
  5008. {
  5009. LPITEM item2;
  5010.  
  5011. if (!IsValidItemPosition(DestCell) || !(item2 = GetItem(DestCell)))
  5012. return false;
  5013.  
  5014. if (item2->IsExchanging())
  5015. return false;
  5016.  
  5017. if (item2->GetVnum() >= 8000 && item2->GetVnum() <= 8009)
  5018. return false;
  5019.  
  5020. if (item2->GetType() == ITEM_PICK) return false;
  5021. if (item2->GetType() == ITEM_ROD) return false;
  5022.  
  5023. int i;
  5024.  
  5025. for (i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  5026. {
  5027. DWORD dwVnum;
  5028.  
  5029. if ((dwVnum = item2->GetSocket(i)) <= 2)
  5030. continue;
  5031.  
  5032. TItemTable * p = ITEM_MANAGER::instance().GetTable(dwVnum);
  5033.  
  5034. if (!p)
  5035. continue;
  5036.  
  5037. if (item->GetValue(5) == p->alValues[5])
  5038. {
  5039. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°°Ŕş Áľ·ůŔÇ ¸ŢĆľĽ®Ŕş ż©·Ż°ł şÎÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  5040. return false;
  5041. }
  5042. }
  5043.  
  5044. if (item2->GetType() == ITEM_ARMOR)
  5045. {
  5046. if (!IS_SET(item->GetWearFlag(), WEARABLE_BODY) || !IS_SET(item2->GetWearFlag(), WEARABLE_BODY))
  5047. {
  5048. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ¸ŢĆľĽ®Ŕş Ŕĺşńżˇ şÎÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  5049. return false;
  5050. }
  5051. }
  5052. else if (item2->GetType() == ITEM_WEAPON)
  5053. {
  5054. if (!IS_SET(item->GetWearFlag(), WEARABLE_WEAPON))
  5055. {
  5056. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ¸ŢĆľĽ®Ŕş ą«±âżˇ şÎÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  5057. return false;
  5058. }
  5059. }
  5060. else
  5061. {
  5062. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şÎÂřÇŇ Ľö ŔÖ´Â ˝˝·ÔŔĚ ľř˝Ŕ´Ď´Ů."));
  5063. return false;
  5064. }
  5065.  
  5066. for (i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  5067. if (item2->GetSocket(i) >= 1 && item2->GetSocket(i) <= 2 && item2->GetSocket(i) >= item->GetValue(2))
  5068. {
  5069. // Ľ® Č®·ü
  5070. if (number(1, 100) <= 30)
  5071. {
  5072. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸ŢĆľĽ® şÎÂřżˇ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  5073. item2->SetSocket(i, item->GetVnum());
  5074. }
  5075. else
  5076. {
  5077. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸ŢĆľĽ® şÎÂřżˇ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  5078. item2->SetSocket(i, ITEM_BROKEN_METIN_VNUM);
  5079. }
  5080.  
  5081. LogManager::instance().ItemLog(this, item2, "SOCKET", item->GetName());
  5082. ITEM_MANAGER::instance().RemoveItem(item, "REMOVE (METIN)");
  5083. break;
  5084. }
  5085.  
  5086. if (i == ITEM_SOCKET_MAX_NUM)
  5087. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("şÎÂřÇŇ Ľö ŔÖ´Â ˝˝·ÔŔĚ ľř˝Ŕ´Ď´Ů."));
  5088. }
  5089. break;
  5090.  
  5091. case ITEM_AUTOUSE:
  5092. case ITEM_MATERIAL:
  5093. case ITEM_SPECIAL:
  5094. case ITEM_TOOL:
  5095. case ITEM_LOTTERY:
  5096. break;
  5097.  
  5098. case ITEM_TOTEM:
  5099. {
  5100. if (!item->IsEquipped())
  5101. EquipItem(item);
  5102. }
  5103. break;
  5104.  
  5105. case ITEM_BLEND:
  5106. // »ő·Îżî ľŕĂʵé
  5107. sys_log(0,"ITEM_BLEND!!");
  5108. if (Blend_Item_find(item->GetVnum()))
  5109. {
  5110. int affect_type = AFFECT_BLEND;
  5111. if (item->GetSocket(0) >= _countof(aApplyInfo))
  5112. {
  5113. sys_err ("INVALID BLEND ITEM(id : %d, vnum : %d). APPLY TYPE IS %d.", item->GetID(), item->GetVnum(), item->GetSocket(0));
  5114. return false;
  5115. }
  5116. int apply_type = aApplyInfo[item->GetSocket(0)].bPointType;
  5117. int apply_value = item->GetSocket(1);
  5118. int apply_duration = item->GetSocket(2);
  5119.  
  5120. if (FindAffect(affect_type, apply_type))
  5121. {
  5122. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  5123. }
  5124. else
  5125. {
  5126. if (FindAffect(AFFECT_EXP_BONUS_EURO_FREE, POINT_RESIST_MAGIC))
  5127. {
  5128. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Čż°ú°ˇ °É·Á ŔÖ˝Ŕ´Ď´Ů."));
  5129. }
  5130. else
  5131. {
  5132. AddAffect(affect_type, apply_type, apply_value, 0, apply_duration, 0, false);
  5133. item->SetCount(item->GetCount() - 1);
  5134. }
  5135. }
  5136. }
  5137. break;
  5138.  
  5139. case ITEM_EXTRACT:
  5140. {
  5141. LPITEM pDestItem = GetItem(DestCell);
  5142. if (NULL == pDestItem)
  5143. {
  5144. return false;
  5145. }
  5146. switch (item->GetSubType())
  5147. {
  5148. case EXTRACT_DRAGON_SOUL:
  5149. if (pDestItem->IsDragonSoul())
  5150. {
  5151. return DSManager::instance().PullOut(this, NPOS, pDestItem, item);
  5152. }
  5153. return false;
  5154. case EXTRACT_DRAGON_HEART:
  5155. if (pDestItem->IsDragonSoul())
  5156. {
  5157. return DSManager::instance().ExtractDragonHeart(this, pDestItem, item);
  5158. }
  5159. return false;
  5160. default:
  5161. return false;
  5162. }
  5163. }
  5164. break;
  5165.  
  5166. case ITEM_NONE:
  5167. sys_err("Item type NONE %s", item->GetName());
  5168. break;
  5169.  
  5170. default:
  5171. sys_log(0, "UseItemEx: Unknown type %s %d", item->GetName(), item->GetType());
  5172. return false;
  5173. }
  5174.  
  5175. return true;
  5176. }
  5177.  
  5178. int g_nPortalLimitTime = 10;
  5179.  
  5180. bool CHARACTER::UseItem(TItemPos Cell, TItemPos DestCell)
  5181. {
  5182. WORD wCell = Cell.cell;
  5183. BYTE window_type = Cell.window_type;
  5184. WORD wDestCell = DestCell.cell;
  5185. BYTE bDestInven = DestCell.window_type;
  5186. LPITEM item;
  5187.  
  5188. if (!CanHandleItem())
  5189. return false;
  5190.  
  5191. if (!IsValidItemPosition(Cell) || !(item = GetItem(Cell)))
  5192. return false;
  5193.  
  5194. sys_log(0, "%s: USE_ITEM %s (inven %d, cell: %d)", GetName(), item->GetName(), window_type, wCell);
  5195.  
  5196. if (item->IsExchanging())
  5197. return false;
  5198.  
  5199. if (!item->CanUsedBy(this))
  5200. {
  5201. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±şÁ÷ŔĚ ¸ÂÁöľĘľĆ ŔĚ ľĆŔĚĹŰŔ» »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  5202. return false;
  5203. }
  5204.  
  5205. if (IsStun())
  5206. return false;
  5207.  
  5208. if (false == FN_check_item_sex(this, item))
  5209. {
  5210. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľşş°ŔĚ ¸ÂÁöľĘľĆ ŔĚ ľĆŔĚĹŰŔ» »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  5211. return false;
  5212. }
  5213.  
  5214. //PREVENT_TRADE_WINDOW
  5215. if (IS_SUMMON_ITEM(item->GetVnum()))
  5216. {
  5217. if (false == IS_SUMMONABLE_ZONE(GetMapIndex()))
  5218. {
  5219. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»çżëÇŇĽö ľř˝Ŕ´Ď´Ů."));
  5220. return false;
  5221. }
  5222.  
  5223. // °ćČĄąÝÁö »çżëÁö »ó´ëąćŔĚ SUMMONABLE_ZONEżˇ Ŕִ°ˇ´Â WarpToPC()żˇĽ­ ĂĽĹ©
  5224.  
  5225. //»ď°Ĺ¸® °ü·Á ¸ĘżˇĽ­´Â ±ÍČŻşÎ¸¦ ¸·ľĆąö¸°´Ů.
  5226. if (CThreeWayWar::instance().IsThreeWayWarMapIndex(GetMapIndex()))
  5227. {
  5228. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("»ď°Ĺ¸® ŔüĹő Âü°ˇÁßżˇ´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎ¸¦ »çżëÇŇĽö ľř˝Ŕ´Ď´Ů."));
  5229. return false;
  5230. }
  5231. int iPulse = thecore_pulse();
  5232.  
  5233. //â°í ż¬ČÄ ĂĽĹ©
  5234. if (iPulse - GetSafeboxLoadTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  5235. {
  5236. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("â°í¸¦ ż¬ČÄ %dĂĘ ŔĚł»żˇ´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎ¸¦ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."), g_nPortalLimitTime);
  5237.  
  5238. if (test_server)
  5239. ChatPacket(CHAT_TYPE_INFO, "[TestOnly]Pulse %d LoadTime %d PASS %d", iPulse, GetSafeboxLoadTime(), PASSES_PER_SEC(g_nPortalLimitTime));
  5240. return false;
  5241. }
  5242.  
  5243. //°Ĺ·ˇ°ü·Ă â ĂĽĹ©
  5244. if (GetExchange() || GetMyShop() || GetShopOwner() || IsOpenSafebox() || IsCubeOpen())
  5245. {
  5246. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°Ĺ·ˇĂ˘,â°í µîŔ» ż¬ »óĹÂżˇĽ­´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎ ¸¦ »çżëÇŇĽö ľř˝Ŕ´Ď´Ů."));
  5247. return false;
  5248. }
  5249.  
  5250. //PREVENT_REFINE_HACK
  5251. //°ł·®ČÄ ˝Ă°ŁĂĽĹ©
  5252. {
  5253. if (iPulse - GetRefineTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  5254. {
  5255. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ °ł·®ČÄ %dĂĘ ŔĚł»żˇ´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎ¸¦ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."), g_nPortalLimitTime);
  5256. return false;
  5257. }
  5258. }
  5259. //END_PREVENT_REFINE_HACK
  5260.  
  5261.  
  5262. //PREVENT_ITEM_COPY
  5263. {
  5264. if (iPulse - GetMyShopTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  5265. {
  5266. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°łŔλóÁˇ »çżëČÄ %dĂĘ ŔĚł»żˇ´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎ¸¦ »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."), g_nPortalLimitTime);
  5267. return false;
  5268. }
  5269.  
  5270. }
  5271. //END_PREVENT_ITEM_COPY
  5272.  
  5273.  
  5274. //±ÍČŻşÎ °Ĺ¸®ĂĽĹ©
  5275. if (item->GetVnum() != 70302)
  5276. {
  5277. PIXEL_POSITION posWarp;
  5278.  
  5279. int x = 0;
  5280. int y = 0;
  5281.  
  5282. double nDist = 0;
  5283. const double nDistant = 5000.0;
  5284. //±ÍČŻ±âľďşÎ
  5285. if (item->GetVnum() == 22010)
  5286. {
  5287. x = item->GetSocket(0) - GetX();
  5288. y = item->GetSocket(1) - GetY();
  5289. }
  5290. //±ÍČŻşÎ
  5291. else if (item->GetVnum() == 22000)
  5292. {
  5293. SECTREE_MANAGER::instance().GetRecallPositionByEmpire(GetMapIndex(), GetEmpire(), posWarp);
  5294.  
  5295. if (item->GetSocket(0) == 0)
  5296. {
  5297. x = posWarp.x - GetX();
  5298. y = posWarp.y - GetY();
  5299. }
  5300. else
  5301. {
  5302. x = item->GetSocket(0) - GetX();
  5303. y = item->GetSocket(1) - GetY();
  5304. }
  5305. }
  5306.  
  5307. nDist = sqrt(pow((float)x,2) + pow((float)y,2));
  5308.  
  5309. if (nDistant > nDist)
  5310. {
  5311. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕ̵ż µÇľîÁú Ŕ§ÄˇżÍ łĘą« °ˇ±îżö ±ÍČŻşÎ¸¦ »çżëÇŇĽö ľř˝Ŕ´Ď´Ů."));
  5312. if (test_server)
  5313. ChatPacket(CHAT_TYPE_INFO, "PossibleDistant %f nNowDist %f", nDistant,nDist);
  5314. return false;
  5315. }
  5316. }
  5317.  
  5318. //PREVENT_PORTAL_AFTER_EXCHANGE
  5319. //±łČŻ ČÄ ˝Ă°ŁĂĽĹ©
  5320. if (iPulse - GetExchangeTime() < PASSES_PER_SEC(g_nPortalLimitTime))
  5321. {
  5322. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°Ĺ·ˇ ČÄ %dĂĘ ŔĚł»żˇ´Â ±ÍČŻşÎ,±ÍČŻ±âľďşÎµîŔ» »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."), g_nPortalLimitTime);
  5323. return false;
  5324. }
  5325. //END_PREVENT_PORTAL_AFTER_EXCHANGE
  5326.  
  5327. }
  5328.  
  5329. //ş¸µű¸® şń´Ü »çżë˝Ă °Ĺ·ˇĂ˘ Á¦ÇŃ ĂĽĹ©
  5330. if (item->GetVnum() == 50200 | item->GetVnum() == 71049)
  5331. {
  5332. if (GetExchange() || GetMyShop() || GetShopOwner() || IsOpenSafebox() || IsCubeOpen())
  5333. {
  5334. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°Ĺ·ˇĂ˘,â°í µîŔ» ż¬ »óĹÂżˇĽ­´Â ş¸µű¸®,şń´Üş¸µű¸®¸¦ »çżëÇŇĽö ľř˝Ŕ´Ď´Ů."));
  5335. return false;
  5336. }
  5337.  
  5338. }
  5339. //END_PREVENT_TRADE_WINDOW
  5340.  
  5341. if (IS_SET(item->GetFlag(), ITEM_FLAG_LOG)) // »çżë ·Î±×¸¦ ł˛±â´Â ľĆŔĚĹŰ Ăł¸®
  5342. {
  5343. DWORD vid = item->GetVID();
  5344. DWORD oldCount = item->GetCount();
  5345. DWORD vnum = item->GetVnum();
  5346.  
  5347. char hint[ITEM_NAME_MAX_LEN + 32 + 1];
  5348. int len = snprintf(hint, sizeof(hint) - 32, "%s", item->GetName());
  5349.  
  5350. if (len < 0 || len >= (int) sizeof(hint) - 32)
  5351. len = (sizeof(hint) - 32) - 1;
  5352.  
  5353. bool ret = UseItemEx(item, DestCell);
  5354.  
  5355. if (NULL == ITEM_MANAGER::instance().FindByVID(vid)) // UseItemExżˇĽ­ ľĆŔĚĹŰŔĚ »čÁ¦ µÇľú´Ů. »čÁ¦ ·Î±×¸¦ ł˛±č
  5356. {
  5357. LogManager::instance().ItemLog(this, vid, vnum, "REMOVE", hint);
  5358. }
  5359. else if (oldCount != item->GetCount())
  5360. {
  5361. snprintf(hint + len, sizeof(hint) - len, " %u", oldCount - 1);
  5362. LogManager::instance().ItemLog(this, vid, vnum, "USE_ITEM", hint);
  5363. }
  5364. return (ret);
  5365. }
  5366. else
  5367. return UseItemEx(item, DestCell);
  5368. }
  5369.  
  5370. bool CHARACTER::DropItem(TItemPos Cell, BYTE bCount)
  5371. {
  5372. LPITEM item = NULL;
  5373.  
  5374. if (!CanHandleItem())
  5375. {
  5376. if (NULL != DragonSoul_RefineWindow_GetOpener())
  5377. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­Ă˘Ŕ» ż¬ »óĹÂżˇĽ­´Â ľĆŔĚĹŰŔ» żĹ±ć Ľö ľř˝Ŕ´Ď´Ů."));
  5378. return false;
  5379. }
  5380.  
  5381. if (IsDead())
  5382. return false;
  5383.  
  5384. if (!IsValidItemPosition(Cell) || !(item = GetItem(Cell)))
  5385. return false;
  5386.  
  5387. if (item->IsExchanging())
  5388. return false;
  5389.  
  5390. if (true == item->isLocked())
  5391. return false;
  5392.  
  5393. if (quest::CQuestManager::instance().GetPCForce(GetPlayerID())->IsRunning() == true)
  5394. return false;
  5395.  
  5396. if (IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_DROP | ITEM_ANTIFLAG_GIVE))
  5397. {
  5398. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ąö¸± Ľö ľř´Â ľĆŔĚĹŰŔÔ´Ď´Ů."));
  5399. return false;
  5400. }
  5401.  
  5402. if (bCount == 0 || bCount > item->GetCount())
  5403. bCount = item->GetCount();
  5404.  
  5405. SyncQuickslot(QUICKSLOT_TYPE_ITEM, Cell.cell, 255); // Quickslot żˇĽ­ Áöżň
  5406.  
  5407. LPITEM pkItemToDrop;
  5408.  
  5409. if (bCount == item->GetCount())
  5410. {
  5411. item->RemoveFromCharacter();
  5412. pkItemToDrop = item;
  5413. }
  5414. else
  5415. {
  5416. if (bCount == 0)
  5417. {
  5418. if (test_server)
  5419. sys_log(0, "[DROP_ITEM] drop item count == 0");
  5420. return false;
  5421. }
  5422.  
  5423. // check non-split items for china
  5424. //if (LC_IsNewCIBN())
  5425. // if (item->GetVnum() == 71095 || item->GetVnum() == 71050 || item->GetVnum() == 70038)
  5426. // return false;
  5427.  
  5428. item->SetCount(item->GetCount() - bCount);
  5429. ITEM_MANAGER::instance().FlushDelayedSave(item);
  5430.  
  5431. pkItemToDrop = ITEM_MANAGER::instance().CreateItem(item->GetVnum(), bCount);
  5432.  
  5433. // copy item socket -- by mhh
  5434. FN_copy_item_socket(pkItemToDrop, item);
  5435.  
  5436. char szBuf[51 + 1];
  5437. snprintf(szBuf, sizeof(szBuf), "%u %u", pkItemToDrop->GetID(), pkItemToDrop->GetCount());
  5438. LogManager::instance().ItemLog(this, item, "ITEM_SPLIT", szBuf);
  5439. }
  5440.  
  5441. PIXEL_POSITION pxPos = GetXYZ();
  5442.  
  5443. if (pkItemToDrop->AddToGround(GetMapIndex(), pxPos))
  5444. // Clear the variable, it looks the player does not dropped any item in the past second.if (thecore_pulse() > LastDropTime + 25) CountDrops = 0; // It looks the player dropped min. 4 items in the past 1 secondif (thecore_pulse() < LastDropTime + 25 && CountDrops >= 4){ // Set it to 0 CountDrops = 0; sys_err("%s[%d] has been disconnected because of drophack using", GetName(), GetPlayerID()); // Disconnect the player GetDesc()->SetPhase(PHASE_CLOSE); return false;}
  5445. {
  5446. // Çѱążˇ´Â ľĆŔĚĹŰŔ» ąö¸®°í şą±¸Çش޶ó´Â Ář»óŔŻŔúµéŔĚ ¸ąľĆĽ­
  5447. // ľĆŔĚĹŰŔ» ąŮ´Úżˇ ąö¸± ˝Ă ĽÓĽş·Î±×¸¦ ł˛±ä´Ů.
  5448. if (LC_IsYMIR())
  5449. item->AttrLog();
  5450.  
  5451. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¶łľîÁř ľĆŔĚĹŰŔş 3şĐ ČÄ »ç¶óÁý´Ď´Ů."));
  5452. pkItemToDrop->StartDestroyEvent();
  5453.  
  5454. ITEM_MANAGER::instance().FlushDelayedSave(pkItemToDrop);
  5455.  
  5456. char szHint[32 + 1];
  5457. snprintf(szHint, sizeof(szHint), "%s %u %u", pkItemToDrop->GetName(), pkItemToDrop->GetCount(), pkItemToDrop->GetOriginalVnum());
  5458. LogManager::instance().ItemLog(this, pkItemToDrop, "DROP", szHint);
  5459. LastDropTime = thecore_pulse(); CountDrops++;
  5460. //Motion(MOTION_PICKUP);
  5461. }
  5462.  
  5463. return true;
  5464. }
  5465.  
  5466. bool CHARACTER::DropGold(int gold){ return false;}
  5467.  
  5468.  
  5469. bool CHARACTER::MoveItem(TItemPos Cell, TItemPos DestCell, BYTE count)
  5470. {
  5471. LPITEM item = NULL;
  5472.  
  5473. if (!IsValidItemPosition(Cell))
  5474. return false;
  5475.  
  5476. if (!(item = GetItem(Cell)))
  5477. return false;
  5478.  
  5479. if (item->IsExchanging())
  5480. return false;
  5481.  
  5482. if (item->GetCount() < count)
  5483. return false;
  5484.  
  5485. if (INVENTORY == Cell.window_type && Cell.cell >= INVENTORY_MAX_NUM && IS_SET(item->GetFlag(), ITEM_FLAG_IRREMOVABLE))
  5486. return false;
  5487.  
  5488. if (true == item->isLocked())
  5489. return false;
  5490.  
  5491. if (!IsValidItemPosition(DestCell))
  5492. {
  5493. return false;
  5494. }
  5495.  
  5496. if (!CanHandleItem())
  5497. {
  5498. if (NULL != DragonSoul_RefineWindow_GetOpener())
  5499. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­Ă˘Ŕ» ż¬ »óĹÂżˇĽ­´Â ľĆŔĚĹŰŔ» żĹ±ć Ľö ľř˝Ŕ´Ď´Ů."));
  5500. return false;
  5501. }
  5502.  
  5503. // ±âČąŔÚŔÇ żäĂ»Ŕ¸·Î ş§Ć® ŔÎşĄĹ丮żˇ´Â ĆŻÁ¤ ŸŔÔŔÇ ľĆŔĚĹ۸¸ łÖŔ» Ľö ŔÖ´Ů.
  5504. if (DestCell.IsBeltInventoryPosition() && false == CBeltInventoryHelper::CanMoveIntoBeltInventory(item))
  5505. {
  5506. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş ş§Ć® ŔÎşĄĹ丮·Î żĹ±ć Ľö ľř˝Ŕ´Ď´Ů."));
  5507. return false;
  5508. }
  5509.  
  5510. // ŔĚąĚ ÂřżëÁßŔÎ ľĆŔĚĹŰŔ» ´Ů¸Ą °÷Ŕ¸·Î żĹ±â´Â °ćżě, 'ŔĺĂĄ ÇŘÁ¦' °ˇ´ÉÇŃ Áö Č®ŔÎÇĎ°í żĹ±č
  5511. if (Cell.IsEquipPosition() && !CanUnequipNow(item))
  5512. return false;
  5513.  
  5514. if (DestCell.IsEquipPosition())
  5515. {
  5516. if (GetItem(DestCell)) // ŔĺşńŔĎ °ćżě ÇŃ °÷¸¸ °Ë»çÇصµ µČ´Ů.
  5517. {
  5518. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Ŕĺşń¸¦ ÂřżëÇĎ°í ŔÖ˝Ŕ´Ď´Ů."));
  5519.  
  5520. return false;
  5521. }
  5522.  
  5523. EquipItem(item, DestCell.cell - INVENTORY_MAX_NUM);
  5524. }
  5525. else
  5526. {
  5527. if (item->IsDragonSoul())
  5528. {
  5529. if (item->IsEquipped())
  5530. {
  5531. return DSManager::instance().PullOut(this, DestCell, item);
  5532. }
  5533. else
  5534. {
  5535. if (DestCell.window_type != DRAGON_SOUL_INVENTORY)
  5536. {
  5537. return false;
  5538. }
  5539.  
  5540. if (!DSManager::instance().IsValidCellForThisItem(item, DestCell))
  5541. return false;
  5542. }
  5543. }
  5544. // żëČĄĽ®ŔĚ ľĆ´Ń ľĆŔĚĹŰŔş żëČĄĽ® ŔÎşĄżˇ µéľî°Ą Ľö ľř´Ů.
  5545. else if (DRAGON_SOUL_INVENTORY == DestCell.window_type)
  5546. return false;
  5547.  
  5548. LPITEM item2;
  5549.  
  5550. if ((item2 = GetItem(DestCell)) && item != item2 && item2->IsStackable() &&
  5551. !IS_SET(item2->GetAntiFlag(), ITEM_ANTIFLAG_STACK) &&
  5552. item2->GetVnum() == item->GetVnum()) // ÇŐÄĄ Ľö ŔÖ´Â ľĆŔĚĹŰŔÇ °ćżě
  5553. {
  5554. for (int i = 0; i < ITEM_SOCKET_MAX_NUM; ++i)
  5555. if (item2->GetSocket(i) != item->GetSocket(i))
  5556. return false;
  5557.  
  5558. if (count == 0)
  5559. count = item->GetCount();
  5560.  
  5561. sys_log(0, "%s: ITEM_STACK %s (window: %d, cell : %d) -> (window:%d, cell %d) count %d", GetName(), item->GetName(), Cell.window_type, Cell.cell,
  5562. DestCell.window_type, DestCell.cell, count);
  5563.  
  5564. count = MIN(200 - item2->GetCount(), count);
  5565.  
  5566. item->SetCount(item->GetCount() - count);
  5567. item2->SetCount(item2->GetCount() + count);
  5568. return true;
  5569. }
  5570.  
  5571. if (!IsEmptyItemGrid(DestCell, item->GetSize(), Cell.cell))
  5572. return false;
  5573.  
  5574. if (count == 0 || count >= item->GetCount() || !item->IsStackable() || IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_STACK))
  5575. {
  5576. sys_log(0, "%s: ITEM_MOVE %s (window: %d, cell : %d) -> (window:%d, cell %d) count %d", GetName(), item->GetName(), Cell.window_type, Cell.cell,
  5577. DestCell.window_type, DestCell.cell, count);
  5578.  
  5579. item->RemoveFromCharacter();
  5580. SetItem(DestCell, item);
  5581.  
  5582. if (INVENTORY == Cell.window_type && INVENTORY == DestCell.window_type)
  5583. SyncQuickslot(QUICKSLOT_TYPE_ITEM, Cell.cell, DestCell.cell);
  5584. }
  5585. else if (count < item->GetCount())
  5586. {
  5587. //check non-split items
  5588. //if (LC_IsNewCIBN())
  5589. //{
  5590. // if (item->GetVnum() == 71095 || item->GetVnum() == 71050 || item->GetVnum() == 70038)
  5591. // {
  5592. // return false;
  5593. // }
  5594. //}
  5595.  
  5596. sys_log(0, "%s: ITEM_SPLIT %s (window: %d, cell : %d) -> (window:%d, cell %d) count %d", GetName(), item->GetName(), Cell.window_type, Cell.cell,
  5597. DestCell.window_type, DestCell.cell, count);
  5598.  
  5599. item->SetCount(item->GetCount() - count);
  5600. LPITEM item2 = ITEM_MANAGER::instance().CreateItem(item->GetVnum(), count);
  5601.  
  5602. // copy socket -- by mhh
  5603. FN_copy_item_socket(item2, item);
  5604.  
  5605. item2->AddToCharacter(this, DestCell);
  5606.  
  5607. char szBuf[51+1];
  5608. snprintf(szBuf, sizeof(szBuf), "%u %u %u %u ", item2->GetID(), item2->GetCount(), item->GetCount(), item->GetCount() + item2->GetCount());
  5609. LogManager::instance().ItemLog(this, item, "ITEM_SPLIT", szBuf);
  5610. }
  5611. }
  5612.  
  5613. return true;
  5614. }
  5615.  
  5616. namespace NPartyPickupDistribute
  5617. {
  5618. struct FFindOwnership
  5619. {
  5620. LPITEM item;
  5621. LPCHARACTER owner;
  5622.  
  5623. FFindOwnership(LPITEM item)
  5624. : item(item), owner(NULL)
  5625. {
  5626. }
  5627.  
  5628. void operator () (LPCHARACTER ch)
  5629. {
  5630. if (item->IsOwnership(ch))
  5631. owner = ch;
  5632. }
  5633. };
  5634.  
  5635. struct FCountNearMember
  5636. {
  5637. int total;
  5638. int x, y;
  5639.  
  5640. FCountNearMember(LPCHARACTER center )
  5641. : total(0), x(center->GetX()), y(center->GetY())
  5642. {
  5643. }
  5644.  
  5645. void operator () (LPCHARACTER ch)
  5646. {
  5647. if (DISTANCE_APPROX(ch->GetX() - x, ch->GetY() - y) <= PARTY_DEFAULT_RANGE)
  5648. total += 1;
  5649. }
  5650. };
  5651.  
  5652. struct FMoneyDistributor
  5653. {
  5654. int total;
  5655. LPCHARACTER c;
  5656. int x, y;
  5657. int iMoney;
  5658.  
  5659. FMoneyDistributor(LPCHARACTER center, int iMoney)
  5660. : total(0), c(center), x(center->GetX()), y(center->GetY()), iMoney(iMoney)
  5661. {
  5662. }
  5663.  
  5664. void operator ()(LPCHARACTER ch)
  5665. {
  5666. if (ch!=c)
  5667. if (DISTANCE_APPROX(ch->GetX() - x, ch->GetY() - y) <= PARTY_DEFAULT_RANGE)
  5668. {
  5669. ch->PointChange(POINT_GOLD, iMoney, true);
  5670.  
  5671. if (iMoney > 1000) // õżř ŔĚ»ó¸¸ ±â·ĎÇŃ´Ů.
  5672. LogManager::instance().CharLog(ch, iMoney, "GET_GOLD", "");
  5673. }
  5674. }
  5675. };
  5676. }
  5677.  
  5678. void CHARACTER::GiveGold(long long iAmount)
  5679. {
  5680. if (iAmount <= 0)
  5681. return;
  5682.  
  5683. sys_log(0, "GIVE_GOLD: %s %lld", GetName(), iAmount);
  5684.  
  5685. if (GetParty())
  5686. {
  5687. LPPARTY pParty = GetParty();
  5688.  
  5689. long long dwTotal = iAmount;
  5690. long long dwMyAmount = dwTotal;
  5691.  
  5692. NPartyPickupDistribute::FCountNearMember funcCountNearMember(this);
  5693. pParty->ForEachOnlineMember(funcCountNearMember);
  5694.  
  5695. if (funcCountNearMember.total > 1)
  5696. {
  5697. DWORD dwShare = dwTotal / funcCountNearMember.total;
  5698. dwMyAmount -= dwShare * (funcCountNearMember.total - 1);
  5699.  
  5700. NPartyPickupDistribute::FMoneyDistributor funcMoneyDist(this, dwShare);
  5701.  
  5702. pParty->ForEachOnlineMember(funcMoneyDist);
  5703. }
  5704.  
  5705. PointChange(POINT_GOLD, dwMyAmount, true);
  5706.  
  5707. if (dwMyAmount > 1000) // õżř ŔĚ»ó¸¸ ±â·ĎÇŃ´Ů.
  5708. LogManager::instance().CharLog(this, dwMyAmount, "GET_GOLD", "");
  5709. }
  5710. else
  5711. {
  5712. PointChange(POINT_GOLD, iAmount, true);
  5713.  
  5714. // şę¶óÁúżˇ µ·ŔĚ ľřľîÁř´Ů´Â ąö±×°ˇ ŔִµĄ,
  5715. // °ˇ´ÉÇŃ ˝ĂłŞ¸®żŔ Áßżˇ ÇĎłŞ´Â,
  5716. // ¸ŢĹ©·ÎłŞ, ÇŮŔ» ˝áĽ­ 1000żř ŔĚÇĎŔÇ µ·Ŕ» °čĽÓ ąö·Á °ńµĺ¸¦ 0Ŕ¸·Î ¸¸µé°í,
  5717. // µ·ŔĚ ľřľîÁł´Ů°í şą±¸ ˝ĹĂ»ÇĎ´Â °ÍŔĎ Ľöµµ ŔÖ´Ů.
  5718. // µű¶óĽ­ ±×·± °ćżě¸¦ Ŕâ±â Ŕ§ÇŘ ł·Ŕş ĽöġŔÇ °ńµĺżˇ ´ëÇŘĽ­µµ ·Î±×¸¦ ł˛±č.
  5719. if (LC_IsBrazil() == true)
  5720. {
  5721. if (iAmount >= 213)
  5722. LogManager::instance().CharLog(this, iAmount, "GET_GOLD", "");
  5723. }
  5724. else
  5725. {
  5726. if (iAmount > 1000) // õżř ŔĚ»ó¸¸ ±â·ĎÇŃ´Ů.
  5727. LogManager::instance().CharLog(this, iAmount, "GET_GOLD", "");
  5728. }
  5729. }
  5730. }
  5731.  
  5732. bool CHARACTER::PickupItem(DWORD dwVID)
  5733. {
  5734. LPITEM item = ITEM_MANAGER::instance().FindByVID(dwVID);
  5735.  
  5736. if (IsObserverMode())
  5737. return false;
  5738.  
  5739. if (!item || !item->GetSectree())
  5740. return false;
  5741.  
  5742. if (item->DistanceValid(this))
  5743. {
  5744. if (item->IsOwnership(this))
  5745. {
  5746. // ¸¸ľŕ ÁÖŔ¸·Á ÇĎ´Â ľĆŔĚĹŰŔĚ ż¤Ĺ©¶ó¸é
  5747. if (item->GetType() == ITEM_ELK)
  5748. {
  5749. GiveGold(item->GetCount());
  5750. item->RemoveFromGround();
  5751.  
  5752. M2_DESTROY_ITEM(item);
  5753.  
  5754. Save();
  5755. }
  5756. // ĆňąüÇŃ ľĆŔĚĹŰŔ̶ó¸é
  5757. else
  5758. {
  5759. if (item->IsStackable() && !IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_STACK))
  5760. {
  5761. BYTE bCount = item->GetCount();
  5762.  
  5763. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  5764. {
  5765. LPITEM item2 = GetInventoryItem(i);
  5766.  
  5767. if (!item2)
  5768. continue;
  5769.  
  5770. if (item2->GetVnum() == item->GetVnum())
  5771. {
  5772. int j;
  5773.  
  5774. for (j = 0; j < ITEM_SOCKET_MAX_NUM; ++j)
  5775. if (item2->GetSocket(j) != item->GetSocket(j))
  5776. break;
  5777.  
  5778. if (j != ITEM_SOCKET_MAX_NUM)
  5779. continue;
  5780.  
  5781. BYTE bCount2 = MIN(200 - item2->GetCount(), bCount);
  5782. bCount -= bCount2;
  5783.  
  5784. item2->SetCount(item2->GetCount() + bCount2);
  5785.  
  5786. if (bCount == 0)
  5787. {
  5788. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s"), item2->GetName());
  5789. M2_DESTROY_ITEM(item);
  5790. if (item2->GetType() == ITEM_QUEST)
  5791. quest::CQuestManager::instance().PickupItem (GetPlayerID(), item2);
  5792. return true;
  5793. }
  5794. }
  5795. }
  5796.  
  5797. item->SetCount(bCount);
  5798. }
  5799.  
  5800. int iEmptyCell;
  5801. if (item->IsDragonSoul())
  5802. {
  5803. if ((iEmptyCell = GetEmptyDragonSoulInventory(item)) == -1)
  5804. {
  5805. sys_log(0, "No empty ds inventory pid %u size %ud itemid %u", GetPlayerID(), item->GetSize(), item->GetID());
  5806. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇĎ°í ŔÖ´Â ľĆŔĚĹŰŔĚ łĘą« ¸ą˝Ŕ´Ď´Ů."));
  5807. return false;
  5808. }
  5809. }
  5810. else
  5811. {
  5812. if ((iEmptyCell = GetEmptyInventory(item->GetSize())) == -1)
  5813. {
  5814. sys_log(0, "No empty inventory pid %u size %ud itemid %u", GetPlayerID(), item->GetSize(), item->GetID());
  5815. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇĎ°í ŔÖ´Â ľĆŔĚĹŰŔĚ łĘą« ¸ą˝Ŕ´Ď´Ů."));
  5816. return false;
  5817. }
  5818. }
  5819.  
  5820. item->RemoveFromGround();
  5821.  
  5822. if (item->IsDragonSoul())
  5823. item->AddToCharacter(this, TItemPos(DRAGON_SOUL_INVENTORY, iEmptyCell));
  5824. else
  5825. item->AddToCharacter(this, TItemPos(INVENTORY, iEmptyCell));
  5826.  
  5827. char szHint[32+1];
  5828. snprintf(szHint, sizeof(szHint), "%s %u %u", item->GetName(), item->GetCount(), item->GetOriginalVnum());
  5829. LogManager::instance().ItemLog(this, item, "GET", szHint);
  5830. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s"), item->GetName());
  5831.  
  5832. if (item->GetType() == ITEM_QUEST)
  5833. quest::CQuestManager::instance().PickupItem (GetPlayerID(), item);
  5834. }
  5835.  
  5836. //Motion(MOTION_PICKUP);
  5837. return true;
  5838. }
  5839. else if (!IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_GIVE | ITEM_ANTIFLAG_DROP) && GetParty())
  5840. {
  5841. // ´Ů¸Ą ĆÄĆĽżř ĽŇŔŻ±Ç ľĆŔĚĹŰŔ» ÁÖŔ¸·Á°í ÇѴٸé
  5842. NPartyPickupDistribute::FFindOwnership funcFindOwnership(item);
  5843.  
  5844. GetParty()->ForEachOnlineMember(funcFindOwnership);
  5845.  
  5846. LPCHARACTER owner = funcFindOwnership.owner;
  5847.  
  5848. int iEmptyCell;
  5849.  
  5850. if (item->IsDragonSoul())
  5851. {
  5852. if (!(owner && (iEmptyCell = owner->GetEmptyDragonSoulInventory(item)) != -1))
  5853. {
  5854. owner = this;
  5855.  
  5856. if ((iEmptyCell = GetEmptyDragonSoulInventory(item)) == -1)
  5857. {
  5858. owner->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇĎ°í ŔÖ´Â ľĆŔĚĹŰŔĚ łĘą« ¸ą˝Ŕ´Ď´Ů."));
  5859. return false;
  5860. }
  5861. }
  5862. }
  5863. else
  5864. {
  5865. if (!(owner && (iEmptyCell = owner->GetEmptyInventory(item->GetSize())) != -1))
  5866. {
  5867. owner = this;
  5868.  
  5869. if ((iEmptyCell = GetEmptyInventory(item->GetSize())) == -1)
  5870. {
  5871. owner->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöÇĎ°í ŔÖ´Â ľĆŔĚĹŰŔĚ łĘą« ¸ą˝Ŕ´Ď´Ů."));
  5872. return false;
  5873. }
  5874. }
  5875. }
  5876.  
  5877. item->RemoveFromGround();
  5878.  
  5879. if (item->IsDragonSoul())
  5880. item->AddToCharacter(owner, TItemPos(DRAGON_SOUL_INVENTORY, iEmptyCell));
  5881. else
  5882. item->AddToCharacter(owner, TItemPos(INVENTORY, iEmptyCell));
  5883.  
  5884. char szHint[32+1];
  5885. snprintf(szHint, sizeof(szHint), "%s %u %u", item->GetName(), item->GetCount(), item->GetOriginalVnum());
  5886. LogManager::instance().ItemLog(owner, item, "GET", szHint);
  5887.  
  5888. if (owner == this)
  5889. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s"), item->GetName());
  5890. else
  5891. {
  5892. owner->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s ´ÔŔ¸·ÎşÎĹÍ %s"), GetName(), item->GetName());
  5893. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Ŕü´Ţ: %s ´Ôżˇ°Ô %s"), owner->GetName(), item->GetName());
  5894. }
  5895.  
  5896. if (item->GetType() == ITEM_QUEST)
  5897. quest::CQuestManager::instance().PickupItem (owner->GetPlayerID(), item);
  5898.  
  5899. return true;
  5900. }
  5901. }
  5902.  
  5903. return false;
  5904. }
  5905.  
  5906. bool CHARACTER::SwapItem(BYTE bCell, BYTE bDestCell)
  5907. {
  5908. if (!CanHandleItem())
  5909. return false;
  5910.  
  5911. TItemPos srcCell(INVENTORY, bCell), destCell(INVENTORY, bDestCell);
  5912.  
  5913. // żĂąŮ¸Ą Cell ŔÎÁö °Ë»ç
  5914. // żëČĄĽ®Ŕş SwapÇŇ Ľö ľřŔ¸ąÇ·Î, ż©±âĽ­ °É¸˛.
  5915. //if (bCell >= INVENTORY_MAX_NUM + WEAR_MAX_NUM || bDestCell >= INVENTORY_MAX_NUM + WEAR_MAX_NUM)
  5916. if (srcCell.IsDragonSoulEquipPosition() || destCell.IsDragonSoulEquipPosition())
  5917. return false;
  5918.  
  5919. // °°Ŕş CELL ŔÎÁö °Ë»ç
  5920. if (bCell == bDestCell)
  5921. return false;
  5922.  
  5923. // µŃ ´Ů Ŕĺşńâ Ŕ§Äˇ¸é Swap ÇŇ Ľö ľř´Ů.
  5924. if (srcCell.IsEquipPosition() && destCell.IsEquipPosition())
  5925. return false;
  5926.  
  5927. LPITEM item1, item2;
  5928.  
  5929. // item2°ˇ Ŕĺşń⿡ ŔÖ´Â °ÍŔĚ µÇµµ·Ď.
  5930. if (srcCell.IsEquipPosition())
  5931. {
  5932. item1 = GetInventoryItem(bDestCell);
  5933. item2 = GetInventoryItem(bCell);
  5934. }
  5935. else
  5936. {
  5937. item1 = GetInventoryItem(bCell);
  5938. item2 = GetInventoryItem(bDestCell);
  5939. }
  5940.  
  5941. if (!item1 || !item2)
  5942. return false;
  5943.  
  5944. if (item1 == item2)
  5945. {
  5946. sys_log(0, "[WARNING][WARNING][HACK USER!] : %s %d %d", m_stName.c_str(), bCell, bDestCell);
  5947. return false;
  5948. }
  5949.  
  5950. // item2°ˇ bCellŔ§Äˇżˇ µéľî°Ą Ľö ŔÖ´ÂÁö Č®ŔÎÇŃ´Ů.
  5951. if (!IsEmptyItemGrid(TItemPos (INVENTORY, item1->GetCell()), item2->GetSize(), item1->GetCell()))
  5952. return false;
  5953.  
  5954. // ąŮ˛Ü ľĆŔĚĹŰŔĚ Ŕĺşń⿡ ŔÖŔ¸¸é
  5955. if (TItemPos(EQUIPMENT, item2->GetCell()).IsEquipPosition())
  5956. {
  5957. BYTE bEquipCell = item2->GetCell() - INVENTORY_MAX_NUM;
  5958. BYTE bInvenCell = item1->GetCell();
  5959.  
  5960. // ÂřżëÁßŔÎ ľĆŔĚĹŰŔ» ąţŔ» Ľö ŔÖ°í, Âřżë żąÁ¤ ľĆŔĚĹŰŔĚ Âřżë °ˇ´ÉÇŃ »óĹÂż©ľß¸¸ ÁřÇŕ
  5961. if (false == CanUnequipNow(item2) || false == CanEquipNow(item1))
  5962. return false;
  5963.  
  5964. if (bEquipCell != item1->FindEquipCell(this)) // °°Ŕş Ŕ§ÄˇŔ϶§¸¸ Çăżë
  5965. return false;
  5966.  
  5967. item2->RemoveFromCharacter();
  5968.  
  5969. if (item1->EquipTo(this, bEquipCell))
  5970. item2->AddToCharacter(this, TItemPos(INVENTORY, bInvenCell));
  5971. else
  5972. sys_err("SwapItem cannot equip %s! item1 %s", item2->GetName(), item1->GetName());
  5973. }
  5974. else
  5975. {
  5976. BYTE bCell1 = item1->GetCell();
  5977. BYTE bCell2 = item2->GetCell();
  5978.  
  5979. item1->RemoveFromCharacter();
  5980. item2->RemoveFromCharacter();
  5981.  
  5982. item1->AddToCharacter(this, TItemPos(INVENTORY, bCell2));
  5983. item2->AddToCharacter(this, TItemPos(INVENTORY, bCell1));
  5984. }
  5985.  
  5986. return true;
  5987. }
  5988.  
  5989. bool CHARACTER::UnequipItem(LPITEM item)
  5990. {
  5991. int pos;
  5992.  
  5993. if (false == CanUnequipNow(item))
  5994. return false;
  5995.  
  5996. if (item->IsDragonSoul())
  5997. pos = GetEmptyDragonSoulInventory(item);
  5998. else
  5999. pos = GetEmptyInventory(item->GetSize());
  6000.  
  6001. // HARD CODING
  6002. if (item->GetVnum() == UNIQUE_ITEM_HIDE_ALIGNMENT_TITLE)
  6003. ShowAlignment(true);
  6004.  
  6005. item->RemoveFromCharacter();
  6006. if (item->IsDragonSoul())
  6007. {
  6008. item->AddToCharacter(this, TItemPos(DRAGON_SOUL_INVENTORY, pos));
  6009. }
  6010. else
  6011. item->AddToCharacter(this, TItemPos(INVENTORY, pos));
  6012.  
  6013. CheckMaximumPoints();
  6014.  
  6015. return true;
  6016. }
  6017.  
  6018. //
  6019. // @version 05/07/05 Bang2ni - Skill »çżëČÄ 1.5 ĂĘ ŔĚł»żˇ Ŕĺşń Âřżë ±ÝÁö
  6020. //
  6021. bool CHARACTER::EquipItem(LPITEM item, int iCandidateCell)
  6022. {
  6023. if (item->IsExchanging())
  6024. return false;
  6025.  
  6026. if (false == item->IsEquipable())
  6027. return false;
  6028.  
  6029. if (false == CanEquipNow(item))
  6030. return false;
  6031.  
  6032. int iWearCell = item->FindEquipCell(this, iCandidateCell);
  6033.  
  6034. if (iWearCell < 0)
  6035. return false;
  6036.  
  6037. // ą«ľđ°ˇ¸¦ Ĺş »óĹÂżˇĽ­ Ĺνõµ ŔԱ⠱ÝÁö
  6038. if (iWearCell == WEAR_BODY && IsRiding() && (item->GetVnum() >= 11901 && item->GetVnum() <= 11904))
  6039. {
  6040. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸»Ŕ» Ĺş »óĹÂżˇĽ­ żąşąŔ» ŔÔŔ» Ľö ľř˝Ŕ´Ď´Ů."));
  6041. return false;
  6042. }
  6043.  
  6044. if (iWearCell != WEAR_ARROW && IsPolymorphed())
  6045. {
  6046. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µĐ°© Áßżˇ´Â ÂřżëÁßŔÎ Ŕĺşń¸¦ şŻ°ćÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  6047. return false;
  6048. }
  6049.  
  6050. if (FN_check_item_sex(this, item) == false)
  6051. {
  6052. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ľşş°ŔĚ ¸ÂÁöľĘľĆ ŔĚ ľĆŔĚĹŰŔ» »çżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  6053. return false;
  6054. }
  6055.  
  6056. //˝Ĺ±Ô Ĺ»°Í »çżë˝Ă ±âÁ¸ ¸» »çżëż©şÎ ĂĽĹ©
  6057. if(item->IsRideItem() && IsRiding())
  6058. {
  6059. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ Ĺ»°ÍŔ» ŔĚżëÁßŔÔ´Ď´Ů."));
  6060. return false;
  6061. }
  6062.  
  6063. // Č­»ě Ŕ̿ܿˇ´Â ¸¶Áö¸· °ř°Ý ˝Ă°Ł ¶Ç´Â ˝şĹł »çżë 1.5 ČÄżˇ Ŕĺşń ±łĂĽ°ˇ °ˇ´É
  6064. DWORD dwCurTime = get_dword_time();
  6065.  
  6066. if (iWearCell != WEAR_ARROW
  6067. && (dwCurTime - GetLastAttackTime() <= 1500 || dwCurTime - m_dwLastSkillTime <= 1500))
  6068. {
  6069. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ˇ¸¸Č÷ ŔÖŔ» ¶§¸¸ ÂřżëÇŇ Ľö ŔÖ˝Ŕ´Ď´Ů."));
  6070. return false;
  6071. }
  6072.  
  6073. // żëČĄĽ® ĆŻĽö Ăł¸®
  6074. if (item->IsDragonSoul())
  6075. {
  6076. // °°Ŕş ŸŔÔŔÇ żëČĄĽ®ŔĚ ŔĚąĚ µéľî°ˇ Ŕִٸé ÂřżëÇŇ Ľö ľř´Ů.
  6077. // żëČĄĽ®Ŕş swapŔ» ÁöżřÇĎ¸é ľČµĘ.
  6078. if(GetInventoryItem(INVENTORY_MAX_NUM + iWearCell))
  6079. {
  6080. ChatPacket(CHAT_TYPE_INFO, "ŔĚąĚ °°Ŕş Áľ·ůŔÇ żëČĄĽ®Ŕ» ÂřżëÇĎ°í ŔÖ˝Ŕ´Ď´Ů.");
  6081. return false;
  6082. }
  6083.  
  6084. if (!item->EquipTo(this, iWearCell))
  6085. {
  6086. return false;
  6087. }
  6088. }
  6089. // żëČĄĽ®ŔĚ ľĆ´Ô.
  6090. else
  6091. {
  6092. // ÂřżëÇŇ °÷żˇ ľĆŔĚĹŰŔĚ Ŕִٸé,
  6093. if (GetWear(iWearCell) && !IS_SET(GetWear(iWearCell)->GetFlag(), ITEM_FLAG_IRREMOVABLE))
  6094. {
  6095. // ŔĚ ľĆŔĚĹŰŔş ÇŃąř ąÚČ÷¸é şŻ°ć şŇ°ˇ. swap żŞ˝Ă żĎŔü şŇ°ˇ
  6096. if (item->GetWearFlag() == WEARABLE_ABILITY)
  6097. return false;
  6098.  
  6099. if (false == SwapItem(item->GetCell(), INVENTORY_MAX_NUM + iWearCell))
  6100. {
  6101. return false;
  6102. }
  6103. }
  6104. else
  6105. {
  6106. BYTE bOldCell = item->GetCell();
  6107.  
  6108. if (item->EquipTo(this, iWearCell))
  6109. {
  6110. SyncQuickslot(QUICKSLOT_TYPE_ITEM, bOldCell, iWearCell);
  6111. }
  6112. }
  6113. }
  6114.  
  6115. if (true == item->IsEquipped())
  6116. {
  6117. // ľĆŔĚĹŰ ĂÖĂĘ »çżë ŔĚČÄşÎĹÍ´Â »çżëÇĎÁö ľĘľĆµµ ˝Ă°ŁŔĚ Â÷°¨µÇ´Â ąć˝Ä Ăł¸®.
  6118. if (-1 != item->GetProto()->cLimitRealTimeFirstUseIndex)
  6119. {
  6120. // ÇŃ ąřŔĚ¶óµµ »çżëÇŃ ľĆŔĚĹŰŔÎÁö ż©şÎ´Â Socket1Ŕ» ş¸°í ĆÇ´ÜÇŃ´Ů. (Socket1żˇ »çżëČ˝Ľö ±â·Ď)
  6121. if (0 == item->GetSocket(1))
  6122. {
  6123. // »çżë°ˇ´É˝Ă°ŁŔş Default °ŞŔ¸·Î Limit Value °ŞŔ» »çżëÇϵÇ, Socket0żˇ °ŞŔĚ ŔÖŔ¸¸é ±× °ŞŔ» »çżëÇϵµ·Ď ÇŃ´Ů. (´ÜŔ§´Â ĂĘ)
  6124. long duration = (0 != item->GetSocket(0)) ? item->GetSocket(0) : item->GetProto()->aLimits[item->GetProto()->cLimitRealTimeFirstUseIndex].lValue;
  6125.  
  6126. if (0 == duration)
  6127. duration = 60 * 60 * 24 * 7;
  6128.  
  6129. item->SetSocket(0, time(0) + duration);
  6130. item->StartRealTimeExpireEvent();
  6131. }
  6132.  
  6133. item->SetSocket(1, item->GetSocket(1) + 1);
  6134. }
  6135.  
  6136. if (item->GetVnum() == UNIQUE_ITEM_HIDE_ALIGNMENT_TITLE)
  6137. ShowAlignment(false);
  6138.  
  6139. const DWORD& dwVnum = item->GetVnum();
  6140.  
  6141. // ¶ó¸¶´Ü ŔĚşĄĆ® Ăʽ´ŢŔÇ ąÝÁö(71135) Âřżë˝Ă ŔĚĆĺĆ® ąßµż
  6142. if (true == CItemVnumHelper::IsRamadanMoonRing(dwVnum))
  6143. {
  6144. this->EffectPacket(SE_EQUIP_RAMADAN_RING);
  6145. }
  6146. // ÇŇ·ÎŔ© »çĹÁ(71136) Âřżë˝Ă ŔĚĆĺĆ® ąßµż
  6147. else if (true == CItemVnumHelper::IsHalloweenCandy(dwVnum))
  6148. {
  6149. this->EffectPacket(SE_EQUIP_HALLOWEEN_CANDY);
  6150. }
  6151. // ÇŕşąŔÇ ąÝÁö(71143) Âřżë˝Ă ŔĚĆĺĆ® ąßµż
  6152. else if (true == CItemVnumHelper::IsHappinessRing(dwVnum))
  6153. {
  6154. this->EffectPacket(SE_EQUIP_HAPPINESS_RING);
  6155. }
  6156. // »ç¶űŔÇ ĆŇ´řĆ®(71145) Âřżë˝Ă ŔĚĆĺĆ® ąßµż
  6157. else if (true == CItemVnumHelper::IsLovePendant(dwVnum))
  6158. {
  6159. this->EffectPacket(SE_EQUIP_LOVE_PENDANT);
  6160. }
  6161. // ITEM_UNIQUEŔÇ °ćżě, SpecialItemGroupżˇ Á¤ŔǵǾî ŔÖ°í, (item->GetSIGVnum() != NULL)
  6162. //
  6163. else if (ITEM_UNIQUE == item->GetType() && 0 != item->GetSIGVnum())
  6164. {
  6165. const CSpecialItemGroup* pGroup = ITEM_MANAGER::instance().GetSpecialItemGroup(item->GetSIGVnum());
  6166. if (NULL != pGroup)
  6167. {
  6168. const CSpecialAttrGroup* pAttrGroup = ITEM_MANAGER::instance().GetSpecialAttrGroup(pGroup->GetAttrVnum(item->GetVnum()));
  6169. if (NULL != pAttrGroup)
  6170. {
  6171. const std::string& std = pAttrGroup->m_stEffectFileName;
  6172. SpecificEffectPacket(std.c_str());
  6173. }
  6174. }
  6175. }
  6176.  
  6177. if (UNIQUE_SPECIAL_RIDE == item->GetSubType() && IS_SET(item->GetFlag(), ITEM_FLAG_QUEST_USE))
  6178. {
  6179. quest::CQuestManager::instance().UseItem(GetPlayerID(), item, false);
  6180. }
  6181. }
  6182.  
  6183. return true;
  6184. }
  6185.  
  6186. void CHARACTER::BuffOnAttr_AddBuffsFromItem(LPITEM pItem)
  6187. {
  6188. for (int i = 0; i < sizeof(g_aBuffOnAttrPoints)/sizeof(g_aBuffOnAttrPoints[0]); i++)
  6189. {
  6190. TMapBuffOnAttrs::iterator it = m_map_buff_on_attrs.find(g_aBuffOnAttrPoints[i]);
  6191. if (it != m_map_buff_on_attrs.end())
  6192. {
  6193. it->second->AddBuffFromItem(pItem);
  6194. }
  6195. }
  6196. }
  6197.  
  6198. void CHARACTER::BuffOnAttr_RemoveBuffsFromItem(LPITEM pItem)
  6199. {
  6200. for (int i = 0; i < sizeof(g_aBuffOnAttrPoints)/sizeof(g_aBuffOnAttrPoints[0]); i++)
  6201. {
  6202. TMapBuffOnAttrs::iterator it = m_map_buff_on_attrs.find(g_aBuffOnAttrPoints[i]);
  6203. if (it != m_map_buff_on_attrs.end())
  6204. {
  6205. it->second->RemoveBuffFromItem(pItem);
  6206. }
  6207. }
  6208. }
  6209.  
  6210. void CHARACTER::BuffOnAttr_ClearAll()
  6211. {
  6212. for (TMapBuffOnAttrs::iterator it = m_map_buff_on_attrs.begin(); it != m_map_buff_on_attrs.end(); it++)
  6213. {
  6214. CBuffOnAttributes* pBuff = it->second;
  6215. if (pBuff)
  6216. {
  6217. pBuff->Initialize();
  6218. }
  6219. }
  6220. }
  6221.  
  6222. void CHARACTER::BuffOnAttr_ValueChange(BYTE bType, BYTE bOldValue, BYTE bNewValue)
  6223. {
  6224. TMapBuffOnAttrs::iterator it = m_map_buff_on_attrs.find(bType);
  6225.  
  6226. if (0 == bNewValue)
  6227. {
  6228. if (m_map_buff_on_attrs.end() == it)
  6229. return;
  6230. else
  6231. it->second->Off();
  6232. }
  6233. else if(0 == bOldValue)
  6234. {
  6235. CBuffOnAttributes* pBuff;
  6236. if (m_map_buff_on_attrs.end() == it)
  6237. {
  6238. switch (bType)
  6239. {
  6240. case POINT_ENERGY:
  6241. {
  6242. static BYTE abSlot[] = { WEAR_BODY, WEAR_HEAD, WEAR_FOOTS, WEAR_WRIST, WEAR_WEAPON, WEAR_NECK, WEAR_EAR, WEAR_SHIELD };
  6243. static std::vector <BYTE> vec_slots (abSlot, abSlot + _countof(abSlot));
  6244. pBuff = M2_NEW CBuffOnAttributes(this, bType, &vec_slots);
  6245. }
  6246. break;
  6247. case POINT_COSTUME_ATTR_BONUS:
  6248. {
  6249. static BYTE abSlot[] = { WEAR_COSTUME_BODY, WEAR_COSTUME_HAIR };
  6250. static std::vector <BYTE> vec_slots (abSlot, abSlot + _countof(abSlot));
  6251. pBuff = M2_NEW CBuffOnAttributes(this, bType, &vec_slots);
  6252. }
  6253. break;
  6254. default:
  6255. break;
  6256. }
  6257. m_map_buff_on_attrs.insert(TMapBuffOnAttrs::value_type(bType, pBuff));
  6258.  
  6259. }
  6260. else
  6261. pBuff = it->second;
  6262.  
  6263. pBuff->On(bNewValue);
  6264. }
  6265. else
  6266. {
  6267. if (m_map_buff_on_attrs.end() == it)
  6268. return;
  6269. else
  6270. it->second->ChangeBuffValue(bNewValue);
  6271. }
  6272. }
  6273.  
  6274.  
  6275. LPITEM CHARACTER::FindSpecifyItem(DWORD vnum) const
  6276. {
  6277. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  6278. if (GetInventoryItem(i) && GetInventoryItem(i)->GetVnum() == vnum)
  6279. return GetInventoryItem(i);
  6280.  
  6281. return NULL;
  6282. }
  6283.  
  6284. LPITEM CHARACTER::FindItemByID(DWORD id) const
  6285. {
  6286. for (int i=0 ; i < INVENTORY_MAX_NUM ; ++i)
  6287. {
  6288. if (NULL != GetInventoryItem(i) && GetInventoryItem(i)->GetID() == id)
  6289. return GetInventoryItem(i);
  6290. }
  6291.  
  6292. for (int i=BELT_INVENTORY_SLOT_START; i < BELT_INVENTORY_SLOT_END ; ++i)
  6293. {
  6294. if (NULL != GetInventoryItem(i) && GetInventoryItem(i)->GetID() == id)
  6295. return GetInventoryItem(i);
  6296. }
  6297.  
  6298. return NULL;
  6299. }
  6300.  
  6301. int CHARACTER::CountSpecifyItem(DWORD vnum) const
  6302. {
  6303. int count = 0;
  6304. LPITEM item;
  6305.  
  6306. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  6307. {
  6308. item = GetInventoryItem(i);
  6309. if (NULL != item && item->GetVnum() == vnum)
  6310. {
  6311. // °łŔÎ »óÁˇżˇ µî·ĎµČ ą°°ÇŔĚ¸é łŃľî°Ł´Ů.
  6312. if (m_pkMyShop && m_pkMyShop->IsSellingItem(item->GetID()))
  6313. {
  6314. continue;
  6315. }
  6316. else
  6317. {
  6318. count += item->GetCount();
  6319. }
  6320. }
  6321. }
  6322.  
  6323. return count;
  6324. }
  6325.  
  6326. void CHARACTER::RemoveSpecifyItem(DWORD vnum, DWORD count)
  6327. {
  6328. if (0 == count)
  6329. return;
  6330.  
  6331. for (UINT i = 0; i < INVENTORY_MAX_NUM; ++i)
  6332. {
  6333. if (NULL == GetInventoryItem(i))
  6334. continue;
  6335.  
  6336. if (GetInventoryItem(i)->GetVnum() != vnum)
  6337. continue;
  6338.  
  6339. //°łŔÎ »óÁˇżˇ µî·ĎµČ ą°°ÇŔĚ¸é łŃľî°Ł´Ů. (°łŔÎ »óÁˇżˇĽ­ ĆǸŵɶ§ ŔĚ şÎşĐŔ¸·Î µéľîżĂ °ćżě ą®Á¦!)
  6340. if(m_pkMyShop)
  6341. {
  6342. bool isItemSelling = m_pkMyShop->IsSellingItem(GetInventoryItem(i)->GetID());
  6343. if (isItemSelling)
  6344. continue;
  6345. }
  6346.  
  6347. if (vnum >= 80003 && vnum <= 80007)
  6348. LogManager::instance().GoldBarLog(GetPlayerID(), GetInventoryItem(i)->GetID(), QUEST, "RemoveSpecifyItem");
  6349.  
  6350. if (count >= GetInventoryItem(i)->GetCount())
  6351. {
  6352. count -= GetInventoryItem(i)->GetCount();
  6353. GetInventoryItem(i)->SetCount(0);
  6354.  
  6355. if (0 == count)
  6356. return;
  6357. }
  6358. else
  6359. {
  6360. GetInventoryItem(i)->SetCount(GetInventoryItem(i)->GetCount() - count);
  6361. return;
  6362. }
  6363. }
  6364.  
  6365. // żążÜĂł¸®°ˇ ľŕÇĎ´Ů.
  6366. if (count)
  6367. sys_log(0, "CHARACTER::RemoveSpecifyItem cannot remove enough item vnum %u, still remain %d", vnum, count);
  6368. }
  6369.  
  6370. int CHARACTER::CountSpecifyTypeItem(BYTE type) const
  6371. {
  6372. int count = 0;
  6373.  
  6374. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  6375. {
  6376. LPITEM pItem = GetInventoryItem(i);
  6377. if (pItem != NULL && pItem->GetType() == type)
  6378. {
  6379. count += pItem->GetCount();
  6380. }
  6381. }
  6382.  
  6383. return count;
  6384. }
  6385.  
  6386. void CHARACTER::RemoveSpecifyTypeItem(BYTE type, DWORD count)
  6387. {
  6388. if (0 == count)
  6389. return;
  6390.  
  6391. for (UINT i = 0; i < INVENTORY_MAX_NUM; ++i)
  6392. {
  6393. if (NULL == GetInventoryItem(i))
  6394. continue;
  6395.  
  6396. if (GetInventoryItem(i)->GetType() != type)
  6397. continue;
  6398.  
  6399. //°łŔÎ »óÁˇżˇ µî·ĎµČ ą°°ÇŔĚ¸é łŃľî°Ł´Ů. (°łŔÎ »óÁˇżˇĽ­ ĆǸŵɶ§ ŔĚ şÎşĐŔ¸·Î µéľîżĂ °ćżě ą®Á¦!)
  6400. if(m_pkMyShop)
  6401. {
  6402. bool isItemSelling = m_pkMyShop->IsSellingItem(GetInventoryItem(i)->GetID());
  6403. if (isItemSelling)
  6404. continue;
  6405. }
  6406.  
  6407. if (count >= GetInventoryItem(i)->GetCount())
  6408. {
  6409. count -= GetInventoryItem(i)->GetCount();
  6410. GetInventoryItem(i)->SetCount(0);
  6411.  
  6412. if (0 == count)
  6413. return;
  6414. }
  6415. else
  6416. {
  6417. GetInventoryItem(i)->SetCount(GetInventoryItem(i)->GetCount() - count);
  6418. return;
  6419. }
  6420. }
  6421. }
  6422.  
  6423. void CHARACTER::AutoGiveItem(LPITEM item, bool longOwnerShip)
  6424. {
  6425. if (NULL == item)
  6426. {
  6427. sys_err ("NULL point.");
  6428. return;
  6429. }
  6430. if (item->GetOwner())
  6431. {
  6432. sys_err ("item %d 's owner exists!",item->GetID());
  6433. return;
  6434. }
  6435.  
  6436. int cell;
  6437. if (item->IsDragonSoul())
  6438. {
  6439. cell = GetEmptyDragonSoulInventory(item);
  6440. }
  6441. else
  6442. {
  6443. cell = GetEmptyInventory (item->GetSize());
  6444. }
  6445.  
  6446. if (cell != -1)
  6447. {
  6448. if (item->IsDragonSoul())
  6449. item->AddToCharacter(this, TItemPos(DRAGON_SOUL_INVENTORY, cell));
  6450. else
  6451. item->AddToCharacter(this, TItemPos(INVENTORY, cell));
  6452.  
  6453. LogManager::instance().ItemLog(this, item, "SYSTEM", item->GetName());
  6454.  
  6455. if (item->GetType() == ITEM_USE && item->GetSubType() == USE_POTION)
  6456. {
  6457. TQuickslot * pSlot;
  6458.  
  6459. if (GetQuickslot(0, &pSlot) && pSlot->type == QUICKSLOT_TYPE_NONE)
  6460. {
  6461. TQuickslot slot;
  6462. slot.type = QUICKSLOT_TYPE_ITEM;
  6463. slot.pos = cell;
  6464. SetQuickslot(0, slot);
  6465. }
  6466. }
  6467. }
  6468. else
  6469. {
  6470. item->AddToGround (GetMapIndex(), GetXYZ());
  6471. item->StartDestroyEvent();
  6472.  
  6473. if (longOwnerShip)
  6474. item->SetOwnership (this, 300);
  6475. else
  6476. item->SetOwnership (this, 60);
  6477. LogManager::instance().ItemLog(this, item, "SYSTEM_DROP", item->GetName());
  6478. }
  6479. }
  6480.  
  6481. LPITEM CHARACTER::AutoGiveItem(DWORD dwItemVnum, BYTE bCount, int iRarePct, bool bMsg)
  6482. {
  6483. TItemTable * p = ITEM_MANAGER::instance().GetTable(dwItemVnum);
  6484.  
  6485. if (!p)
  6486. return NULL;
  6487.  
  6488. DBManager::instance().SendMoneyLog(MONEY_LOG_DROP, dwItemVnum, bCount);
  6489.  
  6490. if (p->dwFlags & ITEM_FLAG_STACKABLE && p->bType != ITEM_BLEND)
  6491. {
  6492. for (int i = 0; i < INVENTORY_MAX_NUM; ++i)
  6493. {
  6494. LPITEM item = GetInventoryItem(i);
  6495.  
  6496. if (!item)
  6497. continue;
  6498.  
  6499. if (item->GetVnum() == dwItemVnum && FN_check_item_socket(item))
  6500. {
  6501. if (IS_SET(p->dwFlags, ITEM_FLAG_MAKECOUNT))
  6502. {
  6503. if (bCount < p->alValues[1])
  6504. bCount = p->alValues[1];
  6505. }
  6506.  
  6507. BYTE bCount2 = MIN(200 - item->GetCount(), bCount);
  6508. bCount -= bCount2;
  6509.  
  6510. item->SetCount(item->GetCount() + bCount2);
  6511.  
  6512. if (bCount == 0)
  6513. {
  6514. if (bMsg)
  6515. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s"), item->GetName());
  6516.  
  6517. return item;
  6518. }
  6519. }
  6520. }
  6521. }
  6522.  
  6523. LPITEM item = ITEM_MANAGER::instance().CreateItem(dwItemVnum, bCount, 0, true);
  6524.  
  6525. if (!item)
  6526. {
  6527. sys_err("cannot create item by vnum %u (name: %s)", dwItemVnum, GetName());
  6528. return NULL;
  6529. }
  6530.  
  6531. if (item->GetType() == ITEM_BLEND)
  6532. {
  6533. for (int i=0; i < INVENTORY_MAX_NUM; i++)
  6534. {
  6535. LPITEM inv_item = GetInventoryItem(i);
  6536.  
  6537. if (inv_item == NULL) continue;
  6538.  
  6539. if (inv_item->GetType() == ITEM_BLEND)
  6540. {
  6541. if (inv_item->GetVnum() == item->GetVnum())
  6542. {
  6543. if (inv_item->GetSocket(0) == item->GetSocket(0) &&
  6544. inv_item->GetSocket(1) == item->GetSocket(1) &&
  6545. inv_item->GetSocket(2) == item->GetSocket(2) &&
  6546. inv_item->GetCount() < ITEM_MAX_COUNT)
  6547. {
  6548. inv_item->SetCount(inv_item->GetCount() + item->GetCount());
  6549. return inv_item;
  6550. }
  6551. }
  6552. }
  6553. }
  6554. }
  6555.  
  6556. int iEmptyCell;
  6557. if (item->IsDragonSoul())
  6558. {
  6559. iEmptyCell = GetEmptyDragonSoulInventory(item);
  6560. }
  6561. else
  6562. iEmptyCell = GetEmptyInventory(item->GetSize());
  6563.  
  6564. if (iEmptyCell != -1)
  6565. {
  6566. if (bMsg)
  6567. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆŔĚĹŰ Čąµć: %s"), item->GetName());
  6568.  
  6569. if (item->IsDragonSoul())
  6570. item->AddToCharacter(this, TItemPos(DRAGON_SOUL_INVENTORY, iEmptyCell));
  6571. else
  6572. item->AddToCharacter(this, TItemPos(INVENTORY, iEmptyCell));
  6573. LogManager::instance().ItemLog(this, item, "SYSTEM", item->GetName());
  6574.  
  6575. if (item->GetType() == ITEM_USE && item->GetSubType() == USE_POTION)
  6576. {
  6577. TQuickslot * pSlot;
  6578.  
  6579. if (GetQuickslot(0, &pSlot) && pSlot->type == QUICKSLOT_TYPE_NONE)
  6580. {
  6581. TQuickslot slot;
  6582. slot.type = QUICKSLOT_TYPE_ITEM;
  6583. slot.pos = iEmptyCell;
  6584. SetQuickslot(0, slot);
  6585. }
  6586. }
  6587. }
  6588. else
  6589. {
  6590. item->AddToGround(GetMapIndex(), GetXYZ());
  6591. item->StartDestroyEvent();
  6592. // ľČĆĽ µĺ¶ř flag°ˇ °É·ÁŔÖ´Â ľĆŔĚĹŰŔÇ °ćżě,
  6593. // ŔÎşĄżˇ şó °ř°ŁŔĚ ľřľîĽ­ ľîÂż Ľö ľřŔĚ ¶łľîĆ®¸®°Ô µÇ¸é,
  6594. // ownershipŔ» ľĆŔĚĹŰŔĚ »ç¶óÁú ¶§±îÁö(300ĂĘ) ŔŻÁöÇŃ´Ů.
  6595. if (IS_SET(item->GetAntiFlag(), ITEM_ANTIFLAG_DROP))
  6596. item->SetOwnership(this, 300);
  6597. else
  6598. item->SetOwnership(this, 60);
  6599. LogManager::instance().ItemLog(this, item, "SYSTEM_DROP", item->GetName());
  6600. }
  6601.  
  6602. sys_log(0,
  6603. "7: %d %d", dwItemVnum, bCount);
  6604. return item;
  6605. }
  6606.  
  6607. bool CHARACTER::GiveItem(LPCHARACTER victim, TItemPos Cell)
  6608. {
  6609. if (!CanHandleItem())
  6610. return false;
  6611.  
  6612. LPITEM item = GetItem(Cell);
  6613.  
  6614. if (item && !item->IsExchanging())
  6615. {
  6616. if (victim->CanReceiveItem(this, item))
  6617. {
  6618. victim->ReceiveItem(this, item);
  6619. return true;
  6620. }
  6621. }
  6622.  
  6623. return false;
  6624. }
  6625.  
  6626. bool CHARACTER::CanReceiveItem(LPCHARACTER from, LPITEM item) const
  6627. {
  6628. if (IsPC())
  6629. return false;
  6630.  
  6631. // TOO_LONG_DISTANCE_EXCHANGE_BUG_FIX
  6632. if (DISTANCE_APPROX(GetX() - from->GetX(), GetY() - from->GetY()) > 2000)
  6633. return false;
  6634. // END_OF_TOO_LONG_DISTANCE_EXCHANGE_BUG_FIX
  6635.  
  6636. switch (GetRaceNum())
  6637. {
  6638. case fishing::CAMPFIRE_MOB:
  6639. if (item->GetType() == ITEM_FISH &&
  6640. (item->GetSubType() == FISH_ALIVE || item->GetSubType() == FISH_DEAD))
  6641. return true;
  6642. break;
  6643.  
  6644. case fishing::FISHER_MOB:
  6645. if (item->GetType() == ITEM_ROD)
  6646. return true;
  6647. break;
  6648.  
  6649. // BUILDING_NPC
  6650. case BLACKSMITH_WEAPON_MOB:
  6651. case DEVILTOWER_BLACKSMITH_WEAPON_MOB:
  6652. if (item->GetType() == ITEM_WEAPON &&
  6653. item->GetRefinedVnum())
  6654. return true;
  6655. else
  6656. return false;
  6657. break;
  6658.  
  6659. case BLACKSMITH_ARMOR_MOB:
  6660. case DEVILTOWER_BLACKSMITH_ARMOR_MOB:
  6661. if (item->GetType() == ITEM_ARMOR &&
  6662. (item->GetSubType() == ARMOR_BODY || item->GetSubType() == ARMOR_SHIELD || item->GetSubType() == ARMOR_HEAD) &&
  6663. item->GetRefinedVnum())
  6664. return true;
  6665. else
  6666. return false;
  6667. break;
  6668.  
  6669. case BLACKSMITH_ACCESSORY_MOB:
  6670. case DEVILTOWER_BLACKSMITH_ACCESSORY_MOB:
  6671. if (item->GetType() == ITEM_ARMOR &&
  6672. !(item->GetSubType() == ARMOR_BODY || item->GetSubType() == ARMOR_SHIELD || item->GetSubType() == ARMOR_HEAD) &&
  6673. item->GetRefinedVnum())
  6674. return true;
  6675. else
  6676. return false;
  6677. break;
  6678. // END_OF_BUILDING_NPC
  6679.  
  6680. case BLACKSMITH_MOB:
  6681. if (item->GetRefinedVnum() && item->GetRefineSet() < 500)
  6682. {
  6683. return true;
  6684. }
  6685. else
  6686. {
  6687. return false;
  6688. }
  6689.  
  6690. case BLACKSMITH2_MOB:
  6691. if (item->GetRefineSet() >= 500)
  6692. {
  6693. return true;
  6694. }
  6695. else
  6696. {
  6697. return false;
  6698. }
  6699.  
  6700. case ALCHEMIST_MOB:
  6701. if (item->GetRefinedVnum())
  6702. return true;
  6703. break;
  6704.  
  6705. case 20101:
  6706. case 20102:
  6707. case 20103:
  6708. // ĂĘ±Ţ ¸»
  6709. if (item->GetVnum() == ITEM_REVIVE_HORSE_1)
  6710. {
  6711. if (!IsDead())
  6712. {
  6713. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Áö ľĘŔş ¸»żˇ°Ô Ľ±Ăʸ¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6714. return false;
  6715. }
  6716. return true;
  6717. }
  6718. else if (item->GetVnum() == ITEM_HORSE_FOOD_1)
  6719. {
  6720. if (IsDead())
  6721. {
  6722. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Ŕş ¸»żˇ°Ô »ç·á¸¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6723. return false;
  6724. }
  6725. return true;
  6726. }
  6727. else if (item->GetVnum() == ITEM_HORSE_FOOD_2 || item->GetVnum() == ITEM_HORSE_FOOD_3)
  6728. {
  6729. return false;
  6730. }
  6731. break;
  6732. case 20104:
  6733. case 20105:
  6734. case 20106:
  6735. // Áß±Ţ ¸»
  6736. if (item->GetVnum() == ITEM_REVIVE_HORSE_2)
  6737. {
  6738. if (!IsDead())
  6739. {
  6740. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Áö ľĘŔş ¸»żˇ°Ô Ľ±Ăʸ¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6741. return false;
  6742. }
  6743. return true;
  6744. }
  6745. else if (item->GetVnum() == ITEM_HORSE_FOOD_2)
  6746. {
  6747. if (IsDead())
  6748. {
  6749. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Ŕş ¸»żˇ°Ô »ç·á¸¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6750. return false;
  6751. }
  6752. return true;
  6753. }
  6754. else if (item->GetVnum() == ITEM_HORSE_FOOD_1 || item->GetVnum() == ITEM_HORSE_FOOD_3)
  6755. {
  6756. return false;
  6757. }
  6758. break;
  6759. case 20107:
  6760. case 20108:
  6761. case 20109:
  6762. // °í±Ţ ¸»
  6763. if (item->GetVnum() == ITEM_REVIVE_HORSE_3)
  6764. {
  6765. if (!IsDead())
  6766. {
  6767. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Áö ľĘŔş ¸»żˇ°Ô Ľ±Ăʸ¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6768. return false;
  6769. }
  6770. return true;
  6771. }
  6772. else if (item->GetVnum() == ITEM_HORSE_FOOD_3)
  6773. {
  6774. if (IsDead())
  6775. {
  6776. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Á×Ŕş ¸»żˇ°Ô »ç·á¸¦ ¸ÔŔĎ Ľö ľř˝Ŕ´Ď´Ů."));
  6777. return false;
  6778. }
  6779. return true;
  6780. }
  6781. else if (item->GetVnum() == ITEM_HORSE_FOOD_1 || item->GetVnum() == ITEM_HORSE_FOOD_2)
  6782. {
  6783. return false;
  6784. }
  6785. break;
  6786. }
  6787.  
  6788. //if (IS_SET(item->GetFlag(), ITEM_FLAG_QUEST_GIVE))
  6789. {
  6790. return true;
  6791. }
  6792.  
  6793. return false;
  6794. }
  6795.  
  6796. void CHARACTER::ReceiveItem(LPCHARACTER from, LPITEM item)
  6797. {
  6798. if (IsPC())
  6799. return;
  6800.  
  6801. switch (GetRaceNum())
  6802. {
  6803. case fishing::CAMPFIRE_MOB:
  6804. if (item->GetType() == ITEM_FISH && (item->GetSubType() == FISH_ALIVE || item->GetSubType() == FISH_DEAD))
  6805. fishing::Grill(from, item);
  6806. else
  6807. {
  6808. // TAKE_ITEM_BUG_FIX
  6809. from->SetQuestNPCID(GetVID());
  6810. // END_OF_TAKE_ITEM_BUG_FIX
  6811. quest::CQuestManager::instance().TakeItem(from->GetPlayerID(), GetRaceNum(), item);
  6812. }
  6813. break;
  6814.  
  6815. // DEVILTOWER_NPC
  6816. case DEVILTOWER_BLACKSMITH_WEAPON_MOB:
  6817. case DEVILTOWER_BLACKSMITH_ARMOR_MOB:
  6818. case DEVILTOWER_BLACKSMITH_ACCESSORY_MOB:
  6819. if (item->GetRefinedVnum() != 0 && item->GetRefineSet() != 0 && item->GetRefineSet() < 500)
  6820. {
  6821. from->SetRefineNPC(this);
  6822. from->RefineInformation(item->GetCell(), REFINE_TYPE_MONEY_ONLY);
  6823. }
  6824. else
  6825. {
  6826. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  6827. }
  6828. break;
  6829. // END_OF_DEVILTOWER_NPC
  6830.  
  6831. case BLACKSMITH_MOB:
  6832. case BLACKSMITH2_MOB:
  6833. case BLACKSMITH_WEAPON_MOB:
  6834. case BLACKSMITH_ARMOR_MOB:
  6835. case BLACKSMITH_ACCESSORY_MOB:
  6836. if (item->GetRefinedVnum())
  6837. {
  6838. from->SetRefineNPC(this);
  6839. from->RefineInformation(item->GetCell(), REFINE_TYPE_NORMAL);
  6840. }
  6841. else
  6842. {
  6843. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚ ľĆŔĚĹŰŔş °ł·®ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  6844. }
  6845. break;
  6846.  
  6847. case 20101:
  6848. case 20102:
  6849. case 20103:
  6850. case 20104:
  6851. case 20105:
  6852. case 20106:
  6853. case 20107:
  6854. case 20108:
  6855. case 20109:
  6856. if (item->GetVnum() == ITEM_REVIVE_HORSE_1 ||
  6857. item->GetVnum() == ITEM_REVIVE_HORSE_2 ||
  6858. item->GetVnum() == ITEM_REVIVE_HORSE_3)
  6859. {
  6860. from->ReviveHorse();
  6861. item->SetCount(item->GetCount()-1);
  6862. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸»żˇ°Ô Ľ±Ăʸ¦ ÁÖľú˝Ŕ´Ď´Ů."));
  6863. }
  6864. else if (item->GetVnum() == ITEM_HORSE_FOOD_1 ||
  6865. item->GetVnum() == ITEM_HORSE_FOOD_2 ||
  6866. item->GetVnum() == ITEM_HORSE_FOOD_3)
  6867. {
  6868. from->FeedHorse();
  6869. from->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("¸»żˇ°Ô »ç·á¸¦ ÁÖľú˝Ŕ´Ď´Ů."));
  6870. item->SetCount(item->GetCount()-1);
  6871. EffectPacket(SE_HPUP_RED);
  6872. }
  6873. break;
  6874.  
  6875. default:
  6876. sys_log(0, "TakeItem %s %d %s", from->GetName(), GetRaceNum(), item->GetName());
  6877. from->SetQuestNPCID(GetVID());
  6878. quest::CQuestManager::instance().TakeItem(from->GetPlayerID(), GetRaceNum(), item);
  6879. break;
  6880. }
  6881. }
  6882.  
  6883. bool CHARACTER::IsEquipUniqueItem(DWORD dwItemVnum) const
  6884. {
  6885. {
  6886. LPITEM u = GetWear(WEAR_UNIQUE1);
  6887.  
  6888. if (u && u->GetVnum() == dwItemVnum)
  6889. return true;
  6890. }
  6891.  
  6892. {
  6893. LPITEM u = GetWear(WEAR_UNIQUE2);
  6894.  
  6895. if (u && u->GetVnum() == dwItemVnum)
  6896. return true;
  6897. }
  6898.  
  6899. // ľđľîąÝÁöŔÎ °ćżě ľđľîąÝÁö(°ßş») ŔÎÁöµµ ĂĽĹ©ÇŃ´Ů.
  6900. if (dwItemVnum == UNIQUE_ITEM_RING_OF_LANGUAGE)
  6901. return IsEquipUniqueItem(UNIQUE_ITEM_RING_OF_LANGUAGE_SAMPLE);
  6902.  
  6903. return false;
  6904. }
  6905.  
  6906. // CHECK_UNIQUE_GROUP
  6907. bool CHARACTER::IsEquipUniqueGroup(DWORD dwGroupVnum) const
  6908. {
  6909. {
  6910. LPITEM u = GetWear(WEAR_UNIQUE1);
  6911.  
  6912. if (u && u->GetSpecialGroup() == (int) dwGroupVnum)
  6913. return true;
  6914. }
  6915.  
  6916. {
  6917. LPITEM u = GetWear(WEAR_UNIQUE2);
  6918.  
  6919. if (u && u->GetSpecialGroup() == (int) dwGroupVnum)
  6920. return true;
  6921. }
  6922.  
  6923. return false;
  6924. }
  6925. // END_OF_CHECK_UNIQUE_GROUP
  6926.  
  6927. void CHARACTER::SetRefineMode(int iAdditionalCell)
  6928. {
  6929. m_iRefineAdditionalCell = iAdditionalCell;
  6930. m_bUnderRefine = true;
  6931. }
  6932.  
  6933. void CHARACTER::ClearRefineMode()
  6934. {
  6935. m_bUnderRefine = false;
  6936. SetRefineNPC( NULL );
  6937. }
  6938.  
  6939. bool CHARACTER::GiveItemFromSpecialItemGroup(DWORD dwGroupNum, std::vector<DWORD> &dwItemVnums,
  6940. std::vector<DWORD> &dwItemCounts, std::vector <LPITEM> &item_gets, int &count)
  6941. {
  6942. const CSpecialItemGroup* pGroup = ITEM_MANAGER::instance().GetSpecialItemGroup(dwGroupNum);
  6943.  
  6944. if (!pGroup)
  6945. {
  6946. sys_err("cannot find special item group %d", dwGroupNum);
  6947. return false;
  6948. }
  6949.  
  6950. std::vector <int> idxes;
  6951. int n = pGroup->GetMultiIndex(idxes);
  6952.  
  6953. bool bSuccess;
  6954.  
  6955. for (int i = 0; i < n; i++)
  6956. {
  6957. bSuccess = false;
  6958. int idx = idxes[i];
  6959. DWORD dwVnum = pGroup->GetVnum(idx);
  6960. DWORD dwCount = pGroup->GetCount(idx);
  6961. int iRarePct = pGroup->GetRarePct(idx);
  6962. LPITEM item_get = NULL;
  6963. switch (dwVnum)
  6964. {
  6965. case CSpecialItemGroup::GOLD:
  6966. PointChange(POINT_GOLD, dwCount);
  6967. LogManager::instance().CharLog(this, dwCount, "TREASURE_GOLD", "");
  6968.  
  6969. bSuccess = true;
  6970. break;
  6971. case CSpecialItemGroup::EXP:
  6972. {
  6973. PointChange(POINT_EXP, dwCount);
  6974. LogManager::instance().CharLog(this, dwCount, "TREASURE_EXP", "");
  6975.  
  6976. bSuccess = true;
  6977. }
  6978. break;
  6979.  
  6980. case CSpecialItemGroup::MOB:
  6981. {
  6982. sys_log(0, "CSpecialItemGroup::MOB %d", dwCount);
  6983. int x = GetX() + number(-500, 500);
  6984. int y = GetY() + number(-500, 500);
  6985.  
  6986. LPCHARACTER ch = CHARACTER_MANAGER::instance().SpawnMob(dwCount, GetMapIndex(), x, y, 0, true, -1);
  6987. if (ch)
  6988. ch->SetAggressive();
  6989. bSuccess = true;
  6990. }
  6991. break;
  6992. case CSpecialItemGroup::SLOW:
  6993. {
  6994. sys_log(0, "CSpecialItemGroup::SLOW %d", -(int)dwCount);
  6995. AddAffect(AFFECT_SLOW, POINT_MOV_SPEED, -(int)dwCount, AFF_SLOW, 300, 0, true);
  6996. bSuccess = true;
  6997. }
  6998. break;
  6999. case CSpecialItemGroup::DRAIN_HP:
  7000. {
  7001. int iDropHP = GetMaxHP()*dwCount/100;
  7002. sys_log(0, "CSpecialItemGroup::DRAIN_HP %d", -iDropHP);
  7003. iDropHP = MIN(iDropHP, GetHP()-1);
  7004. sys_log(0, "CSpecialItemGroup::DRAIN_HP %d", -iDropHP);
  7005. PointChange(POINT_HP, -iDropHP);
  7006. bSuccess = true;
  7007. }
  7008. break;
  7009. case CSpecialItemGroup::POISON:
  7010. {
  7011. AttackedByPoison(NULL);
  7012. bSuccess = true;
  7013. }
  7014. break;
  7015.  
  7016. case CSpecialItemGroup::MOB_GROUP:
  7017. {
  7018. int sx = GetX() - number(300, 500);
  7019. int sy = GetY() - number(300, 500);
  7020. int ex = GetX() + number(300, 500);
  7021. int ey = GetY() + number(300, 500);
  7022. CHARACTER_MANAGER::instance().SpawnGroup(dwCount, GetMapIndex(), sx, sy, ex, ey, NULL, true);
  7023.  
  7024. bSuccess = true;
  7025. }
  7026. break;
  7027. default:
  7028. {
  7029. item_get = AutoGiveItem(dwVnum, dwCount, iRarePct);
  7030.  
  7031. if (item_get)
  7032. {
  7033. bSuccess = true;
  7034. }
  7035. }
  7036. break;
  7037. }
  7038.  
  7039. if (bSuccess)
  7040. {
  7041. dwItemVnums.push_back(dwVnum);
  7042. dwItemCounts.push_back(dwCount);
  7043. item_gets.push_back(item_get);
  7044. count++;
  7045.  
  7046. }
  7047. else
  7048. {
  7049. return false;
  7050. }
  7051. }
  7052. return bSuccess;
  7053. }
  7054.  
  7055. // NEW_HAIR_STYLE_ADD
  7056. bool CHARACTER::ItemProcess_Hair(LPITEM item, int iDestCell)
  7057. {
  7058. if (item->CheckItemUseLevel(GetLevel()) == false)
  7059. {
  7060. // ·ąş§ Á¦ÇŃżˇ °É¸˛
  7061. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ľĆÁ÷ ŔĚ ¸Ó¸®¸¦ »çżëÇŇ Ľö ľř´Â ·ąş§ŔÔ´Ď´Ů."));
  7062. return false;
  7063. }
  7064.  
  7065. DWORD hair = item->GetVnum();
  7066.  
  7067. switch (GetJob())
  7068. {
  7069. case JOB_WARRIOR :
  7070. hair -= 72000; // 73001 - 72000 = 1001 şÎĹÍ Çěľî ąřČŁ ˝ĂŔŰ
  7071. break;
  7072.  
  7073. case JOB_ASSASSIN :
  7074. hair -= 71250;
  7075. break;
  7076.  
  7077. case JOB_SURA :
  7078. hair -= 70500;
  7079. break;
  7080.  
  7081. case JOB_SHAMAN :
  7082. hair -= 69750;
  7083. break;
  7084.  
  7085. default :
  7086. return false;
  7087. break;
  7088. }
  7089.  
  7090. if (hair == GetPart(PART_HAIR))
  7091. {
  7092. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µżŔĎÇŃ ¸Ó¸® ˝şĹ¸ŔϷδ ±łĂĽÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7093. return true;
  7094. }
  7095.  
  7096. item->SetCount(item->GetCount() - 1);
  7097.  
  7098. SetPart(PART_HAIR, hair);
  7099. UpdatePacket();
  7100.  
  7101. return true;
  7102. }
  7103. // END_NEW_HAIR_STYLE_ADD
  7104.  
  7105. bool CHARACTER::ItemProcess_Polymorph(LPITEM item)
  7106. {
  7107. if (IsPolymorphed())
  7108. {
  7109. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ŔĚąĚ µĐ°©ÁßŔÎ »óĹÂŔÔ´Ď´Ů."));
  7110. return false;
  7111. }
  7112.  
  7113. if (true == IsRiding())
  7114. {
  7115. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µĐ°©ÇŇ Ľö ľř´Â »óĹÂŔÔ´Ď´Ů."));
  7116. return false;
  7117. }
  7118.  
  7119. DWORD dwVnum = item->GetSocket(0);
  7120.  
  7121. if (dwVnum == 0)
  7122. {
  7123. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕ߸řµČ µĐ°© ľĆŔĚĹŰŔÔ´Ď´Ů."));
  7124. item->SetCount(item->GetCount()-1);
  7125. return false;
  7126. }
  7127.  
  7128. const CMob* pMob = CMobManager::instance().Get(dwVnum);
  7129.  
  7130. if (pMob == NULL)
  7131. {
  7132. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Ŕ߸řµČ µĐ°© ľĆŔĚĹŰŔÔ´Ď´Ů."));
  7133. item->SetCount(item->GetCount()-1);
  7134. return false;
  7135. }
  7136.  
  7137. switch (item->GetVnum())
  7138. {
  7139. case 70104 :
  7140. case 70105 :
  7141. case 70106 :
  7142. case 70107 :
  7143. case 71093 :
  7144. {
  7145. // µĐ°©±¸ Ăł¸®
  7146. sys_log(0, "USE_POLYMORPH_BALL PID(%d) vnum(%d)", GetPlayerID(), dwVnum);
  7147.  
  7148. // ·ąş§ Á¦ÇŃ ĂĽĹ©
  7149. int iPolymorphLevelLimit = MAX(0, 20 - GetLevel() * 3 / 10);
  7150. if (pMob->m_table.bLevel >= GetLevel() + iPolymorphLevelLimit)
  7151. {
  7152. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("łŞş¸´Ů łĘą« łôŔş ·ąş§ŔÇ ¸ó˝şĹͷδ şŻ˝Ĺ ÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7153. return false;
  7154. }
  7155.  
  7156. int iDuration = GetSkillLevel(POLYMORPH_SKILL_ID) == 0 ? 5 : (5 + (5 + GetSkillLevel(POLYMORPH_SKILL_ID)/40 * 25));
  7157. iDuration *= 60;
  7158.  
  7159. DWORD dwBonus = 0;
  7160.  
  7161. if (true == LC_IsYMIR() || true == LC_IsKorea())
  7162. {
  7163. dwBonus = GetSkillLevel(POLYMORPH_SKILL_ID) + 60;
  7164. }
  7165. else
  7166. {
  7167. dwBonus = (2 + GetSkillLevel(POLYMORPH_SKILL_ID)/40) * 100;
  7168. }
  7169.  
  7170. AddAffect(AFFECT_POLYMORPH, POINT_POLYMORPH, dwVnum, AFF_POLYMORPH, iDuration, 0, true);
  7171. AddAffect(AFFECT_POLYMORPH, POINT_ATT_BONUS, dwBonus, AFF_POLYMORPH, iDuration, 0, false);
  7172.  
  7173. item->SetCount(item->GetCount()-1);
  7174. }
  7175. break;
  7176.  
  7177. case 50322:
  7178. {
  7179. // ş¸·ů
  7180.  
  7181. // µĐ°©Ľ­ Ăł¸®
  7182. // ĽŇÄĎ0 ĽŇÄĎ1 ĽŇÄĎ2
  7183. // µĐ°©ÇŇ ¸ó˝şĹÍ ąřČŁ Ľö·ĂÁ¤µµ µĐ°©Ľ­ ·ąş§
  7184. sys_log(0, "USE_POLYMORPH_BOOK: %s(%u) vnum(%u)", GetName(), GetPlayerID(), dwVnum);
  7185.  
  7186. if (CPolymorphUtils::instance().PolymorphCharacter(this, item, pMob) == true)
  7187. {
  7188. CPolymorphUtils::instance().UpdateBookPracticeGrade(this, item);
  7189. }
  7190. else
  7191. {
  7192. }
  7193. }
  7194. break;
  7195.  
  7196. default :
  7197. sys_err("POLYMORPH invalid item passed PID(%d) vnum(%d)", GetPlayerID(), item->GetOriginalVnum());
  7198. return false;
  7199. }
  7200.  
  7201. return true;
  7202. }
  7203.  
  7204. bool CHARACTER::CanDoCube() const
  7205. {
  7206. if (m_bIsObserver) return false;
  7207. if (GetShop()) return false;
  7208. if (GetMyShop()) return false;
  7209. if (m_bUnderRefine) return false;
  7210. if (IsWarping()) return false;
  7211.  
  7212. return true;
  7213. }
  7214.  
  7215. bool CHARACTER::UnEquipSpecialRideUniqueItem()
  7216. {
  7217. LPITEM Unique1 = GetWear(WEAR_UNIQUE1);
  7218. LPITEM Unique2 = GetWear(WEAR_UNIQUE2);
  7219.  
  7220. if( NULL != Unique1 )
  7221. {
  7222. if( UNIQUE_GROUP_SPECIAL_RIDE == Unique1->GetSpecialGroup() )
  7223. {
  7224. return UnequipItem(Unique1);
  7225. }
  7226. }
  7227.  
  7228. if( NULL != Unique2 )
  7229. {
  7230. if( UNIQUE_GROUP_SPECIAL_RIDE == Unique2->GetSpecialGroup() )
  7231. {
  7232. return UnequipItem(Unique2);
  7233. }
  7234. }
  7235.  
  7236. return true;
  7237. }
  7238.  
  7239. void CHARACTER::AutoRecoveryItemProcess(const EAffectTypes type)
  7240. {
  7241. if (true == IsDead() || true == IsStun())
  7242. return;
  7243.  
  7244. if (false == IsPC())
  7245. return;
  7246.  
  7247. if (AFFECT_AUTO_HP_RECOVERY != type && AFFECT_AUTO_SP_RECOVERY != type)
  7248. return;
  7249.  
  7250. if (NULL != FindAffect(AFFECT_STUN))
  7251. return;
  7252.  
  7253. {
  7254. const DWORD stunSkills[] = { SKILL_TANHWAN, SKILL_GEOMPUNG, SKILL_BYEURAK, SKILL_GIGUNG };
  7255.  
  7256. for (size_t i=0 ; i < sizeof(stunSkills)/sizeof(DWORD) ; ++i)
  7257. {
  7258. const CAffect* p = FindAffect(stunSkills[i]);
  7259.  
  7260. if (NULL != p && AFF_STUN == p->dwFlag)
  7261. return;
  7262. }
  7263. }
  7264.  
  7265. const CAffect* pAffect = FindAffect(type);
  7266. const size_t idx_of_amount_of_used = 1;
  7267. const size_t idx_of_amount_of_full = 2;
  7268.  
  7269. if (NULL != pAffect)
  7270. {
  7271. LPITEM pItem = FindItemByID(pAffect->dwFlag);
  7272.  
  7273. if (NULL != pItem && true == pItem->GetSocket(0))
  7274. {
  7275. if (false == CArenaManager::instance().IsArenaMap(GetMapIndex()))
  7276. {
  7277. const long amount_of_used = pItem->GetSocket(idx_of_amount_of_used);
  7278. const long amount_of_full = pItem->GetSocket(idx_of_amount_of_full);
  7279.  
  7280. const int32_t avail = amount_of_full - amount_of_used;
  7281.  
  7282. int32_t amount = 0;
  7283.  
  7284. if (AFFECT_AUTO_HP_RECOVERY == type)
  7285. {
  7286. amount = GetMaxHP() - (GetHP() + GetPoint(POINT_HP_RECOVERY));
  7287. }
  7288. else if (AFFECT_AUTO_SP_RECOVERY == type)
  7289. {
  7290. amount = GetMaxSP() - (GetSP() + GetPoint(POINT_SP_RECOVERY));
  7291. }
  7292.  
  7293. if (amount > 0)
  7294. {
  7295. if (avail > amount)
  7296. {
  7297. const int pct_of_used = amount_of_used * 100 / amount_of_full;
  7298. const int pct_of_will_used = (amount_of_used + amount) * 100 / amount_of_full;
  7299.  
  7300. bool bLog = false;
  7301. // »çżë·®ŔÇ 10% ´ÜŔ§·Î ·Î±×¸¦ ł˛±č
  7302. // (»çżë·®ŔÇ %żˇĽ­, ˝ĘŔÇ ŔÚ¸®°ˇ ąŮ˛đ ¶§¸¶´Ů ·Î±×¸¦ ł˛±č.)
  7303. if ((pct_of_will_used / 10) - (pct_of_used / 10) >= 1)
  7304. bLog = true;
  7305. pItem->SetSocket(idx_of_amount_of_used, amount_of_used + amount, bLog);
  7306. }
  7307. else
  7308. {
  7309. amount = avail;
  7310.  
  7311. ITEM_MANAGER::instance().RemoveItem( pItem );
  7312. }
  7313.  
  7314. if (AFFECT_AUTO_HP_RECOVERY == type)
  7315. {
  7316. PointChange( POINT_HP_RECOVERY, amount );
  7317. EffectPacket( SE_AUTO_HPUP );
  7318. }
  7319. else if (AFFECT_AUTO_SP_RECOVERY == type)
  7320. {
  7321. PointChange( POINT_SP_RECOVERY, amount );
  7322. EffectPacket( SE_AUTO_SPUP );
  7323. }
  7324. }
  7325. }
  7326. else
  7327. {
  7328. pItem->Lock(false);
  7329. pItem->SetSocket(0, false);
  7330. RemoveAffect( const_cast<CAffect*>(pAffect) );
  7331. }
  7332. }
  7333. else
  7334. {
  7335. RemoveAffect( const_cast<CAffect*>(pAffect) );
  7336. }
  7337. }
  7338. }
  7339.  
  7340. bool CHARACTER::IsValidItemPosition(TItemPos Pos) const
  7341. {
  7342. BYTE window_type = Pos.window_type;
  7343. WORD cell = Pos.cell;
  7344.  
  7345. switch (window_type)
  7346. {
  7347. case RESERVED_WINDOW:
  7348. return false;
  7349.  
  7350. case INVENTORY:
  7351. case EQUIPMENT:
  7352. return cell < (INVENTORY_AND_EQUIP_SLOT_MAX);
  7353.  
  7354. case DRAGON_SOUL_INVENTORY:
  7355. return cell < (DRAGON_SOUL_INVENTORY_MAX_NUM);
  7356.  
  7357. case SAFEBOX:
  7358. if (NULL != m_pkSafebox)
  7359. return m_pkSafebox->IsValidPosition(cell);
  7360. else
  7361. return false;
  7362.  
  7363. case MALL:
  7364. if (NULL != m_pkMall)
  7365. return m_pkMall->IsValidPosition(cell);
  7366. else
  7367. return false;
  7368. default:
  7369. return false;
  7370. }
  7371. }
  7372.  
  7373.  
  7374. // ±ÍÂúľĆĽ­ ¸¸µç ¸ĹĹ©·Î.. exp°ˇ true¸é msg¸¦ Ăâ·ÂÇĎ°í return false ÇĎ´Â ¸ĹĹ©·Î (ŔĎąÝŔűŔÎ verify żëµµ¶űŔş return ¶§ą®żˇ ľŕ°Ł ąÝ´ë¶ó Ŕ̸§¶§ą®żˇ Çň°Ą¸± Ľöµµ ŔÖ°Ú´Ů..)
  7375. #define VERIFY_MSG(exp, msg) \
  7376. if (true == (exp)) { \
  7377. ChatPacket(CHAT_TYPE_INFO, LC_TEXT(msg)); \
  7378. return false; \
  7379. }
  7380.  
  7381.  
  7382. /// ÇöŔç Äł¸ŻĹÍŔÇ »óŸ¦ ąŮĹÁŔ¸·Î ÁÖľîÁř itemŔ» ÂřżëÇŇ Ľö ŔÖ´Â Áö Č®ŔÎÇĎ°í, şŇ°ˇ´É Çϴٸé Äł¸ŻĹÍżˇ°Ô ŔĚŔŻ¸¦ ľË·ÁÁÖ´Â ÇÔĽö
  7383. bool CHARACTER::CanEquipNow(const LPITEM item, const TItemPos& srcCell, const TItemPos& destCell) /*const*/
  7384. {
  7385. const TItemTable* itemTable = item->GetProto();
  7386. BYTE itemType = item->GetType();
  7387. BYTE itemSubType = item->GetSubType();
  7388.  
  7389. switch (GetJob())
  7390. {
  7391. case JOB_WARRIOR:
  7392. if (item->GetAntiFlag() & ITEM_ANTIFLAG_WARRIOR)
  7393. return false;
  7394. break;
  7395.  
  7396. case JOB_ASSASSIN:
  7397. if (item->GetAntiFlag() & ITEM_ANTIFLAG_ASSASSIN)
  7398. return false;
  7399. break;
  7400.  
  7401. case JOB_SHAMAN:
  7402. if (item->GetAntiFlag() & ITEM_ANTIFLAG_SHAMAN)
  7403. return false;
  7404. break;
  7405.  
  7406. case JOB_SURA:
  7407. if (item->GetAntiFlag() & ITEM_ANTIFLAG_SURA)
  7408. return false;
  7409. break;
  7410. }
  7411.  
  7412. for (int i = 0; i < ITEM_LIMIT_MAX_NUM; ++i)
  7413. {
  7414. long limit = itemTable->aLimits[i].lValue;
  7415. switch (itemTable->aLimits[i].bType)
  7416. {
  7417. case LIMIT_LEVEL:
  7418. if (GetLevel() < limit)
  7419. {
  7420. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("·ąş§ŔĚ ł·ľĆ ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7421. return false;
  7422. }
  7423. break;
  7424.  
  7425. case LIMIT_STR:
  7426. if (GetPoint(POINT_ST) < limit)
  7427. {
  7428. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("±Ů·ÂŔĚ ł·ľĆ ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7429. return false;
  7430. }
  7431. break;
  7432.  
  7433. case LIMIT_INT:
  7434. if (GetPoint(POINT_IQ) < limit)
  7435. {
  7436. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Áö´ÉŔĚ ł·ľĆ ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7437. return false;
  7438. }
  7439. break;
  7440.  
  7441. case LIMIT_DEX:
  7442. if (GetPoint(POINT_DX) < limit)
  7443. {
  7444. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ąÎøŔĚ ł·ľĆ ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7445. return false;
  7446. }
  7447. break;
  7448.  
  7449. case LIMIT_CON:
  7450. if (GetPoint(POINT_HT) < limit)
  7451. {
  7452. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĂĽ·ÂŔĚ ł·ľĆ ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7453. return false;
  7454. }
  7455. break;
  7456. }
  7457. }
  7458.  
  7459. if (item->GetWearFlag() & WEARABLE_UNIQUE)
  7460. {
  7461. if ((GetWear(WEAR_UNIQUE1) && GetWear(WEAR_UNIQUE1)->IsSameSpecialGroup(item)) ||
  7462. (GetWear(WEAR_UNIQUE2) && GetWear(WEAR_UNIQUE2)->IsSameSpecialGroup(item)))
  7463. {
  7464. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°°Ŕş Áľ·ůŔÇ ŔŻ´ĎĹ© ľĆŔĚĹŰ µÎ °ł¸¦ µż˝Ăżˇ ŔĺÂřÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7465. return false;
  7466. }
  7467.  
  7468. if (marriage::CManager::instance().IsMarriageUniqueItem(item->GetVnum()) &&
  7469. !marriage::CManager::instance().IsMarried(GetPlayerID()))
  7470. {
  7471. ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°áČĄÇĎÁö ľĘŔş »óĹÂżˇĽ­ żąą°Ŕ» ÂřżëÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  7472. return false;
  7473. }
  7474.  
  7475. }
  7476.  
  7477. return true;
  7478. }
  7479.  
  7480. /// ÇöŔç Äł¸ŻĹÍŔÇ »óŸ¦ ąŮĹÁŔ¸·Î Âřżë ÁßŔÎ itemŔ» ąţŔ» Ľö ŔÖ´Â Áö Č®ŔÎÇĎ°í, şŇ°ˇ´É Çϴٸé Äł¸ŻĹÍżˇ°Ô ŔĚŔŻ¸¦ ľË·ÁÁÖ´Â ÇÔĽö
  7481. bool CHARACTER::CanUnequipNow(const LPITEM item, const TItemPos& srcCell, const TItemPos& destCell) /*const*/
  7482. {
  7483.  
  7484. if (ITEM_BELT == item->GetType())
  7485. VERIFY_MSG(CBeltInventoryHelper::IsExistItemInBeltInventory(this), "ş§Ć® ŔÎşĄĹ丮żˇ ľĆŔĚĹŰŔĚ Á¸ŔçÇϸé ÇŘÁ¦ÇŇ Ľö ľř˝Ŕ´Ď´Ů.");
  7486.  
  7487. // żµżřČ÷ ÇŘÁ¦ÇŇ Ľö ľř´Â ľĆŔĚĹŰ
  7488. if (IS_SET(item->GetFlag(), ITEM_FLAG_IRREMOVABLE))
  7489. return false;
  7490.  
  7491. // ľĆŔĚĹŰ unequip˝Ă ŔÎşĄĹ丮·Î żĹ±ć ¶§ şó ŔÚ¸®°ˇ ŔÖ´Â Áö Č®ŔÎ
  7492. {
  7493. int pos = -1;
  7494.  
  7495. if (item->IsDragonSoul())
  7496. pos = GetEmptyDragonSoulInventory(item);
  7497. else
  7498. pos = GetEmptyInventory(item->GetSize());
  7499.  
  7500. VERIFY_MSG( -1 == pos, "ĽŇÁöÇ°żˇ şó °ř°ŁŔĚ ľř˝Ŕ´Ď´Ů." );
  7501. }
  7502.  
  7503.  
  7504. return true;
  7505. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement