Enable project panels toggle from menu

Close #8533
This commit is contained in:
Udo Hoffmann 2020-07-06 16:21:50 +02:00 committed by Don HO
parent a74877f262
commit 783798e1ab
9 changed files with 132 additions and 61 deletions

View File

@ -810,17 +810,17 @@ bool Notepad_plus::saveProjectPanelsParams()
{ {
if (_pProjectPanel_1) if (_pProjectPanel_1)
{ {
_pProjectPanel_1->checkIfNeedSave(TEXT("Project Panel 1")); if (!_pProjectPanel_1->checkIfNeedSave()) return false;
(NppParameters::getInstance()).setWorkSpaceFilePath(0, _pProjectPanel_1->getWorkSpaceFilePath()); (NppParameters::getInstance()).setWorkSpaceFilePath(0, _pProjectPanel_1->getWorkSpaceFilePath());
} }
if (_pProjectPanel_2) if (_pProjectPanel_2)
{ {
_pProjectPanel_2->checkIfNeedSave(TEXT("Project Panel 2")); if (!_pProjectPanel_2->checkIfNeedSave()) return false;
(NppParameters::getInstance()).setWorkSpaceFilePath(1, _pProjectPanel_2->getWorkSpaceFilePath()); (NppParameters::getInstance()).setWorkSpaceFilePath(1, _pProjectPanel_2->getWorkSpaceFilePath());
} }
if (_pProjectPanel_3) if (_pProjectPanel_3)
{ {
_pProjectPanel_3->checkIfNeedSave(TEXT("Project Panel 3")); if (!_pProjectPanel_3->checkIfNeedSave()) return false;
(NppParameters::getInstance()).setWorkSpaceFilePath(2, _pProjectPanel_3->getWorkSpaceFilePath()); (NppParameters::getInstance()).setWorkSpaceFilePath(2, _pProjectPanel_3->getWorkSpaceFilePath());
} }
return (NppParameters::getInstance()).writeProjectPanelsSettings(); return (NppParameters::getInstance()).writeProjectPanelsSettings();
@ -6053,6 +6053,44 @@ void Notepad_plus::launchFileBrowser(const vector<generic_string> & folders, boo
_pFileBrowser->setClosed(false); _pFileBrowser->setClosed(false);
} }
void Notepad_plus::checkProjectMenuItem()
{
HMENU viewMenu = ::GetSubMenu(_mainMenuHandle, MENUINDEX_VIEW);
int viewMenuCount = ::GetMenuItemCount(viewMenu);
for (int i = 0; i < viewMenuCount; i++)
{
HMENU subMenu = ::GetSubMenu(viewMenu, i);
if (subMenu)
{
int subMenuCount = ::GetMenuItemCount(subMenu);
bool found = false;
bool checked = false;
for (int j = 0; j < subMenuCount; j++)
{
UINT const ids [] = {IDM_VIEW_PROJECT_PANEL_1, IDM_VIEW_PROJECT_PANEL_2, IDM_VIEW_PROJECT_PANEL_3};
UINT id = GetMenuItemID (subMenu, j);
for (int k = 0; k < _countof(ids); k++)
{
if (id == ids [k])
{
found = true;
UINT s = GetMenuState(subMenu, j, MF_BYPOSITION);
if (s & MF_CHECKED)
{
checked = true;
break;
}
}
}
}
if (found)
{
CheckMenuItem(viewMenu, i, (checked ? MF_CHECKED : MF_UNCHECKED) | MF_BYPOSITION);
break;
}
}
}
}
void Notepad_plus::launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int panelID) void Notepad_plus::launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int panelID)
{ {
@ -6060,7 +6098,7 @@ void Notepad_plus::launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int
if (!(*pProjPanel)) if (!(*pProjPanel))
{ {
(*pProjPanel) = new ProjectPanel; (*pProjPanel) = new ProjectPanel;
(*pProjPanel)->init(_pPublicInterface->getHinst(), _pPublicInterface->getHSelf()); (*pProjPanel)->init(_pPublicInterface->getHinst(), _pPublicInterface->getHSelf(), panelID);
(*pProjPanel)->setWorkSpaceFilePath(nppParam.getWorkSpaceFilePath(panelID)); (*pProjPanel)->setWorkSpaceFilePath(nppParam.getWorkSpaceFilePath(panelID));
tTbData data; tTbData data;
@ -6080,14 +6118,10 @@ void Notepad_plus::launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int
data.dlgID = cmdID; data.dlgID = cmdID;
NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker(); NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker();
generic_string title_temp = pNativeSpeaker->getAttrNameStr(PM_PROJECTPANELTITLE, "ProjectManager", "PanelTitle"); generic_string title_no = to_wstring (panelID + 1);
generic_string title_temp = pNativeSpeaker->getAttrNameStr(PM_PROJECTPANELTITLE, "ProjectManager", "PanelTitle") + TEXT(" ") + title_no;
static TCHAR title[32]; (*pProjPanel)->setPanelTitle(title_temp);
if (title_temp.length() < 32) data.pszName = (*pProjPanel)->getPanelTitle();
{
wcscpy_s(title, title_temp.c_str());
data.pszName = title;
}
::SendMessage(_pPublicInterface->getHSelf(), NPPM_DMMREGASDCKDLG, 0, reinterpret_cast<LPARAM>(&data)); ::SendMessage(_pPublicInterface->getHSelf(), NPPM_DMMREGASDCKDLG, 0, reinterpret_cast<LPARAM>(&data));
COLORREF fgColor = (NppParameters::getInstance()).getCurrentDefaultFgColor(); COLORREF fgColor = (NppParameters::getInstance()).getCurrentDefaultFgColor();
@ -6098,10 +6132,13 @@ void Notepad_plus::launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int
} }
else else
{ {
if ((*pProjPanel)->saveWorkspaceRequest()) (*pProjPanel)->openWorkSpace(nppParam.getWorkSpaceFilePath(panelID));
(*pProjPanel)->openWorkSpace(nppParam.getWorkSpaceFilePath(panelID));
} }
(*pProjPanel)->display(); (*pProjPanel)->display();
checkMenuItem(cmdID, true);
checkProjectMenuItem();
(*pProjPanel)->setClosed(false);
} }

