--- a/src/mainwindow.cpp Sun Nov 03 12:17:41 2019 +0200 +++ b/src/mainwindow.cpp Sun Nov 03 12:56:42 2019 +0200 @@ -23,6 +23,7 @@ connect(ui->actionSettingsEditor, &QAction::triggered, this, &MainWindow::runSettingsEditor); this->updateTitle(); this->restoreSettings(); + this->newModel(); } MainWindow::~MainWindow() @@ -31,8 +32,7 @@ void MainWindow::newModel() { - documents.newModel(); - this->updateTabs(); + this->openModelForEditing(documents.newModel()); } void MainWindow::openModel() @@ -44,22 +44,29 @@ tr("LDraw models (*.ldr *.dat)")); if (not path.isEmpty()) { - QString errorString; - QTextStream errorStream{&errorString}; - QString modelName = this->documents.openModel(path, errorStream); - if (not modelName.isEmpty()) - { - Document* document = new Document{this->documents.findModelByName(modelName)}; - this->ui->tabs->addTab(document, modelName); - } - else - { - const QString errorMessage = utility::format( + this->openModelFromPath(path); + } +} + +void MainWindow::openModelFromPath(const QString& path) +{ + QString errorString; + QTextStream errorStream{&errorString}; + QString modelName = this->documents.openModel(path, errorStream); + if (not modelName.isEmpty()) + { + this->openModelForEditing(modelName); + this->addRecentlyOpenedFile(path); + } + else + { + QMessageBox::critical( + this, + tr("Problem opening file"), + utility::format( tr("Could not open %1: %2"), path, - errorString); - QMessageBox::critical(this, tr("Problem opening file"), errorMessage); - } + errorString)); } } @@ -86,6 +93,27 @@ } } +void MainWindow::addRecentlyOpenedFile(const QString& path) +{ + this->recentlyOpenedFiles.removeAll(path); + this->recentlyOpenedFiles.insert(0, path); + while (this->recentlyOpenedFiles.size() > maxRecentlyOpenedFiles) + { + this->recentlyOpenedFiles.removeLast(); + } + this->saveSettings(); + this->updateRecentlyOpenedDocumentsMenu(); +} + +void MainWindow::openModelForEditing(const QString& modelName) +{ + Document* document = new Document{this->documents.findModelByName(modelName)}; + this->ui->tabs->addTab(document, modelName); + this->ui->tabs->setCurrentWidget(document); + document->restoreSplitterState(this->documentSplitterState); + connect(document, &Document::splitterChanged, this, &MainWindow::handleDocumentSplitterChange); +} + void MainWindow::runSettingsEditor() { SettingsEditor settingsEditor{&this->settings, this}; @@ -96,6 +124,46 @@ } } +void MainWindow::handleDocumentSplitterChange() +{ + Document* currentDocument = qobject_cast<Document*>(this->ui->tabs->currentWidget()); + if (currentDocument != nullptr) + { + this->documentSplitterState = currentDocument->saveSplitterState(); + for (int i = 0; i < this->ui->tabs->count(); i += 1) + { + Document* document = qobject_cast<Document*>(this->ui->tabs->widget(i)); + if (document != nullptr and document != currentDocument) + { + document->restoreSplitterState(this->documentSplitterState); + } + } + this->settings.setValue("MainWindow/DocumentSplitterState", this->documentSplitterState); + } +} + +void MainWindow::updateRecentlyOpenedDocumentsMenu() +{ + this->ui->menuRecentFiles->clear(); + for (const QString& path : this->recentlyOpenedFiles) + { + QAction* action = new QAction{path, this}; + action->setData(path); + this->ui->menuRecentFiles->addAction(action); + connect(action, &QAction::triggered, this, &MainWindow::openRecentFile); + } +} + +void MainWindow::openRecentFile() +{ + QAction* action = qobject_cast<QAction*>(this->sender()); + if (action != nullptr) + { + const QString path = action->data().toString(); + this->openModelFromPath(path); + } +} + void MainWindow::changeEvent(QEvent* event) { if (event != nullptr) @@ -123,51 +191,6 @@ } /** - * @brief Creates a new tab widget for the specified model. - * @param model Model to get a new tab widget for - * @return widget - */ -QWidget* MainWindow::createWidgetForModel(Model* model) -{ - Q_UNUSED(model); - QWidget* widget = new QWidget(ui->tabs); - QLabel* label = new QLabel("asdf", widget); - QVBoxLayout* layout = new QVBoxLayout; - layout->addWidget(label); - widget->setLayout(layout); - return widget; -} - -/** - * @brief Gets a tab widget for the specified model. If it does not exist, - * it will be created. - * @param model Model to get a tab widget for - * @return widget - */ -QWidget* MainWindow::getWidgetForModel(Model* model) -{ - QWidget* widget = this->modelWidgets.value(model); - if (widget == nullptr) - { - QWidget* const new_widget = createWidgetForModel(model); - this->modelWidgets[model] = new_widget; - return new_widget; - } - else - { - return widget; - } -} - -/** - * @brief Updates the tab widget - */ -void MainWindow::updateTabs() -{ - -} - -/** * @brief Updates the title of the main window so to contain the app's name * and version as well as the open document name. */ @@ -184,7 +207,9 @@ */ void MainWindow::saveSettings() { - this->settings.setValue("mainwindow/geometry", this->saveGeometry()); + this->settings.setValue("MainWindow/Geometry", this->saveGeometry()); + this->settings.setValue("MainWindow/RecentlyOpened", this->recentlyOpenedFiles); + this->settings.setValue("MainWindow/DocumentSplitterState", this->documentSplitterState); this->libraries.storeToSettings(&this->settings); } @@ -193,11 +218,14 @@ */ void MainWindow::restoreSettings() { - this->restoreGeometry(this->settings.value("mainwindow/geometry").toByteArray()); + this->restoreGeometry(this->settings.value("MainWindow/Geometry").toByteArray()); + this->recentlyOpenedFiles = this->settings.value("MainWindow/RecentlyOpened").toStringList(); + this->documentSplitterState = this->settings.value("MainWindow/DocumentSplitterState").toByteArray(); const QString systemLocale = QLocale::system().name(); const QVariant defaultLocale = this->settings.value("locale", systemLocale); changeLanguage(defaultLocale.toString()); this->libraries.restoreFromSettings(&this->settings); + this->updateRecentlyOpenedDocumentsMenu(); } QString MainWindow::pathToTranslation(const QString& localeCode)