- fix Entry::read_tree() and get_next_path_component()

- jump to FileChildWindow's directory when entered in address bar

svn path=/trunk/; revision=9105
This commit is contained in:
Martin Fuchs 2004-04-12 15:58:48 +00:00
parent d24371eaec
commit 6a3ea3a956
19 changed files with 171 additions and 76 deletions

View file

@ -60,7 +60,7 @@ void CollectProgramsThread::collect_programs(const ShellPath& path)
ShellDirectory* dir = new ShellDirectory(GetDesktopFolder(), path, 0); ShellDirectory* dir = new ShellDirectory(GetDesktopFolder(), path, 0);
_dirs.push(dir); _dirs.push(dir);
dir->smart_scan(/*SCAN_EXTRACT_ICONS|*/SCAN_FILESYSTEM); dir->smart_scan(SORT_NONE, /*SCAN_EXTRACT_ICONS|*/SCAN_FILESYSTEM);
for(Entry*entry=dir->_down; entry; entry=entry->_next) { for(Entry*entry=dir->_down; entry; entry=entry->_next) {
if (!_alive) if (!_alive)

View file

@ -112,24 +112,24 @@ Entry::~Entry()
// read directory tree and expand to the given location // read directory tree and expand to the given location
Entry* Entry::read_tree(const void* path, SORT_ORDER sortOrder) Entry* Entry::read_tree(const void* path, SORT_ORDER sortOrder, int scan_flags)
{ {
CONTEXT("Entry::read_tree()"); CONTEXT("Entry::read_tree()");
HCURSOR old_cursor = SetCursor(LoadCursor(0, IDC_WAIT)); HCURSOR old_cursor = SetCursor(LoadCursor(0, IDC_WAIT));
Entry* entry = this; Entry* entry = this;
Entry* next_entry = entry;
for(const void*p=path; p&&next_entry; p=entry->get_next_path_component(p)) { for(const void*p=path; p && entry; ) {
entry = next_entry; entry->smart_scan(sortOrder, scan_flags);
entry->read_directory(sortOrder);
if (entry->_down) if (entry->_down)
entry->_expanded = true; entry->_expanded = true;
next_entry = entry->find_entry(p); Entry* found = entry->find_entry(p);
p = entry->get_next_path_component(p);
entry = found;
} }
SetCursor(old_cursor); SetCursor(old_cursor);
@ -138,9 +138,9 @@ Entry* Entry::read_tree(const void* path, SORT_ORDER sortOrder)
} }
void Entry::read_directory(SORT_ORDER sortOrder, int scan_flags) void Entry::read_directory_base(SORT_ORDER sortOrder, int scan_flags)
{ {
CONTEXT("Entry::read_directory(SORT_ORDER)"); CONTEXT("Entry::read_directory_base()");
// call into subclass // call into subclass
read_directory(scan_flags); read_directory(scan_flags);
@ -304,13 +304,13 @@ void Entry::sort_directory(SORT_ORDER sortOrder)
} }
void Entry::smart_scan(int scan_flags) void Entry::smart_scan(SORT_ORDER sortOrder, int scan_flags)
{ {
CONTEXT("Entry::smart_scan()"); CONTEXT("Entry::smart_scan()");
if (!_scanned) { if (!_scanned) {
free_subentries(); free_subentries();
read_directory(SORT_NAME, scan_flags); // we could use IShellFolder2::GetDefaultColumn to determine sort order read_directory_base(sortOrder, scan_flags); ///@todo We could use IShellFolder2::GetDefaultColumn to determine sort order.
} }
} }
@ -475,18 +475,26 @@ void Entry::free_subentries()
} }
const void* Directory::get_next_path_component(const void* p) Entry* Root::read_tree(LPCTSTR path, int scan_flags)
{ {
LPCTSTR s = (LPCTSTR) p; Entry* entry;
while(*s && *s!=TEXT('\\') && *s!=TEXT('/')) if (path && *path)
++s; entry = _entry->read_tree(path, _sort_order);
else {
entry = _entry->read_tree(NULL, _sort_order);
while(*s==TEXT('\\') || *s==TEXT('/')) _entry->smart_scan();
++s;
if (!*s) if (_entry->_down)
return NULL; _entry->_expanded = true;
}
return s;
return entry;
}
Entry* Root::read_tree(LPCITEMIDLIST pidl, int scan_flags)
{
return _entry->read_tree(pidl, _sort_order);
} }

