summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorClinton Stimpson <clinton@elemtech.com>2007-11-05 18:20:54 (GMT)
committerClinton Stimpson <clinton@elemtech.com>2007-11-05 18:20:54 (GMT)
commitcfa723d45792ef6969304fb7d9274778f662a116 (patch)
tree740899517a9a87583acad024d06e1cf4d2e0d011
parent7bd73d3e0dd1cc1515575b58db41e80f17474532 (diff)
downloadCMake-cfa723d45792ef6969304fb7d9274778f662a116.zip
CMake-cfa723d45792ef6969304fb7d9274778f662a116.tar.gz
CMake-cfa723d45792ef6969304fb7d9274778f662a116.tar.bz2
ENH: Prompt user for generator when there is none.
Many minor improvements, bug fixes, and style fixes.
-rw-r--r--Source/QtDialog/CMakeSetup.cxx1
-rw-r--r--Source/QtDialog/CMakeSetupDialog.cxx205
-rw-r--r--Source/QtDialog/CMakeSetupDialog.h25
-rw-r--r--Source/QtDialog/QCMake.cxx67
-rw-r--r--Source/QtDialog/QCMake.h25
-rw-r--r--Source/QtDialog/QCMakeCacheView.cxx112
-rw-r--r--Source/QtDialog/QCMakeCacheView.h7
7 files changed, 301 insertions, 141 deletions
diff --git a/Source/QtDialog/CMakeSetup.cxx b/Source/QtDialog/CMakeSetup.cxx
index 16178cd..b29e742 100644
--- a/Source/QtDialog/CMakeSetup.cxx
+++ b/Source/QtDialog/CMakeSetup.cxx
@@ -31,6 +31,7 @@ int main(int argc, char** argv)
// TODO handle CMake args
CMakeSetupDialog dialog;
+ dialog.setWindowTitle("CMakeSetup");
dialog.show();
return app.exec();
diff --git a/Source/QtDialog/CMakeSetupDialog.cxx b/Source/QtDialog/CMakeSetupDialog.cxx
index e718bc5..3a39c81 100644
--- a/Source/QtDialog/CMakeSetupDialog.cxx
+++ b/Source/QtDialog/CMakeSetupDialog.cxx
@@ -18,32 +18,46 @@
#include "CMakeSetupDialog.h"
#include <QFileDialog>
-#include <QThread>
#include <QProgressBar>
#include <QMessageBox>
#include <QStatusBar>
#include <QToolButton>
#include <QDialogButtonBox>
#include <QCloseEvent>
+#include <QCoreApplication>
#include "QCMake.h"
#include "QCMakeCacheView.h"
-// QCMake instance on a thread
-class QCMakeThread : public QThread
+QCMakeThread::QCMakeThread(QObject* p)
+ : QThread(p), CMakeInstance(NULL)
{
-public:
- QCMakeThread(QObject* p) : QThread(p) { }
- QCMake* CMakeInstance;
-
-protected:
- virtual void run()
- {
- this->CMakeInstance = new QCMake;
- this->exec();
- delete this->CMakeInstance;
- }
-};
+}
+
+QCMake* QCMakeThread::cmakeInstance() const
+{
+ return this->CMakeInstance;
+}
+
+void QCMakeThread::processEvents()
+{
+ QCoreApplication::processEvents();
+}
+
+void QCMakeThread::run()
+{
+ this->CMakeInstance = new QCMake;
+ // make the cmake thread to process events it receives from the GUI thread
+ QObject::connect(this->CMakeInstance, SIGNAL(progressChanged(QString, float)),
+ this, SLOT(processEvents()), Qt::DirectConnection);
+ QObject::connect(this->CMakeInstance, SIGNAL(outputMessage(QString)),
+ this, SLOT(processEvents()), Qt::DirectConnection);
+ // emit that this cmake thread is ready for use
+ emit this->cmakeInitialized();
+ this->exec();
+ delete this->CMakeInstance;
+ this->CMakeInstance = NULL;
+}
CMakeSetupDialog::CMakeSetupDialog()
{
@@ -65,25 +79,26 @@ CMakeSetupDialog::CMakeSetupDialog()
// start the cmake worker thread
this->CMakeThread = new QCMakeThread(this);
- // TODO does this guarantee the QCMake instance is created before initialize is called?
- QObject::connect(this->CMakeThread, SIGNAL(started()),
- this, SLOT(initialize()));
+ QObject::connect(this->CMakeThread, SIGNAL(cmakeInitialized()),
+ this, SLOT(initialize()), Qt::QueuedConnection);
this->CMakeThread->start();
}
void CMakeSetupDialog::initialize()
{
// now the cmake worker thread is running, lets make our connections to it
- QObject::connect(this->CMakeThread->CMakeInstance,
+ QObject::connect(this->CMakeThread->cmakeInstance(),
SIGNAL(propertiesChanged(const QCMakeCachePropertyList&)),
this->CacheValues->cacheModel(),
SLOT(setProperties(const QCMakeCachePropertyList&)));
QObject::connect(this->ConfigureButton, SIGNAL(clicked(bool)),
this, SLOT(doConfigure()));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(configureDone(int)),
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(configureDone(int)),
this, SLOT(finishConfigure(int)));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(generateDone(int)),
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(generateDone(int)),
this, SLOT(finishGenerate(int)));
QObject::connect(this->GenerateButton, SIGNAL(clicked(bool)),
@@ -98,25 +113,31 @@ void CMakeSetupDialog::initialize()
this, SLOT(doBinaryBrowse()));
QObject::connect(this->BinaryDirectory, SIGNAL(editTextChanged(QString)),
- this->CMakeThread->CMakeInstance, SLOT(setBinaryDirectory(QString)));
+ this, SLOT(setBinaryDirectory(QString)));
QObject::connect(this->SourceDirectory, SIGNAL(textChanged(QString)),
- this->CMakeThread->CMakeInstance, SLOT(setSourceDirectory(QString)));
+ this->CMakeThread->cmakeInstance(),
+ SLOT(setSourceDirectory(QString)));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(sourceDirChanged(QString)),
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(sourceDirChanged(QString)),
this, SLOT(updateSourceDirectory(QString)));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(progressChanged(QString, float)),
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(progressChanged(QString, float)),
this, SLOT(showProgress(QString,float)));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(error(QString, QString, bool*)),
- this, SLOT(error(QString,QString,bool*)), Qt::BlockingQueuedConnection);
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(error(QString, QString, bool*)),
+ this, SLOT(error(QString,QString,bool*)),
+ Qt::BlockingQueuedConnection);
QObject::connect(this->InterruptButton, SIGNAL(clicked(bool)),
- this->CMakeThread->CMakeInstance, SLOT(interrupt()));
+ this->CMakeThread->cmakeInstance(), SLOT(interrupt()));
QObject::connect(this->InterruptButton, SIGNAL(clicked(bool)),
this, SLOT(doInterrupt()));
- QObject::connect(this->CMakeThread->CMakeInstance, SIGNAL(outputMessage(QString)),
+ QObject::connect(this->CMakeThread->cmakeInstance(),
+ SIGNAL(outputMessage(QString)),
this->Output, SLOT(append(QString)));
QObject::connect(this->HelpButton, SIGNAL(clicked(bool)),
@@ -135,36 +156,45 @@ void CMakeSetupDialog::doConfigure()
QDir dir(this->BinaryDirectory->currentText());
if(!dir.exists())
{
- QString message = tr("Build directory does not exist, should I create it?\n\n"
+ QString message = tr("Build directory does not exist, "
+ "should I create it?\n\n"
"Directory: ");
message += this->BinaryDirectory->currentText();
QString title = tr("Create Directory");
- QMessageBox::StandardButton btn =
- QMessageBox::information(this, title, message, QMessageBox::Yes | QMessageBox::No);
+ QMessageBox::StandardButton btn;
+ btn = QMessageBox::information(this, title, message,
+ QMessageBox::Yes | QMessageBox::No);
if(btn == QMessageBox::No)
{
return;
}
dir.mkpath(".");
}
+
+ // prompt for generator if one doesn't exist
+ if(this->CMakeThread->cmakeInstance()->generator().isEmpty())
+ {
+ this->promptForGenerator();
+ }
+
this->InterruptButton->setEnabled(true);
this->setEnabledState(false);
this->Output->clear();
- QMetaObject::invokeMethod(this->CMakeThread->CMakeInstance,
+ QMetaObject::invokeMethod(this->CMakeThread->cmakeInstance(),
"setProperties", Qt::QueuedConnection,
Q_ARG(QCMakeCachePropertyList,
this->CacheValues->cacheModel()->properties()));
- QMetaObject::invokeMethod(this->CMakeThread->CMakeInstance,
+ QMetaObject::invokeMethod(this->CMakeThread->cmakeInstance(),
"configure", Qt::QueuedConnection);
}
-void CMakeSetupDialog::finishConfigure(int error)
+void CMakeSetupDialog::finishConfigure(int err)
{
this->InterruptButton->setEnabled(false);
this->setEnabledState(true);
this->ProgressBar->reset();
this->statusBar()->showMessage(tr("Configure Done"), 2000);
- if(error != 0)
+ if(err != 0)
{
QMessageBox::critical(this, tr("Error"),
tr("Error in configuration process, project files may be invalid"),
@@ -172,13 +202,13 @@ void CMakeSetupDialog::finishConfigure(int error)
}
}
-void CMakeSetupDialog::finishGenerate(int error)
+void CMakeSetupDialog::finishGenerate(int err)
{
this->InterruptButton->setEnabled(false);
this->setEnabledState(true);
this->ProgressBar->reset();
this->statusBar()->showMessage(tr("Generate Done"), 2000);
- if(error != 0)
+ if(err != 0)
{
QMessageBox::critical(this, tr("Error"),
tr("Error in generation process, project files may be invalid"),
@@ -195,19 +225,27 @@ void CMakeSetupDialog::doOk()
this->InterruptButton->setEnabled(true);
this->setEnabledState(false);
this->Output->clear();
- QMetaObject::invokeMethod(this->CMakeThread->CMakeInstance,
+ QMetaObject::invokeMethod(this->CMakeThread->cmakeInstance(),
"generate", Qt::QueuedConnection);
}
void CMakeSetupDialog::closeEvent(QCloseEvent* e)
{
+ // don't close if we're busy
+ if(this->InterruptButton->isEnabled())
+ {
+ e->ignore();
+ }
+
+ // prompt for close if there are unsaved changes
if(this->CacheValues->cacheModel()->isDirty())
{
QString message = tr("You have changed options but not rebuilt, "
"are you sure you want to exit?");
QString title = tr("Confirm Exit");
- QMessageBox::StandardButton btn =
- QMessageBox::critical(this, title, message, QMessageBox::Yes | QMessageBox::No);
+ QMessageBox::StandardButton btn;
+ btn = QMessageBox::critical(this, title, message,
+ QMessageBox::Yes | QMessageBox::No);
if(btn == QMessageBox::No)
{
e->ignore();
@@ -217,30 +255,31 @@ void CMakeSetupDialog::closeEvent(QCloseEvent* e)
void CMakeSetupDialog::doHelp()
{
- QString msg = tr("CMake is used to configure and generate build files for"
- "software projects. The basic steps for configuring a project are as"
- "follows:\r\n\r\n1. Select the source directory for the project. This should"
- "contain the CMakeLists.txt files for the project.\r\n\r\n2. Select the build"
- "directory for the project. This is the directory where the project will be"
- "built. It can be the same or a different directory than the source"
- "directory. For easy clean up, a separate build directory is recommended."
- "CMake will create the directory if it does not exist.\r\n\r\n3. Once the"
- "source and binary directories are selected, it is time to press the"
- "Configure button. This will cause CMake to read all of the input files and"
- "discover all the variables used by the project. The first time a variable"
- "is displayed it will be in Red. Users should inspect red variables making"
- "sure the values are correct. For some projects the Configure process can"
- "be iterative, so continue to press the Configure button until there are no"
- "longer red entries.\r\n\r\n4. Once there are no longer red entries, you"
- "should click the OK button. This will write the build files to the build"
+ QString msg = tr("CMake is used to configure and generate build files for "
+ "software projects. The basic steps for configuring a project are as "
+ "follows:\r\n\r\n1. Select the source directory for the project. This should "
+ "contain the CMakeLists.txt files for the project.\r\n\r\n2. Select the build "
+ "directory for the project. This is the directory where the project will be "
+ "built. It can be the same or a different directory than the source "
+ "directory. For easy clean up, a separate build directory is recommended. "
+ "CMake will create the directory if it does not exist.\r\n\r\n3. Once the "
+ "source and binary directories are selected, it is time to press the "
+ "Configure button. This will cause CMake to read all of the input files and "
+ "discover all the variables used by the project. The first time a variable "
+ "is displayed it will be in Red. Users should inspect red variables making "
+ "sure the values are correct. For some projects the Configure process can "
+ "be iterative, so continue to press the Configure button until there are no "
+ "longer red entries.\r\n\r\n4. Once there are no longer red entries, you "
+ "should click the OK button. This will write the build files to the build "
"directory and exit CMake.");
QDialog dialog;
+ dialog.setWindowTitle(tr("CMakeSetup Help"));
QVBoxLayout* l = new QVBoxLayout(&dialog);
- QLabel* label = new QLabel(&dialog);
- l->addWidget(label);
- label->setText(msg);
- label->setWordWrap(true);
+ QLabel* lab = new QLabel(&dialog);
+ l->addWidget(lab);
+ lab->setText(msg);
+ lab->setWordWrap(true);
QDialogButtonBox* btns = new QDialogButtonBox(QDialogButtonBox::Ok,
Qt::Horizontal, &dialog);
QObject::connect(btns, SIGNAL(accepted()), &dialog, SLOT(accept()));
@@ -276,7 +315,7 @@ void CMakeSetupDialog::doBinaryBrowse()
{
QString dir = QFileDialog::getExistingDirectory(this,
tr("Enter Path to Build"), this->BinaryDirectory->currentText());
- if(!dir.isEmpty())
+ if(!dir.isEmpty() && dir != this->BinaryDirectory->currentText())
{
this->setBinaryDirectory(dir);
}
@@ -284,12 +323,11 @@ void CMakeSetupDialog::doBinaryBrowse()
void CMakeSetupDialog::setBinaryDirectory(const QString& dir)
{
- if(dir != this->BinaryDirectory->currentText())
- {
- this->CacheValues->cacheModel()->setProperties(QCMakeCachePropertyList());
- this->Output->clear();
- this->BinaryDirectory->setEditText(dir);
- }
+ this->CacheValues->cacheModel()->clear();
+ this->Output->clear();
+ this->BinaryDirectory->setEditText(dir);
+ QMetaObject::invokeMethod(this->CMakeThread->cmakeInstance(),
+ "setBinaryDirectory", Qt::QueuedConnection, Q_ARG(QString, dir));
}
void CMakeSetupDialog::showProgress(const QString& msg, float percent)
@@ -298,10 +336,12 @@ void CMakeSetupDialog::showProgress(const QString& msg, float percent)
this->ProgressBar->setValue(qRound(percent * 100));
}
-void CMakeSetupDialog::error(const QString& title, const QString& message, bool* cancel)
+void CMakeSetupDialog::error(const QString& title, const QString& message,
+ bool* cancel)
{
- QMessageBox::StandardButton btn =
- QMessageBox::critical(this, title, message, QMessageBox::Ok | QMessageBox::Cancel);
+ QMessageBox::StandardButton btn;
+ btn = QMessageBox::critical(this, title, message,
+ QMessageBox::Ok | QMessageBox::Cancel);
if(btn == QMessageBox::Cancel)
{
*cancel = false;
@@ -318,7 +358,28 @@ void CMakeSetupDialog::setEnabledState(bool enabled)
this->ConfigureButton->setEnabled(enabled);
this->GenerateButton->setEnabled(enabled);
this->CancelButton->setEnabled(enabled);
- this->HelpButton->setEnabled(enabled);
}
+void CMakeSetupDialog::promptForGenerator()
+{
+ QStringList gens = this->CMakeThread->cmakeInstance()->availableGenerators();
+ QDialog dialog;
+ dialog.setWindowTitle(tr("CMakeSetup choose generator"));
+ QLabel* lab = new QLabel(&dialog);
+ lab->setText(tr("Please select what build system you want CMake to generate files for.\n"
+ "You should select the tool that you will use to build the project.\n"
+ "Press OK once you have made your selection."));
+ QComboBox* combo = new QComboBox(&dialog);
+ combo->addItems(gens);
+ QDialogButtonBox* btns = new QDialogButtonBox(QDialogButtonBox::Ok,
+ Qt::Horizontal, &dialog);
+ QObject::connect(btns, SIGNAL(accepted()), &dialog, SLOT(accept()));
+
+ QVBoxLayout* l = new QVBoxLayout(&dialog);
+ l->addWidget(lab);
+ l->addWidget(combo);
+ l->addWidget(btns);
+ dialog.exec();
+ this->CMakeThread->cmakeInstance()->setGenerator(combo->currentText());
+}
diff --git a/Source/QtDialog/CMakeSetupDialog.h b/Source/QtDialog/CMakeSetupDialog.h
index a8221be..d1efcce 100644
--- a/Source/QtDialog/CMakeSetupDialog.h
+++ b/Source/QtDialog/CMakeSetupDialog.h
@@ -15,8 +15,12 @@
=========================================================================*/
+#ifndef CMakeSetupDialog_h
+#define CMakeSetupDialog_h
+
#include "QCMake.h"
#include <QMainWindow>
+#include <QThread>
#include "ui_CMakeSetupDialog.h"
class QCMakeThread;
@@ -48,6 +52,7 @@ protected slots:
void setBinaryDirectory(const QString& dir);
void showProgress(const QString& msg, float percent);
void setEnabledState(bool);
+ void promptForGenerator();
protected:
void closeEvent(QCloseEvent*);
@@ -57,3 +62,23 @@ protected:
QToolButton* InterruptButton;
};
+// QCMake instance on a thread
+class QCMakeThread : public QThread
+{
+ Q_OBJECT
+public:
+ QCMakeThread(QObject* p);
+ QCMake* cmakeInstance() const;
+
+signals:
+ void cmakeInitialized();
+
+protected slots:
+ void processEvents();
+
+protected:
+ virtual void run();
+ QCMake* CMakeInstance;
+};
+
+#endif // CMakeSetupDialog_h
diff --git a/Source/QtDialog/QCMake.cxx b/Source/QtDialog/QCMake.cxx
index 495d404..367f6b3 100644
--- a/Source/QtDialog/QCMake.cxx
+++ b/Source/QtDialog/QCMake.cxx
@@ -17,18 +17,19 @@
#include "QCMake.h"
-#include <QCoreApplication>
#include <QDir>
+#include <QCoreApplication>
#include "cmake.h"
#include "cmCacheManager.h"
#include "cmSystemTools.h"
+#include "cmExternalMakefileProjectGenerator.h"
QCMake::QCMake(QObject* p)
: QObject(p)
{
- static int metaId = qRegisterMetaType<QCMakeCacheProperty>();
- static int metaIdList = qRegisterMetaType<QCMakeCachePropertyList>();
+ qRegisterMetaType<QCMakeCacheProperty>();
+ qRegisterMetaType<QCMakeCachePropertyList>();
QDir appDir(QCoreApplication::applicationDirPath());
#if defined(Q_OS_WIN)
@@ -46,6 +47,14 @@ QCMake::QCMake(QObject* p)
this->CMakeInstance = new cmake;
this->CMakeInstance->SetProgressCallback(QCMake::progressCallback, this);
+
+ std::vector<std::string> generators;
+ this->CMakeInstance->GetRegisteredGenerators(generators);
+ std::vector<std::string>::iterator iter;
+ for(iter = generators.begin(); iter != generators.end(); ++iter)
+ {
+ this->AvailableGenerators.append(QString::fromStdString(*iter));
+ }
}
QCMake::~QCMake()
@@ -74,7 +83,17 @@ void QCMake::setBinaryDirectory(const QString& dir)
{
cmCacheManager *cachem = this->CMakeInstance->GetCacheManager();
this->BinaryDirectory = dir;
- this->CMakeInstance->GetCacheManager()->LoadCache(dir.toLocal8Bit().data());
+ this->setGenerator(QString());
+ if(!this->CMakeInstance->GetCacheManager()->LoadCache(dir.toLocal8Bit().data()))
+ {
+ QDir testDir(dir);
+ if(testDir.exists("CMakeCache.txt"))
+ {
+ 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.");
+ }
+ }
QCMakeCachePropertyList props = this->properties();
emit this->propertiesChanged(props);
cmCacheManager::CacheIterator itm = cachem->NewIterator();
@@ -82,12 +101,24 @@ void QCMake::setBinaryDirectory(const QString& dir)
{
setSourceDirectory(itm.GetValue());
}
+ if ( itm.Find("CMAKE_GENERATOR"))
+ {
+ const char* extraGen = cachem->GetCacheValue("CMAKE_EXTRA_GENERATOR");
+ std::string curGen = cmExternalMakefileProjectGenerator::
+ CreateFullGeneratorName(itm.GetValue(), extraGen);
+ this->setGenerator(QString::fromStdString(curGen));
+ }
}
}
-void QCMake::setGenerator(const QString& generator)
+void QCMake::setGenerator(const QString& gen)
{
+ if(this->Generator != gen)
+ {
+ this->Generator = gen;
+ emit this->generatorChanged(this->Generator);
+ }
}
void QCMake::configure()
@@ -97,23 +128,23 @@ void QCMake::configure()
this->CMakeInstance->SetHomeOutputDirectory(this->BinaryDirectory.toAscii().data());
this->CMakeInstance->SetStartOutputDirectory(this->BinaryDirectory.toAscii().data());
this->CMakeInstance->SetGlobalGenerator(
- this->CMakeInstance->CreateGlobalGenerator("Unix Makefiles")); // TODO
+ this->CMakeInstance->CreateGlobalGenerator(this->Generator.toAscii().data()));
this->CMakeInstance->SetCMakeCommand(this->CMakeExecutable.toAscii().data());
this->CMakeInstance->LoadCache();
cmSystemTools::ResetErrorOccuredFlag();
- int error = this->CMakeInstance->Configure();
+ int err = this->CMakeInstance->Configure();
emit this->propertiesChanged(this->properties());
- emit this->configureDone(error);
+ emit this->configureDone(err);
}
void QCMake::generate()
{
cmSystemTools::ResetErrorOccuredFlag();
- int error = this->CMakeInstance->Generate();
- emit this->generateDone(error);
+ int err = this->CMakeInstance->Generate();
+ emit this->generateDone(err);
}
void QCMake::setProperties(const QCMakeCachePropertyList& props)
@@ -137,7 +168,7 @@ void QCMake::setProperties(const QCMakeCachePropertyList& props)
cachem->SaveCache(this->BinaryDirectory.toAscii().data());
}
-QCMakeCachePropertyList QCMake::properties()
+QCMakeCachePropertyList QCMake::properties() const
{
QCMakeCachePropertyList ret;
@@ -198,12 +229,22 @@ void QCMake::progressCallback(const char* msg, float percent, void* cd)
{
emit self->outputMessage(msg);
}
- QCoreApplication::processEvents();
}
-void QCMake::errorCallback(const char* msg, const char* title, bool& stop, void* cd)
+void QCMake::errorCallback(const char* msg, const char* title,
+ bool& stop, void* cd)
{
QCMake* self = reinterpret_cast<QCMake*>(cd);
emit self->error(title, msg, &stop);
}
+QString QCMake::generator() const
+{
+ return this->Generator;
+}
+
+QStringList QCMake::availableGenerators() const
+{
+ return this->AvailableGenerators;
+}
+
diff --git a/Source/QtDialog/QCMake.h b/Source/QtDialog/QCMake.h
index bfd2585..d28a917 100644
--- a/Source/QtDialog/QCMake.h
+++ b/Source/QtDialog/QCMake.h
@@ -26,6 +26,7 @@
#include <QString>
#include <QVariant>
#include <QList>
+#include <QStringList>
#include <QMetaType>
class cmake;
@@ -40,8 +41,14 @@ struct QCMakeCacheProperty
QString Help;
PropertyType Type;
bool Advanced;
- bool operator==(const QCMakeCacheProperty& other) const { return this->Key == other.Key; }
- bool operator<(const QCMakeCacheProperty& other) const { return this->Key < other.Key; }
+ bool operator==(const QCMakeCacheProperty& other) const
+ {
+ return this->Key == other.Key;
+ }
+ bool operator<(const QCMakeCacheProperty& other) const
+ {
+ return this->Key < other.Key;
+ }
};
// make types usable with QVariant
@@ -79,15 +86,15 @@ public slots:
public:
/// get the list of cache properties
- QCMakeCachePropertyList properties();
+ QCMakeCachePropertyList properties() const;
/// get the current binary directory
- QString binaryDirectory();
+ QString binaryDirectory() const;
/// get the current source directory
- QString sourceDirectory();
+ QString sourceDirectory() const;
/// get the current generator
- QString generator();
+ QString generator() const;
/// get the available generators
- QStringList availableGenerators();
+ QStringList availableGenerators() const;
signals:
/// signal when properties change (during read from disk or configure process)
@@ -112,11 +119,13 @@ protected:
cmake* CMakeInstance;
static void progressCallback(const char* msg, float percent, void* cd);
- static void errorCallback(const char* msg, const char* title, bool&, void* cd);
+ static void errorCallback(const char* msg, const char* title,
+ bool&, void* cd);
QString SourceDirectory;
QString BinaryDirectory;
QString Generator;
+ QStringList AvailableGenerators;
QString CMakeExecutable;
};
diff --git a/Source/QtDialog/QCMakeCacheView.cxx b/Source/QtDialog/QCMakeCacheView.cxx
index 4003c2f..9b732e8 100644
--- a/Source/QtDialog/QCMakeCacheView.cxx
+++ b/Source/QtDialog/QCMakeCacheView.cxx
@@ -22,17 +22,28 @@
#include <QHBoxLayout>
#include <QHeaderView>
#include <QEvent>
+#include <QFileInfo>
+#include <QStyle>
+#include <QKeyEvent>
QCMakeCacheView::QCMakeCacheView(QWidget* p)
: QTableView(p), Init(false)
{
+ // hook up our model
QCMakeCacheModel* m = new QCMakeCacheModel(this);
this->setModel(m);
- this->horizontalHeader()->setStretchLastSection(true);
- this->verticalHeader()->hide();
+ // our delegate for creating our editors
QCMakeCacheModelDelegate* delegate = new QCMakeCacheModelDelegate(this);
this->setItemDelegate(delegate);
+
+ // set up headers and sizes
+ int h = 0;
+ QFontMetrics met(this->font());
+ h = qMax(met.height(), this->style()->pixelMetric(QStyle::PM_IndicatorHeight));
+ this->verticalHeader()->setDefaultSectionSize(h + 4);
+ this->horizontalHeader()->setStretchLastSection(true);
+ this->verticalHeader()->hide();
}
void QCMakeCacheView::showEvent(QShowEvent* e)
@@ -106,6 +117,11 @@ static uint qHash(const QCMakeCacheProperty& p)
return qHash(p.Key);
}
+void QCMakeCacheModel::clear()
+{
+ this->setProperties(QCMakeCachePropertyList());
+}
+
void QCMakeCacheModel::setProperties(const QCMakeCachePropertyList& props)
{
QSet<QCMakeCacheProperty> newProps = props.toSet();
@@ -132,63 +148,63 @@ QCMakeCachePropertyList QCMakeCacheModel::properties() const
return this->Properties;
}
-int QCMakeCacheModel::columnCount (const QModelIndex& /*parent*/ ) const
+int QCMakeCacheModel::columnCount (const QModelIndex& /*p*/ ) const
{
return 2;
}
-QVariant QCMakeCacheModel::data (const QModelIndex& index, int role) const
+QVariant QCMakeCacheModel::data (const QModelIndex& idx, int role) const
{
- if(index.column() == 0 && (role == Qt::DisplayRole || role == Qt::EditRole))
+ if(idx.column() == 0 && (role == Qt::DisplayRole || role == Qt::EditRole))
{
- return this->Properties[index.row()].Key;
+ return this->Properties[idx.row()].Key;
}
- else if(index.column() == 0 && role == Qt::ToolTipRole)
+ else if(idx.column() == 0 && role == Qt::ToolTipRole)
{
- return this->data(index, Qt::DisplayRole).toString() + "\n" +
- this->data(index, QCMakeCacheModel::HelpRole).toString();
+ return this->data(idx, Qt::DisplayRole).toString() + "\n" +
+ this->data(idx, QCMakeCacheModel::HelpRole).toString();
}
- else if(index.column() == 1 && (role == Qt::DisplayRole || role == Qt::EditRole))
+ else if(idx.column() == 1 && (role == Qt::DisplayRole || role == Qt::EditRole))
{
- if(this->Properties[index.row()].Type != QCMakeCacheProperty::BOOL)
+ if(this->Properties[idx.row()].Type != QCMakeCacheProperty::BOOL)
{
- return this->Properties[index.row()].Value;
+ return this->Properties[idx.row()].Value;
}
}
- else if(index.column() == 1 && role == Qt::CheckStateRole)
+ else if(idx.column() == 1 && role == Qt::CheckStateRole)
{
- if(this->Properties[index.row()].Type == QCMakeCacheProperty::BOOL)
+ if(this->Properties[idx.row()].Type == QCMakeCacheProperty::BOOL)
{
- return this->Properties[index.row()].Value.toBool() ? Qt::Checked : Qt::Unchecked;
+ return this->Properties[idx.row()].Value.toBool() ? Qt::Checked : Qt::Unchecked;
}
}
else if(role == QCMakeCacheModel::HelpRole)
{
- return this->Properties[index.row()].Help;
+ return this->Properties[idx.row()].Help;
}
else if(role == QCMakeCacheModel::TypeRole)
{
- return this->Properties[index.row()].Type;
+ return this->Properties[idx.row()].Type;
}
else if(role == QCMakeCacheModel::AdvancedRole)
{
- return this->Properties[index.row()].Advanced;
+ return this->Properties[idx.row()].Advanced;
}
- else if(role == Qt::BackgroundRole && index.row()+1 <= this->NewCount)
+ else if(role == Qt::BackgroundRole && idx.row()+1 <= this->NewCount)
{
return QBrush(QColor(255,100,100));
}
return QVariant();
}
-QModelIndex QCMakeCacheModel::parent (const QModelIndex& /*index*/) const
+QModelIndex QCMakeCacheModel::parent (const QModelIndex& /*idx*/) const
{
return QModelIndex();
}
-int QCMakeCacheModel::rowCount (const QModelIndex& parent) const
+int QCMakeCacheModel::rowCount (const QModelIndex& p) const
{
- if(parent.isValid())
+ if(p.isValid())
{
return 0;
}
@@ -205,15 +221,15 @@ QVariant QCMakeCacheModel::headerData (int section, Qt::Orientation orient, int
return QVariant();
}
-Qt::ItemFlags QCMakeCacheModel::flags (const QModelIndex& index) const
+Qt::ItemFlags QCMakeCacheModel::flags (const QModelIndex& idx) const
{
Qt::ItemFlags f = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
// all column 1's are editable
- if(index.column() == 1)
+ if(idx.column() == 1)
{
f |= Qt::ItemIsEditable;
// booleans are editable in place
- if(this->Properties[index.row()].Type == QCMakeCacheProperty::BOOL)
+ if(this->Properties[idx.row()].Type == QCMakeCacheProperty::BOOL)
{
f |= Qt::ItemIsUserCheckable;
}
@@ -222,25 +238,25 @@ Qt::ItemFlags QCMakeCacheModel::flags (const QModelIndex& index) const
}
-bool QCMakeCacheModel::setData (const QModelIndex& index, const QVariant& value, int role)
+bool QCMakeCacheModel::setData (const QModelIndex& idx, const QVariant& value, int role)
{
- if(index.column() == 0 && (role == Qt::DisplayRole || role == Qt::EditRole))
+ if(idx.column() == 0 && (role == Qt::DisplayRole || role == Qt::EditRole))
{
- this->Properties[index.row()].Key = value.toString();
+ this->Properties[idx.row()].Key = value.toString();
this->IsDirty = true;
- emit this->dataChanged(index, index);
+ emit this->dataChanged(idx, idx);
}
- else if(index.column() == 1 && (role == Qt::DisplayRole || role == Qt::EditRole))
+ else if(idx.column() == 1 && (role == Qt::DisplayRole || role == Qt::EditRole))
{
- this->Properties[index.row()].Value = value.toString();
+ this->Properties[idx.row()].Value = value.toString();
this->IsDirty = true;
- emit this->dataChanged(index, index);
+ emit this->dataChanged(idx, idx);
}
- else if(index.column() == 1 && (role == Qt::CheckStateRole))
+ else if(idx.column() == 1 && (role == Qt::CheckStateRole))
{
- this->Properties[index.row()].Value = value.toInt() == Qt::Checked;
+ this->Properties[idx.row()].Value = value.toInt() == Qt::Checked;
this->IsDirty = true;
- emit this->dataChanged(index, index);
+ emit this->dataChanged(idx, idx);
}
return false;
}
@@ -252,28 +268,28 @@ QCMakeCacheModelDelegate::QCMakeCacheModelDelegate(QObject* p)
{
}
-QWidget* QCMakeCacheModelDelegate::createEditor(QWidget* parent,
- const QStyleOptionViewItem&, const QModelIndex& index) const
+QWidget* QCMakeCacheModelDelegate::createEditor(QWidget* p,
+ const QStyleOptionViewItem&, const QModelIndex& idx) const
{
- QVariant type = index.data(QCMakeCacheModel::TypeRole);
+ QVariant type = idx.data(QCMakeCacheModel::TypeRole);
if(type == QCMakeCacheProperty::BOOL)
{
return NULL;
}
else if(type == QCMakeCacheProperty::PATH)
{
- return new QCMakeCachePathEditor(index.data().toString(), false, parent);
+ return new QCMakeCachePathEditor(idx.data().toString(), false, p);
}
else if(type == QCMakeCacheProperty::FILEPATH)
{
- return new QCMakeCachePathEditor(index.data().toString(), true, parent);
+ return new QCMakeCachePathEditor(idx.data().toString(), true, p);
}
- return new QLineEdit(parent);
+ return new QLineEdit(p);
}
-
-
-QCMakeCachePathEditor::QCMakeCachePathEditor(const QString& file, bool fp, QWidget* p)
+
+QCMakeCachePathEditor::QCMakeCachePathEditor(const QString& file, bool fp,
+ QWidget* p)
: QWidget(p), LineEdit(this), IsFilePath(fp)
{
QHBoxLayout* l = new QHBoxLayout(this);
@@ -286,6 +302,7 @@ QCMakeCachePathEditor::QCMakeCachePathEditor(const QString& file, bool fp, QWidg
QObject::connect(tb, SIGNAL(clicked(bool)),
this, SLOT(chooseFile()));
this->LineEdit.setText(file);
+ this->LineEdit.selectAll();
tb->setFocusProxy(&this->LineEdit);
this->setFocusProxy(&this->LineEdit);
}
@@ -295,11 +312,14 @@ void QCMakeCachePathEditor::chooseFile()
QString path;
if(this->IsFilePath)
{
- path = QFileDialog::getOpenFileName(this, "TODO");
+ QFileInfo info(this->value());
+ path = QFileDialog::getOpenFileName(this, tr("Select File"),
+ info.absolutePath());
}
else
{
- path = QFileDialog::getExistingDirectory(this, "TODO", this->value());
+ path = QFileDialog::getExistingDirectory(this, tr("Select Path"),
+ this->value());
}
if(!path.isEmpty())
{
diff --git a/Source/QtDialog/QCMakeCacheView.h b/Source/QtDialog/QCMakeCacheView.h
index 892d84f..91d1053 100644
--- a/Source/QtDialog/QCMakeCacheView.h
+++ b/Source/QtDialog/QCMakeCacheView.h
@@ -55,6 +55,7 @@ public:
public slots:
void setProperties(const QCMakeCachePropertyList& props);
+ void clear();
public:
// satisfy [pure] virtuals
@@ -77,14 +78,16 @@ protected:
bool IsDirty;
};
-/// Qt delegate class for interaction (or other customization) with cache properties
+/// Qt delegate class for interaction (or other customization)
+/// with cache properties
class QCMakeCacheModelDelegate : public QItemDelegate
{
Q_OBJECT
public:
QCMakeCacheModelDelegate(QObject* p);
/// create our own editors for cache properties
- QWidget* createEditor(QWidget * parent, const QStyleOptionViewItem & option, const QModelIndex & index ) const;
+ QWidget* createEditor(QWidget* parent, const QStyleOptionViewItem& option,
+ const QModelIndex& index ) const;
};
/// Editor widget for editing paths or file paths