From f3f9aa82247279c7897270da9809f5a3603426cd Mon Sep 17 00:00:00 2001 From: Steven Edwards Date: Tue, 8 Jul 2003 03:21:15 +0000 Subject: [PATCH] Added a simple explorer bar to desktop. Patch by Alexander Ciobanu with parts by Martin Fuchs. svn path=/trunk/; revision=5014 --- reactos/subsys/system/explorer/desktop.c | 29 +- reactos/subsys/system/explorer/ex_bar.c | 295 +++++++++++ reactos/subsys/system/explorer/explorer.h | 15 + reactos/subsys/system/explorer/explorer.lst | 5 + reactos/subsys/system/explorer/makefile_rex | 4 +- reactos/subsys/system/explorer/readme.txt | 13 + reactos/subsys/system/explorer/startup.c | 521 ++++++++++++++++++++ 7 files changed, 868 insertions(+), 14 deletions(-) create mode 100644 reactos/subsys/system/explorer/ex_bar.c create mode 100644 reactos/subsys/system/explorer/explorer.h create mode 100644 reactos/subsys/system/explorer/explorer.lst create mode 100644 reactos/subsys/system/explorer/startup.c diff --git a/reactos/subsys/system/explorer/desktop.c b/reactos/subsys/system/explorer/desktop.c index 5e27795da9a..6f98d38c1d6 100644 --- a/reactos/subsys/system/explorer/desktop.c +++ b/reactos/subsys/system/explorer/desktop.c @@ -7,6 +7,7 @@ #include +#include "explorer.h" const char DesktopClassName[] = "DesktopWindow"; @@ -61,9 +62,15 @@ LRESULT CALLBACK DeskWndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) -int main() +int main(int argc, char *argv[]) { + int Width, Height; WNDCLASSEX wc; + HWND Desktop; + + STARTUPINFO startupinfo; + int cmdshow = SW_SHOWNORMAL; + wc.cbSize = sizeof(WNDCLASSEX); wc.style = 0; @@ -81,10 +88,6 @@ int main() if (! RegisterClassEx(&wc)) return 1; // error - - HWND Desktop; - int Width, Height; - Width = GetSystemMetrics(SM_CXSCREEN); Height = GetSystemMetrics(SM_CYSCREEN); @@ -94,15 +97,15 @@ int main() NULL, NULL, GetModuleHandle(NULL), NULL); if (! Desktop) - return 1; // error + return 1; // error - MSG Msg; + // call winefile/menu startup routine + startupinfo.wShowWindow = SW_SHOWNORMAL; + GetStartupInfo(&startupinfo); - while (GetMessage(&Msg, 0, 0, 0) != 0) - { - TranslateMessage(&Msg); - DispatchMessage(&Msg); - } + if (startupinfo.dwFlags & STARTF_USESHOWWINDOW) + cmdshow = startupinfo.wShowWindow; - return 0; // get the return code! + return Ex_BarMain(GetModuleHandle(NULL), Desktop, NULL, cmdshow); + //return startup(argc, argv); // invoke the startup groups } diff --git a/reactos/subsys/system/explorer/ex_bar.c b/reactos/subsys/system/explorer/ex_bar.c new file mode 100644 index 00000000000..ace98bedc80 --- /dev/null +++ b/reactos/subsys/system/explorer/ex_bar.c @@ -0,0 +1,295 @@ +// Explorer Panel (PlugIn based) +// +// Alexander Ciobanu +// alex@prodidactica.md +// +// + +#include +#include + +HFONT tf; +HINSTANCE PlugInsHI[2]; // PlugIns table +int PlugNumber; // Number of loaded plugins + +LRESULT WINAPI ExplorerBarProc(HWND, UINT, WPARAM, LPARAM); + +// Loads a configuration style given by PInt +// FIXME : Load all these values from registry ! +// +DWORD LoadProperty(int PInt) +{ + switch(PInt) + { + case 1: // WS_EX_Style for creating the bar + return WS_EX_DLGMODALFRAME | WS_EX_TOPMOST; + break; + case 2: // WS_Style for creating the bar + return 0; + break; + case 3: // Start X for the panel + return 0; + break; + case 4: + return 0; // Start Y for the panel + break; + case 5: + return GetSystemMetrics(SM_CXSCREEN); // XLen for the panel + break; + case 6: + return 50; // YLen for the panel + break; + } + return 0; +} + +// Initializez and creates the Explorer Panel +// HINSTANCE as a parameter +// +HWND InitializeExplorerBar(HINSTANCE hInstance, int nCmdShow) +{ + HWND ExplorerBar; + WNDCLASS ExplorerBarClass; + + ExplorerBarClass.lpszClassName = "ExplorerBar"; // ExplorerBar classname + ExplorerBarClass.lpfnWndProc = ExplorerBarProc; // Default Explorer Callback Procedure + ExplorerBarClass.style = CS_VREDRAW | CS_HREDRAW; // Styles + ExplorerBarClass.hInstance = hInstance; // Instance + ExplorerBarClass.hIcon = LoadIcon(NULL, IDI_APPLICATION); // Configurable ???? + ExplorerBarClass.hCursor = LoadCursor(NULL, IDC_ARROW); + ExplorerBarClass.hbrBackground = (HBRUSH)GetStockObject(GRAY_BRUSH); // BackGround + ExplorerBarClass.lpszMenuName = NULL; // No Menu needed for the bar + ExplorerBarClass.cbClsExtra = 0; // Nothing YET! !! + ExplorerBarClass.cbWndExtra = 0; // + + if (RegisterClass(&ExplorerBarClass) == 0) // Cold not register anything :( + { + fprintf(stderr, "Could not register Explorer Bar. Last error was 0x%X\n",GetLastError()); + return NULL; + } + + ExplorerBar = CreateWindowEx(LoadProperty(1),"ExplorerBar", + "ReactOS Explorer Bar",LoadProperty(2),LoadProperty(3),LoadProperty(4), + LoadProperty(5),LoadProperty(6),NULL,NULL,hInstance,NULL); + if (ExplorerBar == NULL) + { + fprintf(stderr, "Cold not create Explorer Bar.Last error 0x%X\n",GetLastError()); + return(NULL); + } + + tf = CreateFontA(14, 0, 0, TA_BASELINE, FW_NORMAL, FALSE, FALSE, FALSE, + ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, + DEFAULT_QUALITY, FIXED_PITCH|FF_DONTCARE, "Timmons"); + + ShowWindow(ExplorerBar, nCmdShow); // Show the bar + return ExplorerBar; +} + + +// ************************************************************************************** +// * Default Buit-in Plugin * +// ************************************************************************************** +HWND epl_AppButtons[10]; +char epl_line[10][80]; +int epl_Buttons; + + + +// Initialize the plugin +// +HINSTANCE InitializeExplorerPlugIn(HWND ExplorerHandle) +{ + FILE* Conf; // Configuration File; + char line[80]; // Blah Blah Blah + char ttl[80]; // Title of the button + int i; + int x; + + if (!(Conf=fopen("explorer.lst","r"))) // Error ! + { + fprintf(stderr,"DefaultPlugin : No configuration file found !\n"); + return NULL; + } + + fgets(line,80,Conf); // Read how many entries are in the file + epl_Buttons=atoi(line); // atoi it ! + + + for (i=0;i +#include + +#define MAX_LINE_LENGTH (2*MAX_PATH+2) + +static BOOL GetLine( HANDLE hFile, char *buf, size_t buflen ) +{ + int i=0; + buf[0]='\0'; + + do + { + DWORD read; + if( !ReadFile( hFile, buf, 1, &read, NULL ) || read!=1 ) + { + return FALSE; + } + + } while( isspace( *buf ) ); + + while( buf[i]!='\n' && i<=buflen && + ReadFile( hFile, buf+i+1, 1, NULL, NULL ) ) + { + ++i; + } + + + if( buf[i]!='\n' ) + { + return FALSE; + } + + if( i>0 && buf[i-1]=='\r' ) + --i; + + buf[i]='\0'; + + return TRUE; +} + +/* Performs the rename operations dictated in %SystemRoot%\Wininit.ini. + * Returns FALSE if there was an error, or otherwise if all is ok. + */ +static BOOL wininit() +{ + return TRUE; +} + +static BOOL pendingRename() +{ + static const WCHAR ValueName[] = {'P','e','n','d','i','n','g', + 'F','i','l','e','R','e','n','a','m','e', + 'O','p','e','r','a','t','i','o','n','s',0}; + static const WCHAR SessionW[] = { 'S','y','s','t','e','m','\\', + 'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\', + 'C','o','n','t','r','o','l','\\', + 'S','e','s','s','i','o','n',' ','M','a','n','a','g','e','r',0}; + WCHAR *buffer=NULL; + const WCHAR *src=NULL, *dst=NULL; + DWORD dataLength=0; + HKEY hSession=NULL; + DWORD res; + + printf("Entered\n"); + + if( (res=RegOpenKeyExW( HKEY_LOCAL_MACHINE, SessionW, 0, KEY_ALL_ACCESS, &hSession )) + !=ERROR_SUCCESS ) + { + if( res==ERROR_FILE_NOT_FOUND ) + { + printf("The key was not found - skipping\n"); + res=TRUE; + } + else + { + printf("Couldn't open key, error %ld\n", res ); + res=FALSE; + } + + goto end; + } + + res=RegQueryValueExW( hSession, ValueName, NULL, NULL /* The value type does not really interest us, as it is not + truely a REG_MULTI_SZ anyways */, + NULL, &dataLength ); + if( res==ERROR_FILE_NOT_FOUND ) + { + /* No value - nothing to do. Great! */ + printf("Value not present - nothing to rename\n"); + res=TRUE; + goto end; + } + + if( res!=ERROR_SUCCESS ) + { + printf("Couldn't query value's length (%ld)\n", res ); + res=FALSE; + goto end; + } + + buffer=malloc( dataLength ); + if( buffer==NULL ) + { + printf("Couldn't allocate %lu bytes for the value\n", dataLength ); + res=FALSE; + goto end; + } + + res=RegQueryValueExW( hSession, ValueName, NULL, NULL, (LPBYTE)buffer, &dataLength ); + if( res!=ERROR_SUCCESS ) + { + printf("Couldn't query value after successfully querying before (%lu),\n" + "please report to wine-devel@winehq.org\n", res); + res=FALSE; + goto end; + } + + /* Make sure that the data is long enough and ends with two NULLs. This + * simplifies the code later on. + */ + if( dataLength<2*sizeof(buffer[0]) || + buffer[dataLength/sizeof(buffer[0])-1]!='\0' || + buffer[dataLength/sizeof(buffer[0])-2]!='\0' ) + { + printf("Improper value format - doesn't end with NULL\n"); + res=FALSE; + goto end; + } + + for( src=buffer; (src-buffer)*sizeof(src[0])0 ) + { + DWORD nValLength=nMaxValue, nDataLength=nMaxCmdLine; + DWORD type; + + --i; + + if( (res=RegEnumValueW( hkRun, i, szValue, &nValLength, 0, &type, + (LPBYTE)szCmdLine, &nDataLength ))!=ERROR_SUCCESS ) + { + printf("Couldn't read in value %ld - %ld\n", i, res ); + + continue; + } + + if( bDelete && (res=RegDeleteValueW( hkRun, szValue ))!=ERROR_SUCCESS ) + { + printf("Couldn't delete value - %ld, %ld. Running command anyways.\n", i, res ); + } + + if( type!=REG_SZ ) + { + printf("Incorrect type of value #%ld (%ld)\n", i, type ); + + continue; + } + + if( (res=runCmd(szCmdLine, NULL, bSynchronous, FALSE ))==INVALID_RUNCMD_RETURN ) + { + printf("Error running cmd #%ld (%ld)\n", i, GetLastError() ); + } + + printf("Done processing cmd #%ld\n", i); + } + + res=ERROR_SUCCESS; + +end: + if( hkRun!=NULL ) + RegCloseKey( hkRun ); + if( hkWin!=NULL ) + RegCloseKey( hkWin ); + + printf("done\n"); + + return res==ERROR_SUCCESS?TRUE:FALSE; +} + +struct op_mask { + BOOL w9xonly; /* Perform only operations done on Windows 9x */ + BOOL ntonly; /* Perform only operations done on Windows NT */ + BOOL startup; /* Perform the operations that are performed every boot */ + BOOL preboot; /* Perform file renames typically done before the system starts */ + BOOL prelogin; /* Perform the operations typically done before the user logs in */ + BOOL postlogin; /* Operations done after login */ +}; + +static const struct op_mask SESSION_START={FALSE, FALSE, TRUE, TRUE, TRUE, TRUE}, + SETUP={FALSE, FALSE, FALSE, TRUE, TRUE, TRUE}; +#define DEFAULT SESSION_START + +int startup( int argc, char *argv[] ) +{ + struct op_mask ops; /* Which of the ops do we want to perform? */ + /* First, set the current directory to SystemRoot */ + TCHAR gen_path[MAX_PATH]; + DWORD res; + + res=GetWindowsDirectory( gen_path, sizeof(gen_path) ); + + if( res==0 ) + { + printf("Couldn't get the windows directory - error %ld\n", + GetLastError() ); + + return 100; + } + + if( res>=sizeof(gen_path) ) + { + printf("Windows path too long (%ld)\n", res ); + + return 100; + } + + if( !SetCurrentDirectory( gen_path ) ) + { + printf("Cannot set the dir to %s (%ld)\n", gen_path, GetLastError() ); + + return 100; + } + + if( argc>1 ) + { + switch( argv[1][0] ) + { + case 'r': /* Restart */ + ops=SETUP; + break; + case 's': /* Full start */ + ops=SESSION_START; + break; + default: + ops=DEFAULT; + break; + } + } else + ops=DEFAULT; + + /* Perform the ops by order, stopping if one fails, skipping if necessary */ + /* Shachar: Sorry for the perl syntax */ + res=(ops.ntonly || !ops.preboot || wininit())&& + (ops.w9xonly || !ops.preboot || pendingRename()) && + (ops.ntonly || !ops.prelogin || + ProcessRunKeys( HKEY_LOCAL_MACHINE, runkeys_names[RUNKEY_RUNSERVICESONCE], + TRUE, FALSE )) && + (ops.ntonly || !ops.prelogin || !ops.startup || + ProcessRunKeys( HKEY_LOCAL_MACHINE, runkeys_names[RUNKEY_RUNSERVICES], + FALSE, FALSE )) && + (!ops.postlogin || + ProcessRunKeys( HKEY_LOCAL_MACHINE, runkeys_names[RUNKEY_RUNONCE], + TRUE, TRUE )) && + (!ops.postlogin || !ops.startup || + ProcessRunKeys( HKEY_LOCAL_MACHINE, runkeys_names[RUNKEY_RUN], + FALSE, FALSE )) && + (!ops.postlogin || !ops.startup || + ProcessRunKeys( HKEY_CURRENT_USER, runkeys_names[RUNKEY_RUN], + FALSE, FALSE )); + + printf("Operation done\n"); + + //return res?0:101; +}