ReactOS 0.4.15-dev-7788-g1ad9096
favorites.cpp
Go to the documentation of this file.
1/*
2 * Copyright 2004, 2006 Martin Fuchs
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17 */
18
19
20 //
21 // Explorer and Desktop clone
22 //
23 // favorites.cpp
24 //
25 // Martin Fuchs, 04.04.2004
26 //
27
28
29#include <precomp.h>
30
31#include "startmenu.h"
32
33
35{
37 LPTSTR o = buffer;
38
39 for(const char* p=s; *p; ++p)
40 if (*p == '%') {
41 if (!strncmp(p+1, "20", 2)) {
42 *o++ = ' ';
43 p += 2;
44 } else
45 *o++ = *p;
46 } else
47 *o++ = *p;
48
49 return String(buffer, o-buffer);
50}
51
52
55{
56 char line[BUFFER_LEN];
57
58 tifstream in(path);
59
60 while(in.good()) {
61 in.getline(line, BUFFER_LEN);
62
63 const char* p = line;
64 while(isspace(*p))
65 ++p;
66
67 const char* keyword = p;
68 const char* eq = strchr(p, '=');
69
70 if (eq) {
71 const char* cont = eq + 1;
72 while(isspace(*cont))
73 ++cont;
74
75 if (!_strnicmp(keyword, "URL", 3))
76 _url = DecodeURLString(cont);
77 else if (!_strnicmp(keyword, "IconFile", 8))
79 }
80 }
81
82 return true;
83}
84
86bool Bookmark::read(const_XMLPos& pos)
87{
88 _url = pos.get("href").c_str();
89
90 if (pos.go_down("title")) {
91 _name = pos->get_content();
92 pos.back();
93 }
94
95 if (pos.go_down("desc")) {
96 _description = pos->get_content();
97 pos.back();
98 }
99
100 if (pos.go_down("info")) {
101 const_XMLChildrenFilter metadata(pos, "metadata");
102
103 for(const_XMLChildrenFilter::const_iterator it=metadata.begin(); it!=metadata.end(); ++it) {
104 const XMLNode& node = **it;
105 const_XMLPos sub_pos(&node);
106
107 if (node.get("owner") == "ros-explorer") {
108 if (sub_pos.go_down("icon")) {
109 _icon_path = sub_pos.get("path").c_str();
110 _icon_idx = XS_toi(sub_pos.get("index"));
111
112 sub_pos.back(); // </icon>
113 }
114 }
115 }
116
117 pos.back(); // </metadata>
118 pos.back(); // </info>
119 }
120
121 return !_url.empty(); // _url is mandatory.
122}
123
125void Bookmark::write(XMLPos& pos) const
126{
127 pos.create("bookmark");
128
129 pos["href"] = _url.c_str();
130
131 if (!_name.empty()) {
132 pos.create("title");
133 pos->set_content(_name);
134 pos.back();
135 }
136
137 if (!_description.empty()) {
138 pos.create("desc");
139 pos->set_content(_description);
140 pos.back();
141 }
142
143 if (!_icon_path.empty()) {
144 pos.create("info");
145 pos.create("metadata");
146 pos["owner"] = "ros-explorer";
147 pos.create("icon");
148 pos["path"] = _icon_path.c_str();
149 pos["index"].printf(XS_TEXT("%d"), _icon_idx);
150 pos.back(); // </icon>
151 pos.back(); // </metadata>
152 pos.back(); // </info>
153 }
154
155 pos.back();
156}
157
158
160void BookmarkFolder::read(const_XMLPos& pos)
161{
162 if (pos.go_down("title")) {
163 _name = pos->get_content();
164 pos.back();
165 }
166
167 if (pos.go_down("desc")) {
168 _description = pos->get_content();
169 pos.back();
170 }
171
173}
174
176void BookmarkFolder::write(XMLPos& pos) const
177{
178 pos.create("folder");
179
180 if (!_name.empty()) {
181 pos.create("title");
182 pos->set_content(_name);
183 pos.back();
184 }
185
186 if (!_description.empty()) {
187 pos.create("desc");
188 pos->set_content(_description);
189 pos.back();
190 }
191
193}
194
195
197 : _type(BMNT_NONE)
198{
200}
201
203 : _type(BMNT_BOOKMARK)
204{
205 _pbookmark = new Bookmark(bm);
206}
207
209 : _type(BMNT_FOLDER)
210{
211 _pfolder = new BookmarkFolder(bmf);
212}
213
215 : _type(other._type)
216{
217 if (other._type == BMNT_BOOKMARK)
218 _pbookmark = new Bookmark(*other._pbookmark);
219 else if (other._type == BMNT_FOLDER)
220 _pfolder = new BookmarkFolder(*other._pfolder);
221 else
223}
224
226{
227 if (_type == BMNT_BOOKMARK)
228 delete _pbookmark;
229 else if (_type == BMNT_FOLDER)
230 delete _pfolder;
231}
232
234{
235 clear();
236
237 _pbookmark = new Bookmark(bm);
238
239 return *this;
240}
241
243{
244 clear();
245
246 _pfolder = new BookmarkFolder(bmf);
247
248 return *this;
249}
250
252{
253 clear();
254
255 _type = other._type;
256
257 if (other._type == BMNT_BOOKMARK)
258 _pbookmark = new Bookmark(*other._pbookmark);
259 else if (other._type == BMNT_FOLDER)
260 _pfolder = new BookmarkFolder(*other._pfolder);
261
262 return *this;
263}
264
266{
267 if (_type == BMNT_BOOKMARK) {
268 delete _pbookmark;
270 }
271 else if (_type == BMNT_FOLDER) {
272 delete _pfolder;
273 _pfolder = NULL;
274 }
275
277}
278
279
281void BookmarkList::read(const_XMLPos& pos)
282{
283 const XMLNode::Children& children = pos->get_children();
284
285 for(XMLNode::Children::const_iterator it=children.begin(); it!=children.end(); ++it) {
286 const XMLNode& node = **it;
287 const_XMLPos sub_pos(&node);
288
289 if (node == "folder") {
291
292 folder.read(sub_pos);
293
295 } else if (node == "bookmark") {
296 Bookmark bookmark;
297
298 if (bookmark.read(sub_pos))
299 push_back(bookmark);
300 }
301 }
302}
303
305void BookmarkList::write(XMLPos& pos) const
306{
307 for(const_iterator it=begin(); it!=end(); ++it) {
308 const BookmarkNode& node = *it;
309
310 if (node._type == BookmarkNode::BMNT_FOLDER) {
311 const BookmarkFolder& folder = *node._pfolder;
312
313 folder.write(pos);
314
315 pos.back();
316 } else if (node._type == BookmarkNode::BMNT_BOOKMARK) {
317 const Bookmark& bookmark = *node._pbookmark;
318
319 if (!bookmark._url.empty())
320 bookmark.write(pos);
321 }
322 }
323}
324
325
328{
329 TV_INSERTSTRUCT tvi;
330
331 tvi.hParent = parent;
332 tvi.hInsertAfter = TVI_LAST;
333
334 TV_ITEM& tv = tvi.item;
336
337 for(const_iterator it=begin(); it!=end(); ++it) {
338 const BookmarkNode& node = *it;
339
340 tv.lParam = (LPARAM)&node;
341
342 if (node._type == BookmarkNode::BMNT_FOLDER) {
343 const BookmarkFolder& folder = *node._pfolder;
344
345 tv.pszText = (LPTSTR)folder._name.c_str();
346 tv.iImage = 3; // folder
347 tv.iSelectedImage = 4; // open folder
348 HTREEITEM hitem = TreeView_InsertItem(hwnd, &tvi);
349
350 folder._bookmarks.fill_tree(hwnd, hitem, himagelist, hdc_wnd);
351 } else if (node._type == BookmarkNode::BMNT_BOOKMARK) {
352 const Bookmark& bookmark = *node._pbookmark;
353
354 tv.pszText = (LPTSTR)bookmark._name.c_str();
355 tv.iImage = 1; // bookmark
356 tv.iSelectedImage = 2; // selected bookmark
357
358 if (!bookmark._icon_path.empty()) {
359 const Icon& icon = g_Globals._icon_cache.extract(bookmark._icon_path, bookmark._icon_idx);
360
361 if ((ICON_ID)icon != ICID_NONE)
362 tv.iImage = tv.iSelectedImage = icon.add_to_imagelist(himagelist, hdc_wnd);
363 }
364
366 }
367 }
368}
369
370
373{
375
377
378 for(Entry*entry=dir._down; entry; entry=entry->_next) {
379 if (entry->_shell_attribs & SFGAO_HIDDEN) // ignore files like "desktop.ini"
380 continue;
381
382 String name;
383
384 if (entry->_etype == ET_SHELL)
385 name = dir._folder.get_name(static_cast<ShellEntry*>(entry)->_pidl);
386 else
387 name = entry->_display_name;
388
389 if (entry->_data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
390 BookmarkFolder new_folder;
391
392 new_folder._name = DecodeXMLString(name);
393
394 if (entry->_etype == ET_SHELL) {
395 ShellDirectory new_dir(dir._folder, static_cast<ShellEntry*>(entry)->_pidl, hwnd);
397 } else {
398 entry->get_path(path, COUNTOF(path));
401 }
402
403 push_back(new_folder);
404 } else {
405 Bookmark bookmark;
406
407 bookmark._name = DecodeXMLString(name);
408
409 entry->get_path(path, COUNTOF(path));
410 _tsplitpath_s(path, NULL, 0, NULL, 0, NULL, 0, ext, COUNTOF(ext));
411
412 if (!_tcsicmp(ext, TEXT(".url"))) {
413 bookmark.read_url(path);
414 push_back(bookmark);
415 } else {
417 //assert(0);
418 }
419 }
420 }
421}
422
423
426{
427 XMLDoc xbel;
428
429 if (!xbel.read_file(path)) {
430 if (!xbel._errors.empty())
431 MessageBox(g_Globals._hwndDesktop, xbel._errors.str(),
432 TEXT("ROS Explorer - reading bookmark file"), MB_OK);
433 }
434
435 const_XMLPos pos(&xbel);
436
437 if (!pos.go_down("xbel"))
438 return false;
439
441
442 pos.back();
443
444 return true;
445}
446
449{
450 XMLDoc xbel;
451
452 XMLPos pos(&xbel);
453 pos.create("xbel");
455 pos.back();
456
457 xbel._format._doctype._name = "xbel";
458 xbel._format._doctype._public = "+//IDN python.org//DTD XML Bookmark Exchange Language 1.0//EN//XML";
459 xbel._format._doctype._system = "http://www.python.org/topics/xml/dtds/xbel-1.0.dtd";
460
461 xbel.write_file(path);
462}
463
466{
467 WaitCursor wait;
468
470
471 try {
474 } catch(COMException&) {
475 }
476
477 for(StartMenuShellDirs::iterator it=dirs.begin(); it!=dirs.end(); ++it) {
478 StartMenuDirectory& smd = *it;
479 ShellDirectory& dir = smd._dir;
480
481 try {
483 } catch(COMException&) {
484 }
485 }
486
487 return true;
488}
#define isspace(c)
Definition: acclib.h:69
int strncmp(const char *String1, const char *String2, ACPI_SIZE Count)
Definition: utclib.c:534
char * strchr(const char *String, int ch)
Definition: utclib.c:501
unsigned int dir
Definition: maze.c:112
VOID WaitCursor(BOOL bBegin)
Definition: dialog.c:114
void push_back(const_reference __x)
Definition: _list.h:509
_STLP_PRIV _List_iterator< BookmarkNode, _Const_traits< BookmarkNode > > const_iterator
Definition: _list.h:276
iterator begin()
Definition: _list.h:367
_STLP_PRIV _List_iterator< StartMenuDirectory, _Nonconst_traits< StartMenuDirectory > > iterator
Definition: _list.h:275
iterator end()
Definition: _list.h:370
#define NULL
Definition: types.h:112
#define _strnicmp(_String1, _String2, _MaxCount)
Definition: compat.h:23
#define MAX_PATH
Definition: compat.h:34
static const WCHAR *const ext[]
Definition: module.c:53
r parent
Definition: btrfs.c:3010
@ SCAN_DONT_EXTRACT_ICONS
Definition: entries.h:53
@ ET_SHELL
Definition: entries.h:37
String DecodeURLString(const char *s)
Definition: favorites.cpp:34
static void new_dir(void)
Definition: check.c:1099
GLdouble s
Definition: gl.h:2039
GLuint buffer
Definition: glext.h:5915
GLuint in
Definition: glext.h:9616
GLfloat GLfloat p
Definition: glext.h:8902
#define _tsplitpath_s
Definition: tchar.h:687
uint32_t entry
Definition: isohybrid.c:63
#define TEXT(s)
Definition: k32.h:26
ExplorerGlobals g_Globals
Definition: explorer.cpp:52
ICON_ID
Definition: globals.h:62
@ ICID_NONE
Definition: globals.h:64
#define BUFFER_LEN
Definition: utility.h:97
#define COUNTOF(x)
Definition: utility.h:93
#define _MAX_EXT
Definition: utility.h:76
static HDC
Definition: imagelist.c:92
#define eq(received, expected, label, type)
Definition: locale.c:144
int other
Definition: msacm.c:1376
#define FILE_ATTRIBUTE_DIRECTORY
Definition: nt_native.h:705
#define TVI_LAST
Definition: commctrl.h:3370
#define TVIF_TEXT
Definition: commctrl.h:3266
#define TVIF_IMAGE
Definition: commctrl.h:3267
#define TV_INSERTSTRUCT
Definition: commctrl.h:3377
#define TV_ITEM
Definition: commctrl.h:3300
#define TVIF_PARAM
Definition: commctrl.h:3268
#define TreeView_InsertItem(hwnd, lpis)
Definition: commctrl.h:3412
#define TVIF_SELECTEDIMAGE
Definition: commctrl.h:3271
ShellFolder & GetDesktopFolder()
#define CSIDL_FAVORITES
Definition: shlobj.h:2164
#define CSIDL_COMMON_FAVORITES
Definition: shlobj.h:2188
void write(XMLPos &pos) const
write bookmark folder content from XBEL formated XML tree
Definition: favorites.cpp:176
void read(const_XMLPos &pos)
read bookmark folder from XBEL formated XML tree
Definition: favorites.cpp:160
String _description
Definition: favorites.h:89
String _name
Definition: favorites.h:88
BookmarkList _bookmarks
Definition: favorites.h:90
void write(XMLPos &pos) const
write bookmark list into XBEL formated XML tree
Definition: favorites.cpp:305
void import_IE_favorites(struct ShellDirectory &dir, HWND hwnd)
import Internet Explorer bookmarks from Favorites folder into bookmark list
Definition: favorites.cpp:372
void fill_tree(HWND hwnd, HTREEITEM parent, HIMAGELIST, HDC hdc_wnd) const
fill treeview control with bookmark tree content
Definition: favorites.cpp:327
void read(const_XMLPos &pos)
read bookmark list from XBEL formated XML tree
Definition: favorites.cpp:281
void clear()
Definition: favorites.cpp:265
BookmarkNode & operator=(const Bookmark &bm)
Definition: favorites.cpp:233
Bookmark * _pbookmark
Definition: favorites.h:71
BookmarkFolder * _pfolder
Definition: favorites.h:72
BOOKMARKNODE_TYPE _type
Definition: favorites.h:68
String _description
Definition: favorites.h:37
int _icon_idx
Definition: favorites.h:40
void write(XMLPos &pos) const
write XBEL bookmark node
Definition: favorites.cpp:125
bool read_url(LPCTSTR path)
read .URL file
Definition: favorites.cpp:54
String _url
Definition: favorites.h:38
String _icon_path
Definition: favorites.h:39
bool read(const_XMLPos &pos)
convert XBEL bookmark node
Definition: favorites.cpp:86
String _name
Definition: favorites.h:36
Exception with context information.
Definition: shellclasses.h:114
base of all file and directory entries
Definition: entries.h:83
IconCache _icon_cache
Definition: globals.h:285
HWND _hwndDesktop
Definition: globals.h:289
bool read(LPCTSTR path)
read XBEL bookmark file
Definition: favorites.cpp:425
bool import_IE_favorites(HWND hwnd)
import Internet Explorer bookmarks from Favorites folder
Definition: favorites.cpp:465
void write(LPCTSTR path) const
write XBEL bookmark file
Definition: favorites.cpp:448
const Icon & extract(LPCTSTR path, ICONCACHE_FLAGS flags=ICF_NORMAL)
Definition: explorer.cpp:416
Definition: globals.h:96
int add_to_imagelist(HIMAGELIST himl, HDC hdc_wnd, COLORREF bk_color=GetSysColor(COLOR_WINDOW), HBRUSH bk_brush=GetSysColorBrush(COLOR_WINDOW)) const
Definition: explorer.cpp:306
shell folder entry
Definition: shellfs.h:54
shell file/directory entry
Definition: shellfs.h:31
ShellPath _pidl
Definition: shellfs.h:44
Retrieval of special shell folder paths.
Definition: shellclasses.h:982
StartMenuDirectory is used to store the base directory of start menus.
Definition: startmenu.h:53
ShellDirectory _dir
Definition: startmenu.h:64
Definition: fci.c:116
Definition: parser.c:49
Definition: name.c:39
Definition: dlist.c:348
_Must_inspect_result_ _In_ WDFDEVICE _In_ WDFSTRING String
Definition: wdfdevice.h:2433
_In_ LONG _In_ HWND hwnd
Definition: winddi.h:4023
LONG_PTR LPARAM
Definition: windef.h:208
#define MB_OK
Definition: winuser.h:790
#define MessageBox
Definition: winuser.h:5822
char TCHAR
Definition: xmlstorage.h:189
#define XS_toi
Definition: xmlstorage.h:244
#define XS_TEXT(x)
Definition: xmlstorage.h:237
const CHAR * LPCTSTR
Definition: xmlstorage.h:193
CHAR * LPTSTR
Definition: xmlstorage.h:192
#define _tcsicmp
Definition: xmlstorage.h:205
#define SORT_NAME
Definition: xpath.c:439