View file

@ -99,14 +99,14 @@ public:
void free_subentries(); void free_subentries();
void read_directory(SORT_ORDER sortOrder, int scan_flags=SCAN_ALL); void read_directory_base(SORT_ORDER sortOrder=SORT_NAME, int scan_flags=SCAN_ALL);
Entry* read_tree(const void* path, SORT_ORDER sortOrder); Entry* read_tree(const void* path, SORT_ORDER sortOrder=SORT_NAME, int scan_flags=SCAN_ALL);
void sort_directory(SORT_ORDER sortOrder); void sort_directory(SORT_ORDER sortOrder);
void smart_scan(int scan_flags=SCAN_ALL); void smart_scan(SORT_ORDER sortOrder=SORT_NAME, int scan_flags=SCAN_ALL);
void extract_icon(); void extract_icon();
virtual void read_directory(int scan_flags=SCAN_ALL) {} virtual void read_directory(int scan_flags=SCAN_ALL) {}
virtual const void* get_next_path_component(const void*) {return NULL;} virtual const void* get_next_path_component(const void*) const {return NULL;}
virtual Entry* find_entry(const void*) {return NULL;} virtual Entry* find_entry(const void*) {return NULL;}
virtual bool get_path(PTSTR path) const = 0; virtual bool get_path(PTSTR path) const = 0;
virtual ShellPath create_absolute_pidl() const {return (LPCITEMIDLIST)NULL;} virtual ShellPath create_absolute_pidl() const {return (LPCITEMIDLIST)NULL;}
@ -121,9 +121,6 @@ protected:
Directory() : _path(NULL) {} Directory() : _path(NULL) {}
virtual ~Directory() {} virtual ~Directory() {}
// default implementation like that of Windows file systems
virtual const void* get_next_path_component(const void*);
void* _path; void* _path;
}; };
@ -139,4 +136,8 @@ struct Root {
TCHAR _fs[_MAX_DIR]; TCHAR _fs[_MAX_DIR];
DWORD _drive_type; DWORD _drive_type;
DWORD _fs_flags; DWORD _fs_flags;
SORT_ORDER _sort_order;
Entry* read_tree(LPCTSTR path, int scan_flags=SCAN_ALL);
Entry* read_tree(LPCITEMIDLIST pidl, int scan_flags=SCAN_ALL);
}; };

View file

