fix: parse world_gen_settings.dat for seed (#5071)

This commit is contained in:
Alexandru Ionut Tripon 2026-02-22 21:57:00 +00:00 committed by GitHub
commit eb26dcd516
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -153,18 +153,23 @@ QByteArray serializeLevelDat(nbt::tag_compound* levelInfo)
return val; return val;
} }
QString getLevelDatFromFS(const QFileInfo& file) QString getDatFromFS(const QFileInfo& root, QString file)
{ {
QDir worldDir(file.filePath()); QDir worldDir(root.filePath());
if (!file.isDir() || !worldDir.exists("level.dat")) { if (!root.isDir() || !worldDir.exists(file)) {
return QString(); return QString();
} }
return worldDir.absoluteFilePath("level.dat"); return worldDir.absoluteFilePath(file);
} }
QByteArray getLevelDatDataFromFS(const QFileInfo& file) QString getLevelDatFromFS(const QFileInfo& file)
{ {
auto fullFilePath = getLevelDatFromFS(file); return getDatFromFS(file, "level.dat");
}
QByteArray getDatDataFromFS(const QFileInfo& root, QString file)
{
auto fullFilePath = getDatFromFS(root, file);
if (fullFilePath.isNull()) { if (fullFilePath.isNull()) {
return QByteArray(); return QByteArray();
} }
@ -175,6 +180,16 @@ QByteArray getLevelDatDataFromFS(const QFileInfo& file)
return f.readAll(); return f.readAll();
} }
QByteArray getLevelDatDataFromFS(const QFileInfo& file)
{
return getDatDataFromFS(file, "level.dat");
}
QByteArray getWorldGenDataFromFS(const QFileInfo& file)
{
return getDatDataFromFS(file, "data/minecraft/world_gen_settings.dat");
}
bool putLevelDatDataToFS(const QFileInfo& file, QByteArray& data) bool putLevelDatDataToFS(const QFileInfo& file, QByteArray& data)
{ {
auto fullFilePath = getLevelDatFromFS(file); auto fullFilePath = getLevelDatFromFS(file);
@ -229,6 +244,8 @@ bool World::resetIcon()
return false; return false;
} }
int64_t loadSeed(QByteArray data);
void World::readFromFS(const QFileInfo& file) void World::readFromFS(const QFileInfo& file)
{ {
auto bytes = getLevelDatDataFromFS(file); auto bytes = getLevelDatDataFromFS(file);
@ -238,6 +255,12 @@ void World::readFromFS(const QFileInfo& file)
} }
loadFromLevelDat(bytes); loadFromLevelDat(bytes);
m_levelDatTime = file.lastModified(); m_levelDatTime = file.lastModified();
if (m_randomSeed == 0) {
auto bytes = getWorldGenDataFromFS(file);
if (!bytes.isEmpty()) {
m_randomSeed = loadSeed(bytes);
}
}
} }
void World::readFromZip(const QFileInfo& file) void World::readFromZip(const QFileInfo& file)
@ -393,6 +416,28 @@ GameType read_gametype(nbt::value& parent, const char* name)
} // namespace } // namespace
int64_t loadSeed(QByteArray data)
{
auto levelData = parseLevelDat(data);
if (!levelData) {
return 0;
}
nbt::value* valPtr = nullptr;
try {
valPtr = &levelData->at("data");
} catch (const std::out_of_range& e) {
return 0;
}
nbt::value& val = *valPtr;
try {
return read_long(val, "seed").value_or(0);
} catch (const std::out_of_range&) {
}
return 0;
}
void World::loadFromLevelDat(QByteArray data) void World::loadFromLevelDat(QByteArray data)
{ {
auto levelData = parseLevelDat(data); auto levelData = parseLevelDat(data);