View File

@ -387,10 +387,6 @@ private:
// and "Enable session snapshot and periodic backup" is not enabled // and "Enable session snapshot and periodic backup" is not enabled
// then WM_ENDSESSION is send with wParam == FALSE // then WM_ENDSESSION is send with wParam == FALSE
// in this case this boolean is set true, so Notepad++ will quit and its current session will be saved // in this case this boolean is set true, so Notepad++ will quit and its current session will be saved
bool _isWorkspaceFileLoadedFromCommandLine = false; // Set during Notepad_plus::doOpen if workspace file is opened.
// But it is only evaluated during startup, when doOpen
// has been called while command line interpretation.
ScintillaCtrls _scintillaCtrls4Plugins; ScintillaCtrls _scintillaCtrls4Plugins;
std::vector<std::pair<int, int> > _hideLinesMarks; std::vector<std::pair<int, int> > _hideLinesMarks;
@ -607,6 +603,7 @@ private:
void launchAnsiCharPanel(); void launchAnsiCharPanel();
void launchClipboardHistoryPanel(); void launchClipboardHistoryPanel();
void launchFileSwitcherPanel(); void launchFileSwitcherPanel();
void checkProjectMenuItem();
void launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int panelID); void launchProjectPanel(int cmdID, ProjectPanel ** pProjPanel, int panelID);
void launchDocMap(); void launchDocMap();
void launchFunctionList(); void launchFunctionList();

View File

@ -549,7 +549,7 @@ BEGIN
MENUITEM SEPARATOR MENUITEM SEPARATOR
MENUITEM "Summary...", IDM_VIEW_SUMMARY MENUITEM "Summary...", IDM_VIEW_SUMMARY
MENUITEM SEPARATOR MENUITEM SEPARATOR
POPUP "Project" POPUP "Project Panels"
BEGIN BEGIN
MENUITEM "Project Panel 1", IDM_VIEW_PROJECT_PANEL_1 MENUITEM "Project Panel 1", IDM_VIEW_PROJECT_PANEL_1
MENUITEM "Project Panel 2", IDM_VIEW_PROJECT_PANEL_2 MENUITEM "Project Panel 2", IDM_VIEW_PROJECT_PANEL_2

