diff --git a/reactos/subsys/system/explorer/taskbar/startmenu.cpp b/reactos/subsys/system/explorer/taskbar/startmenu.cpp new file mode 100644 index 00000000000..281725b6c43 --- /dev/null +++ b/reactos/subsys/system/explorer/taskbar/startmenu.cpp @@ -0,0 +1,234 @@ +/* + * Copyright 2003 Martin Fuchs + * + * 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 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + + + // + // Explorer clone + // + // startmenu.cpp + // + // Martin Fuchs, 19.08.2003 + // + + +#include "../utility/utility.h" + +#include "../explorer.h" +#include "../globals.h" +#include "../explorer_intres.h" + +#include "taskbar.h" +#include "startmenu.h" + + +BtnWindowClass StartMenu::s_wcStartMenu(CLASSNAME_STARTMENU); + +StartMenu::StartMenu(HWND hwnd) + : super(hwnd) +{ + _next_id = IDC_FIRST_MENU; +} + +StartMenu::StartMenu(HWND hwnd, const StartMenuFolders& info) + : super(hwnd) +{ + for(StartMenuFolders::const_iterator it=info.begin(); it!=info.end(); ++it) + _dirs.push_back(ShellDirectory(Desktop(), *it, _hwnd)); +} + + +/* +HWND StartMenu::Create(int x, int y, HWND hwndParent) +{ + return Window::Create(WINDOW_CREATOR(StartMenu), NULL, s_wcStartMenu, TITLE_STARTMENU, + WS_POPUP|WS_THICKFRAME|WS_CLIPCHILDREN|WS_VISIBLE, x, y, STARTMENU_WIDTH, 4, hwndParent); +} +*/ + +HWND StartMenu::Create(int x, int y, const StartMenuFolders& folders, HWND hwndParent) +{ + return Window::Create(WINDOW_CREATOR_INFO(StartMenu,StartMenuFolders), &folders, 0, s_wcStartMenu, NULL, + WS_POPUP|WS_THICKFRAME|WS_CLIPCHILDREN|WS_VISIBLE, x, y, STARTMENU_WIDTH, 4, hwndParent); +} + + +LRESULT StartMenu::Init(LPCREATESTRUCT pcs) +{ + if (super::Init(pcs)) + return 1; + + WaitCursor wait; + + for(StartMenuShellDirs::iterator it=_dirs.begin(); it!=_dirs.end(); ++it) { + ShellDirectory& dir = *it; + + dir.smart_scan(); + + AddShellEntries(dir); + } + + return 0; +} + +void StartMenu::AddShellEntries(const ShellDirectory& dir, bool subfolders) +{ + for(const Entry*entry=dir._down; entry; entry=entry->_next) { + if (entry->_data.dwFileAttributes & FILE_ATTRIBUTE_HIDDEN) + continue; + + HICON hIcon = entry->_hicon; + + if (entry->_data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { + if (!subfolders) + continue; + + hIcon = SmallIcon(IDI_EXPLORER); + } + + AddButton(dir._folder.get_name(&*static_cast(entry)->_pidl).c_str(), hIcon); + } +} + +LRESULT StartMenu::WndProc(UINT nmsg, WPARAM wparam, LPARAM lparam) +{ + switch(nmsg) { + case WM_NCHITTEST: { + LRESULT res = super::WndProc(nmsg, wparam, lparam); + + if (res>=HTSIZEFIRST && res<=HTSIZELAST) + return HTCLIENT; // disable window resizing + else + return res; + } + + case WM_SYSCOMMAND: + if ((wparam&0xFFF0) == SC_SIZE) + return 0; // disable window resizing + goto def; + + default: def: + return super::WndProc(nmsg, wparam, lparam); + } + + return 0; +} + +int StartMenu::Command(int id, int code) +{ + switch(id) { + case IDCANCEL: + DestroyWindow(_hwnd); + break; + + default: + return super::Command(id, code); + } + + return 0; +} + +void StartMenu::AddButton(LPCTSTR text, HICON hIcon, UINT id) +{ + if (id == (UINT)-1) + id = ++_next_id; + + WindowRect rect(_hwnd); + + rect.top -= STARTMENU_LINE_HEIGHT; + + if (rect.top < 0) { + rect.top += STARTMENU_LINE_HEIGHT; + rect.bottom += STARTMENU_LINE_HEIGHT; + } + + MoveWindow(_hwnd, rect.left, rect.top, rect.right-rect.left, rect.bottom-rect.top, TRUE); + + StartMenuButton(_hwnd, rect.bottom-rect.top-STARTMENU_LINE_HEIGHT-4, text, id, hIcon); +} + + +StartMenuRoot::StartMenuRoot(HWND hwnd) + : super(hwnd) +{ +} + +HWND StartMenuRoot::Create(int x, int y, HWND hwndParent) +{ + return Window::Create(WINDOW_CREATOR(StartMenuRoot), 0, s_wcStartMenu, TITLE_STARTMENU, + WS_POPUP|WS_THICKFRAME|WS_CLIPCHILDREN|WS_VISIBLE, x, y, STARTMENU_WIDTH, 4, hwndParent); +} + +LRESULT StartMenuRoot::Init(LPCREATESTRUCT pcs) +{ + if (super::Init(pcs)) + return 1; + + WaitCursor wait; + + // insert start menu entries links from "All Users\Start Menu" and "\Start Menu" + ShellDirectory cmn_startmenu(Desktop(), SpecialFolder(CSIDL_COMMON_STARTMENU, _hwnd), _hwnd); + cmn_startmenu.read_directory(); + AddShellEntries(cmn_startmenu, false); + + ShellDirectory usr_startmenu(Desktop(), SpecialFolder(CSIDL_STARTMENU, _hwnd), _hwnd); + usr_startmenu.read_directory(); + AddShellEntries(usr_startmenu, false); + + // insert hard coded start entries + //AddButton(ResString(IDS_PROGRAMS),0, IDC_PROGRAMS); + AddButton(ResString(IDS_EXPLORE), SmallIcon(IDI_EXPLORER), IDC_EXPLORE); + AddButton(ResString(IDS_FAVORITES), 0, IDC_FAVORITES); + AddButton(ResString(IDS_DOCUMENTS), 0, IDC_DOCUMENTS); + AddButton(ResString(IDS_SETTINGS), 0, IDC_SETTINGS); + AddButton(ResString(IDS_SEARCH), 0, IDC_SEARCH); + AddButton(ResString(IDS_START_HELP),0, IDC_START_HELP); + AddButton(ResString(IDS_LAUNCH), 0, IDC_LAUNCH); + AddButton(ResString(IDS_SHUTDOWN), SmallIcon(IDI_LOGOFF), IDC_SHUTDOWN); + AddButton(ResString(IDS_LOGOFF), SmallIcon(IDI_LOGOFF), IDC_LOGOFF); + + + //TEST: open programs menu folder + StartMenuFolders prg_folders; + + prg_folders.push_back(SpecialFolder(CSIDL_COMMON_PROGRAMS, _hwnd)); + prg_folders.push_back(SpecialFolder(CSIDL_PROGRAMS, _hwnd)); + + WindowRect my_pos(_hwnd); + StartMenu::Create(my_pos.right, my_pos.top+STARTMENU_HEIGHT-4, prg_folders, _hwnd); + + + return 0; +} + +int StartMenuRoot::Command(int id, int code) +{ + switch(id) { + case IDC_LOGOFF: + DestroyWindow(GetParent(_hwnd)); //TODO: show dialog and ask for acknowledge + break; + + case IDC_SHUTDOWN: + DestroyWindow(GetParent(_hwnd)); //TODO: show dialog box and shut down system + break; + + default: + return super::Command(id, code); + } + + return 0; +} diff --git a/reactos/subsys/system/explorer/taskbar/startmenu.h b/reactos/subsys/system/explorer/taskbar/startmenu.h new file mode 100644 index 00000000000..ae8e81f7061 --- /dev/null +++ b/reactos/subsys/system/explorer/taskbar/startmenu.h @@ -0,0 +1,91 @@ +/* + * Copyright 2003 Martin Fuchs + * + * 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 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + + + // + // Explorer and Desktop clone + // + // startmenu.h + // + // Martin Fuchs, 16.08.2003 + // + + +#include + + +#define CLASSNAME_STARTMENU _T("ReactosStartmenuClass") +#define TITLE_STARTMENU _T("Start Menu") + + + // Startmenu button +struct StartMenuButton : public Button +{ + StartMenuButton(HWND parent, int y, LPCTSTR text, + UINT id, HICON hIcon, DWORD style=WS_VISIBLE|WS_CHILD|BS_PUSHBUTTON|BS_OWNERDRAW, DWORD exStyle=0) + : Button(parent, text, 2, y, STARTMENU_WIDTH-4, STARTMENU_LINE_HEIGHT, id, style, exStyle) + { + *new StartmenuEntry(_hwnd, hIcon); + + SetWindowFont(_hwnd, GetStockFont(DEFAULT_GUI_FONT), FALSE); + } +}; + + +typedef list StartMenuFolders; +typedef list StartMenuShellDirs; + + // Startmenu window +struct StartMenu : public OwnerDrawParent +{ + typedef OwnerDrawParent super; + + StartMenu(HWND hwnd); + StartMenu(HWND hwnd, const StartMenuFolders& info); + + static HWND Create(int x, int y, HWND hwndParent=0); + static HWND Create(int x, int y, const StartMenuFolders&, HWND hwndParent=0); + +protected: + int _next_id; + StartMenuShellDirs _dirs; + + static BtnWindowClass s_wcStartMenu; + + LRESULT Init(LPCREATESTRUCT pcs); + LRESULT WndProc(UINT nmsg, WPARAM wparam, LPARAM lparam); + int Command(int id, int code); + + void AddButton(LPCTSTR text, HICON hIcon=0, UINT id=(UINT)-1); + void AddShellEntries(const ShellDirectory& dir, bool subfolders=true); +}; + + + // Startmenu root window +struct StartMenuRoot : public StartMenu +{ + typedef StartMenu super; + + StartMenuRoot(HWND hwnd); + + static HWND Create(int x, int y, HWND hwndParent=0); + +protected: + LRESULT Init(LPCREATESTRUCT pcs); + int Command(int id, int code); +};