@ -203,6 +203,23 @@ void FATDirectory::read_directory(int scan_flags)
} }
const void* FATDirectory::get_next_path_component(const void* p) const
{
LPCTSTR s = (LPCTSTR) p;
while(*s && *s!=TEXT('\\') && *s!=TEXT('/'))
++s;
while(*s==TEXT('\\') || *s==TEXT('/'))
++s;
if (!*s)
return NULL;
return s;
}
Entry* FATDirectory::find_entry(const void* p) Entry* FATDirectory::find_entry(const void* p)
{ {
LPCTSTR name = (LPCTSTR)p; LPCTSTR name = (LPCTSTR)p;

View file

@ -51,6 +51,7 @@ struct FATDirectory : public FATEntry, public Directory
~FATDirectory(); ~FATDirectory();
virtual void read_directory(int scan_flags=SCAN_ALL); virtual void read_directory(int scan_flags=SCAN_ALL);
virtual const void* get_next_path_component(const void*) const;
virtual Entry* find_entry(const void*); virtual Entry* find_entry(const void*);
protected: protected:

View file

@ -138,6 +138,8 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
switch(info._etype) { switch(info._etype) {
case ET_SHELL: { //@@ separate into FileChildWindow in ShellChildWindow, WinChildWindow, UnixChildWindow ? case ET_SHELL: { //@@ separate into FileChildWindow in ShellChildWindow, WinChildWindow, UnixChildWindow ?
_root._drive_type = DRIVE_UNKNOWN; _root._drive_type = DRIVE_UNKNOWN;
_root._sort_order = SORT_NAME;
lstrcpy(drv, TEXT("\\")); lstrcpy(drv, TEXT("\\"));
lstrcpy(_root._volname, TEXT("Desktop")); lstrcpy(_root._volname, TEXT("Desktop"));
_root._fs_flags = 0; _root._fs_flags = 0;
@ -145,12 +147,13 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
_root._entry = new ShellDirectory(GetDesktopFolder(), DesktopFolderPath(), hwnd); _root._entry = new ShellDirectory(GetDesktopFolder(), DesktopFolderPath(), hwnd);
const ShellChildWndInfo& shell_info = static_cast<const ShellChildWndInfo&>(info); const ShellChildWndInfo& shell_info = static_cast<const ShellChildWndInfo&>(info);
entry = _root._entry->read_tree((LPCTSTR)&*shell_info._shell_path, SORT_NAME); entry = _root.read_tree(&*shell_info._shell_path);
break;} break;}
#ifdef __WINE__ #ifdef __WINE__
case ET_UNIX: case ET_UNIX:
_root._drive_type = GetDriveType(info._path); _root._drive_type = GetDriveType(info._path);
_root._sort_order = SORT_NAME;
_tsplitpath(info._path, drv, NULL, NULL, NULL); _tsplitpath(info._path, drv, NULL, NULL, NULL);
lstrcat(drv, TEXT("/")); lstrcat(drv, TEXT("/"));
@ -159,12 +162,13 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
lstrcpy(_root._fs, TEXT("unixfs")); lstrcpy(_root._fs, TEXT("unixfs"));
lstrcpy(_root._path, TEXT("/")); lstrcpy(_root._path, TEXT("/"));
_root._entry = new UnixDirectory(_root._path); _root._entry = new UnixDirectory(_root._path);
entry = _root._entry->read_tree(info._path, SORT_NAME); entry = _root.read_tree(info._path+_tcslen(_root._path));
break; break;
#endif #endif
case ET_NTOBJS: case ET_NTOBJS:
_root._drive_type = DRIVE_UNKNOWN; _root._drive_type = DRIVE_UNKNOWN;
_root._sort_order = SORT_NAME;
_tsplitpath(info._path, drv, NULL, NULL, NULL); _tsplitpath(info._path, drv, NULL, NULL, NULL);
lstrcat(drv, TEXT("\\")); lstrcat(drv, TEXT("\\"));
@ -172,11 +176,12 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
lstrcpy(_root._fs, TEXT("NTOBJ")); lstrcpy(_root._fs, TEXT("NTOBJ"));
lstrcpy(_root._path, drv); lstrcpy(_root._path, drv);
_root._entry = new NtObjDirectory(_root._path); _root._entry = new NtObjDirectory(_root._path);
entry = _root._entry->read_tree(info._path, SORT_NAME); entry = _root.read_tree(info._path+_tcslen(_root._path));
break; break;
case ET_REGISTRY: case ET_REGISTRY:
_root._drive_type = DRIVE_UNKNOWN; _root._drive_type = DRIVE_UNKNOWN;
_root._sort_order = SORT_NONE;
_tsplitpath(info._path, drv, NULL, NULL, NULL); _tsplitpath(info._path, drv, NULL, NULL, NULL);
lstrcat(drv, TEXT("\\")); lstrcat(drv, TEXT("\\"));
@ -184,11 +189,12 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
lstrcpy(_root._fs, TEXT("Registry")); lstrcpy(_root._fs, TEXT("Registry"));
lstrcpy(_root._path, drv); lstrcpy(_root._path, drv);
_root._entry = new RegistryRoot(); _root._entry = new RegistryRoot();
entry = _root._entry->read_tree(info._path, SORT_NONE); entry = _root.read_tree(info._path+_tcslen(_root._path));
break; break;
case ET_FAT: { case ET_FAT: {
_root._drive_type = DRIVE_UNKNOWN; _root._drive_type = DRIVE_UNKNOWN;
_root._sort_order = SORT_NONE;
_tsplitpath(info._path, drv, NULL, NULL, NULL); _tsplitpath(info._path, drv, NULL, NULL, NULL);
lstrcat(drv, TEXT("\\")); lstrcat(drv, TEXT("\\"));
@ -199,19 +205,20 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
if (drive->_hDrive != INVALID_HANDLE_VALUE) { if (drive->_hDrive != INVALID_HANDLE_VALUE) {
_root._entry = drive; _root._entry = drive;
entry = _root._entry->read_tree(info._path, SORT_NONE); entry = _root.read_tree(info._path+_tcslen(_root._path));
} }
break;} break;}
default: // ET_WINDOWS default: // ET_WINDOWS
_root._drive_type = GetDriveType(info._path); _root._drive_type = GetDriveType(info._path);
_root._sort_order = SORT_NAME;
_tsplitpath(info._path, drv, NULL, NULL, NULL); _tsplitpath(info._path, drv, NULL, NULL, NULL);
lstrcat(drv, TEXT("\\")); lstrcat(drv, TEXT("\\"));
GetVolumeInformation(drv, _root._volname, _MAX_FNAME, 0, 0, &_root._fs_flags, _root._fs, _MAX_DIR); GetVolumeInformation(drv, _root._volname, _MAX_FNAME, 0, 0, &_root._fs_flags, _root._fs, _MAX_DIR);
lstrcpy(_root._path, drv); lstrcpy(_root._path, drv);
_root._entry = new WinDirectory(_root._path); _root._entry = new WinDirectory(_root._path);
entry = _root._entry->read_tree(info._path, SORT_NAME); entry = _root.read_tree(info._path+_tcslen(_root._path));
} }
if (_root._entry) { if (_root._entry) {
@ -230,17 +237,17 @@ FileChildWindow::FileChildWindow(HWND hwnd, const FileChildWndInfo& info)
COL_TYPE|COL_SIZE|COL_DATE|COL_TIME|COL_ATTRIBUTES|COL_INDEX|COL_LINKS|COL_CONTENT)); COL_TYPE|COL_SIZE|COL_DATE|COL_TIME|COL_ATTRIBUTES|COL_INDEX|COL_LINKS|COL_CONTENT));
} }
_sortOrder = SORT_NAME;
_header_wdths_ok = false; _header_wdths_ok = false;
if (entry) if (entry)
set_curdir(entry); set_curdir(entry);
else
set_curdir(_root._entry);
if (_left_hwnd) { if (_left_hwnd) {
int idx = ListBox_FindItemData(_left_hwnd, ListBox_GetCurSel(_left_hwnd), _left->_cur); int idx = ListBox_FindItemData(_left_hwnd, ListBox_GetCurSel(_left_hwnd), _left->_cur);
ListBox_SetCurSel(_left_hwnd, idx); ListBox_SetCurSel(_left_hwnd, idx);
//SetFocus(_left_hwnd);
///@todo scroll to visibility
} }
// store path into history // store path into history
@ -263,8 +270,10 @@ void FileChildWindow::set_curdir(Entry* entry)
if (!entry->_scanned) if (!entry->_scanned)
scan_entry(entry); scan_entry(entry);
else { else {
HiddenWindow hide(_right_hwnd);
ListBox_ResetContent(_right_hwnd); ListBox_ResetContent(_right_hwnd);
_right->insert_entries(entry->_down, -1); _right->insert_entries(entry->_down);
_right->calc_widths(false); _right->calc_widths(false);
_right->set_header(); _right->set_header();
} }
@ -277,7 +286,7 @@ void FileChildWindow::set_curdir(Entry* entry)
if (_path[0]) if (_path[0])
if (SetCurrentDirectory(_path)) if (SetCurrentDirectory(_path))
set_url(_path); //@@ use "file://" format? set_url(_path); //set_url(FmtString(TEXT("file://%s"), _path));
else else
_path[0] = TEXT('\0'); _path[0] = TEXT('\0');
} }
@ -313,6 +322,8 @@ bool FileChildWindow::expand_entry(Entry* dir)
dir->_expanded = true; dir->_expanded = true;
// insert entries in left pane // insert entries in left pane
HiddenWindow hide(_left_hwnd);
_left->insert_entries(p, idx); _left->insert_entries(p, idx);
if (!_header_wdths_ok) { if (!_header_wdths_ok) {
@ -621,15 +632,16 @@ void FileChildWindow::scan_entry(Entry* entry)
entry->_expanded = false; entry->_expanded = false;
// read contents from disk // read contents from disk
entry->read_directory(_sortOrder); entry->read_directory_base(_root._sort_order); ///@todo use modifyable sort order instead of fixed file system default
// insert found entries in right pane // insert found entries in right pane
_right->insert_entries(entry->_down, -1); HiddenWindow hide(_right_hwnd);
_right->insert_entries(entry->_down);
_right->calc_widths(false); _right->calc_widths(false);
_right->set_header(); _right->set_header();
_header_wdths_ok = FALSE; _header_wdths_ok = false;
SetCursor(old_cursor); SetCursor(old_cursor);
} }
@ -652,42 +664,61 @@ String FileChildWindow::jump_to_int(LPCTSTR url)
switch(_root._entry->_etype) { switch(_root._entry->_etype) {
case ET_SHELL: { //@@ separate into FileChildWindow in ShellChildWindow, WinChildWindow, UnixChildWindow ? case ET_SHELL: { //@@ separate into FileChildWindow in ShellChildWindow, WinChildWindow, UnixChildWindow ?
ShellPath shell_path(dir); ShellPath shell_path(dir);
entry = _root._entry->read_tree((LPCTSTR)&*shell_path, SORT_NAME); entry = _root.read_tree(&*shell_path);
break;} break;}
#ifdef __WINE__ #ifdef __WINE__
case ET_UNIX: case ET_UNIX:
entry = _root._entry->read_tree(info._path, SORT_NAME); {
LPCTSTR path = dir;
if (!_tcsicmp(path, _root._path, _tcslen(_root._path)))
path += _tcslen(_root._path);
entry = _root.read_tree(path);
}
break; break;
#endif #endif
case ET_NTOBJS: default: // ET_UNIX, ET_NTOBJS, ET_REGISTRY, ET_FAT, ET_WINDOWS
entry = _root._entry->read_tree(dir, SORT_NAME); {
break; LPCTSTR path = dir;
case ET_REGISTRY: if (!_tcsnicmp(path, _root._path, _tcslen(_root._path)))
entry = _root._entry->read_tree(dir, SORT_NONE); path += _tcslen(_root._path);
break;
case ET_FAT: { entry = _root.read_tree(path);
entry = _root._entry->read_tree(dir, SORT_NONE); }
break;}
default: // ET_WINDOWS
entry = _root._entry->read_tree(dir, SORT_NAME); //@@ smart_scan() ?!
} }
if (entry) { if (entry) {
// refresh left pane entries
HiddenWindow hide(_left_hwnd);
ListBox_ResetContent(_left_hwnd);
_left->insert_entries(_root._entry);
if (!_header_wdths_ok) {
if (_left->calc_widths(false)) {
_left->set_header();
_header_wdths_ok = true;
}
}
set_curdir(entry); set_curdir(entry);
if (_left_hwnd) { if (_left_hwnd) {
int idx = ListBox_FindItemData(_left_hwnd, ListBox_GetCurSel(_left_hwnd), entry); int idx = ListBox_FindItemData(_left_hwnd, -1, entry);
ListBox_SetCurSel(_left_hwnd, idx);
///@todo scroll to visibility if (idx != -1) { // The item should always be found.
ListBox_SetCurSel(_left_hwnd, idx);
SetFocus(_left_hwnd);
}
} }
return FmtString(TEXT("file://%s"), (LPCTSTR)dir); return dir; //FmtString(TEXT("file://%s"), (LPCTSTR)dir);
} }
} }

