summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mainwindow.cpp104
-rw-r--r--src/mainwindow.h5
-rw-r--r--src/modinfodialog.cpp358
-rw-r--r--src/modinfodialog.h58
-rw-r--r--src/modinfodialogcategories.cpp2
-rw-r--r--src/modinfodialogconflicts.cpp7
-rw-r--r--src/modinfodialogconflicts.h3
-rw-r--r--src/modinfodialogesps.cpp2
-rw-r--r--src/modinfodialogfiletree.cpp4
-rw-r--r--src/modinfodialogimages.cpp12
-rw-r--r--src/modinfodialogimages.h2
-rw-r--r--src/modinfodialognexus.cpp2
-rw-r--r--src/modinfodialogtab.cpp22
-rw-r--r--src/modinfodialogtab.h3
-rw-r--r--src/modinfodialogtextfiles.cpp2
15 files changed, 374 insertions, 212 deletions
diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp
index f9bfaafb..67dc8418 100644
--- a/src/mainwindow.cpp
+++ b/src/mainwindow.cpp
@@ -3223,18 +3223,14 @@ void MainWindow::displayModInformation(ModInfo::Ptr modInfo, unsigned int index,
} else {
modInfo->saveMeta();
- ModInfoDialog dialog(
- modInfo, modInfo->hasFlag(ModInfo::FLAG_FOREIGN),
- &m_OrganizerCore, &m_PluginContainer, this);
-
- connect(&dialog, SIGNAL(modOpen(QString, int)), this, SLOT(displayModInformation(QString, int)), Qt::QueuedConnection);
- connect(&dialog, SIGNAL(modOpenNext(int)), this, SLOT(modOpenNext(int)), Qt::QueuedConnection);
- connect(&dialog, SIGNAL(modOpenPrev(int)), this, SLOT(modOpenPrev(int)), Qt::QueuedConnection);
+ ModInfoDialog dialog(this, &m_OrganizerCore, &m_PluginContainer);
connect(&dialog, SIGNAL(originModified(int)), this, SLOT(originModified(int)));
+ dialog.setMod(modInfo);
+
//Open the tab first if we want to use the standard indexes of the tabs.
if (tab != -1) {
- dialog.openTab(tab);
+ dialog.setTab(tab);
}
dialog.restoreState(m_OrganizerCore.settings());
@@ -3244,16 +3240,6 @@ void MainWindow::displayModInformation(ModInfo::Ptr modInfo, unsigned int index,
dialog.restoreGeometry(settings.value(key).toByteArray());
}
- //If no tab was specified use the first tab from the left based on the user order.
- if (tab == -1) {
- for (int i = 0; i < dialog.findChild<QTabWidget*>("tabWidget")->count(); ++i) {
- if (dialog.findChild<QTabWidget*>("tabWidget")->isTabEnabled(i)) {
- dialog.findChild<QTabWidget*>("tabWidget")->setCurrentIndex(i);
- break;
- }
- }
- }
-
dialog.exec();
dialog.saveState(m_OrganizerCore.settings());
settings.setValue(key, dialog.saveGeometry());
@@ -3296,43 +3282,71 @@ void MainWindow::setWindowEnabled(bool enabled)
}
-void MainWindow::modOpenNext(int tab)
+ModInfo::Ptr MainWindow::nextModInList()
{
- QModelIndex index = m_ModListSortProxy->mapFromSource(m_OrganizerCore.modList()->index(m_ContextRow, 0));
- index = m_ModListSortProxy->index((index.row() + 1) % m_ModListSortProxy->rowCount(), 0);
+ const QModelIndex start = m_ModListSortProxy->mapFromSource(
+ m_OrganizerCore.modList()->index(m_ContextRow, 0));
+
+ auto index = start;
+
+ for (;;) {
+ index = m_ModListSortProxy->index((index.row() + 1) % m_ModListSortProxy->rowCount(), 0);
+ m_ContextRow = m_ModListSortProxy->mapToSource(index).row();
+
+ if (index == start || !index.isValid()) {
+ // wrapped around, give up
+ break;
+ }
+
+ ModInfo::Ptr mod = ModInfo::getByIndex(m_ContextRow);
- m_ContextRow = m_ModListSortProxy->mapToSource(index).row();
- ModInfo::Ptr mod = ModInfo::getByIndex(m_ContextRow);
- std::vector<ModInfo::EFlag> flags = mod->getFlags();
- if ((std::find(flags.begin(), flags.end(), ModInfo::FLAG_OVERWRITE) != flags.end()) ||
- (std::find(flags.begin(), flags.end(), ModInfo::FLAG_BACKUP) != flags.end()) ||
- (std::find(flags.begin(), flags.end(), ModInfo::FLAG_SEPARATOR) != flags.end())) {
// skip overwrite and backups and separators
- modOpenNext(tab);
- } else {
- displayModInformation(m_ContextRow,tab);
+ if (mod->hasFlag(ModInfo::FLAG_OVERWRITE) ||
+ mod->hasFlag(ModInfo::FLAG_BACKUP) ||
+ mod->hasFlag(ModInfo::FLAG_SEPARATOR)) {
+ continue;
+ }
+
+ return mod;
}
+
+ return {};
}
-void MainWindow::modOpenPrev(int tab)
+ModInfo::Ptr MainWindow::previousModInList()
{
- QModelIndex index = m_ModListSortProxy->mapFromSource(m_OrganizerCore.modList()->index(m_ContextRow, 0));
- int row = index.row() - 1;
- if (row == -1) {
- row = m_ModListSortProxy->rowCount() - 1;
- }
+ const QModelIndex start = m_ModListSortProxy->mapFromSource(
+ m_OrganizerCore.modList()->index(m_ContextRow, 0));
+
+ auto index = start;
+
+ for (;;) {
+ int row = index.row() - 1;
+ if (row == -1) {
+ row = m_ModListSortProxy->rowCount() - 1;
+ }
+
+ index = m_ModListSortProxy->index(row, 0);
+ m_ContextRow = m_ModListSortProxy->mapToSource(index).row();
+
+ if (index == start || !index.isValid()) {
+ // wrapped around, give up
+ break;
+ }
- m_ContextRow = m_ModListSortProxy->mapToSource(m_ModListSortProxy->index(row, 0)).row();
- ModInfo::Ptr mod = ModInfo::getByIndex(m_ContextRow);
- std::vector<ModInfo::EFlag> flags = mod->getFlags();
- if ((std::find(flags.begin(), flags.end(), ModInfo::FLAG_OVERWRITE) != flags.end()) ||
- (std::find(flags.begin(), flags.end(), ModInfo::FLAG_BACKUP) != flags.end()) ||
- (std::find(flags.begin(), flags.end(), ModInfo::FLAG_SEPARATOR) != flags.end())) {
// skip overwrite and backups and separators
- modOpenPrev(tab);
- } else {
- displayModInformation(m_ContextRow,tab);
+ ModInfo::Ptr mod = ModInfo::getByIndex(m_ContextRow);
+
+ if (mod->hasFlag(ModInfo::FLAG_OVERWRITE) ||
+ mod->hasFlag(ModInfo::FLAG_BACKUP) ||
+ mod->hasFlag(ModInfo::FLAG_SEPARATOR)) {
+ continue;
+ }
+
+ return mod;
}
+
+ return {};
}
void MainWindow::displayModInformation(const QString &modName, int tab)
diff --git a/src/mainwindow.h b/src/mainwindow.h
index b6283a26..f204211e 100644
--- a/src/mainwindow.h
+++ b/src/mainwindow.h
@@ -160,6 +160,9 @@ public:
virtual MOBase::DelayedFileWriterBase &archivesWriter() override { return m_ArchiveListWriter; }
+ ModInfo::Ptr nextModInList();
+ ModInfo::Ptr previousModInList();
+
public slots:
void displayColumnSelection(const QPoint &pos);
@@ -549,8 +552,6 @@ private slots:
void deselectFilters();
void displayModInformation(const QString &modName, int tab);
- void modOpenNext(int tab=-1);
- void modOpenPrev(int tab=-1);
void modRenamed(const QString &oldName, const QString &newName);
void modRemoved(const QString &fileName);
diff --git a/src/modinfodialog.cpp b/src/modinfodialog.cpp
index be7d4aa4..ad704ce8 100644
--- a/src/modinfodialog.cpp
+++ b/src/modinfodialog.cpp
@@ -21,6 +21,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>.
#include "ui_modinfodialog.h"
#include "plugincontainer.h"
#include "organizercore.h"
+#include "mainwindow.h"
#include "modinfodialogtextfiles.h"
#include "modinfodialogimages.h"
#include "modinfodialogesps.h"
@@ -34,23 +35,6 @@ using namespace MOShared;
const int max_scan_for_context_menu = 50;
-
-class ModFileListWidget : public QListWidgetItem {
- friend bool operator<(const ModFileListWidget &LHS, const ModFileListWidget &RHS);
-public:
- ModFileListWidget(const QString &text, int sortValue, QListWidget *parent = 0)
- : QListWidgetItem(text, parent, QListWidgetItem::UserType + 1), m_SortValue(sortValue) {}
-private:
- int m_SortValue;
-};
-
-
-static bool operator<(const ModFileListWidget &LHS, const ModFileListWidget &RHS)
-{
- return LHS.m_SortValue < RHS.m_SortValue;
-}
-
-
bool canPreviewFile(
PluginContainer& pluginContainer, bool isArchive, const QString& filename)
{
@@ -111,74 +95,54 @@ FileRenamer::RenameResults unhideFile(FileRenamer& renamer, const QString &oldNa
}
+ModInfoDialog::TabInfo::TabInfo(std::unique_ptr<ModInfoDialogTab> tab)
+ : tab(std::move(tab)), realPos(-1), widget(nullptr)
+{
+}
+
ModInfoDialog::ModInfoDialog(
- ModInfo::Ptr modInfo, bool unmanaged, OrganizerCore *organizerCore,
- PluginContainer *pluginContainer, QWidget *parent) :
- TutorableDialog("ModInfoDialog", parent), ui(new Ui::ModInfoDialog),
- m_ModInfo(modInfo), m_RootPath(modInfo->absolutePath()),
- m_OrganizerCore(organizerCore), m_PluginContainer(pluginContainer),
- m_Origin(nullptr)
+ MainWindow* mw, OrganizerCore* core, PluginContainer* plugin) :
+ TutorableDialog("ModInfoDialog", mw),
+ ui(new Ui::ModInfoDialog), m_mainWindow(mw),
+ m_core(core), m_plugin(plugin), m_initialTab(-1)
{
ui->setupUi(this);
- auto* ds = m_OrganizerCore->directoryStructure();
- if (ds->originExists(ToWString(m_ModInfo->name()))) {
- m_Origin = &ds->getOriginByName(ToWString(m_ModInfo->name()));
- if (m_Origin->isDisabled()) {
- m_Origin = nullptr;
- }
- }
-
- this->setWindowTitle(m_ModInfo->name());
- this->setWindowModality(Qt::WindowModal);
-
auto* sc = new QShortcut(QKeySequence::Delete, this);
connect(sc, &QShortcut::activated, [&]{ onDeleteShortcut(); });
m_tabs = createTabs();
- bool tabSelected = false;
- for (std::size_t i=0; i<m_tabs.size(); ++i) {
+ for (int i=0; i<ui->tabWidget->count(); ++i) {
+ if (static_cast<std::size_t>(i) >= m_tabs.size()) {
+ qCritical() << "mod info dialog has more tabs than expected";
+ break;
+ }
+
+ auto& tabInfo = m_tabs[static_cast<std::size_t>(i)];
+ tabInfo.widget = ui->tabWidget->widget(i);
+ tabInfo.caption = ui->tabWidget->tabText(i);
+ tabInfo.icon = ui->tabWidget->tabIcon(i);
+ tabInfo.realPos = i;
+
connect(
- m_tabs[i].get(), &ModInfoDialogTab::originModified,
+ tabInfo.tab.get(), &ModInfoDialogTab::originModified,
[&](int originID){ emit originModified(originID); });
connect(
- m_tabs[i].get(), &ModInfoDialogTab::modOpen,
+ tabInfo.tab.get(), &ModInfoDialogTab::modOpen,
[&](const QString& name){
- close();
- emit modOpen(name, static_cast<int>(i));
+ setMod(name);
+ update();
});
-
- bool enabled = true;
-
- if (unmanaged) {
- enabled = m_tabs[i]->canHandleUnmanaged();
- } else if (m_ModInfo->hasFlag(ModInfo::FLAG_SEPARATOR)) {
- enabled = m_tabs[i]->canHandleSeparators();
- }
-
- ui->tabWidget->setTabEnabled(static_cast<int>(i), enabled);
-
- if (!tabSelected && enabled) {
- ui->tabWidget->setCurrentIndex(static_cast<int>(i));
- tabSelected = true;
- }
- }
-
- for (auto& tab : m_tabs) {
- tab->setMod(m_ModInfo, m_Origin);
}
}
-ModInfoDialog::~ModInfoDialog()
-{
- delete ui;
-}
+ModInfoDialog::~ModInfoDialog() = default;
-std::vector<std::unique_ptr<ModInfoDialogTab>> ModInfoDialog::createTabs()
+std::vector<ModInfoDialog::TabInfo> ModInfoDialog::createTabs()
{
- std::vector<std::unique_ptr<ModInfoDialogTab>> v;
+ std::vector<TabInfo> v;
v.push_back(createTab<TextFilesTab>(TAB_TEXTFILES));
v.push_back(createTab<IniFilesTab>(TAB_INIFILES));
@@ -195,31 +159,206 @@ std::vector<std::unique_ptr<ModInfoDialogTab>> ModInfoDialog::createTabs()
int ModInfoDialog::exec()
{
- refreshLists();
+ update();
return TutorableDialog::exec();
}
+void ModInfoDialog::setMod(ModInfo::Ptr mod)
+{
+ m_mod = mod;
+}
+
+void ModInfoDialog::setMod(const QString& name)
+{
+ unsigned int index = ModInfo::getIndex(name);
+ if (index == UINT_MAX) {
+ qCritical() << "failed to resolve mod name " << name;
+ return;
+ }
+
+ auto mod = ModInfo::getByIndex(index);
+ if (!mod) {
+ qCritical() << "mod by index " << index << " is null";
+ return;
+ }
+
+ setMod(mod);
+}
+
+void ModInfoDialog::setTab(int index)
+{
+ if (!isVisible()) {
+ m_initialTab = index;
+ return;
+ }
+
+ switchToTab(index);
+}
+
+void ModInfoDialog::update()
+{
+ setWindowTitle(m_mod->name());
+ setTabsVisibility();
+ updateTabs();
+ feedFiles();
+ setTabsColors();
+
+ if (m_initialTab >= 0) {
+ switchToTab(m_initialTab);
+ m_initialTab = -1;
+ }
+}
+
+void ModInfoDialog::setTabsVisibility()
+{
+ std::vector<bool> visibility(m_tabs.size());
+ bool changed = false;
+
+ for (std::size_t i=0; i<m_tabs.size(); ++i) {
+ const auto& tabInfo = m_tabs[i];
+
+ bool visible = true;
+
+ if (m_mod->hasFlag(ModInfo::FLAG_FOREIGN)) {
+ visible = tabInfo.tab->canHandleUnmanaged();
+ } else if (m_mod->hasFlag(ModInfo::FLAG_SEPARATOR)) {
+ visible = tabInfo.tab->canHandleSeparators();
+ }
+
+ const auto currentlyVisible = (ui->tabWidget->indexOf(tabInfo.widget) != -1);
+
+ if (visible != currentlyVisible) {
+ changed = true;
+ }
+
+ visibility[i] = visible;
+ }
+
+ if (!changed) {
+ return;
+ }
+
+ // remember selection
+ const int sel = ui->tabWidget->currentIndex();
+
+ // remove all tabs
+ ui->tabWidget->clear();
+
+ // add visible tabs
+ for (std::size_t i=0; i<visibility.size(); ++i) {
+ if (visibility[i]) {
+ ui->tabWidget->addTab(m_tabs[i].widget, m_tabs[i].icon, m_tabs[i].caption);
+
+ if (static_cast<int>(i) == sel) {
+ ui->tabWidget->setCurrentIndex(static_cast<int>(i));
+ }
+ }
+ }
+}
+
+void ModInfoDialog::updateTabs()
+{
+ auto* origin = getOrigin();
+
+ for (auto& tabInfo : m_tabs) {
+ tabInfo.tab->setMod(m_mod, origin);
+ tabInfo.tab->clear();
+ tabInfo.tab->update();
+ }
+}
+
+void ModInfoDialog::feedFiles()
+{
+ const auto rootPath = m_mod->absolutePath();
+
+ if (rootPath.length() > 0) {
+ QDirIterator dirIterator(rootPath, QDir::Files, QDirIterator::Subdirectories);
+ while (dirIterator.hasNext()) {
+ QString fileName = dirIterator.next();
+
+ for (auto& tabInfo : m_tabs) {
+ if (tabInfo.tab->feedFile(rootPath, fileName)) {
+ break;
+ }
+ }
+ }
+ }
+}
+
+void ModInfoDialog::setTabsColors()
+{
+ for (const auto& tabInfo : m_tabs) {
+ const auto c = tabInfo.tab->hasData() ?
+ QColor::Invalid :
+ ui->tabWidget->palette().color(QPalette::Disabled, QPalette::WindowText);
+
+ ui->tabWidget->tabBar()->setTabTextColor(tabInfo.realPos, c);
+ }
+}
+
+void ModInfoDialog::switchToTab(std::size_t index)
+{
+ if (index >= m_tabs.size()) {
+ qCritical() << "tab index " << index << "out of range";
+ return;
+ }
+
+ if (ui->tabWidget->indexOf(m_tabs[index].widget) == -1) {
+ qCritical() << "can't switch to tab " << index << ", not available";
+ return;
+ }
+
+ ui->tabWidget->setCurrentIndex(m_tabs[index].realPos);
+}
+
+MOShared::FilesOrigin* ModInfoDialog::getOrigin()
+{
+ MOShared::FilesOrigin* origin = nullptr;
+
+ auto* ds = m_core->directoryStructure();
+ if (ds->originExists(ToWString(m_mod->name()))) {
+ auto* origin = &ds->getOriginByName(ToWString(m_mod->name()));
+ if (!origin->isDisabled()) {
+ return origin;
+ }
+ }
+
+ return nullptr;
+}
+
void ModInfoDialog::saveState(Settings& s) const
{
- s.directInterface().setValue("mod_info_tabs", saveTabState());
+ //s.directInterface().setValue("mod_info_tabs", saveTabState());
- for (const auto& tab : m_tabs) {
- tab->saveState(s);
+ for (const auto& tabInfo : m_tabs) {
+ tabInfo.tab->saveState(s);
}
}
void ModInfoDialog::restoreState(const Settings& s)
{
- restoreTabState(s.directInterface().value("mod_info_tabs").toByteArray());
+ //restoreTabState(s.directInterface().value("mod_info_tabs").toByteArray());
- for (const auto& tab : m_tabs) {
- tab->restoreState(s);
+ for (const auto& tabInfo : m_tabs) {
+ tabInfo.tab->restoreState(s);
}
}
+QByteArray ModInfoDialog::saveTabState() const
+{
+ QByteArray result;
+ /*QDataStream stream(&result, QIODevice::WriteOnly);
+ stream << ui->tabWidget->count();
+ for (int i = 0; i < ui->tabWidget->count(); ++i) {
+ stream << ui->tabWidget->widget(i)->objectName();
+ }*/
+
+ return result;
+}
+
void ModInfoDialog::restoreTabState(const QByteArray &state)
{
- QDataStream stream(state);
+ /*QDataStream stream(state);
int count = 0;
stream >> count;
@@ -232,9 +371,9 @@ void ModInfoDialog::restoreTabState(const QByteArray &state)
tabIds.append(tabId);
int oldPos = tabIndex(tabId);
if (oldPos != -1) {
- m_RealTabPos[newPos] = oldPos;
+ m_realTabPos[newPos] = oldPos;
} else {
- m_RealTabPos[newPos] = newPos;
+ m_realTabPos[newPos] = newPos;
}
}
@@ -246,19 +385,7 @@ void ModInfoDialog::restoreTabState(const QByteArray &state)
int oldPos = tabIndex(tabId);
tabBar->moveTab(oldPos, newPos);
}
- ui->tabWidget->blockSignals(false);
-}
-
-QByteArray ModInfoDialog::saveTabState() const
-{
- QByteArray result;
- QDataStream stream(&result, QIODevice::WriteOnly);
- stream << ui->tabWidget->count();
- for (int i = 0; i < ui->tabWidget->count(); ++i) {
- stream << ui->tabWidget->widget(i)->objectName();
- }
-
- return result;
+ ui->tabWidget->blockSignals(false);*/
}
int ModInfoDialog::tabIndex(const QString& tabId)
@@ -273,37 +400,17 @@ int ModInfoDialog::tabIndex(const QString& tabId)
void ModInfoDialog::onDeleteShortcut()
{
- for (auto& t : m_tabs) {
- if (t->deleteRequested()) {
+ for (auto& tabInfo : m_tabs) {
+ if (tabInfo.tab->deleteRequested()) {
break;
}
}
}
-void ModInfoDialog::refreshLists()
-{
- for (auto& tab : m_tabs) {
- tab->update();
- }
-
- if (m_RootPath.length() > 0) {
- QDirIterator dirIterator(m_RootPath, QDir::Files, QDirIterator::Subdirectories);
- while (dirIterator.hasNext()) {
- QString fileName = dirIterator.next();
-
- for (auto& tab : m_tabs) {
- if (tab->feedFile(m_RootPath, fileName)) {
- break;
- }
- }
- }
- }
-}
-
void ModInfoDialog::on_closeButton_clicked()
{
- for (auto& tab : m_tabs) {
- if (!tab->canClose()) {
+ for (auto& tabInfo : m_tabs) {
+ if (!tabInfo.tab->canClose()) {
return;
}
}
@@ -311,31 +418,28 @@ void ModInfoDialog::on_closeButton_clicked()
close();
}
-void ModInfoDialog::openTab(int tab)
-{
- if (ui->tabWidget->isTabEnabled(tab)) {
- ui->tabWidget->setCurrentIndex(tab);
- }
-}
-
void ModInfoDialog::on_tabWidget_currentChanged(int index)
{
}
void ModInfoDialog::on_nextButton_clicked()
{
- int currentTab = ui->tabWidget->currentIndex();
- int tab = m_RealTabPos[currentTab];
+ auto mod = m_mainWindow->nextModInList();
+ if (mod == m_mod) {
+ return;
+ }
- emit modOpenNext(tab);
- this->accept();
+ setMod(mod);
+ update();
}
void ModInfoDialog::on_prevButton_clicked()
{
- int currentTab = ui->tabWidget->currentIndex();
- int tab = m_RealTabPos[currentTab];
+ auto mod = m_mainWindow->previousModInList();
+ if (mod == m_mod) {
+ return;
+ }
- emit modOpenPrev(tab);
- this->accept();
+ setMod(mod);
+ update();
}
diff --git a/src/modinfodialog.h b/src/modinfodialog.h
index 020e7958..1cefc71a 100644
--- a/src/modinfodialog.h
+++ b/src/modinfodialog.h
@@ -32,7 +32,7 @@ class PluginContainer;
class OrganizerCore;
class Settings;
class ModInfoDialogTab;
-
+class MainWindow;
bool canPreviewFile(PluginContainer& pluginContainer, bool isArchive, const QString& filename);
bool canOpenFile(bool isArchive, const QString& filename);
@@ -71,10 +71,7 @@ public:
* @param modInfo info structure about the mod to display
* @param parent parend widget
**/
- explicit ModInfoDialog(
- ModInfo::Ptr modInfo,
- bool unmanaged, OrganizerCore *organizerCore, PluginContainer *pluginContainer,
- QWidget *parent = 0);
+ ModInfoDialog(MainWindow* mw, OrganizerCore* core, PluginContainer* plugin);
~ModInfoDialog();
@@ -92,12 +89,9 @@ public:
**/
const int getModID() const;
- /**
- * @brief open the specified tab in the dialog if it's enabled
- *
- * @param tab the tab to activate
- **/
- void openTab(int tab);
+ void setMod(ModInfo::Ptr mod);
+ void setMod(const QString& name);
+ void setTab(int index);
int exec() override;
@@ -105,9 +99,6 @@ public:
void restoreState(const Settings& s);
signals:
- void modOpen(const QString &modName, int tab);
- void modOpenNext(int tab=-1);
- void modOpenPrev(int tab=-1);
void originModified(int originID);
private slots:
@@ -117,27 +108,42 @@ private slots:
void on_prevButton_clicked();
private:
- Ui::ModInfoDialog *ui;
- ModInfo::Ptr m_ModInfo;
- std::vector<std::unique_ptr<ModInfoDialogTab>> m_tabs;
- QString m_RootPath;
- OrganizerCore *m_OrganizerCore;
- PluginContainer *m_PluginContainer;
- MOShared::FilesOrigin *m_Origin;
- std::map<int, int> m_RealTabPos;
+ struct TabInfo
+ {
+ std::unique_ptr<ModInfoDialogTab> tab;
+ int realPos;
+ QWidget* widget;
+ QString caption;
+ QIcon icon;
+
+ TabInfo(std::unique_ptr<ModInfoDialogTab> tab);
+ };
+
+ std::unique_ptr<Ui::ModInfoDialog> ui;
+ MainWindow* m_mainWindow;
+ ModInfo::Ptr m_mod;
+ OrganizerCore* m_core;
+ PluginContainer* m_plugin;
+ std::vector<TabInfo> m_tabs;
+ int m_initialTab;
- std::vector<std::unique_ptr<ModInfoDialogTab>> createTabs();
- void refreshLists();
+ std::vector<TabInfo> createTabs();
void restoreTabState(const QByteArray &state);
QByteArray saveTabState() const;
+ void update();
void onDeleteShortcut();
int tabIndex(const QString &tabId);
+ MOShared::FilesOrigin* getOrigin();
+ void setTabsVisibility();
+ void updateTabs();
+ void feedFiles();
+ void setTabsColors();
+ void switchToTab(std::size_t index);
template <class T>
std::unique_ptr<ModInfoDialogTab> createTab(int index)
{
- return std::make_unique<T>(
- *m_OrganizerCore, *m_PluginContainer, this, ui, index);
+ return std::make_unique<T>(*m_core, *m_plugin, this, ui.get(), index);
}
};
diff --git a/src/modinfodialogcategories.cpp b/src/modinfodialogcategories.cpp
index 321c22b8..bce1162b 100644
--- a/src/modinfodialogcategories.cpp
+++ b/src/modinfodialogcategories.cpp
@@ -22,6 +22,7 @@ void CategoriesTab::clear()
{
ui->categories->clear();
ui->primaryCategories->clear();
+ setHasData(false);
}
void CategoriesTab::update()
@@ -33,6 +34,7 @@ void CategoriesTab::update()
ui->categories->invisibleRootItem(), 0);
updatePrimary();
+ setHasData(ui->primaryCategories->count() > 0);
}
bool CategoriesTab::canHandleSeparators() const
diff --git a/src/modinfodialogconflicts.cpp b/src/modinfodialogconflicts.cpp
index 15bb7ed4..dde00354 100644
--- a/src/modinfodialogconflicts.cpp
+++ b/src/modinfodialogconflicts.cpp
@@ -148,7 +148,7 @@ ConflictsTab::ConflictsTab(
void ConflictsTab::update()
{
- m_general.update();
+ setHasData(m_general.update());
m_advanced.update();
}
@@ -156,6 +156,7 @@ void ConflictsTab::clear()
{
m_general.clear();
m_advanced.clear();
+ setHasData(false);
}
void ConflictsTab::saveState(Settings& s)
@@ -572,7 +573,7 @@ void GeneralConflictsTab::restoreState(const Settings& s)
.value("mod_info_conflicts_general_overwritten").toByteArray());
}
-void GeneralConflictsTab::update()
+bool GeneralConflictsTab::update()
{
clear();
@@ -616,6 +617,8 @@ void GeneralConflictsTab::update()
ui->overwriteCount->display(numOverwrite);
ui->overwrittenCount->display(numOverwritten);
ui->noConflictCount->display(numNonConflicting);
+
+ return (numOverwrite > 0 || numOverwritten > 0);
}
QTreeWidgetItem* GeneralConflictsTab::createOverwriteItem(
diff --git a/src/modinfodialogconflicts.h b/src/modinfodialogconflicts.h
index a05682ba..38fa6a74 100644
--- a/src/modinfodialogconflicts.h
+++ b/src/modinfodialogconflicts.h
@@ -22,7 +22,7 @@ public:
void saveState(Settings& s);
void restoreState(const Settings& s);
- void update();
+ bool update();
signals:
void modOpen(QString name);
@@ -100,7 +100,6 @@ public:
QWidget* parent, Ui::ModInfoDialog* ui, int index);
void update() override;
-
void clear() override;
void saveState(Settings& s) override;
void restoreState(const Settings& s) override;
diff --git a/src/modinfodialogesps.cpp b/src/modinfodialogesps.cpp
index dd4fff0b..d0dcaf2b 100644
--- a/src/modinfodialogesps.cpp
+++ b/src/modinfodialogesps.cpp
@@ -138,6 +138,7 @@ void ESPsTab::clear()
{
ui->inactiveESPList->clear();
ui->activeESPList->clear();
+ setHasData(false);
}
bool ESPsTab::feedFile(const QString& rootPath, const QString& fullPath)
@@ -158,6 +159,7 @@ bool ESPsTab::feedFile(const QString& rootPath, const QString& fullPath)
ui->inactiveESPList->addItem(item);
}
+ setHasData(true);
return true;
}
}
diff --git a/src/modinfodialogfiletree.cpp b/src/modinfodialogfiletree.cpp
index 3e233ccc..dae37f25 100644
--- a/src/modinfodialogfiletree.cpp
+++ b/src/modinfodialogfiletree.cpp
@@ -49,7 +49,9 @@ FileTreeTab::FileTreeTab(
void FileTreeTab::clear()
{
m_fs->setRootPath({});
- //ui->filetree->
+
+ // always has data; even if the mod is empty, it still has a meta.ini
+ setHasData(true);
}
void FileTreeTab::update()
diff --git a/src/modinfodialogimages.cpp b/src/modinfodialogimages.cpp
index 332a0984..9a60fc8e 100644
--- a/src/modinfodialogimages.cpp
+++ b/src/modinfodialogimages.cpp
@@ -105,6 +105,7 @@ void ImagesTab::clear()
}
static_cast<QVBoxLayout*>(ui->imagesThumbnails->layout())->addStretch(1);
+ setHasData(false);
}
bool ImagesTab::feedFile(const QString& rootPath, const QString& fullPath)
@@ -115,7 +116,10 @@ bool ImagesTab::feedFile(const QString& rootPath, const QString& fullPath)
for (const auto* e : extensions) {
if (fullPath.endsWith(e, Qt::CaseInsensitive)) {
- add(fullPath);
+ if (add(fullPath)) {
+ setHasData(true);
+ }
+
return true;
}
}
@@ -123,13 +127,13 @@ bool ImagesTab::feedFile(const QString& rootPath, const QString& fullPath)
return false;
}
-void ImagesTab::add(const QString& fullPath)
+bool ImagesTab::add(const QString& fullPath)
{
QImage image = QImage(fullPath);
if (image.isNull()) {
qWarning() << "ImagesTab: '" << fullPath << "' is not a valid image";
- return;
+ return false;
}
auto* thumbnail = new ScalableImage(std::move(image));
@@ -140,6 +144,8 @@ void ImagesTab::add(const QString& fullPath)
static_cast<QVBoxLayout*>(ui->imagesThumbnails->layout())->insertWidget(
ui->imagesThumbnails->layout()->count() - 1, thumbnail);
+
+ return true;
}
void ImagesTab::onClicked(const QImage& original)
diff --git a/src/modinfodialogimages.h b/src/modinfodialogimages.h
index 689b8e93..60271da0 100644
--- a/src/modinfodialogimages.h
+++ b/src/modinfodialogimages.h
@@ -44,7 +44,7 @@ public:
private:
ScalableImage* m_image;
- void add(const QString& fullPath);
+ bool add(const QString& fullPath);
void onClicked(const QImage& image);
};
diff --git a/src/modinfodialognexus.cpp b/src/modinfodialognexus.cpp
index 9d51871c..61b868d1 100644
--- a/src/modinfodialognexus.cpp
+++ b/src/modinfodialognexus.cpp
@@ -48,6 +48,7 @@ void NexusTab::clear()
ui->version->clear();
ui->browser->setPage(new NexusTabWebpage(ui->browser));
ui->url->clear();
+ setHasData(false);
}
void NexusTab::update()
@@ -88,6 +89,7 @@ void NexusTab::update()
(mod()->endorsedState() == ModInfo::ENDORSED_NEVER));
updateWebpage();
+ setHasData(mod()->getNexusID() >= 0);
}
void NexusTab::setMod(ModInfo::Ptr mod, MOShared::FilesOrigin* origin)
diff --git a/src/modinfodialogtab.cpp b/src/modinfodialogtab.cpp
index 1b7fadbb..e50aec29 100644
--- a/src/modinfodialogtab.cpp
+++ b/src/modinfodialogtab.cpp
@@ -7,7 +7,7 @@ ModInfoDialogTab::ModInfoDialogTab(
OrganizerCore& oc, PluginContainer& plugin,
QWidget* parent, Ui::ModInfoDialog* ui, int index) :
ui(ui), m_core(oc), m_plugin(plugin), m_parent(parent),
- m_origin(nullptr), m_tabIndex(index)
+ m_origin(nullptr), m_tabIndex(index), m_hasData(false)
{
}
@@ -74,6 +74,11 @@ int ModInfoDialogTab::tabIndex() const
return m_tabIndex;
}
+bool ModInfoDialogTab::hasData() const
+{
+ return m_hasData;
+}
+
OrganizerCore& ModInfoDialogTab::core()
{
return m_core;
@@ -101,6 +106,11 @@ void ModInfoDialogTab::emitModOpen(QString name)
emit modOpen(name);
}
+void ModInfoDialogTab::setHasData(bool b)
+{
+ m_hasData = b;
+}
+
NotesTab::NotesTab(
OrganizerCore& oc, PluginContainer& plugin,
@@ -115,12 +125,18 @@ void NotesTab::clear()
{
ui->commentsEdit->clear();
ui->notesEdit->clear();
+ setHasData(false);
}
void NotesTab::update()
{
- ui->commentsEdit->setText(mod()->comments());
- ui->notesEdit->setText(mod()->notes());
+ const auto comments = mod()->comments();
+ const auto notes = mod()->notes();
+
+ ui->commentsEdit->setText(comments);
+ ui->notesEdit->setText(notes);
+
+ setHasData(!comments.isEmpty() || !notes.isEmpty());
}
bool NotesTab::canHandleSeparators() const
diff --git a/src/modinfodialogtab.h b/src/modinfodialogtab.h
index 1f99344f..8fe7d2d4 100644
--- a/src/modinfodialogtab.h
+++ b/src/modinfodialogtab.h
@@ -38,6 +38,7 @@ public:
MOShared::FilesOrigin* origin() const;
int tabIndex() const;
+ bool hasData() const;
signals:
void originModified(int originID);
@@ -57,6 +58,7 @@ protected:
void emitOriginModified();
void emitModOpen(QString name);
+ void setHasData(bool b);
private:
OrganizerCore& m_core;
@@ -65,6 +67,7 @@ private:
ModInfo::Ptr m_mod;
MOShared::FilesOrigin* m_origin;
int m_tabIndex;
+ bool m_hasData;
};
diff --git a/src/modinfodialogtextfiles.cpp b/src/modinfodialogtextfiles.cpp
index fddfafba..bd175c24 100644
--- a/src/modinfodialogtextfiles.cpp
+++ b/src/modinfodialogtextfiles.cpp
@@ -42,6 +42,7 @@ void GenericFilesTab::clear()
{
m_list->clear();
select(nullptr);
+ setHasData(false);
}
bool GenericFilesTab::canClose()
@@ -76,6 +77,7 @@ bool GenericFilesTab::feedFile(const QString& rootPath, const QString& fullPath)
for (const auto* e : extensions) {
if (wantsFile(rootPath, fullPath)) {
m_list->addItem(new FileListItem(rootPath, fullPath));
+ setHasData(true);
return true;
}
}