2006-02-16 23:23:37 +00:00
/*
2006-07-31 23:21:55 +00:00
* Copyright 2003 , 2004 , 2005 , 2006 Martin Fuchs
2006-02-16 23:23:37 +00:00
*
* This library is free software ; you can redistribute it and / or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation ; either
* version 2.1 of the License , or ( at your option ) any later version .
*
* This library is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the GNU
* Lesser General Public License for more details .
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library ; if not , write to the Free Software
2009-10-27 10:34:16 +00:00
* Foundation , Inc . , 51 Franklin Street , Fifth Floor , Boston , MA 02110 - 1301 USA
2006-02-16 23:23:37 +00:00
*/
//
// Explorer clone
//
// explorer.cpp
//
// Martin Fuchs, 23.07.2003
//
// Credits: Thanks to Leon Finker for his explorer cabinet window example
//
2012-04-20 19:12:07 +00:00
# include <precomp.h> // <precomp.h> instead of "precomp.h" because the ROS build system needs this to find the precompiled header file (*.gch) in the output directory tree
2006-02-16 23:23:37 +00:00
2014-01-13 13:03:08 +00:00
# include <shlwapi.h>
2013-01-26 15:06:49 +00:00
# include <locale.h> // for setlocale()
2013-01-24 23:00:42 +00:00
2006-02-16 23:23:37 +00:00
# ifndef __WINE__
2012-04-20 19:12:07 +00:00
# include <io.h> // for dup2()
# include <fcntl.h> // for _O_RDONLY
2006-02-16 23:23:37 +00:00
# endif
2013-01-24 23:00:42 +00:00
//#include "dialogs/settings.h" // for MdiSdiDlg
2006-02-16 23:23:37 +00:00
# include "services/shellservices.h"
2012-04-20 19:12:07 +00:00
extern " C " int initialize_gdb_stub ( ) ; // start up GDB stub
2006-02-16 23:23:37 +00:00
DynamicLoadLibFct < void ( __stdcall * ) ( BOOL ) > g_SHDOCVW_ShellDDEInit ( TEXT ( " SHDOCVW " ) , 118 ) ;
ExplorerGlobals g_Globals ;
2012-04-20 19:24:27 +00:00
boolean SelectOpt = FALSE ;
2006-02-16 23:23:37 +00:00
ExplorerGlobals : : ExplorerGlobals ( )
{
2012-04-20 19:12:07 +00:00
_hInstance = 0 ;
_cfStrFName = 0 ;
2006-02-16 23:23:37 +00:00
# ifndef ROSSHELL
2012-04-20 19:12:07 +00:00
_hframeClass = 0 ;
_hMainWnd = 0 ;
_desktop_mode = false ;
_prescan_nodes = false ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
_log = NULL ;
_SHRestricted = 0 ;
_hwndDesktopBar = 0 ;
_hwndShellView = 0 ;
_hwndDesktop = 0 ;
2006-02-16 23:23:37 +00:00
}
void ExplorerGlobals : : init ( HINSTANCE hInstance )
{
2012-04-20 19:12:07 +00:00
_hInstance = hInstance ;
_SHRestricted = ( DWORD ( STDAPICALLTYPE * ) ( RESTRICTIONS ) ) GetProcAddress ( GetModuleHandle ( TEXT ( " SHELL32 " ) ) , " SHRestricted " ) ;
_icon_cache . init ( ) ;
2006-02-16 23:23:37 +00:00
}
void ExplorerGlobals : : read_persistent ( )
{
2012-04-20 19:12:07 +00:00
// read configuration file
_cfg_dir . printf ( TEXT ( " %s \\ ReactOS " ) , ( LPCTSTR ) SpecialFolderFSPath ( CSIDL_APPDATA , 0 ) ) ;
_cfg_path . printf ( TEXT ( " %s \\ ros-explorer-cfg.xml " ) , _cfg_dir . c_str ( ) ) ;
if ( ! _cfg . read_file ( _cfg_path ) ) {
if ( ! _cfg . _errors . empty ( ) ) {
MessageBox ( _hwndDesktop ,
_cfg . _errors . str ( ) ,
TEXT ( " ROS Explorer - reading user settings " ) ,
MB_OK ) ;
}
_cfg . read_file ( TEXT ( " explorer-cfg-template.xml " ) ) ;
}
// read bookmarks
_favorites_path . printf ( TEXT ( " %s \\ ros-explorer-bookmarks.xml " ) , _cfg_dir . c_str ( ) ) ;
if ( ! _favorites . read ( _favorites_path ) ) {
_favorites . import_IE_favorites ( 0 ) ;
_favorites . write ( _favorites_path ) ;
}
2006-02-16 23:23:37 +00:00
}
void ExplorerGlobals : : write_persistent ( )
{
2012-04-20 19:12:07 +00:00
// write configuration file
RecursiveCreateDirectory ( _cfg_dir ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
_cfg . write_file ( _cfg_path ) ;
_favorites . write ( _favorites_path ) ;
2006-02-16 23:23:37 +00:00
}
XMLPos ExplorerGlobals : : get_cfg ( )
{
2012-04-20 19:12:07 +00:00
XMLPos cfg_pos ( & _cfg ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
cfg_pos . smart_create ( " explorer-cfg " ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return cfg_pos ;
2006-02-16 23:23:37 +00:00
}
XMLPos ExplorerGlobals : : get_cfg ( const char * path )
{
2012-04-20 19:12:07 +00:00
XMLPos cfg_pos ( & _cfg ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
cfg_pos . smart_create ( " explorer-cfg " ) ;
cfg_pos . create_relative ( path ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return cfg_pos ;
2006-02-16 23:23:37 +00:00
}
void _log_ ( LPCTSTR txt )
{
2012-04-20 19:12:07 +00:00
FmtString msg ( TEXT ( " %s \n " ) , txt ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( g_Globals . _log )
_fputts ( msg , g_Globals . _log ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
OutputDebugString ( msg ) ;
2006-02-16 23:23:37 +00:00
}
bool FileTypeManager : : is_exe_file ( LPCTSTR ext )
{
2012-04-20 19:12:07 +00:00
static const LPCTSTR s_executable_extensions [ ] = {
TEXT ( " COM " ) ,
TEXT ( " EXE " ) ,
TEXT ( " BAT " ) ,
TEXT ( " CMD " ) ,
TEXT ( " CMM " ) ,
TEXT ( " BTM " ) ,
TEXT ( " AWK " ) ,
0
} ;
TCHAR ext_buffer [ _MAX_EXT ] ;
const LPCTSTR * p ;
LPCTSTR s ;
LPTSTR d ;
for ( s = ext + 1 , d = ext_buffer ; ( * d = toupper ( * s ) ) ; s + + )
+ + d ;
for ( p = s_executable_extensions ; * p ; p + + )
if ( ! lstrcmp ( ext_buffer , * p ) )
return true ;
return false ;
2006-02-16 23:23:37 +00:00
}
const FileTypeInfo & FileTypeManager : : operator [ ] ( String ext )
{
2012-04-20 19:12:07 +00:00
ext . toLower ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
iterator found = find ( ext ) ;
if ( found ! = end ( ) )
return found - > second ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
FileTypeInfo & ftype = super : : operator [ ] ( ext ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
ftype . _neverShowExt = false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HKEY hkey ;
TCHAR value [ MAX_PATH ] , display_name [ MAX_PATH ] ;
LONG valuelen = sizeof ( value ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! RegQueryValue ( HKEY_CLASSES_ROOT , ext , value , & valuelen ) ) {
ftype . _classname = value ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
valuelen = sizeof ( display_name ) ;
if ( ! RegQueryValue ( HKEY_CLASSES_ROOT , ftype . _classname , display_name , & valuelen ) )
ftype . _displayname = display_name ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! RegOpenKey ( HKEY_CLASSES_ROOT , ftype . _classname , & hkey ) ) {
if ( ! RegQueryValueEx ( hkey , TEXT ( " NeverShowExt " ) , 0 , NULL , NULL , NULL ) )
ftype . _neverShowExt = true ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
RegCloseKey ( hkey ) ;
}
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ftype ;
2006-02-16 23:23:37 +00:00
}
LPCTSTR FileTypeManager : : set_type ( Entry * entry , bool dont_hide_ext )
{
2012-04-20 19:12:07 +00:00
LPCTSTR ext = _tcsrchr ( entry - > _data . cFileName , TEXT ( ' . ' ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ext ) {
const FileTypeInfo & type = ( * this ) [ ext ] ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! type . _displayname . empty ( ) )
entry - > _type_name = _tcsdup ( type . _displayname ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// hide some file extensions
if ( type . _neverShowExt & & ! dont_hide_ext ) {
int len = ext - entry - > _data . cFileName ;
2008-02-12 18:49:20 +00:00
2012-04-20 19:12:07 +00:00
if ( entry - > _display_name ! = entry - > _data . cFileName )
free ( entry - > _display_name ) ;
2008-02-12 18:49:20 +00:00
2012-04-20 19:12:07 +00:00
entry - > _display_name = ( LPTSTR ) malloc ( ( len + 1 ) * sizeof ( TCHAR ) ) ;
lstrcpyn ( entry - > _display_name , entry - > _data . cFileName , len + 1 ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( is_exe_file ( ext ) )
entry - > _data . dwFileAttributes | = ATTRIBUTE_EXECUTABLE ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ext ;
2006-02-16 23:23:37 +00:00
}
Icon : : Icon ( )
2012-04-20 19:12:07 +00:00
: _id ( ICID_UNKNOWN ) ,
_itype ( IT_STATIC ) ,
_hicon ( 0 )
2006-02-16 23:23:37 +00:00
{
}
2012-04-20 19:12:07 +00:00
Icon : : Icon ( ICON_ID id , UINT nid ) //, int cx, int cy
: _id ( id ) ,
_itype ( IT_STATIC ) ,
_hicon ( ResIcon ( nid ) ) // ResIconEx(nid, cx, cy)
2006-02-16 23:23:37 +00:00
{
}
Icon : : Icon ( ICON_ID id , UINT nid , int icon_size )
2012-04-20 19:12:07 +00:00
: _id ( id ) ,
_itype ( IT_STATIC ) ,
_hicon ( ResIconEx ( nid , icon_size , icon_size ) )
2006-02-16 23:23:37 +00:00
{
}
Icon : : Icon ( ICON_TYPE itype , int id , HICON hIcon )
2012-04-20 19:12:07 +00:00
: _id ( ( ICON_ID ) id ) ,
_itype ( itype ) ,
_hicon ( hIcon )
2006-02-16 23:23:37 +00:00
{
}
Icon : : Icon ( ICON_TYPE itype , int id , int sys_idx )
2012-04-20 19:12:07 +00:00
: _id ( ( ICON_ID ) id ) ,
_itype ( itype ) ,
_sys_idx ( sys_idx )
2006-02-16 23:23:37 +00:00
{
}
void Icon : : draw ( HDC hdc , int x , int y , int cx , int cy , COLORREF bk_color , HBRUSH bk_brush ) const
{
2012-04-20 19:12:07 +00:00
if ( _itype = = IT_SYSCACHE )
ImageList_DrawEx ( g_Globals . _icon_cache . get_sys_imagelist ( ) , _sys_idx , hdc , x , y , cx , cy , bk_color , CLR_DEFAULT , ILD_NORMAL ) ;
else
DrawIconEx ( hdc , x , y , _hicon , cx , cy , 0 , bk_brush , DI_NORMAL ) ;
2006-02-16 23:23:37 +00:00
}
2012-04-20 19:12:07 +00:00
HBITMAP Icon : : create_bitmap ( COLORREF bk_color , HBRUSH hbrBkgnd , HDC hdc_wnd ) const
2006-02-16 23:23:37 +00:00
{
2012-04-20 19:12:07 +00:00
if ( _itype = = IT_SYSCACHE ) {
HIMAGELIST himl = g_Globals . _icon_cache . get_sys_imagelist ( ) ;
int cx , cy ;
ImageList_GetIconSize ( himl , & cx , & cy ) ;
HBITMAP hbmp = CreateCompatibleBitmap ( hdc_wnd , cx , cy ) ;
HDC hdc = CreateCompatibleDC ( hdc_wnd ) ;
HBITMAP hbmp_old = SelectBitmap ( hdc , hbmp ) ;
ImageList_DrawEx ( himl , _sys_idx , hdc , 0 , 0 , cx , cy , bk_color , CLR_DEFAULT , ILD_NORMAL ) ;
SelectBitmap ( hdc , hbmp_old ) ;
DeleteDC ( hdc ) ;
return hbmp ;
} else
return create_bitmap_from_icon ( _hicon , hbrBkgnd , hdc_wnd ) ;
2006-02-16 23:23:37 +00:00
}
int Icon : : add_to_imagelist ( HIMAGELIST himl , HDC hdc_wnd , COLORREF bk_color , HBRUSH bk_brush ) const
{
2012-04-20 19:12:07 +00:00
int ret ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( _itype = = IT_SYSCACHE ) {
HIMAGELIST himl = g_Globals . _icon_cache . get_sys_imagelist ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int cx , cy ;
ImageList_GetIconSize ( himl , & cx , & cy ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HBITMAP hbmp = CreateCompatibleBitmap ( hdc_wnd , cx , cy ) ;
HDC hdc = CreateCompatibleDC ( hdc_wnd ) ;
HBITMAP hbmp_old = SelectBitmap ( hdc , hbmp ) ;
ImageList_DrawEx ( himl , _sys_idx , hdc , 0 , 0 , cx , cy , bk_color , CLR_DEFAULT , ILD_NORMAL ) ;
SelectBitmap ( hdc , hbmp_old ) ;
DeleteDC ( hdc ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
ret = ImageList_Add ( himl , hbmp , 0 ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
DeleteObject ( hbmp ) ;
} else
ret = ImageList_AddAlphaIcon ( himl , _hicon , bk_brush , hdc_wnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ret ;
2006-02-16 23:23:37 +00:00
}
HBITMAP create_bitmap_from_icon ( HICON hIcon , HBRUSH hbrush_bkgnd , HDC hdc_wnd /*, int icon_size*/ )
{
2012-04-20 19:12:07 +00:00
int cx = ICON_SIZE_SMALL ;
int cy = ICON_SIZE_SMALL ;
HBITMAP hbmp = CreateCompatibleBitmap ( hdc_wnd , cx , cy ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
MemCanvas canvas ;
BitmapSelection sel ( canvas , hbmp ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
RECT rect = { 0 , 0 , cx , cy } ;
FillRect ( canvas , & rect , hbrush_bkgnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
DrawIconEx ( canvas , 0 , 0 , hIcon , cx , cy , 0 , hbrush_bkgnd , DI_NORMAL ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return hbmp ;
2006-02-16 23:23:37 +00:00
}
HBITMAP create_small_bitmap_from_icon ( HICON hIcon , HBRUSH hbrush_bkgnd , HDC hdc_wnd )
{
2012-04-20 19:12:07 +00:00
int cx = GetSystemMetrics ( SM_CXSMICON ) ;
int cy = GetSystemMetrics ( SM_CYSMICON ) ;
HBITMAP hbmp = CreateCompatibleBitmap ( hdc_wnd , cx , cy ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
MemCanvas canvas ;
BitmapSelection sel ( canvas , hbmp ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
RECT rect = { 0 , 0 , cx , cy } ;
FillRect ( canvas , & rect , hbrush_bkgnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
DrawIconEx ( canvas , 0 , 0 , hIcon , cx , cy , 0 , hbrush_bkgnd , DI_NORMAL ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return hbmp ;
2006-02-16 23:23:37 +00:00
}
int ImageList_AddAlphaIcon ( HIMAGELIST himl , HICON hIcon , HBRUSH hbrush_bkgnd , HDC hdc_wnd )
{
2012-04-20 19:12:07 +00:00
HBITMAP hbmp = create_bitmap_from_icon ( hIcon , hbrush_bkgnd , hdc_wnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int ret = ImageList_Add ( himl , hbmp , 0 ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
DeleteObject ( hbmp ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ret ;
2006-02-16 23:23:37 +00:00
}
int IconCache : : s_next_id = ICID_DYNAMIC ;
void IconCache : : init ( )
{
2012-04-20 19:12:07 +00:00
int icon_size = STARTMENUROOT_ICON_SIZE ;
_icons [ ICID_NONE ] = Icon ( IT_STATIC , ICID_NONE , ( HICON ) 0 ) ;
_icons [ ICID_FOLDER ] = Icon ( ICID_FOLDER , IDI_FOLDER ) ;
//_icons[ICID_DOCUMENT] = Icon(ICID_DOCUMENT, IDI_DOCUMENT);
_icons [ ICID_EXPLORER ] = Icon ( ICID_EXPLORER , IDI_EXPLORER ) ;
//_icons[ICID_APP] = Icon(ICID_APP, IDI_APPICON);
_icons [ ICID_CONFIG ] = Icon ( ICID_CONFIG , IDI_CONFIG , icon_size ) ;
_icons [ ICID_DOCUMENTS ] = Icon ( ICID_DOCUMENTS , IDI_DOCUMENTS , icon_size ) ;
_icons [ ICID_FAVORITES ] = Icon ( ICID_FAVORITES , IDI_FAVORITES , icon_size ) ;
_icons [ ICID_INFO ] = Icon ( ICID_INFO , IDI_INFO , icon_size ) ;
_icons [ ICID_APPS ] = Icon ( ICID_APPS , IDI_APPS , icon_size ) ;
_icons [ ICID_SEARCH ] = Icon ( ICID_SEARCH , IDI_SEARCH , icon_size ) ;
_icons [ ICID_ACTION ] = Icon ( ICID_ACTION , IDI_ACTION , icon_size ) ;
_icons [ ICID_SEARCH_DOC ] = Icon ( ICID_SEARCH_DOC , IDI_SEARCH_DOC , icon_size ) ;
_icons [ ICID_PRINTER ] = Icon ( ICID_PRINTER , IDI_PRINTER , icon_size ) ;
_icons [ ICID_NETWORK ] = Icon ( ICID_NETWORK , IDI_NETWORK , icon_size ) ;
_icons [ ICID_COMPUTER ] = Icon ( ICID_COMPUTER , IDI_COMPUTER , icon_size ) ;
_icons [ ICID_LOGOFF ] = Icon ( ICID_LOGOFF , IDI_LOGOFF , icon_size ) ;
_icons [ ICID_SHUTDOWN ] = Icon ( ICID_SHUTDOWN , IDI_SHUTDOWN , icon_size ) ;
_icons [ ICID_RESTART ] = Icon ( ICID_RESTART , IDI_RESTART , icon_size ) ;
_icons [ ICID_BOOKMARK ] = Icon ( ICID_BOOKMARK , IDI_DOT_TRANS , icon_size ) ;
_icons [ ICID_MINIMIZE ] = Icon ( ICID_MINIMIZE , IDI_MINIMIZE , icon_size ) ;
_icons [ ICID_CONTROLPAN ] = Icon ( ICID_CONTROLPAN , IDI_CONTROLPAN , icon_size ) ;
_icons [ ICID_DESKSETTING ] = Icon ( ICID_DESKSETTING , IDI_DESKSETTING , icon_size ) ;
_icons [ ICID_NETCONNS ] = Icon ( ICID_NETCONNS , IDI_NETCONNS , icon_size ) ;
_icons [ ICID_ADMIN ] = Icon ( ICID_ADMIN , IDI_ADMIN , icon_size ) ;
_icons [ ICID_RECENT ] = Icon ( ICID_RECENT , IDI_RECENT , icon_size ) ;
2006-02-16 23:23:37 +00:00
}
const Icon & IconCache : : extract ( LPCTSTR path , ICONCACHE_FLAGS flags )
{
2012-04-20 19:12:07 +00:00
// search for matching icon with unchanged flags in the cache
CacheKey mapkey ( path , flags ) ;
PathCacheMap : : iterator found = _pathCache . find ( mapkey ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pathCache . end ( ) )
return _icons [ found - > second ] ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// search for matching icon with handle
CacheKey mapkey_hicon ( path , flags | ICF_HICON ) ;
if ( flags ! = mapkey_hicon . second ) {
found = _pathCache . find ( mapkey_hicon ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pathCache . end ( ) )
return _icons [ found - > second ] ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// search for matching icon in the system image list cache
CacheKey mapkey_syscache ( path , flags | ICF_SYSCACHE ) ;
if ( flags ! = mapkey_syscache . second ) {
found = _pathCache . find ( mapkey_syscache ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pathCache . end ( ) )
return _icons [ found - > second ] ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
SHFILEINFO sfi ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int shgfi_flags = 0 ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( flags & ICF_OPEN )
shgfi_flags | = SHGFI_OPENICON ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ( flags & ( ICF_LARGE | ICF_MIDDLE | ICF_OVERLAYS | ICF_HICON ) ) & & ! ( flags & ICF_SYSCACHE ) ) {
shgfi_flags | = SHGFI_ICON ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! ( flags & ( ICF_LARGE | ICF_MIDDLE ) ) )
shgfi_flags | = SHGFI_SMALLICON ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( flags & ICF_OVERLAYS )
shgfi_flags | = SHGFI_ADDOVERLAYS ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// get small/big icons with/without overlays
if ( SHGetFileInfo ( path , 0 , & sfi , sizeof ( sfi ) , shgfi_flags ) ) {
const Icon & icon = add ( sfi . hIcon , IT_CACHED ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
///@todo limit cache size
_pathCache [ mapkey_hicon ] = icon ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return icon ;
}
} else {
assert ( ! ( flags & ICF_OVERLAYS ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
shgfi_flags | = SHGFI_SYSICONINDEX | SHGFI_SMALLICON ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// use system image list - the "search program dialog" needs it
HIMAGELIST himlSys_small = ( HIMAGELIST ) SHGetFileInfo ( path , 0 , & sfi , sizeof ( sfi ) , shgfi_flags ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( himlSys_small ) {
_himlSys_small = himlSys_small ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
const Icon & icon = add ( sfi . iIcon /*, IT_SYSCACHE*/ ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
///@todo limit cache size
_pathCache [ mapkey_syscache ] = icon ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return icon ;
}
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ ICID_NONE ] ;
2006-02-16 23:23:37 +00:00
}
const Icon & IconCache : : extract ( LPCTSTR path , int icon_idx , ICONCACHE_FLAGS flags )
{
2012-04-20 19:12:07 +00:00
IdxCacheKey key ( path , make_pair ( icon_idx , ( flags | ICF_HICON ) & ~ ICF_SYSCACHE ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
key . first . toLower ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
IdxCacheMap : : iterator found = _idxCache . find ( key ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _idxCache . end ( ) )
return _icons [ found - > second ] ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HICON hIcon ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ( int ) ExtractIconEx ( path , icon_idx , NULL , & hIcon , 1 ) > 0 ) {
const Icon & icon = add ( hIcon , IT_CACHED ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
_idxCache [ key ] = icon ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return icon ;
} else {
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
///@todo retreive "http://.../favicon.ico" format icons
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ ICID_NONE ] ;
}
2006-02-16 23:23:37 +00:00
}
const Icon & IconCache : : extract ( IExtractIcon * pExtract , LPCTSTR path , int icon_idx , ICONCACHE_FLAGS flags )
{
2012-04-20 19:12:07 +00:00
HICON hIconLarge = 0 ;
HICON hIcon ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int icon_size = ICON_SIZE_FROM_ICF ( flags ) ;
HRESULT hr = pExtract - > Extract ( path , icon_idx , & hIconLarge , & hIcon , MAKELONG ( GetSystemMetrics ( SM_CXICON ) , icon_size ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( hr = = NOERROR ) { //@@ oder SUCCEEDED(hr) ?
if ( icon_size > ICON_SIZE_SMALL ) { //@@ OK?
if ( hIcon )
DestroyIcon ( hIcon ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
hIcon = hIconLarge ;
} else {
if ( hIconLarge )
DestroyIcon ( hIconLarge ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( hIcon )
return add ( hIcon ) ; //@@ When do we want not to free this icons?
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ ICID_NONE ] ;
2006-02-16 23:23:37 +00:00
}
2012-04-20 19:12:07 +00:00
const Icon & IconCache : : extract ( LPCITEMIDLIST pidl , ICONCACHE_FLAGS flags )
2006-02-21 20:55:41 +00:00
{
2012-04-20 19:12:07 +00:00
// search for matching icon with unchanged flags in the cache
PidlCacheKey mapkey ( pidl , flags ) ;
PidlCacheMap : : iterator found = _pidlcache . find ( mapkey ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pidlcache . end ( ) )
return _icons [ found - > second ] ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
// search for matching icon with handle
PidlCacheKey mapkey_hicon ( pidl , flags | ICF_HICON ) ;
if ( flags ! = mapkey_hicon . second ) {
found = _pidlcache . find ( mapkey_hicon ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pidlcache . end ( ) )
return _icons [ found - > second ] ;
}
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
// search for matching icon in the system image list cache
PidlCacheKey mapkey_syscache ( pidl , flags | ICF_SYSCACHE ) ;
if ( flags ! = mapkey_syscache . second ) {
found = _pidlcache . find ( mapkey_syscache ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _pidlcache . end ( ) )
return _icons [ found - > second ] ;
}
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
SHFILEINFO sfi ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
int shgfi_flags = SHGFI_PIDL ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( ! ( flags & ( ICF_LARGE | ICF_MIDDLE ) ) )
shgfi_flags | = SHGFI_SMALLICON ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( flags & ICF_OPEN )
shgfi_flags | = SHGFI_OPENICON ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( flags & ICF_SYSCACHE ) {
assert ( ! ( flags & ICF_OVERLAYS ) ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
HIMAGELIST himlSys = ( HIMAGELIST ) SHGetFileInfo ( ( LPCTSTR ) pidl , 0 , & sfi , sizeof ( sfi ) , SHGFI_SYSICONINDEX | shgfi_flags ) ;
if ( himlSys ) {
const Icon & icon = add ( sfi . iIcon /*, IT_SYSCACHE*/ ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
///@todo limit cache size
_pidlcache [ mapkey_syscache ] = icon ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
return icon ;
}
} else {
if ( flags & ICF_OVERLAYS )
shgfi_flags | = SHGFI_ADDOVERLAYS ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
if ( SHGetFileInfo ( ( LPCTSTR ) pidl , 0 , & sfi , sizeof ( sfi ) , SHGFI_ICON | shgfi_flags ) ) {
const Icon & icon = add ( sfi . hIcon , IT_CACHED ) ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
///@todo limit cache size
_pidlcache [ mapkey_hicon ] = icon ;
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
return icon ;
}
}
2006-02-21 20:55:41 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ ICID_NONE ] ;
2006-02-21 20:55:41 +00:00
}
2006-02-16 23:23:37 +00:00
const Icon & IconCache : : add ( HICON hIcon , ICON_TYPE type )
{
2012-04-20 19:12:07 +00:00
int id = + + s_next_id ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ id ] = Icon ( type , id , hIcon ) ;
2006-02-16 23:23:37 +00:00
}
2012-04-20 19:12:07 +00:00
const Icon & IconCache : : add ( int sys_idx /*, ICON_TYPE type=IT_SYSCACHE*/ )
2006-02-16 23:23:37 +00:00
{
2012-04-20 19:12:07 +00:00
int id = + + s_next_id ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return _icons [ id ] = SysCacheIcon ( id , sys_idx ) ;
2006-02-16 23:23:37 +00:00
}
const Icon & IconCache : : get_icon ( int id )
{
2012-04-20 19:12:07 +00:00
return _icons [ id ] ;
2006-02-16 23:23:37 +00:00
}
2008-02-12 18:49:20 +00:00
IconCache : : ~ IconCache ( )
{
2008-05-13 21:01:09 +00:00
/* We don't need to free cached resources - they are automatically freed at process termination
2012-04-20 19:12:07 +00:00
for ( int index = s_next_id ; index > = 0 ; index - - ) {
IconMap : : iterator found = _icons . find ( index ) ;
if ( found ! = _icons . end ( ) ) {
Icon & icon = found - > second ;
if ( ( icon . get_icontype ( ) = = IT_DYNAMIC ) | |
( icon . get_icontype ( ) = = IT_CACHED ) )
{
DestroyIcon ( icon . get_hicon ( ) ) ;
_icons . erase ( found ) ;
}
}
}
2008-05-13 21:01:09 +00:00
*/
2008-02-12 18:49:20 +00:00
}
2006-02-16 23:23:37 +00:00
void IconCache : : free_icon ( int icon_id )
{
2012-04-20 19:12:07 +00:00
IconMap : : iterator found = _icons . find ( icon_id ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( found ! = _icons . end ( ) ) {
Icon & icon = found - > second ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( icon . destroy ( ) )
_icons . erase ( found ) ;
}
2006-02-16 23:23:37 +00:00
}
ResString : : ResString ( UINT nid )
{
2012-04-20 19:12:07 +00:00
TCHAR buffer [ BUFFER_LEN ] ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int len = LoadString ( g_Globals . _hInstance , nid , buffer , sizeof ( buffer ) / sizeof ( TCHAR ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
super : : assign ( buffer , len ) ;
2006-02-16 23:23:37 +00:00
}
ResIcon : : ResIcon ( UINT nid )
{
2012-04-20 19:12:07 +00:00
_hicon = LoadIcon ( g_Globals . _hInstance , MAKEINTRESOURCE ( nid ) ) ;
2006-02-16 23:23:37 +00:00
}
SmallIcon : : SmallIcon ( UINT nid )
{
2012-04-20 19:12:07 +00:00
_hicon = ( HICON ) LoadImage ( g_Globals . _hInstance , MAKEINTRESOURCE ( nid ) , IMAGE_ICON , GetSystemMetrics ( SM_CXSMICON ) , GetSystemMetrics ( SM_CYSMICON ) , LR_SHARED ) ;
2006-02-16 23:23:37 +00:00
}
ResIconEx : : ResIconEx ( UINT nid , int w , int h )
{
2012-04-20 19:12:07 +00:00
_hicon = ( HICON ) LoadImage ( g_Globals . _hInstance , MAKEINTRESOURCE ( nid ) , IMAGE_ICON , w , h , LR_SHARED ) ;
2006-02-16 23:23:37 +00:00
}
void SetWindowIcon ( HWND hwnd , UINT nid )
{
2012-04-20 19:12:07 +00:00
HICON hIcon = ResIcon ( nid ) ;
( void ) Window_SetIcon ( hwnd , ICON_BIG , hIcon ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HICON hIconSmall = SmallIcon ( nid ) ;
( void ) Window_SetIcon ( hwnd , ICON_SMALL , hIconSmall ) ;
2006-02-16 23:23:37 +00:00
}
ResBitmap : : ResBitmap ( UINT nid )
{
2012-04-20 19:12:07 +00:00
_hBmp = LoadBitmap ( g_Globals . _hInstance , MAKEINTRESOURCE ( nid ) ) ;
2006-02-16 23:23:37 +00:00
}
# ifndef ROSSHELL
void explorer_show_frame ( int cmdShow , LPTSTR lpCmdLine )
{
2012-04-20 19:12:07 +00:00
ExplorerCmd cmd ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( g_Globals . _hMainWnd ) {
if ( IsIconic ( g_Globals . _hMainWnd ) )
ShowWindow ( g_Globals . _hMainWnd , SW_RESTORE ) ;
else
SetForegroundWindow ( g_Globals . _hMainWnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . _prescan_nodes = false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
cmd . _mdi = true ;
cmd . _cmdShow = cmdShow ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// parse command line options, which may overwrite the MDI flag
if ( lpCmdLine )
cmd . ParseCmdLine ( lpCmdLine ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// create main window
MainFrameBase : : Create ( cmd ) ;
2006-02-16 23:23:37 +00:00
}
bool ExplorerCmd : : ParseCmdLine ( LPCTSTR lpCmdLine )
{
2012-04-20 19:12:07 +00:00
bool ok = true ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
LPCTSTR b = lpCmdLine ;
LPCTSTR p = b ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
while ( * b ) {
// remove leading space
while ( _istspace ( ( unsigned ) * b ) )
+ + b ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
p = b ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
bool quote = false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// options are separated by ','
for ( ; * p ; + + p ) {
if ( * p = = ' " ' ) // Quote characters may appear at any position in the command line.
quote = ! quote ;
else if ( * p = = ' , ' & & ! quote )
break ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( p > b ) {
int l = p - b ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// remove trailing space
while ( l > 0 & & _istspace ( ( unsigned ) b [ l - 1 ] ) )
- - l ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! EvaluateOption ( String ( b , l ) ) )
ok = false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( * p )
+ + p ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
b = p ;
}
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ok ;
2006-02-16 23:23:37 +00:00
}
bool ExplorerCmd : : EvaluateOption ( LPCTSTR option )
{
2012-04-20 19:12:07 +00:00
String opt_str ;
// Remove quote characters, as they are evaluated at this point.
for ( ; * option ; + + option )
if ( * option ! = ' " ' )
opt_str + = * option ;
option = opt_str ;
if ( option [ 0 ] = = ' / ' ) {
+ + option ;
// option /e for windows in explorer mode
if ( ! _tcsicmp ( option , TEXT ( " e " ) ) )
_flags | = OWM_EXPLORE ;
// option /root for rooted explorer windows
else if ( ! _tcsicmp ( option , TEXT ( " root " ) ) )
_flags | = OWM_ROOTED ;
// non-standard options: /mdi, /sdi
else if ( ! _tcsicmp ( option , TEXT ( " mdi " ) ) )
_mdi = true ;
else if ( ! _tcsicmp ( option , TEXT ( " sdi " ) ) )
_mdi = false ;
2012-04-20 19:21:16 +00:00
else if ( ! _tcsicmp ( option , TEXT ( " n " ) ) )
{
// Do nothing
}
else if ( ! _tcsicmp ( option , TEXT ( " select " ) ) )
{
SelectOpt = TRUE ;
}
2012-04-20 19:12:07 +00:00
else
return false ;
2012-04-20 19:21:16 +00:00
2012-04-20 19:12:07 +00:00
} else {
if ( ! _path . empty ( ) )
return false ;
2012-04-20 19:21:16 +00:00
if ( ( SelectOpt = = TRUE ) & & ( PathFileExists ( option ) ) )
{
WCHAR szDir [ MAX_PATH ] ;
_wsplitpath ( option , szPath , szDir , NULL , NULL ) ;
wcscat ( szPath , szDir ) ;
PathRemoveBackslash ( szPath ) ;
_path = szPath ;
SelectOpt = FALSE ;
}
else
_path = opt_str ;
2012-04-20 19:12:07 +00:00
}
return true ;
2006-02-16 23:23:37 +00:00
}
bool ExplorerCmd : : IsValidPath ( ) const
{
2012-04-20 19:12:07 +00:00
if ( ! _path . empty ( ) ) {
DWORD attribs = GetFileAttributes ( _path ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( attribs ! = INVALID_FILE_ATTRIBUTES & & ( attribs & FILE_ATTRIBUTE_DIRECTORY ) )
return true ; // file system path
else if ( * _path = = ' : ' & & _path . at ( 1 ) = = ' : ' )
return true ; // text encoded IDL
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return false ;
2006-02-16 23:23:37 +00:00
}
# else
void explorer_show_frame ( int cmdShow , LPTSTR lpCmdLine )
{
2012-04-20 19:12:07 +00:00
if ( ! lpCmdLine )
lpCmdLine = TEXT ( " explorer.exe " ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
launch_file ( GetDesktopWindow ( ) , lpCmdLine , cmdShow ) ;
2006-02-16 23:23:37 +00:00
}
# endif
PopupMenu : : PopupMenu ( UINT nid )
{
2012-04-20 19:12:07 +00:00
HMENU hMenu = LoadMenu ( g_Globals . _hInstance , MAKEINTRESOURCE ( nid ) ) ;
_hmenu = GetSubMenu ( hMenu , 0 ) ;
RemoveMenu ( hMenu , 0 , MF_BYPOSITION ) ;
DestroyMenu ( hMenu ) ;
2006-02-16 23:23:37 +00:00
}
/// "About Explorer" Dialog
struct ExplorerAboutDlg : public
2012-04-20 19:12:07 +00:00
CtlColorParent <
OwnerDrawParent < Dialog >
>
2006-02-16 23:23:37 +00:00
{
2012-04-20 19:12:07 +00:00
typedef CtlColorParent <
OwnerDrawParent < Dialog >
> super ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
ExplorerAboutDlg ( HWND hwnd )
: super ( hwnd )
{
SetWindowIcon ( hwnd , IDI_REACTOS ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
new FlatButton ( hwnd , IDOK ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
_hfont = CreateFont ( 20 , 0 , 0 , 0 , FW_BOLD , TRUE , 0 , 0 , 0 , 0 , 0 , 0 , 0 , TEXT ( " Sans Serif " ) ) ;
new ColorStatic ( hwnd , IDC_ROS_EXPLORER , RGB ( 32 , 32 , 128 ) , 0 , _hfont ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
new HyperlinkCtrl ( hwnd , IDC_WWW ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
FmtString ver_txt ( ResString ( IDS_EXPLORER_VERSION_STR ) , ( LPCTSTR ) ResString ( IDS_VERSION_STR ) ) ;
SetWindowText ( GetDlgItem ( hwnd , IDC_VERSION_TXT ) , ver_txt ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HWND hwnd_winver = GetDlgItem ( hwnd , IDC_WIN_VERSION ) ;
SetWindowText ( hwnd_winver , get_windows_version_str ( ) ) ;
SetWindowFont ( hwnd_winver , GetStockFont ( DEFAULT_GUI_FONT ) , FALSE ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
CenterWindow ( hwnd ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
~ ExplorerAboutDlg ( )
{
DeleteObject ( _hfont ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
LRESULT WndProc ( UINT nmsg , WPARAM wparam , LPARAM lparam )
{
switch ( nmsg ) {
case WM_PAINT :
Paint ( ) ;
break ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
default :
return super : : WndProc ( nmsg , wparam , lparam ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return 0 ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
void Paint ( )
{
PaintCanvas canvas ( _hwnd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HICON hicon = ( HICON ) LoadImage ( g_Globals . _hInstance , MAKEINTRESOURCE ( IDI_REACTOS_BIG ) , IMAGE_ICON , 0 , 0 , LR_SHARED ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
DrawIconEx ( canvas , 20 , 10 , hicon , 0 , 0 , 0 , 0 , DI_NORMAL ) ;
}
2006-02-16 23:23:37 +00:00
protected :
2012-04-20 19:12:07 +00:00
HFONT _hfont ;
2006-02-16 23:23:37 +00:00
} ;
void explorer_about ( HWND hwndParent )
{
2012-04-20 19:12:07 +00:00
Dialog : : DoModal ( IDD_ABOUT_EXPLORER , WINDOW_CREATOR ( ExplorerAboutDlg ) , hwndParent ) ;
2006-02-16 23:23:37 +00:00
}
static void InitInstance ( HINSTANCE hInstance )
{
2012-04-20 19:12:07 +00:00
CONTEXT ( " InitInstance " ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
setlocale ( LC_COLLATE , " " ) ; // set collating rules to local settings for compareName
2006-02-16 23:23:37 +00:00
# ifndef ROSSHELL
2012-04-20 19:12:07 +00:00
// register frame window class
g_Globals . _hframeClass = IconWindowClass ( CLASSNAME_FRAME , IDI_EXPLORER ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// register child window class
WindowClass ( CLASSNAME_CHILDWND , CS_CLASSDC | CS_DBLCLKS ) . Register ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// register tree window class
WindowClass ( CLASSNAME_WINEFILETREE , CS_CLASSDC | CS_DBLCLKS ) . Register ( ) ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
g_Globals . _cfStrFName = RegisterClipboardFormat ( CFSTR_FILENAME ) ;
2006-02-16 23:23:37 +00:00
}
int explorer_main ( HINSTANCE hInstance , LPTSTR lpCmdLine , int cmdShow )
{
2012-04-20 19:12:07 +00:00
CONTEXT ( " explorer_main " ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// initialize Common Controls library
CommonControlInit usingCmnCtrl ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
try {
InitInstance ( hInstance ) ;
} catch ( COMException & e ) {
HandleException ( e , GetDesktopWindow ( ) ) ;
return - 1 ;
}
2006-02-16 23:23:37 +00:00
# ifndef ROSSHELL
2012-04-20 19:12:07 +00:00
if ( cmdShow ! = SW_HIDE ) {
/* // don't maximize if being called from the ROS desktop
if ( cmdShow = = SW_SHOWNORMAL )
///@todo read window placement from registry
cmdShow = SW_MAXIMIZE ;
2006-02-16 23:23:37 +00:00
*/
2012-04-20 19:12:07 +00:00
explorer_show_frame ( cmdShow , lpCmdLine ) ;
}
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
Window : : MessageLoop ( ) ;
return 1 ;
2006-02-16 23:23:37 +00:00
}
static bool SetShellReadyEvent ( LPCTSTR evtName )
{
2012-04-20 19:12:07 +00:00
HANDLE hEvent = OpenEvent ( EVENT_MODIFY_STATE , FALSE , evtName ) ;
if ( ! hEvent )
return false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
SetEvent ( hEvent ) ;
CloseHandle ( hEvent ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return true ;
2006-02-16 23:23:37 +00:00
}
int WINAPI _tWinMain ( HINSTANCE hInstance , HINSTANCE hPrevInstance , LPTSTR lpCmdLine , int nShowCmd )
{
2012-04-20 19:12:07 +00:00
CONTEXT ( " WinMain() " ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
BOOL any_desktop_running = IsAnyDesktopRunning ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
BOOL startup_desktop ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// strip extended options from the front of the command line
String ext_options ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
while ( * lpCmdLine = = ' - ' ) {
while ( * lpCmdLine & & ! _istspace ( ( unsigned ) * lpCmdLine ) )
ext_options + = * lpCmdLine + + ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
while ( _istspace ( ( unsigned ) * lpCmdLine ) )
+ + lpCmdLine ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// command line option "-install" to replace previous shell application with ROS Explorer
if ( _tcsstr ( ext_options , TEXT ( " -install " ) ) ) {
// install ROS Explorer into the registry
TCHAR path [ MAX_PATH ] ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
int l = GetModuleFileName ( 0 , path , COUNTOF ( path ) ) ;
if ( l ) {
HKEY hkey ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! RegOpenKey ( HKEY_LOCAL_MACHINE , TEXT ( " SOFTWARE \\ Microsoft \\ Windows NT \\ CurrentVersion \\ Winlogon " ) , & hkey ) ) {
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
///@todo save previous shell application in config file
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
RegSetValueEx ( hkey , TEXT ( " Shell " ) , 0 , REG_SZ , ( LPBYTE ) path , l * sizeof ( TCHAR ) ) ;
RegCloseKey ( hkey ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! RegOpenKey ( HKEY_CURRENT_USER , TEXT ( " SOFTWARE \\ Microsoft \\ Windows NT \\ CurrentVersion \\ Winlogon " ) , & hkey ) ) {
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
///@todo save previous shell application in config file
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
RegSetValueEx ( hkey , TEXT ( " Shell " ) , 0 , REG_SZ , ( LPBYTE ) TEXT ( " " ) , l * sizeof ( TCHAR ) ) ;
RegCloseKey ( hkey ) ;
}
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
HWND shellWindow = GetShellWindow ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( shellWindow ) {
DWORD pid ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// terminate shell process for NT like systems
GetWindowThreadProcessId ( shellWindow , & pid ) ;
HANDLE hProcess = OpenProcess ( PROCESS_ALL_ACCESS , FALSE , pid ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// On Win 9x it's sufficient to destroy the shell window.
DestroyWindow ( shellWindow ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( TerminateProcess ( hProcess , 0 ) )
WaitForSingleObject ( hProcess , INFINITE ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
CloseHandle ( hProcess ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
startup_desktop = TRUE ;
} else {
// create desktop window and task bar only, if there is no other shell and we are
// the first explorer instance
// MS Explorer looks additionally into the registry entry HKCU\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon\shell,
// to decide wether it is currently configured as shell application.
startup_desktop = ! any_desktop_running ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
bool autostart = ! any_desktop_running ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// disable autostart if the SHIFT key is pressed
if ( GetAsyncKeyState ( VK_SHIFT ) < 0 )
autostart = false ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
# ifdef _DEBUG //MF: disabled for debugging
autostart = false ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
// If there is given the command line option "-desktop", create desktop window anyways
if ( _tcsstr ( ext_options , TEXT ( " -desktop " ) ) )
startup_desktop = TRUE ;
2006-02-16 23:23:37 +00:00
# ifndef ROSSHELL
2012-04-20 19:12:07 +00:00
else if ( _tcsstr ( ext_options , TEXT ( " -nodesktop " ) ) )
startup_desktop = FALSE ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// Don't display cabinet window in desktop mode
if ( startup_desktop & & ! _tcsstr ( ext_options , TEXT ( " -explorer " ) ) )
nShowCmd = SW_HIDE ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
if ( _tcsstr ( ext_options , TEXT ( " -noautostart " ) ) )
autostart = false ;
else if ( _tcsstr ( ext_options , TEXT ( " -autostart " ) ) )
autostart = true ;
2006-02-16 23:23:37 +00:00
# ifndef __WINE__
2012-04-20 19:12:07 +00:00
if ( _tcsstr ( ext_options , TEXT ( " -console " ) ) ) {
AllocConsole ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
_dup2 ( _open_osfhandle ( ( long ) GetStdHandle ( STD_INPUT_HANDLE ) , _O_RDONLY ) , 0 ) ;
_dup2 ( _open_osfhandle ( ( long ) GetStdHandle ( STD_OUTPUT_HANDLE ) , 0 ) , 1 ) ;
_dup2 ( _open_osfhandle ( ( long ) GetStdHandle ( STD_ERROR_HANDLE ) , 0 ) , 2 ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . _log = _fdopen ( 1 , " w " ) ;
setvbuf ( g_Globals . _log , 0 , _IONBF , 0 ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
LOG ( TEXT ( " starting explorer debug log \n " ) ) ;
}
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
if ( startup_desktop ) {
// hide the XP login screen (Credit to Nicolas Escuder)
// another undocumented event: "Global\\msgina: ReturnToWelcome"
if ( ! SetShellReadyEvent ( TEXT ( " msgina: ShellReadyEvent " ) ) )
SetShellReadyEvent ( TEXT ( " Global \\ msgina: ShellReadyEvent " ) ) ;
}
2006-02-16 23:23:37 +00:00
# ifdef ROSSHELL
2012-04-20 19:12:07 +00:00
else
return 0 ; // no shell to launch, so exit immediatelly
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
if ( ! any_desktop_running ) {
// launch the shell DDE server
if ( g_SHDOCVW_ShellDDEInit )
( * g_SHDOCVW_ShellDDEInit ) ( TRUE ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
bool use_gdb_stub = false ; // !IsDebuggerPresent();
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( _tcsstr ( ext_options , TEXT ( " -debug " ) ) )
use_gdb_stub = true ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( _tcsstr ( ext_options , TEXT ( " -break " ) ) ) {
LOG ( TEXT ( " debugger breakpoint " ) ) ;
2013-09-15 18:39:50 +00:00
__debugbreak ( ) ;
2012-04-20 19:12:07 +00:00
}
2006-02-16 23:23:37 +00:00
2013-09-15 18:39:50 +00:00
# ifdef _M_IX86
2012-04-20 19:12:07 +00:00
// activate GDB remote debugging stub if no other debugger is running
if ( use_gdb_stub ) {
LOG ( TEXT ( " waiting for debugger connection... \n " ) ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
initialize_gdb_stub ( ) ;
}
2013-09-15 18:39:50 +00:00
# endif
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . init ( hInstance ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// initialize COM and OLE before creating the desktop window
OleInit usingCOM ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// init common controls library
CommonControlInit usingCmnCtrl ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . read_persistent ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( startup_desktop ) {
WaitCursor wait ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . _desktops . init ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
g_Globals . _hwndDesktop = DesktopWindow : : Create ( ) ;
2006-02-16 23:23:37 +00:00
# ifdef _USE_HDESK
2012-04-20 19:12:07 +00:00
g_Globals . _desktops . get_current_Desktop ( ) - > _hwndDesktop = g_Globals . _hwndDesktop ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
}
if ( _tcsstr ( ext_options , TEXT ( " -? " ) ) ) {
MessageBoxA ( g_Globals . _hwndDesktop ,
" /e open cabinet window in explorer mode \r \n "
" /root open cabinet window in rooted mode \r \n "
" /mdi open cabinet window in MDI mode \r \n "
" /sdi open cabinet window in SDI mode \r \n "
" \r \n "
" -? display command line options \r \n "
" \r \n "
" -desktop start in desktop mode regardless of an already running shell \r \n "
" -nodesktop disable desktop mode \r \n "
" -explorer display cabinet window regardless of enabled desktop mode \r \n "
" \r \n "
" -install replace previous shell application with ROS Explorer \r \n "
" \r \n "
" -noautostart disable autostarts \r \n "
" -autostart enable autostarts regardless of debug build \r \n "
" \r \n "
" -console open debug console \r \n "
" \r \n "
" -debug activate GDB remote debugging stub \r \n "
" -break activate debugger breakpoint \r \n " ,
" ROS Explorer - command line options " , MB_OK ) ;
}
2014-06-15 20:02:26 +00:00
/*
* Set our shutdown parameters : we want to shutdown the very last ,
* but before any TaskMgr instance ( which has a shutdown level of 1 ) .
*/
SetProcessShutdownParameters ( 2 , 0 ) ;
2012-04-20 19:12:07 +00:00
Thread * pSSOThread = NULL ;
if ( startup_desktop ) {
// launch SSO thread to allow message processing independent from the explorer main thread
pSSOThread = new SSOThread ;
pSSOThread - > Start ( ) ;
}
/**TODO launching autostart programs can be moved into a background thread. */
if ( autostart ) {
const char * argv [ ] = { " " , " s " } ; // call startup routine in SESSION_START mode
startup ( 2 , argv ) ;
}
2006-02-16 23:23:37 +00:00
# ifndef ROSSHELL
2012-04-20 19:12:07 +00:00
if ( g_Globals . _hwndDesktop )
g_Globals . _desktop_mode = true ;
2006-02-16 23:23:37 +00:00
# endif
2012-04-20 19:12:07 +00:00
int ret = explorer_main ( hInstance , lpCmdLine , nShowCmd ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
// write configuration file
g_Globals . write_persistent ( ) ;
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( pSSOThread ) {
pSSOThread - > Stop ( ) ;
delete pSSOThread ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
if ( ! any_desktop_running ) {
// shutdown the shell DDE server
if ( g_SHDOCVW_ShellDDEInit )
( * g_SHDOCVW_ShellDDEInit ) ( FALSE ) ;
}
2006-02-16 23:23:37 +00:00
2012-04-20 19:12:07 +00:00
return ret ;
2006-02-16 23:23:37 +00:00
}