View file

@ -113,7 +113,6 @@ protected:
Root _root; Root _root;
Pane* _left; Pane* _left;
Pane* _right; Pane* _right;
SORT_ORDER _sortOrder;
TCHAR _path[MAX_PATH]; TCHAR _path[MAX_PATH];
bool _header_wdths_ok; bool _header_wdths_ok;

View file

@ -663,8 +663,6 @@ void Pane::insert_entries(Entry* dir, int idx)
if (!entry) if (!entry)
return; return;
SendMessage(_hwnd, WM_SETREDRAW, FALSE, 0); //ShowWindow(_hwnd, SW_HIDE);
for(; entry; entry=entry->_next) { for(; entry; entry=entry->_next) {
#ifndef _LEFT_FILES #ifndef _LEFT_FILES
if (_treePane && if (_treePane &&
@ -688,8 +686,6 @@ void Pane::insert_entries(Entry* dir, int idx)
if (_treePane && entry->_expanded) if (_treePane && entry->_expanded)
insert_entries(entry->_down, idx); insert_entries(entry->_down, idx);
} }
SendMessage(_hwnd, WM_SETREDRAW, TRUE, 0); //ShowWindow(_hwnd, SW_SHOW);
} }

View file

@ -92,7 +92,7 @@ struct Pane : public SubclassedWindow
void calc_single_width(int col); void calc_single_width(int col);
void draw_item(LPDRAWITEMSTRUCT dis, Entry* entry, int calcWidthCol=-1); void draw_item(LPDRAWITEMSTRUCT dis, Entry* entry, int calcWidthCol=-1);
void insert_entries(Entry* dir, int idx); void insert_entries(Entry* dir, int idx=-1);
BOOL command(UINT cmd); BOOL command(UINT cmd);
int Notify(int id, NMHDR* pnmh); int Notify(int id, NMHDR* pnmh);

