summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMikaël Capelle <capelle.mikael@gmail.com>2020-12-31 03:28:18 +0100
committerMikaël Capelle <capelle.mikael@gmail.com>2021-01-02 15:38:17 +0100
commit4f89665056b2256ca353bc27314cd025db2f554c (patch)
treecab3d682a4cf35cd1dc5507d26c17f03711bac4a /src
parent51281ac304f64170d310ae543d50879614c550d3 (diff)
Move the regular context menu.
Diffstat (limited to 'src')
-rw-r--r--src/mainwindow.cpp233
-rw-r--r--src/mainwindow.h6
-rw-r--r--src/modlistcontextmenu.cpp118
-rw-r--r--src/modlistview.cpp14
-rw-r--r--src/modlistview.h5
-rw-r--r--src/modlistviewactions.cpp232
-rw-r--r--src/modlistviewactions.h19
7 files changed, 366 insertions, 261 deletions
diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp
index cd31a0bf..1475be50 100644
--- a/src/mainwindow.cpp
+++ b/src/mainwindow.cpp
@@ -539,6 +539,7 @@ void MainWindow::setupModList()
ui->modList->setup(m_OrganizerCore, actions, ui);
connect(actions, &ModListViewActions::overwriteCleared, [=]() { scheduleCheckForProblems(); });
+ connect(actions, &ModListViewActions::originModified, this, &MainWindow::originModified);
connect(ui->modList, &ModListView::removeSelectedMods, [=]() { removeMod_clicked(-1); });
connect(m_OrganizerCore.modList(), &ModList::clearOverwrite, actions, &ModListViewActions::clearOverwrite);
connect(m_OrganizerCore.modList(), &ModList::modPrioritiesChanged, [&]() { m_ArchiveListWriter.write(); });
@@ -2287,10 +2288,7 @@ void MainWindow::modInstalled(const QString &modName)
}
// force an update to happen
- std::multimap<QString, int> IDs;
- ModInfo::Ptr info = ModInfo::getByIndex(index);
- IDs.insert(std::make_pair<QString, int>(info->gameName(), info->nexusId()));
- modUpdateCheck(IDs);
+ ui->modList->actions().checkModsForUpdates({ m_OrganizerCore.modList()->index(index, 0) });
}
void MainWindow::showMessage(const QString &message)
@@ -3423,35 +3421,6 @@ void MainWindow::checkModsForUpdates()
}
}
-void MainWindow::changeVersioningScheme(int modIndex) {
- if (QMessageBox::question(this, tr("Continue?"),
- tr("The versioning scheme decides which version is considered newer than another.\n"
- "This function will guess the versioning scheme under the assumption that the installed version is outdated."),
- QMessageBox::Yes | QMessageBox::Cancel) == QMessageBox::Yes) {
-
- ModInfo::Ptr info = ModInfo::getByIndex(modIndex);
-
- bool success = false;
-
- static VersionInfo::VersionScheme schemes[] = { VersionInfo::SCHEME_REGULAR, VersionInfo::SCHEME_DECIMALMARK, VersionInfo::SCHEME_NUMBERSANDLETTERS };
-
- for (int i = 0; i < sizeof(schemes) / sizeof(VersionInfo::VersionScheme) && !success; ++i) {
- VersionInfo verOld(info->version().canonicalString(), schemes[i]);
- VersionInfo verNew(info->newestVersion().canonicalString(), schemes[i]);
- if (verOld < verNew) {
- info->setVersion(verOld);
- info->setNewestVersion(verNew);
- success = true;
- }
- }
- if (!success) {
- QMessageBox::information(this, tr("Sorry"),
- tr("I don't know a versioning scheme where %1 is newer than %2.").arg(info->newestVersion().canonicalString()).arg(info->version().canonicalString()),
- QMessageBox::Ok);
- }
- }
-}
-
void MainWindow::ignoreUpdate(int modIndex)
{
QItemSelectionModel *selection = ui->modList->selectionModel();
@@ -3470,22 +3439,6 @@ void MainWindow::ignoreUpdate(int modIndex)
}
}
-void MainWindow::checkModUpdates_clicked(int modIndex)
-{
- std::multimap<QString, int> IDs;
- QItemSelectionModel *selection = ui->modList->selectionModel();
- if (selection->hasSelection() && selection->selectedRows().count() > 1) {
- for (QModelIndex idx : selection->selectedRows()) {
- ModInfo::Ptr info = ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt());
- IDs.insert(std::make_pair<QString, int>(info->gameName(), info->nexusId()));
- }
- } else {
- ModInfo::Ptr info = ModInfo::getByIndex(modIndex);
- IDs.insert(std::make_pair<QString, int>(info->gameName(), info->nexusId()));
- }
- modUpdateCheck(IDs);
-}
-
void MainWindow::unignoreUpdate(int modIndex)
{
QItemSelectionModel *selection = ui->modList->selectionModel();
@@ -3652,162 +3605,14 @@ void MainWindow::addPluginSendToContextMenu(QMenu *menu)
void MainWindow::on_modList_customContextMenuRequested(const QPoint &pos)
{
try {
- QTreeView *modList = findChild<QTreeView*>("modList");
-
QModelIndex contextIdx = mapToModel(m_OrganizerCore.modList(), ui->modList->indexAt(pos));
if (!contextIdx.isValid()) {
// no selection
- ModListGlobalContextMenu(m_OrganizerCore, ui->modList).exec(modList->viewport()->mapToGlobal(pos));
+ ModListGlobalContextMenu(m_OrganizerCore, ui->modList).exec(ui->modList->viewport()->mapToGlobal(pos));
}
else {
- int modIndex = ui->modList->indexAt(pos).data(ModList::IndexRole).toInt();
- int contextColumn = contextIdx.column();
-
- ModListContextMenu menu(contextIdx, m_OrganizerCore, m_CategoryFactory, ui->modList);
-
- ModInfo::Ptr info = ModInfo::getByIndex(modIndex);
- std::vector<ModInfo::EFlag> flags = info->getFlags();
-
- // context menu for overwrites
- if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_OVERWRITE) != flags.end()) {
- }
-
- // context menu for mod backups
- else if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_BACKUP) != flags.end()) {
- }
-
- // separator
- else if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_SEPARATOR) != flags.end()){
- }
-
- // foregin
- else if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_FOREIGN) != flags.end()) {
- }
-
- // regular
- else {
- QMenu* addRemoveCategoriesMenu = new QMenu(tr("Change Categories"), &menu);
- populateMenuCategories(modIndex, addRemoveCategoriesMenu, 0);
- connect(addRemoveCategoriesMenu, &QMenu::aboutToHide, [=]() { addRemoveCategories_MenuHandler(addRemoveCategoriesMenu, modIndex, contextIdx); });
- addMenuAsPushButton(&menu, addRemoveCategoriesMenu);
-
- QMenu* primaryCategoryMenu = new QMenu(tr("Primary Category"), &menu);
- connect(primaryCategoryMenu, &QMenu::aboutToShow, [=]() { setPrimaryCategoryCandidates(primaryCategoryMenu, info); });
- addMenuAsPushButton(&menu, primaryCategoryMenu);
-
- menu.addSeparator();
-
- if (info->downgradeAvailable()) {
- menu.addAction(tr("Change versioning scheme"), [=]() { changeVersioningScheme(modIndex); });
- }
-
- if (info->nexusId() > 0)
- menu.addAction(tr("Force-check updates"), [=]() { checkModUpdates_clicked(modIndex); });
- if (info->updateIgnored()) {
- menu.addAction(tr("Un-ignore update"), [=]() { unignoreUpdate(modIndex); });
- }
- else {
- if (info->updateAvailable() || info->downgradeAvailable()) {
- menu.addAction(tr("Ignore update"), [=]() { ignoreUpdate(modIndex); });
- }
- }
- menu.addSeparator();
-
- menu.addAction(tr("Enable selected"), [=]() { enableSelectedMods_clicked(); });
- menu.addAction(tr("Disable selected"), [=]() { disableSelectedMods_clicked(); });
-
- menu.addSeparator();
-
- if (ui->modList->sortColumn() == ModList::COL_PRIORITY) {
- menu.addMenu(menu.createSendToContextMenu());
- menu.addSeparator();
- }
-
- menu.addAction(tr("Rename Mod..."), [=]() { renameMod_clicked(); });
- menu.addAction(tr("Reinstall Mod"), [=]() { reinstallMod_clicked(modIndex); });
- menu.addAction(tr("Remove Mod..."), [=]() { removeMod_clicked(modIndex); });
- menu.addAction(tr("Create Backup"), [=]() { backupMod_clicked(modIndex); });
-
- if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_HIDDEN_FILES) != flags.end()) {
- menu.addAction(tr("Restore hidden files"), [=]() { restoreHiddenFiles_clicked(modIndex); });
- }
-
- menu.addSeparator();
-
- if (contextColumn == ModList::COL_NOTES) {
- menu.addAction(tr("Select Color..."), [=]() { setColor_clicked(modIndex); });
- if (info->color().isValid()) {
- menu.addAction(tr("Reset Color"), [=]() { resetColor_clicked(modIndex); });
- }
- menu.addSeparator();
- }
-
- if (info->nexusId() > 0 && Settings::instance().nexus().endorsementIntegration()) {
- switch (info->endorsedState()) {
- case EndorsedState::ENDORSED_TRUE: {
- menu.addAction(tr("Un-Endorse"), [=]() { unendorse_clicked(); });
- } break;
- case EndorsedState::ENDORSED_FALSE: {
- menu.addAction(tr("Endorse"), [=]() { endorse_clicked(); });
- menu.addAction(tr("Won't endorse"), [=]() { dontendorse_clicked(modIndex); });
- } break;
- case EndorsedState::ENDORSED_NEVER: {
- menu.addAction(tr("Endorse"), [=]() { endorse_clicked(); });
- } break;
- default: {
- QAction *action = new QAction(tr("Endorsement state unknown"), &menu);
- action->setEnabled(false);
- menu.addAction(action);
- } break;
- }
- }
-
- if (info->nexusId() > 0 && Settings::instance().nexus().trackedIntegration()) {
- switch (info->trackedState()) {
- case TrackedState::TRACKED_FALSE: {
- menu.addAction(tr("Start tracking"), [=]() { track_clicked(); });
- } break;
- case TrackedState::TRACKED_TRUE: {
- menu.addAction(tr("Stop tracking"), [=]() { untrack_clicked(); });
- } break;
- default: {
- QAction *action = new QAction(tr("Tracked state unknown"), &menu);
- action->setEnabled(false);
- menu.addAction(action);
- } break;
- }
- }
-
- menu.addSeparator();
-
- std::vector<ModInfo::EFlag> flags = info->getFlags();
- if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_INVALID) != flags.end()) {
- menu.addAction(tr("Ignore missing data"), [=]() { ignoreMissingData_clicked(modIndex); });
- }
-
- if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_ALTERNATE_GAME) != flags.end()) {
- menu.addAction(tr("Mark as converted/working"), [=]() { markConverted_clicked(modIndex); });
- }
-
- menu.addSeparator();
-
- if (info->nexusId() > 0) {
- menu.addAction(tr("Visit on Nexus"), [=]() { visitOnNexus_clicked(modIndex); });
- }
-
- const auto url = info->parseCustomURL();
- if (url.isValid()) {
- menu.addAction(tr("Visit on %1").arg(url.host()), [=]() { visitWebPage_clicked(modIndex); });
- }
-
- menu.addAction(tr("Open in Explorer"), [=]() { ui->modList->actions().openExplorer({ contextIdx }); });
-
- QAction* infoAction = menu.addAction(tr("Information..."), [=]() { information_clicked(modIndex); });
- menu.setDefaultAction(infoAction);
- }
-
- menu.exec(modList->viewport()->mapToGlobal(pos));
+ ModListContextMenu(contextIdx, m_OrganizerCore, m_CategoryFactory, ui->modList).exec(ui->modList->viewport()->mapToGlobal(pos));
}
} catch (const std::exception &e) {
reportError(tr("Exception: ").arg(e.what()));
@@ -4091,18 +3896,6 @@ void MainWindow::sendSelectedPluginsToPriority_clicked()
m_OrganizerCore.pluginList()->sendToPriority(ui->espList->selectionModel(), newPriority);
}
-
-void MainWindow::enableSelectedMods_clicked()
-{
- ui->modList->enableSelected();
-}
-
-
-void MainWindow::disableSelectedMods_clicked()
-{
- ui->modList->disableSelected();
-}
-
void MainWindow::updateAvailable()
{
ui->actionUpdate->setEnabled(true);
@@ -4166,24 +3959,6 @@ void MainWindow::actionWontEndorseMO()
}
}
-void MainWindow::modUpdateCheck(std::multimap<QString, int> IDs)
-{
- if (m_OrganizerCore.settings().network().offlineMode()) {
- return;
- }
-
- if (NexusInterface::instance().getAccessManager()->validated()) {
- ModInfo::manualUpdateCheck(this, IDs);
- } else {
- QString apiKey;
- if (GlobalSettings::nexusApiKey(apiKey)) {
- m_OrganizerCore.doAfterLogin([=]() { this->modUpdateCheck(IDs); });
- NexusInterface::instance().getAccessManager()->apiCheck(apiKey);
- } else
- log::warn("{}", tr("You are not currently authenticated with Nexus. Please do so under Settings -> Nexus."));
- }
-}
-
void MainWindow::toggleMO2EndorseState()
{
const auto& s = m_OrganizerCore.settings();
diff --git a/src/mainwindow.h b/src/mainwindow.h
index 440e39cc..61bd9326 100644
--- a/src/mainwindow.h
+++ b/src/mainwindow.h
@@ -370,8 +370,6 @@ private slots:
void openPluginOriginExplorer_clicked();
void openOriginInformation_clicked();
void information_clicked(int modIndex);
- void enableSelectedMods_clicked();
- void disableSelectedMods_clicked();
// data-tree context menu
// pluginlist context menu
@@ -410,8 +408,6 @@ private slots:
void modInstalled(const QString &modName);
- void modUpdateCheck(std::multimap<QString, int> IDs);
-
void finishUpdateInfo();
void nxmEndorsementsAvailable(QVariant userData, QVariant resultData, int);
@@ -487,8 +483,6 @@ private slots:
void removeFromToolbar(QAction* action);
void overwriteClosed(int);
- void changeVersioningScheme(int modIndex);
- void checkModUpdates_clicked(int modIndex);
void ignoreUpdate(int modIndex);
void unignoreUpdate(int modIndex);
diff --git a/src/modlistcontextmenu.cpp b/src/modlistcontextmenu.cpp
index 05c2eebf..303362ba 100644
--- a/src/modlistcontextmenu.cpp
+++ b/src/modlistcontextmenu.cpp
@@ -257,7 +257,7 @@ void ModListContextMenu::addSeparatorActions(ModInfo::Ptr mod)
addAction(tr("Select Color..."), [=]() { m_actions.setColor(m_selected, m_index); });
if (mod->color().isValid()) {
- addAction(tr("Reset Color"), [=]() { m_actions.resetColor(m_selected, m_index); });
+ addAction(tr("Reset Color"), [=]() { m_actions.resetColor(m_selected); });
}
addSeparator();
@@ -297,5 +297,121 @@ void ModListContextMenu::addBackupActions(ModInfo::Ptr mod)
void ModListContextMenu::addRegularActions(ModInfo::Ptr mod)
{
+ auto flags = mod->getFlags();
+
+ // categories
+ ModListChangeCategoryMenu* categoriesMenu = new ModListChangeCategoryMenu(m_categories, mod, this);
+ connect(categoriesMenu, &QMenu::aboutToHide, [=]() {
+ m_actions.setCategories(m_selected, m_index, categoriesMenu->categories());
+ });
+ addMenuAsPushButton(categoriesMenu);
+
+ ModListPrimaryCategoryMenu* primaryCategoryMenu = new ModListPrimaryCategoryMenu(m_categories, mod, this);
+ addMenuAsPushButton(primaryCategoryMenu);
+ addSeparator();
+
+ if (mod->downgradeAvailable()) {
+ addAction(tr("Change versioning scheme"), [=]() { m_actions.changeVersioningScheme(m_index); });
+ }
+
+ if (mod->nexusId() > 0)
+ addAction(tr("Force-check updates"), [=]() { m_actions.checkModsForUpdates(m_selected); });
+ if (mod->updateIgnored()) {
+ addAction(tr("Un-ignore update"), [=]() { m_actions.setIgnoreUpdate(m_selected, false); });
+ }
+ else {
+ if (mod->updateAvailable() || mod->downgradeAvailable()) {
+ addAction(tr("Ignore update"), [=]() { m_actions.setIgnoreUpdate(m_selected, true); });
+ }
+ }
+ addSeparator();
+
+ addAction(tr("Enable selected"), [=]() { m_core.modList()->setActive(m_selected, true); });
+ addAction(tr("Disable selected"), [=]() { m_core.modList()->setActive(m_selected, false); });
+
+ addSeparator();
+
+
+ if (m_view->sortColumn() == ModList::COL_PRIORITY) {
+ addMenu(createSendToContextMenu());
+ addSeparator();
+ }
+
+ addAction(tr("Rename Mod..."), [=]() { m_actions.renameMod(m_index); });
+ addAction(tr("Reinstall Mod"), [=]() { m_actions.reinstallMod(m_index); });
+ addAction(tr("Remove Mod..."), [=]() { m_actions.removeMods(m_selected); });
+ addAction(tr("Create Backup"), [=]() { m_actions.createBackup(m_index); });
+
+ if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_HIDDEN_FILES) != flags.end()) {
+ addAction(tr("Restore hidden files"), [=]() { m_actions.restoreHiddenFiles(m_selected); });
+ }
+
+ addSeparator();
+
+ if (m_index.column() == ModList::COL_NOTES) {
+ addAction(tr("Select Color..."), [=]() { m_actions.setColor(m_selected, m_index); });
+ if (mod->color().isValid()) {
+ addAction(tr("Reset Color"), [=]() { m_actions.resetColor(m_selected); });
+ }
+ addSeparator();
+ }
+
+ if (mod->nexusId() > 0 && Settings::instance().nexus().endorsementIntegration()) {
+ switch (mod->endorsedState()) {
+ case EndorsedState::ENDORSED_TRUE: {
+ addAction(tr("Un-Endorse"), [=]() { m_actions.setEndorsed(m_selected, false); });
+ } break;
+ case EndorsedState::ENDORSED_FALSE: {
+ addAction(tr("Endorse"), [=]() { m_actions.setEndorsed(m_selected, true); });
+ addAction(tr("Won't endorse"), [=]() { m_actions.willNotEndorsed(m_selected); });
+ } break;
+ case EndorsedState::ENDORSED_NEVER: {
+ addAction(tr("Endorse"), [=]() { m_actions.setEndorsed(m_selected, true); });
+ } break;
+ default: {
+ QAction* action = new QAction(tr("Endorsement state unknown"), this);
+ action->setEnabled(false);
+ addAction(action);
+ } break;
+ }
+ }
+
+ if (mod->nexusId() > 0 && Settings::instance().nexus().trackedIntegration()) {
+ switch (mod->trackedState()) {
+ case TrackedState::TRACKED_FALSE: {
+ addAction(tr("Start tracking"), [=]() { m_actions.setTracked(m_selected, true); });
+ } break;
+ case TrackedState::TRACKED_TRUE: {
+ addAction(tr("Stop tracking"), [=]() { m_actions.setTracked(m_selected, false); });
+ } break;
+ default: {
+ QAction* action = new QAction(tr("Tracked state unknown"), this);
+ action->setEnabled(false);
+ addAction(action);
+ } break;
+ }
+ }
+
+ addSeparator();
+
+ if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_INVALID) != flags.end()) {
+ addAction(tr("Ignore missing data"), [=]() { m_actions.ignoreMissingData(m_selected); });
+ }
+ if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_ALTERNATE_GAME) != flags.end()) {
+ addAction(tr("Mark as converted/working"), [=]() { m_actions.markConverted(m_selected); });
+ }
+
+ addSeparator();
+
+ if (mod->nexusId() > 0) {
+ addAction(tr("Visit on Nexus"), [=]() { m_actions.visitOnNexus(m_selected); });
+ }
+
+ const auto url = mod->parseCustomURL();
+ if (url.isValid()) {
+ addAction(tr("Visit on %1").arg(url.host()), [=]() { m_actions.visitWebPage(m_selected); });
+ }
+
+ addAction(tr("Open in Explorer"), [=]() { m_actions.openExplorer(m_selected); });
}
diff --git a/src/modlistview.cpp b/src/modlistview.cpp
index 8c826882..cf35abdd 100644
--- a/src/modlistview.cpp
+++ b/src/modlistview.cpp
@@ -196,20 +196,6 @@ void ModListView::disableAllVisible()
m_core->modList()->setActive(indexViewToModel(allIndex(model())), false);
}
-void ModListView::enableSelected()
-{
- if (selectionModel()->hasSelection()) {
- m_core->modList()->setActive(indexViewToModel(selectionModel()->selectedRows()), true);
- }
-}
-
-void ModListView::disableSelected()
-{
- if (selectionModel()->hasSelection()) {
- m_core->modList()->setActive(indexViewToModel(selectionModel()->selectedRows()), false);
- }
-}
-
void ModListView::setFilterCriteria(const std::vector<ModListSortProxy::Criteria>& criteria)
{
m_sortProxy->setCriteria(criteria);
diff --git a/src/modlistview.h b/src/modlistview.h
index 0f131631..4f27769c 100644
--- a/src/modlistview.h
+++ b/src/modlistview.h
@@ -91,11 +91,6 @@ public slots:
void enableAllVisible();
void disableAllVisible();
- // enable/disable all selected mods
- //
- void enableSelected();
- void disableSelected();
-
// set the filter criteria/options for mods
//
void setFilterCriteria(const std::vector<ModListSortProxy::Criteria>& criteria);
diff --git a/src/modlistviewactions.cpp b/src/modlistviewactions.cpp
index f8fd0e4c..5b9c07bc 100644
--- a/src/modlistviewactions.cpp
+++ b/src/modlistviewactions.cpp
@@ -193,6 +193,36 @@ void ModListViewActions::checkModsForUpdates() const
}
}
+void ModListViewActions::checkModsForUpdates(std::multimap<QString, int> const& IDs) const
+{
+ if (m_core.settings().network().offlineMode()) {
+ return;
+ }
+
+ if (NexusInterface::instance().getAccessManager()->validated()) {
+ ModInfo::manualUpdateCheck(m_main, IDs);
+ }
+ else {
+ QString apiKey;
+ if (GlobalSettings::nexusApiKey(apiKey)) {
+ m_core.doAfterLogin([=]() { checkModsForUpdates(IDs); });
+ NexusInterface::instance().getAccessManager()->apiCheck(apiKey);
+ }
+ else
+ log::warn("{}", tr("You are not currently authenticated with Nexus. Please do so under Settings -> Nexus."));
+ }
+}
+
+void ModListViewActions::checkModsForUpdates(const QModelIndexList& indices) const
+{
+ std::multimap<QString, int> ids;
+ for (auto& idx : indices) {
+ ModInfo::Ptr info = ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt());
+ ids.insert(std::make_pair<QString, int>(info->gameName(), info->nexusId()));
+ }
+ checkModsForUpdates(ids);
+}
+
void ModListViewActions::exportModListCSV() const
{
QDialog selection(m_view);
@@ -509,7 +539,7 @@ void ModListViewActions::sendModsToSeparator(const QModelIndexList& index) const
void ModListViewActions::renameMod(const QModelIndex& index) const
{
try {
- m_view->edit(index);
+ m_view->edit(m_view->indexModelToView(index));
}
catch (const std::exception& e) {
reportError(tr("failed to rename mod: %1").arg(e.what()));
@@ -578,13 +608,52 @@ void ModListViewActions::ignoreMissingData(const QModelIndexList& indices) const
}
}
+void ModListViewActions::setIgnoreUpdate(const QModelIndexList& indices, bool ignore) const
+{
+ for (auto& idx : indices) {
+ int modIdx = idx.data(ModList::IndexRole).toInt();
+ ModInfo::Ptr info = ModInfo::getByIndex(modIdx);
+ info->ignoreUpdate(ignore);
+ m_core.modList()->notifyChange(modIdx);
+ }
+}
+
+void ModListViewActions::changeVersioningScheme(const QModelIndex& index) const {
+ if (QMessageBox::question(m_view, tr("Continue?"),
+ tr("The versioning scheme decides which version is considered newer than another.\n"
+ "This function will guess the versioning scheme under the assumption that the installed version is outdated."),
+ QMessageBox::Yes | QMessageBox::Cancel) == QMessageBox::Yes) {
+
+ ModInfo::Ptr info = ModInfo::getByIndex(index.data(ModList::IndexRole).toInt());
+
+ bool success = false;
+
+ static VersionInfo::VersionScheme schemes[] = { VersionInfo::SCHEME_REGULAR, VersionInfo::SCHEME_DECIMALMARK, VersionInfo::SCHEME_NUMBERSANDLETTERS };
+
+ for (int i = 0; i < sizeof(schemes) / sizeof(VersionInfo::VersionScheme) && !success; ++i) {
+ VersionInfo verOld(info->version().canonicalString(), schemes[i]);
+ VersionInfo verNew(info->newestVersion().canonicalString(), schemes[i]);
+ if (verOld < verNew) {
+ info->setVersion(verOld);
+ info->setNewestVersion(verNew);
+ success = true;
+ }
+ }
+ if (!success) {
+ QMessageBox::information(m_view, tr("Sorry"),
+ tr("I don't know a versioning scheme where %1 is newer than %2.").arg(info->newestVersion().canonicalString()).arg(info->version().canonicalString()),
+ QMessageBox::Ok);
+ }
+ }
+}
+
void ModListViewActions::markConverted(const QModelIndexList& indices) const
{
for (auto& idx : indices) {
- int row_idx = idx.data(ModList::IndexRole).toInt();
- ModInfo::Ptr info = ModInfo::getByIndex(row_idx);
+ int modIdx = idx.data(ModList::IndexRole).toInt();
+ ModInfo::Ptr info = ModInfo::getByIndex(modIdx);
info->markConverted(true);
- m_core.modList()->notifyChange(row_idx);
+ m_core.modList()->notifyChange(modIdx);
}
}
@@ -664,6 +733,159 @@ void ModListViewActions::visitNexusOrWebPage(const QModelIndexList& indices) con
}
}
+void ModListViewActions::reinstallMod(const QModelIndex& index) const
+{
+ ModInfo::Ptr modInfo = ModInfo::getByIndex(index.data(ModList::IndexRole).toInt());
+ QString installationFile = modInfo->installationFile();
+ if (installationFile.length() != 0) {
+ QString fullInstallationFile;
+ QFileInfo fileInfo(installationFile);
+ if (fileInfo.isAbsolute()) {
+ if (fileInfo.exists()) {
+ fullInstallationFile = installationFile;
+ }
+ else {
+ fullInstallationFile = m_core.downloadManager()->getOutputDirectory() + "/" + fileInfo.fileName();
+ }
+ }
+ else {
+ fullInstallationFile = m_core.downloadManager()->getOutputDirectory() + "/" + installationFile;
+ }
+ if (QFile::exists(fullInstallationFile)) {
+ m_core.installMod(fullInstallationFile, true, modInfo, modInfo->name());
+ }
+ else {
+ QMessageBox::information(m_view, tr("Failed"), tr("Installation file no longer exists"));
+ }
+ }
+ else {
+ QMessageBox::information(m_view, tr("Failed"),
+ tr("Mods installed with old versions of MO can't be reinstalled in this way."));
+ }
+}
+
+void ModListViewActions::createBackup(const QModelIndex& index) const
+{
+ ModInfo::Ptr modInfo = ModInfo::getByIndex(index.data(ModList::IndexRole).toInt());
+ QString backupDirectory = m_core.installationManager()->generateBackupName(modInfo->absolutePath());
+ if (!copyDir(modInfo->absolutePath(), backupDirectory, false)) {
+ QMessageBox::information(m_view, tr("Failed"),
+ tr("Failed to create backup."));
+ }
+ m_core.refresh();
+ m_view->updateModCount();
+}
+
+void ModListViewActions::restoreHiddenFiles(const QModelIndexList& indices) const
+{
+ const int max_items = 20;
+
+ QFlags<FileRenamer::RenameFlags> flags = FileRenamer::UNHIDE;
+ flags |= FileRenamer::MULTIPLE;
+
+ FileRenamer renamer(m_view, flags);
+
+ FileRenamer::RenameResults result = FileRenamer::RESULT_OK;
+
+ // multi selection
+ if (indices.size() > 1) {
+
+ QStringList modNames;
+ for (auto& idx : indices) {
+
+ ModInfo::Ptr modInfo = ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt());
+ const auto flags = modInfo->getFlags();
+
+ if (!modInfo->isRegular() ||
+ std::find(flags.begin(), flags.end(), ModInfo::FLAG_HIDDEN_FILES) == flags.end()) {
+ continue;
+ }
+
+ modNames.append(idx.data(Qt::DisplayRole).toString());
+ }
+
+ QString mods = "<li>" + modNames.mid(0, max_items).join("</li><li>") + "</li>";
+ if (modNames.size() > max_items) {
+ mods += "<li>...</li>";
+ }
+
+ if (QMessageBox::question(m_view, tr("Confirm"),
+ tr("Restore all hidden files in the following mods?<br><ul>%1</ul>").arg(mods),
+ QMessageBox::Yes | QMessageBox::No) == QMessageBox::Yes) {
+
+ for (auto& idx : indices) {
+
+ ModInfo::Ptr modInfo = ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt());
+
+ const auto flags = modInfo->getFlags();
+ if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_HIDDEN_FILES) != flags.end()) {
+ const QString modDir = modInfo->absolutePath();
+
+ auto partialResult = restoreHiddenFilesRecursive(renamer, modDir);
+
+ if (partialResult == FileRenamer::RESULT_CANCEL) {
+ result = FileRenamer::RESULT_CANCEL;
+ break;
+ }
+ emit originModified((m_core.directoryStructure()->getOriginByName(
+ ToWString(modInfo->internalName()))).getID());
+ }
+ }
+ }
+ }
+ else if (!indices.isEmpty()) {
+ //single selection
+ ModInfo::Ptr modInfo = ModInfo::getByIndex(indices[0].data(ModList::IndexRole).toInt());
+ const QString modDir = modInfo->absolutePath();
+
+ if (QMessageBox::question(m_view, tr("Are you sure?"),
+ tr("About to restore all hidden files in:\n") + modInfo->name(),
+ QMessageBox::Ok | QMessageBox::Cancel) == QMessageBox::Ok) {
+
+ result = restoreHiddenFilesRecursive(renamer, modDir);
+
+ emit originModified((m_core.directoryStructure()->getOriginByName(
+ ToWString(modInfo->internalName()))).getID());
+ }
+ }
+
+ if (result == FileRenamer::RESULT_CANCEL) {
+ log::debug("Restoring hidden files operation cancelled");
+ }
+ else {
+ log::debug("Finished restoring hidden files");
+ }
+}
+
+void ModListViewActions::setTracked(const QModelIndexList& indices, bool tracked) const
+{
+ m_core.loggedInAction(m_view, [=] {
+ for (auto& idx : indices) {
+ ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt())->track(tracked);
+ }
+ });
+}
+
+void ModListViewActions::setEndorsed(const QModelIndexList& indices, bool endorsed) const
+{
+ m_core.loggedInAction(m_view, [=] {
+ if (indices.size() > 1) {
+ MessageDialog::showMessage(tr("Endorsing multiple mods will take a while. Please wait..."), m_view);
+ }
+
+ for (auto& idx : indices) {
+ ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt())->endorse(endorsed);
+ }
+ });
+}
+
+void ModListViewActions::willNotEndorsed(const QModelIndexList& indices) const
+{
+ for (auto& idx : indices) {
+ ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt())->setNeverEndorse();
+ }
+}
+
void ModListViewActions::setColor(const QModelIndexList& indices, const QModelIndex& refIndex) const
{
auto& settings = m_core.settings();
@@ -696,7 +918,7 @@ void ModListViewActions::setColor(const QModelIndexList& indices, const QModelIn
}
-void ModListViewActions::resetColor(const QModelIndexList& indices, const QModelIndex& refIndex) const
+void ModListViewActions::resetColor(const QModelIndexList& indices) const
{
for (auto& idx : indices) {
ModInfo::Ptr info = ModInfo::getByIndex(idx.data(ModList::IndexRole).toInt());
diff --git a/src/modlistviewactions.h b/src/modlistviewactions.h
index 52db019c..26efde47 100644
--- a/src/modlistviewactions.h
+++ b/src/modlistviewactions.h
@@ -42,6 +42,7 @@ public:
// check all mods for update
//
void checkModsForUpdates() const;
+ void checkModsForUpdates(const QModelIndexList& indices) const;
// start the "Export Mod List" dialog
//
@@ -65,16 +66,24 @@ public:
void renameMod(const QModelIndex& index) const;
void removeMods(const QModelIndexList& indices) const;
void ignoreMissingData(const QModelIndexList& indices) const;
+ void setIgnoreUpdate(const QModelIndexList& indices, bool ignore) const;
+ void changeVersioningScheme(const QModelIndex& indices) const;
void markConverted(const QModelIndexList& indices) const;
void visitOnNexus(const QModelIndexList& indices) const;
void visitWebPage(const QModelIndexList& indices) const;
void visitNexusOrWebPage(const QModelIndexList& indices) const;
+ void reinstallMod(const QModelIndex& index) const;
+ void createBackup(const QModelIndex& index) const;
+ void restoreHiddenFiles(const QModelIndexList& indices) const;
+ void setTracked(const QModelIndexList& indices, bool tracked) const;
+ void setEndorsed(const QModelIndexList& indices, bool endorsed) const;
+ void willNotEndorsed(const QModelIndexList& indices) const;
// set/reset color of the given selection, using the given reference index (index
// at which the context menu was shown)
//
void setColor(const QModelIndexList& indices, const QModelIndex& refIndex) const;
- void resetColor(const QModelIndexList& indices, const QModelIndex& refIndex) const;
+ void resetColor(const QModelIndexList& indices) const;
// set the category of the mod in the given list, using the given index as reference
// - the categories are set as-is on the refernce mod
@@ -104,6 +113,10 @@ signals:
//
void overwriteCleared() const;
+ // emitted when the origin of a file is modified
+ //
+ void originModified(int originId) const;
+
private:
// move the contents of the overwrite to the given path
@@ -119,6 +132,10 @@ private:
//
void setCategoriesIf(ModInfo::Ptr mod, ModInfo::Ptr ref, const std::vector<std::pair<int, bool>>& categories) const;
+ // check the given mods from update, the map should map game names to nexus ID
+ //
+ void checkModsForUpdates(std::multimap<QString, int> const& IDs) const;
+
private:
OrganizerCore& m_core;