UIFinderWindow.cpp 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618
  1. //
  2. // Copyright (c) 2014-2017, THUNDERBEAST GAMES LLC All rights reserved
  3. //
  4. // Permission is hereby granted, free of charge, to any person obtaining a copy
  5. // of this software and associated documentation files (the "Software"), to deal
  6. // in the Software without restriction, including without limitation the rights
  7. // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  8. // copies of the Software, and to permit persons to whom the Software is
  9. // furnished to do so, subject to the following conditions:
  10. //
  11. // The above copyright notice and this permission notice shall be included in
  12. // all copies or substantial portions of the Software.
  13. //
  14. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  19. // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  20. // THE SOFTWARE.
  21. //
  22. #include <TurboBadger/tb_widgets.h>
  23. #include <TurboBadger/tb_widgets_common.h>
  24. #include <Atomic/IO/FileSystem.h>
  25. #include <Atomic/IO/Log.h>
  26. #include <Atomic/IO/File.h>
  27. #include "UI.h"
  28. #include "UIEvents.h"
  29. #include "UIWindow.h"
  30. #include "UIEditField.h"
  31. #include "UISelectList.h"
  32. #include "UIPromptWindow.h"
  33. #include "UIFinderWindow.h"
  34. #include "UISelectItem.h"
  35. #include "UIMenuWindow.h"
  36. using namespace tb;
  37. namespace Atomic
  38. {
  39. /// finder window
  40. UIFinderWindow::UIFinderWindow(Context* context, UIWidget* target, const String& id, bool createWidget) :
  41. UIWindow(context, false),
  42. finderMode_(0),
  43. currentPath_(),
  44. resultPath_(),
  45. bookmarks_(),
  46. bookmarkPaths_(),
  47. newBookmarkPtr_(),
  48. newFolderPtr_(),
  49. bookmarksDirty_(0)
  50. {
  51. if (createWidget)
  52. {
  53. widget_ = new TBFinderWindow(target ? target->GetInternalWidget() : 0, TBIDC(id.CString()));
  54. widget_->SetDelegate(this);
  55. GetSubsystem<UI>()->WrapWidget(this, widget_);
  56. }
  57. }
  58. UIFinderWindow::~UIFinderWindow()
  59. {
  60. SaveBookmarks();
  61. if ( !newFolderPtr_.Expired())
  62. newFolderPtr_->UnsubscribeFromAllEvents();
  63. if ( !newBookmarkPtr_.Expired() )
  64. newBookmarkPtr_->UnsubscribeFromAllEvents();
  65. }
  66. void UIFinderWindow::FindFile(const String& title, const String& preset, int dimmer, int width, int height)
  67. {
  68. if (!widget_)
  69. return;
  70. if ( ((TBFinderWindow*)widget_)->Show(title.CString(), preset.CString(), dimmer, width, height) )
  71. {
  72. CreateBookmarks();
  73. PresetCurrentPath(preset);
  74. UpdateUiPath();
  75. UpdateUiList();
  76. UpdateUiResult();
  77. }
  78. }
  79. void UIFinderWindow::FindPath(const String& title, const String& preset, int dimmer, int width, int height)
  80. {
  81. if (!widget_)
  82. return;
  83. finderMode_ = 1;
  84. if ( ((TBFinderWindow*)widget_)->Show(title.CString(), preset.CString(), dimmer, width, height) )
  85. {
  86. UIWidget *reswid = GetResultWidget();
  87. if (reswid) reswid->SetVisibility( UI_WIDGET_VISIBILITY_INVISIBLE );
  88. CreateBookmarks();
  89. PresetCurrentPath(preset);
  90. UpdateUiPath();
  91. UpdateUiList();
  92. UpdateUiResult();
  93. }
  94. }
  95. bool UIFinderWindow::OnEvent(const tb::TBWidgetEvent &ev)
  96. {
  97. if ( ev.type == EVENT_TYPE_CHANGED && ev.target && ((uint32)ev.target->GetID()) == UIFINDEREDITPATHID )
  98. {
  99. FileSystem* filesystem = GetSubsystem<FileSystem>();
  100. UIWidget *pathwidget = GetPathWidget(); // paste or type in currentpath widget
  101. if(pathwidget)
  102. {
  103. if ( filesystem->DirExists (pathwidget->GetText()))
  104. {
  105. if ( pathwidget->GetText() != currentPath_ )
  106. {
  107. resultPath_ = "";
  108. SetCurrentPath (pathwidget->GetText());
  109. UpdateUiList();
  110. UpdateUiResult();
  111. }
  112. }
  113. }
  114. return true;
  115. }
  116. if ( ev.type == EVENT_TYPE_POINTER_UP && ev.target && ((uint32)ev.target->GetID()) == UIFINDERUPBUTTONID ) // go up
  117. {
  118. GoFolderUp();
  119. return true;
  120. }
  121. if ( ev.type == EVENT_TYPE_POINTER_UP && ev.target && ((uint32)ev.target->GetID()) == UIFINDERBOOKBUTTONID ) // add bookmark request
  122. {
  123. // this check is necessary because you can kill the bookmark window with the "X" and
  124. // this kills the UI but not the newBookmarkPtr to it, and it doesnt get cleaned up properly.
  125. if ( newBookmarkPtr_.NotNull() )
  126. {
  127. newBookmarkPtr_->UnsubscribeFromAllEvents();
  128. newBookmarkPtr_.Reset();
  129. }
  130. newBookmarkPtr_ = new UIPromptWindow(context_, this, "createbookmark", true);
  131. SubscribeToEvent(newBookmarkPtr_, E_UIPROMPTCOMPLETE, ATOMIC_HANDLER(UIFinderWindow, HandleCreateBookmark ));
  132. String prospect = "";
  133. char delim = '/';
  134. Vector <String> tokens = currentPath_.Split(delim, false);
  135. prospect = tokens[ tokens.Size()-1 ]; // get the last folder name as preset
  136. newBookmarkPtr_->Show("Create New Bookmark", "Enter a name for the new bookmark", prospect );
  137. return true;
  138. }
  139. if ( ev.type == EVENT_TYPE_POINTER_UP && ev.target && ((uint32)ev.target->GetID()) == UIFINDERFOLDERBUTTONID ) // add folder request
  140. {
  141. if (newFolderPtr_.NotNull())
  142. {
  143. newFolderPtr_->UnsubscribeFromAllEvents();
  144. newFolderPtr_.Reset();
  145. }
  146. newFolderPtr_ = new UIPromptWindow(context_, this, "createfolder", true);
  147. SubscribeToEvent(newFolderPtr_, E_UIPROMPTCOMPLETE, ATOMIC_HANDLER(UIFinderWindow, HandleCreateFolder));
  148. newFolderPtr_->Show("Create new folder", "Enter a name for the new folder", "" );
  149. return true;
  150. }
  151. if ( ev.type == EVENT_TYPE_CLICK && ev.target && ((uint32)ev.target->GetID()) == 5 ) // clicked in bookmarks
  152. {
  153. UISelectList *bklist = static_cast<UISelectList *>(GetBookmarksWidget());
  154. int selected = bklist->GetValue();
  155. if ( selected >= 0 )
  156. {
  157. resultPath_ = ""; // were going back, give up file.
  158. SetCurrentPath ( bookmarkPaths_[selected]);
  159. UpdateUiPath();
  160. UpdateUiList();
  161. UpdateUiResult();
  162. bklist->SetValue(-1); // clear the select visuals
  163. }
  164. return true;
  165. }
  166. if ( ev.type == EVENT_TYPE_CUSTOM && ev.target && ((uint32)ev.target->GetID()) == UIFINDERBOOKLISTID ) // bookmarks TB context menu result
  167. {
  168. UI* ui = GetSubsystem<UI>();
  169. if ( ev.special_key == tb::TB_KEY_DELETE ) // we wanna delete something
  170. {
  171. String myid;
  172. ui->GetTBIDString(ev.target?((uint32)ev.target->GetID()) : 0, myid);
  173. UISelectList *bklist = static_cast<UISelectList *>(GetBookmarksWidget());
  174. if (bklist)
  175. {
  176. int myindex = bklist->FindId ( (uint32)ev.ref_id );
  177. if ( myindex >= 0 )
  178. {
  179. DeleteBookmark(myindex);
  180. }
  181. }
  182. }
  183. return true;
  184. }
  185. if ( ev.type == EVENT_TYPE_CLICK && ev.target && ((uint32)ev.target->GetID()) == UIFINDERFILELISTID ) // clicked dirfiles list
  186. {
  187. UISelectList *filelist = static_cast<UISelectList *>(GetFilesWidget());
  188. ComposePath( filelist->GetSelectedItemString() );
  189. return true;
  190. }
  191. if ( ev.type == EVENT_TYPE_CLICK && (ev.ref_id == UIFINDEROKBUTTONID|| ev.ref_id == UIFINDERCANCELBUTTONID ) ) // clicked ok or cancel button
  192. {
  193. UI* ui = GetSubsystem<UI>();
  194. VariantMap eventData;
  195. String title = "FinderWindow";
  196. TBStr tbtext;
  197. if( widget_ && (TBWindow*)widget_->GetText(tbtext) )
  198. title = tbtext.CStr();
  199. eventData[UIFinderComplete::P_TITLE] = title;
  200. eventData[UIFinderComplete::P_SELECTED] = "";
  201. eventData[UIFinderComplete::P_REASON] = "CANCEL";
  202. if (ev.ref_id == UIFINDEROKBUTTONID) // ok button was pressed, otherwise it was cancel button
  203. {
  204. eventData[UIFinderComplete::P_REASON] = "OK";
  205. if ( finderMode_ == 0 ) // finding a file
  206. { // get from widget, in case the user had been typing.
  207. UIWidget *ewidget = GetResultWidget();
  208. if( ewidget) eventData[UIFinderComplete::P_SELECTED] = ewidget->GetText();
  209. }
  210. else // finding a folder
  211. {
  212. UIWidget *cwidget = GetPathWidget();
  213. if( cwidget) eventData[UIFinderComplete::P_SELECTED] = cwidget->GetText();
  214. }
  215. }
  216. ConvertEvent(this, ui->WrapWidget(ev.target), ev, eventData);
  217. SendEvent(E_UIFINDERCOMPLETE, eventData);
  218. if (eventData[WidgetEvent::P_HANDLED].GetBool())
  219. return true;
  220. }
  221. return UIWindow::OnEvent(ev);
  222. }
  223. void UIFinderWindow::HandleCreateBookmark(StringHash eventType, VariantMap& eventData)
  224. {
  225. String Title = eventData["Title"].GetString();
  226. String Reason = eventData["Reason"].GetString();
  227. String Selected = eventData["Selected"].GetString();
  228. if( Reason == "OK" )
  229. CreateBookmark( Selected, currentPath_ );
  230. if (newBookmarkPtr_)
  231. {
  232. newBookmarkPtr_->UnsubscribeFromAllEvents();
  233. newBookmarkPtr_.Reset();
  234. }
  235. }
  236. void UIFinderWindow::HandleCreateFolder(StringHash eventType, VariantMap& eventData)
  237. {
  238. String Title = eventData["Title"].GetString();
  239. String Reason = eventData["Reason"].GetString();
  240. String Selected = eventData["Selected"].GetString();
  241. if( Reason == "OK" )
  242. CreateFolder(Selected);
  243. if (newFolderPtr_)
  244. {
  245. newFolderPtr_->UnsubscribeFromAllEvents();
  246. newFolderPtr_.Reset();
  247. }
  248. }
  249. UIWidget* UIFinderWindow::GetWindowWidget()
  250. {
  251. if (!widget_)
  252. return 0;
  253. UI* ui = GetSubsystem<UI>();
  254. return ui->WrapWidget(widget_);
  255. }
  256. UIWidget* UIFinderWindow::GetPathWidget()
  257. {
  258. if (!widget_)
  259. return 0;
  260. TBWidget* child = (TBWidget*) widget_->GetWidgetByIDAndType<TBEditField>(UIFINDEREDITPATHID);
  261. if (!child)
  262. return 0;
  263. UI* ui = GetSubsystem<UI>();
  264. return ui->WrapWidget(child);
  265. }
  266. UIWidget* UIFinderWindow::GetResultWidget()
  267. {
  268. if (!widget_)
  269. return 0;
  270. TBWidget* child = (TBWidget*)widget_->GetWidgetByIDAndType<TBEditField>(UIFINDEREDITFILEID);
  271. if (!child)
  272. return 0;
  273. UI* ui = GetSubsystem<UI>();
  274. return ui->WrapWidget(child);
  275. }
  276. UIWidget* UIFinderWindow::GetBookmarksWidget()
  277. {
  278. if (!widget_)
  279. return 0;
  280. TBWidget* child = (TBWidget*)widget_->GetWidgetByIDAndType<TBSelectList>(UIFINDERBOOKLISTID);
  281. if (!child)
  282. return 0;
  283. UI* ui = GetSubsystem<UI>();
  284. return ui->WrapWidget(child);
  285. }
  286. UIWidget* UIFinderWindow::GetFilesWidget()
  287. {
  288. if (!widget_)
  289. return 0;
  290. TBWidget* child = (TBWidget*)widget_->GetWidgetByIDAndType<TBSelectList>(UIFINDERFILELISTID);
  291. if (!child)
  292. return 0;
  293. UI* ui = GetSubsystem<UI>();
  294. return ui->WrapWidget(child);
  295. }
  296. // where the finder starts
  297. void UIFinderWindow::PresetCurrentPath( const String& preset )
  298. {
  299. FileSystem* filesystem = GetSubsystem<FileSystem>();
  300. if ( !preset.Empty() && filesystem->DirExists (preset) )
  301. SetCurrentPath (preset);
  302. else
  303. SetCurrentPath ( filesystem->GetUserDocumentsDir() );
  304. }
  305. // set the current path value
  306. void UIFinderWindow::SetCurrentPath( const String& string )
  307. {
  308. currentPath_ = string;
  309. }
  310. //using the list, jam things together, we'll either get another path or a file.
  311. void UIFinderWindow::ComposePath (const String& string )
  312. {
  313. String prospect = currentPath_ + string;
  314. FileSystem* filesystem = GetSubsystem<FileSystem>();
  315. if ( !filesystem->FileExists ( prospect ) ) // its a dir, feel the joy
  316. {
  317. SetCurrentPath( prospect + "/" ); // add the trailing slash, OR ELSE
  318. UpdateUiPath();
  319. UpdateUiList();
  320. UpdateUiResult();
  321. }
  322. else // its a file
  323. {
  324. resultPath_ = prospect;
  325. UpdateUiResult();
  326. }
  327. }
  328. // create the list of bookmarks ... can be different per platform
  329. void UIFinderWindow::CreateBookmarks()
  330. {
  331. FileSystem* filesystem = GetSubsystem<FileSystem>();
  332. String basepath = filesystem->GetUserDocumentsDir();
  333. UISelectList *bklist = static_cast<UISelectList *>(GetBookmarksWidget());
  334. #if defined(ATOMIC_PLATFORM_LINUX)
  335. if ( filesystem->DirExists ( basepath )) CreateBookmark ( "Home", basepath );
  336. if ( filesystem->DirExists ( basepath + "Documents")) CreateBookmark ( "Documents", basepath + "Documents/" );
  337. if ( filesystem->DirExists ( basepath + "Music")) CreateBookmark ( "Music", basepath + "Music/" );
  338. if ( filesystem->DirExists ( basepath + "Pictures" )) CreateBookmark ( "Pictures", basepath + "Pictures/" );
  339. if ( filesystem->DirExists ( basepath + "Videos" )) CreateBookmark ( "Videos", basepath + "Videos/" );
  340. if ( filesystem->DirExists ( basepath + "Downloads")) CreateBookmark ( "Downloads", basepath + "Downloads/" );
  341. #elif defined(ATOMIC_PLATFORM_WINDOWS)
  342. if ( filesystem->DirExists ( basepath )) CreateBookmark ( "Home", basepath );
  343. if ( filesystem->DirExists ( basepath + "Desktop")) CreateBookmark ( "Desktop", basepath + "Desktop/" );
  344. if ( filesystem->DirExists ( basepath + "Documents")) CreateBookmark ( "Documents", basepath + "Documents/" );
  345. if ( filesystem->DirExists ( basepath + "Downloads")) CreateBookmark ( "Downloads", basepath + "Downloads/" );
  346. if ( filesystem->DirExists ( basepath + "Music")) CreateBookmark ( "Music", basepath + "Music/" );
  347. if ( filesystem->DirExists ( basepath + "Pictures" )) CreateBookmark ( "Pictures", basepath + "Pictures/" );
  348. if ( filesystem->DirExists ( basepath + "Videos" )) CreateBookmark ( "Videos", basepath + "Videos/" );
  349. #elif defined(ATOMIC_PLATFORM_OSX)
  350. if ( filesystem->DirExists ( basepath )) CreateBookmark ( "Home", basepath );
  351. if ( filesystem->DirExists ( basepath + "Documents")) CreateBookmark ( "Documents", basepath + "Documents/" );
  352. if ( filesystem->DirExists ( basepath + "Downloads")) CreateBookmark ( "Downloads", basepath + "Downloads/" );
  353. if ( filesystem->DirExists ( basepath + "Public")) CreateBookmark ( "Public", basepath + "Public/" );
  354. #else // android, ios, web?
  355. if ( filesystem->DirExists ( basepath )) CreateBookmark ( "Home", basepath );
  356. #endif
  357. CreateBookmark ( "-", basepath ); // create separator!
  358. LoadBookmarks();
  359. bklist->SetValue(-1); // fix the selection and scrolling
  360. }
  361. // go up tree 1 folder
  362. void UIFinderWindow::GoFolderUp()
  363. {
  364. String prospect = "";
  365. char delim = '/';
  366. Vector <String> tokens = currentPath_.Split(delim, false);
  367. if ( tokens.Size() == 0 ) // were at the top
  368. prospect = "/";
  369. else
  370. {
  371. int nn = 0;
  372. for ( nn=0; nn<tokens.Size()-1; nn++ )
  373. {
  374. prospect += delim;
  375. prospect += tokens[nn];
  376. }
  377. prospect += delim;
  378. }
  379. if ( prospect != currentPath_ )
  380. {
  381. resultPath_ = "";
  382. SetCurrentPath (prospect);
  383. UpdateUiPath();
  384. UpdateUiList();
  385. UpdateUiResult();
  386. }
  387. }
  388. // move current path to widget
  389. void UIFinderWindow::UpdateUiPath ()
  390. {
  391. UIWidget *pathwidget = GetPathWidget();
  392. if(pathwidget)
  393. {
  394. if ( pathwidget->GetText() != currentPath_ )
  395. pathwidget->SetText(currentPath_);
  396. }
  397. }
  398. // move result path to widget
  399. void UIFinderWindow::UpdateUiResult ()
  400. {
  401. UIWidget *resultwidget = GetResultWidget();
  402. if( resultwidget)
  403. {
  404. if ( resultwidget->GetText() != resultPath_ )
  405. resultwidget->SetText(resultPath_);
  406. }
  407. }
  408. #include "Container/Sort.h"
  409. // a very local compare function
  410. bool CompareStrs(const String& a, const String &b)
  411. {
  412. return a < b;
  413. }
  414. // move folder contents into list
  415. void UIFinderWindow::UpdateUiList()
  416. {
  417. FileSystem* filesystem = GetSubsystem<FileSystem>();
  418. UISelectList *filelist = static_cast<UISelectList *>(GetFilesWidget());
  419. UISelectItemSource *fileSource = new UISelectItemSource(context_);
  420. if ( filesystem->DirExists (currentPath_ ) )
  421. {
  422. Vector <String> mydirs;
  423. int nn = 0;
  424. filesystem->ScanDir (mydirs,currentPath_, "*", SCAN_DIRS, false );
  425. Sort(mydirs.Begin(), mydirs.End(), CompareStrs); // sort them
  426. for ( nn=0; nn<mydirs.Size(); nn++ )
  427. {
  428. if ( mydirs[nn] == "." ) continue;
  429. if ( mydirs[nn] == ".." ) continue;
  430. String idz = "DIR"+ String(nn);
  431. fileSource->AddItem( new UISelectItem(context_, mydirs[nn], idz, "FolderIcon" ));
  432. }
  433. Vector <String> myfiles;
  434. filesystem->ScanDir (myfiles, currentPath_, "*", SCAN_FILES, false );
  435. Sort(myfiles.Begin(), myfiles.End(), CompareStrs);
  436. for ( nn=0; nn<myfiles.Size(); nn++ )
  437. {
  438. String idz = "FIL"+ String(nn);
  439. fileSource->AddItem(new UISelectItem( context_, myfiles[nn], idz));
  440. }
  441. }
  442. filelist->SetValue(-1);
  443. filelist->SetSource(fileSource);
  444. }
  445. // utility to add a folder in current path
  446. void UIFinderWindow::CreateFolder( const String& string )
  447. {
  448. FileSystem* filesystem = GetSubsystem<FileSystem>();
  449. if ( filesystem->CreateDir( currentPath_ + string ) )
  450. {
  451. UpdateUiList();
  452. }
  453. }
  454. // utility to add a bookmark from the current path
  455. void UIFinderWindow::CreateBookmark ( const String& bkname, const String& bkpath )
  456. {
  457. UISelectList *bklist = static_cast<UISelectList *>(GetBookmarksWidget());
  458. if (bklist )
  459. {
  460. int inspos = bklist->GetNumItems();
  461. if ( inspos < 0 ) inspos = 0;
  462. String idz = "BKM" + String(inspos);
  463. if ( bklist->AddItem ( inspos, bkname, idz ) )
  464. {
  465. bookmarks_.Push(bkname);
  466. bookmarkPaths_.Push (bkpath);
  467. bookmarksDirty_ = 1;
  468. }
  469. }
  470. }
  471. // removes a bookmark based upon its index in the bookmark list
  472. void UIFinderWindow::DeleteBookmark ( int bkindex )
  473. {
  474. UISelectList *bklist = static_cast<UISelectList *>(GetBookmarksWidget());
  475. if (bklist && bkindex >= 0)
  476. {
  477. bklist->DeleteItem(bkindex);
  478. bookmarks_.Erase(bkindex,1);
  479. bookmarkPaths_.Erase(bkindex,1);
  480. resultPath_ = "";
  481. SetCurrentPath (bookmarkPaths_[0]);
  482. UpdateUiPath();
  483. UpdateUiList();
  484. UpdateUiResult();
  485. bklist->SetValue(-1);
  486. bookmarksDirty_ = 1;
  487. }
  488. }
  489. void UIFinderWindow::LoadBookmarks()
  490. {
  491. FileSystem* filesystem = GetSubsystem<FileSystem>();
  492. String bkdata = "";
  493. String bkpath = "";
  494. #if defined(ATOMIC_PLATFORM_ANDROID) || defined(ATOMIC_PLATFORM_IOS)
  495. bkpath = filesystem->GetUserDocumentsDir(); // somewhere writable on mobile
  496. #else
  497. bkpath = filesystem->GetAppPreferencesDir("AtomicGameEngine", "Bookmarks"); // desktop systems
  498. #endif
  499. bkpath += "/Bookmarks.txt";
  500. if ( filesystem->FileExists ( bkpath ) )
  501. {
  502. File *fp = new File (context_, bkpath, FILE_READ);
  503. if(fp->IsOpen())
  504. {
  505. fp->ReadText(bkdata);
  506. fp->Close();
  507. }
  508. }
  509. char delim = '\n';
  510. Vector <String> tokens = bkdata.Split(delim, false);
  511. int nn=0;
  512. for ( nn=0; nn< tokens.Size(); nn+=2)
  513. {
  514. CreateBookmark ( tokens[nn], tokens[nn+1] );
  515. }
  516. bookmarksDirty_ = 0;
  517. }
  518. void UIFinderWindow::SaveBookmarks()
  519. {
  520. if ( bookmarksDirty_ > 0 )
  521. {
  522. FileSystem* filesystem = GetSubsystem<FileSystem>();
  523. String bkpath = "";
  524. #if defined(ATOMIC_PLATFORM_ANDROID) || defined(ATOMIC_PLATFORM_IOS)
  525. bkpath = filesystem->GetUserDocumentsDir();
  526. #else
  527. bkpath = filesystem->GetAppPreferencesDir("AtomicGameEngine", "Bookmarks");
  528. #endif
  529. bkpath += "/Bookmarks.txt";
  530. String bkdata = "";
  531. int nn=0, sep=-1;
  532. for ( nn = 0; nn<bookmarks_.Size(); nn++)
  533. {
  534. if ( sep > 0 )
  535. {
  536. bkdata += bookmarks_[nn];
  537. bkdata += "\n";
  538. bkdata += bookmarkPaths_[nn];
  539. bkdata += "\n";
  540. }
  541. if ( bookmarks_[nn] == "-" )
  542. sep = nn;
  543. }
  544. File *fp = new File (context_, bkpath, FILE_WRITE);
  545. if(fp->IsOpen())
  546. {
  547. fp->Write ((const void *)bkdata.CString(), bkdata.Length() );
  548. fp->Close();
  549. }
  550. }
  551. }
  552. }