View file

@ -181,6 +181,23 @@ void RegDirectory::read_directory(int scan_flags)
} }
const void* RegDirectory::get_next_path_component(const void* p) const
{
LPCTSTR s = (LPCTSTR) p;
while(*s && *s!=TEXT('\\'))
++s;
while(*s==TEXT('\\'))
++s;
if (!*s)
return NULL;
return s;
}
Entry* RegDirectory::find_entry(const void* p) Entry* RegDirectory::find_entry(const void* p)
{ {
LPCTSTR name = (LPCTSTR)p; LPCTSTR name = (LPCTSTR)p;

View file

@ -51,6 +51,7 @@ struct RegDirectory : public RegEntry, public Directory
} }
virtual void read_directory(int scan_flags=SCAN_ALL); virtual void read_directory(int scan_flags=SCAN_ALL);
virtual const void* get_next_path_component(const void*) const;
virtual Entry* find_entry(const void*); virtual Entry* find_entry(const void*);
protected: protected:

View file

@ -80,18 +80,20 @@ LRESULT ShellBrowserChild::Init(LPCREATESTRUCT pcs)
const String& root_name = GetDesktopFolder().get_name(_create_info._root_shell_path, SHGDN_FORPARSING); const String& root_name = GetDesktopFolder().get_name(_create_info._root_shell_path, SHGDN_FORPARSING);
_root._drive_type = DRIVE_UNKNOWN; _root._drive_type = DRIVE_UNKNOWN;
_root._sort_order = SORT_NAME;
lstrcpy(_root._volname, root_name); // most of the time "Desktop" lstrcpy(_root._volname, root_name); // most of the time "Desktop"
_root._fs_flags = 0; _root._fs_flags = 0;
lstrcpy(_root._fs, TEXT("Desktop")); lstrcpy(_root._fs, TEXT("Desktop"));
//@@ _root._entry->read_tree(shell_info._root_shell_path.get_folder(), info._shell_path, SORT_NAME/*_sortOrder*/); //@@ _root._entry->read_tree(shell_info._root_shell_path.get_folder(), info._shell_path, _root._sort_order/*_sortOrder*/);
/*@todo /*@todo
we should call read_tree() here to iterate through the hierarchy and open all folders from shell_info._root_shell_path to shell_info._shell_path we should call read_tree() here to iterate through the hierarchy and open all folders from shell_info._root_shell_path to shell_info._shell_path
-> see FileChildWindow::FileChildWindow() -> see FileChildWindow::FileChildWindow()
*/ */
_root._entry = new ShellDirectory(GetDesktopFolder(), _create_info._root_shell_path, _hwnd); _root._entry = new ShellDirectory(GetDesktopFolder(), _create_info._root_shell_path, _hwnd);
_root._entry->read_directory(); _root._entry->read_directory_base(_root._sort_order);
/* already filled by ShellDirectory constructor /* already filled by ShellDirectory constructor
lstrcpy(_root._entry->_data.cFileName, TEXT("Desktop")); */ lstrcpy(_root._entry->_data.cFileName, TEXT("Desktop")); */

