23 #include "configurationdialog.h"
24 #include "ui_configurationdialog.h"
26 #include "configpage.h"
27 #include "qtmetapointer.h"
29 #include <QAbstractButton>
32 #include <QStandardItem>
33 #include <QStandardItemModel>
37 DClass<ConfigurationDialog> :
public Ui::ConfigurationDialog
49 QList<ConfigPage *> configPages;
52 QModelIndex findPageModelIndex(
const QModelIndex &rootIndex,
ConfigPage *page)
54 auto model =
static_cast<QStandardItemModel *
>(tvOptionsList->model());
55 for (
int row = 0; row < model->rowCount(rootIndex); ++row)
57 QModelIndex index = model->index(row, COL_META, rootIndex);
58 ConfigPage *pageAtIndex = pageFromIndex(index);
59 if (pageAtIndex == page)
61 QModelIndex childIndex = findPageModelIndex(index, page);
62 if (childIndex.isValid())
68 ConfigPage *pageFromIndex(
const QModelIndex &index)
70 QModelIndex pageIndex = index.sibling(index.row(), COL_META);
72 void *pointer = metaPointer;
81 return QIcon(
":icons/exclamation_16.png");
95 auto model =
new QStandardItemModel(
this);
97 column < PrivData<ConfigurationDialog>::COLSIZE; ++column)
99 model->setHorizontalHeaderItem(column,
new QStandardItem());
101 d->tvOptionsList->setModel(model);
103 d->tvOptionsList->header()->setSectionResizeMode(
105 d->tvOptionsList->header()->setSectionResizeMode(
108 d->currentlyDisplayedPage =
nullptr;
109 connect(d->buttonBox, SIGNAL(clicked(QAbstractButton*)),
this, SLOT (btnClicked(QAbstractButton*)));
110 this->connect(d->tvOptionsList->selectionModel(), SIGNAL(currentChanged(QModelIndex,QModelIndex)),
111 SLOT(switchToItem(QModelIndex,QModelIndex)));
114 ConfigurationDialog::~ConfigurationDialog()
116 for (
int i = 0; i < d->configPages.count(); ++i)
117 delete d->configPages[i];
121 QStandardItem *rootItem,
ConfigPage *configPage,
int position)
123 if (!canConfigPageBeAdded(configPage))
126 auto pModel = (QStandardItemModel *)d->tvOptionsList->model();
127 if (rootItem ==
nullptr)
128 rootItem = pModel->invisibleRootItem();
130 if (!this->hasItemOnList(rootItem))
133 QList<QStandardItem *> row;
135 QStandardItem *nameItem =
new QStandardItem(configPage->
name());
136 nameItem->setIcon(configPage->
icon());
141 nameItem->setData(QVariant::fromValue(metaPointer), Qt::UserRole);
146 rootItem->appendRow(row);
148 rootItem->insertRow(position, row);
150 d->configPages << configPage;
151 this->connect(configPage, SIGNAL(validationRequested()),
152 SLOT(onPageValidationRequested()));
156 validatePage(configPage);
163 auto pModel = (QStandardItemModel *)d->tvOptionsList->model();
164 if (rootItem ==
nullptr)
165 rootItem = pModel->invisibleRootItem();
167 if (!this->hasItemOnList(rootItem))
171 QVariant variantMetaPointer = QVariant::fromValue(metaPointer);
173 QList<QStandardItem *> row;
175 auto nameItem =
new QStandardItem(label);
176 nameItem->setData(variantMetaPointer, Qt::UserRole);
181 rootItem->appendRow(row);
183 rootItem->insertRow(position, row);
188 void ConfigurationDialog::btnClicked(QAbstractButton *button)
191 switch (d->buttonBox->standardButton(button))
196 case QDialogButtonBox::Ok:
197 if (this->validate())
200 this->saveSettings();
204 case QDialogButtonBox::Apply:
205 if (this->validate())
206 this->saveSettings();
209 case QDialogButtonBox::Cancel:
215 bool ConfigurationDialog::canConfigPageBeAdded(
ConfigPage *configPage)
217 return isConfigPageValid(configPage) && !hasConfigPage(configPage);
220 QModelIndex ConfigurationDialog::findPageModelIndex(
ConfigPage *page)
222 auto model =
static_cast<QStandardItemModel *
>(d->tvOptionsList->model());
223 return d->findPageModelIndex(model->indexFromItem(model->invisibleRootItem()), page);
226 bool ConfigurationDialog::isConfigPageValid(
ConfigPage *configPage)
228 return configPage !=
nullptr && !configPage->
name().isEmpty();
231 bool ConfigurationDialog::hasConfigPage(
ConfigPage *configPage)
235 if (configPage == addedPage)
242 void ConfigurationDialog::keyPressEvent(QKeyEvent *e)
254 QDialog::keyPressEvent(e);
258 bool ConfigurationDialog::hasItemOnList(QStandardItem *pItem)
const
260 if (pItem ==
nullptr)
263 auto pModel = (QStandardItemModel *)d->tvOptionsList->model();
268 return pModel->invisibleRootItem() == pItem
269 || pModel->indexFromItem(pItem).isValid();
272 void ConfigurationDialog::onPageValidationRequested()
274 auto page = qobject_cast<
ConfigPage *>(sender());
275 assert(page !=
nullptr);
279 void ConfigurationDialog::reject()
288 void ConfigurationDialog::switchToItem(
const QModelIndex ¤t,
const QModelIndex &previous)
290 if (current.isValid() && current != previous)
292 ConfigPage *configPage = d->pageFromIndex(current);
296 if (isConfigPageValid(configPage))
303 return d->tvOptionsList;
306 void ConfigurationDialog::saveSettings()
309 for (
int i = 0; i < d->configPages.count(); ++i)
310 d->configPages[i]->save();
317 for (
int i = 0; i < d->configPages.count(); ++i)
319 d->configPages[i]->read();
320 validatePage(d->configPages[i]);
327 if (d->currentlyDisplayedPage !=
nullptr)
329 validatePage(d->currentlyDisplayedPage);
330 d->currentlyDisplayedPage->hide();
331 d->mainPanel->setTitle(QString());
333 d->currentlyDisplayedPage = page;
339 d->mainPanel->layout()->addWidget(page);
340 d->mainPanel->setTitle(page->
title());
345 void ConfigurationDialog::validatePage(
ConfigPage *page)
347 assert(page !=
nullptr);
348 QModelIndex pageIndex = findPageModelIndex(page);
349 assert(pageIndex.isValid());
352 assert(validationIndex.isValid());
354 auto model =
static_cast<QStandardItemModel *
>(d->tvOptionsList->model());
355 QStandardItem *validationItem = model->itemFromIndex(validationIndex);
356 validationItem->setIcon(d->validationIcon(page->
validate()));