Compare commits

..
Author SHA1 Message Date
Tannin dce78b62b8 - bugfix: when installing mods through the nmm importer if no other mods were previously installed
the correct installation directory was never set
- bugfix: the nmm importer didn't "sanitize" mod names and potentially tried to create invalid directories
- bugfix: 0.99.x packages didn't contain qt plugins to handle certain image formats
2013-09-12 21:45:57 +02:00
Tannin af6e1c3ab4 - when installing mods from outside the download directory the absolute path is now stored
- added a context menu to the toolbar buttons so tool icons can be removed directly
- initweaks modinfo tab is now always available and allows new ini tweaks to be created
- fake esms are now treated as masters (as they should)
- MO will now display a warning if not all masters of an esp are enabled. The tooltip gives a list of required masters
- bugfix: path returned by getfullpathname was sometimes not correctly terminated
- bugfix: path after reverse-rerouting was sometimes incorrect, missing a path separator
- bugfix: change of current directory sometimes used a fake directory without need
- bugfix: icons in shortcut menu were not alwayscorrectly updated
2013-09-11 22:54:45 +02:00
Tannin 50325c8fc2 Added tag release v0.99.6 for changeset d9dedb857683 2013-09-05 21:14:19 +02:00
17 changed files with 222 additions and 127 deletions
+2 -1
View File
@@ -13,7 +13,8 @@ SUBDIRS = bsatk \
proxydll \
nxmhandler \
BossDummy \
pythonRunner
pythonRunner \
esptk
hookdll.depends = shared
organizer.depends = shared, uibase, plugins
+1 -1
View File
@@ -150,7 +150,7 @@ void DownloadListWidgetDelegate::paint(QPainter *painter, const QStyleOptionView
}
m_InstallLabel->setPalette(labelPalette);
if (m_Manager->isInfoIncomplete(downloadIndex)) {
m_NameLabel->setText("<img src=\":/MO/gui/resources/dialog-warning_16.png\" /> " + m_NameLabel->text());
m_NameLabel->setText("<img src=\":/MO/gui/warning_16\" /> " + m_NameLabel->text());
}
} else {
m_InstallLabel->setVisible(false);
+1 -1
View File
@@ -137,7 +137,7 @@ void DownloadListWidgetCompactDelegate::paint(QPainter *painter, const QStyleOpt
m_DoneLabel->setForegroundRole(QPalette::WindowText);
}
if (m_Manager->isInfoIncomplete(downloadIndex)) {
m_NameLabel->setText("<img src=\":/MO/gui/resources/dialog-warning_16.png\"/> " + m_NameLabel->text());
m_NameLabel->setText("<img src=\":/MO/gui/warning_16\"/> " + m_NameLabel->text());
}
} else {
m_DoneLabel->setVisible(false);
+6 -3
View File
@@ -431,7 +431,7 @@ QString InstallationManager::generateBackupName(const QString &directoryName) co
bool InstallationManager::testOverwrite(GuessedValue<QString> &modName) const
{
QString targetDirectory = QDir::fromNativeSeparators(m_ModsDirectory.mid(0).append("\\").append(modName));
QString targetDirectory = QDir::fromNativeSeparators(m_ModsDirectory + "\\" + modName);
while (QDir(targetDirectory).exists()) {
QueryOverwriteDialog overwriteDialog(m_ParentWidget);
@@ -664,8 +664,11 @@ bool InstallationManager::install(const QString &fileName, GuessedValue<QString>
modName.update(guessedModName, GUESS_GOOD);
}
qDebug("using mod name \"%s\" (id %d)", modName->toUtf8().constData(), modID);
m_CurrentFile = fileInfo.fileName();
m_CurrentFile = fileInfo.absoluteFilePath();
if (fileInfo.dir() == QDir(ToQString(GameInfo::instance().getDownloadDir()))) {
m_CurrentFile = fileInfo.fileName();
}
qDebug("using mod name \"%s\" (id %d) -> %s", modName->toUtf8().constData(), modID, qPrintable(m_CurrentFile));
// open the archive and construct the directory tree the installers work on
bool archiveOpen = m_CurrentArchive->open(ToWString(QDir::toNativeSeparators(fileName)).c_str(),
+5
View File
@@ -57,6 +57,11 @@ public:
~InstallationManager();
/**
* @brief update the directory where mods are to be installed
* @param modsDirectory the mod directory
* @note this is called a lot, probably redundantly
*/
void setModsDirectory(const QString &modsDirectory) { m_ModsDirectory = modsDirectory; }
/**
+52 -17
View File
@@ -144,7 +144,7 @@ MainWindow::MainWindow(const QString &exeName, QSettings &initSettings, QWidget
m_InstallationManager(this), m_Translator(NULL), m_TranslatorQt(NULL),
m_Updater(NexusInterface::instance(), this), m_CategoryFactory(CategoryFactory::instance()),
m_CurrentProfile(NULL), m_AskForNexusPW(false), m_LoginAttempted(false),
m_ArchivesInit(false), m_ContextItem(NULL), m_CurrentSaveView(NULL),
m_ArchivesInit(false), m_ContextItem(NULL), m_ContextAction(NULL), m_CurrentSaveView(NULL),
m_GameInfo(new GameInfoImpl())
{
ui->setupUi(this);
@@ -213,6 +213,8 @@ MainWindow::MainWindow(const QString &exeName, QSettings &initSettings, QWidget
NexusInterface::instance()->setCacheDirectory(m_Settings.getCacheDirectory());
NexusInterface::instance()->setNMMVersion(m_Settings.getNMMVersion());
m_InstallationManager.setModsDirectory(m_Settings.getModDirectory());
updateDownloadListDelegate();
ui->savegameList->installEventFilter(this);
@@ -261,6 +263,8 @@ MainWindow::MainWindow(const QString &exeName, QSettings &initSettings, QWidget
connect(&TutorialManager::instance(), SIGNAL(windowTutorialFinished(QString)), this, SLOT(windowTutorialFinished(QString)));
connect(ui->toolBar, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(toolBar_customContextMenuRequested(QPoint)));
connect(this, SIGNAL(styleChanged(QString)), this, SLOT(updateStyle(QString)));
m_CheckBSATimer.setSingleShot(true);
@@ -1122,6 +1126,8 @@ IModInterface *MainWindow::createMod(GuessedValue<QString> &name)
return NULL;
}
m_InstallationManager.setModsDirectory(m_Settings.getModDirectory());
/* QString fixedName = name;
fixDirectoryName(fixedName);
unsigned int index = ModInfo::getIndex(fixedName);
@@ -1325,17 +1331,6 @@ void MainWindow::setExecutableIndex(int index)
executableBox->setCurrentIndex(1);
}
const Executable &selectedExecutable = executableBox->itemData(executableBox->currentIndex()).value<Executable>();
QIcon addIcon(":/MO/gui/link");
QIcon removeIcon(":/MO/gui/remove");
QFileInfo linkDesktopFile(QDir::fromNativeSeparators(getDesktopDirectory()) + "/" + selectedExecutable.m_Title + ".lnk");
QFileInfo linkMenuFile(QDir::fromNativeSeparators(getStartMenuDirectory()) + "/" + selectedExecutable.m_Title + ".lnk");
ui->linkButton->menu()->actions().at(0)->setIcon(selectedExecutable.m_Toolbar ? removeIcon : addIcon);
ui->linkButton->menu()->actions().at(1)->setIcon(linkDesktopFile.exists() ? removeIcon : addIcon);
ui->linkButton->menu()->actions().at(2)->setIcon(linkMenuFile.exists() ? removeIcon : addIcon);
}
@@ -1768,14 +1763,14 @@ void MainWindow::checkBSAList()
if (item->checkState(0) == Qt::Unchecked) {
if (m_DefaultArchives.contains(filename)) {
item->setIcon(0, QIcon(":/MO/gui/resources/dialog-warning.png"));
item->setIcon(0, QIcon(":/MO/gui/warning"));
item->setToolTip(0, tr("This bsa is enabled in the ini file so it may be required!"));
modWarning = true;
} else {
QString espName = filename.mid(0, filename.length() - 3).append("esp").toLower();
QString esmName = filename.mid(0, filename.length() - 3).append("esm").toLower();
if (m_PluginList.isEnabled(espName) || m_PluginList.isEnabled(esmName)) {
item->setIcon(0, QIcon(":/MO/gui/resources/dialog-warning.png"));
item->setIcon(0, QIcon(":/MO/gui/warning"));
item->setToolTip(0, tr("This archive will still be loaded since there is a plugin of the same name but "
"its files will not follow installation order!"));
modWarning = true;
@@ -1790,7 +1785,7 @@ void MainWindow::checkBSAList()
}
if (warning) {
ui->tabWidget->setTabIcon(1, QIcon(":/MO/gui/resources/dialog-warning.png"));
ui->tabWidget->setTabIcon(1, QIcon(":/MO/gui/warning"));
} else {
ui->tabWidget->setTabIcon(1, QIcon());
}
@@ -2735,8 +2730,13 @@ void MainWindow::reinstallMod_clicked()
QString installationFile = modInfo->getInstallationFile();
if (installationFile.length() != 0) {
QString fullInstallationFile;
if (QFileInfo(installationFile).isAbsolute()) {
fullInstallationFile = installationFile;
QFileInfo fileInfo(installationFile);
if (fileInfo.isAbsolute()) {
if (fileInfo.exists()) {
fullInstallationFile = installationFile;
} else {
fullInstallationFile = m_DownloadManager.getOutputDirectory().append("/").append(fileInfo.fileName());
}
} else {
fullInstallationFile = m_DownloadManager.getOutputDirectory().append("/").append(installationFile);
}
@@ -3625,6 +3625,7 @@ void MainWindow::on_actionSettings_triggered()
QString oldCacheDirectory(m_Settings.getCacheDirectory());
bool proxy = m_Settings.useProxy();
m_Settings.query(this);
m_InstallationManager.setModsDirectory(m_Settings.getModDirectory());
fixCategories();
refreshFilters();
if (QDir::fromNativeSeparators(m_DownloadManager.getOutputDirectory()) != QDir::fromNativeSeparators(m_Settings.getDownloadDirectory())) {
@@ -4494,6 +4495,25 @@ void MainWindow::unlockESPIndex()
}
void MainWindow::removeFromToolbar()
{
Executable &exe = m_ExecutablesList.find(m_ContextAction->text());
exe.m_Toolbar = false;
updateToolBar();
}
void MainWindow::toolBar_customContextMenuRequested(const QPoint &point)
{
QAction *action = ui->toolBar->actionAt(point);
if (action->objectName().startsWith("custom_")) {
m_ContextAction = action;
QMenu menu;
menu.addAction(tr("Remove"), this, SLOT(removeFromToolbar()));
menu.exec(ui->toolBar->mapToGlobal(point));
}
}
void MainWindow::on_espList_customContextMenuRequested(const QPoint &pos)
{
m_ContextRow = m_PluginListSortProxy->mapToSource(ui->espList->indexAt(pos)).row();
@@ -4565,3 +4585,18 @@ void MainWindow::on_groupCombo_currentIndexChanged(int index)
m_ModListSortProxy->setSourceModel(&m_ModList);
}
}
void MainWindow::on_linkButton_pressed()
{
const Executable &selectedExecutable = ui->executablesListBox->itemData(ui->executablesListBox->currentIndex()).value<Executable>();
QIcon addIcon(":/MO/gui/link");
QIcon removeIcon(":/MO/gui/remove");
QFileInfo linkDesktopFile(QDir::fromNativeSeparators(getDesktopDirectory()) + "/" + selectedExecutable.m_Title + ".lnk");
QFileInfo linkMenuFile(QDir::fromNativeSeparators(getStartMenuDirectory()) + "/" + selectedExecutable.m_Title + ".lnk");
ui->linkButton->menu()->actions().at(0)->setIcon(selectedExecutable.m_Toolbar ? removeIcon : addIcon);
ui->linkButton->menu()->actions().at(1)->setIcon(linkDesktopFile.exists() ? removeIcon : addIcon);
ui->linkButton->menu()->actions().at(2)->setIcon(linkMenuFile.exists() ? removeIcon : addIcon);
}
+6
View File
@@ -276,6 +276,8 @@ private:
int m_ContextRow;
QTreeWidgetItem *m_ContextItem;
QAction *m_ContextAction;
int m_SelectedSaveGame;
Settings m_Settings;
@@ -454,6 +456,9 @@ private slots:
void downloadSpeed(const QString &serverName, int bytesPerSecond);
void toolBar_customContextMenuRequested(const QPoint &point);
void removeFromToolbar();
private slots: // ui slots
// actions
void on_actionAdd_Profile_triggered();
@@ -485,6 +490,7 @@ private slots: // ui slots
void on_displayCategoriesBtn_toggled(bool checked);
void on_groupCombo_currentIndexChanged(int index);
void on_categoriesList_itemSelectionChanged();
void on_linkButton_pressed();
};
#endif // MAINWINDOW_H
+7 -52
View File
@@ -31,16 +31,7 @@
<property name="spacing">
<number>4</number>
</property>
<property name="leftMargin">
<number>6</number>
</property>
<property name="topMargin">
<number>6</number>
</property>
<property name="rightMargin">
<number>6</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>6</number>
</property>
<item>
@@ -730,16 +721,7 @@ p, li { white-space: pre-wrap; }
<string notr="true">Archives</string>
</attribute>
<layout class="QVBoxLayout" name="verticalLayout_9">
<property name="leftMargin">
<number>6</number>
</property>
<property name="topMargin">
<number>6</number>
</property>
<property name="rightMargin">
<number>6</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>6</number>
</property>
<item>
@@ -818,16 +800,7 @@ BSAs checked here are loaded in such a way that your installation order is obeye
<string>Data</string>
</attribute>
<layout class="QVBoxLayout" name="verticalLayout_5">
<property name="leftMargin">
<number>6</number>
</property>
<property name="topMargin">
<number>6</number>
</property>
<property name="rightMargin">
<number>6</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>6</number>
</property>
<item>
@@ -897,16 +870,7 @@ BSAs checked here are loaded in such a way that your installation order is obeye
<string>Saves</string>
</attribute>
<layout class="QVBoxLayout" name="verticalLayout_3">
<property name="leftMargin">
<number>6</number>
</property>
<property name="topMargin">
<number>6</number>
</property>
<property name="rightMargin">
<number>6</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>6</number>
</property>
<item>
@@ -935,16 +899,7 @@ p, li { white-space: pre-wrap; }
<string>Downloads</string>
</attribute>
<layout class="QVBoxLayout" name="verticalLayout_7">
<property name="leftMargin">
<number>2</number>
</property>
<property name="topMargin">
<number>2</number>
</property>
<property name="rightMargin">
<number>2</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>2</number>
</property>
<item>
@@ -1045,7 +1000,7 @@ p, li { white-space: pre-wrap; }
<bool>true</bool>
</property>
<property name="contextMenuPolicy">
<enum>Qt::PreventContextMenu</enum>
<enum>Qt::CustomContextMenu</enum>
</property>
<property name="windowTitle">
<string>Tool Bar</string>
@@ -1210,7 +1165,7 @@ p, li { white-space: pre-wrap; }
</property>
<property name="icon">
<iconset resource="resources.qrc">
<normaloff>:/MO/gui/resources/dialog-warning.png</normaloff>:/MO/gui/resources/dialog-warning.png</iconset>
<normaloff>:/MO/gui/warning</normaloff>:/MO/gui/warning</iconset>
</property>
<property name="text">
<string>No Problems</string>
+31 -5
View File
@@ -38,6 +38,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>.
#include <QFileSystemModel>
#include <Shlwapi.h>
#include <sstream>
#include <QInputDialog>
using QtJson::Json;
@@ -146,7 +147,7 @@ ModInfoDialog::ModInfoDialog(ModInfo::Ptr modInfo, const DirectoryEntry *directo
QTabWidget *tabWidget = findChild<QTabWidget*>("tabWidget");
tabWidget->setTabEnabled(TAB_TEXTFILES, textFileList->count() != 0);
tabWidget->setTabEnabled(TAB_INIFILES, (iniFileList->count() != 0) || (iniTweaksList->count() != 0));
//tabWidget->setTabEnabled(TAB_INIFILES, (iniFileList->count() != 0) || (iniTweaksList->count() != 0));
tabWidget->setTabEnabled(TAB_IMAGES, thumbnailArea->count() != 0);
tabWidget->setTabEnabled(TAB_ESPS, (inactiveESPList->count() != 0) || (activeESPList->count() != 0));
tabWidget->setTabEnabled(TAB_CONFLICTS, m_Origin != NULL);
@@ -409,8 +410,6 @@ void ModInfoDialog::openTextFile(const QString &fileName)
void ModInfoDialog::openIniFile(const QString &fileName)
{
QPushButton* saveButton = findChild<QPushButton*>("saveButton");
QFile iniFile(fileName);
iniFile.open(QIODevice::ReadOnly);
QByteArray buffer = iniFile.readAll();
@@ -421,7 +420,7 @@ void ModInfoDialog::openIniFile(const QString &fileName)
iniFileView->setProperty("encoding", codec->name());
iniFile.close();
saveButton->setEnabled(false);
ui->saveButton->setEnabled(false);
}
@@ -515,8 +514,9 @@ void ModInfoDialog::saveCurrentIniFile()
{
QVariant fileNameVar = ui->iniFileView->property("currentFile");
QVariant encodingVar = ui->iniFileView->property("encoding");
if (fileNameVar.isValid()) {
if (fileNameVar.isValid() && !fileNameVar.toString().isEmpty()) {
QString fileName = fileNameVar.toString();
QDir().mkpath(QFileInfo(fileName).absolutePath());
QFile txtFile(fileName);
txtFile.open(QIODevice::WriteOnly);
txtFile.resize(0);
@@ -1171,3 +1171,29 @@ void ModInfoDialog::on_prevButton_clicked()
emit modOpenPrev();
this->accept();
}
void ModInfoDialog::createTweak()
{
QString name = QInputDialog::getText(this, tr("Name"), tr("Please enter a name"));
if (!fixDirectoryName(name)) {
QMessageBox::critical(this, tr("Error"), tr("Invalid name. Must be a valid file name"));
return;
} else if (name.isEmpty()) {
return;
} else if (ui->iniTweaksList->findItems(name, Qt::MatchFixedString).count() != 0) {
QMessageBox::critical(this, tr("Error"), tr("A tweak by that name exists"));
return;
}
QListWidgetItem *newTweak = new QListWidgetItem(name);
newTweak->setData(Qt::UserRole, "INI Tweaks/" + name + ".ini");
ui->iniTweaksList->addItem(newTweak);
}
void ModInfoDialog::on_iniTweaksList_customContextMenuRequested(const QPoint &pos)
{
QMenu menu;
menu.addAction(tr("Create Tweak"), this, SLOT(createTweak()));
menu.exec(ui->iniTweaksList->mapToGlobal(pos));
}
+3
View File
@@ -186,6 +186,9 @@ private slots:
void on_prevButton_clicked();
void on_iniTweaksList_customContextMenuRequested(const QPoint &pos);
void createTweak();
private:
Ui::ModInfoDialog *ui;
+4 -10
View File
@@ -106,6 +106,9 @@
<height>16777215</height>
</size>
</property>
<property name="contextMenuPolicy">
<enum>Qt::CustomContextMenu</enum>
</property>
</widget>
</item>
</layout>
@@ -224,16 +227,7 @@ p, li { white-space: pre-wrap; }
<property name="spacing">
<number>0</number>
</property>
<property name="leftMargin">
<number>0</number>
</property>
<property name="topMargin">
<number>0</number>
</property>
<property name="rightMargin">
<number>0</number>
</property>
<property name="bottomMargin">
<property name="margin">
<number>0</number>
</property>
<item>
+9 -3
View File
@@ -77,7 +77,10 @@ SOURCES += \
qtgroupingproxy.cpp \
modlistview.cpp \
problemsdialog.cpp \
serverinfo.cpp
serverinfo.cpp \
../esptk/record.cpp \
../esptk/espfile.cpp \
../esptk/subrecord.cpp
HEADERS += \
transfersavesdialog.h \
@@ -142,7 +145,10 @@ HEADERS += \
qtgroupingproxy.h \
modlistview.h \
problemsdialog.h \
serverinfo.h
serverinfo.h \
../esptk/record.h \
../esptk/espfile.h \
../esptk/subrecord.h
FORMS += \
transfersavesdialog.ui \
@@ -174,7 +180,7 @@ FORMS += \
savetextasdialog.ui \
problemsdialog.ui
INCLUDEPATH += ../shared ../archive ../uibase ../bsatk "$(BOOSTPATH)"
INCLUDEPATH += ../shared ../archive ../uibase ../bsatk ../esptk "$(BOOSTPATH)"
LIBS += -L"$(BOOSTPATH)/stage/lib"
+67 -8
View File
@@ -23,6 +23,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>.
#include <utility.h>
#include "settings.h"
#include <gameinfo.h>
#include <espfile.h>
#include <windows_error.h>
#include <QtDebug>
@@ -140,7 +141,7 @@ void PluginList::refresh(const QString &profileName, const DirectoryEntry &baseD
bool archive = false;
FilesOrigin &origin = baseDirectory.getOriginByID(current->getOrigin(archive));
m_ESPs.push_back(ESPInfo(filename, forceEnabled, current->getFileTime(), ToQString(origin.getName())));
m_ESPs.push_back(ESPInfo(filename, forceEnabled, current->getFileTime(), ToQString(origin.getName()), ToQString(current->getFullPath())));
}
}
@@ -329,6 +330,8 @@ void PluginList::readEnabledFrom(const QString &fileName)
}
file.close();
testMasters();
}
@@ -589,6 +592,31 @@ int PluginList::columnCount(const QModelIndex &) const
}
void PluginList::testMasters()
{
std::set<QString> enabledMasters;
for (auto iter = m_ESPs.begin(); iter != m_ESPs.end(); ++iter) {
if (iter->m_Enabled) {
enabledMasters.insert(iter->m_Name.toLower());
}
}
for (auto iter = m_ESPs.begin(); iter != m_ESPs.end(); ++iter) {
iter->m_MasterUnset = false;
if (iter->m_Enabled) {
for (auto master = iter->m_Masters.begin(); master != iter->m_Masters.end(); ++master) {
if (enabledMasters.find(master->toLower()) == enabledMasters.end()) {
iter->m_MasterUnset = true;
break;
}
}
}
}
emit layoutChanged();
}
QVariant PluginList::data(const QModelIndex &modelIndex, int role) const
{
int index = modelIndex.row();
@@ -613,13 +641,22 @@ QVariant PluginList::data(const QModelIndex &modelIndex, int role) const
} break;
}
} else if ((role == Qt::DecorationRole) && (modelIndex.column() == 0)) {
if (m_LockedOrder.find(m_ESPs[index].m_Name.toLower()) != m_LockedOrder.end()) {
if (m_ESPs[index].m_MasterUnset) {
return QIcon(":/MO/gui/warning");
} else if (m_LockedOrder.find(m_ESPs[index].m_Name.toLower()) != m_LockedOrder.end()) {
return QIcon(":/MO/gui/locked");
} else {
return QVariant();
}
} else if ((role == Qt::CheckStateRole) && (modelIndex.column() == 0)) {
return m_ESPs[index].m_Enabled ? Qt::Checked : Qt::Unchecked;
} else if (role == Qt::FontRole) {
QFont result;
if (m_ESPs[index].m_IsMaster) {
result.setItalic(true);
result.setWeight(QFont::Bold);
}
return result;
} else if (role == Qt::TextAlignmentRole) {
if (modelIndex.column() == 0) {
return QVariant(Qt::AlignLeft | Qt::AlignVCenter);
@@ -630,7 +667,11 @@ QVariant PluginList::data(const QModelIndex &modelIndex, int role) const
if (m_ESPs[index].m_ForceEnabled) {
return tr("This plugin can't be disabled (enforced by the game)");
} else {
return tr("Origin: %1").arg(m_ESPs[index].m_OriginName);
QString text = tr("Origin: %1").arg(m_ESPs[index].m_OriginName);
if (m_ESPs[index].m_MasterUnset) {
text += "\nDepends on the following masters: " + SetJoin(m_ESPs[index].m_Masters, ", ");
}
return text;
}
} else {
return QVariant();
@@ -694,17 +735,16 @@ void PluginList::setPluginPriority(int row, int &newPriority)
{
int newPriorityTemp = newPriority;
QString sourceExtension = m_ESPs[row].m_Name.right(3).toLower();
if (sourceExtension == "esp") {
if (!m_ESPs[row].m_IsMaster) {
// don't allow esps to be moved above esms
while ((newPriorityTemp < static_cast<int>(m_ESPsByPriority.size() - 1)) &&
(m_ESPs[m_ESPsByPriority[newPriorityTemp]].m_Name.right(3).toLower() == "esm")) {
m_ESPs[m_ESPsByPriority[newPriorityTemp]].m_IsMaster) {
++newPriorityTemp;
}
} else {
// don't allow esms to be moved below esps
while ((newPriorityTemp > 0) &&
(m_ESPs[m_ESPsByPriority[newPriorityTemp - 1]].m_Name.right(3).toLower() == "esp")) {
!m_ESPs[m_ESPsByPriority[newPriorityTemp]].m_IsMaster) {
--newPriorityTemp;
}
// also don't allow "regular" esms to be moved above primary plugins
@@ -774,6 +814,8 @@ void PluginList::changePluginPriority(std::vector<int> rows, int newPriority)
void PluginList::startSaveTime()
{
testMasters();
if (!m_SaveTimer.isActive()) {
m_SaveTimer.start(2000);
}
@@ -814,7 +856,6 @@ bool PluginList::dropMimeData(const QMimeData *mimeData, Qt::DropAction action,
}
changePluginPriority(sourceRows, newPriority);
return false;
}
@@ -883,3 +924,21 @@ bool PluginList::eventFilter(QObject *obj, QEvent *event)
}
return QObject::eventFilter(obj, event);
}
PluginList::ESPInfo::ESPInfo(const QString &name, bool enabled, FILETIME time, const QString &originName, const QString &fullPath)
: m_Name(name), m_Enabled(enabled), m_ForceEnabled(enabled), m_Removed(false), m_Priority(0),
m_LoadOrder(-1), m_Time(time), m_OriginName(originName)
{
try {
ESP::File file(ToWString(fullPath));
m_IsMaster = file.isMaster();
std::set<std::string> masters = file.masters();
for (auto iter = masters.begin(); iter != masters.end(); ++iter) {
m_Masters.insert(QString(iter->c_str()));
}
} catch (const std::exception &e) {
reportError(tr("failed to parse esp file %1: %2").arg(fullPath).arg(e.what()));
m_IsMaster = false;
}
}
+24 -22
View File
@@ -169,6 +169,29 @@ signals:
*/
void saveTimer();
private:
struct ESPInfo {
ESPInfo(const QString &name, bool enabled, FILETIME time, const QString &originName, const QString &fullPath);
QString m_Name;
QString m_FullPath;
bool m_Enabled;
bool m_ForceEnabled;
bool m_Removed;
int m_Priority;
int m_LoadOrder;
FILETIME m_Time;
QString m_OriginName;
bool m_IsMaster;
std::set<QString> m_Masters;
mutable bool m_MasterUnset;
};
friend bool ByName(const ESPInfo& LHS, const ESPInfo& RHS);
friend bool ByDate(const ESPInfo& LHS, const ESPInfo& RHS);
friend bool ByPriority(const ESPInfo& LHS, const ESPInfo& RHS);
private:
void syncLoadOrder();
@@ -184,28 +207,7 @@ private:
void startSaveTime();
private:
struct ESPInfo {
ESPInfo(const QString &name, bool enabled, FILETIME time, const QString &originName)
: m_Name(name), m_Enabled(enabled), m_ForceEnabled(enabled), m_Removed(false), m_Priority(0),
m_LoadOrder(-1), m_Time(time), m_OriginName(originName),
m_IsMaster(name.endsWith("esm", Qt::CaseInsensitive)) {}
QString m_Name;
bool m_Enabled;
bool m_ForceEnabled;
bool m_Removed;
int m_Priority;
int m_LoadOrder;
FILETIME m_Time;
QString m_OriginName;
bool m_IsMaster;
};
friend bool ByName(const ESPInfo& LHS, const ESPInfo& RHS);
friend bool ByDate(const ESPInfo& LHS, const ESPInfo& RHS);
friend bool ByPriority(const ESPInfo& LHS, const ESPInfo& RHS);
void testMasters();
private:
+2 -2
View File
@@ -27,8 +27,7 @@
<file>resources/emblem-important.png</file>
<file>resources/check.png</file>
<file>mo_icon.ico</file>
<file>resources/dialog-warning.png</file>
<file>resources/dialog-warning_16.png</file>
<file alias="warning">resources/dialog-warning.png</file>
<file alias="emblem_backup">resources/symbol-backup.png</file>
<file alias="icon_tools">resources/applications-accessories.png</file>
<file alias="emblem_problem">resources/emblem-unreadable.png</file>
@@ -51,5 +50,6 @@
<file alias="emblem_conflict_redundant">resources/conflict-redundant.png</file>
<file alias="emblem_notes">resources/accessories-text-editor.png</file>
<file alias="version_date">resources/x-office-calendar.png</file>
<file alias="warning_16">resources/dialog-warning_16.png</file>
</qresource>
</RCC>
Binary file not shown.

After

Width:  |  Height:  |  Size: 603 B

+2 -2
View File
@@ -1,7 +1,7 @@
#include "Winver.h"
#define VER_FILEVERSION 0,99,6,0
#define VER_FILEVERSION_STR "0,99,6,0\0"
#define VER_FILEVERSION 0,99,7,0
#define VER_FILEVERSION_STR "0,99,7,0\0"
VS_VERSION_INFO VERSIONINFO
FILEVERSION VER_FILEVERSION