loading gui + converter

This commit is contained in:
Sen 2025-03-16 21:58:40 +01:00
parent 9df6406a93
commit 90de256e04
7 changed files with 259 additions and 178 deletions

View file

@ -15,6 +15,7 @@ import java.util.zip.InflaterInputStream;
import com.google.common.collect.Maps;
import game.Game;
import game.biome.Biome;
import game.block.Block;
import game.block.BlockCactus;
@ -57,6 +58,9 @@ import game.entity.animal.EntityWolf;
import game.entity.item.EntityBoat;
import game.entity.item.EntityMinecart;
import game.entity.npc.EntityHuman;
import game.gui.GuiLoading;
import game.gui.GuiLoading.Callback;
import game.gui.world.GuiWorlds;
import game.init.BlockRegistry;
import game.init.Blocks;
import game.init.Config;
@ -86,7 +90,7 @@ import game.tileentity.TileEntitySign;
import game.tileentity.TileEntitySkull;
import game.world.Region.FolderInfo;
public abstract class Converter {
public final class Converter {
public static enum SaveVersion {
ALPHA_1_0("Alpha 1.0 - Beta 1.2"),
BETA_1_3("Beta 1.3 - Release 1.8.9"),
@ -189,8 +193,11 @@ public abstract class Converter {
private static interface BlockFunction {
State getState(int id, int data);
}
private Converter() {
}
private static long postProgress(long start, int progress) {
private long postProgress(long start, int progress) {
// SKC.info("... " + progress + "%");
if(System.currentTimeMillis() - start >= 500L) {
start = System.currentTimeMillis();
@ -205,6 +212,14 @@ public abstract class Converter {
private static final char[] BLOCK_MAP = new char[65536];
// private static final Map<Character, BlockFunction> BLOCK_FUNCS = Maps.newHashMap();
private static final Map<String, String> OLD_GAMERULES = Maps.newHashMap();
private String action;
private String task;
private String file;
private int totalRegions;
private int doneRegions;
private int totalChunks;
private int doneChunks;
private static void mapEntity(Class<? extends Entity> clazz, String ... names) {
String name = EntityRegistry.getEntityString(clazz);
@ -1110,13 +1125,17 @@ public abstract class Converter {
return tag;
}
private static long convertChunks(File dir, File file, long start, int progress, int total) {
private long convertChunks(File dir, File file, long start, int progress, int total) {
String name = file.getName();
this.file = name;
this.totalChunks = 1024;
boolean legacy = name.endsWith(".mcr");
int rx, rz;
String[] reg = name.split("\\.");
if(reg.length != 4) {
Log.JNI.warn("Unbekannte Region " + file);
this.doneChunks = 0;
this.file = null;
return start;
}
try {
@ -1125,6 +1144,8 @@ public abstract class Converter {
}
catch(NumberFormatException e) {
Log.JNI.warn("Unbekannte Region " + file);
this.doneChunks = 0;
this.file = null;
return start;
}
try {
@ -1136,8 +1157,10 @@ public abstract class Converter {
Region newreg;
for(int bx = 0; bx < 4; bx++) {
for(int bz = 0; bz < 4; bz++) {
if(!oldreg.hasRegion(bx, bz))
if(!oldreg.hasRegion(bx, bz)) {
this.doneChunks += 64;
continue;
}
areas++;
newreg = new Region(dir, rx * 4 + bx, rz * 4 + bz);
Log.JNI.info("Konvertiere " + file + " zu " + newreg.getFile() + " ...");
@ -1150,6 +1173,7 @@ public abstract class Converter {
DataInputStream in = oldreg.getInputStream(x, z);
if(in == null) {
Log.JNI.warn("Konnte " + file.getPath() + "@" + x + "," + z + " nicht lesen");
this.doneChunks += 1;
continue;
}
NBTTagCompound tag = NBTLoader.read(in);
@ -1160,6 +1184,7 @@ public abstract class Converter {
// out.close();
newreg.writeTag(nx, nz, tag);
}
this.doneChunks += 1;
}
}
newreg.close(false);
@ -1168,6 +1193,7 @@ public abstract class Converter {
if(percent > prev) {
start = postProgress(start, percent);
}
// this.doneChunks += 1;
}
}
oldreg.close();
@ -1176,6 +1202,8 @@ public abstract class Converter {
catch(IOException e) {
e.printStackTrace();
}
this.doneChunks = 0;
this.file = null;
return start;
}
@ -1222,122 +1250,161 @@ public abstract class Converter {
// NBTTagCompound nbt = getLegacyWorldInfo(dir);
// if(nbt == null)
// return false;
Log.IO.info("Version: %s", ver);
if(ver != SaveVersion.RELEASE_1_13) {
Log.JNI.info("Konvertiere Chunk-Daten von region/*.mca,*.mcr");
File regionDir = new File(dir, "region");
if(regionDir.exists()) {
File chunkDir = new File(new File(dir, "chunk"), "terra");
Log.JNI.info("Konvertiere Welt nach '" + chunkDir + "' ...");
Log.JNI.info("Durchsuche Ordner unter '" + regionDir + "' nach .mca- und .mcr-Dateien ...");
File[] files = regionDir.listFiles(new FilenameFilter() {
public boolean accept(File file, String name) {
return name.endsWith(".mca") || name.endsWith(".mcr");
}
});
if(files.length == 0) {
Log.JNI.info("Keine .mca- oder .mcr-Dateien gefunden.");
final Converter conv = new Converter();
Game.getGame().displayGuiScreen(new GuiLoading("Konvertiere Welt ...", new Callback() {
public void poll(Game gm, GuiLoading gui) {
if(conv.totalRegions > 0) {
gui.setBar(conv.task, "Regionen", conv.totalRegions);
gui.setProgress(conv.doneRegions);
}
else {
Log.JNI.info("Ingesamt wurden " + files.length + " .mca-Dateien und .mcr-Dateien gefunden, konvertiere ...");
if(ver == SaveVersion.RELEASE_1_9)
Log.JNI.info("Konvertiere von neuerer Version, dies wird Blöcke entfernen ...");
chunkDir.mkdirs();
int progress = 0;
long time = System.currentTimeMillis();
long start = postProgress(time, 0);
for(File file : files) {
start = convertChunks(chunkDir, file, start, progress, files.length);
++progress;
int percent = (int)Math.round(100.0D * (double)progress / (double)files.length);
Log.JNI.info("Konvertiere Chunk-Daten: " + file.getName() + " (" + progress + "/" + files.length + ")");
start = postProgress(start, percent);
}
time = System.currentTimeMillis() - time;
Log.JNI.info("Fertig. Konversion dauerte " + ((time / 60000L) > 0 ? ((time / 60000L) + " Minuten und ") : "") + ((time / 1000L) % 60L) + " Sekunden.");
gui.resetBar();
}
if(conv.totalChunks > 0) {
gui.setSub(conv.file, "Chunks", conv.totalChunks);
gui.setSubProgress(conv.doneChunks);
}
else {
gui.resetSub();
}
gui.setTask(conv.action == null ? "" : conv.action);
}
}
else {
Log.JNI.warn("Konvertiere keine Chunk-Daten, da Version zu neu");
}
Log.JNI.info("Konvertiere Daten von level.dat");
Config.clear();
UniverseRegistry.clear();
if(nbt.hasKey("GameRules", 10)) {
NBTTagCompound rules = nbt.getCompoundTag("GameRules");
for(Entry<String, String> rule : OLD_GAMERULES.entrySet()) {
if(rules.hasKey(rule.getKey(), 8))
Config.set(rule.getValue(), rules.getString(rule.getKey()), null);
}));
final NBTTagCompound tag = nbt;
new Thread(new Runnable() {
public void run() {
Log.IO.info("Version: %s", ver);
if(ver != SaveVersion.RELEASE_1_13) {
conv.action = "Suche nach Chunk-Daten";
Log.JNI.info("Konvertiere Chunk-Daten von region/*.mca,*.mcr");
File regionDir = new File(dir, "region");
if(regionDir.exists()) {
File chunkDir = new File(new File(dir, "chunk"), "terra");
Log.JNI.info("Konvertiere Welt nach '" + chunkDir + "' ...");
Log.JNI.info("Durchsuche Ordner unter '" + regionDir + "' nach .mca- und .mcr-Dateien ...");
File[] files = regionDir.listFiles(new FilenameFilter() {
public boolean accept(File file, String name) {
return name.endsWith(".mca") || name.endsWith(".mcr");
}
});
if(files.length == 0) {
Log.JNI.info("Keine .mca- oder .mcr-Dateien gefunden.");
}
else {
conv.task = "Konvertiere Chunkdaten";
conv.totalRegions = files.length;
Log.JNI.info("Ingesamt wurden " + files.length + " .mca-Dateien und .mcr-Dateien gefunden, konvertiere ...");
if(ver == SaveVersion.RELEASE_1_9)
Log.JNI.info("Konvertiere von neuerer Version, dies wird Blöcke entfernen ...");
chunkDir.mkdirs();
int progress = 0;
long time = System.currentTimeMillis();
long start = conv.postProgress(time, 0);
for(File file : files) {
int percent = (int)Math.round(100.0D * (double)progress / (double)files.length);
Log.JNI.info("Konvertiere Chunk-Daten: " + file.getName() + " (" + progress + "/" + files.length + ")");
start = conv.convertChunks(chunkDir, file, start, progress, files.length);
++progress;
start = conv.postProgress(start, percent);
conv.doneRegions += 1;
}
time = System.currentTimeMillis() - time;
Log.JNI.info("Fertig. Konversion dauerte " + ((time / 60000L) > 0 ? ((time / 60000L) + " Minuten und ") : "") + ((time / 1000L) % 60L) + " Sekunden.");
}
}
}
else {
Log.JNI.warn("Konvertiere keine Chunk-Daten, da Version zu neu");
}
conv.doneRegions = 0;
conv.task = null;
conv.action = "Konvertiere level.dat";
Log.JNI.info("Konvertiere Daten von level.dat");
Config.clear();
UniverseRegistry.clear();
if(tag.hasKey("GameRules", 10)) {
NBTTagCompound rules = tag.getCompoundTag("GameRules");
for(Entry<String, String> rule : OLD_GAMERULES.entrySet()) {
if(rules.hasKey(rule.getKey(), 8))
Config.set(rule.getValue(), rules.getString(rule.getKey()), null);
}
}
// Config.setVar("noRespawn", "" + nbt.getBoolean("hardcore"), false);
// int id = nbt.getInteger("GameType");
// Config.set("defaultNoCreative", "" + (id == 2 || id == 0), false);
Config.set("spawnX", "" + tag.getInteger("SpawnX"), null);
Config.set("spawnY", "" + tag.getInteger("SpawnY"), null);
Config.set("spawnZ", "" + tag.getInteger("SpawnZ"), null);
Config.set("spawnDim", "" + 1, null);
Log.JNI.info("Speichere neue level.nbt ...");
Region.saveWorldInfo(dir, wtime, user);
if(tag.hasKey("Player", 10)) {
conv.action = "Konvertiere Spielerdaten";
NBTTagCompound player = tag.getCompoundTag("Player");
NBTTagList pos = player.getTagList("Pos", 6);
NBTTagList motion = player.getTagList("Motion", 6);
NBTTagList rotation = player.getTagList("Rotation", 5);
boolean ground = player.getBoolean("OnGround");
BlockPos spawn = null;
// boolean force = player.getBoolean("OnGround");
// int mode = -1;
// if(player.hasKey("playerGameType", 99)) {
// mode = player.getInteger("playerGameType");
// mode = mode == 0 || mode == 2 ? 0 : (mode == 1 || mode == 3 ? 1 : -1);
// }
if(player.hasKey("SpawnX", 99) && player.hasKey("SpawnY", 99) && player.hasKey("SpawnZ", 99)) {
spawn = new BlockPos(player.getInteger("SpawnX"), player.getInteger("SpawnY"),
player.getInteger("SpawnZ"));
// force = player.getBoolean("SpawnForced");
}
player.getKeySet().clear();
player.setTag("Pos", pos);
player.setTag("Motion", motion);
player.setTag("Rotation", rotation);
player.setBoolean("OnGround", ground);
player.setInteger("Dimension", 1);
player.setString("id", EntityRegistry.getEntityString(EntityHuman.class));
if(spawn != null) {
player.setInteger("SpawnX", spawn.getX());
player.setInteger("SpawnY", spawn.getY());
player.setInteger("SpawnZ", spawn.getZ());
player.setInteger("SpawnDim", 1);
// player.setBoolean("SpawnForced", force);
}
// if(mode >= 0)
// player.setBoolean("creative", mode == 1);
Log.JNI.info("Speichere neue Spielerdaten " + user.toLowerCase() + ".nbt ...");
File pdat = new File(new File(dir, "players"), user.toLowerCase() + ".nbt");
try {
pdat.getParentFile().mkdirs();
NBTLoader.writeGZip(player, pdat);
}
catch(Exception e) {
Log.JNI.error(e, "Fehler beim Schreiben von " + pdat);
}
}
Weather weather = tag.getBoolean("thundering") ? Weather.THUNDER : (tag.getBoolean("raining") ? Weather.RAIN : Weather.CLEAR);
if(weather != Weather.CLEAR) {
conv.action = "Konvertiere Dimensionsdaten";
NBTTagCompound dataTag = new NBTTagCompound();
dataTag.setString("Weather", weather.getName());
Log.JNI.info("Speichere neue data.nbt ...");
File dataFile = new File(new File(new File(dir, "chunk"), "terra"), "data.nbt");
try {
NBTLoader.writeGZip(dataTag, dataFile);
}
catch(Exception e) {
Log.JNI.error(e, "Konnte Weltdaten nicht speichern");
}
}
Log.IO.info("Welt '" + dir + "' wurde in %d Sekunden konvertiert", (System.currentTimeMillis() - cur) / 1000L);
Game.getGame().schedule(new Runnable() {
public void run() {
Game.getGame().displayGuiScreen(GuiWorlds.INSTANCE);
}
});
}
}
// Config.setVar("noRespawn", "" + nbt.getBoolean("hardcore"), false);
// int id = nbt.getInteger("GameType");
// Config.set("defaultNoCreative", "" + (id == 2 || id == 0), false);
Config.set("spawnX", "" + nbt.getInteger("SpawnX"), null);
Config.set("spawnY", "" + nbt.getInteger("SpawnY"), null);
Config.set("spawnZ", "" + nbt.getInteger("SpawnZ"), null);
Config.set("spawnDim", "" + 1, null);
Log.JNI.info("Speichere neue level.nbt ...");
Region.saveWorldInfo(dir, wtime, user);
if(nbt.hasKey("Player", 10)) {
NBTTagCompound player = nbt.getCompoundTag("Player");
NBTTagList pos = player.getTagList("Pos", 6);
NBTTagList motion = player.getTagList("Motion", 6);
NBTTagList rotation = player.getTagList("Rotation", 5);
boolean ground = player.getBoolean("OnGround");
BlockPos spawn = null;
// boolean force = player.getBoolean("OnGround");
// int mode = -1;
// if(player.hasKey("playerGameType", 99)) {
// mode = player.getInteger("playerGameType");
// mode = mode == 0 || mode == 2 ? 0 : (mode == 1 || mode == 3 ? 1 : -1);
// }
if(player.hasKey("SpawnX", 99) && player.hasKey("SpawnY", 99) && player.hasKey("SpawnZ", 99)) {
spawn = new BlockPos(player.getInteger("SpawnX"), player.getInteger("SpawnY"),
player.getInteger("SpawnZ"));
// force = player.getBoolean("SpawnForced");
}
player.getKeySet().clear();
player.setTag("Pos", pos);
player.setTag("Motion", motion);
player.setTag("Rotation", rotation);
player.setBoolean("OnGround", ground);
player.setInteger("Dimension", 1);
player.setString("id", EntityRegistry.getEntityString(EntityHuman.class));
if(spawn != null) {
player.setInteger("SpawnX", spawn.getX());
player.setInteger("SpawnY", spawn.getY());
player.setInteger("SpawnZ", spawn.getZ());
player.setInteger("SpawnDim", 1);
// player.setBoolean("SpawnForced", force);
}
// if(mode >= 0)
// player.setBoolean("creative", mode == 1);
Log.JNI.info("Speichere neue Spielerdaten " + user.toLowerCase() + ".nbt ...");
File pdat = new File(new File(dir, "players"), user.toLowerCase() + ".nbt");
try {
pdat.getParentFile().mkdirs();
NBTLoader.writeGZip(player, pdat);
}
catch(Exception e) {
Log.JNI.error(e, "Fehler beim Schreiben von " + pdat);
}
}
Weather weather = nbt.getBoolean("thundering") ? Weather.THUNDER : (nbt.getBoolean("raining") ? Weather.RAIN : Weather.CLEAR);
if(weather != Weather.CLEAR) {
NBTTagCompound dataTag = new NBTTagCompound();
dataTag.setString("Weather", weather.getName());
Log.JNI.info("Speichere neue data.nbt ...");
File dataFile = new File(new File(new File(dir, "chunk"), "terra"), "data.nbt");
try {
NBTLoader.writeGZip(dataTag, dataFile);
}
catch(Exception e) {
Log.JNI.error(e, "Konnte Weltdaten nicht speichern");
}
}
Log.IO.info("Welt '" + dir + "' wurde in %d Sekunden konvertiert", (System.currentTimeMillis() - cur) / 1000L);
}, "Converter Thread").start();
return new FolderInfo(wtime, user, System.currentTimeMillis(), null, Config.VERSION);
}