View File

@ -185,10 +185,6 @@ void Notepad_plus_Window::init(HINSTANCE hInst, HWND parent, const TCHAR *cmdLin
_notepad_plus_plus_core._pTrayIco->doTrayIcon(ADD); _notepad_plus_plus_core._pTrayIco->doTrayIcon(ADD);
} }
std::vector<generic_string> fns;
if (cmdLine)
fns = _notepad_plus_plus_core.loadCommandlineParams(cmdLine, cmdLineParams);
std::vector<generic_string> fileNames; std::vector<generic_string> fileNames;
std::vector<generic_string> patterns; std::vector<generic_string> patterns;
patterns.push_back(TEXT("*.xml")); patterns.push_back(TEXT("*.xml"));
@ -239,20 +235,16 @@ void Notepad_plus_Window::init(HINSTANCE hInst, HWND parent, const TCHAR *cmdLin
for (size_t i = 0, len = _notepad_plus_plus_core._internalFuncIDs.size() ; i < len ; ++i) for (size_t i = 0, len = _notepad_plus_plus_core._internalFuncIDs.size() ; i < len ; ++i)
::SendMessage(_hSelf, WM_COMMAND, _notepad_plus_plus_core._internalFuncIDs[i], 0); ::SendMessage(_hSelf, WM_COMMAND, _notepad_plus_plus_core._internalFuncIDs[i], 0);
std::vector<generic_string> fns;
if (cmdLine)
fns = _notepad_plus_plus_core.loadCommandlineParams(cmdLine, cmdLineParams);
// Launch folder as workspace after all this dockable panel being restored from the last session // Launch folder as workspace after all this dockable panel being restored from the last session
// To avoid dockable panel toggle problem. // To avoid dockable panel toggle problem.
if (cmdLineParams->_openFoldersAsWorkspace) if (cmdLineParams->_openFoldersAsWorkspace)
{ {
_notepad_plus_plus_core.launchFileBrowser(fns, true); _notepad_plus_plus_core.launchFileBrowser(fns, true);
} }
else if (_notepad_plus_plus_core._isWorkspaceFileLoadedFromCommandLine)
{
// Switch back to Project Panel 1, when a workspace file has been specified in the command line.
// This code is executed only once in lifetime of the process, at the first initialization. It is necessary, because
// the Project Panels are not loaded by Notepad_plus::doOpen only, but also by the Plugin Manager restoring the state
// of the last session from config.xml.
::SendMessage(_hSelf, WM_COMMAND, IDM_VIEW_PROJECT_PANEL_1, 0);
}
::SendMessage(_hSelf, WM_ACTIVATE, WA_ACTIVE, 0); ::SendMessage(_hSelf, WM_ACTIVATE, WA_ACTIVE, 0);
// Notify plugins that Notepad++ is ready // Notify plugins that Notepad++ is ready

View File

@ -1786,6 +1786,9 @@ LRESULT Notepad_plus::process(HWND hwnd, UINT message, WPARAM wParam, LPARAM lPa
if (nppgui._rememberLastSession) if (nppgui._rememberLastSession)
_lastRecentFileList.setLock(false); //only lock when the session is remembered _lastRecentFileList.setLock(false); //only lock when the session is remembered
if (!saveProjectPanelsParams()) allClosed = false; //writeProjectPanelsSettings
saveFileBrowserParam();
if (!allClosed) if (!allClosed)
{ {
//User cancelled the shutdown //User cancelled the shutdown
@ -1813,8 +1816,6 @@ LRESULT Notepad_plus::process(HWND hwnd, UINT message, WPARAM wParam, LPARAM lPa
saveGUIParams(); //writeGUIParams writeScintillaParams saveGUIParams(); //writeGUIParams writeScintillaParams
saveFindHistory(); //writeFindHistory saveFindHistory(); //writeFindHistory
_lastRecentFileList.saveLRFL(); //writeRecentFileHistorySettings, writeHistory _lastRecentFileList.saveLRFL(); //writeRecentFileHistorySettings, writeHistory
saveProjectPanelsParams(); //writeProjectPanelsSettings
saveFileBrowserParam();
// //
// saving config.xml // saving config.xml
// //

View File

@ -35,6 +35,7 @@
#include "VerticalFileSwitcher.h" #include "VerticalFileSwitcher.h"
#include "documentMap.h" #include "documentMap.h"
#include "functionListPanel.h" #include "functionListPanel.h"
#include "ProjectPanel.h"
#include "fileBrowser.h" #include "fileBrowser.h"
#include "Sorters.h" #include "Sorters.h"
#include "verifySignedfile.h" #include "verifySignedfile.h"
@ -687,18 +688,34 @@ void Notepad_plus::command(int id)
break; break;
case IDM_VIEW_PROJECT_PANEL_1: case IDM_VIEW_PROJECT_PANEL_1:
{
launchProjectPanel(id, &_pProjectPanel_1, 0);
}
break;
case IDM_VIEW_PROJECT_PANEL_2: case IDM_VIEW_PROJECT_PANEL_2:
{
launchProjectPanel(id, &_pProjectPanel_2, 1);
}
break;
case IDM_VIEW_PROJECT_PANEL_3: case IDM_VIEW_PROJECT_PANEL_3:
{ {
launchProjectPanel(id, &_pProjectPanel_3, 2); ProjectPanel** pp [] = {&_pProjectPanel_1, &_pProjectPanel_2, &_pProjectPanel_3};
int idx = id - IDM_VIEW_PROJECT_PANEL_1;
if (*pp [idx] == nullptr)
{
launchProjectPanel(id, pp [idx], idx);
}
else
{
if (not (*pp[idx])->isClosed())
{
if ((*pp[idx])->checkIfNeedSave())
{
if (::IsChild((*pp[idx])->getHSelf(), ::GetFocus()))
::SetFocus(_pEditView->getHSelf());
(*pp[idx])->display(false);
(*pp[idx])->setClosed(true);
checkMenuItem(id, false);
checkProjectMenuItem();
}
}
else
{
launchProjectPanel(id, pp [idx], idx);
}
}
} }
break; break;

View File

@ -211,10 +211,9 @@ BufferID Notepad_plus::doOpen(const generic_string& fileName, bool isRecursive,
if (isFileWorkspace(longFileName) && PathFileExists(longFileName)) if (isFileWorkspace(longFileName) && PathFileExists(longFileName))
{ {
nppParam.setWorkSpaceFilePath(0, longFileName); nppParam.setWorkSpaceFilePath(0, longFileName);
_isWorkspaceFileLoadedFromCommandLine = true;
// This line switches to Project Panel 1 while starting up Npp // This line switches to Project Panel 1 while starting up Npp
// and after dragging a workspace file to Npp: // and after dragging a workspace file to Npp:
command(IDM_VIEW_PROJECT_PANEL_1); launchProjectPanel(IDM_VIEW_PROJECT_PANEL_1, &_pProjectPanel_1, 0);
return BUFFER_INVALID; return BUFFER_INVALID;
} }

View File

@ -99,7 +99,7 @@ INT_PTR CALLBACK ProjectPanel::run_dlgProc(UINT message, WPARAM wParam, LPARAM l
_treeView.addCanNotDragOutList(INDEX_PROJECT); _treeView.addCanNotDragOutList(INDEX_PROJECT);
_treeView.display(); _treeView.display();
if (!openWorkSpace(_workSpaceFilePath.c_str())) if (!openWorkSpace(_workSpaceFilePath.c_str(), true))
newWorkSpace(); newWorkSpace();
return TRUE; return TRUE;
@ -185,18 +185,17 @@ INT_PTR CALLBACK ProjectPanel::run_dlgProc(UINT message, WPARAM wParam, LPARAM l
return DockingDlgInterface::run_dlgProc(message, wParam, lParam); return DockingDlgInterface::run_dlgProc(message, wParam, lParam);
} }
void ProjectPanel::checkIfNeedSave(const TCHAR *title) bool ProjectPanel::checkIfNeedSave()
{ {
if (_isDirty) if (_isDirty)
{ {
display(); const TCHAR * title = _workSpaceFilePath.length() > 0 ? PathFindFileName (_workSpaceFilePath.c_str()) : _panelTitle.c_str();
NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker(); NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker();
int res = pNativeSpeaker->messageBox("ProjectPanelChanged", int res = pNativeSpeaker->messageBox("ProjectPanelChanged",
_hSelf, _hSelf,
TEXT("The workspace was modified. Do you want to save it?"), TEXT("The workspace was modified. Do you want to save it?"),
TEXT("$STR_REPLACE$"), TEXT("$STR_REPLACE$"),
MB_YESNO | MB_ICONQUESTION, MB_YESNOCANCEL | MB_ICONQUESTION,
0, 0,
title); title);
@ -211,9 +210,17 @@ void ProjectPanel::checkIfNeedSave(const TCHAR *title)
0, 0,
title); title);
} }
//else if (res == IDNO) else if (res == IDNO)
{
// Don't save so do nothing here // Don't save so do nothing here
}
else
{
// Cancelled
return false;
}
} }
return true;
} }
void ProjectPanel::initMenus() void ProjectPanel::initMenus()
@ -362,8 +369,17 @@ void ProjectPanel::destroyMenus()
::DestroyMenu(_hFileMenu); ::DestroyMenu(_hFileMenu);
} }
bool ProjectPanel::openWorkSpace(const TCHAR *projectFileName) bool ProjectPanel::openWorkSpace(const TCHAR *projectFileName, bool force)
{ {
if ((!force) && (_workSpaceFilePath.length() > 0))
{ // Return if it is better to keep the current workspace tree
generic_string newWorkspace = projectFileName;
if (newWorkspace == _workSpaceFilePath)
return true;
if (!saveWorkspaceRequest())
return true;
}
TiXmlDocument *pXmlDocProject = new TiXmlDocument(projectFileName); TiXmlDocument *pXmlDocProject = new TiXmlDocument(projectFileName);
bool loadOkay = pXmlDocProject->LoadFile(); bool loadOkay = pXmlDocProject->LoadFile();
if (!loadOkay) if (!loadOkay)
@ -396,8 +412,6 @@ bool ProjectPanel::openWorkSpace(const TCHAR *projectFileName)
_treeView.removeAllItems(); _treeView.removeAllItems();
_workSpaceFilePath = projectFileName; _workSpaceFilePath = projectFileName;
NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker();
generic_string workspace = pNativeSpeaker->getAttrNameStr(PM_WORKSPACEROOTNAME, "ProjectManager", "WorkspaceRootName");
TCHAR * fileName = PathFindFileName(projectFileName); TCHAR * fileName = PathFindFileName(projectFileName);
HTREEITEM rootItem = _treeView.addItem(fileName, TVI_ROOT, INDEX_CLEAN_ROOT); HTREEITEM rootItem = _treeView.addItem(fileName, TVI_ROOT, INDEX_CLEAN_ROOT);
@ -432,7 +446,6 @@ bool ProjectPanel::saveWorkSpace()
{ {
writeWorkSpace(); writeWorkSpace();
setWorkSpaceDirty(false); setWorkSpaceDirty(false);
_isDirty = false;
return true; return true;
} }
} }
@ -455,7 +468,7 @@ bool ProjectPanel::writeWorkSpace(TCHAR *projectFileName)
if (!tvRoot) if (!tvRoot)
return false; return false;
TCHAR * fileName = PathFindFileName(projectFileName); TCHAR * fileName = PathFindFileName(fn2write);
_treeView.renameItem(tvRoot, fileName); _treeView.renameItem(tvRoot, fileName);
for (HTREEITEM tvProj = _treeView.getChildFrom(tvRoot); for (HTREEITEM tvProj = _treeView.getChildFrom(tvRoot);
@ -595,7 +608,12 @@ void ProjectPanel::openSelectFile()
void ProjectPanel::notified(LPNMHDR notification) void ProjectPanel::notified(LPNMHDR notification)
{ {
if ((notification->hwndFrom == _treeView.getHSelf())) if (notification->code == DMN_CLOSE)
{
::SendMessage(_hParent, WM_COMMAND, IDM_VIEW_PROJECT_PANEL_1 + _panelID, 0);
SetWindowLongPtr (getHSelf(), DWLP_MSGRESULT, _isClosed ? 0 : 1);
}
else if ((notification->hwndFrom == _treeView.getHSelf()))
{ {
TCHAR textBuffer[MAX_PATH]; TCHAR textBuffer[MAX_PATH];
TVITEM tvItem; TVITEM tvItem;
@ -1025,7 +1043,7 @@ void ProjectPanel::popupMenuCmd(int cmdID)
setFileExtFilter(fDlg); setFileExtFilter(fDlg);
if (TCHAR *fn = fDlg.doOpenSingleFileDlg()) if (TCHAR *fn = fDlg.doOpenSingleFileDlg())
{ {
if (!openWorkSpace(fn)) if (!openWorkSpace(fn, true))
{ {
NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker(); NativeLangSpeaker *pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker();
pNativeSpeaker->messageBox("ProjectPanelOpenFailed", pNativeSpeaker->messageBox("ProjectPanelOpenFailed",

View File

@ -32,7 +32,7 @@
#include "TreeView.h" #include "TreeView.h"
#include "ProjectPanel_rc.h" #include "ProjectPanel_rc.h"
#define PM_PROJECTPANELTITLE TEXT("Project") #define PM_PROJECTPANELTITLE TEXT("Project Panel")
#define PM_WORKSPACEROOTNAME TEXT("Workspace") #define PM_WORKSPACEROOTNAME TEXT("Workspace")
#define PM_NEWFOLDERNAME TEXT("Folder Name") #define PM_NEWFOLDERNAME TEXT("Folder Name")
#define PM_NEWPROJECTNAME TEXT("Project Name") #define PM_NEWPROJECTNAME TEXT("Project Name")
@ -70,8 +70,9 @@ public:
ProjectPanel(): DockingDlgInterface(IDD_PROJECTPANEL) {}; ProjectPanel(): DockingDlgInterface(IDD_PROJECTPANEL) {};
~ProjectPanel(); ~ProjectPanel();
void init(HINSTANCE hInst, HWND hPere) { void init(HINSTANCE hInst, HWND hPere, int panelID) {
DockingDlgInterface::init(hInst, hPere); DockingDlgInterface::init(hInst, hPere);
_panelID = panelID;
} }
virtual void display(bool toShow = true) const { virtual void display(bool toShow = true) const {
@ -82,9 +83,16 @@ public:
_hParent = parent2set; _hParent = parent2set;
}; };
void setPanelTitle(generic_string title) {
_panelTitle = title;
};
const TCHAR * getPanelTitle() const {
return _panelTitle.c_str();
};
void newWorkSpace(); void newWorkSpace();
bool saveWorkspaceRequest(); bool saveWorkspaceRequest();
bool openWorkSpace(const TCHAR *projectFileName); bool openWorkSpace(const TCHAR *projectFileName, bool force = false);
bool saveWorkSpace(); bool saveWorkSpace();
bool saveWorkSpaceAs(bool saveCopyAs); bool saveWorkSpaceAs(bool saveCopyAs);
void setWorkSpaceFilePath(const TCHAR *projectFileName){ void setWorkSpaceFilePath(const TCHAR *projectFileName){
@ -96,7 +104,7 @@ public:
bool isDirty() const { bool isDirty() const {
return _isDirty; return _isDirty;
}; };
void checkIfNeedSave(const TCHAR *title); bool checkIfNeedSave();
virtual void setBackgroundColor(COLORREF bgColour) { virtual void setBackgroundColor(COLORREF bgColour) {
TreeView_SetBkColor(_treeView.getHSelf(), bgColour); TreeView_SetBkColor(_treeView.getHSelf(), bgColour);
@ -113,9 +121,11 @@ protected:
HMENU _hProjectMenu = nullptr; HMENU _hProjectMenu = nullptr;
HMENU _hFolderMenu = nullptr; HMENU _hFolderMenu = nullptr;
HMENU _hFileMenu = nullptr; HMENU _hFileMenu = nullptr;
generic_string _panelTitle;
generic_string _workSpaceFilePath; generic_string _workSpaceFilePath;
generic_string _selDirOfFilesFromDirDlg; generic_string _selDirOfFilesFromDirDlg;
bool _isDirty = false; bool _isDirty = false;
int _panelID = 0;
void initMenus(); void initMenus();
void destroyMenus(); void destroyMenus();