From 4f01b94f01180989abbdf0407cdf95483970dba8 Mon Sep 17 00:00:00 2001 From: isanae <14251494+isanae@users.noreply.github.com> Date: Fri, 7 Jun 2019 17:53:42 -0400 Subject: replaced ExecutablesList::getExecutables() by a standard container interface renamed ExecutablesList::init() to addFromPlugin() renamed ExecutablesList::find() to get() and added a find() that returns an iterator changed some calls from get() to find() so they can handle failure because they didn't seem to handle std::runtime_error at all --- src/editexecutablesdialog.cpp | 43 ++++++++++++++++---- src/executableslist.cpp | 84 +++++++++++++++++++-------------------- src/executableslist.h | 63 +++++++++++------------------ src/mainwindow.cpp | 92 ++++++++++++++++++++++++++----------------- src/organizercore.cpp | 16 ++++---- 5 files changed, 164 insertions(+), 134 deletions(-) (limited to 'src') diff --git a/src/editexecutablesdialog.cpp b/src/editexecutablesdialog.cpp index 67fbff31..9dbc6bae 100644 --- a/src/editexecutablesdialog.cpp +++ b/src/editexecutablesdialog.cpp @@ -59,20 +59,29 @@ ExecutablesList EditExecutablesDialog::getExecutablesList() const { ExecutablesList newList; for (int i = 0; i < ui->executablesListBox->count(); ++i) { - newList.addExecutable(m_ExecutablesList.find(ui->executablesListBox->item(i)->text())); + const auto& title = ui->executablesListBox->item(i)->text(); + auto itor = m_ExecutablesList.find(title); + + if (itor == m_ExecutablesList.end()) { + qWarning().nospace() + << "getExecutablesList(): executable '" << title << "' not found"; + + continue; + } + + newList.addExecutable(*itor); } + return newList; } void EditExecutablesDialog::refreshExecutablesWidget() { ui->executablesListBox->clear(); - std::vector::const_iterator current, end; - m_ExecutablesList.getExecutables(current, end); - for(; current != end; ++current) { - QListWidgetItem *newItem = new QListWidgetItem(current->title()); - newItem->setTextColor(current->isCustom() ? QColor(Qt::black) : QColor(Qt::darkGray)); + for(const auto& exe : m_ExecutablesList) { + QListWidgetItem *newItem = new QListWidgetItem(exe.title()); + newItem->setTextColor(exe.isCustom() ? QColor(Qt::black) : QColor(Qt::darkGray)); ui->executablesListBox->addItem(newItem); } @@ -282,7 +291,17 @@ void EditExecutablesDialog::on_titleEdit_textChanged(const QString &arg1) bool EditExecutablesDialog::executableChanged() { if (m_CurrentItem != nullptr) { - Executable const &selectedExecutable(m_ExecutablesList.find(m_CurrentItem->text())); + const auto& title = m_CurrentItem->text(); + auto itor = m_ExecutablesList.find(title); + + if (itor == m_ExecutablesList.end()) { + qWarning().nospace() + << "executableChanged(): title '" << title << "' not found"; + + return false; + } + + const Executable& selectedExecutable = *itor; QString storedCustomOverwrite = m_Profile->setting("custom_overwrites", selectedExecutable.title()).toString(); @@ -374,7 +393,15 @@ void EditExecutablesDialog::on_executablesListBox_clicked(const QModelIndex &cur m_CurrentItem = ui->executablesListBox->item(current.row()); - Executable const &selectedExecutable(m_ExecutablesList.find(m_CurrentItem->text())); + const auto& title = m_CurrentItem->text(); + auto itor = m_ExecutablesList.find(title); + + if (itor == m_ExecutablesList.end()) { + qWarning().nospace() << "selection: executable '" << title << "' not found"; + return; + } + + const Executable& selectedExecutable = *itor; ui->titleEdit->setText(selectedExecutable.title()); ui->binaryEdit->setText(QDir::toNativeSeparators(selectedExecutable.binaryInfo().absoluteFilePath())); diff --git a/src/executableslist.cpp b/src/executableslist.cpp index 79b17f5b..2ea9c3d9 100644 --- a/src/executableslist.cpp +++ b/src/executableslist.cpp @@ -33,19 +33,40 @@ along with Mod Organizer. If not, see . using namespace MOBase; +ExecutablesList::iterator ExecutablesList::begin() +{ + return m_Executables.begin(); +} + +ExecutablesList::const_iterator ExecutablesList::begin() const +{ + return m_Executables.begin(); +} + +ExecutablesList::iterator ExecutablesList::end() +{ + return m_Executables.end(); +} + +ExecutablesList::const_iterator ExecutablesList::end() const +{ + return m_Executables.end(); +} -ExecutablesList::ExecutablesList() +std::size_t ExecutablesList::size() const { + return m_Executables.size(); } -ExecutablesList::~ExecutablesList() +bool ExecutablesList::empty() const { + return m_Executables.empty(); } -void ExecutablesList::init(IPluginGame const *game) +void ExecutablesList::addFromPlugin(IPluginGame const *game) { Q_ASSERT(game != nullptr); - m_Executables.clear(); + for (const ExecutableInfo &info : game->executables()) { if (info.isValid()) { addExecutableInternal(info.title(), @@ -55,6 +76,7 @@ void ExecutablesList::init(IPluginGame const *game) info.steamAppID()); } } + ExecutableInfo explorerpp = ExecutableInfo("Explore Virtual Folder", QFileInfo(QCoreApplication::applicationDirPath() + "/explorer++/Explorer++.exe" )) .withArgument(QString("\"%1\"").arg(QDir::toNativeSeparators(game->dataDirectory().absolutePath()))); @@ -65,45 +87,25 @@ void ExecutablesList::init(IPluginGame const *game) explorerpp.workingDirectory().absolutePath(), explorerpp.steamAppID()); } - } -void ExecutablesList::getExecutables(std::vector::iterator &begin, std::vector::iterator &end) +const Executable &ExecutablesList::get(const QString &title) const { - begin = m_Executables.begin(); - end = m_Executables.end(); -} - -void ExecutablesList::getExecutables(std::vector::const_iterator &begin, - std::vector::const_iterator &end) const -{ - begin = m_Executables.begin(); - end = m_Executables.end(); -} - -const Executable &ExecutablesList::find(const QString &title) const -{ - for (Executable const &exe : m_Executables) { + for (const auto& exe : m_Executables) { if (exe.title() == title) { return exe; } } - throw std::runtime_error(QString("invalid executable name: %1").arg(title).toLocal8Bit().constData()); -} + throw std::runtime_error(QString("executable not found: %1").arg(title).toLocal8Bit().constData()); +} -Executable &ExecutablesList::find(const QString &title) +Executable &ExecutablesList::get(const QString &title) { - for (Executable &exe : m_Executables) { - if (exe.title() == title) { - return exe; - } - } - throw std::runtime_error(QString("invalid executable name: %1").arg(title).toLocal8Bit().constData()); + return const_cast(std::as_const(*this).get(title)); } - -Executable &ExecutablesList::findByBinary(const QFileInfo &info) +Executable &ExecutablesList::getByBinary(const QFileInfo &info) { for (Executable &exe : m_Executables) { if (exe.binaryInfo() == info) { @@ -113,17 +115,15 @@ Executable &ExecutablesList::findByBinary(const QFileInfo &info) throw std::runtime_error("invalid info"); } - -std::vector::iterator ExecutablesList::findExe(const QString &title) +ExecutablesList::iterator ExecutablesList::find(const QString &title) { - for (std::vector::iterator iter = m_Executables.begin(); iter != m_Executables.end(); ++iter) { - if (iter->title() == title) { - return iter; - } - } - return m_Executables.end(); + return std::find_if(begin(), end(), [&](auto&& e) { return e.title() == title; }); } +ExecutablesList::const_iterator ExecutablesList::find(const QString &title) const +{ + return std::find_if(begin(), end(), [&](auto&& e) { return e.title() == title; }); +} bool ExecutablesList::titleExists(const QString &title) const { @@ -131,10 +131,9 @@ bool ExecutablesList::titleExists(const QString &title) const return std::find_if(m_Executables.begin(), m_Executables.end(), test) != m_Executables.end(); } - void ExecutablesList::addExecutable(const Executable &executable) { - auto existingExe = findExe(executable.title()); + auto existingExe = find(executable.title()); if (existingExe != m_Executables.end()) { *existingExe = executable; } else { @@ -142,7 +141,6 @@ void ExecutablesList::addExecutable(const Executable &executable) } } - void ExecutablesList::updateExecutable(const QString &title, const QString &executableName, const QString &arguments, @@ -153,7 +151,7 @@ void ExecutablesList::updateExecutable(const QString &title, { QFileInfo file(executableName); QDir dir(workingDirectory); - auto existingExe = findExe(title); + auto existingExe = find(title); flags &= mask; if (existingExe != m_Executables.end()) { diff --git a/src/executableslist.h b/src/executableslist.h index 0e43b337..b8e4cf77 100644 --- a/src/executableslist.h +++ b/src/executableslist.h @@ -88,28 +88,33 @@ private: **/ class ExecutablesList { public: + using vector_type = std::vector; + using iterator = vector_type::iterator; + using const_iterator = vector_type::const_iterator; /** - * @brief constructor - * - **/ - ExecutablesList(); - - ~ExecutablesList(); + * standard container interface + */ + iterator begin(); + const_iterator begin() const; + iterator end(); + const_iterator end() const; + std::size_t size() const; + bool empty() const; /** - * @brief initialise the list with the executables preconfigured for this game + * @brief add the executables preconfigured for this game **/ - void init(MOBase::IPluginGame const *game); + void addFromPlugin(MOBase::IPluginGame const *game); /** - * @brief find an executable by its name + * @brief get an executable by name * * @param title the title of the executable to look up * @return the executable - * @exception runtime_error will throw an exception if the name is not correct + * @exception runtime_error will throw an exception if the executable is not found **/ - const Executable &find(const QString &title) const; + const Executable &get(const QString &title) const; /** * @brief find an executable by its name @@ -118,7 +123,7 @@ public: * @return the executable * @exception runtime_error will throw an exception if the name is not correct **/ - Executable &find(const QString &title); + Executable &get(const QString &title); /** * @brief find an executable by a fileinfo structure @@ -126,7 +131,13 @@ public: * @return the executable * @exception runtime_error will throw an exception if the name is not correct */ - Executable &findByBinary(const QFileInfo &info); + Executable &getByBinary(const QFileInfo &info); + + /** + * @brief returns an iterator for the given executable by title, or end() + */ + iterator find(const QString &title); + const_iterator find(const QString &title) const; /** * @brief determine if an executable exists @@ -183,33 +194,7 @@ public: **/ void remove(const QString &title); - /** - * @brief retrieve begin and end iterators of the configured executables - * - * @param begin iterator to the first executable - * @param end iterator one past the last executable - **/ - void getExecutables(std::vector::const_iterator &begin, std::vector::const_iterator &end) const; - - /** - * @brief retrieve begin and end iterators of the configured executables - * - * @param begin iterator to the first executable - * @param end iterator one past the last executable - **/ - void getExecutables(std::vector::iterator &begin, std::vector::iterator &end); - - /** - * @brief get the number of executables (custom or otherwise) - **/ - size_t size() const { - return m_Executables.size(); - } - private: - - std::vector::iterator findExe(const QString &title); - void addExecutableInternal(const QString &title, const QString &executableName, const QString &arguments, const QString &workingDirectory, const QString &steamAppID); diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp index 38b2ed3f..2fbdbec7 100644 --- a/src/mainwindow.cpp +++ b/src/mainwindow.cpp @@ -733,15 +733,12 @@ void MainWindow::updatePinnedExecutables() bool hasLinks = false; - std::vector::iterator begin, end; - m_OrganizerCore.executablesList()->getExecutables(begin, end); - - for (auto iter = begin; iter != end; ++iter) { - if (iter->isShownOnToolbar()) { + for (const auto& exe : *m_OrganizerCore.executablesList()) { + if (exe.isShownOnToolbar()) { hasLinks = true; QAction *exeAction = new QAction( - iconForExecutable(iter->binaryInfo().filePath()), iter->title()); + iconForExecutable(exe.binaryInfo().filePath()), exe.title()); exeAction->setObjectName(QString("custom__") + iter->m_Title); exeAction->setStatusTip(iter->m_BinaryInfo.filePath()); @@ -1504,24 +1501,42 @@ void MainWindow::registerModPage(IPluginModPage *modPage) void MainWindow::startExeAction() { QAction *action = qobject_cast(sender()); - if (action != nullptr) { - const Executable &selectedExecutable(m_OrganizerCore.executablesList()->find(action->text())); - QString customOverwrite = m_OrganizerCore.currentProfile()->setting("custom_overwrites", selectedExecutable.title()).toString(); - auto forcedLibraries = m_OrganizerCore.currentProfile()->determineForcedLibraries(selectedExecutable.title()); - if (!m_OrganizerCore.currentProfile()->forcedLibrariesEnabled(selectedExecutable.title())) { - forcedLibraries.clear(); - } - m_OrganizerCore.spawnBinary( - selectedExecutable.binaryInfo(), selectedExecutable.arguments(), - selectedExecutable.workingDirectory().length() != 0 - ? selectedExecutable.workingDirectory() - : selectedExecutable.binaryInfo().absolutePath(), - selectedExecutable.steamAppID(), - customOverwrite, - forcedLibraries); - } else { + + if (action == nullptr) { qCritical("not an action?"); + return; } + + const auto& list = *m_OrganizerCore.executablesList(); + + const auto title = action->text(); + auto itor = list.find(title); + + if (itor == list.end()) { + qWarning().nospace() + << "startExeAction(): executable '" << title << "' not found"; + + return; + } + + const Executable& exe = *itor; + auto& profile = *m_OrganizerCore.currentProfile(); + + QString customOverwrite = profile.setting("custom_overwrites", exe.title()).toString(); + auto forcedLibraries = profile.determineForcedLibraries(exe.title()); + + if (!profile.forcedLibrariesEnabled(exe.title())) { + forcedLibraries.clear(); + } + + m_OrganizerCore.spawnBinary( + exe.binaryInfo(), exe.arguments(), + exe.workingDirectory().length() != 0 + ? exe.workingDirectory() + : exe.binaryInfo().absolutePath(), + exe.steamAppID(), + customOverwrite, + forcedLibraries); } @@ -1789,12 +1804,12 @@ void MainWindow::refreshExecutablesList() QAbstractItemModel *model = executablesList->model(); - std::vector::const_iterator current, end; - m_OrganizerCore.executablesList()->getExecutables(current, end); - for(int i = 0; current != end; ++current, ++i) { - QIcon icon = iconForExecutable(current->binaryInfo().filePath()); - executablesList->addItem(icon, current->title()); + int i = 0; + for (const auto& exe : *m_OrganizerCore.executablesList()) { + QIcon icon = iconForExecutable(exe.binaryInfo().filePath()); + executablesList->addItem(icon, exe.title()); model->setData(model->index(i, 0), QSize(0, executablesList->iconSize().height() + 4), Qt::SizeHintRole); + ++i; } setExecutableIndex(1); @@ -6389,13 +6404,18 @@ void MainWindow::unlockESPIndex() void MainWindow::removeFromToolbar() { - try { - Executable &exe = m_OrganizerCore.executablesList()->find(m_ContextAction->text()); - exe.setShownOnToolbar(false); - } catch (const std::runtime_error&) { - qDebug("executable doesn't exist any more"); + const auto& title = m_ContextAction->text(); + auto& list = *m_OrganizerCore.executablesList(); + + auto itor = list.find(title); + if (itor == list.end()) { + qWarning().nospace() + << "removeFromToolbar(): executable '" << title << "' not found"; + + return; } + itor->setShownOnToolbar(false); updatePinnedExecutables(); } @@ -6520,14 +6540,14 @@ void MainWindow::on_groupCombo_currentIndexChanged(int index) const Executable &MainWindow::getSelectedExecutable() const { - QString name = ui->executablesListBox->itemText(ui->executablesListBox->currentIndex()); - return m_OrganizerCore.executablesList()->find(name); + const QString name = ui->executablesListBox->itemText(ui->executablesListBox->currentIndex()); + return m_OrganizerCore.executablesList()->get(name); } Executable &MainWindow::getSelectedExecutable() { - QString name = ui->executablesListBox->itemText(ui->executablesListBox->currentIndex()); - return m_OrganizerCore.executablesList()->find(name); + const QString name = ui->executablesListBox->itemText(ui->executablesListBox->currentIndex()); + return m_OrganizerCore.executablesList()->get(name); } void MainWindow::on_linkButton_pressed() diff --git a/src/organizercore.cpp b/src/organizercore.cpp index cfbcad39..4d11a35f 100644 --- a/src/organizercore.cpp +++ b/src/organizercore.cpp @@ -375,11 +375,10 @@ QSettings::Status OrganizerCore::storeSettings(const QString &fileName) settings.remove("customExecutables"); settings.beginWriteArray("customExecutables"); - std::vector::const_iterator current, end; - m_ExecutablesList.getExecutables(current, end); + int count = 0; - for (; current != end; ++current) { - const Executable &item = *current; + + for (const auto& item : m_ExecutablesList) { settings.setArrayIndex(count++); settings.setValue("title", item.title()); settings.setValue("custom", item.isCustom()); @@ -508,7 +507,7 @@ void OrganizerCore::updateExecutablesList(QSettings &settings) return; } - m_ExecutablesList.init(managedGame()); + m_ExecutablesList.addFromPlugin(managedGame()); qDebug("setting up configured executables"); @@ -1735,7 +1734,8 @@ HANDLE OrganizerCore::runShortcut(const MOShortcut& shortcut) .arg(shortcut.instance(),shortcut.executable()) .toLocal8Bit().constData()); - Executable& exe = m_ExecutablesList.find(shortcut.executable()); + const Executable& exe = m_ExecutablesList.get(shortcut.executable()); + auto forcedLibaries = m_CurrentProfile->determineForcedLibraries(shortcut.executable()); if (!m_CurrentProfile->forcedLibrariesEnabled(shortcut.executable())) { forcedLibaries.clear(); @@ -1786,7 +1786,7 @@ HANDLE OrganizerCore::startApplication(const QString &executable, currentDirectory = binary.absolutePath(); } try { - const Executable &exe = m_ExecutablesList.findByBinary(binary); + const Executable &exe = m_ExecutablesList.getByBinary(binary); steamAppID = exe.steamAppID(); customOverwrite = m_CurrentProfile->setting("custom_overwrites", exe.title()) @@ -1800,7 +1800,7 @@ HANDLE OrganizerCore::startApplication(const QString &executable, } else { // only a file name, search executables list try { - const Executable &exe = m_ExecutablesList.find(executable); + const Executable &exe = m_ExecutablesList.get(executable); steamAppID = exe.steamAppID(); customOverwrite = m_CurrentProfile->setting("custom_overwrites", exe.title()) -- cgit v1.3.1