CategoryDownload.cpp
上传用户:lds876
上传日期:2013-05-25
资源大小:567k
文件大小:18k
源码类别:

P2P编程

开发平台:

Visual C++

  1. // CategoryDownload1.cpp : implementation file
  2. //
  3. #include "stdafx.h"
  4. #include "testbt.h"
  5. #include "CategoryDownload.h"
  6. #include "download.h"
  7. #include "FilesListCtrl.h"
  8. #include "DlgNewDownload.h"
  9. #include "FileBase.h"
  10. #include "SetupRegister.h"
  11. #ifdef _DEBUG
  12. #define new DEBUG_NEW
  13. #undef THIS_FILE
  14. static char THIS_FILE[] = __FILE__;
  15. #endif
  16. /////////////////////////////////////////////////////////////////////////////
  17. // CCategoryDownload
  18. CCategoryDownload::CCategoryDownload()
  19. {
  20. // BOOL bRet  = DeleteDiretory("d:\复件 Downloads");
  21. m_pFilesListCtrl = 0;
  22. }
  23. CCategoryDownload::~CCategoryDownload()
  24. {
  25. }
  26. BEGIN_MESSAGE_MAP(CCategoryDownload, CTreeCtrl)
  27. //{{AFX_MSG_MAP(CCategoryDownload)
  28. ON_WM_DESTROY()
  29. //}}AFX_MSG_MAP
  30. ON_MESSAGE(DOWNLOAD_TERMINATED, OnDownloadTerminated)
  31. ON_MESSAGE(STORAGE_CHECK_COMPLETE, OnStorageCheckComplete)
  32. END_MESSAGE_MAP()
  33. /////////////////////////////////////////////////////////////////////////////
  34. // CCategoryDownload message handlers
  35. void CCategoryDownload::SetFilesListCtrl(CFilesListCtrl* pFilesListCtrl)
  36. {
  37. assert(pFilesListCtrl);
  38. m_pFilesListCtrl = pFilesListCtrl;
  39. }
  40. int CCategoryDownload::OnCreate(LPCREATESTRUCT lpCreateStruct) 
  41. {
  42. return 0;
  43. }
  44. void CCategoryDownload::GetRateTotals(long& lUpRate, long& lDownRate)
  45. {
  46. lUpRate = 0, lDownRate = 0;
  47. for (int i=0; i<m_vRuninings.size(); i++)
  48. {
  49. if (!m_vRuninings[i]->m_pDownload)
  50. {
  51. assert(false);
  52. m_vRuninings.erase(m_vRuninings.begin() + i);
  53. break;
  54. }
  55. if (m_vRuninings[i]->m_pDownload && 
  56. m_vRuninings[i]->m_pDownload->IsDownloading() && 
  57. !m_vRuninings[i]->m_pDownload->IsPause())
  58. {
  59. lUpRate += m_vRuninings[i]->m_pDownload->GetStatics().m_lUpRate;
  60. lDownRate  += m_vRuninings[i]->m_pDownload->GetStatics().m_lDownRate;
  61. }
  62. }
  63. }
  64. /**********************************************************************
  65. base .
  66. **********************************************************************/
  67. void CCategoryDownload::ContinueTheUncloseds()
  68. {
  69. for (int i=0; i<m_vUncloseds.size(); i++)
  70. {
  71. Download(CTreeCursor(m_vUncloseds[i].m_hTreeItem, this), m_vUncloseds[i].m_pFileDBItem);
  72. }
  73. m_vUncloseds.clear();
  74. }
  75. // called before save and exit.
  76. void CCategoryDownload::StopAllCompleteds() 
  77. {
  78. CCategoryDBItem* pItem = (CCategoryDBItem*)m_curDownloading.GetData();
  79. for (int i=0; i<pItem->m_vFileDBItems.size(); i++)
  80. {
  81. if (pItem->m_vFileDBItems[i]->m_pDownload)
  82. pItem->m_vFileDBItems[i]->m_bUnclosed = true;
  83. _StopDBFileItem(pItem->m_vFileDBItems[i]);
  84. StopDBFilesMoveComplete(pItem->m_vFileDBItems[i]);
  85. }
  86. }
  87. void CCategoryDownload::OnDestroy() 
  88. {
  89. // Release downloads.
  90. DeleteAllData(GetRootItem());
  91. for (int i=0; i<m_vDeleteings.size(); i++)
  92. {
  93. CDownload* pDownload = m_vDeleteings[i];
  94. delete pDownload;
  95. }
  96. m_vDeleteings.clear();
  97. CTreeCtrl::OnDestroy();
  98. }
  99. void CCategoryDownload::DeleteAllData(CTreeCursor& curDel) 
  100. {
  101. if (!curDel) return;
  102. if (curDel.HasChildren())
  103. {
  104. CTreeCursor curNext;
  105. CTreeCursor curChild = curDel.GetChild();
  106. while (curChild)
  107. {
  108. DeleteAllData(curChild);
  109. curChild = curChild.GetNext(TVGN_NEXT);
  110. }
  111. }
  112. CCategoryDBItem* pData = (CCategoryDBItem*)curDel.GetData();
  113. assert(pData);
  114. for (int i=0; i<pData->m_vFileDBItems.size(); i++)
  115. {
  116. // delete.
  117. if (pData->m_vFileDBItems[i]->m_pDownload)
  118. _StopDBFileItem(pData->m_vFileDBItems[i]);
  119. delete pData->m_vFileDBItems[i];
  120. }
  121. delete pData;
  122. // curDel.Delete();
  123. }
  124. /**********************************************************************
  125.  download object feedback message handler
  126.  parameter : 
  127. long wParam : handle to cursor.
  128. long lParam : pointer to download object.
  129. **********************************************************************/
  130. void CCategoryDownload::OnDownloadTerminated(long wParam, long lParam)
  131. {
  132. if (m_bNoNotifications)
  133. {
  134. assert(false);
  135. return;
  136. }
  137. assert(wParam && lParam);
  138. for (int i=0; i<m_vDeleteings.size(); i++)
  139. {
  140. if (m_vDeleteings[i] == (CDownload*) lParam)
  141. {
  142. CDownload* pDownload = (CDownload*) lParam;
  143. delete pDownload;
  144. m_vDeleteings.erase(m_vDeleteings.begin() + i);
  145. TRACE("rndownload terminatedrn");
  146. // m_pFilesListCtrl->OnDownloadTerminated(lParam);
  147. return;
  148. }
  149. }
  150. CFileDBItem* pBadFileDBItem = findCursorByDownloadPointer(GetRootItem(), (CDownload*) lParam);
  151. if (!pBadFileDBItem)
  152. {
  153. assert(false);
  154. return;
  155. }
  156. _StopDBFileItem(pBadFileDBItem);
  157. bool bCompletedMove = StopDBFilesMoveComplete(pBadFileDBItem);
  158. /*
  159. string strBadMsg = pBadFileDBItem->m_pDownload->GetBadMsg().data();
  160. pBadFileDBItem->m_pDownload->GetSystemMessage(pBadFileDBItem->m_vMsg);
  161. pBadFileDBItem->m_bBad = true;
  162. pBadFileDBItem->m_fComplete = 0;
  163. //*/
  164. // popup from download waiting deque, let engine start next one. refresh filelist if need.
  165. m_DownloadEngine.StopDownload(pBadFileDBItem);
  166. m_pFilesListCtrl->OnDownloadTerminated((long)pBadFileDBItem, bCompletedMove);
  167. // release download object
  168. // delete pBadFileDBItem->m_pDownload;
  169. // pBadFileDBItem->m_pDownload = 0;
  170. }
  171. void CCategoryDownload::OnStorageCheckComplete(long wParam, long lParam)
  172. {
  173. assert(lParam);
  174. m_DownloadEngine.ExcuteDownload(lParam);
  175. }
  176. CFileDBItem* CCategoryDownload::findCursorByDownloadPointer(CTreeCursor curItem, CDownload* pDownload)
  177. {
  178. CCategoryDBItem* pItem = (CCategoryDBItem*)curItem.GetData();
  179. assert(pItem && curItem);
  180. for (int i=0; i<pItem->m_vFileDBItems.size(); i++)
  181. {
  182. if (pDownload == pItem->m_vFileDBItems[i]->m_pDownload)
  183. {
  184. return pItem->m_vFileDBItems[i];
  185. }
  186. }
  187. if (curItem.HasChildren())
  188. {
  189. CTreeCursor curChild = curItem.GetChild();
  190. while (curChild)
  191. {
  192. CFileDBItem* pRet = findCursorByDownloadPointer(curChild, pDownload);
  193. if (pRet)
  194. return pRet;
  195. curChild = curChild.GetNext(TVGN_NEXT);
  196. }
  197. }
  198. return 0;
  199. }
  200. /**********************************************************************
  201.  data manipulate.
  202. **********************************************************************/
  203. bool CCategoryDownload::Download(CTreeCursor curItem, CFileDBItem* pFileDBItem)
  204. {
  205. // put the download operation in Download deque.
  206. pFileDBItem->m_bBad = false;
  207. if (m_vRuninings.size() >= m_pSetupRegister->m_lDownloadAllCount)
  208. {
  209. pFileDBItem->m_bBad = true;
  210. CString strBad;
  211. strBad.Format("已运行任务数大于全局任务数(%d), 请查看你的任务数设置", m_pSetupRegister->m_lDownloadAllCount);
  212. time_t tNow;
  213. time(&tNow);
  214. time(&pFileDBItem->m_tModifiedTime);
  215. pFileDBItem->m_vMsg.push_back(CSystemMsg(tNow, strBad.GetBuffer(0), CSystemMsg::eBad));
  216. }
  217. else
  218. {
  219. m_vRuninings.push_back(pFileDBItem);
  220. m_DownloadEngine.StartDownload(pFileDBItem, curItem);
  221. }
  222. //
  223. // Move from true category to downloading category.
  224. //
  225. if (curItem == m_curDownloading)
  226. return false;
  227. if (!_MoveItemFromto(curItem, m_curDownloading, pFileDBItem))
  228. return false;
  229. return true;
  230. }
  231. void CCategoryDownload::PauseDBFiles(CFileDBItem* pFileDBItem)
  232. {
  233. if (!pFileDBItem->m_pDownload || pFileDBItem->m_pDownload->IsPause())
  234. {
  235. assert(false);
  236. return;
  237. }
  238. if (pFileDBItem->m_pDownload->IsDownloading())
  239. {
  240. CStatics statics = pFileDBItem->m_pDownload->GetStatics();
  241. if (statics.m_bCheckingDone)
  242. {
  243. vector<long> vHaves;
  244. pFileDBItem->m_pDownload->GetFractions(vHaves);
  245. float fComplete = statics.m_fCompleted;
  246. pFileDBItem->SetHave(vHaves, fComplete);
  247. pFileDBItem->m_lPieceCount = vHaves.size();
  248. if (!pFileDBItem->m_vUnneededFileInx.empty())
  249. pFileDBItem->m_fCompletePart = statics.m_fCompletedPart;
  250. }
  251. }
  252. pFileDBItem->m_pDownload->Pause();
  253. }
  254. void CCategoryDownload::StopDBFiles(vector<CFileDBItem*> vToStopFileDBItems)
  255. {
  256. //
  257. // release from m_DownloadEngine.
  258. //
  259. m_DownloadEngine.StopDownloadArray(vToStopFileDBItems);
  260. //
  261. // truely release the download object.
  262. //
  263. for (int i=0; i<vToStopFileDBItems.size(); i++)
  264. {
  265. CFileDBItem* pFileDBItem = vToStopFileDBItems[i];
  266. if (!pFileDBItem->m_pDownload)
  267. {
  268. assert(false);
  269. continue;
  270. }
  271. _StopDBFileItem(pFileDBItem);
  272. time_t tNow;
  273. time(&tNow);
  274. pFileDBItem->m_vMsg.push_back(CSystemMsg(tNow, "用户取消了该任务", CSystemMsg::eCmd));
  275. }
  276. }
  277. void CCategoryDownload::_StopDBFileItem(CFileDBItem* pFileDBItem)
  278. {
  279. if (!pFileDBItem->m_pDownload)
  280. return;
  281. //
  282. // remove from runnning vector.
  283. //
  284. vector<CFileDBItem*>::iterator iter = find(m_vRuninings.begin(), m_vRuninings.end(), pFileDBItem);
  285. if (iter == m_vRuninings.end())
  286. assert(false);
  287. else
  288. {
  289. m_vRuninings.erase(iter);
  290. }
  291. //
  292. // if bad
  293. //
  294. if (pFileDBItem->m_pDownload->IsBad())
  295. {
  296. pFileDBItem->m_bBad = true;
  297. vector<long> vHaves;
  298. pFileDBItem->SetHave(vHaves, 0);
  299. }
  300. if (pFileDBItem->m_pDownload->IsDownloading())
  301. {
  302. CStatics statics = pFileDBItem->m_pDownload->GetStatics();
  303. // Checking and downloading means check completed.
  304. // if (!statics.m_bStorageChecking)
  305. if (statics.m_bCheckingDone)
  306. {
  307. float fComplete = statics.m_fCompleted;
  308. vector<long> vHaves;
  309. pFileDBItem->m_pDownload->GetFractions(vHaves);
  310. pFileDBItem->SetHave(vHaves, fComplete);
  311. pFileDBItem->m_lPieceCount = vHaves.size();
  312. if (!pFileDBItem->m_vUnneededFileInx.empty())
  313. pFileDBItem->m_fCompletePart = statics.m_fCompletedPart;
  314. }
  315. pFileDBItem->m_pDownload->CloseDownload();
  316. pFileDBItem->m_pDownload->GetSystemMessage(pFileDBItem->m_vMsg);
  317. m_vDeleteings.push_back(pFileDBItem->m_pDownload);
  318. }
  319. else
  320. {
  321. pFileDBItem->m_pDownload->GetSystemMessage(pFileDBItem->m_vMsg);
  322. delete pFileDBItem->m_pDownload;
  323. }
  324. pFileDBItem->m_pDownload = 0;
  325. }
  326. bool CCategoryDownload::StopDBFilesMoveComplete(CFileDBItem* pFileDBItem)
  327. {
  328. assert(pFileDBItem);
  329. if (!pFileDBItem->m_vUnneededFileInx.empty())
  330. {
  331. if (pFileDBItem->m_fCompletePart < 1)
  332. return false;
  333. }
  334. else
  335. {
  336. if (pFileDBItem->m_fComplete < 1)
  337. return false;
  338. }
  339. //
  340. // move the stoped completed item to the true category assinged.
  341. //
  342. CTreeCursor curTrueItem = findCursorByDirid(pFileDBItem->m_lDirectoryID);
  343. if (!curTrueItem)
  344. {
  345. assert(false);
  346. return false;
  347. }
  348. if (curTrueItem == m_curDownloading)
  349. return false;
  350. if (!_MoveItemFromto(m_curDownloading, curTrueItem, pFileDBItem))
  351. {
  352. assert(false);
  353. return false;
  354. }
  355. return true;
  356. }
  357. bool CCategoryDownload::DeleteDBFile(CTreeCursor curCategory, CFileDBItem* pFileDBItem, 
  358.  bool bForceDelete, bool bDelUncompleted, bool bDelCompleted)
  359. {
  360. //
  361. // Release from m_DownloadEngine.
  362. //
  363. if (pFileDBItem->m_pDownload)
  364. m_DownloadEngine.StopDownload(pFileDBItem);
  365. //
  366. // If temperory delete, just move it to recycle category.
  367. //
  368. if (curCategory != m_curRecycle && !bForceDelete)
  369. {
  370. _StopDBFileItem(pFileDBItem);
  371. // FileDBItemMoveto(curCategory, m_curRecycle, pFileDBItem, false, true);
  372. _MoveItemFromto(curCategory, m_curRecycle, pFileDBItem);
  373. return true;
  374. }
  375. //
  376. // Remove the item in current category, and release it.
  377. //
  378. CCategoryDBItem* pTrueCategory = (CCategoryDBItem*)curCategory.GetData();
  379. assert(curCategory && pTrueCategory);
  380. bool bfind = false;
  381. for (int i=0; i<pTrueCategory->m_vFileDBItems.size(); i++)
  382. {
  383. if (pTrueCategory->m_vFileDBItems[i] == pFileDBItem)
  384. {
  385. pTrueCategory->m_vFileDBItems.erase(pTrueCategory->m_vFileDBItems.begin() + i);
  386. _StopDBFileItem(pFileDBItem);
  387. if (pFileDBItem->m_fComplete >= 1) 
  388. DeleteFileDBItemFiles(pFileDBItem, bDelCompleted);
  389. else
  390. DeleteFileDBItemFiles(pFileDBItem, bDelUncompleted);
  391. delete pFileDBItem;
  392. bfind = true;
  393. break;
  394. }
  395. }
  396. assert(bfind);
  397. return true;
  398. }
  399. bool CCategoryDownload::DeleteFileDBItemFiles(CFileDBItem* pFileDBItem, bool bDelDownloaded) const
  400. {
  401. CString strTorrentFileName= (GetDBSavePath() + pFileDBItem->m_strTorrentFileName).data(); 
  402. BOOL bRet = DeleteFile(strTorrentFileName);
  403. if (!bRet)
  404. {
  405. CString strErr = WSAShowError().data();
  406. assert(false);
  407. // return false;
  408. }
  409. if (bDelDownloaded)
  410. {
  411. if (!DeleteDiretory(pFileDBItem->m_strFileName.data()))
  412. {
  413. assert(false);
  414. return false;
  415. }
  416. }
  417. return true;
  418. }
  419. bool CCategoryDownload::IsMovingFiles()
  420. {
  421. return ::IsMovingFiles() > 0;
  422. }
  423. bool CCategoryDownload::FileDBItemMovetoArray(CTreeCursor curSrc, CTreeCursor curTarget, vector<CFileDBItem*>& vFileDBItem)
  424. {
  425. if (curSrc == curTarget)
  426. return false;
  427. bool bMoveFile = false, bMoveCategory = true;
  428. //
  429. // Get running items.
  430. //
  431. vector<CFileDBItem*> vToStopFileDBItems;
  432. for (int i=0; i< vFileDBItem.size(); i++)
  433. {
  434. CFileDBItem* pFileDBItem = vFileDBItem[i];
  435. if (pFileDBItem->m_pDownload)
  436. vToStopFileDBItems.push_back(pFileDBItem);
  437. }
  438. //
  439. // Query user operations.
  440. //
  441. if (curTarget == m_curRecycle)
  442. {
  443. if (!vToStopFileDBItems.empty())
  444. {
  445. if (AfxMessageBox("有下载正在进行中, 您是否确定删除?", MB_YESNO|MB_DEFBUTTON2) != IDYES)
  446. return false;
  447. // if is downloading, popup it from starting engine deque.
  448. StopDBFiles(vToStopFileDBItems);
  449. bMoveFile = false;
  450. bMoveCategory = true;
  451. }
  452. }
  453. else
  454. {
  455. bMoveFile = false;
  456. bMoveCategory = true;
  457. // if (curSrc == m_curDownloading)
  458. // bMoveCategory = false;
  459. switch (m_pSetupRegister->m_eOperMoveToCate)
  460. {
  461. case CSetupRegister::ePromptMoveCate:
  462. {
  463. if (!vToStopFileDBItems.empty())
  464. {
  465. if (AfxMessageBox("有下载正在进行中,移动已下载文件将停止下载,您是否确定移动已下载文件?", MB_YESNO|MB_DEFBUTTON2) == IDYES)
  466. bMoveFile = true;
  467. else
  468. return false;
  469. StopDBFiles(vToStopFileDBItems);
  470. }
  471. else
  472. {
  473. if (AfxMessageBox("是否移动已下载文件?", MB_YESNO|MB_ICONQUESTION) == IDYES)
  474. bMoveFile = true;
  475. }
  476. }
  477. break;
  478. case CSetupRegister::eDontMove:
  479. {
  480. bMoveFile = false;
  481. }
  482. break;
  483. case CSetupRegister::eMove:
  484. {
  485. bMoveFile = true;
  486. }
  487. break;
  488. }
  489. }
  490. //
  491. // Move.
  492. //
  493. if (bMoveFile)
  494. {
  495. // get target path.
  496. CCategoryDBItem* pTragetItem= (CCategoryDBItem*)curTarget.GetData();
  497. CString strTargetPath = pTragetItem->m_strDefaultDirectory.data();
  498. // get move file path vector.
  499. vector<CString> vstrPathToMove;
  500. for (i=0; i< vFileDBItem.size(); i++)
  501. {
  502. CFileDBItem* pFileDBItem = vFileDBItem[i];
  503. DWORD dwAttr = GetFileAttributes(pFileDBItem->m_strFileName.data());
  504. if (dwAttr !=  0xffffffff)
  505. {
  506. string strName, strPath;
  507. SplitPathName(pFileDBItem->m_strFileName, strPath, strName);
  508. if (formatDir(pTragetItem->m_strDefaultDirectory) != formatDir(strPath))
  509. {
  510. vstrPathToMove.push_back(pFileDBItem->m_strFileName.data());
  511. }
  512. }
  513. }
  514. // call move function.
  515. if (!vstrPathToMove.empty())
  516. {
  517. if (!MoveDiretorySystem(vstrPathToMove, pTragetItem->m_strDefaultDirectory.data(), GetSafeHwnd()))
  518. {
  519. assert(false);
  520. return false;
  521. }
  522. }
  523. // change the filedbitem path.
  524. for (i=0; i< vFileDBItem.size(); i++)
  525. {
  526. CFileDBItem* pFileDBItem = vFileDBItem[i];
  527. string strName, strPath;
  528. SplitPathName(pFileDBItem->m_strFileName, strPath, strName);
  529. if (formatDir(pTragetItem->m_strDefaultDirectory) != formatDir(strPath))
  530. {
  531. pFileDBItem->m_strFileName = formatDir(pTragetItem->m_strDefaultDirectory) + strName;
  532. }
  533. }
  534. }
  535. for (i=0; i< vFileDBItem.size(); i++)
  536. {
  537. CFileDBItem* pFileDBItem = vFileDBItem[i];
  538. FileDBItemMoveto(curSrc, curTarget, pFileDBItem, bMoveFile, bMoveCategory);
  539. }
  540. return bMoveCategory;
  541. }
  542. bool CCategoryDownload::FileDBItemMoveto(CTreeCursor curSrc, CTreeCursor curTarget, CFileDBItem* pFileDBItem, bool bMoveFile, bool bMoveCategory)
  543. {
  544. CCategoryDBItem* pTragetItem= (CCategoryDBItem*)curTarget.GetData();
  545. assert(pTragetItem);
  546. if (bMoveFile)
  547. {
  548. /*
  549. DWORD dwAttr = GetFileAttributes(pFileDBItem->m_strFileName.data());
  550. if (dwAttr !=  0xffffffff)
  551. {
  552. string strName, strPath;
  553. SplitPathName(pFileDBItem->m_strFileName, strPath, strName);
  554. if (formatDir(pTragetItem->m_strDefaultDirectory) != formatDir(strPath))
  555. {
  556. if (!MoveDiretorySystem(pFileDBItem->m_strFileName.data(), pTragetItem->m_strDefaultDirectory.data(), GetSafeHwnd()))
  557. return false;
  558. pFileDBItem->m_strFileName = formatDir(pTragetItem->m_strDefaultDirectory) + strName;
  559. }
  560. }
  561. //*/
  562. }
  563. if (bMoveCategory)
  564. {
  565. if (!_MoveItemFromto(curSrc, curTarget, pFileDBItem))
  566. return false;
  567. }
  568. // change dirid to target dirid.
  569. pFileDBItem->m_lDirectoryID = pTragetItem->m_lDirectoryID;
  570. return true;
  571. }
  572. bool CCategoryDownload::FileDBItemRestore(CFileDBItem* pFileDBItem)
  573. {
  574. CTreeCursor curMove = findCursorByDirid(pFileDBItem->m_lDirectoryID);
  575. if (pFileDBItem->m_fComplete < 1)
  576. curMove = m_curDownloading;
  577. assert(curMove);
  578. _MoveItemFromto(m_curRecycle, curMove, pFileDBItem);
  579. return true;
  580. }
  581. bool CCategoryDownload::_MoveItemFromto(CTreeCursor curSrc, CTreeCursor curTarget, CFileDBItem* pFileDBItem)
  582. {
  583. if (curSrc == curTarget || !curSrc || !curTarget)
  584. {
  585. assert(false);
  586. return false;
  587. }
  588. // remove form src.
  589. bool bfind = false;
  590. CCategoryDBItem* pSrcItem= (CCategoryDBItem*)curSrc.GetData();
  591. assert(pSrcItem);
  592. for (int i=0; i<pSrcItem->m_vFileDBItems.size(); i++)
  593. {
  594. if (pSrcItem->m_vFileDBItems[i] == pFileDBItem)
  595. {
  596. pSrcItem->m_vFileDBItems.erase(pSrcItem->m_vFileDBItems.begin() + i);
  597. bfind = true;
  598. break;
  599. }
  600. }
  601. if (!bfind)
  602. {
  603. assert(false);
  604. return false;
  605. }
  606. // insert into target.
  607. CCategoryDBItem* pTragetItem= (CCategoryDBItem*)curTarget.GetData();
  608. assert(pTragetItem);
  609. pTragetItem->m_vFileDBItems.push_back(pFileDBItem);
  610. return true;
  611. }
  612. /********************************************************************
  613.   Attributes.
  614. ********************************************************************/
  615. bool CCategoryDownload::IsDownloading()
  616. {
  617. return findDownloading(GetRootItem());
  618. }
  619. bool CCategoryDownload::findDownloading(CTreeCursor curItem)
  620. {
  621. if (!curItem)
  622. {
  623. assert(false);
  624. return false;
  625. }
  626. CCategoryDBItem* pItem = (CCategoryDBItem*)curItem.GetData();
  627. assert(pItem && curItem);
  628. for (int i=0; i<pItem->m_vFileDBItems.size(); i++)
  629. {
  630. if (pItem->m_vFileDBItems[i]->m_pDownload)
  631. {
  632. return true;
  633. }
  634. }
  635. if (curItem.HasChildren())
  636. {
  637. CTreeCursor curChild = curItem.GetChild();
  638. while (curChild)
  639. {
  640. if (findDownloading(curChild))
  641. return true;
  642. curChild = curChild.GetNext(TVGN_NEXT);
  643. }
  644. }
  645. return false;
  646. }