View file

@ -433,7 +433,7 @@ void ShellDirectory::read_directory(int scan_flags)
_scanned = true; _scanned = true;
} }
const void* ShellDirectory::get_next_path_component(const void* p) const void* ShellDirectory::get_next_path_component(const void* p) const
{ {
LPITEMIDLIST pidl = (LPITEMIDLIST)p; LPITEMIDLIST pidl = (LPITEMIDLIST)p;
@ -450,6 +450,10 @@ Entry* ShellDirectory::find_entry(const void* p)
{ {
LPITEMIDLIST pidl = (LPITEMIDLIST) p; LPITEMIDLIST pidl = (LPITEMIDLIST) p;
// handle special case of empty trailing id list entry
if (!pidl->mkid.cb)
return this;
for(Entry*entry=_down; entry; entry=entry->_next) for(Entry*entry=_down; entry; entry=entry->_next)
if (entry->_etype == ET_SHELL) { if (entry->_etype == ET_SHELL) {
ShellEntry* se = static_cast<ShellEntry*>(entry); ShellEntry* se = static_cast<ShellEntry*>(entry);

View file

@ -99,7 +99,7 @@ struct ShellDirectory : public ShellEntry, public Directory
} }
virtual void read_directory(int scan_flags=SCAN_ALL); virtual void read_directory(int scan_flags=SCAN_ALL);
virtual const void* get_next_path_component(const void*); virtual const void* get_next_path_component(const void*) const;
virtual Entry* find_entry(const void* p); virtual Entry* find_entry(const void* p);
virtual bool get_path(PTSTR path) const; virtual bool get_path(PTSTR path) const;

View file

@ -188,6 +188,23 @@ void WinDirectory::read_directory(int scan_flags)
} }
const void* WinDirectory::get_next_path_component(const void* p) const
{
LPCTSTR s = (LPCTSTR) p;
while(*s && *s!=TEXT('\\') && *s!=TEXT('/'))
++s;
while(*s==TEXT('\\') || *s==TEXT('/'))
++s;
if (!*s)
return NULL;
return s;
}
Entry* WinDirectory::find_entry(const void* p) Entry* WinDirectory::find_entry(const void* p)
{ {
LPCTSTR name = (LPCTSTR)p; LPCTSTR name = (LPCTSTR)p;

View file

@ -61,6 +61,7 @@ struct WinDirectory : public WinEntry, public Directory
} }
virtual void read_directory(int scan_flags=SCAN_ALL); virtual void read_directory(int scan_flags=SCAN_ALL);
virtual const void* get_next_path_component(const void*) const;
virtual Entry* find_entry(const void*); virtual Entry* find_entry(const void*);
}; };

