Resync
[CMakeLuaTailorHgBridge.git] / CMakeLua / Source / MFCDialog / CMakeSetupDialog.cpp
blob1098c97d3003f2d8be5de0934ebbc094703f3687
1 // pcbuilderdialogDlg.cpp : implementation file
2 //
4 #include "stdafx.h"
5 #include "shellapi.h"
6 // a fun undef for DOT NET
7 #undef DEBUG
8 #include "CMakeSetup.h"
9 #include "MakeHelp.h"
10 #include "cmVersion.h"
11 #include "PathDialog.h"
12 #include "CMakeSetupDialog.h"
13 #include "CMakeCommandLineInfo.h"
14 #include "../cmExternalMakefileProjectGenerator.h"
15 #include "../cmListFileCache.h"
16 #include "../cmCacheManager.h"
17 #include "../cmake.h"
18 #include "../cmGlobalGenerator.h"
19 #include "../cmDynamicLoader.h"
20 #ifdef _DEBUG
21 #define new DEBUG_NEW
22 #undef THIS_FILE
23 static char THIS_FILE[] = __FILE__;
24 #endif
27 /////////////////////////////////////////////////////////////////////////////
28 // CAboutDlg dialog used for App About
30 class CAboutDlg : public CDialog
32 public:
33 CAboutDlg();
35 // Dialog Data
36 //{{AFX_DATA(CAboutDlg)
37 enum { IDD = IDD_ABOUTBOX };
38 //}}AFX_DATA
40 // ClassWizard generated virtual function overrides
41 //{{AFX_VIRTUAL(CAboutDlg)
42 protected:
43 virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
44 //}}AFX_VIRTUAL
46 // Implementation
47 protected:
48 //{{AFX_MSG(CAboutDlg)
49 //}}AFX_MSG
50 DECLARE_MESSAGE_MAP()
53 CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
55 //{{AFX_DATA_INIT(CAboutDlg)
56 //}}AFX_DATA_INIT
59 void CAboutDlg::DoDataExchange(CDataExchange* pDX)
61 CDialog::DoDataExchange(pDX);
62 //{{AFX_DATA_MAP(CAboutDlg)
63 //}}AFX_DATA_MAP
66 BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
67 //{{AFX_MSG_MAP(CAboutDlg)
68 // No message handlers
69 //}}AFX_MSG_MAP
70 END_MESSAGE_MAP();
73 void MFCMessageCallback(const char* m, const char* title, bool& nomore, void*)
75 std::string message = m;
76 message += "\n\n(Press Cancel to suppress any further messages.)";
77 if(::MessageBox(0, message.c_str(), title,
78 MB_OKCANCEL|MB_TASKMODAL) == IDCANCEL)
80 nomore = true;
84 /////////////////////////////////////////////////////////////////////////////
85 // CMakeSetupDialog dialog
86 void updateProgress(const char *msg, float prog, void *cd)
88 char* tmp = new char[strlen(msg) + 40];
89 if (prog >= 0)
91 sprintf(tmp,"%s %i%%",msg,(int)(100*prog));
93 else
95 sprintf(tmp,"%s",msg);
97 CMakeSetupDialog *self = (CMakeSetupDialog *)cd;
98 self->SetDlgItemText(IDC_PROGRESS, tmp);
99 CWnd* cancel = self->GetDlgItem(IDCANCEL);
101 // Retrieve and dispatch any waiting messages.
103 MSG wmsg;
104 while (::PeekMessage (&wmsg, NULL, 0, 0, PM_REMOVE))
106 switch(wmsg.message)
108 case WM_LBUTTONDOWN:
109 case WM_LBUTTONUP:
110 case WM_LBUTTONDBLCLK:
112 if(wmsg.hwnd == cancel->m_hWnd)
114 ::DispatchMessage(&wmsg);
117 break;
118 case WM_COMMAND:
119 case WM_SETCURSOR:
120 case WM_PAINT:
121 ::DispatchMessage(&wmsg);
122 break;
125 delete [] tmp;
128 // Convert to Win32 path (slashes). This calls the system tools one and then
129 // removes the spaces. It is not in system tools because we don't want any
130 // generators accidentally use it
131 std::string ConvertToWindowsPath(const char* path)
133 // Convert to output path.
134 // Remove the "" around it (if any) since it's an output path for
135 // the shell. If another shell-oriented feature is not designed
136 // for a GUI use, then we are in trouble.
137 // save the value of the force to unix path option
138 bool saveForce = cmSystemTools::GetForceUnixPaths();
139 // make sure we get windows paths no matter what for the GUI
140 cmSystemTools::SetForceUnixPaths(false);
141 std::string s = cmSystemTools::ConvertToOutputPath(path);
142 // now restore the force unix path to its previous value
143 cmSystemTools::SetForceUnixPaths(saveForce);
144 if (s.size())
146 std::string::iterator i = s.begin();
147 if (*i == '\"')
149 s.erase(i, i + 1);
151 i = s.begin() + s.length() - 1;
152 if (*i == '\"')
154 s.erase(i, i + 1);
157 return s;
160 CMakeSetupDialog::CMakeSetupDialog(const CMakeCommandLineInfo& cmdInfo,
161 CWnd* pParent /*=NULL*/)
162 : CDialog(CMakeSetupDialog::IDD, pParent)
164 m_GeneratorPicked = false;
165 m_Cursor = LoadCursor(NULL, IDC_ARROW);
166 m_RunningConfigure = false;
167 cmSystemTools::SetRunCommandHideConsole(true);
168 cmSystemTools::SetErrorCallback(MFCMessageCallback);
169 m_RegistryKey = "Software\\Kitware\\CMakeSetup\\Settings\\StartPath";
170 m_CacheEntriesList.m_CMakeSetupDialog = this;
172 m_CMakeInstance = new cmake;
173 m_CMakeInstance->SetCMakeEditCommand("CMakeSetup");
174 m_CMakeInstance->SetProgressCallback(updateProgress, (void *)this);
176 //{{AFX_DATA_INIT(CMakeSetupDialog)
177 //}}AFX_DATA_INIT
179 // Get the parameters from the command line info
180 // If an unknown parameter is found, try to interpret it too, since it
181 // is likely to be a file dropped on the shortcut :)
182 if (cmdInfo.m_LastUnknownParameter.IsEmpty())
184 this->m_WhereSource = cmdInfo.m_WhereSource;
185 this->m_WhereBuild = cmdInfo.m_WhereBuild;
186 this->m_GeneratorDialog.m_GeneratorChoiceString =
187 cmdInfo.m_GeneratorChoiceString;
188 this->m_AdvancedValues = cmdInfo.m_AdvancedValues;
190 else
192 this->m_WhereSource = _T("");
193 this->m_WhereBuild = _T("");
194 this->m_AdvancedValues = FALSE;
195 this->m_GeneratorDialog.m_GeneratorChoiceString =
196 cmdInfo.m_GeneratorChoiceString;
197 this->ChangeDirectoriesFromFile((LPCTSTR)cmdInfo.m_LastUnknownParameter);
200 // Note that LoadIcon does not require a subsequent DestroyIcon in Win32
201 m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
202 m_BuildPathChanged = false;
203 // Find the path to the cmake.exe executable
204 char fname[1024];
205 ::GetModuleFileName(NULL,fname,1023);
206 // extract just the path part
207 m_PathToExecutable = cmSystemTools::GetProgramPath(fname).c_str();
208 // add the cmake.exe to the path
209 m_PathToExecutable += "/cmake.exe";
211 m_oldCX = -1;
212 m_deltaXRemainder = 0;
215 CMakeSetupDialog::~CMakeSetupDialog()
217 delete m_CMakeInstance;
218 // clean up globals
219 cmDynamicLoader::FlushCache();
222 void CMakeSetupDialog::DoDataExchange(CDataExchange* pDX)
224 CDialog::DoDataExchange(pDX);
225 //{{AFX_DATA_MAP(CMakeSetupDialog)
226 DDX_Control(pDX, IDC_AdvancedValues, m_AdvancedValuesControl);
227 DDX_Control(pDX, IDC_SUPPRESS_DEV_WARNINGS, m_SuppressDevWarningsControl);
228 DDX_Check(pDX, IDC_SUPPRESS_DEV_WARNINGS, m_SuppressDevValue);
229 DDX_Control(pDX, IDC_BROWSE_SOURCE, m_BrowseSource);
230 DDX_Control(pDX, IDC_BROWSE_BUILD, m_BrowseBuild);
231 DDX_Control(pDX, IDC_DELETE_BUTTON, m_DeleteButton);
232 DDX_Control(pDX, IDC_HELP_BUTTON, m_HelpButton);
233 DDX_Control(pDX, IDC_OK, m_OKButton);
234 DDX_Control(pDX, IDCANCEL, m_CancelButton);
235 DDX_CBStringExact(pDX, IDC_WhereSource, m_WhereSource);
236 DDX_CBStringExact(pDX, IDC_WhereBuild, m_WhereBuild);
237 DDX_Control(pDX, IDC_FRAME, m_ListFrame);
238 DDX_Control(pDX, IDC_WhereSource, m_WhereSourceControl);
239 DDX_Control(pDX, IDC_WhereBuild, m_WhereBuildControl);
240 DDX_Control(pDX, IDC_LIST2, m_CacheEntriesList);
241 DDX_Control(pDX, IDC_MouseHelpCaption, m_MouseHelp);
242 DDX_Control(pDX, IDC_PROGRESS, m_StatusDisplay);
243 DDX_Control(pDX, IDC_BuildProjects, m_Configure);
244 DDX_Check(pDX, IDC_AdvancedValues, m_AdvancedValues);
245 //}}AFX_DATA_MAP
248 BEGIN_MESSAGE_MAP(CMakeSetupDialog, CDialog)
249 //{{AFX_MSG_MAP(CMakeSetupDialog)
250 ON_WM_SYSCOMMAND()
251 ON_WM_PAINT()
252 ON_WM_QUERYDRAGICON()
253 ON_BN_CLICKED(IDC_BUTTON2, OnBrowseWhereSource)
254 ON_BN_CLICKED(IDC_BuildProjects, OnConfigure)
255 ON_BN_CLICKED(IDC_BUTTON3, OnBrowseWhereBuild)
256 ON_CBN_EDITCHANGE(IDC_WhereBuild, OnChangeWhereBuild)
257 ON_CBN_SELCHANGE(IDC_WhereBuild, OnSelendokWhereBuild)
258 ON_CBN_EDITCHANGE(IDC_WhereSource, OnChangeWhereSource)
259 ON_CBN_SELENDOK(IDC_WhereSource, OnSelendokWhereSource)
260 ON_WM_SIZE()
261 ON_WM_GETMINMAXINFO()
262 ON_BN_CLICKED(IDC_OK, OnOk)
263 ON_BN_CLICKED(IDC_DELETE_BUTTON, OnDeleteButton)
264 ON_BN_CLICKED(IDC_HELP_BUTTON, OnHelpButton)
265 ON_BN_CLICKED(IDC_AdvancedValues, OnAdvancedValues)
266 ON_BN_CLICKED(IDC_SUPPRESS_DEV_WARNINGS, OnSuppressDevValue)
267 ON_BN_DOUBLECLICKED(IDC_SUPPRESS_DEV_WARNINGS, OnDoubleclickedSuppressDevValue)
268 ON_BN_DOUBLECLICKED(IDC_AdvancedValues, OnDoubleclickedAdvancedValues)
269 ON_WM_DROPFILES()
270 ON_BN_CLICKED(IDCANCEL, OnCancel)
271 ON_WM_SETCURSOR()
272 //}}AFX_MSG_MAP
273 END_MESSAGE_MAP()
275 /////////////////////////////////////////////////////////////////////////////
276 // CMakeSetupDialog message handlers
278 BOOL CMakeSetupDialog::OnInitDialog()
280 CDialog::OnInitDialog();
281 this->DragAcceptFiles(true);
283 // Add "Create shortcut" menu item to system menu.
285 // IDM_CREATESHORTCUT must be in the system command range.
286 ASSERT((IDM_CREATESHORTCUT & 0xFFF0) == IDM_CREATESHORTCUT);
287 ASSERT(IDM_CREATESHORTCUT < 0xF000);
289 // Add "About..." menu item to system menu.
291 // IDM_ABOUTBOX must be in the system command range.
292 ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
293 ASSERT(IDM_ABOUTBOX < 0xF000);
295 CMenu* pSysMenu = GetSystemMenu(FALSE);
296 if (pSysMenu != NULL)
298 CString strCreateShortcutMenu;
299 strCreateShortcutMenu.LoadString(IDS_CREATESHORTCUT);
300 if (!strCreateShortcutMenu.IsEmpty())
302 pSysMenu->AppendMenu(MF_SEPARATOR);
303 pSysMenu->AppendMenu(MF_STRING,
304 IDM_CREATESHORTCUT,
305 strCreateShortcutMenu);
308 CString strAboutMenu;
309 strAboutMenu.LoadString(IDS_ABOUTBOX);
310 if (!strAboutMenu.IsEmpty())
312 pSysMenu->AppendMenu(MF_SEPARATOR);
313 pSysMenu->AppendMenu(MF_STRING,
314 IDM_ABOUTBOX,
315 strAboutMenu);
319 // Set the icon for this dialog. The framework does this automatically
320 // when the application's main window is not a dialog
321 SetIcon(m_hIcon, TRUE); // Set big icon
322 SetIcon(m_hIcon, FALSE); // Set small icon
323 // Load source and build dirs from registry
324 this->LoadFromRegistry();
326 // try to load the cmake cache from disk
327 this->LoadCacheFromDiskToGUI();
328 m_WhereBuildControl.LimitText(2048);
329 m_WhereSourceControl.LimitText(2048);
331 // Set the version number
332 char tmp[1024];
333 sprintf(tmp,"CMake %s", cmVersion::GetCMakeVersion());
334 SetDlgItemText(IDC_PROGRESS, "");
335 this->SetWindowText(tmp);
336 this->UpdateData(FALSE);
337 return TRUE; // return TRUE unless you set the focus to a control
341 // About dialog invoke
342 void CMakeSetupDialog::OnSysCommand(UINT nID, LPARAM lParam)
344 if ((nID & 0xFFF0) == IDM_ABOUTBOX)
346 CAboutDlg dlgAbout;
347 dlgAbout.DoModal();
349 else if ((nID & 0xFFF0) == IDM_CREATESHORTCUT)
351 CreateShortcut();
353 else
355 CDialog::OnSysCommand(nID, lParam);
359 // If you add a minimize button to your dialog, you will need the code below
360 // to draw the icon. For MFC applications using the document/view model,
361 // this is automatically done for you by the framework.
363 void CMakeSetupDialog::OnPaint()
365 if (IsIconic())
367 CPaintDC dc(this); // device context for painting
369 SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
371 // Center icon in client rectangle
372 int cxIcon = GetSystemMetrics(SM_CXICON);
373 int cyIcon = GetSystemMetrics(SM_CYICON);
374 CRect rect;
375 GetClientRect(&rect);
376 int x = (rect.Width() - cxIcon + 1) / 2;
377 int y = (rect.Height() - cyIcon + 1) / 2;
379 // Draw the icon
380 dc.DrawIcon(x, y, m_hIcon);
382 else
384 CDialog::OnPaint();
388 // The system calls this to obtain the cursor to display while the user drags
389 // the minimized window.
390 HCURSOR CMakeSetupDialog::OnQueryDragIcon()
392 return (HCURSOR) m_hIcon;
397 // Browse button
398 bool CMakeSetupDialog::Browse(CString &result, const char *title)
400 CString initialDir = result;
401 initialDir.Replace("/", "\\");
402 CPathDialog dlg("Select Path", title, initialDir);
403 if(dlg.DoModal()==IDOK)
405 result = dlg.GetPathName();
406 return true;
408 else
410 return false;
417 void CMakeSetupDialog::SaveToRegistry()
419 HKEY hKey;
420 DWORD dwDummy;
422 if(RegCreateKeyEx(HKEY_CURRENT_USER,
423 m_RegistryKey,
424 0, "", REG_OPTION_NON_VOLATILE, KEY_READ|KEY_WRITE,
425 NULL, &hKey, &dwDummy) != ERROR_SUCCESS)
427 return;
429 else
431 // save some values
432 CString regvalue;
434 // write the size of the dialog
435 CRect size;
436 this->GetWindowRect(&size);
437 unsigned long width = size.Width();
438 unsigned long height = size.Height();
439 RegSetValueEx(hKey, _T("Width"), 0, REG_DWORD,
440 (CONST BYTE *)(&width),4);
441 RegSetValueEx(hKey, _T("Height"), 0, REG_DWORD,
442 (CONST BYTE *)(&height),4);
444 this->ReadRegistryValue(hKey, &(regvalue),"WhereSource1","C:\\");
445 int shiftEnd = 9;
446 if(m_WhereSource != regvalue)
448 char keyName[1024];
449 char keyName2[1024];
450 int i;
451 for (i = 2; i < 10; ++i)
453 regvalue = "";
454 sprintf(keyName,"WhereSource%i",i);
455 this->ReadRegistryValue(hKey, &(regvalue),keyName,"");
456 // check for short circuit, if the new value is already in
457 // the list then we stop
458 if (m_WhereSource == regvalue)
460 shiftEnd = i - 1;
464 for (i = shiftEnd; i; --i)
466 regvalue = "";
467 sprintf(keyName,"WhereSource%i",i);
468 sprintf(keyName2,"WhereSource%i",i+1);
470 this->ReadRegistryValue(hKey, &(regvalue),keyName,"");
471 if (strlen(regvalue))
473 RegSetValueEx(hKey, _T(keyName2), 0, REG_SZ,
474 (CONST BYTE *)(const char *)regvalue,
475 regvalue.GetLength());
478 RegSetValueEx(hKey, _T("WhereSource1"), 0, REG_SZ,
479 (CONST BYTE *)(const char *)m_WhereSource,
480 m_WhereSource.GetLength());
483 this->ReadRegistryValue(hKey, &(regvalue),"WhereBuild1","C:\\");
484 if(m_WhereBuild != regvalue)
486 int i;
487 char keyName[1024];
488 char keyName2[1024];
489 for (i = 2; i < 10; ++i)
491 regvalue = "";
492 sprintf(keyName,"WhereBuild%i",i);
493 this->ReadRegistryValue(hKey, &(regvalue),keyName,"");
494 // check for short circuit, if the new value is already in
495 // the list then we stop
496 if (m_WhereBuild == regvalue)
498 shiftEnd = i - 1;
501 for (i = shiftEnd; i; --i)
503 regvalue = "";
504 sprintf(keyName,"WhereBuild%i",i);
505 sprintf(keyName2,"WhereBuild%i",i+1);
507 this->ReadRegistryValue(hKey, &(regvalue),keyName,"");
508 if (strlen(regvalue))
510 RegSetValueEx(hKey, _T(keyName2), 0, REG_SZ,
511 (CONST BYTE *)(const char *)regvalue,
512 regvalue.GetLength());
515 RegSetValueEx(hKey, _T("WhereBuild1"), 0, REG_SZ,
516 (CONST BYTE *)(const char *)m_WhereBuild,
517 m_WhereBuild.GetLength());
520 RegCloseKey(hKey);
524 void CMakeSetupDialog::ReadRegistryValue(HKEY hKey,
525 CString *val,
526 const char *key,
527 const char *adefault)
529 DWORD dwType, dwSize;
530 char *pb;
532 dwType = REG_SZ;
533 pb = val->GetBuffer(MAX_PATH);
534 dwSize = MAX_PATH;
535 if(RegQueryValueEx(hKey,_T(key), NULL, &dwType,
536 (BYTE *)pb, &dwSize) != ERROR_SUCCESS)
538 val->ReleaseBuffer();
539 *val = _T(adefault);
541 else
543 val->ReleaseBuffer();
548 void CMakeSetupDialog::LoadFromRegistry()
550 HKEY hKey;
551 if(RegOpenKeyEx(HKEY_CURRENT_USER,
552 m_RegistryKey,
553 0, KEY_READ, &hKey) != ERROR_SUCCESS)
555 return;
557 else
559 // load some values
560 DWORD dwSize = 4;
561 DWORD width, height;
563 if (RegQueryValueEx(hKey,_T("Width"), NULL, NULL,
564 (BYTE *)&width, &dwSize) == ERROR_SUCCESS &&
565 RegQueryValueEx(hKey,_T("Height"), NULL, NULL,
566 (BYTE *)&height, &dwSize) == ERROR_SUCCESS)
568 this->SetWindowPos(0,0,0,width,height,SWP_NOZORDER | SWP_NOMOVE);
571 if (m_WhereSource.IsEmpty())
573 this->ReadRegistryValue(hKey, &(m_WhereSource),"WhereSource1","C:\\");
575 if (m_WhereBuild.IsEmpty())
577 this->ReadRegistryValue(hKey, &(m_WhereBuild),"WhereBuild1","C:\\");
579 m_WhereSourceControl.AddString(m_WhereSource);
580 m_WhereBuildControl.AddString(m_WhereBuild);
582 char keyname[1024];
583 CString regvalue;
584 int i;
585 for (i = 2; i <= 10; ++i)
587 sprintf(keyname,"WhereSource%i",i);
588 regvalue = "";
589 this->ReadRegistryValue(hKey, &(regvalue),keyname,"C:\\");
590 if (strcmp("C:\\",regvalue))
592 m_WhereSourceControl.AddString(regvalue);
594 sprintf(keyname,"WhereBuild%i",i);
595 regvalue = "";
596 this->ReadRegistryValue(hKey, &(regvalue),keyname,"C:\\");
597 if (strcmp("C:\\",regvalue))
599 m_WhereBuildControl.AddString(regvalue);
603 RegCloseKey(hKey);
608 // Callback for browse source button
609 void CMakeSetupDialog::OnBrowseWhereSource()
611 this->UpdateData();
612 Browse(m_WhereSource, "Enter Path to Source");
613 this->UpdateData(false);
614 this->OnChangeWhereSource();
617 // Callback for browser build button
618 void CMakeSetupDialog::OnBrowseWhereBuild()
620 this->UpdateData();
621 Browse(m_WhereBuild, "Enter Path to Build");
622 this->UpdateData(false);
623 this->OnChangeWhereBuild();
626 void CMakeSetupDialog::RunCMake(bool generateProjectFiles)
628 if(!cmSystemTools::FileExists(m_WhereBuild))
630 std::string message =
631 "Build directory does not exist, should I create it?\n\n"
632 "Directory: ";
633 message += (const char*)m_WhereBuild;
634 if(MessageBox(message.c_str(), "Create Directory", MB_OKCANCEL) == IDOK)
636 cmSystemTools::MakeDirectory(m_WhereBuild);
638 else
640 MessageBox("Build Project aborted, nothing done.");
641 return;
644 // set the wait cursor
645 m_Cursor = LoadCursor(NULL, IDC_WAIT);
646 ::SetCursor(m_Cursor);
647 m_RunningConfigure = true;
649 // get all the info from the dialog
650 this->UpdateData();
651 // always save the current gui values to disk
652 this->SaveCacheFromGUI();
653 // Make sure we are working from the cache on disk
654 this->LoadCacheFromDiskToGUI();
655 m_OKButton.EnableWindow(false);
657 // setup the cmake instance
658 if (generateProjectFiles)
660 if(m_CMakeInstance->Generate() != 0)
662 cmSystemTools::Error(
663 "Error in generation process, project files may be invalid");
666 else
668 m_CMakeInstance->SetHomeDirectory(m_WhereSource);
669 m_CMakeInstance->SetStartDirectory(m_WhereSource);
670 m_CMakeInstance->SetHomeOutputDirectory(m_WhereBuild);
671 m_CMakeInstance->SetStartOutputDirectory(m_WhereBuild);
672 m_CMakeInstance->SetGlobalGenerator(
673 m_CMakeInstance->CreateGlobalGenerator(m_GeneratorDialog.m_GeneratorChoiceString));
674 m_CMakeInstance->SetCMakeCommand(m_PathToExecutable);
675 m_CMakeInstance->LoadCache();
676 if(m_SuppressDevValue)
678 m_CMakeInstance->SetSuppressDevWarnings(true);
680 else
682 m_CMakeInstance->SetSuppressDevWarnings(false);
684 if(m_CMakeInstance->Configure() != 0)
686 cmSystemTools::Error(
687 "Error in configuration process, project files may be invalid");
689 // update the GUI with any new values in the caused by the
690 // generation process
691 this->LoadCacheFromDiskToGUI();
694 // save source and build paths to registry
695 this->SaveToRegistry();
696 // path is up-to-date now
697 m_BuildPathChanged = false;
698 // put the cursor back
699 m_Cursor = LoadCursor(NULL, IDC_ARROW);
700 ::SetCursor(m_Cursor);
701 m_RunningConfigure = false;
702 cmSystemTools::ResetErrorOccuredFlag();
706 // Callback for build projects button
707 void CMakeSetupDialog::OnConfigure()
709 if(!m_GeneratorPicked)
711 m_GeneratorDialog.m_CMakeInstance = this->m_CMakeInstance;
712 if(m_GeneratorDialog.DoModal() != IDOK)
714 return;
716 // save the generator choice in the registry
717 HKEY hKey;
718 DWORD dwDummy;
720 if(RegCreateKeyEx(HKEY_CURRENT_USER,
721 m_RegistryKey,
722 0, "", REG_OPTION_NON_VOLATILE, KEY_READ|KEY_WRITE,
723 NULL, &hKey, &dwDummy) == ERROR_SUCCESS)
725 // save some values
726 RegSetValueEx(hKey, _T("LastGenerator"), 0, REG_SZ,
727 (CONST BYTE *)(const char *)m_GeneratorDialog.m_GeneratorChoiceString,
728 m_GeneratorDialog.m_GeneratorChoiceString.GetLength());
732 // enable error messages each time configure is pressed
733 cmSystemTools::EnableMessages();
734 this->RunCMake(false);
740 // callback for combo box menu where build selection
741 void CMakeSetupDialog::OnSelendokWhereBuild()
743 m_WhereBuildControl.GetLBText(m_WhereBuildControl.GetCurSel(),
744 m_WhereBuild);
745 m_WhereBuildControl.SetWindowText( m_WhereBuild);
746 this->UpdateData(FALSE);
747 this->OnChangeWhereBuild();
750 // callback for combo box menu where source selection
751 void CMakeSetupDialog::OnSelendokWhereSource()
753 m_WhereSourceControl.GetLBText(m_WhereSourceControl.GetCurSel(),
754 m_WhereSource);
755 this->UpdateData(FALSE);
756 this->OnChangeWhereSource();
759 // callback for chaing source directory
760 void CMakeSetupDialog::OnChangeWhereSource()
764 // callback for changing the build directory
765 void CMakeSetupDialog::OnChangeWhereBuild()
767 this->UpdateData();
769 // The build dir has changed, check if there is a cache, and
770 // grab the source dir from it
772 std::string path = this->m_WhereBuild;
773 cmSystemTools::ConvertToUnixSlashes(path);
775 // adjust the cmake instance
776 m_CMakeInstance->SetHomeOutputDirectory(m_WhereBuild);
777 m_CMakeInstance->SetStartOutputDirectory(m_WhereBuild);
779 std::string cache_file = path;
780 cache_file += "/CMakeCache.txt";
782 cmCacheManager *cachem = this->m_CMakeInstance->GetCacheManager();
783 cmCacheManager::CacheIterator it = cachem->NewIterator();
785 m_GeneratorPicked = false;
787 // make sure we have a normal cache file, specifically if one exists make
788 // sure it can be read
789 if (cmSystemTools::FileExists(cache_file.c_str()))
791 if (cachem->LoadCache(path.c_str()))
793 if (it.Find("CMAKE_HOME_DIRECTORY"))
795 path = ConvertToWindowsPath(it.GetValue());
796 this->m_WhereSource = path.c_str();
797 this->m_WhereSourceControl.SetWindowText(this->m_WhereSource);
798 this->OnChangeWhereSource();
799 m_GeneratorPicked = true;
802 else
804 //file exists but cqnnot be read
805 cmSystemTools::Error("There is a CMakeCache.txt file for the current binary tree but cmake does not have permission to read it. Please check the permissions of the directory you are trying to run CMake on.");
806 return;
810 m_CacheEntriesList.RemoveAll();
811 m_CacheEntriesList.ShowWindow(SW_SHOW);
812 this->LoadCacheFromDiskToGUI();
813 m_BuildPathChanged = true;
817 // copy from the cache manager to the cache edit list box
818 void CMakeSetupDialog::FillCacheGUIFromCacheManager()
820 cmCacheManager *cachem = this->m_CMakeInstance->GetCacheManager();
821 cmCacheManager::CacheIterator it = cachem->NewIterator();
823 // if there are already entries in the cache, then
824 // put the new ones in the top, so they show up first
825 bool reverseOrder = false;
826 // all the current values are not new any more
827 std::set<CPropertyItem*> items = m_CacheEntriesList.GetItems();
828 for(std::set<CPropertyItem*>::iterator i = items.begin();
829 i != items.end(); ++i)
831 // first check to see if it is still in the cache
832 CPropertyItem* item = *i;
833 if ( !it.Find((const char*)item->m_propName) )
835 m_CacheEntriesList.RemoveProperty((const char*)item->m_propName);
837 else
839 // if it is still in the cache then it is no longer new
840 item->m_NewValue = false;
843 for(cmCacheManager::CacheIterator i = cachem->NewIterator();
844 !i.IsAtEnd(); i.Next())
846 const char* key = i.GetName();
848 // if value has trailing space or tab, enclose it in single quotes
849 // to enforce the fact that it has 'invisible' trailing stuff
850 std::string value = i.GetValue();
851 if (value.size() &&
852 (value[value.size() - 1] == ' ' ||
853 value[value.size() - 1] == '\t'))
855 value = '\'' + value + '\'';
857 bool advanced = i.GetPropertyAsBool("ADVANCED");
858 switch(i.GetType() )
860 case cmCacheManager::BOOL:
861 if(cmSystemTools::IsOn(value.c_str()))
863 m_CacheEntriesList.AddProperty(key,
864 "ON",
865 i.GetProperty("HELPSTRING"),
866 CPropertyList::COMBO,"ON|OFF",
867 reverseOrder,
868 advanced
871 else
873 m_CacheEntriesList.AddProperty(key,
874 "OFF",
875 i.GetProperty("HELPSTRING"),
876 CPropertyList::COMBO,"ON|OFF",
877 reverseOrder, advanced
880 break;
881 case cmCacheManager::PATH:
882 m_CacheEntriesList.AddProperty(key,
883 value.c_str(),
884 i.GetProperty("HELPSTRING"),
885 CPropertyList::PATH,"",
886 reverseOrder, advanced
888 break;
889 case cmCacheManager::FILEPATH:
890 m_CacheEntriesList.AddProperty(key,
891 value.c_str(),
892 i.GetProperty("HELPSTRING"),
893 CPropertyList::FILE,"",
894 reverseOrder, advanced
896 break;
897 case cmCacheManager::STRING:
898 m_CacheEntriesList.AddProperty(key,
899 value.c_str(),
900 i.GetProperty("HELPSTRING"),
901 CPropertyList::EDIT,"",
902 reverseOrder, advanced
904 break;
905 case cmCacheManager::INTERNAL:
906 m_CacheEntriesList.RemoveProperty(key);
907 break;
910 if(m_CacheEntriesList.GetShowAdvanced())
912 m_CacheEntriesList.ShowAdvanced();
914 else
916 m_CacheEntriesList.HideAdvanced();
919 m_OKButton.EnableWindow(false);
920 if(cachem->GetSize() > 0 && !cmSystemTools::GetErrorOccuredFlag())
922 bool enable = true;
923 items = m_CacheEntriesList.GetItems();
924 for(std::set<CPropertyItem*>::iterator i = items.begin();
925 i != items.end(); ++i)
927 CPropertyItem* item = *i;
928 if(item->m_Advanced )
930 if(item->m_NewValue && m_CacheEntriesList.GetShowAdvanced())
932 enable = false;
933 break;
936 else
938 if(item->m_NewValue)
940 // if one new value then disable to OK button
941 enable = false;
942 break;
946 if(enable)
948 m_OKButton.EnableWindow(true);
952 // redraw the list
953 m_CacheEntriesList.SetTopIndex(0);
954 m_CacheEntriesList.Invalidate();
957 // copy from the list box to the cache manager
958 void CMakeSetupDialog::FillCacheManagerFromCacheGUI()
960 cmCacheManager *cachem = this->m_CMakeInstance->GetCacheManager();
961 std::set<CPropertyItem*> items = m_CacheEntriesList.GetItems();
962 cmCacheManager::CacheIterator it = cachem->NewIterator();
963 for(std::set<CPropertyItem*>::iterator i = items.begin();
964 i != items.end(); ++i)
966 CPropertyItem* item = *i;
967 if ( it.Find((const char*)item->m_propName) )
969 // if value is enclosed in single quotes ('foo') then remove them
970 // they were used to enforce the fact that it had 'invisible'
971 // trailing stuff
972 if (item->m_curValue.GetLength() >= 2 &&
973 item->m_curValue[0] == '\'' &&
974 item->m_curValue[item->m_curValue.GetLength() - 1] == '\'')
976 it.SetValue(item->m_curValue.Mid(
977 1, item->m_curValue.GetLength() - 2));
979 else
981 it.SetValue(item->m_curValue);
989 //! Load cache file from m_WhereBuild and display in GUI editor
990 void CMakeSetupDialog::LoadCacheFromDiskToGUI()
992 cmCacheManager *cachem = this->m_CMakeInstance->GetCacheManager();
993 if(m_WhereBuild != "")
995 if (!cachem->LoadCache(m_WhereBuild))
997 // if it does exist, but isn;t readable then warn the user
998 std::string cacheFile = m_WhereBuild;
999 cacheFile += "/CMakeCache.txt";
1000 if(cmSystemTools::FileExists(cacheFile.c_str()))
1002 cmSystemTools::Error("There is a CMakeCache.txt file for the current binary tree but cmake does not have permission to read it. Please check the permissions of the directory you are trying to run CMake on.");
1003 return;
1006 cmCacheManager::CacheIterator itm = cachem->NewIterator();
1007 if ( itm.Find("CMAKE_HOME_DIRECTORY"))
1009 std::string path = ConvertToWindowsPath(itm.GetValue());
1010 this->m_WhereSource = path.c_str();
1011 this->m_WhereSourceControl.SetWindowText(this->m_WhereSource);
1012 this->OnChangeWhereSource();
1014 m_CMakeInstance->SetHomeDirectory(m_WhereSource);
1015 m_CMakeInstance->SetStartDirectory(m_WhereSource);
1016 m_CMakeInstance->SetHomeOutputDirectory(m_WhereBuild);
1017 m_CMakeInstance->SetStartOutputDirectory(m_WhereBuild);
1018 m_CMakeInstance->PreLoadCMakeFiles();
1019 this->FillCacheGUIFromCacheManager();
1020 cmCacheManager::CacheIterator it =
1021 cachem->GetCacheIterator("CMAKE_GENERATOR");
1022 if(!it.IsAtEnd())
1024 m_GeneratorPicked = true;
1025 const char* extraGen = cachem->GetCacheValue("CMAKE_EXTRA_GENERATOR");
1026 std::string curGen = cmExternalMakefileProjectGenerator::
1027 CreateFullGeneratorName(it.GetValue(), extraGen);
1029 if(m_GeneratorDialog.m_GeneratorChoiceString != curGen.c_str())
1031 m_GeneratorDialog.m_GeneratorChoiceString = curGen.c_str();
1032 this->UpdateData(FALSE);
1038 //! Save GUI values to cmCacheManager and then save to disk.
1039 void CMakeSetupDialog::SaveCacheFromGUI()
1041 cmCacheManager *cachem = this->m_CMakeInstance->GetCacheManager();
1042 this->FillCacheManagerFromCacheGUI();
1043 if(m_WhereBuild != "")
1045 cachem->SaveCache(m_WhereBuild);
1050 void CMakeSetupDialog::OnSize(UINT nType, int cx, int cy)
1052 if (nType == SIZE_MINIMIZED)
1054 CDialog::OnSize(nType, cx, cy);
1055 return;
1057 if (m_oldCX == -1)
1059 m_oldCX = cx;
1060 m_oldCY = cy;
1062 int deltax = cx - m_oldCX;
1063 int deltay = cy - m_oldCY;
1065 m_oldCX = cx;
1066 m_oldCY = cy;
1068 CDialog::OnSize(nType, cx, cy);
1070 if (deltax == 0 && deltay == 0)
1072 return;
1075 if(m_CacheEntriesList.m_hWnd)
1077 // get the original sizes/positions
1078 CRect cRect;
1079 m_AdvancedValuesControl.GetWindowRect(&cRect);
1080 this->ScreenToClient(&cRect);
1081 m_AdvancedValuesControl.SetWindowPos(&wndTop, cRect.left + deltax,
1082 cRect.top,
1083 0, 0,
1084 SWP_NOCOPYBITS |
1085 SWP_NOSIZE | SWP_NOZORDER);
1086 m_SuppressDevWarningsControl.GetWindowRect(&cRect);
1087 this->ScreenToClient(&cRect);
1088 m_SuppressDevWarningsControl.SetWindowPos(&wndTop, cRect.left + deltax,
1089 cRect.top,
1090 0, 0,
1091 SWP_NOCOPYBITS |
1092 SWP_NOSIZE | SWP_NOZORDER);
1093 m_BrowseSource.GetWindowRect(&cRect);
1094 this->ScreenToClient(&cRect);
1095 m_BrowseSource.SetWindowPos(&wndTop, cRect.left + deltax,
1096 cRect.top,
1097 0, 0,
1098 SWP_NOCOPYBITS | SWP_NOSIZE | SWP_NOZORDER);
1099 m_BrowseBuild.GetWindowRect(&cRect);
1100 this->ScreenToClient(&cRect);
1101 m_BrowseBuild.SetWindowPos(&wndTop, cRect.left + deltax,
1102 cRect.top,
1103 0, 0,
1104 SWP_NOCOPYBITS | SWP_NOSIZE | SWP_NOZORDER);
1106 m_WhereSourceControl.GetWindowRect(&cRect);
1107 m_WhereSourceControl.SetWindowPos(&wndTop, cRect.left, cRect.top,
1108 cRect.Width() + deltax,
1109 cRect.Height(),
1110 SWP_NOCOPYBITS |
1111 SWP_NOMOVE | SWP_NOZORDER);
1112 m_WhereBuildControl.GetWindowRect(&cRect);
1113 m_WhereBuildControl.SetWindowPos(&wndTop, cRect.left, cRect.top,
1114 cRect.Width() + deltax,
1115 cRect.Height(),
1116 SWP_NOCOPYBITS |
1117 SWP_NOMOVE | SWP_NOZORDER);
1118 m_ListFrame.GetWindowRect(&cRect);
1119 m_ListFrame.SetWindowPos(&wndTop, cRect.left, cRect.top,
1120 cRect.Width() + deltax,
1121 cRect.Height() + deltay,
1122 SWP_NOCOPYBITS | SWP_NOMOVE | SWP_NOZORDER);
1123 m_CacheEntriesList.GetWindowRect(&cRect);
1124 m_CacheEntriesList.SetWindowPos(&wndTop, cRect.left, cRect.top,
1125 cRect.Width() + deltax,
1126 cRect.Height() + deltay,
1127 SWP_NOCOPYBITS | SWP_NOMOVE | SWP_NOZORDER);
1129 m_StatusDisplay.GetWindowRect(&cRect);
1130 this->ScreenToClient(&cRect);
1131 m_StatusDisplay.SetWindowPos(&wndBottom, cRect.left,
1132 cRect.top + deltay,
1133 cRect.Width() + deltax, cRect.Height(),
1134 SWP_NOCOPYBITS);
1136 m_MouseHelp.GetWindowRect(&cRect);
1137 this->ScreenToClient(&cRect);
1138 m_MouseHelp.SetWindowPos(&wndTop, cRect.left ,
1139 cRect.top + deltay,
1140 cRect.Width() + deltax, cRect.Height(),
1141 SWP_NOCOPYBITS | SWP_NOZORDER);
1143 deltax = int(deltax + m_deltaXRemainder);
1144 m_deltaXRemainder = float(deltax%2);
1147 m_Configure.GetWindowRect(&cRect);
1148 this->ScreenToClient(&cRect);
1149 m_Configure.SetWindowPos(&wndTop, cRect.left + deltax/2,
1150 cRect.top + deltay,
1151 0, 0,
1152 SWP_NOCOPYBITS | SWP_NOSIZE);
1153 m_CancelButton.GetWindowRect(&cRect);
1154 this->ScreenToClient(&cRect);
1155 m_CancelButton.SetWindowPos(&wndTop, cRect.left + deltax/2,
1156 cRect.top + deltay,
1157 0, 0,
1158 SWP_NOCOPYBITS | SWP_NOSIZE);
1159 m_OKButton.GetWindowRect(&cRect);
1160 this->ScreenToClient(&cRect);
1161 m_OKButton.SetWindowPos(&wndTop, cRect.left + deltax/2,
1162 cRect.top + deltay,
1163 0, 0,
1164 SWP_NOCOPYBITS | SWP_NOSIZE);
1165 m_DeleteButton.GetWindowRect(&cRect);
1166 this->ScreenToClient(&cRect);
1167 m_DeleteButton.SetWindowPos(&wndTop, cRect.left + deltax/2,
1168 cRect.top + deltay,
1169 0, 0,
1170 SWP_NOCOPYBITS | SWP_NOSIZE);
1171 m_HelpButton.GetWindowRect(&cRect);
1172 this->ScreenToClient(&cRect);
1173 m_HelpButton.SetWindowPos(&wndTop, cRect.left + deltax/2,
1174 cRect.top + deltay,
1175 0, 0,
1176 SWP_NOCOPYBITS | SWP_NOSIZE);
1182 void CMakeSetupDialog::OnGetMinMaxInfo( MINMAXINFO FAR* lpMMI )
1184 lpMMI->ptMinTrackSize.x = 550;
1185 lpMMI->ptMinTrackSize.y = 272;
1188 void CMakeSetupDialog::OnCancel()
1190 if(m_RunningConfigure)
1192 if(MessageBox("You are in the middle of a Configure.\n"
1193 "If you Cancel now the configure information will be lost.\n"
1194 "Are you sure you want to Cancel?", "Confirm Exit",
1195 MB_YESNO) == IDYES)
1197 cmSystemTools::SetFatalErrorOccured();
1199 return;
1201 if(m_CacheEntriesList.IsDirty())
1203 if(MessageBox("You have changed options but not rebuilt, "
1204 "are you sure you want to exit?", "Confirm Exit",
1205 MB_YESNO) == IDYES)
1207 CDialog::OnOK();
1210 else
1212 CDialog::OnOK();
1216 void CMakeSetupDialog::OnOk()
1218 // enable error messages each time configure is pressed
1219 cmSystemTools::EnableMessages();
1220 m_CacheEntriesList.ClearDirty();
1221 this->RunCMake(true);
1223 // save the size of the dialog
1226 if (!(::GetKeyState(VK_SHIFT) & 0x1000))
1228 CDialog::OnOK();
1232 // Create a shortcut on the desktop with the current Source/Build dir.
1233 int CMakeSetupDialog::CreateShortcut()
1235 // Find the desktop folder and create the link name
1237 HKEY hKey;
1238 if(RegOpenKeyEx(HKEY_CURRENT_USER,
1239 "Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders",
1240 0, KEY_READ, &hKey) != ERROR_SUCCESS)
1242 AfxMessageBox ("Create shortcut: unable to find 'Shell Folders' key in registry!");
1243 return 1;
1246 DWORD dwType, dwSize;
1247 #define MAXPATH 1024
1248 char link_name[MAXPATH];
1249 dwSize = MAXPATH;
1250 if(RegQueryValueEx(hKey,
1251 (LPCTSTR)"Desktop",
1252 NULL,
1253 &dwType,
1254 (BYTE *)link_name,
1255 &dwSize) != ERROR_SUCCESS)
1257 AfxMessageBox ("Create shortcut: unable to find 'Desktop' registry value in 'Shell Folders' key!");
1258 return 1;
1261 if(dwType != REG_SZ)
1263 AfxMessageBox ("Create shortcut: 'Desktop' registry value in 'Shell Folders' key has wrong type!");
1264 return 1;
1267 strcat(link_name, "\\CMake - ");
1268 std::string current_dir = cmSystemTools::GetFilenameName((LPCTSTR)m_WhereSource);
1269 strcat(link_name, current_dir.c_str());
1270 strcat(link_name, ".lnk");
1272 // Find the path to the current executable
1274 char path_to_current_exe[MAXPATH];
1275 ::GetModuleFileName(NULL, path_to_current_exe, MAXPATH);
1277 // Create the shortcut
1279 HRESULT hres;
1280 IShellLink *psl;
1282 // Initialize the COM library
1284 hres = CoInitialize(NULL);
1286 if (! SUCCEEDED (hres))
1288 AfxMessageBox ("Create shortcut: unable to initialize the COM library!");
1289 return 1;
1292 // Create an IShellLink object and get a pointer to the IShellLink
1293 // interface (returned from CoCreateInstance).
1295 hres = CoCreateInstance(CLSID_ShellLink,
1296 NULL,
1297 CLSCTX_INPROC_SERVER,
1298 IID_IShellLink,
1299 (void **)&psl);
1301 if (! SUCCEEDED (hres))
1303 AfxMessageBox ("Create shortcut: unable to create IShellLink instance!");
1304 return 1;
1307 IPersistFile *ppf;
1309 // Query IShellLink for the IPersistFile interface for
1310 // saving the shortcut in persistent storage.
1312 hres = psl->QueryInterface(IID_IPersistFile, (void **)&ppf);
1314 if (SUCCEEDED (hres))
1316 // Set the path to the shortcut target.
1317 hres = psl->SetPath(path_to_current_exe);
1319 if (! SUCCEEDED (hres))
1321 AfxMessageBox ("Create shortcut: SetPath failed!");
1324 // Set the arguments of the shortcut.
1325 CString args = " /H=\"" + m_WhereSource + "\" /B=\"" + m_WhereBuild + "\" /G=\"" + m_GeneratorDialog.m_GeneratorChoiceString + "\" /A=\"" + (m_AdvancedValues ? "TRUE" : "FALSE") + "\"";
1327 hres = psl->SetArguments(args);
1329 if (! SUCCEEDED (hres))
1331 AfxMessageBox ("Create shortcut: SetArguments failed!");
1334 // Set the description of the shortcut.
1335 hres = psl->SetDescription("Shortcut to CMakeSetup");
1337 if (! SUCCEEDED (hres))
1339 AfxMessageBox ("Create shortcut: SetDescription failed!");
1342 // Ensure that the string consists of ANSI characters.
1343 WORD wszAr[MAX_PATH];
1344 LPWSTR wsz = (LPWSTR)wszAr;
1345 MultiByteToWideChar(CP_ACP, 0, link_name, -1, (LPWSTR)(wsz), MAX_PATH);
1347 // Save the shortcut via the IPersistFile::Save member function.
1348 hres = ppf->Save(wsz, TRUE);
1350 if (! SUCCEEDED (hres))
1352 AfxMessageBox ("Create shortcut: Save failed!");
1355 // Release the pointer to IPersistFile.
1356 ppf->Release ();
1358 // Release the pointer to IShellLink.
1359 psl->Release ();
1361 return 0;
1364 void CMakeSetupDialog::OnHelpButton()
1366 CMakeHelp dialog;
1367 dialog.DoModal();
1370 void CMakeSetupDialog::OnDeleteButton()
1372 std::string message = "Are you sure you want to delete the CMakeCache.txt file for:\n";
1373 message += m_WhereBuild;
1374 if(::MessageBox(0, message.c_str(), "Delete Cache?",
1375 MB_YESNO|MB_TASKMODAL) == IDNO)
1377 return;
1379 m_GeneratorPicked = false;
1381 if(m_WhereBuild != "" && this->m_CMakeInstance)
1383 this->m_CMakeInstance->GetCacheManager()->DeleteCache(m_WhereBuild);
1386 // Make sure we are working from the cache on disk
1387 this->LoadCacheFromDiskToGUI();
1389 m_OKButton.EnableWindow(false);
1392 void CMakeSetupDialog::ShowAdvancedValues()
1394 m_CacheEntriesList.ShowAdvanced();
1397 void CMakeSetupDialog::RemoveAdvancedValues()
1399 m_CacheEntriesList.HideAdvanced();
1403 void CMakeSetupDialog::OnSuppressDevValue()
1407 void CMakeSetupDialog::OnDoubleclickedSuppressDevValue()
1409 this->OnSuppressDevValue();
1412 void CMakeSetupDialog::OnAdvancedValues()
1414 this->UpdateData();
1415 if(m_AdvancedValues)
1417 this->ShowAdvancedValues();
1419 else
1421 this->RemoveAdvancedValues();
1425 void CMakeSetupDialog::OnDoubleclickedAdvancedValues()
1427 this->OnAdvancedValues();
1430 // Handle param or single dropped file.
1431 void CMakeSetupDialog::ChangeDirectoriesFromFile(const char* arg)
1433 // Check if the argument refers to a CMakeCache.txt or
1434 // CMakeLists.txt file.
1435 std::string listPath;
1436 std::string cachePath;
1437 bool argIsFile = false;
1438 if(cmSystemTools::FileIsDirectory(arg))
1440 std::string path = cmSystemTools::CollapseFullPath(arg);
1441 cmSystemTools::ConvertToUnixSlashes(path);
1442 std::string cacheFile = path;
1443 cacheFile += "/CMakeCache.txt";
1444 std::string listFile = path;
1445 listFile += "/CMakeLists.txt";
1446 if(cmSystemTools::FileExists(cacheFile.c_str()))
1448 cachePath = path;
1450 if(cmSystemTools::FileExists(listFile.c_str()))
1452 listPath = path;
1455 else if(cmSystemTools::FileExists(arg))
1457 argIsFile = true;
1458 std::string fullPath = cmSystemTools::CollapseFullPath(arg);
1459 std::string name = cmSystemTools::GetFilenameName(fullPath.c_str());
1460 name = cmSystemTools::LowerCase(name);
1461 if(name == "cmakecache.txt")
1463 cachePath = cmSystemTools::GetFilenamePath(fullPath.c_str());
1465 else if(name == "cmakelists.txt")
1467 listPath = cmSystemTools::GetFilenamePath(fullPath.c_str());
1471 // If there is a CMakeCache.txt file, use its settings.
1472 if(cachePath.length() > 0)
1474 cmCacheManager* cachem = m_CMakeInstance->GetCacheManager();
1475 cmCacheManager::CacheIterator it = cachem->NewIterator();
1476 if(cachem->LoadCache(cachePath.c_str()) && it.Find("CMAKE_HOME_DIRECTORY"))
1478 std::string path = ConvertToWindowsPath(cachePath.c_str());
1479 m_WhereBuild = path.c_str();
1481 path = ConvertToWindowsPath(it.GetValue());
1482 m_WhereSource = path.c_str();
1484 m_GeneratorDialog.m_GeneratorChoiceString = _T("");
1485 return;
1489 // If there is a CMakeLists.txt file, use it as the source tree.
1490 if(listPath.length() > 0)
1492 std::string path = ConvertToWindowsPath(listPath.c_str());
1493 m_WhereSource = path.c_str();
1495 if(argIsFile)
1497 // Source CMakeLists.txt file given. It was probably dropped
1498 // onto the window or executable. Default to an in-source
1499 // build.
1500 m_WhereBuild = path.c_str();
1502 else
1504 // Source directory given on command line. Use current working
1505 // directory as build tree.
1506 std::string cwd = cmSystemTools::GetCurrentWorkingDirectory();
1507 path = ConvertToWindowsPath(cwd.c_str());
1508 m_WhereBuild = path.c_str();
1514 // The framework calls this member function when the user releases the
1515 // left mouse button over a window that has registered itself as the
1516 // recipient of dropped files.
1518 void CMakeSetupDialog::OnDropFiles(HDROP hDropInfo)
1520 UINT nb_files = DragQueryFile(hDropInfo, 0xFFFFFFFF, NULL, 0);
1521 if (nb_files > 0)
1523 UINT buffer_size = DragQueryFile(hDropInfo, 0, NULL, 0);
1524 char *buffer = new char [buffer_size + 1];
1525 DragQueryFile(hDropInfo, 0, buffer, buffer_size + 1);
1527 this->ChangeDirectoriesFromFile(buffer);
1528 delete [] buffer;
1530 this->m_WhereSourceControl.SetWindowText(this->m_WhereSource);
1531 this->m_WhereBuildControl.SetWindowText(this->m_WhereBuild);
1533 this->UpdateData(FALSE);
1535 this->OnChangeWhereSource();
1536 this->OnChangeWhereBuild();
1539 DragFinish(hDropInfo);
1542 BOOL CMakeSetupDialog::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message)
1544 CDialog::OnSetCursor(pWnd, nHitTest, message);
1545 if(m_Cursor == LoadCursor(NULL, IDC_WAIT))
1547 ::SetCursor(m_Cursor);
1549 return true;