eri000n

Untitled

Apr 5th, 2023
57
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 34.05 KB | None | 0 0
  1. #include "stdafx.h"
  2. #include "constants.h"
  3. #include "item.h"
  4. #include "item_manager.h"
  5. #include "unique_item.h"
  6. #include "packet.h"
  7. #include "desc.h"
  8. #include "char.h"
  9. #include "dragon_soul_table.h"
  10. #include "log.h"
  11. #include "DragonSoul.h"
  12. #include <boost/lexical_cast.hpp>
  13.  
  14. typedef std::vector <std::string> TTokenVector;
  15. template <typename T> T MINMAX(T min, T value, T max)
  16. {
  17. T tv;
  18.  
  19. tv = (min > value ? min : value);
  20. return (max < tv) ? max : tv;
  21. }
  22. int Gamble(std::vector<float>& vec_probs)
  23. {
  24. float range = 0.f;
  25. for (int i = 0; i < vec_probs.size(); i++)
  26. {
  27. range += vec_probs[i];
  28. }
  29. float fProb = fnumber(0.f, range);
  30. float sum = 0.f;
  31. for (int idx = 0; idx < vec_probs.size(); idx++)
  32. {
  33. sum += vec_probs[idx];
  34. if (sum >= fProb)
  35. return idx;
  36. }
  37. return -1;
  38. }
  39.  
  40. // °ˇÁßġ Ĺ×ŔĚşí(prob_lst)Ŕ» ąŢľĆ random_set.size()°łŔÇ index¸¦ Ľ±ĹĂÇĎż© random_setŔ» return
  41. bool MakeDistinctRandomNumberSet(std::list <float> prob_lst, OUT std::vector<int>& random_set)
  42. {
  43. int size = prob_lst.size();
  44. int n = random_set.size();
  45. if (size < n)
  46. return false;
  47.  
  48. std::vector <int> select_bit(size, 0);
  49. for (int i = 0; i < n; i++)
  50. {
  51. float range = 0.f;
  52. for (std::list <float>::iterator it = prob_lst.begin(); it != prob_lst.end(); it++)
  53. {
  54. range += *it;
  55. }
  56. float r = fnumber (0.f, range);
  57. float sum = 0.f;
  58. int idx = 0;
  59. for (std::list <float>::iterator it = prob_lst.begin(); it != prob_lst.end(); it++)
  60. {
  61. while (select_bit[idx++]);
  62.  
  63. sum += *it;
  64. if (sum >= r)
  65. {
  66. select_bit[idx - 1] = 1;
  67. random_set[i] = idx - 1;
  68. prob_lst.erase(it);
  69. break;
  70. }
  71. }
  72. }
  73. return true;
  74. }
  75.  
  76. /* żëČĄĽ® Vnumżˇ ´ëÇŃ comment
  77. * ITEM VNUMŔ» 10¸¸ ŔÚ¸®şÎĹÍ, FEDCBA¶ó°í ÇѴٸé
  78. * FE : żëČĄĽ® Áľ·ů. D : µî±Ţ
  79. * C : ´Ü°č B : °­Č­
  80. * A : ż©ąúŔÇ ąřČŁµé...
  81. */
  82.  
  83. BYTE GetType(DWORD dwVnum)
  84. {
  85. return (dwVnum / 10000);
  86. }
  87.  
  88. BYTE GetGradeIdx(DWORD dwVnum)
  89. {
  90. return (dwVnum / 1000) % 10;
  91. }
  92.  
  93. BYTE GetStepIdx(DWORD dwVnum)
  94. {
  95. return (dwVnum / 100) % 10;
  96. }
  97.  
  98. BYTE GetStrengthIdx(DWORD dwVnum)
  99. {
  100. return (dwVnum / 10) % 10;
  101. }
  102.  
  103. bool DSManager::ReadDragonSoulTableFile(const char * c_pszFileName)
  104. {
  105. m_pTable = new DragonSoulTable();
  106. return m_pTable->ReadDragonSoulTableFile(c_pszFileName);
  107. }
  108.  
  109. void DSManager::GetDragonSoulInfo(DWORD dwVnum, BYTE& bType, BYTE& bGrade, BYTE& bStep, BYTE& bStrength) const
  110. {
  111. bType = GetType(dwVnum);
  112. bGrade = GetGradeIdx(dwVnum);
  113. bStep = GetStepIdx(dwVnum);
  114. bStrength = GetStrengthIdx(dwVnum);
  115. }
  116.  
  117. bool DSManager::IsValidCellForThisItem(const LPITEM pItem, const TItemPos& Cell) const
  118. {
  119. if (NULL == pItem)
  120. return false;
  121.  
  122. WORD wBaseCell = GetBasePosition(pItem);
  123. if (WORD_MAX == wBaseCell)
  124. return false;
  125.  
  126. if (Cell.window_type != DRAGON_SOUL_INVENTORY
  127. || (Cell.cell < wBaseCell || Cell.cell >= wBaseCell + DRAGON_SOUL_BOX_SIZE))
  128. {
  129. return false;
  130. }
  131. else
  132. return true;
  133.  
  134. }
  135.  
  136. WORD DSManager::GetBasePosition(const LPITEM pItem) const
  137. {
  138. if (NULL == pItem)
  139. return WORD_MAX;
  140.  
  141. BYTE type, grade_idx, step_idx, strength_idx;
  142. GetDragonSoulInfo(pItem->GetVnum(), type, grade_idx, step_idx, strength_idx);
  143.  
  144. BYTE col_type = pItem->GetSubType();
  145. BYTE row_type = grade_idx;
  146. if (row_type > DRAGON_SOUL_GRADE_MAX)
  147. return WORD_MAX;
  148.  
  149. return col_type * DRAGON_SOUL_STEP_MAX * DRAGON_SOUL_BOX_SIZE + row_type * DRAGON_SOUL_BOX_SIZE;
  150. }
  151.  
  152. bool DSManager::RefreshItemAttributes(LPITEM pDS)
  153. {
  154. if (!pDS->IsDragonSoul())
  155. {
  156. sys_err ("This item(ID : %d) is not DragonSoul.", pDS->GetID());
  157. return false;
  158. }
  159.  
  160. BYTE ds_type, grade_idx, step_idx, strength_idx;
  161. GetDragonSoulInfo(pDS->GetVnum(), ds_type, grade_idx, step_idx, strength_idx);
  162.  
  163. DragonSoulTable::TVecApplys vec_basic_applys;
  164. DragonSoulTable::TVecApplys vec_addtional_applys;
  165.  
  166. if (!m_pTable->GetBasicApplys(ds_type, vec_basic_applys))
  167. {
  168. sys_err ("There is no BasicApply about %d type dragon soul.", ds_type);
  169. return false;
  170. }
  171.  
  172. if (!m_pTable->GetAdditionalApplys(ds_type, vec_addtional_applys))
  173. {
  174. sys_err ("There is no AdditionalApply about %d type dragon soul.", ds_type);
  175. return false;
  176. }
  177.  
  178. // add_min°ú add_max´Â ´őąĚ·Î ŔĐŔ˝.
  179. int basic_apply_num, add_min, add_max;
  180. if (!m_pTable->GetApplyNumSettings(ds_type, grade_idx, basic_apply_num, add_min, add_max))
  181. {
  182. sys_err ("In ApplyNumSettings, INVALID VALUES Group type(%d), GRADE idx(%d)", ds_type, grade_idx);
  183. return false;
  184. }
  185.  
  186. float fWeight = 0.f;
  187. if (!m_pTable->GetWeight(ds_type, grade_idx, step_idx, strength_idx, fWeight))
  188. {
  189. return false;
  190. }
  191. fWeight /= 100.f;
  192.  
  193. int n = MIN(basic_apply_num, vec_basic_applys.size());
  194. for (int i = 0; i < n; i++)
  195. {
  196. const SApply& basic_apply = vec_basic_applys[i];
  197. BYTE bType = basic_apply.apply_type;
  198. short sValue = (short)(ceil((float)basic_apply.apply_value * fWeight - 0.01f));
  199.  
  200. pDS->SetForceAttribute(i, bType, sValue);
  201. }
  202.  
  203. for (int i = DRAGON_SOUL_ADDITIONAL_ATTR_START_IDX; i < ITEM_ATTRIBUTE_MAX_NUM; i++)
  204. {
  205. BYTE bType = pDS->GetAttributeType(i);
  206. short sValue = 0;
  207. if (APPLY_NONE == bType)
  208. continue;
  209. for (int j = 0; j < vec_addtional_applys.size(); j++)
  210. {
  211. if (vec_addtional_applys[j].apply_type == bType)
  212. {
  213. sValue = vec_addtional_applys[j].apply_value;
  214. break;
  215. }
  216. }
  217. pDS->SetForceAttribute(i, bType, (short)(ceil((float)sValue * fWeight - 0.01f)));
  218. }
  219. return true;
  220. }
  221.  
  222. bool DSManager::PutAttributes(LPITEM pDS)
  223. {
  224. if (!pDS->IsDragonSoul())
  225. {
  226. sys_err ("This item(ID : %d) is not DragonSoul.", pDS->GetID());
  227. return false;
  228. }
  229.  
  230. BYTE ds_type, grade_idx, step_idx, strength_idx;
  231. GetDragonSoulInfo(pDS->GetVnum(), ds_type, grade_idx, step_idx, strength_idx);
  232.  
  233. DragonSoulTable::TVecApplys vec_basic_applys;
  234. DragonSoulTable::TVecApplys vec_addtional_applys;
  235.  
  236. if (!m_pTable->GetBasicApplys(ds_type, vec_basic_applys))
  237. {
  238. sys_err ("There is no BasicApply about %d type dragon soul.", ds_type);
  239. return false;
  240. }
  241. if (!m_pTable->GetAdditionalApplys(ds_type, vec_addtional_applys))
  242. {
  243. sys_err ("There is no AdditionalApply about %d type dragon soul.", ds_type);
  244. return false;
  245. }
  246.  
  247.  
  248. int basic_apply_num, add_min, add_max;
  249. if (!m_pTable->GetApplyNumSettings(ds_type, grade_idx, basic_apply_num, add_min, add_max))
  250. {
  251. sys_err ("In ApplyNumSettings, INVALID VALUES Group type(%d), GRADE idx(%d)", ds_type, grade_idx);
  252. return false;
  253. }
  254.  
  255. float fWeight = 0.f;
  256. if (!m_pTable->GetWeight(ds_type, grade_idx, step_idx, strength_idx, fWeight))
  257. {
  258. return false;
  259. }
  260. fWeight /= 100.f;
  261.  
  262. int n = MIN(basic_apply_num, vec_basic_applys.size());
  263. for (int i = 0; i < n; i++)
  264. {
  265. const SApply& basic_apply = vec_basic_applys[i];
  266. BYTE bType = basic_apply.apply_type;
  267. short sValue = (short)(ceil((float)basic_apply.apply_value * fWeight - 0.01f));
  268.  
  269. pDS->SetForceAttribute(i, bType, sValue);
  270. }
  271.  
  272. BYTE additional_attr_num = MIN(number (add_min, add_max), 3);
  273.  
  274. std::vector <int> random_set;
  275. if (additional_attr_num > 0)
  276. {
  277. random_set.resize(additional_attr_num);
  278. std::list <float> list_probs;
  279. for (int i = 0; i < vec_addtional_applys.size(); i++)
  280. {
  281. list_probs.push_back(vec_addtional_applys[i].prob);
  282. }
  283. if (!MakeDistinctRandomNumberSet(list_probs, random_set))
  284. {
  285. sys_err ("MakeDistinctRandomNumberSet error.");
  286. return false;
  287. }
  288.  
  289. for (int i = 0; i < additional_attr_num; i++)
  290. {
  291. int r = random_set[i];
  292. const SApply& additional_attr = vec_addtional_applys[r];
  293. BYTE bType = additional_attr.apply_type;
  294. short sValue = (short)(ceil((float)additional_attr.apply_value * fWeight - 0.01f));
  295.  
  296. pDS->SetForceAttribute(DRAGON_SOUL_ADDITIONAL_ATTR_START_IDX + i, bType, sValue);
  297. }
  298. }
  299.  
  300. return true;
  301. }
  302.  
  303. bool DSManager::DragonSoulItemInitialize(LPITEM pItem)
  304. {
  305. if (NULL == pItem || !pItem->IsDragonSoul())
  306. return false;
  307. PutAttributes(pItem);
  308. int time = DSManager::instance().GetDuration(pItem);
  309. if (time > 0)
  310. pItem->SetSocket(ITEM_SOCKET_REMAIN_SEC, time);
  311. return true;
  312. }
  313.  
  314. DWORD DSManager::MakeDragonSoulVnum(BYTE bType, BYTE grade, BYTE step, BYTE refine)
  315. {
  316. return bType * 10000 + grade * 1000 + step * 100 + refine * 10;
  317. }
  318.  
  319. int DSManager::GetDuration(const LPITEM pItem) const
  320. {
  321. return pItem->GetDuration();
  322. }
  323.  
  324. // żëČĄĽ®Ŕ» ąŢľĆĽ­ żë˝ÉŔ» ĂßĂâÇĎ´Â ÇÔĽö
  325. bool DSManager::ExtractDragonHeart(LPCHARACTER ch, LPITEM pItem, LPITEM pExtractor)
  326. {
  327. if (NULL == ch || NULL == pItem)
  328. return false;
  329. if (pItem->IsEquipped())
  330. {
  331. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("Âřżë ÁßŔÎ żëČĄĽ®Ŕş ĂßĂâÇŇ Ľö ľř˝Ŕ´Ď´Ů."));
  332. return false;
  333. }
  334.  
  335. DWORD dwVnum = pItem->GetVnum();
  336. BYTE ds_type, grade_idx, step_idx, strength_idx;
  337. GetDragonSoulInfo(dwVnum, ds_type, grade_idx, step_idx, strength_idx);
  338.  
  339. int iBonus = 0;
  340.  
  341. if (NULL != pExtractor)
  342. {
  343. iBonus = pExtractor->GetValue(0);
  344. }
  345.  
  346. std::vector <float> vec_chargings;
  347. std::vector <float> vec_probs;
  348.  
  349. if (!m_pTable->GetDragonHeartExtValues(ds_type, grade_idx, vec_chargings, vec_probs))
  350. {
  351. return false;
  352. }
  353.  
  354. int idx = Gamble(vec_probs);
  355.  
  356. float sum = 0.f;
  357. if (-1 == idx)
  358. {
  359. sys_err ("Gamble is failed. ds_type(%d), grade_idx(%d)", ds_type, grade_idx);
  360. return false;
  361. }
  362.  
  363. float fCharge = vec_chargings[idx] * (100 + iBonus) / 100.f;
  364. fCharge = MINMAX <float> (0.f, fCharge, 100.f);
  365.  
  366. if (fCharge < FLT_EPSILON)
  367. {
  368. pItem->SetCount(pItem->GetCount() - 1);
  369. if (NULL != pExtractor)
  370. {
  371. pExtractor->SetCount(pExtractor->GetCount() - 1);
  372. }
  373. LogManager::instance().ItemLog(ch, pItem, "DS_HEART_EXTRACT_FAIL", "");
  374.  
  375. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żë˝É ĂßĂ⿡ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  376. return false;
  377. }
  378. else
  379. {
  380. LPITEM pDH = ITEM_MANAGER::instance().CreateItem(DRAGON_HEART_VNUM);
  381.  
  382. if (NULL == pDH)
  383. {
  384. sys_err ("Cannot create DRAGON_HEART(%d).", DRAGON_HEART_VNUM);
  385. return NULL;
  386. }
  387.  
  388. pItem->SetCount(pItem->GetCount() - 1);
  389. if (NULL != pExtractor)
  390. {
  391. pExtractor->SetCount(pExtractor->GetCount() - 1);
  392. }
  393.  
  394. int iCharge = (int)(fCharge + 0.5f);
  395. pDH->SetSocket(ITEM_SOCKET_CHARGING_AMOUNT_IDX, iCharge);
  396. ch->AutoGiveItem(pDH, true);
  397.  
  398. std::string s = boost::lexical_cast <std::string> (iCharge);
  399. s += "%s";
  400. LogManager::instance().ItemLog(ch, pItem, "DS_HEART_EXTRACT_SUCCESS", s.c_str());
  401. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żë˝É ĂßĂ⿡ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  402. return true;
  403. }
  404. }
  405.  
  406. // ĆŻÁ¤ żëČĄĽ®Ŕ» Ŕĺşń⿡Ľ­ Á¦°ĹÇŇ ¶§żˇ Ľş°ř ż©şÎ¸¦ °áÁ¤Çϰí, ˝ÇĆнà şÎ»ęą°Ŕ» ÁÖ´Â ÇÔĽö.
  407. bool DSManager::PullOut(LPCHARACTER ch, TItemPos DestCell, LPITEM& pItem, LPITEM pExtractor)
  408. {
  409. if (NULL == ch || NULL == pItem)
  410. {
  411. sys_err ("NULL POINTER. ch(%p) or pItem(%p)", ch, pItem);
  412. return false;
  413. }
  414.  
  415. // ¸ńÇĄ Ŕ§Äˇ°ˇ validÇŃÁö °Ë»ç ČÄ, validÇĎÁö ľĘ´Ů¸é ŔÓŔÇŔÇ şó °ř°ŁŔ» ĂŁ´Â´Ů.
  416. if (!IsValidCellForThisItem(pItem, DestCell))
  417. {
  418. int iEmptyCell = ch->GetEmptyDragonSoulInventory(pItem);
  419. if (iEmptyCell < 0)
  420. {
  421. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("ĽŇÁöǰżˇ şó °ř°ŁŔĚ ľř˝Ŕ´Ď´Ů."));
  422. return false;
  423. }
  424. else
  425. {
  426. DestCell.window_type = DRAGON_SOUL_INVENTORY;
  427. DestCell.cell = iEmptyCell;
  428. }
  429. }
  430.  
  431. if (!pItem->IsEquipped() || !pItem->RemoveFromCharacter())
  432. return false;
  433.  
  434. bool bSuccess;
  435. DWORD dwByProduct = 0;
  436. int iBonus = 0;
  437. float fProb;
  438. float fDice;
  439. // żëČĄĽ® ĂßĂâ Ľş°ř ż©şÎ °áÁ¤.
  440. {
  441. DWORD dwVnum = pItem->GetVnum();
  442.  
  443. BYTE ds_type, grade_idx, step_idx, strength_idx;
  444. GetDragonSoulInfo(pItem->GetVnum(), ds_type, grade_idx, step_idx, strength_idx);
  445.  
  446. // ĂßĂâ Á¤ş¸°ˇ ľř´Ů¸é ŔĎ´Ü ą«Á¶°Ç Ľş°řÇĎ´Â °ÍŔ̶ó »ý°˘ÇĎŔÚ.
  447. if (!m_pTable->GetDragonSoulExtValues(ds_type, grade_idx, fProb, dwByProduct))
  448. {
  449. pItem->AddToCharacter(ch, DestCell);
  450. return true;
  451. }
  452.  
  453.  
  454. if (NULL != pExtractor)
  455. {
  456. iBonus = pExtractor->GetValue(ITEM_VALUE_DRAGON_SOUL_POLL_OUT_BONUS_IDX);
  457. pExtractor->SetCount(pExtractor->GetCount() - 1);
  458. }
  459. fDice = fnumber(0.f, 100.f);
  460. bSuccess = fDice <= (fProb * (100 + iBonus) / 100.f);
  461. }
  462.  
  463. // Äł¸ŻĹÍŔÇ żëČĄĽ® ĂßĂâ ą× Ăß°ˇ ȤŔş Á¦°Ĺ. şÎ»ęą° Á¦°ř.
  464. {
  465. char buf[128];
  466.  
  467. if (bSuccess)
  468. {
  469. if (pExtractor)
  470. {
  471. sprintf(buf, "dice(%d) prob(%d + %d) EXTR(VN:%d)", (int)fDice, (int)fProb, iBonus, pExtractor->GetVnum());
  472. }
  473. else
  474. {
  475. sprintf(buf, "dice(%d) prob(%d)", fDice, fProb);
  476. }
  477. LogManager::instance().ItemLog(ch, pItem, "DS_PULL_OUT_SUCCESS", buf);
  478. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żëČĄĽ® ĂßĂ⿡ Ľş°řÇĎż´˝Ŕ´Ď´Ů."));
  479. pItem->AddToCharacter(ch, DestCell);
  480. return true;
  481. }
  482. else
  483. {
  484. if (pExtractor)
  485. {
  486. sprintf(buf, "dice(%d) prob(%d + %d) EXTR(VN:%d) ByProd(VN:%d)", (int)fDice, (int)fProb, iBonus, pExtractor->GetVnum(), dwByProduct);
  487. }
  488. else
  489. {
  490. sprintf(buf, "dice(%d) prob(%d) ByProd(VNUM:%d)", (int)fDice, (int)fProb, dwByProduct);
  491. }
  492. LogManager::instance().ItemLog(ch, pItem, "DS_PULL_OUT_FAILED", buf);
  493. M2_DESTROY_ITEM(pItem);
  494. pItem = NULL;
  495. if (dwByProduct)
  496. {
  497. LPITEM pByProduct = ch->AutoGiveItem(dwByProduct, true);
  498. if (pByProduct)
  499. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żëČĄĽ® ĂßĂ⿡ ˝ÇĆĐÇĎż© %s¸¦ ľňľú˝Ŕ´Ď´Ů."), pByProduct->GetName());
  500. else
  501. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żëČĄĽ® ĂßĂ⿡ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  502. }
  503. else
  504. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("żëČĄĽ® ĂßĂ⿡ ˝ÇĆĐÇĎż´˝Ŕ´Ď´Ů."));
  505. }
  506. }
  507.  
  508. return bSuccess;
  509. }
  510.  
  511. bool DSManager::DoRefineGrade(LPCHARACTER ch, TItemPos (&aItemPoses)[DRAGON_SOUL_REFINE_GRID_SIZE])
  512. {
  513. if (NULL == ch)
  514. return false;
  515.  
  516. if (NULL == aItemPoses)
  517. {
  518. return false;
  519. }
  520.  
  521. if (!ch->DragonSoul_RefineWindow_CanRefine())
  522. {
  523. sys_err ("%s do not activate DragonSoulRefineWindow. But how can he come here?", ch->GetName());
  524. ch->ChatPacket(CHAT_TYPE_INFO, "[SYSTEM ERROR]You cannot upgrade dragon soul without refine window.");
  525. return false;
  526. }
  527.  
  528. // Ȥ˝ĂłŞ ¸đ¸¦ ÁßşąµÇ´Â item pointer ľřľÖ±â Ŕ§ÇŘĽ­ set »çżë
  529. // ŔĚ»óÇŃ ĆĐŶŔ» ş¸łľ °ćżě, ÁßşąµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ°í, Ŕ߸řµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ´Ů.
  530. std::set <LPITEM> set_items;
  531. for (int i = 0; i < DRAGON_SOUL_REFINE_GRID_SIZE; i++)
  532. {
  533. if (aItemPoses[i].IsEquipPosition())
  534. return false;
  535. LPITEM pItem = ch->GetItem(aItemPoses[i]);
  536. if (NULL != pItem)
  537. {
  538. // żëČĄĽ®ŔĚ ľĆ´Ń ľĆŔĚĹŰŔĚ °ł·®Ă˘żˇ ŔÖŔ» Ľö ľř´Ů.
  539. if (!pItem->IsDragonSoul())
  540. {
  541. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µî±Ţ °ł·®żˇ ÇĘżäÇŃ Ŕç·á°ˇ ľĆ´Ő´Ď´Ů."));
  542. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  543.  
  544. return false;
  545. }
  546.  
  547. set_items.insert(pItem);
  548. }
  549. }
  550.  
  551. if (set_items.size() == 0)
  552. {
  553. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MATERIAL, NPOS);
  554. return false;
  555. }
  556.  
  557. int count = set_items.size();
  558. int need_count = 0;
  559. int fee = 0;
  560. std::vector <float> vec_probs;
  561. float prob_sum;
  562.  
  563. BYTE ds_type, grade_idx, step_idx, strength_idx;
  564. int result_grade;
  565.  
  566. // °ˇŔĺ ĂłŔ˝ °ÍŔ» °­Č­ŔÇ ±âÁŘŔ¸·Î »ď´Â´Ů.
  567. std::set <LPITEM>::iterator it = set_items.begin();
  568. {
  569. LPITEM pItem = *it;
  570.  
  571. GetDragonSoulInfo(pItem->GetVnum(), ds_type, grade_idx, step_idx, strength_idx);
  572.  
  573. if (!m_pTable->GetRefineGradeValues(ds_type, grade_idx, need_count, fee, vec_probs))
  574. {
  575. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µî±Ţ °ł·®ÇŇ Ľö ľř´Â żëČĄĽ®ŔÔ´Ď´Ů."));
  576. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  577.  
  578. return false;
  579. }
  580. }
  581. while (++it != set_items.end())
  582. {
  583. LPITEM pItem = *it;
  584.  
  585. // Ŭ¶ó uiżˇĽ­ ŔĺÂřÇŃ ľĆŔĚĹŰŔş °ł·®Ă˘żˇ żĂ¸± Ľö ľřµµ·Ď ¸·ľŇ±â ¶§ą®żˇ,
  586. // ş°µµŔÇ ľË¸˛ Ăł¸®´Â ľČÇÔ.
  587. if (pItem->IsEquipped())
  588. {
  589. return false;
  590. }
  591.  
  592. if (ds_type != GetType(pItem->GetVnum()) || grade_idx != GetGradeIdx(pItem->GetVnum()))
  593. {
  594. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µî±Ţ °ł·®żˇ ÇĘżäÇŃ Ŕç·á°ˇ ľĆ´Ő´Ď´Ů."));
  595. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  596.  
  597. return false;
  598. }
  599. }
  600.  
  601. // Ŭ¶óżˇĽ­ ÇŃąř °ąĽö ĂĽĹ©¸¦ Çϱ⠶§ą®żˇ count != need_count¶ó¸é invalid Ŭ¶óŔĎ °ˇ´ÉĽşŔĚ Ĺ©´Ů.
  602. if (count != need_count)
  603. {
  604. sys_err ("Possiblity of invalid client. Name %s", ch->GetName());
  605. BYTE bSubHeader = count < need_count? DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MATERIAL : DS_SUB_HEADER_REFINE_FAIL_TOO_MUCH_MATERIAL;
  606. SendRefineResultPacket(ch, bSubHeader, NPOS);
  607. return false;
  608. }
  609.  
  610. if (ch->GetGold() < fee)
  611. {
  612. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ µ·ŔĚ şÎÁ·ÇŐ´Ď´Ů."));
  613. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MONEY, NPOS);
  614. return false;
  615. }
  616.  
  617. if (-1 == (result_grade = Gamble(vec_probs)))
  618. {
  619. sys_err ("Gamble failed. See RefineGardeTables' probabilities");
  620. return false;
  621. }
  622.  
  623. LPITEM pResultItem = ITEM_MANAGER::instance().CreateItem(MakeDragonSoulVnum(ds_type, (BYTE)result_grade, 0, 0));
  624.  
  625. if (NULL == pResultItem)
  626. {
  627. sys_err ("INVALID DRAGON SOUL(%d)", MakeDragonSoulVnum(ds_type, (BYTE)result_grade, 0, 0));
  628. return false;
  629. }
  630.  
  631. ch->PointChange(POINT_GOLD, -fee);
  632. int left_count = need_count;
  633.  
  634. for (std::set <LPITEM>::iterator it = set_items.begin(); it != set_items.end(); it++)
  635. {
  636. LPITEM pItem = *it;
  637. int n = pItem->GetCount();
  638. if (left_count > n)
  639. {
  640. pItem->RemoveFromCharacter();
  641. M2_DESTROY_ITEM(pItem);
  642. left_count -= n;
  643. }
  644. else
  645. {
  646. pItem->SetCount(n - left_count);
  647. }
  648. }
  649.  
  650. ch->AutoGiveItem(pResultItem, true);
  651.  
  652. if (result_grade > grade_idx)
  653. {
  654. char buf[128];
  655. sprintf(buf, "GRADE : %d -> %d", grade_idx, result_grade);
  656. LogManager::instance().ItemLog(ch, pResultItem, "DS_GRADE_REFINE_SUCCESS", buf);
  657. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µî±Ţ °ł·®żˇ Ľş°řÇß˝Ŕ´Ď´Ů."));
  658. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_SUCCEED, TItemPos (pResultItem->GetWindow(), pResultItem->GetCell()));
  659. return true;
  660. }
  661. else
  662. {
  663. char buf[128];
  664. sprintf(buf, "GRADE : %d -> %d", grade_idx, result_grade);
  665. LogManager::instance().ItemLog(ch, pResultItem, "DS_GRADE_REFINE_FAIL", buf);
  666. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("µî±Ţ °ł·®żˇ ˝ÇĆĐÇß˝Ŕ´Ď´Ů."));
  667. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL, TItemPos (pResultItem->GetWindow(), pResultItem->GetCell()));
  668. return false;
  669. }
  670. }
  671.  
  672. bool DSManager::DoRefineStep(LPCHARACTER ch, TItemPos (&aItemPoses)[DRAGON_SOUL_REFINE_GRID_SIZE])
  673. {
  674. if (NULL == ch)
  675. return false;
  676. if (NULL == aItemPoses)
  677. {
  678. return false;
  679. }
  680.  
  681. if (!ch->DragonSoul_RefineWindow_CanRefine())
  682. {
  683. sys_err ("%s do not activate DragonSoulRefineWindow. But how can he come here?", ch->GetName());
  684. ch->ChatPacket(CHAT_TYPE_INFO, "[SYSTEM ERROR]You cannot use dragon soul refine window.");
  685. return false;
  686. }
  687.  
  688. // Ȥ˝ĂłŞ ¸đ¸¦ ÁßşąµÇ´Â item pointer ľřľÖ±â Ŕ§ÇŘĽ­ set »çżë
  689. // ŔĚ»óÇŃ ĆĐŶŔ» ş¸łľ °ćżě, ÁßşąµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ°í, Ŕ߸řµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ´Ů.
  690. std::set <LPITEM> set_items;
  691. for (int i = 0; i < DRAGON_SOUL_REFINE_GRID_SIZE; i++)
  692. {
  693. LPITEM pItem = ch->GetItem(aItemPoses[i]);
  694. if (NULL != pItem)
  695. {
  696. // żëČĄĽ®ŔĚ ľĆ´Ń ľĆŔĚĹŰŔĚ °ł·®Ă˘żˇ ŔÖŔ» Ľö ľř´Ů.
  697. if (!pItem->IsDragonSoul())
  698. {
  699. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ü°č °ł·®żˇ ÇĘżäÇŃ Ŕç·á°ˇ ľĆ´Ő´Ď´Ů."));
  700. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  701. return false;
  702. }
  703. set_items.insert(pItem);
  704. }
  705. }
  706.  
  707. if (set_items.size() == 0)
  708. {
  709. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MATERIAL, NPOS);
  710. return false;
  711. }
  712.  
  713. std::string stGroupName;
  714. int count = set_items.size();
  715. int need_count = 0;
  716. int fee = 0;
  717. std::vector <float> vec_probs;
  718.  
  719. BYTE ds_type, grade_idx, step_idx, strength_idx;
  720. int result_step;
  721.  
  722. // °ˇŔĺ ĂłŔ˝ °ÍŔ» °­Č­ŔÇ ±âÁŘŔ¸·Î »ď´Â´Ů.
  723. std::set <LPITEM>::iterator it = set_items.begin();
  724. {
  725. LPITEM pItem = *it;
  726. GetDragonSoulInfo(pItem->GetVnum(), ds_type, grade_idx, step_idx, strength_idx);
  727.  
  728. if (!m_pTable->GetRefineStepValues(ds_type, step_idx, need_count, fee, vec_probs))
  729. {
  730. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ü°č °ł·®ÇŇ Ľö ľř´Â żëČĄĽ®ŔÔ´Ď´Ů."));
  731. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  732. return false;
  733. }
  734. }
  735.  
  736. while(++it != set_items.end())
  737. {
  738. LPITEM pItem = *it;
  739. // Ŭ¶ó uiżˇĽ­ ŔĺÂřÇŃ ľĆŔĚĹŰŔş °ł·®Ă˘żˇ żĂ¸± Ľö ľřµµ·Ď ¸·ľŇ±â ¶§ą®żˇ,
  740. // ş°µµŔÇ ľË¸˛ Ăł¸®´Â ľČÇÔ.
  741. if (pItem->IsEquipped())
  742. {
  743. return false;
  744. }
  745. if (ds_type != GetType(pItem->GetVnum()) || grade_idx != GetGradeIdx(pItem->GetVnum()) || step_idx != GetStepIdx(pItem->GetVnum()))
  746. {
  747. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ü°č °ł·®żˇ ÇĘżäÇŃ Ŕç·á°ˇ ľĆ´Ő´Ď´Ů."));
  748. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  749. return false;
  750. }
  751. }
  752.  
  753. // Ŭ¶óżˇĽ­ ÇŃąř °ąĽö ĂĽĹ©¸¦ Çϱ⠶§ą®żˇ count != need_count¶ó¸é invalid Ŭ¶óŔĎ °ˇ´ÉĽşŔĚ Ĺ©´Ů.
  754. if (count != need_count)
  755. {
  756. sys_err ("Possiblity of invalid client. Name %s", ch->GetName());
  757. BYTE bSubHeader = count < need_count? DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MATERIAL : DS_SUB_HEADER_REFINE_FAIL_TOO_MUCH_MATERIAL;
  758. SendRefineResultPacket(ch, bSubHeader, NPOS);
  759. return false;
  760. }
  761.  
  762. if (ch->GetGold() < fee)
  763. {
  764. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ µ·ŔĚ şÎÁ·ÇŐ´Ď´Ů."));
  765. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MONEY, NPOS);
  766. return false;
  767. }
  768.  
  769. float sum = 0.f;
  770.  
  771. if (-1 == (result_step = Gamble(vec_probs)))
  772. {
  773. sys_err ("Gamble failed. See RefineStepTables' probabilities");
  774. return false;
  775. }
  776.  
  777. LPITEM pResultItem = ITEM_MANAGER::instance().CreateItem(MakeDragonSoulVnum(ds_type, grade_idx, (BYTE)result_step, 0));
  778.  
  779. if (NULL == pResultItem)
  780. {
  781. sys_err ("INVALID DRAGON SOUL(%d)", MakeDragonSoulVnum(ds_type, grade_idx, (BYTE)result_step, 0));
  782. return false;
  783. }
  784.  
  785. ch->PointChange(POINT_GOLD, -fee);
  786. int left_count = need_count;
  787. for (std::set <LPITEM>::iterator it = set_items.begin(); it != set_items.end(); it++)
  788. {
  789. LPITEM pItem = *it;
  790. int n = pItem->GetCount();
  791. if (left_count > n)
  792. {
  793. pItem->RemoveFromCharacter();
  794. M2_DESTROY_ITEM(pItem);
  795. left_count -= n;
  796. }
  797. else
  798. {
  799. pItem->SetCount(n - left_count);
  800. }
  801. }
  802.  
  803. ch->AutoGiveItem(pResultItem, true);
  804. if (result_step > step_idx)
  805. {
  806. char buf[128];
  807. sprintf(buf, "STEP : %d -> %d", step_idx, result_step);
  808. LogManager::instance().ItemLog(ch, pResultItem, "DS_STEP_REFINE_SUCCESS", buf);
  809. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ü°č °ł·®żˇ Ľş°řÇß˝Ŕ´Ď´Ů."));
  810. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_SUCCEED, TItemPos (pResultItem->GetWindow(), pResultItem->GetCell()));
  811. return true;
  812. }
  813. else
  814. {
  815. char buf[128];
  816. sprintf(buf, "STEP : %d -> %d", step_idx, result_step);
  817. LogManager::instance().ItemLog(ch, pResultItem, "DS_STEP_REFINE_FAIL", buf);
  818. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("´Ü°č °ł·®żˇ ˝ÇĆĐÇß˝Ŕ´Ď´Ů."));
  819. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL, TItemPos (pResultItem->GetWindow(), pResultItem->GetCell()));
  820. return false;
  821. }
  822. }
  823.  
  824. bool IsDragonSoulRefineMaterial(LPITEM pItem)
  825. {
  826. if (pItem->GetType() != ITEM_MATERIAL)
  827. return false;
  828. return (pItem->GetSubType() == MATERIAL_DS_REFINE_NORMAL ||
  829. pItem->GetSubType() == MATERIAL_DS_REFINE_BLESSED ||
  830. pItem->GetSubType() == MATERIAL_DS_REFINE_HOLLY);
  831. }
  832.  
  833. bool DSManager::DoRefineStrength(LPCHARACTER ch, TItemPos (&aItemPoses)[DRAGON_SOUL_REFINE_GRID_SIZE])
  834. {
  835. if (NULL == ch)
  836. return false;
  837. if (NULL == aItemPoses)
  838. {
  839. return false;
  840. }
  841.  
  842. if (!ch->DragonSoul_RefineWindow_CanRefine())
  843. {
  844. sys_err ("%s do not activate DragonSoulRefineWindow. But how can he come here?", ch->GetName());
  845. ch->ChatPacket(CHAT_TYPE_INFO, "[SYSTEM ERROR]You cannot use dragon soul refine window.");
  846. return false;
  847. }
  848.  
  849. // Ȥ˝ĂłŞ ¸đ¸¦ ÁßşąµÇ´Â item pointer ľřľÖ±â Ŕ§ÇŘĽ­ set »çżë
  850. // ŔĚ»óÇŃ ĆĐŶŔ» ş¸łľ °ćżě, ÁßşąµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ°í, Ŕ߸řµČ TItemPos°ˇ ŔÖŔ» Ľöµµ ŔÖ´Ů.
  851. std::set <LPITEM> set_items;
  852. for (int i = 0; i < DRAGON_SOUL_REFINE_GRID_SIZE; i++)
  853. {
  854. LPITEM pItem = ch->GetItem(aItemPoses[i]);
  855. if (pItem)
  856. {
  857. set_items.insert(pItem);
  858. }
  859. }
  860. if (set_items.size() == 0)
  861. {
  862. return false;
  863. }
  864.  
  865. int fee;
  866.  
  867. LPITEM pRefineStone = NULL;
  868. LPITEM pDragonSoul = NULL;
  869. for (std::set <LPITEM>::iterator it = set_items.begin(); it != set_items.end(); it++)
  870. {
  871. LPITEM pItem = *it;
  872. // Ŭ¶ó uiżˇĽ­ ŔĺÂřÇŃ ľĆŔĚĹŰŔş °ł·®Ă˘żˇ żĂ¸± Ľö ľřµµ·Ď ¸·ľŇ±â ¶§ą®żˇ,
  873. // ş°µµŔÇ ľË¸˛ Ăł¸®´Â ľČÇÔ.
  874. if (pItem->IsEquipped())
  875. {
  876. return false;
  877. }
  878.  
  879. // żëČĄĽ®°ú °­Č­Ľ®¸¸ŔĚ °ł·®Ă˘żˇ ŔÖŔ» Ľö ŔÖ´Ů.
  880. // ±×¸®°í ÇĎłŞľż¸¸ ŔÖľîľßÇŃ´Ů.
  881. if (pItem->IsDragonSoul())
  882. {
  883. if (pDragonSoul != NULL)
  884. {
  885. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_TOO_MUCH_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  886. return false;
  887. }
  888. pDragonSoul = pItem;
  889. }
  890. else if(IsDragonSoulRefineMaterial(pItem))
  891. {
  892. if (pRefineStone != NULL)
  893. {
  894. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_TOO_MUCH_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  895. return false;
  896. }
  897. pRefineStone = pItem;
  898. }
  899. else
  900. {
  901. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­żˇ ÇĘżäÇŃ Ŕç·á°ˇ ľĆ´Ő´Ď´Ů."));
  902. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pItem->GetWindow(), pItem->GetCell()));
  903. return false;
  904. }
  905. }
  906.  
  907. BYTE bType, bGrade, bStep, bStrength;
  908.  
  909. if (!pDragonSoul || !pRefineStone)
  910. {
  911. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MATERIAL, NPOS);
  912.  
  913. return false;
  914. }
  915.  
  916. if (NULL != pDragonSoul)
  917. {
  918. GetDragonSoulInfo(pDragonSoul->GetVnum(), bType, bGrade, bStep, bStrength);
  919.  
  920. float fWeight = 0.f;
  921. // °ˇÁßġ °ŞŔĚ ľř´Ů¸é °­Č­ÇŇ Ľö ľř´Â żëČĄĽ®
  922. if (!m_pTable->GetWeight(bType, bGrade, bStep, bStrength + 1, fWeight))
  923. {
  924. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­ÇŇ Ľö ľř´Â żëČĄĽ®ŔÔ´Ď´Ů."));
  925. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_MAX_REFINE, TItemPos(pDragonSoul->GetWindow(), pDragonSoul->GetCell()));
  926. return false;
  927. }
  928. // °­Č­ÇßŔ» ¶§ °ˇÁßġ°ˇ 0Ŕ̶ó¸é ´ő ŔĚ»ó °­Č­µÇĽ­´Â ľČµČ´Ů.
  929. if (fWeight < FLT_EPSILON)
  930. {
  931. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­ÇŇ Ľö ľř´Â żëČĄĽ®ŔÔ´Ď´Ů."));
  932. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_MAX_REFINE, TItemPos(pDragonSoul->GetWindow(), pDragonSoul->GetCell()));
  933. return false;
  934. }
  935. }
  936.  
  937. float fProb;
  938. if (!m_pTable->GetRefineStrengthValues(bType, pRefineStone->GetSubType(), bStrength, fee, fProb))
  939. {
  940. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­ÇŇ Ľö ľř´Â żëČĄĽ®ŔÔ´Ď´Ů."));
  941. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_INVALID_MATERIAL, TItemPos(pDragonSoul->GetWindow(), pDragonSoul->GetCell()));
  942.  
  943. return false;
  944. }
  945.  
  946. if (ch->GetGold() < fee)
  947. {
  948. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°ł·®Ŕ» Çϱâ Ŕ§ÇŃ µ·ŔĚ şÎÁ·ÇŐ´Ď´Ů."));
  949. SendRefineResultPacket(ch, DS_SUB_HEADER_REFINE_FAIL_NOT_ENOUGH_MONEY, NPOS);
  950. return false;
  951. }
  952.  
  953. ch->PointChange(POINT_GOLD, -fee);
  954. LPITEM pResult = NULL;
  955. BYTE bSubHeader;
  956.  
  957. if (fnumber(0.f, 100.f) <= fProb)
  958. {
  959. pResult = ITEM_MANAGER::instance().CreateItem(MakeDragonSoulVnum(bType, bGrade, bStep, bStrength + 1));
  960. if (NULL == pResult)
  961. {
  962. sys_err ("INVALID DRAGON SOUL(%d)", MakeDragonSoulVnum(bType, bGrade, bStep, bStrength + 1));
  963. return false;
  964. }
  965. pDragonSoul->RemoveFromCharacter();
  966.  
  967. pDragonSoul->CopyAttributeTo(pResult);
  968. RefreshItemAttributes(pResult);
  969.  
  970. pDragonSoul->SetCount(pDragonSoul->GetCount() - 1);
  971. pRefineStone->SetCount(pRefineStone->GetCount() - 1);
  972.  
  973. char buf[128];
  974. sprintf(buf, "STRENGTH : %d -> %d", bStrength, bStrength + 1);
  975. LogManager::instance().ItemLog(ch, pDragonSoul, "DS_STRENGTH_REFINE_SUCCESS", buf);
  976. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­żˇ Ľş°řÇß˝Ŕ´Ď´Ů."));
  977. ch->AutoGiveItem(pResult, true);
  978. bSubHeader = DS_SUB_HEADER_REFINE_SUCCEED;
  979. }
  980. else
  981. {
  982. if (bStrength != 0)
  983. {
  984. pResult = ITEM_MANAGER::instance().CreateItem(MakeDragonSoulVnum(bType, bGrade, bStep, bStrength - 1));
  985. if (NULL == pResult)
  986. {
  987. sys_err ("INVALID DRAGON SOUL(%d)", MakeDragonSoulVnum(bType, bGrade, bStep, bStrength - 1));
  988. return false;
  989. }
  990. pDragonSoul->CopyAttributeTo(pResult);
  991. RefreshItemAttributes(pResult);
  992. }
  993. bSubHeader = DS_SUB_HEADER_REFINE_FAIL;
  994.  
  995. char buf[128];
  996. sprintf(buf, "STRENGTH : %d -> %d", bStrength, bStrength - 1);
  997. // strength°­Č­´Â ˝ÇĆнà ±úÁú Ľöµµ ŔÖľî, żřş» ľĆŔĚĹŰŔ» ąŮĹÁŔ¸·Î ·Î±×¸¦ ł˛±č.
  998. LogManager::instance().ItemLog(ch, pDragonSoul, "DS_STRENGTH_REFINE_FAIL", buf);
  999.  
  1000. ch->ChatPacket(CHAT_TYPE_INFO, LC_TEXT("°­Č­żˇ ˝ÇĆĐÇß˝Ŕ´Ď´Ů."));
  1001. pDragonSoul->SetCount(pDragonSoul->GetCount() - 1);
  1002. pRefineStone->SetCount(pRefineStone->GetCount() - 1);
  1003. if (NULL != pResult)
  1004. ch->AutoGiveItem(pResult, true);
  1005.  
  1006. }
  1007.  
  1008. SendRefineResultPacket(ch, bSubHeader, NULL == pResult? NPOS : TItemPos (pResult->GetWindow(), pResult->GetCell()));
  1009.  
  1010. return true;
  1011. }
  1012.  
  1013. void DSManager::SendRefineResultPacket(LPCHARACTER ch, BYTE bSubHeader, const TItemPos& pos)
  1014. {
  1015. TPacketGCDragonSoulRefine pack;
  1016. pack.bSubType = bSubHeader;
  1017.  
  1018. if (pos.IsValidItemPosition())
  1019. {
  1020. pack.Pos = pos;
  1021. }
  1022. LPDESC d = ch->GetDesc();
  1023. if (NULL == d)
  1024. {
  1025. return ;
  1026. }
  1027. else
  1028. {
  1029. d->Packet(&pack, sizeof(pack));
  1030. }
  1031. }
  1032.  
  1033. int DSManager::LeftTime(LPITEM pItem) const
  1034. {
  1035. if (pItem == NULL)
  1036. return false;
  1037.  
  1038. // ŔĎ´ÜŔş timer based on wearŔÎ żëČĄĽ®¸¸ ˝Ă°Ł ´Ů µÇľîµµ ľČ ľřľîÁř´Ů.
  1039. if (pItem->GetProto()->cLimitTimerBasedOnWearIndex >= 0)
  1040. {
  1041. return pItem->GetSocket(ITEM_SOCKET_REMAIN_SEC);
  1042. }
  1043. // ´Ů¸Ą limit typeŔÎ żëČĄĽ®µéŔş ˝Ă°Ł µÇ¸é ¸đµÎ »ç¶óÁö±â ¶§ą®żˇ ż©±â µéľîżÂ ľĆŔĚĹŰŔş ŔĎ´Ü ˝Ă°ŁŔĚ ł˛ľŇ´Ů°í ĆÇ´Ü.
  1044. else
  1045. {
  1046. return INT_MAX;
  1047. }
  1048. }
  1049.  
  1050. bool DSManager::IsTimeLeftDragonSoul(LPITEM pItem) const
  1051. {
  1052. if (pItem == NULL)
  1053. return false;
  1054.  
  1055. // ŔĎ´ÜŔş timer based on wearŔÎ żëČĄĽ®¸¸ ˝Ă°Ł ´Ů µÇľîµµ ľČ ľřľîÁř´Ů.
  1056. if (pItem->GetProto()->cLimitTimerBasedOnWearIndex >= 0)
  1057. {
  1058. return pItem->GetSocket(ITEM_SOCKET_REMAIN_SEC) > 0;
  1059. }
  1060. // ´Ů¸Ą limit typeŔÎ żëČĄĽ®µéŔş ˝Ă°Ł µÇ¸é ¸đµÎ »ç¶óÁö±â ¶§ą®żˇ ż©±â µéľîżÂ ľĆŔĚĹŰŔş ŔĎ´Ü ˝Ă°ŁŔĚ ł˛ľŇ´Ů°í ĆÇ´Ü.
  1061. else
  1062. {
  1063. return true;
  1064. }
  1065. }
  1066.  
  1067. bool DSManager::IsActiveDragonSoul(LPITEM pItem) const
  1068. {
  1069. return pItem->GetSocket(ITEM_SOCKET_DRAGON_SOUL_ACTIVE_IDX);
  1070. }
  1071.  
  1072. bool DSManager::ActivateDragonSoul(LPITEM pItem)
  1073. {
  1074. if (NULL == pItem)
  1075. return false;
  1076. LPCHARACTER pOwner = pItem->GetOwner();
  1077. if (NULL == pOwner)
  1078. return false;
  1079.  
  1080. int deck_idx = pOwner->DragonSoul_GetActiveDeck();
  1081.  
  1082. if (deck_idx < 0)
  1083. return false;
  1084.  
  1085. if (INVENTORY_MAX_NUM + WEAR_MAX_NUM + DS_SLOT_MAX * deck_idx <= pItem->GetCell() &&
  1086. pItem->GetCell() < INVENTORY_MAX_NUM + WEAR_MAX_NUM + DS_SLOT_MAX * (deck_idx + 1))
  1087. {
  1088. if (IsTimeLeftDragonSoul(pItem) && !IsActiveDragonSoul(pItem))
  1089. {
  1090. char buf[128];
  1091. sprintf (buf, "LEFT TIME(%d)", LeftTime(pItem));
  1092. LogManager::instance().ItemLog(pOwner, pItem, "DS_ACTIVATE", buf);
  1093. pItem->ModifyPoints(true);
  1094. pItem->SetSocket(ITEM_SOCKET_DRAGON_SOUL_ACTIVE_IDX, 1);
  1095.  
  1096. pItem->StartTimerBasedOnWearExpireEvent();
  1097. }
  1098. return true;
  1099. }
  1100. else
  1101. return false;
  1102. }
  1103.  
  1104. bool DSManager::DeactivateDragonSoul(LPITEM pItem, bool bSkipRefreshOwnerActiveState)
  1105. {
  1106. if (NULL == pItem)
  1107. return false;
  1108.  
  1109. LPCHARACTER pOwner = pItem->GetOwner();
  1110. if (NULL == pOwner)
  1111. return false;
  1112.  
  1113. if (!IsActiveDragonSoul(pItem))
  1114. return false;
  1115.  
  1116. char buf[128];
  1117. pItem->StopTimerBasedOnWearExpireEvent();
  1118. pItem->SetSocket(ITEM_SOCKET_DRAGON_SOUL_ACTIVE_IDX, 0);
  1119. pItem->ModifyPoints(false);
  1120.  
  1121. sprintf (buf, "LEFT TIME(%d)", LeftTime(pItem));
  1122. LogManager::instance().ItemLog(pOwner, pItem, "DS_DEACTIVATE", buf);
  1123.  
  1124. if (false == bSkipRefreshOwnerActiveState)
  1125. RefreshDragonSoulState(pOwner);
  1126.  
  1127. return true;
  1128. }
  1129.  
  1130. void DSManager::RefreshDragonSoulState(LPCHARACTER ch)
  1131. {
  1132. if (NULL == ch)
  1133. return ;
  1134. for (int i = WEAR_MAX_NUM; i < WEAR_MAX_NUM + DS_SLOT_MAX * DRAGON_SOUL_DECK_MAX_NUM; i++)
  1135. {
  1136. LPITEM pItem = ch->GetWear(i);
  1137. if (pItem != NULL)
  1138. {
  1139. if(IsActiveDragonSoul(pItem))
  1140. {
  1141. return;
  1142. }
  1143. }
  1144. }
  1145. ch->DragonSoul_DeactivateAll();
  1146. }
  1147.  
  1148. DSManager::DSManager()
  1149. {
  1150. m_pTable = NULL;
  1151. }
  1152.  
  1153. DSManager::~DSManager()
  1154. {
  1155. if (m_pTable)
  1156. delete m_pTable;
  1157. }
  1158.  
Advertisement
Add Comment
Please, Sign In to add comment