View file

@ -376,7 +376,7 @@ void BookmarkList::import_IE_favorites(ShellDirectory& dir, HWND hwnd)
{ {
TCHAR path[MAX_PATH], ext[_MAX_EXT]; TCHAR path[MAX_PATH], ext[_MAX_EXT];
dir.smart_scan(SCAN_FILESYSTEM); dir.smart_scan(SORT_NAME, SCAN_FILESYSTEM);
for(Entry*entry=dir._down; entry; entry=entry->_next) { for(Entry*entry=dir._down; entry; entry=entry->_next) {
if (entry->_shell_attribs & SFGAO_HIDDEN) // ignore files like "desktop.ini" if (entry->_shell_attribs & SFGAO_HIDDEN) // ignore files like "desktop.ini"

View file

@ -108,7 +108,7 @@ void QuickLaunchBar::AddShortcuts()
RecursiveCreateDirectory(path); RecursiveCreateDirectory(path);
_dir = new ShellDirectory(GetDesktopFolder(), path, _hwnd); _dir = new ShellDirectory(GetDesktopFolder(), path, _hwnd);
_dir->smart_scan(SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM); _dir->smart_scan(SORT_NAME, SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM);
} catch(COMException&) { } catch(COMException&) {
return; return;
} }

View file

@ -193,9 +193,9 @@ void StartMenu::AddEntries()
WaitCursor wait; WaitCursor wait;
#ifdef _LAZY_ICONEXTRACT #ifdef _LAZY_ICONEXTRACT
dir.smart_scan(SCAN_FILESYSTEM); // lazy icon extraction, try to read directly from filesystem dir.smart_scan(SORT_NAME, SCAN_FILESYSTEM); // lazy icon extraction, try to read directly from filesystem
#else #else
dir.smart_scan(SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM); dir.smart_scan(SORT_NAME, SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM);
#endif #endif
} }
@ -1870,9 +1870,9 @@ void RecentStartMenu::AddEntries()
WaitCursor wait; WaitCursor wait;
#ifdef _LAZY_ICONEXTRACT #ifdef _LAZY_ICONEXTRACT
dir.smart_scan(SCAN_FILESYSTEM); dir.smart_scan(SORT_NAME, SCAN_FILESYSTEM);
#else #else
dir.smart_scan(SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM); dir.smart_scan(SORT_NAME, SCAN_EXTRACT_ICONS|SCAN_FILESYSTEM);
#endif #endif
} }