diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/dlls.manifest.debug.qt5 | 2 | ||||
| -rw-r--r-- | src/dlls.manifest.qt5 | 2 | ||||
| -rw-r--r-- | src/dummybsa.cpp | 244 | ||||
| -rw-r--r-- | src/dummybsa.h | 64 | ||||
| -rw-r--r-- | src/loadmechanism.cpp | 91 | ||||
| -rw-r--r-- | src/main.cpp | 26 | ||||
| -rw-r--r-- | src/mainwindow.cpp | 119 | ||||
| -rw-r--r-- | src/mainwindow.h | 2 | ||||
| -rw-r--r-- | src/modinfo.cpp | 11 | ||||
| -rw-r--r-- | src/organizer.pro | 4 | ||||
| -rw-r--r-- | src/organizercore.cpp | 75 | ||||
| -rw-r--r-- | src/organizercore.h | 1 | ||||
| -rw-r--r-- | src/pluginlist.cpp | 23 | ||||
| -rw-r--r-- | src/profile.cpp | 124 | ||||
| -rw-r--r-- | src/profile.h | 15 | ||||
| -rw-r--r-- | src/profilesdialog.cpp | 27 | ||||
| -rw-r--r-- | src/profilesdialog.h | 3 | ||||
| -rw-r--r-- | src/selectiondialog.cpp | 23 | ||||
| -rw-r--r-- | src/selectiondialog.h | 5 | ||||
| -rw-r--r-- | src/shared/fallout3info.cpp | 46 | ||||
| -rw-r--r-- | src/shared/fallout3info.h | 37 | ||||
| -rw-r--r-- | src/shared/falloutnvinfo.cpp | 63 | ||||
| -rw-r--r-- | src/shared/falloutnvinfo.h | 37 | ||||
| -rw-r--r-- | src/shared/gameinfo.h | 53 | ||||
| -rw-r--r-- | src/shared/oblivioninfo.cpp | 48 | ||||
| -rw-r--r-- | src/shared/oblivioninfo.h | 39 | ||||
| -rw-r--r-- | src/shared/skyriminfo.cpp | 56 | ||||
| -rw-r--r-- | src/shared/skyriminfo.h | 16 |
28 files changed, 326 insertions, 930 deletions
diff --git a/src/dlls.manifest.debug.qt5 b/src/dlls.manifest.debug.qt5 index e49b33b8..59497baa 100644 --- a/src/dlls.manifest.debug.qt5 +++ b/src/dlls.manifest.debug.qt5 @@ -23,5 +23,7 @@ <file name="Qt5WebKitd.dll"/>
<file name="Qt5WebKitWidgetsd.dll"/>
<file name="Qt5Widgetsd.dll"/>
+ <file name="Qt5WinExtrasd.dll"/>
+ <file name="Qt5Xmld.dll"/>
<file name="Qt5XmlPatternsd.dll"/>
</assembly>
diff --git a/src/dlls.manifest.qt5 b/src/dlls.manifest.qt5 index b8f2d467..76206f21 100644 --- a/src/dlls.manifest.qt5 +++ b/src/dlls.manifest.qt5 @@ -23,5 +23,7 @@ <file name="Qt5WebKit.dll"/>
<file name="Qt5WebKitWidgets.dll"/>
<file name="Qt5Widgets.dll"/>
+ <file name="Qt5WinExtras.dll"/>
+ <file name="Qt5Xml.dll"/>
<file name="Qt5XmlPatterns.dll"/>
</assembly>
\ No newline at end of file diff --git a/src/dummybsa.cpp b/src/dummybsa.cpp deleted file mode 100644 index 49c6ee53..00000000 --- a/src/dummybsa.cpp +++ /dev/null @@ -1,244 +0,0 @@ -/*
-Copyright (C) 2012 Sebastian Herbord. All rights reserved.
-
-This file is part of Mod Organizer.
-
-Mod Organizer is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-Mod Organizer is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#include "dummybsa.h"
-#include <QFile>
-#include <gameinfo.h>
-#define WIN32_LEAN_AND_MEAN
-#include <Windows.h>
-
-
-static void writeUlong(unsigned char* buffer, int offset, unsigned long value)
-{
- union {
- unsigned long ulValue;
- unsigned char cValue[4];
- };
- ulValue = value;
- memcpy(buffer + offset, cValue, 4);
-}
-
-static void writeUlonglong(unsigned char* buffer, int offset, unsigned long long value)
-{
- union {
- unsigned long long ullValue;
- unsigned char cValue[8];
- };
- ullValue = value;
- memcpy(buffer + offset, cValue, 8);
-}
-/*
-static unsigned long long genHashInt(const char* pos, const char* end)
-{
- unsigned long long hash2 = 0;
- for (; pos < end; ++pos) {
- hash2 *= 0x1003f;
- hash2 += *pos;
- }
- return hash2;
-}
-
-
-static unsigned long long genHash(const char* fileName)
-{
- char fileNameLower[MAX_PATH + 1];
- int i = 0;
- for (; i < MAX_PATH && fileName[i] != '\0'; ++i) {
- fileNameLower[i] = tolower(fileName[i]);
- }
- fileNameLower[i] = '\0';
-
- char* ext = strrchr(fileNameLower, '.');
- if (ext == nullptr) {
- ext = fileNameLower + strlen(fileNameLower);
- }
-
- int length = ext - fileNameLower;
-
- unsigned long long hash = 0ULL;
-
- if (length > 0) {
- hash = *(ext - 1) |
- ((length > 2 ? *(ext - 2) : 0) << 8) |
- (length << 16) |
- (fileNameLower[0] << 24);
- }
-
- if (strcmp(ext + 1, "dds") == 0) {
- hash |= 0x8080;
- } // the rest is not supported currently
-
- hash |= genHashInt(fileNameLower + 1, ext - 2) << 0x32;
- hash |= genHashInt(ext, ext + strlen(ext)) << 0x32;
-
- return hash;
-}*/
-
-
-static unsigned long genHashInt(const unsigned char *pos, const unsigned char *end)
-{
- unsigned long hash = 0;
- for (; pos < end; ++pos) {
- hash *= 0x1003f;
- hash += *pos;
- }
- return hash;
-}
-
-
-static unsigned long long genHash(const char* fileName)
-{
- char fileNameLower[MAX_PATH + 1];
- int i = 0;
- for (; i < MAX_PATH && fileName[i] != '\0'; ++i) {
- fileNameLower[i] = static_cast<char>(tolower(fileName[i]));
- if (fileNameLower[i] == '\\') {
- fileNameLower[i] = '/';
- }
- }
- fileNameLower[i] = '\0';
-
- unsigned char *fileNameLowerU = reinterpret_cast<unsigned char*>(fileNameLower);
-
- char* ext = strrchr(fileNameLower, '.');
- if (ext == nullptr) {
- ext = fileNameLower + strlen(fileNameLower);
- }
- unsigned char *extU = reinterpret_cast<unsigned char*>(ext);
-
- int length = ext - fileNameLower;
-
- unsigned long long hash = 0ULL;
-
- if (length > 0) {
- hash = *(extU - 1) |
- ((length > 2 ? *(ext - 2) : 0) << 8) |
- (length << 16) |
- (fileNameLowerU[0] << 24);
- }
-
- if (strlen(ext) > 0) {
- if (strcmp(ext + 1, "kf") == 0) {
- hash |= 0x80;
- } else if (strcmp(ext + 1, "nif") == 0) {
- hash |= 0x8000;
- } else if (strcmp(ext + 1, "dds") == 0) {
- hash |= 0x8080;
- } else if (strcmp(ext + 1, "wav") == 0) {
- hash |= 0x80000000;
- }
-
- unsigned long long temp = static_cast<unsigned long long>(genHashInt(
- fileNameLowerU + 1, extU - 2));
- temp += static_cast<unsigned long long>(genHashInt(
- extU, extU + strlen(ext)));
-
- hash |= (temp & 0xFFFFFFFF) << 32;
- }
- return hash;
-}
-
-
-DummyBSA::DummyBSA()
- : m_Version(MOShared::GameInfo::instance().getBSAVersion()), m_FolderName(""), m_FileName("dummy.dds"),
- m_TotalFileNameLength(0)
-{
-}
-
-
-void DummyBSA::writeHeader(QFile& file)
-{
- unsigned char header[] = {
- 'B', 'S', 'A', '\0', // magic string
- 0xDE, 0xAD, 0xBE, 0xEF, // version - insert later
- 0x24, 0x00, 0x00, 0x00, // offset to folder recors. header size is static
- 0xDE, 0xAD, 0xBE, 0xEF, // archive flags - insert later
- 0x01, 0x00, 0x00, 0x00, // folder count
- 0x01, 0x00, 0x00, 0x00, // file count
- 0xDE, 0xAD, 0xBE, 0xEF, // total folder names length - insert later
- 0xDE, 0xAD, 0xBE, 0xEF, // total file names length - insert later
- 0xDE, 0xAD, 0xBE, 0xEF // file flags - insert later
- };
-
- writeUlong(header, 4, MOShared::GameInfo::instance().getBSAVersion());
- writeUlong(header, 12, 0x01 | 0x02); // has directories and has files.
- writeUlong(header, 24, m_FolderName.length() + 1); // empty folder name
- writeUlong(header, 28, m_TotalFileNameLength); // single character file name
-
- writeUlong(header, 32, 2); // has dds
-
- file.write(reinterpret_cast<char*>(header), sizeof(header));
-}
-
-
-void DummyBSA::writeFolderRecord(QFile& file, const std::string& folderName)
-{
- unsigned char folderRecord[] = {
- 0xDE, 0xAD, 0xBE, 0xEF, 0xDE, 0xAD, 0xBE, 0xEF, // folder hash
- 0x01, 0x00, 0x00, 0x00, // file count
- 0xDE, 0xAD, 0xBE, 0xEF, // offset to folder name
- };
- // we'd usually have to sort folders be the hash value generated here
- writeUlonglong(folderRecord, 0, genHash(folderName.c_str()));
- writeUlong( folderRecord, 12, 0x34 + m_TotalFileNameLength); // TODO: this should be calculated properly
-
- file.write(reinterpret_cast<char*>(folderRecord), sizeof(folderRecord));
-}
-
-
-void DummyBSA::writeFileRecord(QFile& file, const std::string& fileName)
-{
- unsigned char fileRecord[] = {
- 0xDE, 0xAD, 0xBE, 0xEF, 0xDE, 0xAD, 0xBE, 0xEF, // file name hash
- 0xDE, 0xAD, 0xBE, 0xEF, // size
- 0xDE, 0xAD, 0xBE, 0xEF, // offset to file data
- };
-
- // we'd usually have to sort files by the value generated here
- writeUlonglong(fileRecord, 0, genHash(fileName.c_str()));
- writeUlong( fileRecord, 8, 0);
- writeUlong( fileRecord, 12, 0x44 + (fileName.length() + 1) + 4); // after this record we expect the filename and 4 bytes of file size
-
- file.write(reinterpret_cast<char*>(fileRecord), sizeof(fileRecord));
-}
-
-
-void DummyBSA::writeFileRecordBlocks(QFile& file, const std::string& folderName)
-{
- file.write(folderName.c_str(), folderName.length() + 1);
-
- writeFileRecord(file, m_FileName);
-}
-
-
-void DummyBSA::write(const QString& fileName)
-{
- QFile file(fileName);
- file.open(QIODevice::WriteOnly);
-
- m_TotalFileNameLength = m_FileName.length() + 1;
-
- writeHeader(file);
- writeFolderRecord(file, m_FolderName);
- writeFileRecordBlocks(file, m_FolderName);
- file.write(m_FileName.c_str() , m_FileName.length() + 1);
- char fileSize[] = { 0x00, 0x00, 0x00, 0x00 };
- file.write(fileSize, sizeof(fileSize));
- file.close();
-}
diff --git a/src/dummybsa.h b/src/dummybsa.h deleted file mode 100644 index 0d231393..00000000 --- a/src/dummybsa.h +++ /dev/null @@ -1,64 +0,0 @@ -/*
-Copyright (C) 2012 Sebastian Herbord. All rights reserved.
-
-This file is part of Mod Organizer.
-
-Mod Organizer is free software: you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
-
-Mod Organizer is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#ifndef DUMMYBSA_H
-#define DUMMYBSA_H
-
-#include <QString>
-#include <QFile>
-
-/**
- * @brief Class for creating a dummy bsa used for archive invalidation
- **/
-class DummyBSA
-{
-
-public:
-
- /**
- * @brief constructor
- *
- **/
- DummyBSA();
-
- /**
- * @brief write to the specified file
- *
- * @param fileName name of the file to write to
- **/
- void write(const QString& fileName);
-
-private:
-
- void writeHeader(QFile& file);
- void writeFolderRecord(QFile& file, const std::string& folderName);
- void writeFileRecord(QFile& file, const std::string& fileName);
- void writeFileRecordBlocks(QFile& file, const std::string& folderName);
-
-private:
-
- unsigned long m_Version;
- std::string m_FolderName;
- std::string m_FileName;
- unsigned long m_TotalFileNameLength;
-
-};
-
-
-#endif // DUMMYBSA_H
diff --git a/src/loadmechanism.cpp b/src/loadmechanism.cpp index 711a7f1a..913d018c 100644 --- a/src/loadmechanism.cpp +++ b/src/loadmechanism.cpp @@ -20,7 +20,8 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "loadmechanism.h"
#include "utility.h"
#include "util.h"
-#include <gameinfo.h>
+#include <iplugingame.h>
+#include <scriptextender.h>
#include <appconfig.h>
#include <QFile>
#include <QFileInfo>
@@ -28,6 +29,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include <QString>
#include <QMessageBox>
#include <QCryptographicHash>
+#include <QCoreApplication>
using namespace MOBase;
@@ -49,7 +51,7 @@ void LoadMechanism::writeHintFile(const QDir &targetDirectory) if (!hintFile.open(QIODevice::WriteOnly)) {
throw MyException(QObject::tr("failed to open %1: %2").arg(hintFilePath).arg(hintFile.errorString()));
}
- hintFile.write(ToString(GameInfo::instance().getOrganizerDirectory(), true).c_str());
+ hintFile.write(qApp->applicationDirPath().toUtf8().constData());
hintFile.close();
}
@@ -62,38 +64,31 @@ void LoadMechanism::removeHintFile(QDir &targetDirectory) bool LoadMechanism::isDirectLoadingSupported()
{
- if (GameInfo::instance().getType() == GameInfo::TYPE_OBLIVION) {
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ if (game->gameName().compare("oblivion", Qt::CaseInsensitive)) {
// oblivion can be loaded directly if it's not the steam variant
- QString gamePath = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
- QDir gameDir(gamePath);
- // test if this is the steam version of oblivion
- if (QFile(gameDir.absoluteFilePath("steam_api.dll")).exists()) {
- return false;
- }
+ return !game->gameDirectory().exists("steam_api.dll");
+ } else {
+ // all other games work afaik
+ return true;
}
-
- // all other games work afaik
- return true;
}
-
bool LoadMechanism::isScriptExtenderSupported()
{
- QString targetPath = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
- if ((QFile(targetPath.mid(0).append("/").append(ToQString(GameInfo::instance().getSEName())).append("_loader.exe")).exists()) ||
- (QFile(targetPath.mid(0).append("/").append(ToQString(GameInfo::instance().getSEName())).append("_steam_loader.dll")).exists())) {
- return true;
- } else {
- return false;
- }
-}
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ ScriptExtender *extender = game->feature<ScriptExtender>();
+ // test if there even is an extender for the managed game and if so whether it's installed
+ return (extender != nullptr)
+ && (game->gameDirectory().exists(extender->name() + "_loader.exe")
+ || game->gameDirectory().exists(extender->name() + "_steam_loader.dll"));
+}
bool LoadMechanism::isProxyDLLSupported()
{
- QString targetPath = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
- targetPath.append("/").append(ToQString(AppConfig::proxyDLLTarget()));
- return QFile(targetPath).exists();
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ return game->gameDirectory().exists(QString::fromStdWString(AppConfig::proxyDLLTarget()));
}
@@ -124,12 +119,13 @@ bool LoadMechanism::hashIdentical(const QString &fileNameLHS, const QString &fil void LoadMechanism::deactivateScriptExtender()
{
try {
- QString gameDirectory = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
-
- QString pluginsDirPath = gameDirectory;
- pluginsDirPath.append("/data/").append(ToQString(GameInfo::instance().getSEName())).append("/plugins");
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ ScriptExtender *extender = game->feature<ScriptExtender>();
+ if (extender == nullptr) {
+ throw MyException(QObject::tr("game doesn't support a script extender"));
+ }
- QDir pluginsDir(pluginsDirPath);
+ QDir pluginsDir(game->gameDirectory().absolutePath() + "/data/" + extender->name() + "/plugins");
QString hookDLLName = ToQString(AppConfig::hookDLLName());
if (QFile(pluginsDir.absoluteFilePath(hookDLLName)).exists()) {
@@ -149,14 +145,13 @@ void LoadMechanism::deactivateScriptExtender() void LoadMechanism::deactivateProxyDLL()
{
try {
- QString gameDirectory = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
- QString targetPath = gameDirectory;
- targetPath.append("/").append(ToQString(AppConfig::proxyDLLTarget()));
+ QString targetPath = game->gameDirectory().absoluteFilePath(QString::fromStdWString(AppConfig::proxyDLLTarget()));
QFile targetDLL(targetPath);
if (targetDLL.exists()) {
- QString origFile = gameDirectory.mid(0).append(ToQString(AppConfig::proxyDLLOrig()));
+ QString origFile = game->gameDirectory().absoluteFilePath(QString::fromStdWString(AppConfig::proxyDLLOrig()));
// determine if a proxy-dll is installed
// this is a very crude way of making this decision but it should be good enough
if ((targetDLL.size() < 24576) && (QFile(origFile).exists())) {
@@ -169,8 +164,7 @@ void LoadMechanism::deactivateProxyDLL() }
}
- QDir dir(gameDirectory);
- removeHintFile(dir);
+ removeHintFile(game->gameDirectory());
} catch (const std::exception &e) {
QMessageBox::critical(nullptr, QObject::tr("Failed to deactivate proxy-dll loading"), e.what());
}
@@ -180,19 +174,20 @@ void LoadMechanism::deactivateProxyDLL() void LoadMechanism::activateScriptExtender()
{
try {
- QString gameDirectory = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
-
- QString pluginsDirPath = gameDirectory;
- pluginsDirPath.append("/data/").append(ToQString(GameInfo::instance().getSEName())).append("/plugins");
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ ScriptExtender *extender = game->feature<ScriptExtender>();
+ if (extender == nullptr) {
+ throw MyException(QObject::tr("game doesn't support a script extender"));
+ }
- QDir pluginsDir(pluginsDirPath);
+ QDir pluginsDir(game->gameDirectory().absolutePath() + "/data/" + extender->name() + "/plugins");
if (!pluginsDir.exists()) {
pluginsDir.mkpath(".");
}
QString targetPath = pluginsDir.absoluteFilePath(ToQString(AppConfig::hookDLLName()));
- QString hookDLLPath = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getOrganizerDirectory())).append("/").append(ToQString(AppConfig::hookDLLName()));
+ QString hookDLLPath = qApp->applicationDirPath() + "/" + QString::fromStdWString(AppConfig::hookDLLName());
QFile dllFile(targetPath);
@@ -219,17 +214,16 @@ void LoadMechanism::activateScriptExtender() void LoadMechanism::activateProxyDLL()
{
try {
- QString gameDirectory = QDir::fromNativeSeparators(ToQString(GameInfo::instance().getGameDirectory()));
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+
+ QString targetPath = game->gameDirectory().absoluteFilePath(QString::fromStdWString(AppConfig::proxyDLLTarget()));
- QString targetPath = gameDirectory;
- targetPath.append("/").append(ToQString(AppConfig::proxyDLLTarget()));
QFile targetDLL(targetPath);
if (!targetDLL.exists()) {
return;
}
- QString sourcePath = QDir::fromNativeSeparators(
- ToQString(GameInfo::instance().getOrganizerDirectory())).append("/").append(ToQString(AppConfig::proxyDLLSource()));
+ QString sourcePath = qApp->applicationDirPath() + "/" + ToQString(AppConfig::proxyDLLSource());
// this is a very crude way of making this decision but it should be good enough
if (targetDLL.size() < 24576) {
@@ -246,8 +240,7 @@ void LoadMechanism::activateProxyDLL() } else {
// no proxy dll installed yet. move the original and insert proxy-dll
- QString origFile = gameDirectory;
- origFile.append("/").append(ToQString(AppConfig::proxyDLLOrig()));
+ QString origFile = game->gameDirectory().absoluteFilePath(QString::fromStdWString(AppConfig::proxyDLLOrig()));
if (QFile(origFile).exists()) {
// orig-file exists. this may happen if the steam-api was updated or the user messed with the
@@ -263,7 +256,7 @@ void LoadMechanism::activateProxyDLL() throw MyException(QObject::tr("Failed to copy %1 to %2").arg(sourcePath).arg(targetPath));
}
}
- writeHintFile(QDir(gameDirectory));
+ writeHintFile(game->gameDirectory());
} catch (const std::exception &e) {
QMessageBox::critical(nullptr, QObject::tr("Failed to set up proxy-dll loading"), e.what());
}
diff --git a/src/main.cpp b/src/main.cpp index a048d50d..8507d725 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -406,29 +406,17 @@ int main(int argc, char *argv[]) reportError(QObject::tr("No game identified in \"%1\". The directory is required to contain "
"the game binary and its launcher.").arg(gamePath));
}
- SelectionDialog selection(QObject::tr("Please select the game to manage"), nullptr);
+ SelectionDialog selection(QObject::tr("Please select the game to manage"), nullptr, QSize(32, 32));
- { // add options
- QString skyrimPath = ToQString(SkyrimInfo::getRegPathStatic());
- QString falloutNVPath = ToQString(FalloutNVInfo::getRegPathStatic());
- QString fallout3Path = ToQString(Fallout3Info::getRegPathStatic());
- QString oblivionPath = ToQString(OblivionInfo::getRegPathStatic());
- if (skyrimPath.length() != 0) {
- selection.addChoice(QString("Skyrim"), skyrimPath, skyrimPath);
+ for (const IPluginGame * const game : pluginContainer.plugins<IPluginGame>()) {
+ if (game->isInstalled()) {
+ QString path = game->gameDirectory().absolutePath();
+ selection.addChoice(game->gameIcon(), game->gameName(), path, path);
}
- if (falloutNVPath.length() != 0) {
- selection.addChoice(QString("Fallout NV"), falloutNVPath, falloutNVPath);
- }
- if (fallout3Path.length() != 0) {
- selection.addChoice(QString("Fallout 3"), fallout3Path, fallout3Path);
- }
- if (oblivionPath.length() != 0) {
- selection.addChoice(QString("Oblivion"), oblivionPath, oblivionPath);
- }
-
- selection.addChoice(QString("Browse..."), QString(), QString());
}
+ selection.addChoice(QString("Browse..."), QString(), QString());
+
if (selection.exec() == QDialog::Rejected) {
gamePath = "";
done = true;
diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp index 50a07b75..1c54d250 100644 --- a/src/mainwindow.cpp +++ b/src/mainwindow.cpp @@ -60,13 +60,15 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "aboutdialog.h"
#include "safewritefile.h"
#include "organizerproxy.h"
-#include "nxmaccessmanager.h
+#include "nxmaccessmanager.h"
#include <archive.h>
#include <gameinfo.h>
#include <appconfig.h>
#include <utility.h>
#include <ipluginproxy.h>
+#include <dataarchives.h>
#include <questionboxmemory.h>
+#include <taskprogressmanager.h>
#include <util.h>
#include <map>
#include <ctime>
@@ -139,7 +141,7 @@ using namespace MOShared; MainWindow::MainWindow(const QString &exeName
- : QMainWindow(parent), ui(new Ui::MainWindow), m_Tutorial(this, "MainWindow"),
+ , QSettings &initSettings
, OrganizerCore &organizerCore
, PluginContainer &pluginContainer
, QWidget *parent)
@@ -148,7 +150,7 @@ MainWindow::MainWindow(const QString &exeName , m_WasVisible(false)
, m_Tutorial(this, "MainWindow")
, m_ExeName(exeName)
- , m_OldProfileIndex(-1),
+ , m_OldProfileIndex(-1)
, m_ModListGroupingProxy(nullptr)
, m_ModListSortProxy(nullptr)
, m_OldExecutableIndex(-1)
@@ -191,7 +193,7 @@ MainWindow::MainWindow(const QString &exeName updateToolBar();
- languageChange(m_Settings.language());
+ TaskProgressManager::instance().tryCreateTaskbar();
// set up mod list
m_ModListSortProxy = m_OrganizerCore.createModListProxyModel();
@@ -335,7 +337,7 @@ MainWindow::MainWindow(const QString &exeName // refresh profiles so the current profile can be activated
refreshProfiles(false);
- ui->profileBox->setCurrentText(m_OrganizerCore.currentProfile()->getName());
+ ui->profileBox->setCurrentText(m_OrganizerCore.currentProfile()->name());
refreshExecutablesList();
updateToolBar();
@@ -1036,9 +1038,9 @@ void MainWindow::on_profileBox_currentIndexChanged(int index) }
if (ui->profileBox->currentIndex() == 0) {
- ProfilesDialog(m_GamePath, m_OrganizerCore.managedGame(), this).exec();
+ ProfilesDialog(m_GamePath, this).exec();
while (!refreshProfiles()) {
- ProfilesDialog(m_GamePath, m_OrganizerCore.managedGame(), this).exec();
+ ProfilesDialog(m_GamePath, this).exec();
}
ui->profileBox->setCurrentIndex(previousIndex);
} else {
@@ -1213,25 +1215,6 @@ bool MainWindow::refreshProfiles(bool selectProfile) }
-#if QT_VERSION >= 0x050000
-extern QPixmap qt_pixmapFromWinHICON(HICON icon);
-#else
-#define qt_pixmapFromWinHICON(icon) QPixmap::fromWinHICON(icon)
-#endif
-
-QIcon MainWindow::iconForExecutable(const QString &filePath)
-{
- HICON winIcon;
- UINT res = ::ExtractIconExW(ToWString(filePath).c_str(), 0, &winIcon, nullptr, 1);
- if (res == 1) {
- QIcon result = QIcon(qt_pixmapFromWinHICON(winIcon));
- ::DestroyIcon(winIcon);
- return result;
- } else {
- return QIcon(":/MO/gui/executable");
- }
-}
-
void MainWindow::refreshExecutablesList()
{
QComboBox* executablesList = findChild<QComboBox*>("executablesListBox");
@@ -1285,12 +1268,12 @@ void MainWindow::refreshSaveList() QDir savesDir;
if (m_OrganizerCore.currentProfile()->localSavesEnabled()) {
- savesDir.setPath(m_OrganizerCore.currentProfile()->getPath() + "/saves");
+ savesDir.setPath(m_OrganizerCore.currentProfile()->absolutePath() + "/saves");
} else {
wchar_t path[MAX_PATH];
::GetPrivateProfileStringW(L"General", L"SLocalSavePath", L"Saves",
path, MAX_PATH,
- (ToWString(m_OrganizerCore.currentProfile()->getPath()) + L"\\" + GameInfo::instance().getIniFileNames().at(0)).c_str());
+ (ToWString(m_OrganizerCore.currentProfile()->absolutePath()) + L"\\" + GameInfo::instance().getIniFileNames().at(0)).c_str());
savesDir.setPath(m_OrganizerCore.managedGame()->documentsDirectory().absoluteFilePath(QString::fromWCharArray(path)));
}
@@ -1417,42 +1400,46 @@ void MainWindow::updateBSAList(const QStringList &defaultArchives, const QString void MainWindow::checkBSAList()
{
- ui->bsaList->blockSignals(true);
+ DataArchives *archives = m_OrganizerCore.managedGame()->feature<DataArchives>();
- QStringList defaultArchives = m_OrganizerCore.defaultArchiveList();
+ if (archives != nullptr) {
+ ui->bsaList->blockSignals(true);
- bool warning = false;
+ QStringList defaultArchives = archives->archives(m_OrganizerCore.currentProfile());
- for (int i = 0; i < ui->bsaList->topLevelItemCount(); ++i) {
- bool modWarning = false;
- QTreeWidgetItem *tlItem = ui->bsaList->topLevelItem(i);
- for (int j = 0; j < tlItem->childCount(); ++j) {
- QTreeWidgetItem *item = tlItem->child(j);
- QString filename = item->text(0);
- item->setIcon(0, QIcon());
- item->setToolTip(0, QString());
+ bool warning = false;
- if (item->checkState(0) == Qt::Unchecked) {
- if (defaultArchives.contains(filename)) {
- 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;
+ for (int i = 0; i < ui->bsaList->topLevelItemCount(); ++i) {
+ bool modWarning = false;
+ QTreeWidgetItem *tlItem = ui->bsaList->topLevelItem(i);
+ for (int j = 0; j < tlItem->childCount(); ++j) {
+ QTreeWidgetItem *item = tlItem->child(j);
+ QString filename = item->text(0);
+ item->setIcon(0, QIcon());
+ item->setToolTip(0, QString());
+
+ if (item->checkState(0) == Qt::Unchecked) {
+ if (defaultArchives.contains(filename)) {
+ 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;
+ }
}
}
+ if (modWarning) {
+ ui->bsaList->expandItem(ui->bsaList->topLevelItem(i));
+ warning = true;
+ }
}
- if (modWarning) {
- ui->bsaList->expandItem(ui->bsaList->topLevelItem(i));
- warning = true;
+
+ if (warning) {
+ ui->tabWidget->setTabIcon(1, QIcon(":/MO/gui/warning"));
+ } else {
+ ui->tabWidget->setTabIcon(1, QIcon());
}
- }
- if (warning) {
- ui->tabWidget->setTabIcon(1, QIcon(":/MO/gui/warning"));
- } else {
- ui->tabWidget->setTabIcon(1, QIcon());
+ ui->bsaList->blockSignals(false);
}
-
- ui->bsaList->blockSignals(false);
}
@@ -1790,7 +1777,7 @@ void MainWindow::on_actionAdd_Profile_triggered() {
bool repeat = true;
while (repeat) {
- ProfilesDialog profilesDialog(m_GamePath, m_OrganizerCore.managedGame(), this);
+ ProfilesDialog profilesDialog(m_GamePath, this);
profilesDialog.exec();
if (refreshProfiles() && !profilesDialog.failed()) {
repeat = false;
@@ -2333,10 +2320,10 @@ void MainWindow::overwriteClosed(int) void MainWindow::displayModInformation(ModInfo::Ptr modInfo, unsigned int index, int tab)
{
- if (!m_OrganizerCore.modList()->modInfoAboutToChange(modInfo)) { - qDebug("A different mod information dialog is open. If this is incorrect, please restart MO"); - return; - } + if (!m_OrganizerCore.modList()->modInfoAboutToChange(modInfo)) {
+ qDebug("A different mod information dialog is open. If this is incorrect, please restart MO");
+ return;
+ }
std::vector<ModInfo::EFlag> flags = modInfo->getFlags();
if (std::find(flags.begin(), flags.end(), ModInfo::FLAG_OVERWRITE) != flags.end()) {
QDialog *dialog = this->findChild<QDialog*>("__overwriteDialog");
@@ -3379,7 +3366,7 @@ void MainWindow::installTranslator(const QString &name) QString fileName = name + "_" + m_CurrentLanguage;
if (!translator->load(fileName, qApp->applicationDirPath() + "/translations")) {
if ((m_CurrentLanguage != "en-US") && (m_CurrentLanguage != "en_US")) {
- qWarning("localization file %s not found", qPrintable(fileName));
+ qDebug("localization file %s not found", qPrintable(fileName));
} // we don't actually expect localization files for english
}
@@ -3481,10 +3468,10 @@ int MainWindow::getBinaryExecuteInfo(const QFileInfo &targetInfo, QFileInfo &bin { // try to find java automatically
WCHAR buffer[MAX_PATH];
- if (::FindExecutableW(targetPathW.c_str(), nullptr, buffer) > (HINSTANCE)32) { - DWORD binaryType = 0UL; - if (!::GetBinaryTypeW(buffer, &binaryType)) { - qDebug("failed to determine binary type of \"%ls\": %lu", buffer, ::GetLastError()); + if (::FindExecutableW(targetPathW.c_str(), nullptr, buffer) > (HINSTANCE)32) {
+ DWORD binaryType = 0UL;
+ if (!::GetBinaryTypeW(buffer, &binaryType)) {
+ qDebug("failed to determine binary type of \"%ls\": %lu", buffer, ::GetLastError());
} else if (binaryType == SCS_32BIT_BINARY) {
binaryPath = ToQString(buffer);
}
@@ -3659,7 +3646,7 @@ void MainWindow::openDataFile() QString arguments;
switch (getBinaryExecuteInfo(targetInfo, binaryInfo, arguments)) {
case 1: {
- m_OrganizerCore.spawnBinaryDirect(binaryInfo, arguments, m_OrganizerCore.currentProfile()->getName(), targetInfo.absolutePath(), "");
+ m_OrganizerCore.spawnBinaryDirect(binaryInfo, arguments, m_OrganizerCore.currentProfile()->name(), targetInfo.absolutePath(), "");
} break;
case 2: {
::ShellExecuteW(nullptr, L"open", ToWString(targetInfo.absoluteFilePath()).c_str(), nullptr, nullptr, SW_SHOWNORMAL);
@@ -4339,7 +4326,7 @@ void MainWindow::on_bossButton_clicked() createStdoutPipe(&stdOutRead, &stdOutWrite);
HANDLE loot = startBinary(QFileInfo(qApp->applicationDirPath() + "/loot/lootcli.exe"),
parameters.join(" "),
- m_OrganizerCore.currentProfile()->getName(),
+ m_OrganizerCore.currentProfile()->name(),
m_OrganizerCore.settings().logLevel(),
qApp->applicationDirPath() + "/loot",
true,
diff --git a/src/mainwindow.h b/src/mainwindow.h index b9f93cd5..d0e3aaf5 100644 --- a/src/mainwindow.h +++ b/src/mainwindow.h @@ -229,8 +229,6 @@ private: bool errorReported(QString &logFile);
- QIcon iconForExecutable(const QString &filePath);
-
void updateESPLock(bool locked);
static void setupNetworkProxy(bool activate);
diff --git a/src/modinfo.cpp b/src/modinfo.cpp index b1d9bed4..3b8d6b92 100644 --- a/src/modinfo.cpp +++ b/src/modinfo.cpp @@ -28,8 +28,10 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "messagedialog.h" #include <gameinfo.h> +#include <iplugingame.h> #include <versioninfo.h> #include <appconfig.h> +#include <scriptextender.h> #include <QApplication> @@ -862,7 +864,13 @@ std::vector<ModInfo::EContent> ModInfoRegular::getContents() const if (dir.entryList(QStringList() << "*.esp" << "*.esm").size() > 0) { result.push_back(CONTENT_PLUGIN); } - QString sePluginPath = ToQString(GameInfo::instance().getSEName()) + "/plugins"; + + ScriptExtender *extender = qApp->property("managed_game").value<IPluginGame*>()->feature<ScriptExtender>(); + + if (extender != nullptr) { + QString sePluginPath = extender->name() + "/plugins"; + if (dir.exists(sePluginPath)) result.push_back(CONTENT_SKSE); + } if (dir.exists("textures")) result.push_back(CONTENT_TEXTURE); if (dir.exists("meshes")) result.push_back(CONTENT_MESH); if (dir.exists("interface") @@ -870,7 +878,6 @@ std::vector<ModInfo::EContent> ModInfoRegular::getContents() const if (dir.exists("music")) result.push_back(CONTENT_MUSIC); if (dir.exists("sound")) result.push_back(CONTENT_SOUND); if (dir.exists("scripts")) result.push_back(CONTENT_SCRIPT); - if (dir.exists(sePluginPath)) result.push_back(CONTENT_SKSE); if (dir.exists("strings")) result.push_back(CONTENT_STRING); if (dir.exists("SkyProc Patchers")) result.push_back(CONTENT_SKYPROC); return result; diff --git a/src/organizer.pro b/src/organizer.pro index b67fb3e5..9300f348 100644 --- a/src/organizer.pro +++ b/src/organizer.pro @@ -57,7 +57,6 @@ SOURCES += \ filedialogmemory.cpp \
executableslist.cpp \
editexecutablesdialog.cpp \
- dummybsa.cpp \
downloadmanager.cpp \
downloadlistwidgetcompact.cpp \
downloadlistwidget.cpp \
@@ -137,7 +136,6 @@ HEADERS += \ filedialogmemory.h \
executableslist.h \
editexecutablesdialog.h \
- dummybsa.h \
downloadmanager.h \
downloadlistwidgetcompact.h \
downloadlistwidget.h \
@@ -257,7 +255,7 @@ LIBS += -L"E:/Visual Leak Detector/lib/Win32" #DEFINES += TEST_MODELS
-INCLUDEPATH += ../shared ../archive ../uibase ../bsatk ../esptk "$${LOOTPATH}" "$${BOOSTPATH}"
+INCLUDEPATH += ../shared ../archive ../uibase ../bsatk ../esptk ../plugins/gamefeatures "$${LOOTPATH}" "$${BOOSTPATH}"
LIBS += -L"$${BOOSTPATH}/stage/lib"
diff --git a/src/organizercore.cpp b/src/organizercore.cpp index 936e5529..0ea3ccb1 100644 --- a/src/organizercore.cpp +++ b/src/organizercore.cpp @@ -11,7 +11,9 @@ #include "spawn.h"
#include "safewritefile.h"
#include "syncoverwritedialog.h"
+#include "nxmaccessmanager.h"
#include <ipluginmodpage.h>
+#include <dataarchives.h>
#include <directoryentry.h>
#include <scopeguard.h>
#include <utility.h>
@@ -184,7 +186,7 @@ void OrganizerCore::storeSettings() m_UserInterface->storeSettings(settings);
}
if (m_CurrentProfile != nullptr) {
- settings.setValue("selected_profile", m_CurrentProfile->getName().toUtf8().constData());
+ settings.setValue("selected_profile", m_CurrentProfile->name().toUtf8().constData());
}
settings.setValue("ask_for_nexuspw", m_AskForNexusPW);
@@ -368,6 +370,7 @@ void OrganizerCore::setManagedGame(const QString &gameName) m_GameName = gameName;
if (m_PluginContainer != nullptr) {
m_GamePlugin = m_PluginContainer->managedGame(m_GameName);
+ qApp->setProperty("managed_game", QVariant::fromValue(m_GamePlugin));
emit managedGameChanged(m_GamePlugin);
}
}
@@ -473,7 +476,6 @@ InstallationManager *OrganizerCore::installationManager() void OrganizerCore::createDefaultProfile()
{
QString profilesPath = qApp->property("dataPath").toString() + "/" + QString::fromStdWString(AppConfig::profilesPath());
- qDebug("%d", QDir(profilesPath).entryList(QDir::AllDirs | QDir::NoDotAndDotDot).size());
if (QDir(profilesPath).entryList(QDir::AllDirs | QDir::NoDotAndDotDot).size() == 0) {
Profile newProf("Default", managedGame(), false);
}
@@ -506,7 +508,7 @@ MOBase::IModRepositoryBridge *OrganizerCore::createNexusBridge() const QString OrganizerCore::profileName() const
{
if (m_CurrentProfile != nullptr) {
- return m_CurrentProfile->getName();
+ return m_CurrentProfile->name();
} else {
return "";
}
@@ -515,7 +517,7 @@ QString OrganizerCore::profileName() const QString OrganizerCore::profilePath() const
{
if (m_CurrentProfile != nullptr) {
- return m_CurrentProfile->getPath();
+ return m_CurrentProfile->absolutePath();
} else {
return "";
}
@@ -809,7 +811,7 @@ void OrganizerCore::spawnBinary(const QFileInfo &binary, const QString &argument dialog->show();
ON_BLOCK_EXIT([&] () { dialog->hide(); dialog->deleteLater(); });
- HANDLE processHandle = spawnBinaryDirect(binary, arguments, m_CurrentProfile->getName(), currentDirectory, steamAppID);
+ HANDLE processHandle = spawnBinaryDirect(binary, arguments, m_CurrentProfile->name(), currentDirectory, steamAppID);
if (processHandle != INVALID_HANDLE_VALUE) {
if (closeAfterStart && (m_UserInterface != nullptr)) {
m_UserInterface->closeWindow();
@@ -938,7 +940,7 @@ HANDLE OrganizerCore::startApplication(const QString &executable, const QStringL QString profileName = profile;
if (profile.length() == 0) {
if (m_CurrentProfile != nullptr) {
- profileName = m_CurrentProfile->getName();
+ profileName = m_CurrentProfile->name();
} else {
throw MyException(tr("No profile set"));
}
@@ -1081,7 +1083,7 @@ void OrganizerCore::refreshESPList() // clear list
try {
- m_PluginList.refresh(m_CurrentProfile->getName(),
+ m_PluginList.refresh(m_CurrentProfile->name(),
*m_DirectoryStructure,
m_CurrentProfile->getPluginsFileName(),
m_CurrentProfile->getLoadOrderFileName(),
@@ -1091,55 +1093,34 @@ void OrganizerCore::refreshESPList() }
}
-QStringList OrganizerCore::defaultArchiveList()
-{
- QStringList result;
- wchar_t buffer[256];
- std::wstring iniFileName = ToWString(QDir::toNativeSeparators(m_CurrentProfile->getIniFileName()));
-
- if (::GetPrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().append(L"2").c_str(),
- L"", buffer, 256, iniFileName.c_str()) != 0) {
- result.append(ToQString(buffer).split(','));
- }
-
- for (int i = 0; i < result.count(); ++i) {
- result[i] = result[i].trimmed();
- }
-
- return result;
-}
-
void OrganizerCore::refreshBSAList()
{
- m_ArchivesInit = false;
+ DataArchives *archives = m_GamePlugin->feature<DataArchives>();
- m_DefaultArchives = defaultArchiveList();
+ if (archives != nullptr) {
+ m_ArchivesInit = false;
- wchar_t buffer[256];
- std::wstring iniFileName = ToWString(QDir::toNativeSeparators(m_CurrentProfile->getIniFileName()));
- if (::GetPrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(),
- L"", buffer, 256, iniFileName.c_str()) != 0) {
- m_DefaultArchives = ToQString(buffer).split(',');
- } else {
- std::vector<std::wstring> vanillaBSAs = GameInfo::instance().getVanillaBSAs();
- for (auto iter = vanillaBSAs.begin(); iter != vanillaBSAs.end(); ++iter) {
- m_DefaultArchives.append(ToQString(*iter));
+ // default archives are the ones enabled outside MO. if the list can't be found (which might
+ // happen if ini files are missing) use hard-coded defaults (preferrably the same the game would use)
+ m_DefaultArchives = archives->archives(m_CurrentProfile);
+ if (m_DefaultArchives.length() == 0) {
+ m_DefaultArchives = archives->vanillaArchives();
}
- }
- m_ActiveArchives.clear();
+ m_ActiveArchives.clear();
- auto iter = enabledArchives();
- m_ActiveArchives = toStringList(iter.begin(), iter.end());
- if (m_ActiveArchives.isEmpty()) {
- m_ActiveArchives = m_DefaultArchives;
- }
+ auto iter = enabledArchives();
+ m_ActiveArchives = toStringList(iter.begin(), iter.end());
+ if (m_ActiveArchives.isEmpty()) {
+ m_ActiveArchives = m_DefaultArchives;
+ }
- if (m_UserInterface != nullptr) {
- m_UserInterface->updateBSAList(m_DefaultArchives, m_ActiveArchives);
- }
+ if (m_UserInterface != nullptr) {
+ m_UserInterface->updateBSAList(m_DefaultArchives, m_ActiveArchives);
+ }
- m_ArchivesInit = true;
+ m_ArchivesInit = true;
+ }
}
void OrganizerCore::refreshLists()
diff --git a/src/organizercore.h b/src/organizercore.h index 4d9b0a7c..3191e2a9 100644 --- a/src/organizercore.h +++ b/src/organizercore.h @@ -155,7 +155,6 @@ public: bool onAboutToRun(const std::function<bool (const QString &)> &func);
bool onFinishedRun(const std::function<void (const QString &, unsigned int)> &func);
void refreshModList(bool saveChanges = true);
- QStringList defaultArchiveList();
public: // IPluginDiagnose interface
diff --git a/src/pluginlist.cpp b/src/pluginlist.cpp index ad177247..3c7af59f 100644 --- a/src/pluginlist.cpp +++ b/src/pluginlist.cpp @@ -26,6 +26,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "modinfo.h"
#include <utility.h>
#include <gameinfo.h>
+#include <iplugingame.h>
#include <espfile.h>
#include <windows_error.h>
@@ -126,16 +127,19 @@ QString PluginList::getColumnToolTip(int column) }
-void PluginList::refresh(const QString &profileName, const DirectoryEntry &baseDirectory,
- const QString &pluginsFile, const QString &loadOrderFile,
- const QString &lockedOrderFile)
+void PluginList::refresh(const QString &profileName
+ , const DirectoryEntry &baseDirectory
+ , const QString &pluginsFile
+ , const QString &loadOrderFile
+ , const QString &lockedOrderFile)
{
ChangeBracket<PluginList> layoutChange(this);
m_ESPsByName.clear();
m_ESPsByPriority.clear();
m_ESPs.clear();
- std::vector<std::wstring> primaryPlugins = GameInfo::instance().getPrimaryPlugins();
+
+ QStringList primaryPlugins = qApp->property("managed_game").value<IPluginGame*>()->getPrimaryPlugins();
m_CurrentProfile = profileName;
@@ -150,7 +154,7 @@ void PluginList::refresh(const QString &profileName, const DirectoryEntry &baseD if ((extension == "esp") || (extension == "esm")) {
bool forceEnabled = Settings::instance().forceEnableCoreFiles() &&
- std::find(primaryPlugins.begin(), primaryPlugins.end(), ToWString(filename.toLower())) != primaryPlugins.end();
+ std::find(primaryPlugins.begin(), primaryPlugins.end(), filename.toLower()) != primaryPlugins.end();
bool archive = false;
try {
@@ -321,11 +325,10 @@ bool PluginList::readLoadOrder(const QString &fileName) int priority = 0;
- std::vector<std::wstring> primaryPlugins = GameInfo::instance().getPrimaryPlugins();
- for (std::vector<std::wstring>::iterator iter = primaryPlugins.begin();
- iter != primaryPlugins.end(); ++iter) {
- if (availableESPs.find(ToQString(*iter)) != availableESPs.end()) {
- m_ESPLoadOrder[ToQString(*iter)] = priority++;
+ QStringList primaryPlugins = qApp->property("managed_game").value<IPluginGame*>()->getPrimaryPlugins();
+ for (const QString &plugin : primaryPlugins) {
+ if (availableESPs.find(plugin) != availableESPs.end()) {
+ m_ESPLoadOrder[plugin] = priority++;
}
}
diff --git a/src/profile.cpp b/src/profile.cpp index dd6814fd..5d31533a 100644 --- a/src/profile.cpp +++ b/src/profile.cpp @@ -21,7 +21,6 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "report.h" #include "gameinfo.h" #include "windows_error.h" -#include "dummybsa.h" #include "modinfo.h" #include "safewritefile.h" #include <utility.h> @@ -29,6 +28,8 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include <error_report.h> #include <appconfig.h> #include <iplugingame.h> +#include <bsainvalidation.h> +#include <dataarchives.h> #include <QMessageBox> #include <QApplication> #include <QSettings> @@ -58,6 +59,7 @@ void Profile::touchFile(QString fileName) Profile::Profile(const QString &name, IPluginGame *gamePlugin, bool useDefaultSettings) : m_SaveTimer(nullptr) + , m_GamePlugin(gamePlugin) { initTimer(); QString profilesDir = qApp->property("dataPath").toString() + "/" + ToQString(AppConfig::profilesPath()); @@ -120,8 +122,9 @@ Profile::Profile(const QDir &directory, IPluginGame *gamePlugin) } -Profile::Profile(const Profile& reference) - : m_Directory(reference.m_Directory), m_SaveTimer(nullptr) +Profile::Profile(const Profile &reference) + : m_Directory(reference.m_Directory) + , m_SaveTimer(nullptr) { initTimer(); refreshModStatus(); @@ -590,35 +593,22 @@ void Profile::mergeTweaks(ModInfo::Ptr modInfo, const QString &tweakedIni) const bool Profile::invalidationActive(bool *supported) const { - if (GameInfo::instance().requiresBSAInvalidation()) { + IPluginGame *gamePlugin = qApp->property("managed_game").value<IPluginGame*>(); + + BSAInvalidation *invalidation = gamePlugin->feature<BSAInvalidation>(); + DataArchives *dataArchives = gamePlugin->feature<DataArchives>(); + + if ((invalidation != nullptr) && (dataArchives != nullptr)) { if (supported != nullptr) { *supported = true; } - wchar_t buffer[1024]; - std::wstring iniFileName = ToWString(QDir::toNativeSeparators(getIniFileName())); - // epic ms fail: GetPrivateProfileString uses errno (for whatever reason) to signal a fail since the return value - // has a different meaning (number of bytes copied). HOWEVER, it will not set errno to 0 if NO error occured - errno = 0; - if (::GetPrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(), - L"", buffer, 1024, iniFileName.c_str()) == 0) { - if (errno != 0x02) { - if (supported != nullptr) { - *supported = false; - } - return false; - } else { - QString errorMessage = tr("failed to parse ini file (%1)").arg(ToQString(iniFileName)); - throw windows_error(errorMessage.toUtf8().constData()); - } - } - QStringList archives = ToQString(buffer).split(','); - for (int i = 0; i < archives.count(); ++i) { - QString bsaName = archives.at(i).trimmed(); - if (GameInfo::instance().isInvalidationBSA(ToWString(bsaName))) { + for (const QString &archive : dataArchives->archives(this)) { + if (invalidation->isInvalidationBSA(archive)) { return true; } } + return false; } else { *supported = false; } @@ -626,85 +616,26 @@ bool Profile::invalidationActive(bool *supported) const } -void Profile::deactivateInvalidation() const +void Profile::deactivateInvalidation() { - if (GameInfo::instance().requiresBSAInvalidation()) { - wchar_t buffer[1024]; - std::wstring iniFileName = ToWString(QDir::toNativeSeparators(getIniFileName())); - errno = 0; - if (::GetPrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(), - L"", buffer, 1024, iniFileName.c_str()) == 0) { - if (errno == 0x02) { - QString errorMessage = tr("failed to parse ini file (%1): %2").arg(QDir::toNativeSeparators(getIniFileName())).arg(::GetLastError()); - throw windows_error(errorMessage.toUtf8().constData()); - } else { - return; - } - } - QStringList archives = ToQString(buffer).split(", "); - - for (int i = 0; i < archives.count();) { - QString bsaName = archives.at(i).trimmed(); - if (GameInfo::instance().isInvalidationBSA(ToWString(bsaName))) { - archives.removeAt(i); - } else { - ++i; - } - } + IPluginGame *gamePlugin = qApp->property("managed_game").value<IPluginGame*>(); - // just to be safe... - ::SetFileAttributesW(iniFileName.c_str(), FILE_ATTRIBUTE_NORMAL); + BSAInvalidation *invalidation = gamePlugin->feature<BSAInvalidation>(); - if (!::WritePrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(), - ToWString(archives.join(", ").toUtf8()).c_str(), iniFileName.c_str()) || - !::WritePrivateProfileStringW(L"Archive", L"bInvalidateOlderFiles", L"0", iniFileName.c_str()) || - !::WritePrivateProfileStringW(L"Archive", L"SInvalidationFile", L"ArchiveInvalidation.txt", iniFileName.c_str())) { - QString errorMessage = tr("failed to modify \"%1\"").arg(ToQString(iniFileName)); - throw windows_error(errorMessage.toUtf8().constData()); - } + if (invalidation != nullptr) { + invalidation->deactivate(this); } } -void Profile::activateInvalidation(const QString& dataDirectory) const +void Profile::activateInvalidation() { - if (GameInfo::instance().requiresBSAInvalidation()) { - wchar_t buffer[1024]; - std::wstring iniFileName = ToWString(QDir::toNativeSeparators(getIniFileName())); - errno = 0; - if (::GetPrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(), - L"", buffer, 1024, iniFileName.c_str()) == 0) { - if (errno == 0x02) { - throw windows_error("failed to parse ini file"); - } else { - // ignore. shouldn't have gotten here anyway - return; - } - } - QStringList archives = ToQString(buffer).split(", "); - - QString invalidationBSA = ToQString(GameInfo::instance().getInvalidationBSA()); + IPluginGame *gamePlugin = qApp->property("managed_game").value<IPluginGame*>(); - if (!archives.contains(invalidationBSA)) { - archives.insert(0, invalidationBSA); - } - - // just to be safe... - ::SetFileAttributesW(iniFileName.c_str(), FILE_ATTRIBUTE_NORMAL); - - if (!::WritePrivateProfileStringW(L"Archive", GameInfo::instance().archiveListKey().c_str(), - ToWString(archives.join(", ").toUtf8()).c_str(), iniFileName.c_str()) || - !::WritePrivateProfileStringW(L"Archive", L"bInvalidateOlderFiles", L"1", iniFileName.c_str()) || - !::WritePrivateProfileStringW(L"Archive", L"SInvalidationFile", L"", iniFileName.c_str())) { - QString errorMessage = tr("failed to modify \"%1\"").arg(ToQString(iniFileName)); - throw windows_error(errorMessage.toUtf8().constData()); - } + BSAInvalidation *invalidation = gamePlugin->feature<BSAInvalidation>(); - QString bsaFile = dataDirectory + "/" + invalidationBSA; - if (!QFile::exists(bsaFile)) { - DummyBSA bsa; - bsa.write(bsaFile); - } + if (invalidation != nullptr) { + invalidation->activate(this); } } @@ -784,7 +715,7 @@ QString Profile::getProfileTweaks() const return QDir::cleanPath(m_Directory.absoluteFilePath(ToQString(AppConfig::profileTweakIni()))); } -QString Profile::getPath() const +QString Profile::absolutePath() const { return QDir::cleanPath(m_Directory.absolutePath()); } @@ -792,6 +723,7 @@ QString Profile::getPath() const void Profile::rename(const QString &newName) { QDir profileDir(qApp->property("dataPath").toString() + "/" + QString::fromStdWString(AppConfig::profilesPath())); - profileDir.rename(getName(), newName); + profileDir.rename(name(), newName); m_Directory = profileDir.absoluteFilePath(newName); } + diff --git a/src/profile.h b/src/profile.h index 34efd4b2..5eaa1ea1 100644 --- a/src/profile.h +++ b/src/profile.h @@ -22,7 +22,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "modinfo.h" - +#include <iprofile.h> #include <QString> #include <QDir> #include <QMetaType> @@ -38,7 +38,7 @@ namespace MOBase { /** * @brief represents a profile **/ -class Profile : public QObject +class Profile : public QObject, public MOBase::IProfile { Q_OBJECT @@ -112,7 +112,7 @@ public: /** * @brief deactivate archive invalidation if it was active **/ - void deactivateInvalidation() const; + void deactivateInvalidation(); /** * @brief activate archive invalidation @@ -121,7 +121,7 @@ public: * @todo passing the data directory as a parameter is useless, the function should * be able to query it from GameInfo **/ - void activateInvalidation(const QString &dataDirectory) const; + void activateInvalidation(); /** * @return true if this profile uses local save games @@ -139,7 +139,7 @@ public: /** * @return name of the profile (this is identical to its directory name) **/ - QString getName() const { return m_Directory.dirName(); } + QString name() const { return m_Directory.dirName(); } /** * @return the path of the plugins file in this profile @@ -188,7 +188,7 @@ public: /** * @return path to this profile **/ - QString getPath() const; + QString absolutePath() const; void rename(const QString &newName); @@ -315,12 +315,15 @@ private: QDir m_Directory; + MOBase::IPluginGame *m_GamePlugin; + mutable QByteArray m_LastModlistHash; std::vector<ModStatus> m_ModStatus; std::vector<unsigned int> m_ModIndexByPriority; unsigned int m_NumRegularMods; QTimer *m_SaveTimer; + }; Q_DECLARE_METATYPE(Profile) diff --git a/src/profilesdialog.cpp b/src/profilesdialog.cpp index c6731041..44ee96e9 100644 --- a/src/profilesdialog.cpp +++ b/src/profilesdialog.cpp @@ -24,7 +24,9 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include "transfersavesdialog.h"
#include "profileinputdialog.h"
#include "mainwindow.h"
-#include <gameinfo.h>
+#include "aboutdialog.h"
+#include <iplugingame.h>
+#include <bsainvalidation.h>
#include <appconfig.h>
#include <QListWidgetItem>
#include <QInputDialog>
@@ -40,10 +42,9 @@ using namespace MOShared; Q_DECLARE_METATYPE(Profile::Ptr)
-ProfilesDialog::ProfilesDialog(const QString &gamePath, MOBase::IPluginGame *gamePlugin, QWidget *parent)
+ProfilesDialog::ProfilesDialog(const QString &gamePath, QWidget *parent)
: TutorableDialog("Profiles", parent)
, ui(new Ui::ProfilesDialog)
- , m_GamePlugin(gamePlugin)
, m_GamePath(gamePath)
, m_FailState(false)
{
@@ -61,7 +62,11 @@ ProfilesDialog::ProfilesDialog(const QString &gamePath, MOBase::IPluginGame *gam }
QCheckBox *invalidationBox = findChild<QCheckBox*>("invalidationBox");
- if (!GameInfo::instance().requiresBSAInvalidation()) {
+
+ IPluginGame *game = qApp->property("managed_game").value<IPluginGame*>();
+ BSAInvalidation *invalidation = game->feature<BSAInvalidation>();
+
+ if (invalidation == nullptr) {
invalidationBox->setToolTip(tr("Archive invalidation isn't required for this game."));
invalidationBox->setEnabled(false);
}
@@ -97,7 +102,7 @@ void ProfilesDialog::addItem(const QString &name) QDir profileDir(name);
QListWidgetItem *newItem = new QListWidgetItem(profileDir.dirName(), m_ProfilesList);
try {
- newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(new Profile(profileDir, m_GamePlugin))));
+ newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(new Profile(profileDir, qApp->property("managed_game").value<IPluginGame*>()))));
m_FailState = false;
} catch (const std::exception& e) {
reportError(tr("failed to create profile: %1").arg(e.what()));
@@ -109,7 +114,7 @@ void ProfilesDialog::createProfile(const QString &name, bool useDefaultSettings) try {
QListWidget *profilesList = findChild<QListWidget*>("profilesList");
QListWidgetItem *newItem = new QListWidgetItem(name, profilesList);
- newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(new Profile(name, m_GamePlugin, useDefaultSettings))));
+ newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(new Profile(name, qApp->property("managed_game").value<IPluginGame*>(), useDefaultSettings))));
profilesList->addItem(newItem);
m_FailState = false;
} catch (const std::exception&) {
@@ -123,7 +128,7 @@ void ProfilesDialog::createProfile(const QString &name, const Profile &reference try {
QListWidget *profilesList = findChild<QListWidget*>("profilesList");
QListWidgetItem *newItem = new QListWidgetItem(name, profilesList);
- newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(Profile::createPtrFrom(name, reference, m_GamePlugin))));
+ newItem->setData(Qt::UserRole, QVariant::fromValue(Profile::Ptr(Profile::createPtrFrom(name, reference, qApp->property("managed_game").value<IPluginGame*>()))));
profilesList->addItem(newItem);
m_FailState = false;
} catch (const std::exception&) {
@@ -190,7 +195,7 @@ void ProfilesDialog::on_removeProfileButton_clicked() } else {
// on destruction, the profile object would write the profile.ini file again, so
// we have to get rid of the it before deleting the directory
- profilePath = currentProfile->getPath();
+ profilePath = currentProfile->absolutePath();
}
QListWidgetItem* item = profilesList->takeItem(profilesList->currentRow());
if (item != nullptr) {
@@ -216,7 +221,7 @@ void ProfilesDialog::on_renameButton_clicked() while (!valid) {
bool ok = false;
name = QInputDialog::getText(this, tr("Rename Profile"), tr("New Name"),
- QLineEdit::Normal, currentProfile->getName(),
+ QLineEdit::Normal, currentProfile->name(),
&ok);
valid = fixDirectoryName(name);
if (!ok) {
@@ -249,7 +254,7 @@ void ProfilesDialog::on_invalidationBox_stateChanged(int state) if (state == Qt::Unchecked) {
currentProfile->deactivateInvalidation();
} else {
- currentProfile->activateInvalidation(m_GamePath + "/data");
+ currentProfile->activateInvalidation();
}
} catch (const std::exception &e) {
reportError(tr("failed to change archive invalidation state: %1").arg(e.what()));
@@ -318,6 +323,6 @@ void ProfilesDialog::on_localSavesBox_stateChanged(int state) void ProfilesDialog::on_transferButton_clicked()
{
const Profile::Ptr currentProfile = m_ProfilesList->currentItem()->data(Qt::UserRole).value<Profile::Ptr>();
- TransferSavesDialog transferDialog(*currentProfile, m_GamePlugin, this);
+ TransferSavesDialog transferDialog(*currentProfile, qApp->property("managed_game").value<IPluginGame*>(), this);
transferDialog.exec();
}
diff --git a/src/profilesdialog.h b/src/profilesdialog.h index 18b3932f..5cb5a449 100644 --- a/src/profilesdialog.h +++ b/src/profilesdialog.h @@ -50,7 +50,7 @@ public: * @param parent parent widget
* @todo the game path could be retrieved from GameInfo just as easily
**/
- explicit ProfilesDialog(const QString &gamePath, MOBase::IPluginGame *gamePlugin, QWidget *parent = 0);
+ explicit ProfilesDialog(const QString &gamePath, QWidget *parent = 0);
~ProfilesDialog();
/**
@@ -91,7 +91,6 @@ private slots: private:
Ui::ProfilesDialog *ui;
- MOBase::IPluginGame *m_GamePlugin;
QString m_GamePath;
QListWidget *m_ProfilesList;
bool m_FailState;
diff --git a/src/selectiondialog.cpp b/src/selectiondialog.cpp index 1b284928..aae95f56 100644 --- a/src/selectiondialog.cpp +++ b/src/selectiondialog.cpp @@ -22,8 +22,8 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include <QCommandLinkButton>
-SelectionDialog::SelectionDialog(const QString &description, QWidget *parent)
- : QDialog(parent), ui(new Ui::SelectionDialog), m_Choice(nullptr), m_ValidateByData(false)
+SelectionDialog::SelectionDialog(const QString &description, QWidget *parent, const QSize &iconSize)
+ : QDialog(parent), ui(new Ui::SelectionDialog), m_Choice(nullptr), m_ValidateByData(false), m_IconSize(iconSize)
{
ui->setupUi(this);
@@ -35,10 +35,24 @@ SelectionDialog::~SelectionDialog() delete ui;
}
-
void SelectionDialog::addChoice(const QString &buttonText, const QString &description, const QVariant &data)
{
- QCommandLinkButton *button = new QCommandLinkButton(buttonText, description, ui->buttonBox);
+ QAbstractButton *button = new QCommandLinkButton(buttonText, description, ui->buttonBox);
+ if (m_IconSize.isValid()) {
+ button->setIconSize(m_IconSize);
+ }
+ button->setProperty("data", data);
+ ui->buttonBox->addButton(button, QDialogButtonBox::AcceptRole);
+ if (data.isValid()) m_ValidateByData = true;
+}
+
+void SelectionDialog::addChoice(const QIcon &icon, const QString &buttonText, const QString &description, const QVariant &data)
+{
+ QAbstractButton *button = new QCommandLinkButton(buttonText, description, ui->buttonBox);
+ if (m_IconSize.isValid()) {
+ button->setIconSize(m_IconSize);
+ }
+ button->setIcon(icon);
button->setProperty("data", data);
ui->buttonBox->addButton(button, QDialogButtonBox::AcceptRole);
if (data.isValid()) m_ValidateByData = true;
@@ -49,7 +63,6 @@ int SelectionDialog::numChoices() const return ui->buttonBox->findChildren<QCommandLinkButton*>(QString()).count();
}
-
QVariant SelectionDialog::getChoiceData()
{
return m_Choice->property("data");
diff --git a/src/selectiondialog.h b/src/selectiondialog.h index fe148859..43ba9767 100644 --- a/src/selectiondialog.h +++ b/src/selectiondialog.h @@ -33,7 +33,7 @@ class SelectionDialog : public QDialog public:
- explicit SelectionDialog(const QString &description, QWidget *parent = 0);
+ explicit SelectionDialog(const QString &description, QWidget *parent = 0, const QSize &iconSize = QSize());
~SelectionDialog();
@@ -46,6 +46,8 @@ public: */
void addChoice(const QString &buttonText, const QString &description, const QVariant &data);
+ void addChoice(const QIcon &icon, const QString &buttonText, const QString &description, const QVariant &data);
+
int numChoices() const;
QVariant getChoiceData();
@@ -62,6 +64,7 @@ private: Ui::SelectionDialog *ui;
QAbstractButton *m_Choice;
bool m_ValidateByData;
+ QSize m_IconSize;
};
diff --git a/src/shared/fallout3info.cpp b/src/shared/fallout3info.cpp index c8688cc4..37238a2a 100644 --- a/src/shared/fallout3info.cpp +++ b/src/shared/fallout3info.cpp @@ -42,11 +42,6 @@ bool Fallout3Info::identifyGame(const std::wstring &searchPath) FileExists(searchPath, L"FalloutLauncher.exe");
}
-unsigned long Fallout3Info::getBSAVersion()
-{
- return 0x68;
-}
-
std::wstring Fallout3Info::getRegPathStatic()
{
HKEY key;
@@ -67,37 +62,6 @@ std::wstring Fallout3Info::getRegPathStatic() }
}
-std::wstring Fallout3Info::getInvalidationBSA()
-{
- return L"Fallout - Invalidation.bsa";
-}
-
-bool Fallout3Info::isInvalidationBSA(const std::wstring &bsaName)
-{
- static LPCWSTR invalidation[] = { L"Fallout - AI!.bsa", L"Fallout - Invalidation.bsa", nullptr };
-
- for (int i = 0; invalidation[i] != nullptr; ++i) {
- if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
- return true;
- }
- }
- return false;
-}
-
-std::vector<std::wstring> Fallout3Info::getPrimaryPlugins()
-{
- return boost::assign::list_of(L"fallout3.esm");
-}
-
-std::vector<std::wstring> Fallout3Info::getVanillaBSAs()
-{
- return boost::assign::list_of (L"Fallout - Textures.bsa")
- (L"Fallout - Meshes.bsa")
- (L"Fallout - Voices.bsa")
- (L"Fallout - Sound.bsa")
- (L"Fallout - MenuVoices.bsa")
- (L"Fallout - Misc.bsa");
-}
std::vector<std::wstring> Fallout3Info::getDLCPlugins()
{
@@ -125,20 +89,14 @@ std::wstring Fallout3Info::getReferenceDataFile() }
-std::wstring Fallout3Info::getOMODExt()
-{
- return L"fomod";
-}
+
std::vector<std::wstring> Fallout3Info::getSteamVariants() const
{
return boost::assign::list_of(L"Regular")(L"Game Of The Year");
}
-std::wstring Fallout3Info::getSEName()
-{
- return L"fose";
-}
+
std::wstring Fallout3Info::getNexusPage(bool nmmScheme)
{
diff --git a/src/shared/fallout3info.h b/src/shared/fallout3info.h index 6a211d4f..1f3a381d 100644 --- a/src/shared/fallout3info.h +++ b/src/shared/fallout3info.h @@ -35,8 +35,6 @@ public: virtual ~Fallout3Info() {}
- virtual unsigned long getBSAVersion();
-
static std::wstring getRegPathStatic();
virtual std::wstring getRegPath() { return getRegPathStatic(); }
virtual std::wstring getBinaryName() { return L"Fallout3.exe"; }
@@ -45,14 +43,38 @@ public: virtual std::wstring getGameName() const { return L"Fallout 3"; }
virtual std::wstring getGameShortName() const { return L"Fallout3"; }
+/*
+ virtual std::wstring getInvalidationBSA()
+ {
+ return L"Fallout - Invalidation.bsa";
+ }
- virtual std::wstring getInvalidationBSA();
+ virtual bool isInvalidationBSA(const std::wstring &bsaName)
+ {
+ static LPCWSTR invalidation[] = { L"Fallout - AI!.bsa", L"Fallout - Invalidation.bsa", nullptr };
- virtual bool isInvalidationBSA(const std::wstring &bsaName);
+ for (int i = 0; invalidation[i] != nullptr; ++i) {
+ if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
+ return true;
+ }
+ }
+ return false;
+ }
- virtual std::vector<std::wstring> getPrimaryPlugins();
+ virtual std::vector<std::wstring> getVanillaBSAs()
+ {
+ return boost::assign::list_of (L"Fallout - Textures.bsa")
+ (L"Fallout - Meshes.bsa")
+ (L"Fallout - Voices.bsa")
+ (L"Fallout - Sound.bsa")
+ (L"Fallout - MenuVoices.bsa")
+ (L"Fallout - Misc.bsa");
+ }
- virtual std::vector<std::wstring> getVanillaBSAs();
+ virtual std::vector<std::wstring> getPrimaryPlugins()
+ {
+ return boost::assign::list_of(L"fallout3.esm");
+ }*/
virtual std::vector<std::wstring> getDLCPlugins();
virtual std::vector<std::wstring> getSavegameAttachmentExtensions();
@@ -60,12 +82,9 @@ public: virtual std::vector<std::wstring> getIniFileNames();
virtual std::wstring getReferenceDataFile();
- virtual std::wstring getOMODExt();
virtual std::vector<std::wstring> getSteamVariants() const;
- virtual std::wstring getSEName();
-
virtual std::wstring getNexusPage(bool nmmScheme = true);
static std::wstring getNexusInfoUrlStatic();
virtual std::wstring getNexusInfoUrl() { return getNexusInfoUrlStatic(); }
diff --git a/src/shared/falloutnvinfo.cpp b/src/shared/falloutnvinfo.cpp index 8e701887..1203bd25 100644 --- a/src/shared/falloutnvinfo.cpp +++ b/src/shared/falloutnvinfo.cpp @@ -43,11 +43,6 @@ bool FalloutNVInfo::identifyGame(const std::wstring &searchPath) FileExists(searchPath, L"FalloutNVLauncher.exe");
}
-unsigned long FalloutNVInfo::getBSAVersion()
-{
- return 0x68;
-}
-
std::wstring FalloutNVInfo::getRegPathStatic()
{
HKEY key;
@@ -68,38 +63,6 @@ std::wstring FalloutNVInfo::getRegPathStatic() }
}
-std::wstring FalloutNVInfo::getInvalidationBSA()
-{
- return L"Fallout - Invalidation.bsa";
-}
-
-bool FalloutNVInfo::isInvalidationBSA(const std::wstring &bsaName)
-{
- static LPCWSTR invalidation[] = { L"Fallout - AI!.bsa", L"Fallout - Invalidation.bsa", nullptr };
-
- for (int i = 0; invalidation[i] != nullptr; ++i) {
- if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
- return true;
- }
- }
- return false;
-}
-
-std::vector<std::wstring> FalloutNVInfo::getPrimaryPlugins()
-{
- return boost::assign::list_of(L"falloutnv.esm");
-}
-
-std::vector<std::wstring> FalloutNVInfo::getVanillaBSAs()
-{
- return boost::assign::list_of (L"Fallout - Textures.bsa")
- (L"Fallout - Textures2.bsa")
- (L"Fallout - Meshes.bsa")
- (L"Fallout - Voices1.bsa")
- (L"Fallout - Sound.bsa")
- (L"Fallout - Misc.bsa");
-}
-
std::vector<std::wstring> FalloutNVInfo::getDLCPlugins()
{
return boost::assign::list_of (L"DeadMoney.esm")
@@ -129,19 +92,6 @@ std::wstring FalloutNVInfo::getReferenceDataFile() return L"Fallout - Meshes.bsa";
}
-
-std::wstring FalloutNVInfo::getOMODExt()
-{
- return L"fomod";
-}
-
-
-std::wstring FalloutNVInfo::getSEName()
-{
- return L"nvse";
-}
-
-
std::wstring FalloutNVInfo::getNexusPage(bool nmmScheme)
{
if (nmmScheme) {
@@ -176,17 +126,4 @@ bool FalloutNVInfo::rerouteToProfile(const wchar_t *fileName, const wchar_t*) return false;
}
-/*
-std::vector<ExecutableInfo> FalloutNVInfo::getExecutables()
-{
- std::vector<ExecutableInfo> result;
- result.push_back(ExecutableInfo(L"NVSE", L"nvse_loader.exe", L"", L"", DEFAULT_CLOSE));
- result.push_back(ExecutableInfo(L"New Vegas", L"falloutnv.exe", L"", L"", DEFAULT_CLOSE));
- result.push_back(ExecutableInfo(L"Fallout Mod Manager", L"fomm/fomm.exe", L"", L"", DEFAULT_CLOSE));
- result.push_back(ExecutableInfo(L"Construction Kit", L"geck.exe", L"", L"", DEFAULT_CLOSE));
- result.push_back(ExecutableInfo(L"Fallout Launcher", L"FalloutNVLauncher.exe", L"", L"", DEFAULT_CLOSE));
- result.push_back(ExecutableInfo(L"BOSS", L"BOSS/BOSS.exe", L"", L"", NEVER_CLOSE));
-
- return result;
-}*/
} // namespace MOShared
diff --git a/src/shared/falloutnvinfo.h b/src/shared/falloutnvinfo.h index 513b7218..e1a614d2 100644 --- a/src/shared/falloutnvinfo.h +++ b/src/shared/falloutnvinfo.h @@ -35,8 +35,6 @@ public: virtual ~FalloutNVInfo() {}
- virtual unsigned long getBSAVersion();
-
static std::wstring getRegPathStatic();
virtual std::wstring getRegPath() { return getRegPathStatic(); }
virtual std::wstring getBinaryName() { return L"FalloutNV.exe"; }
@@ -48,13 +46,37 @@ public: // virtual bool requiresSteam() const { return true; }
- virtual std::wstring getInvalidationBSA();
+/* virtual std::wstring getInvalidationBSA()
+ {
+ return L"Fallout - Invalidation.bsa";
+ }
+
+ virtual bool isInvalidationBSA(const std::wstring &bsaName)
+ {
+ static LPCWSTR invalidation[] = { L"Fallout - AI!.bsa", L"Fallout - Invalidation.bsa", nullptr };
- virtual bool isInvalidationBSA(const std::wstring &bsaName);
+ for (int i = 0; invalidation[i] != nullptr; ++i) {
+ if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
+ return true;
+ }
+ }
+ return false;
+ }
- virtual std::vector<std::wstring> getPrimaryPlugins();
+ virtual std::vector<std::wstring> getVanillaBSAs()
+ {
+ return boost::assign::list_of (L"Fallout - Textures.bsa")
+ (L"Fallout - Textures2.bsa")
+ (L"Fallout - Meshes.bsa")
+ (L"Fallout - Voices1.bsa")
+ (L"Fallout - Sound.bsa")
+ (L"Fallout - Misc.bsa");
+ }
- virtual std::vector<std::wstring> getVanillaBSAs();
+ virtual std::vector<std::wstring> getPrimaryPlugins()
+ {
+ return boost::assign::list_of(L"falloutnv.esm");
+ }*/
virtual std::vector<std::wstring> getDLCPlugins();
virtual std::vector<std::wstring> getSavegameAttachmentExtensions();
@@ -62,9 +84,6 @@ public: virtual std::vector<std::wstring> getIniFileNames();
virtual std::wstring getReferenceDataFile();
- virtual std::wstring getOMODExt();
-
- virtual std::wstring getSEName();
virtual std::wstring getNexusPage(bool nmmScheme = true);
static std::wstring getNexusInfoUrlStatic();
diff --git a/src/shared/gameinfo.h b/src/shared/gameinfo.h index dbb935f6..77ed4d3c 100644 --- a/src/shared/gameinfo.h +++ b/src/shared/gameinfo.h @@ -28,32 +28,7 @@ along with Mod Organizer. If not, see <http://www.gnu.org/licenses/>. #include <Windows.h>
namespace MOShared {
-/*
-enum CloseMOStyle {
- DEFAULT_CLOSE,
- DEFAULT_STAY,
- NEVER_CLOSE
-};
-struct ExecutableInfo {
-
- ExecutableInfo(const std::wstring &aTitle, const std::wstring &aBinary,
- const std::wstring &aArguments, const std::wstring &aWorkingDirectory, CloseMOStyle aCloseMO)
- : title(aTitle), binary(aBinary), arguments(aArguments), workingDirectory(aWorkingDirectory),
- closeMO(aCloseMO), steamAppID(L"") {}
- ExecutableInfo(const std::wstring &aTitle, const std::wstring &aBinary,
- const std::wstring &aArguments, const std::wstring &aWorkingDirectory,
- CloseMOStyle aCloseMO, const std::wstring &aSteamAppID)
- : title(aTitle), binary(aBinary), arguments(aArguments), workingDirectory(aWorkingDirectory),
- closeMO(aCloseMO), steamAppID(aSteamAppID) {}
- std::wstring title;
- std::wstring binary;
- std::wstring arguments;
- std::wstring workingDirectory;
- CloseMOStyle closeMO;
- std::wstring steamAppID;
-};
-*/
/**
Class to manage information that depends on the used game type. The intention is to keep
@@ -86,8 +61,6 @@ public: virtual std::wstring getRegPath() = 0;
virtual std::wstring getBinaryName() = 0;
- virtual unsigned long getBSAVersion() = 0;
-
virtual GameInfo::Type getType() = 0;
virtual std::wstring getGameName() const = 0;
@@ -98,31 +71,9 @@ public: virtual LoadOrderMechanism getLoadOrderMechanism() const { return TYPE_FILETIME; }
virtual std::wstring getGameDirectory() const;
- // get absolute path to the directory where omo stores its mods
-/* virtual std::wstring getModsDir() const;
- // get absolute path to the directory where omo stores its profiles
- virtual std::wstring getProfilesDir() const;
-
- virtual std::wstring getIniFilename() const;
- virtual std::wstring getOverwriteDir() const;
- virtual std::wstring getLogDir() const;
- virtual std::wstring getLootDir() const;
- virtual std::wstring getTutorialDir() const;*/
- virtual bool requiresBSAInvalidation() const { return true; }
virtual bool requiresSteam() const;
- virtual std::wstring getInvalidationBSA() = 0;
-
- virtual bool isInvalidationBSA(const std::wstring &bsaName) = 0;
-
- // the key in the game's ini-file that defines the list of bsas to load
- virtual std::wstring archiveListKey() = 0;
-
- virtual std::vector<std::wstring> getPrimaryPlugins() = 0;
-
- virtual std::vector<std::wstring> getVanillaBSAs() = 0;
-
// get a list of file extensions for additional files belonging to a save game
virtual std::vector<std::wstring> getSavegameAttachmentExtensions() = 0;
@@ -134,12 +85,8 @@ public: virtual std::wstring getReferenceDataFile() = 0;
- virtual std::wstring getOMODExt() = 0;
-
virtual std::vector<std::wstring> getSteamVariants() const;
- virtual std::wstring getSEName() = 0;
-
virtual std::wstring getNexusPage(bool nmmScheme = true) = 0;
virtual std::wstring getNexusInfoUrl() = 0;
virtual int getNexusModID() = 0;
diff --git a/src/shared/oblivioninfo.cpp b/src/shared/oblivioninfo.cpp index c945dcf4..16748f58 100644 --- a/src/shared/oblivioninfo.cpp +++ b/src/shared/oblivioninfo.cpp @@ -43,11 +43,6 @@ bool OblivionInfo::identifyGame(const std::wstring &searchPath) FileExists(searchPath, L"OblivionLauncher.exe");
}
-unsigned long OblivionInfo::getBSAVersion()
-{
- return 0x67;
-}
-
std::wstring OblivionInfo::getRegPathStatic()
{
HKEY key;
@@ -68,39 +63,14 @@ std::wstring OblivionInfo::getRegPathStatic() }
}
-std::wstring OblivionInfo::getInvalidationBSA()
-{
- return L"Oblivion - Invalidation.bsa";
-}
-bool OblivionInfo::isInvalidationBSA(const std::wstring &bsaName)
-{
- static LPCWSTR invalidation[] = { L"Oblivion - Invalidation.bsa", L"ArchiveInvalidationInvalidated!.bsa",
- L"BSARedirection.bsa", nullptr };
- for (int i = 0; invalidation[i] != nullptr; ++i) {
- if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
- return true;
- }
- }
- return false;
-}
-std::vector<std::wstring> OblivionInfo::getPrimaryPlugins()
-{
- return boost::assign::list_of(L"oblivion.esm");
-}
-std::vector<std::wstring> OblivionInfo::getVanillaBSAs()
-{
- return boost::assign::list_of(L"Oblivion - Meshes.bsa")
- (L"Oblivion - Textures - Compressed.bsa")
- (L"Oblivion - Sounds.bsa")
- (L"Oblivion - Voices1.bsa")
- (L"Oblivion - Voices2.bsa")
- (L"Oblivion - Misc.bsa");
-}
+
+
+
std::vector<std::wstring> OblivionInfo::getDLCPlugins()
@@ -131,10 +101,7 @@ std::vector<std::wstring> OblivionInfo::getIniFileNames() }
-std::wstring OblivionInfo::getSEName()
-{
- return L"obse";
-}
+
std::wstring OblivionInfo::getNexusPage(bool nmmScheme)
@@ -175,11 +142,4 @@ std::wstring OblivionInfo::getReferenceDataFile() return L"Oblivion - Meshes.bsa";
}
-
-std::wstring OblivionInfo::getOMODExt()
-{
- return L"omod";
-}
-
-
} // namespace MOShared
diff --git a/src/shared/oblivioninfo.h b/src/shared/oblivioninfo.h index a93f510e..87ba26ff 100644 --- a/src/shared/oblivioninfo.h +++ b/src/shared/oblivioninfo.h @@ -33,8 +33,6 @@ public: virtual ~OblivionInfo() {}
- virtual unsigned long getBSAVersion();
-
static std::wstring getRegPathStatic();
virtual std::wstring getRegPath() { return getRegPathStatic(); }
virtual std::wstring getBinaryName() { return L"Oblivion.exe"; }
@@ -43,14 +41,40 @@ public: virtual std::wstring getGameName() const { return L"Oblivion"; }
virtual std::wstring getGameShortName() const { return L"Oblivion"; }
+/*
+ virtual std::wstring getInvalidationBSA()
+ {
+ return L"Oblivion - Invalidation.bsa";
+ }
- virtual std::wstring getInvalidationBSA();
+ virtual bool isInvalidationBSA(const std::wstring &bsaName)
+ {
+ static LPCWSTR invalidation[] = { L"Oblivion - Invalidation.bsa", L"ArchiveInvalidationInvalidated!.bsa",
+ L"BSARedirection.bsa", nullptr };
- virtual bool isInvalidationBSA(const std::wstring &bsaName);
+ for (int i = 0; invalidation[i] != nullptr; ++i) {
+ if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
+ return true;
+ }
+ }
+ return false;
+ }
- virtual std::vector<std::wstring> getPrimaryPlugins();
+ virtual std::vector<std::wstring> getVanillaBSAs()
+ {
+ return boost::assign::list_of(L"Oblivion - Meshes.bsa")
+ (L"Oblivion - Textures - Compressed.bsa")
+ (L"Oblivion - Sounds.bsa")
+ (L"Oblivion - Voices1.bsa")
+ (L"Oblivion - Voices2.bsa")
+ (L"Oblivion - Misc.bsa");
+ }
+
+ virtual std::vector<std::wstring> getPrimaryPlugins()
+ {
+ return boost::assign::list_of(L"oblivion.esm");
+ }*/
- virtual std::vector<std::wstring> getVanillaBSAs();
virtual std::vector<std::wstring> getDLCPlugins();
virtual std::vector<std::wstring> getSavegameAttachmentExtensions();
@@ -58,9 +82,6 @@ public: virtual std::vector<std::wstring> getIniFileNames();
virtual std::wstring getReferenceDataFile();
- virtual std::wstring getOMODExt();
-
- virtual std::wstring getSEName();
virtual std::wstring getNexusPage(bool nmmScheme = true);
static std::wstring getNexusInfoUrlStatic();
diff --git a/src/shared/skyriminfo.cpp b/src/shared/skyriminfo.cpp index feaf88a3..f66fcef4 100644 --- a/src/shared/skyriminfo.cpp +++ b/src/shared/skyriminfo.cpp @@ -50,10 +50,7 @@ bool SkyrimInfo::identifyGame(const std::wstring &searchPath) FileExists(searchPath, L"SkyrimLauncher.exe");
}
-unsigned long SkyrimInfo::getBSAVersion()
-{
- return 0x68;
-}
+
std::wstring SkyrimInfo::getRegPathStatic()
@@ -76,25 +73,6 @@ std::wstring SkyrimInfo::getRegPathStatic() }
}
-
-std::wstring SkyrimInfo::getInvalidationBSA()
-{
- return L"Skyrim - Invalidation.bsa";
-}
-
-bool SkyrimInfo::isInvalidationBSA(const std::wstring &bsaName)
-{
- static LPCWSTR invalidation[] = { L"Skyrim - Invalidation.bsa", nullptr };
-
- for (int i = 0; invalidation[i] != nullptr; ++i) {
- if (wcscmp(bsaName.c_str(), invalidation[i]) == 0) {
- return true;
- }
- }
- return false;
-}
-
-
GameInfo::LoadOrderMechanism SkyrimInfo::getLoadOrderMechanism() const
{
std::wstring fileName = getGameDirectory() + L"\\TESV.exe";
@@ -113,27 +91,6 @@ GameInfo::LoadOrderMechanism SkyrimInfo::getLoadOrderMechanism() const }
}
-std::vector<std::wstring> SkyrimInfo::getPrimaryPlugins()
-{
- return boost::assign::list_of(L"skyrim.esm")(L"update.esm");
-}
-
-std::vector<std::wstring> SkyrimInfo::getVanillaBSAs()
-{
- return boost::assign::list_of(L"Skyrim - Misc.bsa")
- (L"Skyrim - Shaders.bsa")
- (L"Skyrim - Textures.bsa")
- (L"HighResTexturePack01.bsa")
- (L"HighResTexturePack02.bsa")
- (L"HighResTexturePack03.bsa")
- (L"Skyrim - Interface.bsa")
- (L"Skyrim - Animations.bsa")
- (L"Skyrim - Meshes.bsa")
- (L"Skyrim - Sounds.bsa")
- (L"Skyrim - Voices.bsa")
- (L"Skyrim - VoicesExtra.bsa");
-}
-
std::vector<std::wstring> SkyrimInfo::getDLCPlugins()
{
return boost::assign::list_of (L"Dawnguard.esm")
@@ -161,17 +118,6 @@ std::wstring SkyrimInfo::getReferenceDataFile() }
-std::wstring SkyrimInfo::getOMODExt()
-{
- return L"fomod";
-}
-
-std::wstring SkyrimInfo::getSEName()
-{
- return L"skse";
-}
-
-
std::wstring SkyrimInfo::getNexusPage(bool nmmScheme)
{
if (nmmScheme) {
diff --git a/src/shared/skyriminfo.h b/src/shared/skyriminfo.h index bf08fb25..5951f910 100644 --- a/src/shared/skyriminfo.h +++ b/src/shared/skyriminfo.h @@ -35,8 +35,6 @@ public: virtual ~SkyrimInfo() {}
- virtual unsigned long getBSAVersion();
-
static std::wstring getRegPathStatic();
virtual std::wstring getRegPath() { return getRegPathStatic(); }
virtual std::wstring getBinaryName() { return L"TESV.exe"; }
@@ -48,15 +46,6 @@ public: virtual LoadOrderMechanism getLoadOrderMechanism() const;
- virtual bool requiresBSAInvalidation() const { return true; }
-
- virtual std::wstring getInvalidationBSA();
-
- virtual bool isInvalidationBSA(const std::wstring &bsaName);
-
- virtual std::vector<std::wstring> getPrimaryPlugins();
-
- virtual std::vector<std::wstring> getVanillaBSAs();
virtual std::vector<std::wstring> getDLCPlugins();
virtual std::vector<std::wstring> getSavegameAttachmentExtensions();
@@ -65,9 +54,6 @@ public: virtual std::vector<std::wstring> getIniFileNames();
virtual std::wstring getReferenceDataFile();
- virtual std::wstring getOMODExt();
-
- virtual std::wstring getSEName();
virtual std::wstring getNexusPage(bool nmmScheme = true);
@@ -80,8 +66,6 @@ public: virtual bool rerouteToProfile(const wchar_t *fileName, const wchar_t *fullPath);
- virtual std::wstring archiveListKey() { return L"SResourceArchiveList"; }
-
private:
SkyrimInfo(const std::wstring &moDirectory, const std::wstring &moDataDirectory, const std::wstring &gameDirectory);
|
