Merge branch 'develop' of https://github.com/PrismLauncher/PrismLauncher into disablemods
Signed-off-by: Trial97 <alexandru.tripon97@gmail.com>
This commit is contained in:
@@ -41,7 +41,7 @@ Task::Ptr ModrinthAPI::currentVersions(const QStringList& hashes, QString hash_f
|
||||
Task::Ptr ModrinthAPI::latestVersion(QString hash,
|
||||
QString hash_format,
|
||||
std::optional<std::list<Version>> mcVersions,
|
||||
std::optional<ModLoaderTypes> loaders,
|
||||
std::optional<ModPlatform::ModLoaderTypes> loaders,
|
||||
std::shared_ptr<QByteArray> response)
|
||||
{
|
||||
auto netJob = makeShared<NetJob>(QString("Modrinth::GetLatestVersion"), APPLICATION->network());
|
||||
@@ -71,7 +71,7 @@ Task::Ptr ModrinthAPI::latestVersion(QString hash,
|
||||
Task::Ptr ModrinthAPI::latestVersions(const QStringList& hashes,
|
||||
QString hash_format,
|
||||
std::optional<std::list<Version>> mcVersions,
|
||||
std::optional<ModLoaderTypes> loaders,
|
||||
std::optional<ModPlatform::ModLoaderTypes> loaders,
|
||||
std::shared_ptr<QByteArray> response)
|
||||
{
|
||||
auto netJob = makeShared<NetJob>(QString("Modrinth::GetLatestVersions"), APPLICATION->network());
|
||||
|
||||
@@ -19,13 +19,13 @@ class ModrinthAPI : public NetworkResourceAPI {
|
||||
auto latestVersion(QString hash,
|
||||
QString hash_format,
|
||||
std::optional<std::list<Version>> mcVersions,
|
||||
std::optional<ModLoaderTypes> loaders,
|
||||
std::optional<ModPlatform::ModLoaderTypes> loaders,
|
||||
std::shared_ptr<QByteArray> response) -> Task::Ptr;
|
||||
|
||||
auto latestVersions(const QStringList& hashes,
|
||||
QString hash_format,
|
||||
std::optional<std::list<Version>> mcVersions,
|
||||
std::optional<ModLoaderTypes> loaders,
|
||||
std::optional<ModPlatform::ModLoaderTypes> loaders,
|
||||
std::shared_ptr<QByteArray> response) -> Task::Ptr;
|
||||
|
||||
Task::Ptr getProjects(QStringList addonIds, std::shared_ptr<QByteArray> response) const override;
|
||||
@@ -35,20 +35,19 @@ class ModrinthAPI : public NetworkResourceAPI {
|
||||
|
||||
inline auto getAuthorURL(const QString& name) const -> QString { return "https://modrinth.com/user/" + name; };
|
||||
|
||||
static auto getModLoaderStrings(const ModLoaderTypes types) -> const QStringList
|
||||
static auto getModLoaderStrings(const ModPlatform::ModLoaderTypes types) -> const QStringList
|
||||
{
|
||||
QStringList l;
|
||||
for (auto loader : { Forge, Fabric, Quilt, LiteLoader }) {
|
||||
for (auto loader :
|
||||
{ ModPlatform::NeoForge, ModPlatform::Forge, ModPlatform::Fabric, ModPlatform::Quilt, ModPlatform::LiteLoader }) {
|
||||
if (types & loader) {
|
||||
l << getModLoaderString(loader);
|
||||
}
|
||||
}
|
||||
if ((types & Quilt) && (~types & Fabric)) // Add Fabric if Quilt is in use, if Fabric isn't already there
|
||||
l << getModLoaderString(Fabric);
|
||||
return l;
|
||||
}
|
||||
|
||||
static auto getModLoaderFilters(ModLoaderTypes types) -> const QString
|
||||
static auto getModLoaderFilters(ModPlatform::ModLoaderTypes types) -> const QString
|
||||
{
|
||||
QStringList l;
|
||||
for (auto loader : getModLoaderStrings(types)) {
|
||||
@@ -141,7 +140,10 @@ class ModrinthAPI : public NetworkResourceAPI {
|
||||
return s.isEmpty() ? QString() : s;
|
||||
}
|
||||
|
||||
static inline auto validateModLoaders(ModLoaderTypes loaders) -> bool { return loaders & (Forge | Fabric | Quilt | LiteLoader); }
|
||||
static inline auto validateModLoaders(ModPlatform::ModLoaderTypes loaders) -> bool
|
||||
{
|
||||
return loaders & (ModPlatform::NeoForge | ModPlatform::Forge | ModPlatform::Fabric | ModPlatform::Quilt | ModPlatform::LiteLoader);
|
||||
}
|
||||
|
||||
[[nodiscard]] std::optional<QString> getDependencyURL(DependencySearchArgs const& args) const override
|
||||
{
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
#include "tasks/ConcurrentTask.h"
|
||||
|
||||
#include "minecraft/mod/ModFolderModel.h"
|
||||
#include "minecraft/mod/ResourceFolderModel.h"
|
||||
|
||||
static ModrinthAPI api;
|
||||
static ModPlatform::ProviderCapabilities ProviderCaps;
|
||||
@@ -39,7 +38,7 @@ void ModrinthCheckUpdate::executeTask()
|
||||
QStringList hashes;
|
||||
auto best_hash_type = ProviderCaps.hashType(ModPlatform::ResourceProvider::MODRINTH).first();
|
||||
|
||||
ConcurrentTask hashing_task(this, "MakeModrinthHashesTask", 10);
|
||||
ConcurrentTask hashing_task(this, "MakeModrinthHashesTask", APPLICATION->settings()->get("NumberOfConcurrentTasks").toInt());
|
||||
for (auto* mod : m_mods) {
|
||||
auto hash = mod->metadata()->hash;
|
||||
|
||||
@@ -106,11 +105,11 @@ void ModrinthCheckUpdate::executeTask()
|
||||
// so we may want to filter it
|
||||
QString loader_filter;
|
||||
if (m_loaders.has_value()) {
|
||||
static auto flags = { ResourceAPI::ModLoaderType::Forge, ResourceAPI::ModLoaderType::Fabric,
|
||||
ResourceAPI::ModLoaderType::Quilt };
|
||||
static auto flags = { ModPlatform::ModLoaderType::NeoForge, ModPlatform::ModLoaderType::Forge,
|
||||
ModPlatform::ModLoaderType::Fabric, ModPlatform::ModLoaderType::Quilt };
|
||||
for (auto flag : flags) {
|
||||
if (m_loaders.value().testFlag(flag)) {
|
||||
loader_filter = api.getModLoaderString(flag);
|
||||
loader_filter = ModPlatform::getModLoaderString(flag);
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -140,26 +139,27 @@ void ModrinthCheckUpdate::executeTask()
|
||||
auto mod = *mod_iter;
|
||||
|
||||
auto key = project_ver.hash;
|
||||
|
||||
// Fake pack with the necessary info to pass to the download task :)
|
||||
auto pack = std::make_shared<ModPlatform::IndexedPack>();
|
||||
pack->name = mod->name();
|
||||
pack->slug = mod->metadata()->slug;
|
||||
pack->addonId = mod->metadata()->project_id;
|
||||
pack->websiteUrl = mod->homeurl();
|
||||
for (auto& author : mod->authors())
|
||||
pack->authors.append({ author });
|
||||
pack->description = mod->description();
|
||||
pack->provider = ModPlatform::ResourceProvider::MODRINTH;
|
||||
if ((key != hash && project_ver.is_preferred) || (mod->status() == ModStatus::NotInstalled)) {
|
||||
if (mod->version() == project_ver.version_number)
|
||||
continue;
|
||||
|
||||
// Fake pack with the necessary info to pass to the download task :)
|
||||
auto pack = std::make_shared<ModPlatform::IndexedPack>();
|
||||
pack->name = mod->name();
|
||||
pack->slug = mod->metadata()->slug;
|
||||
pack->addonId = mod->metadata()->project_id;
|
||||
pack->websiteUrl = mod->homeurl();
|
||||
for (auto& author : mod->authors())
|
||||
pack->authors.append({ author });
|
||||
pack->description = mod->description();
|
||||
pack->provider = ModPlatform::ResourceProvider::MODRINTH;
|
||||
|
||||
auto download_task = makeShared<ResourceDownloadTask>(pack, project_ver, m_mods_folder);
|
||||
|
||||
m_updatable.emplace_back(pack->name, hash, mod->version(), project_ver.version_number, project_ver.changelog,
|
||||
mod->enabled(), ModPlatform::ResourceProvider::MODRINTH, download_task);
|
||||
m_updatable.emplace_back(pack->name, hash, mod->version(), project_ver.version_number, project_ver.version_type,
|
||||
project_ver.changelog, mod->enabled(), ModPlatform::ResourceProvider::MODRINTH, download_task);
|
||||
}
|
||||
m_deps.append(std::make_shared<GetModDependenciesTask::PackDependency>(pack, project_ver));
|
||||
}
|
||||
} catch (Json::JsonException& e) {
|
||||
failed(e.cause() + " : " + e.what());
|
||||
|
||||
@@ -10,7 +10,7 @@ class ModrinthCheckUpdate : public CheckUpdateTask {
|
||||
public:
|
||||
ModrinthCheckUpdate(QList<Mod*>& mods,
|
||||
std::list<Version>& mcVersions,
|
||||
std::optional<ResourceAPI::ModLoaderTypes> loaders,
|
||||
std::optional<ModPlatform::ModLoaderTypes> loaders,
|
||||
std::shared_ptr<ModFolderModel> mods_folder)
|
||||
: CheckUpdateTask(mods, mcVersions, loaders, mods_folder)
|
||||
{}
|
||||
|
||||
@@ -211,6 +211,8 @@ bool ModrinthCreationTask::createInstance()
|
||||
components->setComponentVersion("org.quiltmc.quilt-loader", m_quilt_version);
|
||||
if (!m_forge_version.isEmpty())
|
||||
components->setComponentVersion("net.minecraftforge", m_forge_version);
|
||||
if (!m_neoForge_version.isEmpty())
|
||||
components->setComponentVersion("net.neoforged", m_neoForge_version);
|
||||
|
||||
if (m_instIcon != "default") {
|
||||
instance.setIconKey(m_instIcon);
|
||||
@@ -398,6 +400,8 @@ bool ModrinthCreationTask::parseManifest(const QString& index_path,
|
||||
m_quilt_version = Json::requireString(*it, "Quilt Loader version");
|
||||
} else if (name == "forge") {
|
||||
m_forge_version = Json::requireString(*it, "Forge version");
|
||||
} else if (name == "neoforge") {
|
||||
m_neoForge_version = Json::requireString(*it, "NeoForge version");
|
||||
} else {
|
||||
throw JSONValidationError("Unknown dependency type: " + name);
|
||||
}
|
||||
|
||||
@@ -39,7 +39,7 @@ class ModrinthCreationTask final : public InstanceCreationTask {
|
||||
private:
|
||||
QWidget* m_parent = nullptr;
|
||||
|
||||
QString m_minecraft_version, m_fabric_version, m_quilt_version, m_forge_version;
|
||||
QString m_minecraft_version, m_fabric_version, m_quilt_version, m_forge_version, m_neoForge_version;
|
||||
QString m_managed_id, m_managed_version_id, m_managed_name;
|
||||
|
||||
std::vector<Modrinth::File> m_files;
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
#include "Json.h"
|
||||
#include "MMCZip.h"
|
||||
#include "minecraft/PackProfile.h"
|
||||
#include "minecraft/mod/MetadataHandler.h"
|
||||
#include "minecraft/mod/ModFolderModel.h"
|
||||
|
||||
const QStringList ModrinthPackExportTask::PREFIXES({ "mods/", "coremods/", "resourcepacks/", "texturepacks/", "shaderpacks/" });
|
||||
@@ -33,12 +34,14 @@ const QStringList ModrinthPackExportTask::FILE_EXTENSIONS({ "jar", "litemod", "z
|
||||
ModrinthPackExportTask::ModrinthPackExportTask(const QString& name,
|
||||
const QString& version,
|
||||
const QString& summary,
|
||||
bool optionalFiles,
|
||||
InstancePtr instance,
|
||||
const QString& output,
|
||||
MMCZip::FilterFunction filter)
|
||||
: name(name)
|
||||
, version(version)
|
||||
, summary(summary)
|
||||
, optionalFiles(optionalFiles)
|
||||
, instance(instance)
|
||||
, mcInstance(dynamic_cast<MinecraftInstance*>(instance.get()))
|
||||
, gameRoot(instance->gameRoot())
|
||||
@@ -127,7 +130,8 @@ void ModrinthPackExportTask::collectHashes()
|
||||
QCryptographicHash sha1(QCryptographicHash::Algorithm::Sha1);
|
||||
sha1.addData(data);
|
||||
|
||||
ResolvedFile resolvedFile{ sha1.result().toHex(), sha512.result().toHex(), url.toEncoded(), openFile.size() };
|
||||
ResolvedFile resolvedFile{ sha1.result().toHex(), sha512.result().toHex(), url.toEncoded(), openFile.size(),
|
||||
mod->metadata()->side };
|
||||
resolvedFiles[relative] = resolvedFile;
|
||||
|
||||
// nice! we've managed to resolve based on local metadata!
|
||||
@@ -245,6 +249,7 @@ QByteArray ModrinthPackExportTask::generateIndex()
|
||||
const ComponentPtr quilt = profile->getComponent("org.quiltmc.quilt-loader");
|
||||
const ComponentPtr fabric = profile->getComponent("net.fabricmc.fabric-loader");
|
||||
const ComponentPtr forge = profile->getComponent("net.minecraftforge");
|
||||
const ComponentPtr neoForge = profile->getComponent("net.neoforged");
|
||||
|
||||
// convert all available components to mrpack dependencies
|
||||
QJsonObject dependencies;
|
||||
@@ -256,6 +261,8 @@ QByteArray ModrinthPackExportTask::generateIndex()
|
||||
dependencies["fabric-loader"] = fabric->m_version;
|
||||
if (forge != nullptr)
|
||||
dependencies["forge"] = forge->m_version;
|
||||
if (neoForge != nullptr)
|
||||
dependencies["neoforge"] = neoForge->m_version;
|
||||
|
||||
out["dependencies"] = dependencies;
|
||||
}
|
||||
@@ -267,20 +274,33 @@ QByteArray ModrinthPackExportTask::generateIndex()
|
||||
QString path = iterator.key();
|
||||
const ResolvedFile& value = iterator.value();
|
||||
|
||||
QJsonObject env;
|
||||
|
||||
// detect disabled mod
|
||||
const QFileInfo pathInfo(path);
|
||||
if (pathInfo.suffix() == "disabled") {
|
||||
if (optionalFiles && pathInfo.suffix() == "disabled") {
|
||||
// rename it
|
||||
path = pathInfo.dir().filePath(pathInfo.completeBaseName());
|
||||
// ...and make it optional
|
||||
QJsonObject env;
|
||||
env["client"] = "optional";
|
||||
env["server"] = "optional";
|
||||
fileOut["env"] = env;
|
||||
} else {
|
||||
env["client"] = "required";
|
||||
env["server"] = "required";
|
||||
}
|
||||
switch (iterator->side) {
|
||||
case Metadata::ModSide::ClientSide:
|
||||
env["server"] = "unsupported";
|
||||
break;
|
||||
case Metadata::ModSide::ServerSide:
|
||||
env["client"] = "unsupported";
|
||||
break;
|
||||
case Metadata::ModSide::UniversalSide:
|
||||
break;
|
||||
}
|
||||
fileOut["env"] = env;
|
||||
|
||||
fileOut["path"] = path;
|
||||
fileOut["downloads"] = QJsonArray{ iterator.value().url };
|
||||
fileOut["downloads"] = QJsonArray{ iterator->url };
|
||||
|
||||
QJsonObject hashes;
|
||||
hashes["sha1"] = value.sha1;
|
||||
|
||||
@@ -31,6 +31,7 @@ class ModrinthPackExportTask : public Task {
|
||||
ModrinthPackExportTask(const QString& name,
|
||||
const QString& version,
|
||||
const QString& summary,
|
||||
bool optionalFiles,
|
||||
InstancePtr instance,
|
||||
const QString& output,
|
||||
MMCZip::FilterFunction filter);
|
||||
@@ -43,6 +44,7 @@ class ModrinthPackExportTask : public Task {
|
||||
struct ResolvedFile {
|
||||
QString sha1, sha512, url;
|
||||
qint64 size;
|
||||
Metadata::ModSide side;
|
||||
};
|
||||
|
||||
static const QStringList PREFIXES;
|
||||
@@ -50,6 +52,7 @@ class ModrinthPackExportTask : public Task {
|
||||
|
||||
// inputs
|
||||
const QString name, version, summary;
|
||||
const bool optionalFiles;
|
||||
const InstancePtr instance;
|
||||
MinecraftInstance* mcInstance;
|
||||
const QDir gameRoot;
|
||||
|
||||
@@ -27,6 +27,11 @@
|
||||
static ModrinthAPI api;
|
||||
static ModPlatform::ProviderCapabilities ProviderCaps;
|
||||
|
||||
bool shouldDownloadOnSide(QString side)
|
||||
{
|
||||
return side == "required" || side == "optional";
|
||||
}
|
||||
|
||||
// https://docs.modrinth.com/api-spec/#tag/projects/operation/getProject
|
||||
void Modrinth::loadIndexedPack(ModPlatform::IndexedPack& pack, QJsonObject& obj)
|
||||
{
|
||||
@@ -53,6 +58,17 @@ void Modrinth::loadIndexedPack(ModPlatform::IndexedPack& pack, QJsonObject& obj)
|
||||
modAuthor.url = api.getAuthorURL(modAuthor.name);
|
||||
pack.authors.append(modAuthor);
|
||||
|
||||
auto client = shouldDownloadOnSide(Json::ensureString(obj, "client_side"));
|
||||
auto server = shouldDownloadOnSide(Json::ensureString(obj, "server_side"));
|
||||
|
||||
if (server && client) {
|
||||
pack.side = "both";
|
||||
} else if (server) {
|
||||
pack.side = "server";
|
||||
} else if (client) {
|
||||
pack.side = "client";
|
||||
}
|
||||
|
||||
// Modrinth can have more data than what's provided by the basic search :)
|
||||
pack.extraDataLoaded = false;
|
||||
}
|
||||
@@ -93,19 +109,19 @@ void Modrinth::loadExtraPackData(ModPlatform::IndexedPack& pack, QJsonObject& ob
|
||||
pack.extraDataLoaded = true;
|
||||
}
|
||||
|
||||
void Modrinth::loadIndexedPackVersions(ModPlatform::IndexedPack& pack,
|
||||
QJsonArray& arr,
|
||||
[[maybe_unused]] const shared_qobject_ptr<QNetworkAccessManager>& network,
|
||||
const BaseInstance* inst)
|
||||
void Modrinth::loadIndexedPackVersions(ModPlatform::IndexedPack& pack, QJsonArray& arr, const BaseInstance* inst)
|
||||
{
|
||||
QVector<ModPlatform::IndexedVersion> unsortedVersions;
|
||||
QString mcVersion = (static_cast<const MinecraftInstance*>(inst))->getPackProfile()->getComponentVersion("net.minecraft");
|
||||
auto profile = (dynamic_cast<const MinecraftInstance*>(inst))->getPackProfile();
|
||||
QString mcVersion = profile->getComponentVersion("net.minecraft");
|
||||
auto loaders = profile->getSupportedModLoaders();
|
||||
|
||||
for (auto versionIter : arr) {
|
||||
auto obj = versionIter.toObject();
|
||||
auto file = loadIndexedPackVersion(obj);
|
||||
|
||||
if (file.fileId.isValid()) // Heuristic to check if the returned value is valid
|
||||
if (file.fileId.isValid() &&
|
||||
(!loaders.has_value() || !file.loaders || loaders.value() & file.loaders)) // Heuristic to check if the returned value is valid
|
||||
unsortedVersions.append(file);
|
||||
}
|
||||
auto orderSortPredicate = [](const ModPlatform::IndexedVersion& a, const ModPlatform::IndexedVersion& b) -> bool {
|
||||
@@ -134,10 +150,23 @@ auto Modrinth::loadIndexedPackVersion(QJsonObject& obj, QString preferred_hash_t
|
||||
}
|
||||
auto loaders = Json::requireArray(obj, "loaders");
|
||||
for (auto loader : loaders) {
|
||||
file.loaders.append(loader.toString());
|
||||
if (loader == "neoforge")
|
||||
file.loaders |= ModPlatform::NeoForge;
|
||||
if (loader == "forge")
|
||||
file.loaders |= ModPlatform::Forge;
|
||||
if (loader == "cauldron")
|
||||
file.loaders |= ModPlatform::Cauldron;
|
||||
if (loader == "liteloader")
|
||||
file.loaders |= ModPlatform::LiteLoader;
|
||||
if (loader == "fabric")
|
||||
file.loaders |= ModPlatform::Fabric;
|
||||
if (loader == "quilt")
|
||||
file.loaders |= ModPlatform::Quilt;
|
||||
}
|
||||
file.version = Json::requireString(obj, "name");
|
||||
file.version_number = Json::requireString(obj, "version_number");
|
||||
file.version_type = ModPlatform::IndexedVersionType(Json::requireString(obj, "version_type"));
|
||||
|
||||
file.changelog = Json::requireString(obj, "changelog");
|
||||
|
||||
auto dependencies = Json::ensureArray(obj, "dependencies");
|
||||
@@ -218,15 +247,20 @@ auto Modrinth::loadIndexedPackVersion(QJsonObject& obj, QString preferred_hash_t
|
||||
return {};
|
||||
}
|
||||
|
||||
auto Modrinth::loadDependencyVersions([[maybe_unused]] const ModPlatform::Dependency& m, QJsonArray& arr) -> ModPlatform::IndexedVersion
|
||||
auto Modrinth::loadDependencyVersions([[maybe_unused]] const ModPlatform::Dependency& m, QJsonArray& arr, const BaseInstance* inst)
|
||||
-> ModPlatform::IndexedVersion
|
||||
{
|
||||
QVector<ModPlatform::IndexedVersion> versions;
|
||||
auto profile = (dynamic_cast<const MinecraftInstance*>(inst))->getPackProfile();
|
||||
QString mcVersion = profile->getComponentVersion("net.minecraft");
|
||||
auto loaders = profile->getSupportedModLoaders();
|
||||
|
||||
QVector<ModPlatform::IndexedVersion> versions;
|
||||
for (auto versionIter : arr) {
|
||||
auto obj = versionIter.toObject();
|
||||
auto file = loadIndexedPackVersion(obj);
|
||||
|
||||
if (file.fileId.isValid()) // Heuristic to check if the returned value is valid
|
||||
if (file.fileId.isValid() &&
|
||||
(!loaders.has_value() || !file.loaders || loaders.value() & file.loaders)) // Heuristic to check if the returned value is valid
|
||||
versions.append(file);
|
||||
}
|
||||
auto orderSortPredicate = [](const ModPlatform::IndexedVersion& a, const ModPlatform::IndexedVersion& b) -> bool {
|
||||
|
||||
@@ -26,11 +26,8 @@ namespace Modrinth {
|
||||
|
||||
void loadIndexedPack(ModPlatform::IndexedPack& m, QJsonObject& obj);
|
||||
void loadExtraPackData(ModPlatform::IndexedPack& m, QJsonObject& obj);
|
||||
void loadIndexedPackVersions(ModPlatform::IndexedPack& pack,
|
||||
QJsonArray& arr,
|
||||
const shared_qobject_ptr<QNetworkAccessManager>& network,
|
||||
const BaseInstance* inst);
|
||||
void loadIndexedPackVersions(ModPlatform::IndexedPack& pack, QJsonArray& arr, const BaseInstance* inst);
|
||||
auto loadIndexedPackVersion(QJsonObject& obj, QString hash_type = "sha512", QString filename_prefer = "") -> ModPlatform::IndexedVersion;
|
||||
auto loadDependencyVersions(const ModPlatform::Dependency& m, QJsonArray& arr) -> ModPlatform::IndexedVersion;
|
||||
auto loadDependencyVersions(const ModPlatform::Dependency& m, QJsonArray& arr, const BaseInstance* inst) -> ModPlatform::IndexedVersion;
|
||||
|
||||
} // namespace Modrinth
|
||||
|
||||
@@ -111,8 +111,9 @@ void loadIndexedVersions(Modpack& pack, QJsonDocument& doc)
|
||||
unsortedVersions.append(file);
|
||||
}
|
||||
auto orderSortPredicate = [](const ModpackVersion& a, const ModpackVersion& b) -> bool {
|
||||
bool a_better_release = a.version_type <= b.version_type;
|
||||
// dates are in RFC 3339 format
|
||||
return a.date > b.date;
|
||||
return a.date > b.date && a_better_release;
|
||||
};
|
||||
|
||||
std::sort(unsortedVersions.begin(), unsortedVersions.end(), orderSortPredicate);
|
||||
@@ -128,6 +129,7 @@ auto loadIndexedVersion(QJsonObject& obj) -> ModpackVersion
|
||||
|
||||
file.name = Json::requireString(obj, "name");
|
||||
file.version = Json::requireString(obj, "version_number");
|
||||
file.version_type = ModPlatform::IndexedVersionType(Json::requireString(obj, "version_type"));
|
||||
file.changelog = Json::ensureString(obj, "changelog");
|
||||
|
||||
file.id = Json::requireString(obj, "id");
|
||||
|
||||
@@ -45,6 +45,8 @@
|
||||
#include <QUrl>
|
||||
#include <QVector>
|
||||
|
||||
#include "modplatform/ModIndex.h"
|
||||
|
||||
class MinecraftInstance;
|
||||
|
||||
namespace Modrinth {
|
||||
@@ -79,6 +81,7 @@ struct ModpackExtra {
|
||||
struct ModpackVersion {
|
||||
QString name;
|
||||
QString version;
|
||||
ModPlatform::IndexedVersionType version_type;
|
||||
QString changelog;
|
||||
|
||||
QString id;
|
||||
|
||||
Reference in New Issue
Block a user