From c07dd71d3570f3eeae0550e4d6b69584978846f3 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Sun, 29 Jun 2014 18:22:52 +0200 Subject: [PATCH 01/16] Initial groundwork for Forge: gitignore, build file, example code, mod info --- forge/.gitignore | 5 +++ forge/build.gradle | 63 +++++++++++++++++++++++++++++ forge/src/main/java/wdl/test.java | 20 +++++++++ forge/src/main/resources/mcmod.info | 16 ++++++++ 4 files changed, 104 insertions(+) create mode 100644 forge/.gitignore create mode 100644 forge/build.gradle create mode 100644 forge/src/main/java/wdl/test.java create mode 100644 forge/src/main/resources/mcmod.info diff --git a/forge/.gitignore b/forge/.gitignore new file mode 100644 index 0000000..e5cbe85 --- /dev/null +++ b/forge/.gitignore @@ -0,0 +1,5 @@ +/*.txt +/eclipse +/gradle +/gradlew +/gradlew.bat diff --git a/forge/build.gradle b/forge/build.gradle new file mode 100644 index 0000000..4bebc16 --- /dev/null +++ b/forge/build.gradle @@ -0,0 +1,63 @@ +buildscript { + repositories { + mavenCentral() + maven { + name = "forge" + url = "http://files.minecraftforge.net/maven" + } + maven { + name = "sonatype" + url = "https://oss.sonatype.org/content/repositories/snapshots/" + } + } + dependencies { + classpath 'net.minecraftforge.gradle:ForgeGradle:1.2-SNAPSHOT' + } +} + +apply plugin: 'forge' + +version = "1.7.10" +group= "wdl" // http://maven.apache.org/guides/mini/guide-naming-conventions.html +archivesBaseName = "WorldDownloader" + +minecraft { + version = "1.7.10-10.13.0.1156" + assetDir = "eclipse/assets" +} + +dependencies { + // you may put jars on which you depend on in ./libs + // or you may define them like so.. + //compile "some.group:artifact:version:classifier" + //compile "some.group:artifact:version" + + // real examples + //compile 'com.mod-buildcraft:buildcraft:6.0.8:dev' // adds buildcraft to the dev env + //compile 'com.googlecode.efficient-java-matrix-library:ejml:0.24' // adds ejml to the dev env + + // for more info... + // http://www.gradle.org/docs/current/userguide/artifact_dependencies_tutorial.html + // http://www.gradle.org/docs/current/userguide/dependency_management.html + +} + +processResources +{ + // this will ensure that this task is redone when the versions change. + inputs.property "version", project.version + inputs.property "mcversion", project.minecraft.version + + // replace stuff in mcmod.info, nothing else + from(sourceSets.main.resources.srcDirs) { + include 'mcmod.info' + + // replace version and mcversion + expand 'version':project.version, 'mcversion':project.minecraft.version + } + + // copy everything else, thats not the mcmod.info + from(sourceSets.main.resources.srcDirs) { + exclude 'mcmod.info' + } +} diff --git a/forge/src/main/java/wdl/test.java b/forge/src/main/java/wdl/test.java new file mode 100644 index 0000000..4b11497 --- /dev/null +++ b/forge/src/main/java/wdl/test.java @@ -0,0 +1,20 @@ +package wdl.test; + +import net.minecraft.init.Blocks; +import cpw.mods.fml.common.Mod; +import cpw.mods.fml.common.Mod.EventHandler; +import cpw.mods.fml.common.event.FMLInitializationEvent; + +@Mod(modid = ExampleMod.MODID, version = ExampleMod.VERSION) +public class ExampleMod +{ + public static final String MODID = "WorldDownloader"; + public static final String VERSION = "1.7.10"; + + @EventHandler + public void init(FMLInitializationEvent event) + { + // some example code + System.out.println("DIRT BLOCK >> "+Blocks.dirt.getUnlocalizedName()); + } +} diff --git a/forge/src/main/resources/mcmod.info b/forge/src/main/resources/mcmod.info new file mode 100644 index 0000000..6e41e78 --- /dev/null +++ b/forge/src/main/resources/mcmod.info @@ -0,0 +1,16 @@ +[ +{ + "modid": "WorldDownloader", + "name": "World Downloader", + "description": "Backup your creations from multiplayer servers", + "version": "${version}", + "mcversion": "${mcversion}", + "url": "http://www.minecraftforum.net/topic/1444862-", + "updateUrl": "", + "authorList": ["nairol"],["cubic72"], + "credits": "", + "logoFile": "", + "screenshots": [], + "dependencies": [] +} +] From 7360c39e9e0d7746e37f936745a8aeb63a2ddd73 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Sun, 29 Jun 2014 20:13:23 +0200 Subject: [PATCH 02/16] Added README for Forge setup, updated .gitignore, fixed wrong file name --- forge/.gitignore | 5 +++++ forge/README | 19 +++++++++++++++++++ .../src/main/java/wdl/{test.java => WDL.java} | 6 +++--- 3 files changed, 27 insertions(+), 3 deletions(-) create mode 100644 forge/README rename forge/src/main/java/wdl/{test.java => WDL.java} (82%) diff --git a/forge/.gitignore b/forge/.gitignore index e5cbe85..c0f75de 100644 --- a/forge/.gitignore +++ b/forge/.gitignore @@ -3,3 +3,8 @@ /gradle /gradlew /gradlew.bat +/.gradle +/.classpath +/.project +/.settings +/bin diff --git a/forge/README b/forge/README new file mode 100644 index 0000000..a212d8f --- /dev/null +++ b/forge/README @@ -0,0 +1,19 @@ +# World Downloader Forge +## First time setup +Unzip the latest **Src** bundle from [files.minecraftforge.net](http://files.minecraftforge.net/) into this folder. + +## Updating to newer Forge versions +In the file **build.gradle** change the version number in line 25 to the latest one listed on [files.minecraftforge.net](http://files.minecraftforge.net/) +For example: + + version = "1.7.10-10.13.0.1156" + +The first part is the Minecraft version and the second part is the Forge version. +There is no need to download the latest version! The commands in the next section do this automatically. + +## After first time setup and after each update +* Open a command window in this folder (Windows: Shift+Click -> "Open command window here") +* Run command: `gradlew setupDecompWorkspace` +* Run command: `gradlew eclipse` + +[More information about Forge](http://www.minecraftforge.net/forum/index.php/topic,14048.0.html) \ No newline at end of file diff --git a/forge/src/main/java/wdl/test.java b/forge/src/main/java/wdl/WDL.java similarity index 82% rename from forge/src/main/java/wdl/test.java rename to forge/src/main/java/wdl/WDL.java index 4b11497..cce7e0c 100644 --- a/forge/src/main/java/wdl/test.java +++ b/forge/src/main/java/wdl/WDL.java @@ -1,12 +1,12 @@ -package wdl.test; +package wdl; import net.minecraft.init.Blocks; import cpw.mods.fml.common.Mod; import cpw.mods.fml.common.Mod.EventHandler; import cpw.mods.fml.common.event.FMLInitializationEvent; -@Mod(modid = ExampleMod.MODID, version = ExampleMod.VERSION) -public class ExampleMod +@Mod(modid = WDL.MODID, version = WDL.VERSION) +public class WDL { public static final String MODID = "WorldDownloader"; public static final String VERSION = "1.7.10"; From 109f3b8c2f788edf05dd2522f73e1f110419ba98 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 30 Jun 2014 18:14:30 +0200 Subject: [PATCH 03/16] Fixed invalid JSON in mod info --- forge/src/main/resources/mcmod.info | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/forge/src/main/resources/mcmod.info b/forge/src/main/resources/mcmod.info index 6e41e78..96356c1 100644 --- a/forge/src/main/resources/mcmod.info +++ b/forge/src/main/resources/mcmod.info @@ -7,7 +7,7 @@ "mcversion": "${mcversion}", "url": "http://www.minecraftforum.net/topic/1444862-", "updateUrl": "", - "authorList": ["nairol"],["cubic72"], + "authorList": ["nairol","cubic72"], "credits": "", "logoFile": "", "screenshots": [], From 9631cb8b95e42857068ecc489e6a6b11c992adc6 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 30 Jun 2014 18:15:06 +0200 Subject: [PATCH 04/16] Test chunk events --- forge/src/main/java/wdl/WDL.java | 55 +++++++++++++++++++++++++++++--- 1 file changed, 50 insertions(+), 5 deletions(-) diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index cce7e0c..2ef9392 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -1,20 +1,65 @@ package wdl; -import net.minecraft.init.Blocks; +import net.minecraftforge.common.MinecraftForge; +import net.minecraftforge.event.world.ChunkEvent; +import net.minecraftforge.event.world.WorldEvent; +import cpw.mods.fml.common.FMLLog; import cpw.mods.fml.common.Mod; +import cpw.mods.fml.common.SidedProxy; import cpw.mods.fml.common.Mod.EventHandler; import cpw.mods.fml.common.event.FMLInitializationEvent; +import cpw.mods.fml.common.eventhandler.SubscribeEvent; -@Mod(modid = WDL.MODID, version = WDL.VERSION) +@Mod( modid = WDL.MODID, version = WDL.VERSION ) public class WDL { public static final String MODID = "WorldDownloader"; public static final String VERSION = "1.7.10"; @EventHandler - public void init(FMLInitializationEvent event) + public void init( FMLInitializationEvent event ) { - // some example code - System.out.println("DIRT BLOCK >> "+Blocks.dirt.getUnlocalizedName()); + MinecraftForge.EVENT_BUS.register( this ); + } + + + @SubscribeEvent + public void onChunkLoad( ChunkEvent.Load event ) + { + if( event.world.isRemote ) + { + System.out.println("####### Loaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + } + } + + @SubscribeEvent + public void onChunkUnload( ChunkEvent.Unload event ) + { + if( event.world.isRemote ) + { + System.out.println("####### Unloaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + } + } + + @SubscribeEvent + public void onWorldLoad( WorldEvent.Load event ) + { + if( event.world.isRemote ) + { + System.out.println("####### Loaded world: " + event.world.toString() ); + } + else + { + FMLLog.getLogger().error("World Downloader is a client side mod! Please remove it from the server."); + } + } + + @SubscribeEvent + public void onWorldUnload( WorldEvent.Unload event ) + { + if( event.world.isRemote ) + { + System.err.println("####### Unloaded world: " + event.world.toString() ); + } } } From ce78a7046623105a41c31217409a334918b3a524 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 30 Jun 2014 18:22:02 +0200 Subject: [PATCH 05/16] Updated Forge to 1.7.10-10.13.0.1158 --- forge/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/forge/build.gradle b/forge/build.gradle index 4bebc16..b6158c5 100644 --- a/forge/build.gradle +++ b/forge/build.gradle @@ -22,7 +22,7 @@ group= "wdl" // http://maven.apache.org/guides/mini/guide-naming-conventions.htm archivesBaseName = "WorldDownloader" minecraft { - version = "1.7.10-10.13.0.1156" + version = "1.7.10-10.13.0.1158" assetDir = "eclipse/assets" } From aae8fd51e281c4ffd037fb117c74d2f09faba8ba Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Thu, 3 Jul 2014 06:17:52 +0200 Subject: [PATCH 06/16] ForgeMod.java contains hopefully all necessary hooks ("events") for WDL --- forge/src/main/java/wdl/ForgeMod.java | 101 ++++++++++++++++++++++++++ forge/src/main/resources/mcmod.info | 2 +- 2 files changed, 102 insertions(+), 1 deletion(-) create mode 100644 forge/src/main/java/wdl/ForgeMod.java diff --git a/forge/src/main/java/wdl/ForgeMod.java b/forge/src/main/java/wdl/ForgeMod.java new file mode 100644 index 0000000..786c03d --- /dev/null +++ b/forge/src/main/java/wdl/ForgeMod.java @@ -0,0 +1,101 @@ +package wdl; + +import net.minecraft.client.Minecraft; +import net.minecraft.util.ChatComponentText; +import net.minecraftforge.client.event.ClientChatReceivedEvent; +import net.minecraftforge.client.event.GuiOpenEvent; +import net.minecraftforge.client.event.GuiScreenEvent.ActionPerformedEvent; +import net.minecraftforge.client.event.GuiScreenEvent.InitGuiEvent; +import net.minecraftforge.common.MinecraftForge; +import net.minecraftforge.event.world.ChunkEvent; +import net.minecraftforge.event.world.WorldEvent; +import cpw.mods.fml.common.Mod; +import cpw.mods.fml.common.Mod.EventHandler; +import cpw.mods.fml.common.event.FMLInitializationEvent; +import cpw.mods.fml.common.eventhandler.SubscribeEvent; + +@Mod( modid = ForgeMod.MODID, version = ForgeMod.VERSION ) +public class ForgeMod +{ + public static final String MODID = "WDL"; + public static final String VERSION = "1.7.10"; + + private boolean debug = true; + Minecraft mc; + + @EventHandler + public void init( FMLInitializationEvent event ) + { + MinecraftForge.EVENT_BUS.register( this ); + mc = Minecraft.getMinecraft(); + } + + + @SubscribeEvent + public void onChunkLoad( ChunkEvent.Load event ) + { + if( event.world.isRemote ) + { + chatDebug("Loaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + } + } + + @SubscribeEvent + public void onChunkUnload( ChunkEvent.Unload event ) + { + if( event.world.isRemote ) + { + chatDebug("Unloaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + } + } + + @SubscribeEvent + public void onWorldLoad( WorldEvent.Load event ) + { + if( event.world.isRemote ) + { + chatDebug("Loaded world: " + event.world.toString() ); + } + } + + @SubscribeEvent + public void onWorldUnload( WorldEvent.Unload event ) + { + if( event.world.isRemote ) + { + chatDebug("Unloaded world: " + event.world.toString() ); + } + } + + @SubscribeEvent + public void onGuiDrawn( InitGuiEvent.Post event ) + { + chatDebug("GUI initialized: " + event.gui ); + } + + @SubscribeEvent + public void onGuiSwitch( GuiOpenEvent event ) + { + chatDebug("GUI switched: " + event.gui ); + } + + @SubscribeEvent + public void onGuiButtonClicked( ActionPerformedEvent.Pre event) + { + chatDebug("Button clicked: " + event.button ); + } + + @SubscribeEvent + public void onChatMessage( ClientChatReceivedEvent event ) + { + // Parse seed if found + } + + private void chatDebug( String msg ) + { + if( debug ) + { + mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); + } + } +} diff --git a/forge/src/main/resources/mcmod.info b/forge/src/main/resources/mcmod.info index 96356c1..a8696f9 100644 --- a/forge/src/main/resources/mcmod.info +++ b/forge/src/main/resources/mcmod.info @@ -1,6 +1,6 @@ [ { - "modid": "WorldDownloader", + "modid": "WDL", "name": "World Downloader", "description": "Backup your creations from multiplayer servers", "version": "${version}", From 3e41a6c5392eb46e97f5edc5834a03bc4a3da9f8 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Thu, 3 Jul 2014 06:40:51 +0200 Subject: [PATCH 07/16] Import base WDL files. Need to be changed to work with Forge... --- forge/src/main/java/wdl/GuiWDL.java | 193 +++ forge/src/main/java/wdl/GuiWDLBackup.java | 170 +++ forge/src/main/java/wdl/GuiWDLGenerator.java | 174 +++ forge/src/main/java/wdl/GuiWDLMultiworld.java | 136 ++ .../main/java/wdl/GuiWDLMultiworldSelect.java | 290 ++++ forge/src/main/java/wdl/GuiWDLPlayer.java | 285 ++++ forge/src/main/java/wdl/GuiWDLWorld.java | 444 ++++++ forge/src/main/java/wdl/WDL.java | 1329 ++++++++++++++++- forge/src/main/java/wdl/WDLSaveAsync.java | 11 + .../java/wdl/WDLSaveProgressReporter.java | 27 + 10 files changed, 2994 insertions(+), 65 deletions(-) create mode 100644 forge/src/main/java/wdl/GuiWDL.java create mode 100644 forge/src/main/java/wdl/GuiWDLBackup.java create mode 100644 forge/src/main/java/wdl/GuiWDLGenerator.java create mode 100644 forge/src/main/java/wdl/GuiWDLMultiworld.java create mode 100644 forge/src/main/java/wdl/GuiWDLMultiworldSelect.java create mode 100644 forge/src/main/java/wdl/GuiWDLPlayer.java create mode 100644 forge/src/main/java/wdl/GuiWDLWorld.java create mode 100644 forge/src/main/java/wdl/WDLSaveAsync.java create mode 100644 forge/src/main/java/wdl/WDLSaveProgressReporter.java diff --git a/forge/src/main/java/wdl/GuiWDL.java b/forge/src/main/java/wdl/GuiWDL.java new file mode 100644 index 0000000..14894fa --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDL.java @@ -0,0 +1,193 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; + +public class GuiWDL extends GuiScreen +{ + private String title = ""; + + private GuiScreen parent; + + private GuiTextField worldName; + private GuiButton autoStartBtn; + private GuiButton backupBtn; + private GuiButton worldOverrides; + private GuiButton generatorOverrides; + private GuiButton playerOverrides; + + public GuiWDL(GuiScreen parent) + { + this.parent = parent; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + if (WDL.isMultiworld && WDL.worldName.isEmpty()) + { + this.mc.displayGuiScreen(new GuiWDLMultiworldSelect(this.parent)); + } + + if (!WDL.propsFound) + { + this.mc.displayGuiScreen(new GuiWDLMultiworld(this.parent)); + return; + } + + this.buttonList.clear(); + + this.title = "Options for " + WDL.baseFolderName.replace('@', ':'); + + int w = this.width / 2; + int h = this.height / 4; + + int hi = h - 15; + + if (WDL.baseProps.getProperty("ServerName").isEmpty()) + { + WDL.baseProps.setProperty("ServerName", WDL.getServerName()); + } + + this.worldName = new GuiTextField(this.fontRendererObj, this.width / 2 - 70, hi, 168, 18); + this.updateServerName(false); + + hi += 22; + this.autoStartBtn = new GuiButton(1, w - 100, hi, "Start Download: ERROR"); + this.buttonList.add(this.autoStartBtn); + this.updateAutoStart(false); + + hi += 22; + this.backupBtn = new GuiButton(2, w - 100, hi, "Backup Options..."); + this.backupBtn.enabled = false; + this.buttonList.add(this.backupBtn); + hi += 28; + this.worldOverrides = new GuiButton(4, w - 100, hi, "World Overrides..."); + this.buttonList.add(this.worldOverrides); + hi += 22; + this.generatorOverrides = new GuiButton(5, w - 100, hi, "World Generator Overrides..."); + this.buttonList.add(this.generatorOverrides); + hi += 22; + this.playerOverrides = new GuiButton(6, w - 100, hi, "Player Overrides..."); + this.buttonList.add(this.playerOverrides); + hi += 28; + this.buttonList.add(new GuiButton(100, w - 100, h + 150, "Done")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton guibutton) + { + if (!guibutton.enabled) + return; + + this.updateServerName(true); + + if (guibutton.id == 1) // Auto start + { + this.updateAutoStart(true); + } + else if (guibutton.id == 2) // Backup + { + this.mc.displayGuiScreen(new GuiWDLBackup(this)); + } + else if (guibutton.id == 4) // World Overrides + { + this.mc.displayGuiScreen(new GuiWDLWorld(this)); + } + else if (guibutton.id == 5) // Generator Overrides + { + this.mc.displayGuiScreen(new GuiWDLGenerator(this)); + } + else if (guibutton.id == 6) // Player Overrides + { + this.mc.displayGuiScreen(new GuiWDLPlayer(this)); + } + else if (guibutton.id == 100) // Done + { + WDL.saveProps(); + this.mc.displayGuiScreen(this.parent); + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + this.worldName.mouseClicked(var1, var2, var3); + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char c, int i) + { + super.keyTyped(c, i); + this.worldName.textboxKeyTyped(c, i); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.worldName.updateCursorCounter(); // updateCursorCounter + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); // drawDefaultBackground + this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); + this.drawString(this.fontRendererObj, "Name:", this.width / 2 - 99, this.height / 4 - 10, 16777215); + this.worldName.drawTextBox(); // drawTextBox + super.drawScreen(var1, var2, var3); + } + + public void updateAutoStart(boolean btnClicked) + { + String autoStart = WDL.baseProps.getProperty("AutoStart"); + if (autoStart.equals("true")) + { + if (btnClicked) + { + WDL.baseProps.setProperty("AutoStart", "false"); + this.updateAutoStart(false); + } + else + { + this.autoStartBtn.displayString = "Start Download: Automatically"; + } + } + else if (btnClicked) + { + WDL.baseProps.setProperty("AutoStart", "true"); + this.updateAutoStart(false); + } + else + { + this.autoStartBtn.displayString = "Start Download: Only in menu"; + } + } + + private void updateServerName(boolean var1) + { + if (var1) + { + WDL.baseProps.setProperty("ServerName", this.worldName.getText()); + } + else + { + this.worldName.setText(WDL.baseProps.getProperty("ServerName")); + } + } +} diff --git a/forge/src/main/java/wdl/GuiWDLBackup.java b/forge/src/main/java/wdl/GuiWDLBackup.java new file mode 100644 index 0000000..4d3634e --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLBackup.java @@ -0,0 +1,170 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; + +public class GuiWDLBackup extends GuiScreen +{ + private String title = ""; + + private GuiScreen parent; + + private GuiTextField commandField; + private GuiButton backupBtn; + + boolean cmdBox = false; + + public GuiWDLBackup(GuiScreen parent) + { + this.parent = parent; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + + this.title = "Backup Options for " + WDL.baseFolderName.replace('@', ':'); + + int w = this.width / 2; + int h = this.height / 4; + + this.backupBtn = new GuiButton(10, w - 100, h + 105, "Backup: ERROR"); + this.buttonList.add(this.backupBtn); + this.updateBackup(false); + + this.commandField = new GuiTextField(this.fontRendererObj, w - 98, h + 126, 196, 17); + + this.buttonList.add(new GuiButton(100, w - 100, h + 150, "Done")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + if (var1.id == 10) + { + this.updateBackup(true); + } + else if (var1.id == 100) + { + this.mc.displayGuiScreen(this.parent); + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + + if (this.cmdBox) + { + this.commandField.mouseClicked(var1, var2, var3); + } + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + this.commandField.textboxKeyTyped(var1, var2); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.commandField.updateCursorCounter(); + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); + this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); + this.drawString(this.fontRendererObj, "Name:", this.width / 2 - 99, 50, 16777215); + + if (this.cmdBox) + { + this.commandField.drawTextBox(); + } + + super.drawScreen(var1, var2, var3); + } + + public void updateBackup(boolean var1) + { + this.cmdBox = false; + String var2 = WDL.baseProps.getProperty("Backup"); + + if (var2 == "off") + { + if (var1) + { + WDL.baseProps.setProperty("Backup", "folder"); + this.updateBackup(false); + } + else + { + this.backupBtn.displayString = "Backup: Disabled"; + } + } + else if (var2 == "folder") + { + if (var1) + { + WDL.baseProps.setProperty("Backup", "zip"); + this.updateBackup(false); + } + else + { + this.backupBtn.displayString = "Backup: Copy World Folder"; + } + } + else if (var2 == "zip") + { + if (var1) + { + WDL.baseProps.setProperty("Backup", "command"); + this.updateBackup(false); + } + else + { + this.backupBtn.displayString = "Backup: Zip World Folder"; + } + } + else if (var2 == "command") + { + if (var1) + { + WDL.baseProps.setProperty("Backup", "off"); + this.updateBackup(false); + } + else + { + this.backupBtn.displayString = "Backup: Run the following command"; + this.cmdBox = true; + } + } + else + { + WDL.baseProps.setProperty("Backup", "off"); + this.updateBackup(false); + } + } +} diff --git a/forge/src/main/java/wdl/GuiWDLGenerator.java b/forge/src/main/java/wdl/GuiWDLGenerator.java new file mode 100644 index 0000000..753cfb9 --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLGenerator.java @@ -0,0 +1,174 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; + +public class GuiWDLGenerator extends GuiScreen +{ + private String title = ""; + private GuiScreen parent; + private GuiTextField seedField; + private GuiButton generatorBtn; + private GuiButton generateStructuresBtn; + + public GuiWDLGenerator(GuiScreen var1) + { + this.parent = var1; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + this.title = "World Generator Options for " + WDL.baseFolderName.replace('@', ':'); + int var1 = this.width / 2; + int var2 = this.height / 4; + int var3 = var2 - 15; + this.seedField = new GuiTextField(this.fontRendererObj, this.width / 2 - 70, var3, 168, 18); + this.seedField.setText("ERROR"); + this.updateSeed(false); + var3 += 22; + this.generatorBtn = new GuiButton(1, var1 - 100, var3, "World Generator: ERROR"); + this.buttonList.add(this.generatorBtn); + this.updateGenerator(false); + var3 += 22; + this.generateStructuresBtn = new GuiButton(2, var1 - 100, var3, "Generate Structures: ERROR"); + this.buttonList.add(this.generateStructuresBtn); + this.updateGenerateStructures(false); + this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + if (var1.id == 1) + { + this.updateGenerator(true); + } + else if (var1.id == 2) + { + this.updateGenerateStructures(true); + } + else if (var1.id == 100) + { + this.updateSeed(true); + WDL.saveProps(); + this.mc.displayGuiScreen(this.parent); + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + this.seedField.mouseClicked(var1, var2, var3); + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + this.seedField.textboxKeyTyped(var1, var2); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.seedField.updateCursorCounter(); + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); + this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); + this.drawString(this.fontRendererObj, "Seed:", this.width / 2 - 99, this.height / 4 - 10, 16777215); + this.seedField.drawTextBox(); + super.drawScreen(var1, var2, var3); + } + + private void updateGenerator(boolean var1) + { + String var2 = WDL.worldProps.getProperty("GeneratorName"); + + if (var2.equals("default")) + { + if (var1) + { + WDL.worldProps.setProperty("GeneratorName", "flat"); + WDL.worldProps.setProperty("GeneratorVersion", "0"); + this.updateGenerator(false); + } + else + { + this.generatorBtn.displayString = "World Generator: Default"; + } + } + else if (var1) + { + WDL.worldProps.setProperty("GeneratorName", "default"); + WDL.worldProps.setProperty("GeneratorVersion", "1"); + this.updateGenerator(false); + } + else + { + this.generatorBtn.displayString = "World Generator: Flat"; + } + } + + private void updateGenerateStructures(boolean var1) + { + String var2 = WDL.worldProps.getProperty("MapFeatures"); + + if (var2.equals("true")) + { + if (var1) + { + WDL.worldProps.setProperty("MapFeatures", "false"); + this.updateGenerateStructures(false); + } + else + { + this.generateStructuresBtn.displayString = "Generate Structures: ON"; + } + } + else if (var1) + { + WDL.worldProps.setProperty("MapFeatures", "true"); + this.updateGenerateStructures(false); + } + else + { + this.generateStructuresBtn.displayString = "Generate Structures: OFF"; + } + } + + private void updateSeed(boolean var1) + { + if (var1) + { + WDL.worldProps.setProperty("RandomSeed", this.seedField.getText()); + } + else + { + this.seedField.setText(WDL.worldProps.getProperty("RandomSeed")); + } + } +} diff --git a/forge/src/main/java/wdl/GuiWDLMultiworld.java b/forge/src/main/java/wdl/GuiWDLMultiworld.java new file mode 100644 index 0000000..dabed3e --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLMultiworld.java @@ -0,0 +1,136 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; + +public class GuiWDLMultiworld extends GuiScreen +{ + private GuiScreen parent; + private GuiButton multiworldEnabledBtn; + boolean newMultiworldState = false; + + public GuiWDLMultiworld(GuiScreen var1) + { + this.parent = var1; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + int var1 = this.width / 2; + int var2 = this.height / 4; + int var3 = var2 + 115; + this.multiworldEnabledBtn = new GuiButton(1, var1 - 100, var3, "Multiworld support: ERROR"); + this.buttonList.add(this.multiworldEnabledBtn); + this.updateMultiworldEnabled(false); + this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "OK")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + if (var1.id == 1) + { + this.updateMultiworldEnabled(true); + } + else if (var1.id == 100) + { + if (this.newMultiworldState) + { + this.mc.displayGuiScreen(new GuiWDLMultiworldSelect(this.parent)); + } + else + { + WDL.baseProps.setProperty("LinkedWorlds", ""); + WDL.saveProps(); + WDL.propsFound = true; + + if (this.parent != null) + { + this.mc.displayGuiScreen(new GuiWDL(this.parent)); + } + else + { + WDL.start(); + this.mc.displayGuiScreen((GuiScreen)null); + this.mc.setIngameFocus(); + } + } + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); + drawRect(this.width / 2 - 160, this.height / 4 - 60, this.width / 2 + 160, this.height / 4 + 180, -1342177280); + this.drawCenteredString(this.fontRendererObj, "Multiworld Support", this.width / 2, this.height / 4 - 40, 16711680); + this.drawString(this.fontRendererObj, "Multiworld support is required if at least one of the", this.width / 2 - 150, this.height / 4 - 15, 16777215); + this.drawString(this.fontRendererObj, " following conditions is met:", this.width / 2 - 150, this.height / 4 - 5, 16777215); + this.drawString(this.fontRendererObj, "- \"Multiworld\" is mentioned on the server\'s website", this.width / 2 - 150, this.height / 4 + 15, 16777215); + this.drawString(this.fontRendererObj, "- The server has more than 3 dimensions (or worlds)", this.width / 2 - 150, this.height / 4 + 35, 16777215); + this.drawString(this.fontRendererObj, "- The server has other dimensions than the official ones", this.width / 2 - 150, this.height / 4 + 55, 16777215); + this.drawString(this.fontRendererObj, " (Earth, Nether, The End)", this.width / 2 - 150, this.height / 4 + 65, 16777215); + drawRect(this.width / 2 - 102, this.height / 4 + 113, this.width / 2 + 102, this.height / 4 + 137, -65536); + super.drawScreen(var1, var2, var3); + } + + private void updateMultiworldEnabled(boolean var1) + { + if (!this.newMultiworldState) + { + if (var1) + { + this.newMultiworldState = true; + this.updateMultiworldEnabled(false); + } + else + { + this.multiworldEnabledBtn.displayString = "Multiworld support: Disabled"; + } + } + else if (var1) + { + this.newMultiworldState = false; + this.updateMultiworldEnabled(false); + } + else + { + this.multiworldEnabledBtn.displayString = "Multiworld support: Enabled"; + } + } +} diff --git a/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java b/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java new file mode 100644 index 0000000..195a096 --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java @@ -0,0 +1,290 @@ +package net.minecraft.wdl; + +import java.io.File; +import java.util.Properties; + +import net.minecraft.client.entity.EntityClientPlayerMP; +import net.minecraft.client.entity.EntityPlayerSP; +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; +import net.minecraft.util.Session; + +public class GuiWDLMultiworldSelect extends GuiScreen +{ + private GuiButton cancelBtn; + private GuiTextField newNameField; + private boolean newWorld = false; + private int positionID; + private float yaw; + private int thirdPersonViewSave; + private GuiButton[] buttons; + private String[] worlds; + private GuiScreen parent; + EntityPlayerSP cam; + + public GuiWDLMultiworldSelect(GuiScreen var1) + { + this.parent = var1; + EntityClientPlayerMP var2 = WDL.tp; + this.cam = new EntityPlayerSP(WDL.mc, WDL.wc, new Session("Camera", "", "", "legacy"), var2.dimension); + this.cam.setLocationAndAngles(var2.posX, var2.posY - (double)var2.yOffset, var2.posZ, var2.rotationYaw, 0.0F); + this.yaw = var2.rotationYaw; + this.thirdPersonViewSave = WDL.mc.gameSettings.thirdPersonView; + WDL.mc.gameSettings.thirdPersonView = 0; + WDL.mc.renderViewEntity = this.cam; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + int var1 = this.width / 2; + int var2 = this.height / 4; + int var3 = this.width / 150; + + if (var3 == 0) + { + var3 = 1; + } + + int var4 = this.width / var3 - 5; + this.cancelBtn = new GuiButton(100, var1 - 100, this.height - 30, "Cancel"); + this.buttonList.add(this.cancelBtn); + String var5 = WDL.baseProps.getProperty("LinkedWorlds"); + String[] var6 = var5.split("[|]"); + String[] var7 = new String[var6.length]; + int var8 = 0; + int var9; + + for (var9 = 0; var9 < var6.length; ++var9) + { + if (var6[var9].isEmpty()) + { + var6[var9] = null; + } + else + { + Properties var10 = WDL.loadWorldProps(var6[var9]); + + if (var10 == null) + { + var6[var9] = null; + } + else + { + ++var8; + var7[var9] = var10.getProperty("WorldName"); + } + } + } + + if (var3 > var8 + 1) + { + var3 = var8 + 1; + } + + var9 = (this.width - var3 * var4) / 2; + this.worlds = new String[var8]; + this.buttons = new GuiButton[var8 + 1]; + int var12 = 0; + int var11; + + for (var11 = 0; var11 < var6.length; ++var11) + { + if (var6[var11] != null) + { + this.worlds[var12] = var6[var11]; + this.buttons[var12] = new GuiButton(var12, var12 % var3 * var4 + var9, this.height - 60 - var12 / var3 * 21, var4, 20, var7[var11]); + this.buttonList.add(this.buttons[var12]); + ++var12; + } + } + + var11 = this.buttons.length - 1; + + if (!this.newWorld) + { + this.buttons[var11] = new GuiButton(var11, var11 % var3 * var4 + var9, this.height - 60 - var11 / var3 * 21, var4, 20, "< New Name >"); + this.buttonList.add(this.buttons[var11]); + } + + this.newNameField = new GuiTextField(this.fontRendererObj, var11 % var3 * var4 + var9, this.height - 60 - var11 / var3 * 21 + 1, var4, 18); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + this.newWorld = false; + + if (var1.id == this.worlds.length) + { + this.newWorld = true; + this.buttonList.remove(this.buttons[this.worlds.length]); + } + else if (var1.id == 100) + { + this.mc.displayGuiScreen((GuiScreen)null); + this.mc.setIngameFocus(); + } + else + { + this.worldSelected(this.worlds[var1.id]); + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + + if (this.newWorld) + { + this.newNameField.mouseClicked(var1, var2, var3); + } + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + + if (this.newNameField.isFocused()) + { + this.newNameField.textboxKeyTyped(var1, var2); + + if (var2 == 28) + { + String var3 = this.newNameField.getText(); + + if (var3 != null && !var3.isEmpty()) + { + this.worldSelected(this.addMultiworld(var3)); + } + } + } + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.newNameField.updateCursorCounter(); + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + drawRect(this.width / 2 - 120, 0, this.width / 2 + 120, this.height / 16 + 25, -1073741824); + + if (this.parent == null) + { + this.drawCenteredString(this.fontRendererObj, "World Downloader - Trying To Start Download", this.width / 2, this.height / 16, 16777215); + } + else + { + this.drawCenteredString(this.fontRendererObj, "World Downloader - Trying To Change Options", this.width / 2, this.height / 16, 16777215); + } + + this.drawCenteredString(this.fontRendererObj, "Where are you?", this.width / 2, this.height / 16 + 10, 16711680); + this.cam.prevRotationPitch = this.cam.rotationPitch = 0.0F; + this.cam.prevRotationYaw = this.cam.rotationYaw = this.yaw; + float var4 = 0.475F; + this.cam.lastTickPosY = this.cam.prevPosY = this.cam.posY = WDL.tp.posY; + this.cam.lastTickPosX = this.cam.prevPosX = this.cam.posX = WDL.tp.posX - (double)var4 * Math.sin((double)this.yaw / 180.0D * Math.PI); + this.cam.lastTickPosZ = this.cam.prevPosZ = this.cam.posZ = WDL.tp.posZ + (double)var4 * Math.cos((double)this.yaw / 180.0D * Math.PI); + float var5 = 1.0F; + this.yaw = (float)((double)this.yaw + (double)var5 * (1.0D + 0.699999988079071D * Math.cos((double)(this.yaw + 45.0F) / 45.0D * Math.PI))); + + if (this.newWorld) + { + this.newNameField.drawTextBox(); + } + + super.drawScreen(var1, var2, var3); + } + + /** + * Called when the screen is unloaded. Used to disable keyboard repeat events + */ + public void onGuiClosed() + { + super.onGuiClosed(); + WDL.mc.gameSettings.thirdPersonView = this.thirdPersonViewSave; + this.mc.renderViewEntity = WDL.tp; + } + + private void worldSelected(String var1) + { + WDL.worldName = var1; + WDL.isMultiworld = true; + WDL.propsFound = true; + + if (this.parent == null) + { + WDL.start(); + this.mc.displayGuiScreen((GuiScreen)null); + this.mc.setIngameFocus(); + } + else + { + WDL.worldProps = WDL.loadWorldProps(var1); + this.mc.displayGuiScreen(new GuiWDL(this.parent)); + } + } + + private String addMultiworld(String var1) + { + String var2 = var1; + String var3 = "\\/:*?\"<>|"; + char[] var4 = var3.toCharArray(); + int var5 = var4.length; + int var6; + + for (var6 = 0; var6 < var5; ++var6) + { + char var7 = var4[var6]; + var2 = var2.replace(var7, '_'); + } + + (new File(this.mc.mcDataDir, "saves/" + WDL.baseFolderName + " - " + var2)).mkdirs(); + Properties var11 = new Properties(WDL.baseProps); + var11.setProperty("WorldName", var1); + String[] var12 = new String[this.worlds.length + 1]; + + for (var6 = 0; var6 < this.worlds.length; ++var6) + { + var12[var6] = this.worlds[var6]; + } + + var12[var12.length - 1] = var2; + String var13 = ""; + String[] var14 = var12; + int var8 = var12.length; + + for (int var9 = 0; var9 < var8; ++var9) + { + String var10 = var14[var9]; + var13 = var13 + var10 + "|"; + } + + WDL.baseProps.setProperty("LinkedWorlds", var13); + WDL.saveProps(var2, var11); + return var2; + } +} diff --git a/forge/src/main/java/wdl/GuiWDLPlayer.java b/forge/src/main/java/wdl/GuiWDLPlayer.java new file mode 100644 index 0000000..aaa0df7 --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLPlayer.java @@ -0,0 +1,285 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; + +public class GuiWDLPlayer extends GuiScreen +{ + private String title = ""; + private GuiScreen parent; + private GuiButton healthBtn; + private GuiButton hungerBtn; + private GuiButton playerPosBtn; + private GuiButton pickPosBtn; + private boolean showPosFields = false; + private GuiTextField posX; + private GuiTextField posY; + private GuiTextField posZ; + private int posTextY; + + public GuiWDLPlayer(GuiScreen var1) + { + this.parent = var1; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + this.title = "Player Options for " + WDL.baseFolderName.replace('@', ':'); + int var1 = this.width / 2; + int var2 = this.height / 4; + int var3 = var2 - 15; + this.healthBtn = new GuiButton(1, var1 - 100, var3, "Health: ERROR"); + this.buttonList.add(this.healthBtn); + this.updateHealth(false); + var3 += 22; + this.hungerBtn = new GuiButton(2, var1 - 100, var3, "Hunger: ERROR"); + this.buttonList.add(this.hungerBtn); + this.updateHunger(false); + var3 += 22; + this.playerPosBtn = new GuiButton(3, var1 - 100, var3, "Player Position: ERROR"); + this.buttonList.add(this.playerPosBtn); + var3 += 22; + this.posTextY = var3 + 4; + this.posX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); + this.posY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); + this.posZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); + this.posX.func_146203_f(7); + this.posY.func_146203_f(7); + this.posZ.func_146203_f(7); + var3 += 18; + this.pickPosBtn = new GuiButton(4, var1 - 0, var3, 100, 20, "Current position"); + this.buttonList.add(this.pickPosBtn); + this.updatePlayerPos(false); + this.updatePosXYZ(false); + this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + if (var1.id == 1) + { + this.updateHealth(true); + } + else if (var1.id == 2) + { + this.updateHunger(true); + } + else if (var1.id == 3) + { + this.updatePlayerPos(true); + } + else if (var1.id == 4) + { + this.pickPlayerPos(); + } + else if (var1.id == 100) + { + if (this.showPosFields) + { + this.updatePosXYZ(true); + } + + WDL.saveProps(); + this.mc.displayGuiScreen(this.parent); + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + + if (this.showPosFields) + { + this.posX.mouseClicked(var1, var2, var3); + this.posY.mouseClicked(var1, var2, var3); + this.posZ.mouseClicked(var1, var2, var3); + } + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + this.posX.textboxKeyTyped(var1, var2); + this.posY.textboxKeyTyped(var1, var2); + this.posZ.textboxKeyTyped(var1, var2); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.posX.updateCursorCounter(); + this.posY.updateCursorCounter(); + this.posZ.updateCursorCounter(); + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); + this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); + + if (this.showPosFields) + { + this.drawString(this.fontRendererObj, "X:", this.width / 2 - 99, this.posTextY, 16777215); + this.drawString(this.fontRendererObj, "Y:", this.width / 2 - 31, this.posTextY, 16777215); + this.drawString(this.fontRendererObj, "Z:", this.width / 2 + 37, this.posTextY, 16777215); + this.posX.drawTextBox(); + this.posY.drawTextBox(); + this.posZ.drawTextBox(); + } + + super.drawScreen(var1, var2, var3); + } + + private void updateHealth(boolean var1) + { + String var2 = WDL.baseProps.getProperty("PlayerHealth"); + + if (var2.equals("keep")) + { + if (var1) + { + WDL.baseProps.setProperty("PlayerHealth", "20"); + this.updateHealth(false); + } + else + { + this.healthBtn.displayString = "Health: Don\'t change"; + } + } + else if (var2.equals("20")) + { + if (var1) + { + WDL.baseProps.setProperty("PlayerHealth", "keep"); + this.updateHealth(false); + } + else + { + this.healthBtn.displayString = "Health: Full"; + } + } + } + + private void updateHunger(boolean var1) + { + String var2 = WDL.baseProps.getProperty("PlayerFood"); + + if (var2.equals("keep")) + { + if (var1) + { + WDL.baseProps.setProperty("PlayerFood", "20"); + this.updateHunger(false); + } + else + { + this.hungerBtn.displayString = "Hunger: Don\'t change"; + } + } + else if (var2.equals("20")) + { + if (var1) + { + WDL.baseProps.setProperty("PlayerFood", "keep"); + this.updateHunger(false); + } + else + { + this.hungerBtn.displayString = "Hunger: Full"; + } + } + } + + private void updatePlayerPos(boolean var1) + { + String var2 = WDL.worldProps.getProperty("PlayerPos"); + this.showPosFields = false; + this.pickPosBtn.field_146125_m = false; + + if (var2.equals("keep")) + { + if (var1) + { + WDL.worldProps.setProperty("PlayerPos", "xyz"); + this.updatePlayerPos(false); + } + else + { + this.playerPosBtn.displayString = "Player Position: Don\'t change"; + } + } + else if (var2.equals("xyz")) + { + if (var1) + { + WDL.worldProps.setProperty("PlayerPos", "keep"); + this.updatePlayerPos(false); + } + else + { + this.playerPosBtn.displayString = "Player Position:"; + this.showPosFields = true; + this.pickPosBtn.field_146125_m = true; + } + } + } + + private void updatePosXYZ(boolean var1) + { + if (var1) + { + try + { + int var2 = Integer.parseInt(this.posX.getText()); + int var3 = Integer.parseInt(this.posY.getText()); + int var4 = Integer.parseInt(this.posZ.getText()); + WDL.worldProps.setProperty("PlayerX", String.valueOf(var2)); + WDL.worldProps.setProperty("PlayerY", String.valueOf(var3)); + WDL.worldProps.setProperty("PlayerZ", String.valueOf(var4)); + } + catch (NumberFormatException var5) + { + this.updatePlayerPos(true); + } + } + else + { + this.posX.setText(WDL.worldProps.getProperty("PlayerX")); + this.posY.setText(WDL.worldProps.getProperty("PlayerY")); + this.posZ.setText(WDL.worldProps.getProperty("PlayerZ")); + } + } + + private void pickPlayerPos() + { + int var1 = (int)Math.floor(WDL.tp.posX); + int var2 = (int)Math.floor(WDL.tp.posY); + int var3 = (int)Math.floor(WDL.tp.posZ); + this.posX.setText(String.valueOf(var1)); + this.posY.setText(String.valueOf(var2)); + this.posZ.setText(String.valueOf(var3)); + } +} diff --git a/forge/src/main/java/wdl/GuiWDLWorld.java b/forge/src/main/java/wdl/GuiWDLWorld.java new file mode 100644 index 0000000..eefe35b --- /dev/null +++ b/forge/src/main/java/wdl/GuiWDLWorld.java @@ -0,0 +1,444 @@ +package net.minecraft.wdl; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; + +public class GuiWDLWorld extends GuiScreen +{ + private String title = ""; + private GuiScreen parent; + private GuiButton gameModeBtn; + private GuiButton timeBtn; + private GuiButton weatherBtn; + private GuiButton spawnBtn; + private GuiButton pickSpawnBtn; + private boolean showSpawnFields = false; + private GuiTextField spawnX; + private GuiTextField spawnY; + private GuiTextField spawnZ; + private int spawnTextY; + + public GuiWDLWorld(GuiScreen var1) + { + this.parent = var1; + } + + /** + * Adds the buttons (and other controls) to the screen in question. + */ + public void initGui() + { + this.buttonList.clear(); + this.title = "World Options for " + WDL.baseFolderName.replace('@', ':'); + int var1 = this.width / 2; + int var2 = this.height / 4; + int var3 = var2 - 15; + this.gameModeBtn = new GuiButton(1, var1 - 100, var3, "Game Mode: ERROR"); + this.buttonList.add(this.gameModeBtn); + this.updateGameMode(false); + var3 += 22; + this.timeBtn = new GuiButton(2, var1 - 100, var3, "Time: ERROR"); + this.buttonList.add(this.timeBtn); + this.updateTime(false); + var3 += 22; + this.weatherBtn = new GuiButton(3, var1 - 100, var3, "Weather: ERROR"); + this.buttonList.add(this.weatherBtn); + this.updateWeather(false); + var3 += 22; + this.spawnBtn = new GuiButton(4, var1 - 100, var3, "Spawn Position: ERROR"); + this.buttonList.add(this.spawnBtn); + var3 += 22; + this.spawnTextY = var3 + 4; + this.spawnX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); + this.spawnY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); + this.spawnZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); + this.spawnX.func_146203_f(7); + this.spawnY.func_146203_f(7); + this.spawnZ.func_146203_f(7); + var3 += 18; + this.pickSpawnBtn = new GuiButton(5, var1 - 0, var3, 100, 20, "Current position"); + this.buttonList.add(this.pickSpawnBtn); + this.updateSpawn(false); + this.updateSpawnXYZ(false); + this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); + } + + /** + * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). + */ + protected void actionPerformed(GuiButton var1) + { + if (var1.enabled) + { + if (var1.id == 1) + { + this.updateGameMode(true); + } + else if (var1.id == 2) + { + this.updateTime(true); + } + else if (var1.id == 3) + { + this.updateWeather(true); + } + else if (var1.id == 4) + { + this.updateSpawn(true); + } + else if (var1.id == 5) + { + this.pickSpawn(); + } + else if (var1.id == 100) + { + if (this.showSpawnFields) + { + this.updateSpawnXYZ(true); + } + + WDL.saveProps(); + this.mc.displayGuiScreen(this.parent); + } + } + } + + /** + * Called when the mouse is clicked. + */ + protected void mouseClicked(int var1, int var2, int var3) + { + super.mouseClicked(var1, var2, var3); + + if (this.showSpawnFields) + { + this.spawnX.mouseClicked(var1, var2, var3); + this.spawnY.mouseClicked(var1, var2, var3); + this.spawnZ.mouseClicked(var1, var2, var3); + } + } + + /** + * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). + */ + protected void keyTyped(char var1, int var2) + { + super.keyTyped(var1, var2); + this.spawnX.textboxKeyTyped(var1, var2); + this.spawnY.textboxKeyTyped(var1, var2); + this.spawnZ.textboxKeyTyped(var1, var2); + } + + /** + * Called from the main game loop to update the screen. + */ + public void updateScreen() + { + this.spawnX.updateCursorCounter(); + this.spawnY.updateCursorCounter(); + this.spawnZ.updateCursorCounter(); + super.updateScreen(); + } + + /** + * Draws the screen and all the components in it. + */ + public void drawScreen(int var1, int var2, float var3) + { + this.drawDefaultBackground(); + this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); + + if (this.showSpawnFields) + { + this.drawString(this.fontRendererObj, "X:", this.width / 2 - 99, this.spawnTextY, 16777215); + this.drawString(this.fontRendererObj, "Y:", this.width / 2 - 31, this.spawnTextY, 16777215); + this.drawString(this.fontRendererObj, "Z:", this.width / 2 + 37, this.spawnTextY, 16777215); + this.spawnX.drawTextBox(); + this.spawnY.drawTextBox(); + this.spawnZ.drawTextBox(); + } + + super.drawScreen(var1, var2, var3); + } + + private void updateGameMode(boolean var1) + { + String var2 = WDL.baseProps.getProperty("GameType"); + + if (var2.equals("keep")) + { + if (var1) + { + WDL.baseProps.setProperty("GameType", "creative"); + this.updateGameMode(false); + } + else + { + this.gameModeBtn.displayString = "Game Mode: Don\'t change"; + } + } + else if (var2.equals("creative")) + { + if (var1) + { + WDL.baseProps.setProperty("GameType", "survival"); + this.updateGameMode(false); + } + else + { + this.gameModeBtn.displayString = "Game Mode: Creative"; + } + } + else if (var2.equals("survival")) + { + if (var1) + { + WDL.baseProps.setProperty("GameType", "hardcore"); + this.updateGameMode(false); + } + else + { + this.gameModeBtn.displayString = "Game Mode: Survival"; + } + } + else if (var2.equals("hardcore")) + { + if (var1) + { + WDL.baseProps.setProperty("GameType", "keep"); + this.updateGameMode(false); + } + else + { + this.gameModeBtn.displayString = "Game Mode: Survival Hardcore"; + } + } + } + + private void updateTime(boolean var1) + { + String var2 = WDL.baseProps.getProperty("Time"); + + if (var2.equals("keep")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "23000"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Don\'t change"; + } + } + else if (var2.equals("23000")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "0"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Sunrise"; + } + } + else if (var2.equals("0")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "6000"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Morning"; + } + } + else if (var2.equals("6000")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "11500"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Noon"; + } + } + else if (var2.equals("11500")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "12500"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Evening"; + } + } + else if (var2.equals("12500")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "18000"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Sunset"; + } + } + else if (var2.equals("18000")) + { + if (var1) + { + WDL.baseProps.setProperty("Time", "keep"); + this.updateTime(false); + } + else + { + this.timeBtn.displayString = "Time: Midnight"; + } + } + } + + private void updateWeather(boolean var1) + { + String var2 = WDL.baseProps.getProperty("Weather"); + + if (var2.equals("keep")) + { + if (var1) + { + WDL.baseProps.setProperty("Weather", "sunny"); + this.updateWeather(false); + } + else + { + this.weatherBtn.displayString = "Weather: Don\'t change"; + } + } + else if (var2.equals("sunny")) + { + if (var1) + { + WDL.baseProps.setProperty("Weather", "rain"); + this.updateWeather(false); + } + else + { + this.weatherBtn.displayString = "Weather: Sunny"; + } + } + else if (var2.equals("rain")) + { + if (var1) + { + WDL.baseProps.setProperty("Weather", "thunderstorm"); + this.updateWeather(false); + } + else + { + this.weatherBtn.displayString = "Weather: Rain"; + } + } + else if (var2.equals("thunderstorm")) + { + if (var1) + { + WDL.baseProps.setProperty("Weather", "keep"); + this.updateWeather(false); + } + else + { + this.weatherBtn.displayString = "Weather: Thunderstorm"; + } + } + } + + private void updateSpawn(boolean var1) + { + String var2 = WDL.worldProps.getProperty("Spawn"); + this.showSpawnFields = false; + this.pickSpawnBtn.field_146125_m = false; + + if (var2.equals("auto")) + { + if (var1) + { + WDL.worldProps.setProperty("Spawn", "player"); + this.updateSpawn(false); + } + else + { + this.spawnBtn.displayString = "Spawn Position: Automatic"; + } + } + else if (var2.equals("player")) + { + if (var1) + { + WDL.worldProps.setProperty("Spawn", "xyz"); + this.updateSpawn(false); + } + else + { + this.spawnBtn.displayString = "Spawn Position: Player position"; + } + } + else if (var2.equals("xyz")) + { + if (var1) + { + WDL.worldProps.setProperty("Spawn", "auto"); + this.updateSpawn(false); + } + else + { + this.spawnBtn.displayString = "Spawn Position:"; + this.showSpawnFields = true; + this.pickSpawnBtn.field_146125_m = true; + } + } + } + + private void updateSpawnXYZ(boolean var1) + { + if (var1) + { + try + { + int var2 = Integer.parseInt(this.spawnX.getText()); + int var3 = Integer.parseInt(this.spawnY.getText()); + int var4 = Integer.parseInt(this.spawnZ.getText()); + WDL.worldProps.setProperty("SpawnX", String.valueOf(var2)); + WDL.worldProps.setProperty("SpawnY", String.valueOf(var3)); + WDL.worldProps.setProperty("SpawnZ", String.valueOf(var4)); + } + catch (NumberFormatException var5) + { + this.updateSpawn(true); + } + } + else + { + this.spawnX.setText(WDL.worldProps.getProperty("SpawnX")); + this.spawnY.setText(WDL.worldProps.getProperty("SpawnY")); + this.spawnZ.setText(WDL.worldProps.getProperty("SpawnZ")); + } + } + + private void pickSpawn() + { + int var1 = (int)Math.floor(WDL.tp.posX); + int var2 = (int)Math.floor(WDL.tp.posY); + int var3 = (int)Math.floor(WDL.tp.posZ); + this.spawnX.setText(String.valueOf(var1)); + this.spawnY.setText(String.valueOf(var2)); + this.spawnZ.setText(String.valueOf(var3)); + } +} diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index 2ef9392..024f679 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -1,65 +1,1264 @@ -package wdl; - -import net.minecraftforge.common.MinecraftForge; -import net.minecraftforge.event.world.ChunkEvent; -import net.minecraftforge.event.world.WorldEvent; -import cpw.mods.fml.common.FMLLog; -import cpw.mods.fml.common.Mod; -import cpw.mods.fml.common.SidedProxy; -import cpw.mods.fml.common.Mod.EventHandler; -import cpw.mods.fml.common.event.FMLInitializationEvent; -import cpw.mods.fml.common.eventhandler.SubscribeEvent; - -@Mod( modid = WDL.MODID, version = WDL.VERSION ) -public class WDL -{ - public static final String MODID = "WorldDownloader"; - public static final String VERSION = "1.7.10"; - - @EventHandler - public void init( FMLInitializationEvent event ) - { - MinecraftForge.EVENT_BUS.register( this ); - } - - - @SubscribeEvent - public void onChunkLoad( ChunkEvent.Load event ) - { - if( event.world.isRemote ) - { - System.out.println("####### Loaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); - } - } - - @SubscribeEvent - public void onChunkUnload( ChunkEvent.Unload event ) - { - if( event.world.isRemote ) - { - System.out.println("####### Unloaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); - } - } - - @SubscribeEvent - public void onWorldLoad( WorldEvent.Load event ) - { - if( event.world.isRemote ) - { - System.out.println("####### Loaded world: " + event.world.toString() ); - } - else - { - FMLLog.getLogger().error("World Downloader is a client side mod! Please remove it from the server."); - } - } - - @SubscribeEvent - public void onWorldUnload( WorldEvent.Unload event ) - { - if( event.world.isRemote ) - { - System.err.println("####### Unloaded world: " + event.world.toString() ); - } - } -} +package net.minecraft.wdl; + +import java.io.Console; +import java.io.DataInputStream; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.FileOutputStream; +import java.io.FileReader; +import java.io.FileWriter; +import java.io.IOException; +import java.lang.reflect.Array; +import java.lang.reflect.Field; +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Iterator; +import java.util.List; +import java.util.Properties; +import java.net.URLDecoder; + +import net.minecraft.block.Block; +import net.minecraft.block.BlockBrewingStand; +import net.minecraft.block.BlockChest; +import net.minecraft.block.BlockDispenser; +import net.minecraft.block.BlockFurnace; +import net.minecraft.block.BlockNote; +import net.minecraft.client.Minecraft; +import net.minecraft.client.entity.EntityClientPlayerMP; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.multiplayer.ChunkProviderClient; +import net.minecraft.client.multiplayer.WorldClient; +import net.minecraft.entity.Entity; +import net.minecraft.entity.EntityList; +import net.minecraft.entity.item.EntityMinecart; +import net.minecraft.entity.item.EntityMinecartChest; +import net.minecraft.entity.passive.EntityVillager; +import net.minecraft.init.Blocks; +import net.minecraft.inventory.Container; +import net.minecraft.inventory.ContainerBrewingStand; +import net.minecraft.inventory.ContainerChest; +import net.minecraft.inventory.ContainerDispenser; +import net.minecraft.inventory.ContainerFurnace; +import net.minecraft.inventory.ContainerMerchant; +import net.minecraft.inventory.IInventory; +import net.minecraft.inventory.InventoryEnderChest; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.CompressedStreamTools; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.nbt.NBTTagDouble; +import net.minecraft.nbt.NBTTagFloat; +import net.minecraft.nbt.NBTTagList; +import net.minecraft.network.NetworkManager; +import net.minecraft.tileentity.TileEntity; +import net.minecraft.tileentity.TileEntityBrewingStand; +import net.minecraft.tileentity.TileEntityChest; +import net.minecraft.tileentity.TileEntityDispenser; +import net.minecraft.tileentity.TileEntityEnderChest; +import net.minecraft.tileentity.TileEntityFurnace; +import net.minecraft.tileentity.TileEntityNote; +import net.minecraft.util.ChatComponentText; +import net.minecraft.util.LongHashMap; +import net.minecraft.util.MovingObjectPosition; +import net.minecraft.util.MovingObjectPosition.MovingObjectType; +import net.minecraft.world.ChunkPosition; +import net.minecraft.world.MinecraftException; +import net.minecraft.world.chunk.Chunk; +import net.minecraft.world.chunk.storage.AnvilSaveConverter; +import net.minecraft.world.chunk.storage.IChunkLoader; +import net.minecraft.world.chunk.storage.RegionFileCache; +import net.minecraft.world.storage.ISaveHandler; +import net.minecraft.world.storage.SaveHandler; +import net.minecraft.world.storage.ThreadedFileIOBase; +import net.minecraft.world.storage.WorldInfo; + +import org.lwjgl.opengl.GL11; + +/** + * This is the main class that does most of the work. + */ +public class WDL +{ + public static boolean DEBUG = false; // Setting to false will supress debug output in chat console + // References: + public static Minecraft mc; // Reference to the Minecraft object + public static WorldClient wc; // Reference to the World object that WDL uses + public static NetworkManager nm = null; // Reference to a connection specific object. Used to detect a new connection. + public static EntityClientPlayerMP tp; + /* TODO: Realms support disabled until someone gets it working + public static McoServer mcos; + */ + + public static Container windowContainer; // Reference to the place where all the item stacks end up after receiving them. + public static int lastX = 0, lastY = 0, lastZ = 0; // Last right clicked block. Needed for TileEntity creation! + public static Entity lastEntity; // Last entity clicked (used for non-block tiles like minecarts with chests) + + public static SaveHandler saveHandler; // For player files and the level.dat file + public static IChunkLoader chunkLoader; // For the chunks (despite it's name it does also SAVE them) + + // Positions of newly created TileEntities that will overwrite the imported ones when saving: + public static HashSet newTileEntities = new HashSet(); + + public static GuiScreen guiToShowAsync = null; // A Gui to show in the next world tick. Needed so that the mouse works. + + // State variables: + public static boolean downloading = false; // Read-only outside of this class! + public static boolean isMultiworld = false; // Is this a multiworld server? + public static boolean propsFound = false; // Are there saved properties available? + public static boolean startOnChange = false; // Automatically restart after world changes? + + public static boolean saving = false; + public static boolean worldLoadingDeferred = false; + + // Names: + public static String worldName = "WorldDownloaderERROR"; // safe default + public static String baseFolderName = "WorldDownloaderERROR"; // safe default + + // Properties: + public static Properties baseProps; + public static Properties worldProps; + public static Properties defaultProps; + + // Initialization: + static + { + // Get the static Minecraft reference: + mc = (Minecraft)stealAndGetField(Minecraft.class, Minecraft.class); + + // Initialize the Properties template: + defaultProps = new Properties(); + defaultProps.setProperty("ServerName", ""); + defaultProps.setProperty("WorldName", ""); + defaultProps.setProperty("LinkedWorlds", ""); + defaultProps.setProperty("AutoStart", "false"); + defaultProps.setProperty("Backup", "off"); + defaultProps.setProperty("BackupPath", ""); // Represents folder or zip-file name + defaultProps.setProperty("BackupsToKeep", "1"); + defaultProps.setProperty("BackupCommand", ""); + defaultProps.setProperty("GameType", "keep"); + defaultProps.setProperty("Time", "keep"); + defaultProps.setProperty("Weather", "keep"); + defaultProps.setProperty("MapFeatures", "false"); + defaultProps.setProperty("RandomSeed", ""); + defaultProps.setProperty("GeneratorName", "flat"); + defaultProps.setProperty("GeneratorVersion", "0"); + defaultProps.setProperty("Spawn", "player"); + defaultProps.setProperty("SpawnX", "8"); + defaultProps.setProperty("SpawnY", "127"); + defaultProps.setProperty("SpawnZ", "8"); + defaultProps.setProperty("PlayerPos", "keep"); + defaultProps.setProperty("PlayerX", "8"); + defaultProps.setProperty("PlayerY", "127"); + defaultProps.setProperty("PlayerZ", "8"); + defaultProps.setProperty("PlayerHealth", "20"); + defaultProps.setProperty("PlayerFood", "20"); + + baseProps = new Properties(defaultProps); + worldProps = new Properties(baseProps); + } + + /** Starts the download */ + public static void start() + { + wc = mc.theWorld; + if (isMultiworld && worldName.isEmpty()) + { + // Ask the user which world is loaded + guiToShowAsync = new GuiWDLMultiworldSelect(null); + return; + } + + if (!propsFound) + { + // Never seen this world before. Ask user about multiworlds: + guiToShowAsync = new GuiWDLMultiworld(null); + return; + } + + worldProps = loadWorldProps(worldName); + + saveHandler = (SaveHandler)mc.getSaveLoader().getSaveLoader(getWorldFolderName(worldName), true); + chunkLoader = saveHandler.getChunkLoader(wc.provider); + + newTileEntities = new HashSet(); + + if (baseProps.getProperty("ServerName").isEmpty()) + baseProps.setProperty("ServerName", getServerName()); + + startOnChange = true; + downloading = true; + chatMsg("Download started"); + } + + /** Stops the download */ + public static void stop() + { + if (downloading) + { + // Indicate that downloading has stopped + downloading = false; + startOnChange = false; + chatMsg("Download stopped"); + + startSaveThread(); + } + } + + private static void startSaveThread() + { + // Indicate that we are saving + WDL.chatMsg("Save started."); + WDL.saving = true; + WDLSaveAsync saver = new WDLSaveAsync(); + Thread thread = new Thread(saver, "WDL Save Thread"); + thread.start(); + } + + /** Must be called after the static World object in Minecraft has been replaced */ + public static void onWorldLoad() + { + if (mc.isIntegratedServerRunning()) + return; + + // If already downloading + if (downloading) + { + // If not currently saving, stop the current download and start saving now + if (!saving) + { + WDL.chatMsg("World change detected. Download will start once current save completes."); + // worldLoadingDeferred = true; + startSaveThread(); + } + return; + } + loadWorld(); + } + + public static void loadWorld() + { + worldName = ""; // The new (multi-)world name is unknown at the moment + wc = mc.theWorld; + tp = mc.thePlayer; + windowContainer = tp.openContainer; + + // Is this a different server? + NetworkManager newNM = tp.sendQueue.getNetworkManager(); // tp.sendQueue.getNetManager() + + if (nm != newNM) + { + // Different server, different world! + chatDebug("onWorldLoad: different server!"); + nm = newNM; + loadBaseProps(); + if (baseProps.getProperty("AutoStart").equals("true")) + start(); + else + startOnChange = false; + } + else + { + // Same server, different world! + chatDebug("onWorldLoad: same server!"); + if (startOnChange) + start(); + } + } + + /** Must be called when the world is no longer used */ + public static void onWorldUnload() + { + } + + public static void onSaveComplete() + { + WDL.mc.getSaveLoader().flushCache(); + WDL.saveHandler.flush(); + WDL.wc = null; + + // If still downloading, load the current world and keep on downloading + if (downloading) + { + WDL.chatMsg("Save complete. Starting download again."); + WDL.loadWorld(); + return; + } + + WDL.chatMsg("Save complete. Your single player file is ready to play!"); + } + + /** Must be called when a chunk is no longer needed and should be removed */ + public static void onChunkNoLongerNeeded(Chunk unneededChunk) + { + if (unneededChunk == null || unneededChunk.isModified == false) + return; + + chatDebug("onChunkNoLongerNeeded: " + unneededChunk.xPosition + ", " + unneededChunk.zPosition); + saveChunk(unneededChunk); + } + + /** Must be called when a GUI that receives item stacks from the server is shown */ + public static void onItemGuiOpened() + { + if (mc.objectMouseOver == null) + return; + + if (mc.objectMouseOver.typeOfHit == MovingObjectType.ENTITY) + { + lastEntity = mc.objectMouseOver.entityHit; + } + else + { + lastEntity = null; + lastX = mc.objectMouseOver.blockX; + lastY = mc.objectMouseOver.blockY; + lastZ = mc.objectMouseOver.blockZ; + } + } + + /** Must be called when a GUI that triggered an onItemGuiOpened is no longer shown */ + public static void onItemGuiClosed() + { + String saveName = ""; + + // If the last thing clicked was an ENTITY + if (lastEntity != null) + { + + if (lastEntity instanceof EntityMinecart && windowContainer instanceof ContainerChest) + { + EntityMinecart emc = (EntityMinecart)lastEntity; + if (emc instanceof EntityMinecartChest) + { + EntityMinecartChest emcc = (EntityMinecartChest)emc; + for (int i = 0; i < emcc.getSizeInventory(); i++) + { + emcc.setInventorySlotContents(i, windowContainer.getSlot(i).getStack()); + saveName = "Storage Minecart contents"; + } + } + } + else if (lastEntity instanceof EntityVillager && windowContainer instanceof ContainerMerchant) + { + EntityVillager ev = (EntityVillager)lastEntity; + WDL.chatDebug("Saving villager offers is not yet supported."); + saveName = "Villager offers"; + return; + } + else + { + WDL.chatMsg("Unsupported entity cannot be saved:" + EntityList.getEntityString(lastEntity)); + } + WDL.chatDebug("Saved " + saveName + "."); + return; + } + + // Else, the last thing clicked was a TILE ENTITY + // Get the tile entity which we are going to update the inventory for + TileEntity te = wc.getTileEntity(lastX, lastY, lastZ); + if (te == null) + { + WDL.chatDebug("onItemGuiClosed could not get TE at " + lastX + " " + lastY + " " + lastZ); + return; + } + + if (windowContainer instanceof ContainerChest && te instanceof TileEntityChest) + { + if (windowContainer.inventorySlots.size() > 63) + { + TileEntity te2; + ChunkPosition cp1 = new ChunkPosition(lastX, lastY, lastZ); + ChunkPosition cp2; + TileEntityChest tec1, tec2; + if ((te2 = wc.getTileEntity(lastX, lastY, lastZ + 1)) instanceof TileEntityChest && + ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) + { + tec1 = (TileEntityChest)te; + tec2 = (TileEntityChest)te2; + cp2 = new ChunkPosition(lastX, lastY, lastZ + 1); + } + else if ((te2 = wc.getTileEntity(lastX, lastY, lastZ - 1)) instanceof TileEntityChest && + ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) + { + tec1 = (TileEntityChest)te2; + tec2 = (TileEntityChest)te; + cp2 = new ChunkPosition(lastX, lastY, lastZ - 1); + } + else if ((te2 = wc.getTileEntity(lastX + 1, lastY, lastZ)) instanceof TileEntityChest && + ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) + { + tec1 = (TileEntityChest)te; + tec2 = (TileEntityChest)te2; + cp2 = new ChunkPosition(lastX + 1, lastY, lastZ); + } + else if ((te2 = wc.getTileEntity(lastX - 1, lastY, lastZ)) instanceof TileEntityChest && + ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) + { + tec1 = (TileEntityChest)te2; + tec2 = (TileEntityChest)te; + cp2 = new ChunkPosition(lastX - 1, lastY, lastZ); + } + else + { + WDL.chatMsg("Could not save this chest!"); + return; + } + copyItemStacks(windowContainer, (TileEntityChest)tec1, 0); + copyItemStacks(windowContainer, (TileEntityChest)tec2, 27); + newTileEntities.add(cp1); + newTileEntities.add(cp2); + saveName = "Double Chest contents"; + } + // basic chest + else + { + copyItemStacks(windowContainer, (TileEntityChest)te, 0); + newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); + saveName = "Chest contents"; + } + } + else if (windowContainer instanceof ContainerChest && te instanceof TileEntityEnderChest) + { + InventoryEnderChest inventoryEnderChest = tp.getInventoryEnderChest(); + int inventorySize = inventoryEnderChest.getSizeInventory(); + int containerSize = windowContainer.inventorySlots.size(); + for (int i = 0; i < containerSize && i < inventorySize; i++) + { + inventoryEnderChest.setInventorySlotContents(i, windowContainer.getSlot(i).getStack()); + } + saveName = "Ender Chest contents"; + } + else if (windowContainer instanceof ContainerBrewingStand) + { + copyItemStacks(windowContainer, (TileEntityBrewingStand)te, 0); + newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); + saveName = "Brewing Stand contents"; + } + else if (windowContainer instanceof ContainerDispenser) + { + copyItemStacks(windowContainer, (TileEntityDispenser)te, 0); + newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); + saveName = "Dispenser contents"; + } + else if (windowContainer instanceof ContainerFurnace) + { + copyItemStacks(windowContainer, (TileEntityFurnace)te, 0); + newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); + saveName = "Furnace contents"; + } + else + { + WDL.chatDebug("onItemGuiClosed unhandled TE: " + te); + return; + } + + WDL.chatDebug("Saved " + saveName + "."); + return; + } + + /** + * Must be called when a block event is scheduled for the next tick. The caller has to check if WDL.downloading is true! + */ + public static void onBlockEvent(int x, int y, int z, Block block, int event, int param) + { + // if( blockID == Block.music.blockID ) + if (block == Blocks.noteblock) + { + TileEntityNote newTE = new TileEntityNote(); + newTE.field_145879_a = (byte)(param % 25); + wc.setTileEntity(x, y, z, newTE); + newTileEntities.add(new ChunkPosition(x, y, z)); + chatDebug("onBlockEvent: Note Block: " + x + " " + y + " " + z + " pitch: " + param + " - " + newTE); + } + // Pistons, Chests (open, close), EnderChests, ... (see references to WorldServer.addBlockEvent) + } + + /** Load the previously saved TileEntities and add them to the Chunk **/ + public static void importTileEntities(Chunk chunk) + { + File chunkSaveLocation = (File)stealAndGetField(chunkLoader, File.class); + DataInputStream dis = RegionFileCache.getChunkInputStream(chunkSaveLocation, chunk.xPosition, chunk.zPosition); + try + { + NBTTagCompound chunkNBT = CompressedStreamTools.read(dis); + + // NBTTagCompound levelNBT = chunkNBT.getCompoundTag( "Level" ); + NBTTagCompound levelNBT = chunkNBT.getCompoundTag("Level"); + + // The official code checks if the chunk is in the right location. Should I too?. + NBTTagList tileEntitiesNBT = levelNBT.getTagList("TileEntities", 10); + if (tileEntitiesNBT != null) + { + for (int i = 0; i < tileEntitiesNBT.tagCount(); i++) + { + NBTTagCompound tileEntityNBT = (NBTTagCompound)tileEntitiesNBT.getCompoundTagAt(i); + TileEntity te = TileEntity.createAndLoadEntity(tileEntityNBT); + String entityType = null; + if ((entityType = isImportableTileEntity(te)) != null) + { + if (!newTileEntities.contains(new ChunkPosition(te.field_145851_c, te.field_145848_d, te.field_145849_e))) + { + wc.setTileEntity(te.field_145851_c, te.field_145848_d, te.field_145849_e, te); + chatDebug("Loaded TE: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + } + else + { + chatDebug("Dropping old TE: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + } + } + else + { + chatDebug("Old TE is not importable: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + } + } + } + } + catch (Exception e) + { + } // Couldn't load the old chunk. Nothing unusual. Happens with every not downloaded chunk. + } + + /** Checks if the TileEntity should be imported. Only "problematic" TEs will be imported. */ + public static String isImportableTileEntity(TileEntity te) + { + Block block = wc.getBlock(te.field_145851_c, te.field_145848_d, te.field_145849_e); + if (block instanceof BlockChest && te instanceof TileEntityChest) + { + return "TileEntityChest"; + } + else if (block instanceof BlockDispenser && te instanceof TileEntityDispenser) + { + return "TileEntityDispenser"; + } + else if (block instanceof BlockFurnace && te instanceof TileEntityFurnace) + { + return "TileEntityFurnace"; + } + else if (block instanceof BlockNote && te instanceof TileEntityNote) + { + return "TileEntityNote"; + } + else if (block instanceof BlockBrewingStand && te instanceof TileEntityBrewingStand) + { + return "TileEntityBrewingStand"; + } + else + { + return null; + } + } + + /** Saves all remaining chunks, world info and player info. Usually called when stopping. */ + public static void saveEverything() + { + saveProps(); + + try + { + saveHandler.checkSessionLock(); + } + catch (MinecraftException e) + { + throw new RuntimeException("WorldDownloader: Couldn't get session lock for saving the world!"); + } + + NBTTagCompound playerNBT = new NBTTagCompound(); + tp.writeToNBT(playerNBT); + applyOverridesToPlayer(playerNBT); + + ISaveHandler saveHAndler = wc.getSaveHandler(); + AnvilSaveConverter saveConverter = (AnvilSaveConverter)mc.getSaveLoader(); + + wc.getWorldInfo().setSaveVersion(getSaveVersion(saveConverter)); + + NBTTagCompound worldInfoNBT = wc.getWorldInfo().cloneNBTCompound(playerNBT); + applyOverridesToWorldInfo(worldInfoNBT); + + savePlayer(playerNBT); + saveWorldInfo(worldInfoNBT); + try + { + saveChunks(); + } + catch (IllegalArgumentException e) + { + // TODO Auto-generated catch block + e.printStackTrace(); + } + catch (IllegalAccessException e) + { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + + /** Save the player (position, health, inventory, ...) into its own file in the players directory */ + public static void savePlayer(NBTTagCompound playerNBT) + { + chatDebug("Saving player data..."); + try + { + File playersDirectory = new File(saveHandler.getWorldDirectory(), "playerdata"); + File playerFile = new File(playersDirectory, tp.getUniqueID().toString() + ".dat.tmp"); + File playerFileOld = new File(playersDirectory, tp.getUniqueID().toString() + ".dat"); + + CompressedStreamTools.writeCompressed(playerNBT, new FileOutputStream(playerFile)); + + if (playerFileOld.exists()) + { + playerFileOld.delete(); + } + playerFile.renameTo(playerFileOld); + } + catch (Exception e) + { + throw new RuntimeException("Couldn't save the player!"); + } + chatDebug("Player data saved."); + } + + /** Save the world metadata (time, gamemode, seed, ...) into the level.dat file */ + public static void saveWorldInfo(NBTTagCompound worldInfoNBT) + { + chatDebug("Saving world metadata..."); + File saveDirectory = saveHandler.getWorldDirectory(); + NBTTagCompound dataNBT = new NBTTagCompound(); + dataNBT.setTag("Data", worldInfoNBT); + + try + { + File dataFile = new File(saveDirectory, "level.dat_new"); + File dataFileBackup = new File(saveDirectory, "level.dat_old"); + File dataFileOld = new File(saveDirectory, "level.dat"); + CompressedStreamTools.writeCompressed(dataNBT, new FileOutputStream(dataFile)); + + if (dataFileBackup.exists()) + { + dataFileBackup.delete(); + } + + dataFileOld.renameTo(dataFileBackup); + if (dataFileOld.exists()) + { + dataFileOld.delete(); + } + + dataFile.renameTo(dataFileOld); + if (dataFile.exists()) + { + dataFile.delete(); + } + } + catch (Exception e) + { + throw new RuntimeException("Couldn't save the world metadata!"); + } + chatDebug("World data saved."); + } + + /** + * Calls saveChunk for all currently loaded chunks + * + * @throws IllegalAccessException + * @throws IllegalArgumentException + */ + public static void saveChunks() throws IllegalArgumentException, IllegalAccessException + { + chatDebug("Saving chunks..."); + // Get the ChunkProviderClient from WorldClient + ChunkProviderClient chunkProvider = (ChunkProviderClient)wc.getChunkProvider(); + + // Get the hashArray field and set it accessible + Field hashArrayField = null; + Field[] lhmFields = LongHashMap.class.getDeclaredFields(); + //System.out.println("Looking for hashArray field..."); + for (Field f : lhmFields) + { + //System.out.println("Found field " + f.getName() + " of type " + f.getType().getName()); + if (f.getType().isArray()) + { + hashArrayField = f; + break; + } + } + if (hashArrayField == null) + { + chatMsg("Could not save chunks. Reflection error."); + return; + } + //System.out.println("Setting hashArrayField of type " + hashArrayField.getType().getName() + " accessible."); + hashArrayField.setAccessible(true); + + // Steal the instance of LongHashMap from our chunk provider + //System.out.println("Stealing field from chunkProvider (type=" + chunkProvider.getClass().getName() + ") of type " + LongHashMap.class.getName()); + LongHashMap lhm = (LongHashMap)stealAndGetField(chunkProvider, LongHashMap.class); +/* + if (lhm != null) + { + System.out.println("Successfully got lhm of type" + lhm.getClass().getName()); + } +*/ + // Get the LongHashMap.Entry[] through the now accessible field using a + // LongHashMap we steal from our chunkProvider. + Object[] hashArray = (Object[])hashArrayField.get(lhm); + //System.out.println("hashArray is of type " + hashArray.getClass().getName()); + + //System.out.println("hashArray.length = " + hashArray.length); + if (hashArray.length == 0) + { + chatError("ChunkProviderClient has no chunk data!"); + return; + } + else + { + // Get the actual class for LongHashMap.Entry + Class Entry = null; + for (Object o : hashArray) + { + if(o != null) + { + Entry = o.getClass(); + break; + } + } + if(Entry == null) + { + chatError("Could not get class for LongHashMap.Entry."); + return; + } + + // Find the private fields for 'value' and 'nextEntry' in + // LongHashMap.Entry and make them accessible + Field valueField = Entry.getDeclaredFields()[1]; // value + valueField.setAccessible(true); + Field nextEntryField = Entry.getDeclaredFields()[2]; // nextEntry + nextEntryField.setAccessible(true); + + WDLSaveProgressReporter progressReporter = new WDLSaveProgressReporter(); + progressReporter.start(); + + for (int i = 0; i < hashArray.length; ++i) + { + // for (LongHashMap.Entry entry = hashArray[i]; entry != null; + // entry = entry.nextEntry) + for (Object lhme = hashArray[i]; lhme != null; lhme = nextEntryField.get(lhme)) + { + // Chunk c = (Chunk)lhme.getValue(); + Chunk c = (Chunk)valueField.get(lhme); + if (c != null && c.isModified) + { + saveChunk(c); + + try + { + ThreadedFileIOBase.threadedIOInstance.waitForFinish(); + } catch (Exception e) + { + chatMsg("Threw exception waiting for asynchronous IO to finish. Hmmm."); + } + } else + { + chatMsg("Didn\'t save chunk " + c.xPosition + " " + c.zPosition + " because isModified is false!"); + } + } + } + chatDebug("Chunk data saved."); + } + } + + /** + * Renders World Downloader save progress bar + */ + /* + * public static void renderSaveProgress() { if (saveProgress == 0) return; FontRenderer fontRendererObj = mc.fontRendererObj; ScaledResolution scaledResolution = new ScaledResolution(mc.gameSettings, + * mc.displayWidth, mc.displayHeight); int scaledWidth = scaledResolution.getScaledWidth(); short width = 182; int xPos = scaledWidth / 2 - width / 2; byte yPos = 12; + * mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 74, width, 5); mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 74, width, 5); mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 79, + * saveProgress * width, 5); + * + * String var9 = "Save Progress"; fontRendererObj.drawStringWithShadow(var9, scaledWidth / 2 - fontRendererObj.getStringWidth(var9) / 2, yPos - 10, 16711935); GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); + * GL11.glBindTexture(GL11.GL_TEXTURE_2D, mc.renderEngine.getTexture("/gui/icons.png")); } + */ + + /** Import all not overwritten TileEntities, then save the chunk */ + public static void saveChunk(Chunk c) + { + // chatMsg( "saveChunk at " + c.xPosition + " " + c.zPosition); + importTileEntities(c); + c.isTerrainPopulated = true; + try + { + chunkLoader.saveChunk(wc, c); + } + catch (Exception e) + { + // Better tell the player that something didn't work: + chatMsg("Chunk at chunk position " + c.xPosition + "," + c.zPosition + " can't be saved!"); + } + } + + /** Loads the server specific set of properties */ + public static void loadBaseProps() + { + baseFolderName = getBaseFolderName(); + baseProps = new Properties(defaultProps); + try + { + baseProps.load(new FileReader(new File(mc.mcDataDir, "saves/" + baseFolderName + "/WorldDownloader.txt"))); + propsFound = true; + } + catch (FileNotFoundException e) + { + propsFound = false; + } + catch (Exception e) + { + } + + if (baseProps.getProperty("LinkedWorlds").isEmpty()) + { + isMultiworld = false; + worldProps = new Properties(baseProps); + } + else + isMultiworld = true; + } + + /** Loads the world specific set of properties */ + public static Properties loadWorldProps(String theWorldName) + { + Properties ret = new Properties(baseProps); + if (!theWorldName.isEmpty()) + { + String folder = getWorldFolderName(theWorldName); + + try + { + ret.load(new FileReader(new File(mc.mcDataDir, "saves/" + folder + "/WorldDownloader.txt"))); + } + catch (Exception e) + { + return null; + } + } + return ret; + } + + /** Saves the currently used base and world properties in the corresponding folders */ + public static void saveProps() + { + saveProps(worldName, worldProps); + } + + /** Saves the specified world properties and the base properties in the corresponding folders */ + public static void saveProps(String theWorldName, Properties theWorldProps) + { + if (theWorldName.length() > 0) + { + String folder = getWorldFolderName(theWorldName); + try + { + theWorldProps.store(new FileWriter(new File(mc.mcDataDir, "saves/" + folder + "/WorldDownloader.txt")), ""); + } + catch (Exception e) + { + } + } + else if (!isMultiworld) + { + baseProps.putAll(theWorldProps); + } + + File baseFolder = new File(mc.mcDataDir, "saves/" + baseFolderName); + baseFolder.mkdirs(); + try + { + baseProps.store(new FileWriter(new File(baseFolder, "WorldDownloader.txt")), ""); + } + catch (Exception e) + { + } + } + + /** Change player specific fields according to the overrides found in the properties file */ + public static void applyOverridesToPlayer(NBTTagCompound playerNBT) + { + // Health + String health = worldProps.getProperty("PlayerHealth"); + if (!health.equals("keep")) + { + short h = Short.parseShort(health); + playerNBT.setShort("Health", h); + } + + // foodLevel, foodTimer, foodSaturationLevel, foodExhaustionLevel + String food = worldProps.getProperty("PlayerFood"); + if (!food.equals("keep")) + { + int f = Integer.parseInt(food); + playerNBT.setInteger("foodLevel", f); + playerNBT.setInteger("foodTickTimer", 0); + if (f == 20) + { + playerNBT.setFloat("foodSaturationLevel", 5.0f); + } + else + { + playerNBT.setFloat("foodSaturationLevel", 0.0f); + } + playerNBT.setFloat("foodExhaustionLevel", 0.0f); + } + + // Player Position + String playerPos = worldProps.getProperty("PlayerPos"); + if (playerPos.equals("xyz")) + { + int x = Integer.parseInt(worldProps.getProperty("PlayerX")); + int y = Integer.parseInt(worldProps.getProperty("PlayerY")); + int z = Integer.parseInt(worldProps.getProperty("PlayerZ")); + + NBTTagList pos = playerNBT.getTagList("Pos", 6); + // Out with the old, in with the new + pos.removeTag(0); // removeTag + pos.removeTag(0); + pos.removeTag(0); + pos.appendTag(new NBTTagDouble(x + 0.5D)); // appendTag + pos.appendTag(new NBTTagDouble((double)y + 0.621D)); // Player height + pos.appendTag(new NBTTagDouble(x + 0.5D)); + + NBTTagList motion = playerNBT.getTagList("Motion", 6); + // Out with the old, in with the new + motion.removeTag(0); + motion.removeTag(0); + motion.removeTag(0); + motion.appendTag(new NBTTagDouble(0.0D)); + motion.appendTag(new NBTTagDouble(-0.0001D)); // Needed to land on the ground + motion.appendTag(new NBTTagDouble(0.0D)); + + NBTTagList rotation = playerNBT.getTagList("Rotation", 5); + // Out with the old, in with the new + rotation.removeTag(0); + rotation.removeTag(0); + rotation.appendTag(new NBTTagFloat(0.0f)); + rotation.appendTag(new NBTTagFloat(0.0f)); + } + } + + /** Change world and generator specific fields according to the overrides found in the properties file */ + public static void applyOverridesToWorldInfo(NBTTagCompound worldInfoNBT) + { + // LevelName + String baseName = baseProps.getProperty("ServerName"); + String worldName = worldProps.getProperty("WorldName"); + if (worldName.isEmpty()) + { + worldInfoNBT.setString("LevelName", baseName); + } + else + { + worldInfoNBT.setString("LevelName", baseName + " - " + worldName); + } + + // GameType + String gametypeOption = worldProps.getProperty("GameType"); + if (gametypeOption.equals("keep")) + { + if (tp.capabilities.isCreativeMode) // capabilities + { + worldInfoNBT.setInteger("GameType", 1); // Creative + } + else + { + worldInfoNBT.setInteger("GameType", 0); // Survival + } + } + else if (gametypeOption.equals("survival")) + { + worldInfoNBT.setInteger("GameType", 0); + } + else if (gametypeOption.equals("creative")) + { + worldInfoNBT.setInteger("GameType", 1); + } + else if (gametypeOption.equals("hardcore")) + { + worldInfoNBT.setInteger("GameType", 0); + worldInfoNBT.setBoolean("hardcore", true); + } + + // Time + String timeOption = worldProps.getProperty("Time"); + if (!timeOption.equals("keep")) + { + long t = Integer.parseInt(timeOption); + worldInfoNBT.setLong("Time", t); + } + + // RandomSeed + String randomSeed = worldProps.getProperty("RandomSeed"); + long seed = 0; + if (!randomSeed.isEmpty()) + { + try + { + seed = Long.parseLong(randomSeed); + } + catch (NumberFormatException numberformatexception) + { + seed = randomSeed.hashCode(); + } + } + worldInfoNBT.setLong("RandomSeed", seed); + + // MapFeatures + boolean mapFeatures = Boolean.parseBoolean(worldProps.getProperty("MapFeatures")); + worldInfoNBT.setBoolean("MapFeatures", mapFeatures); + + // generatorName + String generatorName = worldProps.getProperty("GeneratorName"); + worldInfoNBT.setString("generatorName", generatorName); + + // generatorVersion + int generatorVersion = Integer.parseInt(worldProps.getProperty("GeneratorVersion")); + worldInfoNBT.setInteger("generatorVersion", generatorVersion); + + // Weather + String weather = worldProps.getProperty("Weather"); + if (weather.equals("sunny")) + { + worldInfoNBT.setBoolean("raining", false); + worldInfoNBT.setInteger("rainTime", 0); + worldInfoNBT.setBoolean("thundering", false); + worldInfoNBT.setInteger("thunderTime", 0); + } + if (weather.equals("rain")) + { + worldInfoNBT.setBoolean("raining", true); + worldInfoNBT.setInteger("rainTime", 24000); + worldInfoNBT.setBoolean("thundering", false); + worldInfoNBT.setInteger("thunderTime", 0); + } + if (weather.equals("thunderstorm")) + { + worldInfoNBT.setBoolean("raining", true); + worldInfoNBT.setInteger("rainTime", 24000); + worldInfoNBT.setBoolean("thundering", true); + worldInfoNBT.setInteger("thunderTime", 24000); + } + + // Spawn + String spawn = worldProps.getProperty("Spawn"); + if (spawn.equals("player")) + { + int x = (int)Math.floor(tp.posX); + int y = (int)Math.floor(tp.posY); + int z = (int)Math.floor(tp.posZ); + worldInfoNBT.setInteger("SpawnX", x); + worldInfoNBT.setInteger("SpawnY", y); + worldInfoNBT.setInteger("SpawnZ", z); + worldInfoNBT.setBoolean("initialized", true); + } + else if (spawn.equals("xyz")) + { + int x = Integer.parseInt(worldProps.getProperty("SpawnX")); + int y = Integer.parseInt(worldProps.getProperty("SpawnY")); + int z = Integer.parseInt(worldProps.getProperty("SpawnZ")); + worldInfoNBT.setInteger("SpawnX", x); + worldInfoNBT.setInteger("SpawnY", y); + worldInfoNBT.setInteger("SpawnZ", z); + worldInfoNBT.setBoolean("initialized", true); + } + } + + /** Get the name of the server the user specified it in the server list */ + public static String getServerName() + { + try + { + if (mc.func_147104_D() != null) // getServerData + { + return mc.func_147104_D().serverName; + } + /* TODO: Realms support disabled until someone gets it working + else if (mcos != null) + { + return "MCRealm: " + URLDecoder.decode(mcos.field_148810_b, "UTF-8"); + } + */ + } + catch (Exception e) + { + } + return "Unidentified Server"; + } + + /** Get the base folder name for the server we are connected to */ + public static String getBaseFolderName() + { + return getServerName().replaceAll("\\W+", "_"); + } + + /** Get the folder name for the specified world */ + public static String getWorldFolderName(String theWorldName) + { + if (theWorldName.isEmpty()) + { + return baseFolderName; + } + else + { + return baseFolderName + " - " + theWorldName; + } + } + + public static void copyItemStacks(Container c, IInventory i, int startInContainerAt) + { + int containerSize = c.inventorySlots.size(); + int inventorySize = i.getSizeInventory(); + int nc = startInContainerAt; + int ni = 0; + + while ((nc < containerSize) && (ni < inventorySize)) + { + ItemStack is = c.getSlot(nc).getStack(); + i.setInventorySlotContents(ni, is); + ni++; + nc++; + } + } + + /** Adds a chat message with a World Downloader prefix */ + public static void chatMsg(String msg) + { + // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! + mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A7c[WorldDL]\u00A76 " + msg)); + } + + /** Adds a chat message with a World Downloader prefix */ + public static void chatDebug(String msg) + { + if (!WDL.DEBUG) + return; + // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! + mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); + } + + /** Adds a chat message with a World Downloader prefix */ + public static void chatError(String msg) + { + // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! + mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A72[WorldDL]\u00A74 " + msg)); + } + + + private static int getSaveVersion(AnvilSaveConverter asc) + { + int saveVersion = 0; + try + { + Method[] anvilMethods = AnvilSaveConverter.class.getDeclaredMethods(); + for (Method m : anvilMethods) + { + if (m.getParameterTypes().length == 0 && m.getReturnType().equals(int.class)) + { + m.setAccessible(true); + saveVersion = (Integer)m.invoke(asc); + break; + } + } + } catch (Throwable t) + { + // TODO Auto-generated catch block + t.printStackTrace(); + } + if (saveVersion == 0) + { + saveVersion = 19133; // Version for 1.7.2 just in case we can't get + // it + } + return saveVersion; + } + + + /** + * Uses Java's reflection API to get access to an unaccessible field + * + * @param typeOfClass + * Class that the field should be read from + * @param typeOfField + * The type of the field + * @return An Object of type Field + */ + public static Field stealField(Class typeOfClass, Class typeOfField) + { + //System.out.println("stealField: typeOfClass = " + typeOfClass.getName()); + //System.out.println("stealField: typeOfField = " + typeOfField.getName()); + Field[] fields = typeOfClass.getDeclaredFields(); + for (Field f : fields) + { + //System.out.println("stealField: Found field " + f.getName() + + // " of type " + f.getType()); + + if (f.getType().equals(typeOfField)) + { + try + { + f.setAccessible(true); + return f; + } + catch (Exception e) + { + break; // Throw the Exception + } + } + } + throw new RuntimeException("WorldDownloader: Couldn't steal Field of type \"" + typeOfField + "\" from class \"" + typeOfClass + "\" !"); + } + + /** + * Uses Java's reflection API to get access to an unaccessible field + * + * @param object + * Object that the field should be read from or the type of the object if the field is static + * @param typeOfField + * The type of the field + * @return The value of the field + */ + public static Object stealAndGetField(Object object, Class typeOfField) + { + Class typeOfObject; + + if (object instanceof Class) // User asked for static field: + { + typeOfObject = (Class)object; + object = null; + } + else + { + typeOfObject = object.getClass(); + } + + try + { + Field f = stealField(typeOfObject, typeOfField); + return f.get(object); + } + catch (Exception e) + { + throw new RuntimeException("WorldDownloader: Couldn't get Field of type \"" + typeOfField + "\" from object \"" + object + "\" !"); + } + } + + public static void handleServerSeedMessage(String msg) + { + if (downloading && msg.startsWith("Seed: ")) + { + String seed = msg.substring(6); + worldProps.setProperty("RandomSeed", seed); + WDL.chatMsg("Setting single-player world seed to " + seed); + } + /* + * else { WDL.chatMsg("Could not retrieve server seed"); } + */ + } +} diff --git a/forge/src/main/java/wdl/WDLSaveAsync.java b/forge/src/main/java/wdl/WDLSaveAsync.java new file mode 100644 index 0000000..19686f7 --- /dev/null +++ b/forge/src/main/java/wdl/WDLSaveAsync.java @@ -0,0 +1,11 @@ +package net.minecraft.wdl; + +public class WDLSaveAsync implements Runnable +{ + public void run() + { + WDL.saveEverything(); + WDL.saving = false; + WDL.onSaveComplete(); + } +} diff --git a/forge/src/main/java/wdl/WDLSaveProgressReporter.java b/forge/src/main/java/wdl/WDLSaveProgressReporter.java new file mode 100644 index 0000000..72a07d8 --- /dev/null +++ b/forge/src/main/java/wdl/WDLSaveProgressReporter.java @@ -0,0 +1,27 @@ +package net.minecraft.wdl; + +public class WDLSaveProgressReporter implements Runnable +{ + public void run() + { + while (WDL.saving) + { + WDL.chatMsg("Saving..."); + + try + { + Thread.sleep(10000L); + } + catch (InterruptedException var2) + { + var2.printStackTrace(); + } + } + } + + public void start() + { + Thread var1 = new Thread(this); + var1.start(); + } +} From ac6c57be0a7a9e18936187da4a26f7ad51c05f3b Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Thu, 3 Jul 2014 07:24:21 +0200 Subject: [PATCH 08/16] Code cleanup --- forge/src/main/java/wdl/GuiWDL.java | 11 +- forge/src/main/java/wdl/GuiWDLBackup.java | 170 ------------------ forge/src/main/java/wdl/GuiWDLGenerator.java | 2 +- forge/src/main/java/wdl/GuiWDLMultiworld.java | 2 +- .../main/java/wdl/GuiWDLMultiworldSelect.java | 2 +- forge/src/main/java/wdl/GuiWDLPlayer.java | 2 +- forge/src/main/java/wdl/GuiWDLWorld.java | 2 +- forge/src/main/java/wdl/WDL.java | 14 +- forge/src/main/java/wdl/WDLSaveAsync.java | 2 +- .../java/wdl/WDLSaveProgressReporter.java | 2 +- 10 files changed, 9 insertions(+), 200 deletions(-) delete mode 100644 forge/src/main/java/wdl/GuiWDLBackup.java diff --git a/forge/src/main/java/wdl/GuiWDL.java b/forge/src/main/java/wdl/GuiWDL.java index 14894fa..fa84f8a 100644 --- a/forge/src/main/java/wdl/GuiWDL.java +++ b/forge/src/main/java/wdl/GuiWDL.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiScreen; @@ -59,11 +59,6 @@ public void initGui() this.autoStartBtn = new GuiButton(1, w - 100, hi, "Start Download: ERROR"); this.buttonList.add(this.autoStartBtn); this.updateAutoStart(false); - - hi += 22; - this.backupBtn = new GuiButton(2, w - 100, hi, "Backup Options..."); - this.backupBtn.enabled = false; - this.buttonList.add(this.backupBtn); hi += 28; this.worldOverrides = new GuiButton(4, w - 100, hi, "World Overrides..."); this.buttonList.add(this.worldOverrides); @@ -91,10 +86,6 @@ protected void actionPerformed(GuiButton guibutton) { this.updateAutoStart(true); } - else if (guibutton.id == 2) // Backup - { - this.mc.displayGuiScreen(new GuiWDLBackup(this)); - } else if (guibutton.id == 4) // World Overrides { this.mc.displayGuiScreen(new GuiWDLWorld(this)); diff --git a/forge/src/main/java/wdl/GuiWDLBackup.java b/forge/src/main/java/wdl/GuiWDLBackup.java deleted file mode 100644 index 4d3634e..0000000 --- a/forge/src/main/java/wdl/GuiWDLBackup.java +++ /dev/null @@ -1,170 +0,0 @@ -package net.minecraft.wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; - -public class GuiWDLBackup extends GuiScreen -{ - private String title = ""; - - private GuiScreen parent; - - private GuiTextField commandField; - private GuiButton backupBtn; - - boolean cmdBox = false; - - public GuiWDLBackup(GuiScreen parent) - { - this.parent = parent; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - - this.title = "Backup Options for " + WDL.baseFolderName.replace('@', ':'); - - int w = this.width / 2; - int h = this.height / 4; - - this.backupBtn = new GuiButton(10, w - 100, h + 105, "Backup: ERROR"); - this.buttonList.add(this.backupBtn); - this.updateBackup(false); - - this.commandField = new GuiTextField(this.fontRendererObj, w - 98, h + 126, 196, 17); - - this.buttonList.add(new GuiButton(100, w - 100, h + 150, "Done")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - if (var1.id == 10) - { - this.updateBackup(true); - } - else if (var1.id == 100) - { - this.mc.displayGuiScreen(this.parent); - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - - if (this.cmdBox) - { - this.commandField.mouseClicked(var1, var2, var3); - } - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - this.commandField.textboxKeyTyped(var1, var2); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.commandField.updateCursorCounter(); - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); - this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); - this.drawString(this.fontRendererObj, "Name:", this.width / 2 - 99, 50, 16777215); - - if (this.cmdBox) - { - this.commandField.drawTextBox(); - } - - super.drawScreen(var1, var2, var3); - } - - public void updateBackup(boolean var1) - { - this.cmdBox = false; - String var2 = WDL.baseProps.getProperty("Backup"); - - if (var2 == "off") - { - if (var1) - { - WDL.baseProps.setProperty("Backup", "folder"); - this.updateBackup(false); - } - else - { - this.backupBtn.displayString = "Backup: Disabled"; - } - } - else if (var2 == "folder") - { - if (var1) - { - WDL.baseProps.setProperty("Backup", "zip"); - this.updateBackup(false); - } - else - { - this.backupBtn.displayString = "Backup: Copy World Folder"; - } - } - else if (var2 == "zip") - { - if (var1) - { - WDL.baseProps.setProperty("Backup", "command"); - this.updateBackup(false); - } - else - { - this.backupBtn.displayString = "Backup: Zip World Folder"; - } - } - else if (var2 == "command") - { - if (var1) - { - WDL.baseProps.setProperty("Backup", "off"); - this.updateBackup(false); - } - else - { - this.backupBtn.displayString = "Backup: Run the following command"; - this.cmdBox = true; - } - } - else - { - WDL.baseProps.setProperty("Backup", "off"); - this.updateBackup(false); - } - } -} diff --git a/forge/src/main/java/wdl/GuiWDLGenerator.java b/forge/src/main/java/wdl/GuiWDLGenerator.java index 753cfb9..f118e9d 100644 --- a/forge/src/main/java/wdl/GuiWDLGenerator.java +++ b/forge/src/main/java/wdl/GuiWDLGenerator.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiScreen; diff --git a/forge/src/main/java/wdl/GuiWDLMultiworld.java b/forge/src/main/java/wdl/GuiWDLMultiworld.java index dabed3e..a3acd41 100644 --- a/forge/src/main/java/wdl/GuiWDLMultiworld.java +++ b/forge/src/main/java/wdl/GuiWDLMultiworld.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiScreen; diff --git a/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java b/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java index 195a096..b979bf6 100644 --- a/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java +++ b/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import java.io.File; import java.util.Properties; diff --git a/forge/src/main/java/wdl/GuiWDLPlayer.java b/forge/src/main/java/wdl/GuiWDLPlayer.java index aaa0df7..6cbb579 100644 --- a/forge/src/main/java/wdl/GuiWDLPlayer.java +++ b/forge/src/main/java/wdl/GuiWDLPlayer.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiScreen; diff --git a/forge/src/main/java/wdl/GuiWDLWorld.java b/forge/src/main/java/wdl/GuiWDLWorld.java index eefe35b..255b568 100644 --- a/forge/src/main/java/wdl/GuiWDLWorld.java +++ b/forge/src/main/java/wdl/GuiWDLWorld.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiScreen; diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index 024f679..7bb37d7 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -1,23 +1,15 @@ -package net.minecraft.wdl; +package wdl; -import java.io.Console; import java.io.DataInputStream; import java.io.File; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.FileReader; import java.io.FileWriter; -import java.io.IOException; -import java.lang.reflect.Array; import java.lang.reflect.Field; -import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; -import java.util.HashMap; import java.util.HashSet; -import java.util.Iterator; -import java.util.List; import java.util.Properties; -import java.net.URLDecoder; import net.minecraft.block.Block; import net.minecraft.block.BlockBrewingStand; @@ -60,7 +52,6 @@ import net.minecraft.tileentity.TileEntityNote; import net.minecraft.util.ChatComponentText; import net.minecraft.util.LongHashMap; -import net.minecraft.util.MovingObjectPosition; import net.minecraft.util.MovingObjectPosition.MovingObjectType; import net.minecraft.world.ChunkPosition; import net.minecraft.world.MinecraftException; @@ -71,9 +62,6 @@ import net.minecraft.world.storage.ISaveHandler; import net.minecraft.world.storage.SaveHandler; import net.minecraft.world.storage.ThreadedFileIOBase; -import net.minecraft.world.storage.WorldInfo; - -import org.lwjgl.opengl.GL11; /** * This is the main class that does most of the work. diff --git a/forge/src/main/java/wdl/WDLSaveAsync.java b/forge/src/main/java/wdl/WDLSaveAsync.java index 19686f7..894aa0b 100644 --- a/forge/src/main/java/wdl/WDLSaveAsync.java +++ b/forge/src/main/java/wdl/WDLSaveAsync.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; public class WDLSaveAsync implements Runnable { diff --git a/forge/src/main/java/wdl/WDLSaveProgressReporter.java b/forge/src/main/java/wdl/WDLSaveProgressReporter.java index 72a07d8..9d12652 100644 --- a/forge/src/main/java/wdl/WDLSaveProgressReporter.java +++ b/forge/src/main/java/wdl/WDLSaveProgressReporter.java @@ -1,4 +1,4 @@ -package net.minecraft.wdl; +package wdl; public class WDLSaveProgressReporter implements Runnable { From d6714ba44f0e463e6d288cb5e8120b186014e88a Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 7 Jul 2014 16:23:29 +0200 Subject: [PATCH 09/16] Forge port works! Still a few things missing... --- forge/README | 8 + forge/src/main/java/wdl/ForgeMod.java | 182 ++++++++++++++++---- forge/src/main/java/wdl/GuiWDLPlayer.java | 10 +- forge/src/main/java/wdl/GuiWDLWorld.java | 10 +- forge/src/main/java/wdl/WDL.java | 114 +++++++++--- forge/src/main/java/wdl/WDLWorldAccess.java | 68 ++++++++ 6 files changed, 326 insertions(+), 66 deletions(-) create mode 100644 forge/src/main/java/wdl/WDLWorldAccess.java diff --git a/forge/README b/forge/README index a212d8f..00125e1 100644 --- a/forge/README +++ b/forge/README @@ -16,4 +16,12 @@ There is no need to download the latest version! The commands in the next sectio * Run command: `gradlew setupDecompWorkspace` * Run command: `gradlew eclipse` +## Building the mod +* Open a command window in this folder (Windows: Shift+Click -> "Open command window here") +* Run command: `gradlew build` +* The jar file containing the mod can be found in the subfolder **build/libs** + +## Other gradle "tasks" +`gradlew tasks` + [More information about Forge](http://www.minecraftforge.net/forum/index.php/topic,14048.0.html) \ No newline at end of file diff --git a/forge/src/main/java/wdl/ForgeMod.java b/forge/src/main/java/wdl/ForgeMod.java index 786c03d..8e966b0 100644 --- a/forge/src/main/java/wdl/ForgeMod.java +++ b/forge/src/main/java/wdl/ForgeMod.java @@ -1,101 +1,217 @@ package wdl; -import net.minecraft.client.Minecraft; -import net.minecraft.util.ChatComponentText; +import java.util.List; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiIngameMenu; +import net.minecraft.client.gui.GuiScreen; import net.minecraftforge.client.event.ClientChatReceivedEvent; import net.minecraftforge.client.event.GuiOpenEvent; import net.minecraftforge.client.event.GuiScreenEvent.ActionPerformedEvent; import net.minecraftforge.client.event.GuiScreenEvent.InitGuiEvent; import net.minecraftforge.common.MinecraftForge; import net.minecraftforge.event.world.ChunkEvent; +import net.minecraftforge.event.world.NoteBlockEvent; import net.minecraftforge.event.world.WorldEvent; +import cpw.mods.fml.common.FMLCommonHandler; import cpw.mods.fml.common.Mod; import cpw.mods.fml.common.Mod.EventHandler; import cpw.mods.fml.common.event.FMLInitializationEvent; import cpw.mods.fml.common.eventhandler.SubscribeEvent; +import cpw.mods.fml.common.network.FMLNetworkEvent.ClientDisconnectionFromServerEvent; + +// TODO: Use the Forge mod proxy stuff to avoid performance impact in singleplayer. -@Mod( modid = ForgeMod.MODID, version = ForgeMod.VERSION ) +@Mod(modid = ForgeMod.MODID, version = ForgeMod.VERSION) public class ForgeMod { public static final String MODID = "WDL"; public static final String VERSION = "1.7.10"; - private boolean debug = true; - Minecraft mc; - @EventHandler - public void init( FMLInitializationEvent event ) + public void init(FMLInitializationEvent event) { - MinecraftForge.EVENT_BUS.register( this ); - mc = Minecraft.getMinecraft(); + FMLCommonHandler.instance().bus().register(this); + MinecraftForge.EVENT_BUS.register(this); } - @SubscribeEvent - public void onChunkLoad( ChunkEvent.Load event ) + public void onChunkLoad(ChunkEvent.Load event) + { + if(event.world != WDL.wc) + { + WDL.onWorldLoad(); + } + } + + @SubscribeEvent + public void onChunkUnload(ChunkEvent.Unload event) { - if( event.world.isRemote ) + if(WDL.downloading && event.world.isRemote) { - chatDebug("Loaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + WDL.onChunkNoLongerNeeded(event.getChunk()); } } @SubscribeEvent - public void onChunkUnload( ChunkEvent.Unload event ) + public void onWorldLoad(WorldEvent.Load event) { - if( event.world.isRemote ) + if(event.world.isRemote) { - chatDebug("Unloaded chunk: " + event.getChunk().xPosition + " " + event.getChunk().zPosition ); + //WDL.onWorldLoad(); //Does NOT work! The player is not yet initialized here. + event.world.addWorldAccess(new WDLWorldAccess()); } } + /* @SubscribeEvent - public void onWorldLoad( WorldEvent.Load event ) + public void onWorldUnload(WorldEvent.Unload event) { - if( event.world.isRemote ) + if(event.world.isRemote) { - chatDebug("Loaded world: " + event.world.toString() ); + // not used + //WDL.onWorldUnload(); } } + */ @SubscribeEvent - public void onWorldUnload( WorldEvent.Unload event ) + public void onGuiSwitch(GuiOpenEvent event) { - if( event.world.isRemote ) + + if(WDL.downloading) { - chatDebug("Unloaded world: " + event.world.toString() ); + if(WDL.tp.openContainer != WDL.windowContainer) + { + if(WDL.tp.openContainer == WDL.tp.inventoryContainer) + { + WDL.onItemGuiClosed(); + } + WDL.windowContainer = WDL.tp.openContainer; + } } + } @SubscribeEvent - public void onGuiDrawn( InitGuiEvent.Post event ) + public void onNoteBlock(NoteBlockEvent event) { - chatDebug("GUI initialized: " + event.gui ); + if(WDL.downloading && event.world.isRemote) + { + WDL.onBlockEvent(event.x, event.y, event.z, event.block, 0, event.getVanillaNoteId()); + } } @SubscribeEvent - public void onGuiSwitch( GuiOpenEvent event ) + public void onDisconnect(ClientDisconnectionFromServerEvent event) { - chatDebug("GUI switched: " + event.gui ); + WDL.stop(); } + /* @SubscribeEvent - public void onGuiButtonClicked( ActionPerformedEvent.Pre event) + public void onConnect(ClientConnectedToServerEvent event) { - chatDebug("Button clicked: " + event.button ); + // mc.theWorld is still null! } + */ @SubscribeEvent - public void onChatMessage( ClientChatReceivedEvent event ) + public void onGuiDrawn(InitGuiEvent.Post event) { - // Parse seed if found + if(!WDL.mc.isIntegratedServerRunning() && event.gui instanceof GuiIngameMenu) + { + injectWDLButtons((GuiIngameMenu)event.gui, event.buttonList); + } + + if(WDL.downloading) + { + if(WDL.tp.openContainer != WDL.windowContainer) + { + if(WDL.tp.openContainer != WDL.tp.inventoryContainer) + { + WDL.onItemGuiOpened(); + } + WDL.windowContainer = WDL.tp.openContainer; + } + } } - private void chatDebug( String msg ) + @SubscribeEvent + public void onGuiButtonClicked(ActionPerformedEvent.Pre event) { - if( debug ) + if(!WDL.mc.isIntegratedServerRunning() && event.gui instanceof GuiIngameMenu) + { + handleWDLButtonClick((GuiIngameMenu)event.gui, event.button); + } + } + + @SubscribeEvent + public void onChatMessage(ClientChatReceivedEvent event) + { + WDL.handleServerSeedMessage(event.message.getFormattedText()); + } + + + // Add World Downloader buttons to GuiIngameMenu + private void injectWDLButtons(GuiIngameMenu gui, List buttonList) + { + int insertAtYPos = 0; + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.id == 5) // Button "Achievements" + { + insertAtYPos = btn.yPosition + btn.height + 4; + break; + } + } + + // Move other buttons down one slot (= 24 height units) + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.yPosition >= insertAtYPos) + { + btn.yPosition += 24; + } + } + + // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" + GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); + GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); + + wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); + wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); + + wdlOptions.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); + + buttonList.add(wdlDownload); + buttonList.add(wdlOptions); + } + + private void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) + { + if(button.id == 0x57444C73) // "Start/Stop Download" + { + if (WDL.downloading) + { + WDL.stop(); + WDL.mc.displayGuiScreen((GuiScreen)null); + WDL.mc.setIngameFocus(); + } + else + { + WDL.start(); + } + } + else if( button.id == 0x57444C6F) // "..." (options) + { + WDL.mc.displayGuiScreen(new GuiWDL(gui)); + } + else if( button.id == 1) // "Disconnect" { - mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); + WDL.stop(); } } } diff --git a/forge/src/main/java/wdl/GuiWDLPlayer.java b/forge/src/main/java/wdl/GuiWDLPlayer.java index 6cbb579..b2571bc 100644 --- a/forge/src/main/java/wdl/GuiWDLPlayer.java +++ b/forge/src/main/java/wdl/GuiWDLPlayer.java @@ -48,9 +48,9 @@ public void initGui() this.posX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); this.posY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); this.posZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); - this.posX.func_146203_f(7); - this.posY.func_146203_f(7); - this.posZ.func_146203_f(7); + this.posX.setMaxStringLength(7); + this.posY.setMaxStringLength(7); + this.posZ.setMaxStringLength(7); var3 += 18; this.pickPosBtn = new GuiButton(4, var1 - 0, var3, 100, 20, "Current position"); this.buttonList.add(this.pickPosBtn); @@ -217,7 +217,7 @@ private void updatePlayerPos(boolean var1) { String var2 = WDL.worldProps.getProperty("PlayerPos"); this.showPosFields = false; - this.pickPosBtn.field_146125_m = false; + this.pickPosBtn.visible = false; if (var2.equals("keep")) { @@ -242,7 +242,7 @@ else if (var2.equals("xyz")) { this.playerPosBtn.displayString = "Player Position:"; this.showPosFields = true; - this.pickPosBtn.field_146125_m = true; + this.pickPosBtn.visible = true; } } } diff --git a/forge/src/main/java/wdl/GuiWDLWorld.java b/forge/src/main/java/wdl/GuiWDLWorld.java index 255b568..8d868c2 100644 --- a/forge/src/main/java/wdl/GuiWDLWorld.java +++ b/forge/src/main/java/wdl/GuiWDLWorld.java @@ -53,9 +53,9 @@ public void initGui() this.spawnX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); this.spawnY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); this.spawnZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); - this.spawnX.func_146203_f(7); - this.spawnY.func_146203_f(7); - this.spawnZ.func_146203_f(7); + this.spawnX.setMaxStringLength(7); + this.spawnY.setMaxStringLength(7); + this.spawnZ.setMaxStringLength(7); var3 += 18; this.pickSpawnBtn = new GuiButton(5, var1 - 0, var3, 100, 20, "Current position"); this.buttonList.add(this.pickSpawnBtn); @@ -364,7 +364,7 @@ private void updateSpawn(boolean var1) { String var2 = WDL.worldProps.getProperty("Spawn"); this.showSpawnFields = false; - this.pickSpawnBtn.field_146125_m = false; + this.pickSpawnBtn.visible = false; if (var2.equals("auto")) { @@ -401,7 +401,7 @@ else if (var2.equals("xyz")) { this.spawnBtn.displayString = "Spawn Position:"; this.showSpawnFields = true; - this.pickSpawnBtn.field_146125_m = true; + this.pickSpawnBtn.visible = true; } } } diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index 7bb37d7..5db5560 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -24,9 +24,24 @@ import net.minecraft.client.multiplayer.WorldClient; import net.minecraft.entity.Entity; import net.minecraft.entity.EntityList; +import net.minecraft.entity.boss.EntityDragon; +import net.minecraft.entity.item.EntityBoat; +import net.minecraft.entity.item.EntityEnderEye; +import net.minecraft.entity.item.EntityEnderPearl; +import net.minecraft.entity.item.EntityExpBottle; +import net.minecraft.entity.item.EntityFallingBlock; +import net.minecraft.entity.item.EntityItem; import net.minecraft.entity.item.EntityMinecart; import net.minecraft.entity.item.EntityMinecartChest; +import net.minecraft.entity.item.EntityPainting; +import net.minecraft.entity.item.EntityTNTPrimed; +import net.minecraft.entity.item.EntityXPOrb; +import net.minecraft.entity.passive.EntitySquid; import net.minecraft.entity.passive.EntityVillager; +import net.minecraft.entity.passive.IAnimals; +import net.minecraft.entity.projectile.EntityEgg; +import net.minecraft.entity.projectile.EntityFishHook; +import net.minecraft.entity.projectile.EntityPotion; import net.minecraft.init.Blocks; import net.minecraft.inventory.Container; import net.minecraft.inventory.ContainerBrewingStand; @@ -69,6 +84,7 @@ public class WDL { public static boolean DEBUG = false; // Setting to false will supress debug output in chat console + // References: public static Minecraft mc; // Reference to the Minecraft object public static WorldClient wc; // Reference to the World object that WDL uses @@ -111,19 +127,14 @@ public class WDL // Initialization: static { - // Get the static Minecraft reference: - mc = (Minecraft)stealAndGetField(Minecraft.class, Minecraft.class); - + mc = Minecraft.getMinecraft(); + // Initialize the Properties template: defaultProps = new Properties(); defaultProps.setProperty("ServerName", ""); defaultProps.setProperty("WorldName", ""); defaultProps.setProperty("LinkedWorlds", ""); defaultProps.setProperty("AutoStart", "false"); - defaultProps.setProperty("Backup", "off"); - defaultProps.setProperty("BackupPath", ""); // Represents folder or zip-file name - defaultProps.setProperty("BackupsToKeep", "1"); - defaultProps.setProperty("BackupCommand", ""); defaultProps.setProperty("GameType", "keep"); defaultProps.setProperty("Time", "keep"); defaultProps.setProperty("Weather", "keep"); @@ -153,16 +164,21 @@ public static void start() if (isMultiworld && worldName.isEmpty()) { // Ask the user which world is loaded - guiToShowAsync = new GuiWDLMultiworldSelect(null); + //guiToShowAsync = new GuiWDLMultiworldSelect(null); + mc.displayGuiScreen(new GuiWDLMultiworldSelect(null)); return; } if (!propsFound) { // Never seen this world before. Ask user about multiworlds: - guiToShowAsync = new GuiWDLMultiworld(null); + //guiToShowAsync = new GuiWDLMultiworld(null); + mc.displayGuiScreen(new GuiWDLMultiworld(null)); return; } + + WDL.mc.displayGuiScreen((GuiScreen)null); + WDL.mc.setIngameFocus(); worldProps = loadWorldProps(worldName); @@ -454,14 +470,69 @@ public static void onBlockEvent(int x, int y, int z, Block block, int event, int if (block == Blocks.noteblock) { TileEntityNote newTE = new TileEntityNote(); - newTE.field_145879_a = (byte)(param % 25); + newTE.note = (byte)(param % 25); wc.setTileEntity(x, y, z, newTE); newTileEntities.add(new ChunkPosition(x, y, z)); chatDebug("onBlockEvent: Note Block: " + x + " " + y + " " + z + " pitch: " + param + " - " + newTE); } // Pistons, Chests (open, close), EnderChests, ... (see references to WorldServer.addBlockEvent) } - + + + // TODO: Change this in WorldClient.java line 324 + /** + * Must be called when an entity is about to be removed from the world. + * @return true if the entity should not be removed, false if it can be + */ + public static boolean shouldKeepEntity(Entity entity) + { + // If the entity is being removed and it's outside the default tracking range, + // go ahead and remember it until the chunk is saved. + if(WDL.downloading) + { + if(entity != null) + { + int threshold = 0; + if ((entity instanceof EntityFishHook) || + //(entity instanceof EntityArrow) || + //(entity instanceof EntitySmallFireball) || + //(entity instanceof EntitySnowball) || + (entity instanceof EntityEnderPearl) || + (entity instanceof EntityEnderEye) || + (entity instanceof EntityEgg) || + (entity instanceof EntityPotion) || + (entity instanceof EntityExpBottle) || + (entity instanceof EntityItem) || + (entity instanceof EntitySquid)) + { + threshold = 64; + } + else if ((entity instanceof EntityMinecart) || + (entity instanceof EntityBoat) || + (entity instanceof IAnimals)) + { + threshold = 80; + } + else if ((entity instanceof EntityDragon) || + (entity instanceof EntityTNTPrimed) || + (entity instanceof EntityFallingBlock) || + (entity instanceof EntityPainting) || + (entity instanceof EntityXPOrb)) + { + threshold = 160; + } + double distance = entity.getDistance(WDL.tp.posX, entity.posY, WDL.tp.posZ); + if( distance > (double)threshold) + { + WDL.chatDebug("removeEntityFromWorld: Refusing to remove " + EntityList.getEntityString(entity) + " at distance " + distance); + return true; + } + WDL.chatDebug("removeEntityFromWorld: Removing " + EntityList.getEntityString(entity) + " at distance " + distance); + } + } + return false; + } + /** Load the previously saved TileEntities and add them to the Chunk **/ public static void importTileEntities(Chunk chunk) { @@ -485,19 +556,19 @@ public static void importTileEntities(Chunk chunk) String entityType = null; if ((entityType = isImportableTileEntity(te)) != null) { - if (!newTileEntities.contains(new ChunkPosition(te.field_145851_c, te.field_145848_d, te.field_145849_e))) + if (!newTileEntities.contains(new ChunkPosition(te.xCoord, te.yCoord, te.zCoord))) { - wc.setTileEntity(te.field_145851_c, te.field_145848_d, te.field_145849_e, te); - chatDebug("Loaded TE: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + wc.setTileEntity(te.xCoord, te.yCoord, te.zCoord, te); + chatDebug("Loaded TE: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); } else { - chatDebug("Dropping old TE: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + chatDebug("Dropping old TE: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); } } else { - chatDebug("Old TE is not importable: " + entityType + " at " + te.field_145851_c + " " + te.field_145848_d + " " + te.field_145849_e); + chatDebug("Old TE is not importable: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); } } } @@ -510,7 +581,7 @@ public static void importTileEntities(Chunk chunk) /** Checks if the TileEntity should be imported. Only "problematic" TEs will be imported. */ public static String isImportableTileEntity(TileEntity te) { - Block block = wc.getBlock(te.field_145851_c, te.field_145848_d, te.field_145849_e); + Block block = wc.getBlock(te.xCoord, te.yCoord, te.zCoord); if (block instanceof BlockChest && te instanceof TileEntityChest) { return "TileEntityChest"; @@ -571,12 +642,10 @@ public static void saveEverything() } catch (IllegalArgumentException e) { - // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalAccessException e) { - // TODO Auto-generated catch block e.printStackTrace(); } } @@ -1119,7 +1188,7 @@ public static void copyItemStacks(Container c, IInventory i, int startInContaine public static void chatMsg(String msg) { // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A7c[WorldDL]\u00A76 " + msg)); + mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A7c[WorldDL]\u00A76 " + msg)); } /** Adds a chat message with a World Downloader prefix */ @@ -1128,14 +1197,14 @@ public static void chatDebug(String msg) if (!WDL.DEBUG) return; // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); + mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); } /** Adds a chat message with a World Downloader prefix */ public static void chatError(String msg) { // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().func_146227_a(new ChatComponentText("\u00A72[WorldDL]\u00A74 " + msg)); + mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A74 " + msg)); } @@ -1156,7 +1225,6 @@ private static int getSaveVersion(AnvilSaveConverter asc) } } catch (Throwable t) { - // TODO Auto-generated catch block t.printStackTrace(); } if (saveVersion == 0) diff --git a/forge/src/main/java/wdl/WDLWorldAccess.java b/forge/src/main/java/wdl/WDLWorldAccess.java new file mode 100644 index 0000000..0a0a060 --- /dev/null +++ b/forge/src/main/java/wdl/WDLWorldAccess.java @@ -0,0 +1,68 @@ +package wdl; + +import net.minecraft.entity.Entity; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.world.IWorldAccess; + +public class WDLWorldAccess implements IWorldAccess +{ + + // TODO: This needs a better solution! + @Override + public void onEntityDestroy(Entity entity) + { + /* + if(WDL.shouldKeepEntity(entity)) + { + //entity.isDead = false; + WDL.chatDebug("Reviving entity " + entity); + + Entity test = WDL.wc.getEntityByID(entity.getEntityId()); + WDL.chatDebug("test=" + test); + entity.isDead = false; + //WDL.wc.addEntityToWorld(entity.getEntityId(), entity); + //WDL.wc.spawnEntityInWorld(entity); + } + */ + } + + + // Unused: + + @Override + public void onEntityCreate(Entity a) {} + + @Override + public void markBlockForUpdate(int a, int b, int c) {} + + @Override + public void markBlockForRenderUpdate(int a, int b, int c) {} + + @Override + public void markBlockRangeForRenderUpdate(int a, int b, int c, int d, int e, int f) {} + + @Override + public void playSound(String a, double b, double c, double d, float e, float f) {} + + @Override + public void playSoundToNearExcept(EntityPlayer a, String b, double c, double d, double e, float f, float g) {} + + @Override + public void spawnParticle(String a, double b, double c, double d, double e, double f, double g) {} + + @Override + public void playRecord(String a, int b, int c, int d) {} + + @Override + public void broadcastSound(int a, int b, int c, int d, int e) {} + + @Override + public void playAuxSFX(EntityPlayer a, int b, int c, int d, int e, int f) {} + + @Override + public void destroyBlockPartially(int a, int b, int c, int d, int e) {} + + @Override + public void onStaticEntitiesChanged() {} + +} From b8d86640b68b3b820dfed3feecc2c997acb79691 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 7 Jul 2014 23:46:23 +0200 Subject: [PATCH 10/16] Renamed README so that Github parses it as Markdown --- forge/{README => README.md} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename forge/{README => README.md} (100%) diff --git a/forge/README b/forge/README.md similarity index 100% rename from forge/README rename to forge/README.md From 601ffb214632c5cddf0a3cac7cf1196a1662a74a Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Wed, 9 Jul 2014 16:24:35 +0200 Subject: [PATCH 11/16] Move the GuiIngameMenu manipulation code into WDL This can also be used by the standalone version of WDL. In the future I'd like to clean up WDL.java and split it into smaller files... --- forge/src/main/java/wdl/ForgeMod.java | 74 ++----------------------- forge/src/main/java/wdl/WDL.java | 77 ++++++++++++++++++++++++++- 2 files changed, 79 insertions(+), 72 deletions(-) diff --git a/forge/src/main/java/wdl/ForgeMod.java b/forge/src/main/java/wdl/ForgeMod.java index 8e966b0..6b7394d 100644 --- a/forge/src/main/java/wdl/ForgeMod.java +++ b/forge/src/main/java/wdl/ForgeMod.java @@ -1,10 +1,6 @@ package wdl; -import java.util.List; - -import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiIngameMenu; -import net.minecraft.client.gui.GuiScreen; import net.minecraftforge.client.event.ClientChatReceivedEvent; import net.minecraftforge.client.event.GuiOpenEvent; import net.minecraftforge.client.event.GuiScreenEvent.ActionPerformedEvent; @@ -119,9 +115,9 @@ public void onConnect(ClientConnectedToServerEvent event) @SubscribeEvent public void onGuiDrawn(InitGuiEvent.Post event) { - if(!WDL.mc.isIntegratedServerRunning() && event.gui instanceof GuiIngameMenu) + if(event.gui instanceof GuiIngameMenu) { - injectWDLButtons((GuiIngameMenu)event.gui, event.buttonList); + WDL.injectWDLButtons((GuiIngameMenu)event.gui, event.buttonList); } if(WDL.downloading) @@ -140,9 +136,9 @@ public void onGuiDrawn(InitGuiEvent.Post event) @SubscribeEvent public void onGuiButtonClicked(ActionPerformedEvent.Pre event) { - if(!WDL.mc.isIntegratedServerRunning() && event.gui instanceof GuiIngameMenu) + if(event.gui instanceof GuiIngameMenu) { - handleWDLButtonClick((GuiIngameMenu)event.gui, event.button); + WDL.handleWDLButtonClick((GuiIngameMenu)event.gui, event.button); } } @@ -151,67 +147,5 @@ public void onChatMessage(ClientChatReceivedEvent event) { WDL.handleServerSeedMessage(event.message.getFormattedText()); } - - - // Add World Downloader buttons to GuiIngameMenu - private void injectWDLButtons(GuiIngameMenu gui, List buttonList) - { - int insertAtYPos = 0; - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.id == 5) // Button "Achievements" - { - insertAtYPos = btn.yPosition + btn.height + 4; - break; - } - } - - // Move other buttons down one slot (= 24 height units) - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.yPosition >= insertAtYPos) - { - btn.yPosition += 24; - } - } - - // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" - GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); - GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); - - wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); - wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); - wdlOptions.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); - - buttonList.add(wdlDownload); - buttonList.add(wdlOptions); - } - - private void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) - { - if(button.id == 0x57444C73) // "Start/Stop Download" - { - if (WDL.downloading) - { - WDL.stop(); - WDL.mc.displayGuiScreen((GuiScreen)null); - WDL.mc.setIngameFocus(); - } - else - { - WDL.start(); - } - } - else if( button.id == 0x57444C6F) // "..." (options) - { - WDL.mc.displayGuiScreen(new GuiWDL(gui)); - } - else if( button.id == 1) // "Disconnect" - { - WDL.stop(); - } - } } diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index 5db5560..3df0517 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -9,6 +9,7 @@ import java.lang.reflect.Field; import java.lang.reflect.Method; import java.util.HashSet; +import java.util.List; import java.util.Properties; import net.minecraft.block.Block; @@ -19,6 +20,8 @@ import net.minecraft.block.BlockNote; import net.minecraft.client.Minecraft; import net.minecraft.client.entity.EntityClientPlayerMP; +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiIngameMenu; import net.minecraft.client.gui.GuiScreen; import net.minecraft.client.multiplayer.ChunkProviderClient; import net.minecraft.client.multiplayer.WorldClient; @@ -164,7 +167,6 @@ public static void start() if (isMultiworld && worldName.isEmpty()) { // Ask the user which world is loaded - //guiToShowAsync = new GuiWDLMultiworldSelect(null); mc.displayGuiScreen(new GuiWDLMultiworldSelect(null)); return; } @@ -172,7 +174,6 @@ public static void start() if (!propsFound) { // Never seen this world before. Ask user about multiworlds: - //guiToShowAsync = new GuiWDLMultiworld(null); mc.displayGuiScreen(new GuiWDLMultiworld(null)); return; } @@ -1317,4 +1318,76 @@ public static void handleServerSeedMessage(String msg) * else { WDL.chatMsg("Could not retrieve server seed"); } */ } + + // Add World Downloader buttons to GuiIngameMenu + public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) + { + if (mc.isIntegratedServerRunning()) + { + return; // WDL not available if in singleplayer or LAN server mode + } + + int insertAtYPos = 0; + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.id == 5) // Button "Achievements" + { + insertAtYPos = btn.yPosition + btn.height + 4; + break; + } + } + + // Move other buttons down one slot (= 24 height units) + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.yPosition >= insertAtYPos) + { + btn.yPosition += 24; + } + } + + // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" + GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); + GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); + + wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); + wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); + + wdlOptions.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); + + buttonList.add(wdlDownload); + buttonList.add(wdlOptions); + } + + public static void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) + { + if (mc.isIntegratedServerRunning()) + { + return; // WDL not available if in singleplayer or LAN server mode + } + + if(button.id == 0x57444C73) // "Start/Stop Download" + { + if (WDL.downloading) + { + WDL.stop(); + WDL.mc.displayGuiScreen((GuiScreen)null); + WDL.mc.setIngameFocus(); + } + else + { + WDL.start(); + } + } + else if( button.id == 0x57444C6F) // "..." (options) + { + WDL.mc.displayGuiScreen(new GuiWDL(gui)); + } + else if( button.id == 1) // "Disconnect" + { + WDL.stop(); + } + } } From 9a2329eb56823cd0ce2d22acde9af7fbf1e19040 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Wed, 9 Jul 2014 20:30:33 +0200 Subject: [PATCH 12/16] Sync with standalone mod source code --- forge/src/main/java/wdl/WDL.java | 103 +++++++++++++++---------------- 1 file changed, 50 insertions(+), 53 deletions(-) diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index 3df0517..f785361 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -106,9 +106,7 @@ public class WDL // Positions of newly created TileEntities that will overwrite the imported ones when saving: public static HashSet newTileEntities = new HashSet(); - - public static GuiScreen guiToShowAsync = null; // A Gui to show in the next world tick. Needed so that the mouse works. - + // State variables: public static boolean downloading = false; // Read-only outside of this class! public static boolean isMultiworld = false; // Is this a multiworld server? @@ -130,8 +128,8 @@ public class WDL // Initialization: static { - mc = Minecraft.getMinecraft(); - + mc = Minecraft.getMinecraft(); + // Initialize the Properties template: defaultProps = new Properties(); defaultProps.setProperty("ServerName", ""); @@ -167,14 +165,14 @@ public static void start() if (isMultiworld && worldName.isEmpty()) { // Ask the user which world is loaded - mc.displayGuiScreen(new GuiWDLMultiworldSelect(null)); + mc.displayGuiScreen(new GuiWDLMultiworldSelect(null)); return; } if (!propsFound) { // Never seen this world before. Ask user about multiworlds: - mc.displayGuiScreen(new GuiWDLMultiworld(null)); + mc.displayGuiScreen(new GuiWDLMultiworld(null)); return; } @@ -480,7 +478,6 @@ public static void onBlockEvent(int x, int y, int z, Block block, int event, int } - // TODO: Change this in WorldClient.java line 324 /** * Must be called when an entity is about to be removed from the world. * @return true if the entity should not be removed, false if it can be @@ -1322,36 +1319,36 @@ public static void handleServerSeedMessage(String msg) // Add World Downloader buttons to GuiIngameMenu public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) { - if (mc.isIntegratedServerRunning()) - { - return; // WDL not available if in singleplayer or LAN server mode - } - - int insertAtYPos = 0; - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.id == 5) // Button "Achievements" - { - insertAtYPos = btn.yPosition + btn.height + 4; - break; - } - } - - // Move other buttons down one slot (= 24 height units) - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.yPosition >= insertAtYPos) - { - btn.yPosition += 24; - } - } - - // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" - GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); + if (mc.isIntegratedServerRunning()) + { + return; // WDL not available if in singleplayer or LAN server mode + } + + int insertAtYPos = 0; + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.id == 5) // Button "Achievements" + { + insertAtYPos = btn.yPosition + 24; + break; + } + } + + // Move other buttons down one slot (= 24 height units) + for( Object obj : buttonList) + { + GuiButton btn = (GuiButton)obj; + if(btn.yPosition >= insertAtYPos) + { + btn.yPosition += 24; + } + } + + // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" + GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); - + wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); @@ -1363,13 +1360,13 @@ public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) public static void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) { - if (mc.isIntegratedServerRunning()) - { - return; // WDL not available if in singleplayer or LAN server mode - } - - if(button.id == 0x57444C73) // "Start/Stop Download" - { + if (mc.isIntegratedServerRunning()) + { + return; // WDL not available if in singleplayer or LAN server mode + } + + if(button.id == 0x57444C73) // "Start/Stop Download" + { if (WDL.downloading) { WDL.stop(); @@ -1380,14 +1377,14 @@ public static void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) { WDL.start(); } - } - else if( button.id == 0x57444C6F) // "..." (options) - { - WDL.mc.displayGuiScreen(new GuiWDL(gui)); - } - else if( button.id == 1) // "Disconnect" - { - WDL.stop(); - } + } + else if( button.id == 0x57444C6F) // "..." (options) + { + WDL.mc.displayGuiScreen(new GuiWDL(gui)); + } + else if( button.id == 1) // "Disconnect" + { + WDL.stop(); + } } } From 62081e4b74880d85d0bd101c7f17cf9778a43547 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Sat, 12 Jul 2014 21:44:46 +0200 Subject: [PATCH 13/16] Sync with master. Also Eclipse changed some indentation. --- forge/src/main/java/wdl/ForgeMod.java | 136 ++++++++--------- forge/src/main/java/wdl/WDL.java | 156 ++++++++++++++------ forge/src/main/java/wdl/WDLWorldAccess.java | 78 +++++----- 3 files changed, 215 insertions(+), 155 deletions(-) diff --git a/forge/src/main/java/wdl/ForgeMod.java b/forge/src/main/java/wdl/ForgeMod.java index 6b7394d..9836609 100644 --- a/forge/src/main/java/wdl/ForgeMod.java +++ b/forge/src/main/java/wdl/ForgeMod.java @@ -23,42 +23,42 @@ public class ForgeMod { public static final String MODID = "WDL"; public static final String VERSION = "1.7.10"; - + @EventHandler public void init(FMLInitializationEvent event) { - FMLCommonHandler.instance().bus().register(this); - MinecraftForge.EVENT_BUS.register(this); + FMLCommonHandler.instance().bus().register(this); + MinecraftForge.EVENT_BUS.register(this); } - + @SubscribeEvent public void onChunkLoad(ChunkEvent.Load event) { - if(event.world != WDL.wc) - { - WDL.onWorldLoad(); - } + if(event.world != WDL.wc) + { + WDL.onWorldLoad(); + } } - + @SubscribeEvent public void onChunkUnload(ChunkEvent.Unload event) { - if(WDL.downloading && event.world.isRemote) - { - WDL.onChunkNoLongerNeeded(event.getChunk()); - } + if(WDL.downloading && event.world.isRemote) + { + WDL.onChunkNoLongerNeeded(event.getChunk()); + } } - + @SubscribeEvent public void onWorldLoad(WorldEvent.Load event) { - if(event.world.isRemote) - { - //WDL.onWorldLoad(); //Does NOT work! The player is not yet initialized here. - event.world.addWorldAccess(new WDLWorldAccess()); - } + if(event.world.isRemote) + { + //WDL.onWorldLoad(); //Does NOT work! The player is not yet initialized here. + event.world.addWorldAccess(new WDLWorldAccess()); + } } - + /* @SubscribeEvent public void onWorldUnload(WorldEvent.Unload event) @@ -69,83 +69,83 @@ public void onWorldUnload(WorldEvent.Unload event) //WDL.onWorldUnload(); } } - */ - + */ + @SubscribeEvent public void onGuiSwitch(GuiOpenEvent event) { - - if(WDL.downloading) - { - if(WDL.tp.openContainer != WDL.windowContainer) - { - if(WDL.tp.openContainer == WDL.tp.inventoryContainer) - { - WDL.onItemGuiClosed(); - } - WDL.windowContainer = WDL.tp.openContainer; - } - } - + + if(WDL.downloading) + { + if(WDL.tp.openContainer != WDL.windowContainer) + { + if(WDL.tp.openContainer == WDL.tp.inventoryContainer) + { + WDL.onItemGuiClosed(); + } + WDL.windowContainer = WDL.tp.openContainer; + } + } + } - + @SubscribeEvent public void onNoteBlock(NoteBlockEvent event) { - if(WDL.downloading && event.world.isRemote) - { - WDL.onBlockEvent(event.x, event.y, event.z, event.block, 0, event.getVanillaNoteId()); - } + if(WDL.downloading && event.world.isRemote) + { + WDL.onBlockEvent(event.x, event.y, event.z, event.block, 0, event.getVanillaNoteId()); + } } - + @SubscribeEvent public void onDisconnect(ClientDisconnectionFromServerEvent event) { - WDL.stop(); + WDL.stop(); } - + /* @SubscribeEvent public void onConnect(ClientConnectedToServerEvent event) { // mc.theWorld is still null! } - */ - + */ + @SubscribeEvent public void onGuiDrawn(InitGuiEvent.Post event) { - if(event.gui instanceof GuiIngameMenu) - { - WDL.injectWDLButtons((GuiIngameMenu)event.gui, event.buttonList); - } - - if(WDL.downloading) - { - if(WDL.tp.openContainer != WDL.windowContainer) - { - if(WDL.tp.openContainer != WDL.tp.inventoryContainer) - { - WDL.onItemGuiOpened(); - } - WDL.windowContainer = WDL.tp.openContainer; - } - } + if(event.gui instanceof GuiIngameMenu) + { + WDL.injectWDLButtons((GuiIngameMenu)event.gui, event.buttonList); + } + + if(WDL.downloading) + { + if(WDL.tp.openContainer != WDL.windowContainer) + { + if(WDL.tp.openContainer != WDL.tp.inventoryContainer) + { + WDL.onItemGuiOpened(); + } + WDL.windowContainer = WDL.tp.openContainer; + } + } } - + @SubscribeEvent public void onGuiButtonClicked(ActionPerformedEvent.Pre event) { - if(event.gui instanceof GuiIngameMenu) - { - WDL.handleWDLButtonClick((GuiIngameMenu)event.gui, event.button); - } + if(event.gui instanceof GuiIngameMenu) + { + WDL.handleWDLButtonClick((GuiIngameMenu)event.gui, event.button); + } } - + @SubscribeEvent public void onChatMessage(ClientChatReceivedEvent event) { - WDL.handleServerSeedMessage(event.message.getFormattedText()); + WDL.handleServerSeedMessage(event.message.getFormattedText()); } } diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java index f785361..9ea5057 100644 --- a/forge/src/main/java/wdl/WDL.java +++ b/forge/src/main/java/wdl/WDL.java @@ -12,6 +12,9 @@ import java.util.List; import java.util.Properties; +import com.mojang.realmsclient.RealmsMainScreen; +import com.mojang.realmsclient.dto.McoServer; + import net.minecraft.block.Block; import net.minecraft.block.BlockBrewingStand; import net.minecraft.block.BlockChest; @@ -23,8 +26,10 @@ import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiIngameMenu; import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiScreenRealmsProxy; import net.minecraft.client.multiplayer.ChunkProviderClient; import net.minecraft.client.multiplayer.WorldClient; +import net.minecraft.client.resources.I18n; import net.minecraft.entity.Entity; import net.minecraft.entity.EntityList; import net.minecraft.entity.boss.EntityDragon; @@ -61,6 +66,7 @@ import net.minecraft.nbt.NBTTagFloat; import net.minecraft.nbt.NBTTagList; import net.minecraft.network.NetworkManager; +import net.minecraft.realms.RealmsScreen; import net.minecraft.tileentity.TileEntity; import net.minecraft.tileentity.TileEntityBrewingStand; import net.minecraft.tileentity.TileEntityChest; @@ -86,16 +92,15 @@ */ public class WDL { - public static boolean DEBUG = false; // Setting to false will supress debug output in chat console - + //TODO: This class needs to be split into smaller classes. There is way too much different stuff in here. + + public static boolean DEBUG = false; // Setting to false will suppress debug output in chat console + // References: public static Minecraft mc; // Reference to the Minecraft object public static WorldClient wc; // Reference to the World object that WDL uses public static NetworkManager nm = null; // Reference to a connection specific object. Used to detect a new connection. public static EntityClientPlayerMP tp; - /* TODO: Realms support disabled until someone gets it working - public static McoServer mcos; - */ public static Container windowContainer; // Reference to the place where all the item stacks end up after receiving them. public static int lastX = 0, lastY = 0, lastZ = 0; // Last right clicked block. Needed for TileEntity creation! @@ -106,7 +111,7 @@ public class WDL // Positions of newly created TileEntities that will overwrite the imported ones when saving: public static HashSet newTileEntities = new HashSet(); - + // State variables: public static boolean downloading = false; // Read-only outside of this class! public static boolean isMultiworld = false; // Is this a multiworld server? @@ -129,7 +134,7 @@ public class WDL static { mc = Minecraft.getMinecraft(); - + // Initialize the Properties template: defaultProps = new Properties(); defaultProps.setProperty("ServerName", ""); @@ -175,7 +180,7 @@ public static void start() mc.displayGuiScreen(new GuiWDLMultiworld(null)); return; } - + WDL.mc.displayGuiScreen((GuiScreen)null); WDL.mc.setIngameFocus(); @@ -476,8 +481,8 @@ public static void onBlockEvent(int x, int y, int z, Block block, int event, int } // Pistons, Chests (open, close), EnderChests, ... (see references to WorldServer.addBlockEvent) } - - + + /** * Must be called when an entity is about to be removed from the world. * @return true if the entity should not be removed, false if it can be @@ -492,30 +497,30 @@ public static boolean shouldKeepEntity(Entity entity) { int threshold = 0; if ((entity instanceof EntityFishHook) || - //(entity instanceof EntityArrow) || - //(entity instanceof EntitySmallFireball) || - //(entity instanceof EntitySnowball) || - (entity instanceof EntityEnderPearl) || - (entity instanceof EntityEnderEye) || - (entity instanceof EntityEgg) || - (entity instanceof EntityPotion) || - (entity instanceof EntityExpBottle) || - (entity instanceof EntityItem) || - (entity instanceof EntitySquid)) + //(entity instanceof EntityArrow) || + //(entity instanceof EntitySmallFireball) || + //(entity instanceof EntitySnowball) || + (entity instanceof EntityEnderPearl) || + (entity instanceof EntityEnderEye) || + (entity instanceof EntityEgg) || + (entity instanceof EntityPotion) || + (entity instanceof EntityExpBottle) || + (entity instanceof EntityItem) || + (entity instanceof EntitySquid)) { threshold = 64; } else if ((entity instanceof EntityMinecart) || - (entity instanceof EntityBoat) || - (entity instanceof IAnimals)) + (entity instanceof EntityBoat) || + (entity instanceof IAnimals)) { threshold = 80; } else if ((entity instanceof EntityDragon) || - (entity instanceof EntityTNTPrimed) || - (entity instanceof EntityFallingBlock) || - (entity instanceof EntityPainting) || - (entity instanceof EntityXPOrb)) + (entity instanceof EntityTNTPrimed) || + (entity instanceof EntityFallingBlock) || + (entity instanceof EntityPainting) || + (entity instanceof EntityXPOrb)) { threshold = 160; } @@ -530,7 +535,7 @@ else if ((entity instanceof EntityDragon) || } return false; } - + /** Load the previously saved TileEntities and add them to the Chunk **/ public static void importTileEntities(Chunk chunk) { @@ -748,12 +753,12 @@ public static void saveChunks() throws IllegalArgumentException, IllegalAccessEx // Steal the instance of LongHashMap from our chunk provider //System.out.println("Stealing field from chunkProvider (type=" + chunkProvider.getClass().getName() + ") of type " + LongHashMap.class.getName()); LongHashMap lhm = (LongHashMap)stealAndGetField(chunkProvider, LongHashMap.class); -/* + /* if (lhm != null) { System.out.println("Successfully got lhm of type" + lhm.getClass().getName()); } -*/ + */ // Get the LongHashMap.Entry[] through the now accessible field using a // LongHashMap we steal from our chunkProvider. Object[] hashArray = (Object[])hashArrayField.get(lhm); @@ -1132,14 +1137,23 @@ public static String getServerName() { if (mc.func_147104_D() != null) // getServerData { - return mc.func_147104_D().serverName; + String name = mc.func_147104_D().serverName; + + if(name.equals(I18n.format("selectServer.defaultName"))) + { + // Direct connection using domain name or IP (and port) + name = mc.func_147104_D().serverIP; + } + return name; } - /* TODO: Realms support disabled until someone gets it working - else if (mcos != null) + else { - return "MCRealm: " + URLDecoder.decode(mcos.field_148810_b, "UTF-8"); + String realmName = getRealmName(); + if(realmName != null) + { + return realmName; + } } - */ } catch (Exception e) { @@ -1147,6 +1161,52 @@ else if (mcos != null) return "Unidentified Server"; } + public static String getRealmName() + { + // Is this the only way to get the name of the Realms server? Really Mojang? + // If this function turns out to be a pain to update, just remove Realms support completely. + // I doubt anyone will need this anyway since Realms support downloading the world out of the box. + + // Try to get the value of mc.getNetHandler().guiScreenServer: + GuiScreen screen = (GuiScreen) stealAndGetField(mc.getNetHandler(), GuiScreen.class); + + // If it is not a GuiScreenRealmsProxy we are not using a Realms server + if(!(screen instanceof GuiScreenRealmsProxy)) return null; + + // Get the proxy's RealmsScreen object + GuiScreenRealmsProxy screenProxy = (GuiScreenRealmsProxy) screen; + RealmsScreen rs = screenProxy.func_154321_a(); + + // It needs to be of type RealmsMainScreen (this should always be the case) + if(!(rs instanceof RealmsMainScreen)) return null; + + RealmsMainScreen rms = (RealmsMainScreen) rs; + McoServer mcos = null; + try + { + // Find the ID of the selected Realms server. Fortunately unobfuscated names! + Field selectedServerId = rms.getClass().getDeclaredField("selectedServerId"); + selectedServerId.setAccessible(true); + Object obj = selectedServerId.get(rms); + if(!(obj instanceof Long)) return null; + long id = ((Long)obj).longValue(); + + // Get the McoServer instance that was selected + Method findServer = rms.getClass().getDeclaredMethod("findServer", long.class); + findServer.setAccessible(true); + obj = findServer.invoke(rms, id); + if(!(obj instanceof McoServer)) return null; + mcos = (McoServer)obj; + } + catch (Exception e) + { + return null; + } + + // Return its name. Not sure if this is the best naming scheme... + return mcos.name; + } + /** Get the base folder name for the server we are connected to */ public static String getBaseFolderName() { @@ -1197,7 +1257,7 @@ public static void chatDebug(String msg) // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); } - + /** Adds a chat message with a World Downloader prefix */ public static void chatError(String msg) { @@ -1205,7 +1265,7 @@ public static void chatError(String msg) mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A74 " + msg)); } - + private static int getSaveVersion(AnvilSaveConverter asc) { int saveVersion = 0; @@ -1228,12 +1288,12 @@ private static int getSaveVersion(AnvilSaveConverter asc) if (saveVersion == 0) { saveVersion = 19133; // Version for 1.7.2 just in case we can't get - // it + // it } return saveVersion; } - - + + /** * Uses Java's reflection API to get access to an unaccessible field * @@ -1252,7 +1312,7 @@ public static Field stealField(Class typeOfClass, Class typeOfField) { //System.out.println("stealField: Found field " + f.getName() + // " of type " + f.getType()); - + if (f.getType().equals(typeOfField)) { try @@ -1315,7 +1375,7 @@ public static void handleServerSeedMessage(String msg) * else { WDL.chatMsg("Could not retrieve server seed"); } */ } - + // Add World Downloader buttons to GuiIngameMenu public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) { @@ -1323,7 +1383,7 @@ public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) { return; // WDL not available if in singleplayer or LAN server mode } - + int insertAtYPos = 0; for( Object obj : buttonList) { @@ -1334,7 +1394,7 @@ public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) break; } } - + // Move other buttons down one slot (= 24 height units) for( Object obj : buttonList) { @@ -1344,27 +1404,27 @@ public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) btn.yPosition += 24; } } - + // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); - + wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); wdlOptions.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); - + buttonList.add(wdlDownload); buttonList.add(wdlOptions); } - + public static void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) { if (mc.isIntegratedServerRunning()) { return; // WDL not available if in singleplayer or LAN server mode } - + if(button.id == 0x57444C73) // "Start/Stop Download" { if (WDL.downloading) diff --git a/forge/src/main/java/wdl/WDLWorldAccess.java b/forge/src/main/java/wdl/WDLWorldAccess.java index 0a0a060..fae6f5f 100644 --- a/forge/src/main/java/wdl/WDLWorldAccess.java +++ b/forge/src/main/java/wdl/WDLWorldAccess.java @@ -6,63 +6,63 @@ public class WDLWorldAccess implements IWorldAccess { - - // TODO: This needs a better solution! - @Override - public void onEntityDestroy(Entity entity) - { - /* + + // TODO: This needs a better solution! + @Override + public void onEntityDestroy(Entity entity) + { + /* if(WDL.shouldKeepEntity(entity)) { //entity.isDead = false; WDL.chatDebug("Reviving entity " + entity); - + Entity test = WDL.wc.getEntityByID(entity.getEntityId()); WDL.chatDebug("test=" + test); entity.isDead = false; //WDL.wc.addEntityToWorld(entity.getEntityId(), entity); //WDL.wc.spawnEntityInWorld(entity); } - */ - } - - - // Unused: - - @Override - public void onEntityCreate(Entity a) {} - - @Override - public void markBlockForUpdate(int a, int b, int c) {} + */ + } + + + // Unused: + + @Override + public void onEntityCreate(Entity a) {} + + @Override + public void markBlockForUpdate(int a, int b, int c) {} + + @Override + public void markBlockForRenderUpdate(int a, int b, int c) {} - @Override - public void markBlockForRenderUpdate(int a, int b, int c) {} + @Override + public void markBlockRangeForRenderUpdate(int a, int b, int c, int d, int e, int f) {} - @Override - public void markBlockRangeForRenderUpdate(int a, int b, int c, int d, int e, int f) {} + @Override + public void playSound(String a, double b, double c, double d, float e, float f) {} - @Override - public void playSound(String a, double b, double c, double d, float e, float f) {} + @Override + public void playSoundToNearExcept(EntityPlayer a, String b, double c, double d, double e, float f, float g) {} - @Override - public void playSoundToNearExcept(EntityPlayer a, String b, double c, double d, double e, float f, float g) {} + @Override + public void spawnParticle(String a, double b, double c, double d, double e, double f, double g) {} - @Override - public void spawnParticle(String a, double b, double c, double d, double e, double f, double g) {} + @Override + public void playRecord(String a, int b, int c, int d) {} - @Override - public void playRecord(String a, int b, int c, int d) {} + @Override + public void broadcastSound(int a, int b, int c, int d, int e) {} - @Override - public void broadcastSound(int a, int b, int c, int d, int e) {} + @Override + public void playAuxSFX(EntityPlayer a, int b, int c, int d, int e, int f) {} - @Override - public void playAuxSFX(EntityPlayer a, int b, int c, int d, int e, int f) {} + @Override + public void destroyBlockPartially(int a, int b, int c, int d, int e) {} - @Override - public void destroyBlockPartially(int a, int b, int c, int d, int e) {} + @Override + public void onStaticEntitiesChanged() {} - @Override - public void onStaticEntitiesChanged() {} - } From ea6cfc087b9d3c06739c96ee69e761540ddfe33b Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Sun, 13 Jul 2014 00:28:26 +0200 Subject: [PATCH 14/16] Update Forge to 1.7.10-10.13.0.1180 --- forge/build.gradle | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/forge/build.gradle b/forge/build.gradle index b6158c5..7bc6476 100644 --- a/forge/build.gradle +++ b/forge/build.gradle @@ -22,7 +22,7 @@ group= "wdl" // http://maven.apache.org/guides/mini/guide-naming-conventions.htm archivesBaseName = "WorldDownloader" minecraft { - version = "1.7.10-10.13.0.1158" + version = "1.7.10-10.13.0.1180" assetDir = "eclipse/assets" } From e48e40a12f95d63f9284f6db99beda639e4ff2c7 Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Mon, 14 Jul 2014 21:28:48 +0200 Subject: [PATCH 15/16] Remove duplicate (shared) WDL files --- forge/.gitignore | 13 +- forge/src/main/java/.gitignore | 2 + forge/src/main/java/wdl/GuiWDL.java | 184 --- forge/src/main/java/wdl/GuiWDLGenerator.java | 174 -- forge/src/main/java/wdl/GuiWDLMultiworld.java | 136 -- .../main/java/wdl/GuiWDLMultiworldSelect.java | 290 ---- forge/src/main/java/wdl/GuiWDLPlayer.java | 285 ---- forge/src/main/java/wdl/GuiWDLWorld.java | 444 ----- forge/src/main/java/wdl/WDL.java | 1450 ----------------- forge/src/main/java/wdl/WDLSaveAsync.java | 11 - .../java/wdl/WDLSaveProgressReporter.java | 27 - .../java/{wdl => wdl_forge}/ForgeMod.java | 3 +- .../{wdl => wdl_forge}/WDLWorldAccess.java | 2 +- 13 files changed, 12 insertions(+), 3009 deletions(-) create mode 100644 forge/src/main/java/.gitignore delete mode 100644 forge/src/main/java/wdl/GuiWDL.java delete mode 100644 forge/src/main/java/wdl/GuiWDLGenerator.java delete mode 100644 forge/src/main/java/wdl/GuiWDLMultiworld.java delete mode 100644 forge/src/main/java/wdl/GuiWDLMultiworldSelect.java delete mode 100644 forge/src/main/java/wdl/GuiWDLPlayer.java delete mode 100644 forge/src/main/java/wdl/GuiWDLWorld.java delete mode 100644 forge/src/main/java/wdl/WDL.java delete mode 100644 forge/src/main/java/wdl/WDLSaveAsync.java delete mode 100644 forge/src/main/java/wdl/WDLSaveProgressReporter.java rename forge/src/main/java/{wdl => wdl_forge}/ForgeMod.java (99%) rename forge/src/main/java/{wdl => wdl_forge}/WDLWorldAccess.java (95%) diff --git a/forge/.gitignore b/forge/.gitignore index c0f75de..0bc60f9 100644 --- a/forge/.gitignore +++ b/forge/.gitignore @@ -1,10 +1,11 @@ -/*.txt +/.gradle +/.settings +/bin +/build /eclipse /gradle -/gradlew -/gradlew.bat -/.gradle /.classpath /.project -/.settings -/bin +/gradlew +/gradlew.bat +/*.txt diff --git a/forge/src/main/java/.gitignore b/forge/src/main/java/.gitignore new file mode 100644 index 0000000..1e2a3e6 --- /dev/null +++ b/forge/src/main/java/.gitignore @@ -0,0 +1,2 @@ +/wdl +/com/example/examplemod \ No newline at end of file diff --git a/forge/src/main/java/wdl/GuiWDL.java b/forge/src/main/java/wdl/GuiWDL.java deleted file mode 100644 index fa84f8a..0000000 --- a/forge/src/main/java/wdl/GuiWDL.java +++ /dev/null @@ -1,184 +0,0 @@ -package wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; - -public class GuiWDL extends GuiScreen -{ - private String title = ""; - - private GuiScreen parent; - - private GuiTextField worldName; - private GuiButton autoStartBtn; - private GuiButton backupBtn; - private GuiButton worldOverrides; - private GuiButton generatorOverrides; - private GuiButton playerOverrides; - - public GuiWDL(GuiScreen parent) - { - this.parent = parent; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - if (WDL.isMultiworld && WDL.worldName.isEmpty()) - { - this.mc.displayGuiScreen(new GuiWDLMultiworldSelect(this.parent)); - } - - if (!WDL.propsFound) - { - this.mc.displayGuiScreen(new GuiWDLMultiworld(this.parent)); - return; - } - - this.buttonList.clear(); - - this.title = "Options for " + WDL.baseFolderName.replace('@', ':'); - - int w = this.width / 2; - int h = this.height / 4; - - int hi = h - 15; - - if (WDL.baseProps.getProperty("ServerName").isEmpty()) - { - WDL.baseProps.setProperty("ServerName", WDL.getServerName()); - } - - this.worldName = new GuiTextField(this.fontRendererObj, this.width / 2 - 70, hi, 168, 18); - this.updateServerName(false); - - hi += 22; - this.autoStartBtn = new GuiButton(1, w - 100, hi, "Start Download: ERROR"); - this.buttonList.add(this.autoStartBtn); - this.updateAutoStart(false); - hi += 28; - this.worldOverrides = new GuiButton(4, w - 100, hi, "World Overrides..."); - this.buttonList.add(this.worldOverrides); - hi += 22; - this.generatorOverrides = new GuiButton(5, w - 100, hi, "World Generator Overrides..."); - this.buttonList.add(this.generatorOverrides); - hi += 22; - this.playerOverrides = new GuiButton(6, w - 100, hi, "Player Overrides..."); - this.buttonList.add(this.playerOverrides); - hi += 28; - this.buttonList.add(new GuiButton(100, w - 100, h + 150, "Done")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton guibutton) - { - if (!guibutton.enabled) - return; - - this.updateServerName(true); - - if (guibutton.id == 1) // Auto start - { - this.updateAutoStart(true); - } - else if (guibutton.id == 4) // World Overrides - { - this.mc.displayGuiScreen(new GuiWDLWorld(this)); - } - else if (guibutton.id == 5) // Generator Overrides - { - this.mc.displayGuiScreen(new GuiWDLGenerator(this)); - } - else if (guibutton.id == 6) // Player Overrides - { - this.mc.displayGuiScreen(new GuiWDLPlayer(this)); - } - else if (guibutton.id == 100) // Done - { - WDL.saveProps(); - this.mc.displayGuiScreen(this.parent); - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - this.worldName.mouseClicked(var1, var2, var3); - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char c, int i) - { - super.keyTyped(c, i); - this.worldName.textboxKeyTyped(c, i); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.worldName.updateCursorCounter(); // updateCursorCounter - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); // drawDefaultBackground - this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); - this.drawString(this.fontRendererObj, "Name:", this.width / 2 - 99, this.height / 4 - 10, 16777215); - this.worldName.drawTextBox(); // drawTextBox - super.drawScreen(var1, var2, var3); - } - - public void updateAutoStart(boolean btnClicked) - { - String autoStart = WDL.baseProps.getProperty("AutoStart"); - if (autoStart.equals("true")) - { - if (btnClicked) - { - WDL.baseProps.setProperty("AutoStart", "false"); - this.updateAutoStart(false); - } - else - { - this.autoStartBtn.displayString = "Start Download: Automatically"; - } - } - else if (btnClicked) - { - WDL.baseProps.setProperty("AutoStart", "true"); - this.updateAutoStart(false); - } - else - { - this.autoStartBtn.displayString = "Start Download: Only in menu"; - } - } - - private void updateServerName(boolean var1) - { - if (var1) - { - WDL.baseProps.setProperty("ServerName", this.worldName.getText()); - } - else - { - this.worldName.setText(WDL.baseProps.getProperty("ServerName")); - } - } -} diff --git a/forge/src/main/java/wdl/GuiWDLGenerator.java b/forge/src/main/java/wdl/GuiWDLGenerator.java deleted file mode 100644 index f118e9d..0000000 --- a/forge/src/main/java/wdl/GuiWDLGenerator.java +++ /dev/null @@ -1,174 +0,0 @@ -package wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; - -public class GuiWDLGenerator extends GuiScreen -{ - private String title = ""; - private GuiScreen parent; - private GuiTextField seedField; - private GuiButton generatorBtn; - private GuiButton generateStructuresBtn; - - public GuiWDLGenerator(GuiScreen var1) - { - this.parent = var1; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - this.title = "World Generator Options for " + WDL.baseFolderName.replace('@', ':'); - int var1 = this.width / 2; - int var2 = this.height / 4; - int var3 = var2 - 15; - this.seedField = new GuiTextField(this.fontRendererObj, this.width / 2 - 70, var3, 168, 18); - this.seedField.setText("ERROR"); - this.updateSeed(false); - var3 += 22; - this.generatorBtn = new GuiButton(1, var1 - 100, var3, "World Generator: ERROR"); - this.buttonList.add(this.generatorBtn); - this.updateGenerator(false); - var3 += 22; - this.generateStructuresBtn = new GuiButton(2, var1 - 100, var3, "Generate Structures: ERROR"); - this.buttonList.add(this.generateStructuresBtn); - this.updateGenerateStructures(false); - this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - if (var1.id == 1) - { - this.updateGenerator(true); - } - else if (var1.id == 2) - { - this.updateGenerateStructures(true); - } - else if (var1.id == 100) - { - this.updateSeed(true); - WDL.saveProps(); - this.mc.displayGuiScreen(this.parent); - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - this.seedField.mouseClicked(var1, var2, var3); - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - this.seedField.textboxKeyTyped(var1, var2); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.seedField.updateCursorCounter(); - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); - this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); - this.drawString(this.fontRendererObj, "Seed:", this.width / 2 - 99, this.height / 4 - 10, 16777215); - this.seedField.drawTextBox(); - super.drawScreen(var1, var2, var3); - } - - private void updateGenerator(boolean var1) - { - String var2 = WDL.worldProps.getProperty("GeneratorName"); - - if (var2.equals("default")) - { - if (var1) - { - WDL.worldProps.setProperty("GeneratorName", "flat"); - WDL.worldProps.setProperty("GeneratorVersion", "0"); - this.updateGenerator(false); - } - else - { - this.generatorBtn.displayString = "World Generator: Default"; - } - } - else if (var1) - { - WDL.worldProps.setProperty("GeneratorName", "default"); - WDL.worldProps.setProperty("GeneratorVersion", "1"); - this.updateGenerator(false); - } - else - { - this.generatorBtn.displayString = "World Generator: Flat"; - } - } - - private void updateGenerateStructures(boolean var1) - { - String var2 = WDL.worldProps.getProperty("MapFeatures"); - - if (var2.equals("true")) - { - if (var1) - { - WDL.worldProps.setProperty("MapFeatures", "false"); - this.updateGenerateStructures(false); - } - else - { - this.generateStructuresBtn.displayString = "Generate Structures: ON"; - } - } - else if (var1) - { - WDL.worldProps.setProperty("MapFeatures", "true"); - this.updateGenerateStructures(false); - } - else - { - this.generateStructuresBtn.displayString = "Generate Structures: OFF"; - } - } - - private void updateSeed(boolean var1) - { - if (var1) - { - WDL.worldProps.setProperty("RandomSeed", this.seedField.getText()); - } - else - { - this.seedField.setText(WDL.worldProps.getProperty("RandomSeed")); - } - } -} diff --git a/forge/src/main/java/wdl/GuiWDLMultiworld.java b/forge/src/main/java/wdl/GuiWDLMultiworld.java deleted file mode 100644 index a3acd41..0000000 --- a/forge/src/main/java/wdl/GuiWDLMultiworld.java +++ /dev/null @@ -1,136 +0,0 @@ -package wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; - -public class GuiWDLMultiworld extends GuiScreen -{ - private GuiScreen parent; - private GuiButton multiworldEnabledBtn; - boolean newMultiworldState = false; - - public GuiWDLMultiworld(GuiScreen var1) - { - this.parent = var1; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - int var1 = this.width / 2; - int var2 = this.height / 4; - int var3 = var2 + 115; - this.multiworldEnabledBtn = new GuiButton(1, var1 - 100, var3, "Multiworld support: ERROR"); - this.buttonList.add(this.multiworldEnabledBtn); - this.updateMultiworldEnabled(false); - this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "OK")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - if (var1.id == 1) - { - this.updateMultiworldEnabled(true); - } - else if (var1.id == 100) - { - if (this.newMultiworldState) - { - this.mc.displayGuiScreen(new GuiWDLMultiworldSelect(this.parent)); - } - else - { - WDL.baseProps.setProperty("LinkedWorlds", ""); - WDL.saveProps(); - WDL.propsFound = true; - - if (this.parent != null) - { - this.mc.displayGuiScreen(new GuiWDL(this.parent)); - } - else - { - WDL.start(); - this.mc.displayGuiScreen((GuiScreen)null); - this.mc.setIngameFocus(); - } - } - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); - drawRect(this.width / 2 - 160, this.height / 4 - 60, this.width / 2 + 160, this.height / 4 + 180, -1342177280); - this.drawCenteredString(this.fontRendererObj, "Multiworld Support", this.width / 2, this.height / 4 - 40, 16711680); - this.drawString(this.fontRendererObj, "Multiworld support is required if at least one of the", this.width / 2 - 150, this.height / 4 - 15, 16777215); - this.drawString(this.fontRendererObj, " following conditions is met:", this.width / 2 - 150, this.height / 4 - 5, 16777215); - this.drawString(this.fontRendererObj, "- \"Multiworld\" is mentioned on the server\'s website", this.width / 2 - 150, this.height / 4 + 15, 16777215); - this.drawString(this.fontRendererObj, "- The server has more than 3 dimensions (or worlds)", this.width / 2 - 150, this.height / 4 + 35, 16777215); - this.drawString(this.fontRendererObj, "- The server has other dimensions than the official ones", this.width / 2 - 150, this.height / 4 + 55, 16777215); - this.drawString(this.fontRendererObj, " (Earth, Nether, The End)", this.width / 2 - 150, this.height / 4 + 65, 16777215); - drawRect(this.width / 2 - 102, this.height / 4 + 113, this.width / 2 + 102, this.height / 4 + 137, -65536); - super.drawScreen(var1, var2, var3); - } - - private void updateMultiworldEnabled(boolean var1) - { - if (!this.newMultiworldState) - { - if (var1) - { - this.newMultiworldState = true; - this.updateMultiworldEnabled(false); - } - else - { - this.multiworldEnabledBtn.displayString = "Multiworld support: Disabled"; - } - } - else if (var1) - { - this.newMultiworldState = false; - this.updateMultiworldEnabled(false); - } - else - { - this.multiworldEnabledBtn.displayString = "Multiworld support: Enabled"; - } - } -} diff --git a/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java b/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java deleted file mode 100644 index b979bf6..0000000 --- a/forge/src/main/java/wdl/GuiWDLMultiworldSelect.java +++ /dev/null @@ -1,290 +0,0 @@ -package wdl; - -import java.io.File; -import java.util.Properties; - -import net.minecraft.client.entity.EntityClientPlayerMP; -import net.minecraft.client.entity.EntityPlayerSP; -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; -import net.minecraft.util.Session; - -public class GuiWDLMultiworldSelect extends GuiScreen -{ - private GuiButton cancelBtn; - private GuiTextField newNameField; - private boolean newWorld = false; - private int positionID; - private float yaw; - private int thirdPersonViewSave; - private GuiButton[] buttons; - private String[] worlds; - private GuiScreen parent; - EntityPlayerSP cam; - - public GuiWDLMultiworldSelect(GuiScreen var1) - { - this.parent = var1; - EntityClientPlayerMP var2 = WDL.tp; - this.cam = new EntityPlayerSP(WDL.mc, WDL.wc, new Session("Camera", "", "", "legacy"), var2.dimension); - this.cam.setLocationAndAngles(var2.posX, var2.posY - (double)var2.yOffset, var2.posZ, var2.rotationYaw, 0.0F); - this.yaw = var2.rotationYaw; - this.thirdPersonViewSave = WDL.mc.gameSettings.thirdPersonView; - WDL.mc.gameSettings.thirdPersonView = 0; - WDL.mc.renderViewEntity = this.cam; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - int var1 = this.width / 2; - int var2 = this.height / 4; - int var3 = this.width / 150; - - if (var3 == 0) - { - var3 = 1; - } - - int var4 = this.width / var3 - 5; - this.cancelBtn = new GuiButton(100, var1 - 100, this.height - 30, "Cancel"); - this.buttonList.add(this.cancelBtn); - String var5 = WDL.baseProps.getProperty("LinkedWorlds"); - String[] var6 = var5.split("[|]"); - String[] var7 = new String[var6.length]; - int var8 = 0; - int var9; - - for (var9 = 0; var9 < var6.length; ++var9) - { - if (var6[var9].isEmpty()) - { - var6[var9] = null; - } - else - { - Properties var10 = WDL.loadWorldProps(var6[var9]); - - if (var10 == null) - { - var6[var9] = null; - } - else - { - ++var8; - var7[var9] = var10.getProperty("WorldName"); - } - } - } - - if (var3 > var8 + 1) - { - var3 = var8 + 1; - } - - var9 = (this.width - var3 * var4) / 2; - this.worlds = new String[var8]; - this.buttons = new GuiButton[var8 + 1]; - int var12 = 0; - int var11; - - for (var11 = 0; var11 < var6.length; ++var11) - { - if (var6[var11] != null) - { - this.worlds[var12] = var6[var11]; - this.buttons[var12] = new GuiButton(var12, var12 % var3 * var4 + var9, this.height - 60 - var12 / var3 * 21, var4, 20, var7[var11]); - this.buttonList.add(this.buttons[var12]); - ++var12; - } - } - - var11 = this.buttons.length - 1; - - if (!this.newWorld) - { - this.buttons[var11] = new GuiButton(var11, var11 % var3 * var4 + var9, this.height - 60 - var11 / var3 * 21, var4, 20, "< New Name >"); - this.buttonList.add(this.buttons[var11]); - } - - this.newNameField = new GuiTextField(this.fontRendererObj, var11 % var3 * var4 + var9, this.height - 60 - var11 / var3 * 21 + 1, var4, 18); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - this.newWorld = false; - - if (var1.id == this.worlds.length) - { - this.newWorld = true; - this.buttonList.remove(this.buttons[this.worlds.length]); - } - else if (var1.id == 100) - { - this.mc.displayGuiScreen((GuiScreen)null); - this.mc.setIngameFocus(); - } - else - { - this.worldSelected(this.worlds[var1.id]); - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - - if (this.newWorld) - { - this.newNameField.mouseClicked(var1, var2, var3); - } - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - - if (this.newNameField.isFocused()) - { - this.newNameField.textboxKeyTyped(var1, var2); - - if (var2 == 28) - { - String var3 = this.newNameField.getText(); - - if (var3 != null && !var3.isEmpty()) - { - this.worldSelected(this.addMultiworld(var3)); - } - } - } - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.newNameField.updateCursorCounter(); - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - drawRect(this.width / 2 - 120, 0, this.width / 2 + 120, this.height / 16 + 25, -1073741824); - - if (this.parent == null) - { - this.drawCenteredString(this.fontRendererObj, "World Downloader - Trying To Start Download", this.width / 2, this.height / 16, 16777215); - } - else - { - this.drawCenteredString(this.fontRendererObj, "World Downloader - Trying To Change Options", this.width / 2, this.height / 16, 16777215); - } - - this.drawCenteredString(this.fontRendererObj, "Where are you?", this.width / 2, this.height / 16 + 10, 16711680); - this.cam.prevRotationPitch = this.cam.rotationPitch = 0.0F; - this.cam.prevRotationYaw = this.cam.rotationYaw = this.yaw; - float var4 = 0.475F; - this.cam.lastTickPosY = this.cam.prevPosY = this.cam.posY = WDL.tp.posY; - this.cam.lastTickPosX = this.cam.prevPosX = this.cam.posX = WDL.tp.posX - (double)var4 * Math.sin((double)this.yaw / 180.0D * Math.PI); - this.cam.lastTickPosZ = this.cam.prevPosZ = this.cam.posZ = WDL.tp.posZ + (double)var4 * Math.cos((double)this.yaw / 180.0D * Math.PI); - float var5 = 1.0F; - this.yaw = (float)((double)this.yaw + (double)var5 * (1.0D + 0.699999988079071D * Math.cos((double)(this.yaw + 45.0F) / 45.0D * Math.PI))); - - if (this.newWorld) - { - this.newNameField.drawTextBox(); - } - - super.drawScreen(var1, var2, var3); - } - - /** - * Called when the screen is unloaded. Used to disable keyboard repeat events - */ - public void onGuiClosed() - { - super.onGuiClosed(); - WDL.mc.gameSettings.thirdPersonView = this.thirdPersonViewSave; - this.mc.renderViewEntity = WDL.tp; - } - - private void worldSelected(String var1) - { - WDL.worldName = var1; - WDL.isMultiworld = true; - WDL.propsFound = true; - - if (this.parent == null) - { - WDL.start(); - this.mc.displayGuiScreen((GuiScreen)null); - this.mc.setIngameFocus(); - } - else - { - WDL.worldProps = WDL.loadWorldProps(var1); - this.mc.displayGuiScreen(new GuiWDL(this.parent)); - } - } - - private String addMultiworld(String var1) - { - String var2 = var1; - String var3 = "\\/:*?\"<>|"; - char[] var4 = var3.toCharArray(); - int var5 = var4.length; - int var6; - - for (var6 = 0; var6 < var5; ++var6) - { - char var7 = var4[var6]; - var2 = var2.replace(var7, '_'); - } - - (new File(this.mc.mcDataDir, "saves/" + WDL.baseFolderName + " - " + var2)).mkdirs(); - Properties var11 = new Properties(WDL.baseProps); - var11.setProperty("WorldName", var1); - String[] var12 = new String[this.worlds.length + 1]; - - for (var6 = 0; var6 < this.worlds.length; ++var6) - { - var12[var6] = this.worlds[var6]; - } - - var12[var12.length - 1] = var2; - String var13 = ""; - String[] var14 = var12; - int var8 = var12.length; - - for (int var9 = 0; var9 < var8; ++var9) - { - String var10 = var14[var9]; - var13 = var13 + var10 + "|"; - } - - WDL.baseProps.setProperty("LinkedWorlds", var13); - WDL.saveProps(var2, var11); - return var2; - } -} diff --git a/forge/src/main/java/wdl/GuiWDLPlayer.java b/forge/src/main/java/wdl/GuiWDLPlayer.java deleted file mode 100644 index b2571bc..0000000 --- a/forge/src/main/java/wdl/GuiWDLPlayer.java +++ /dev/null @@ -1,285 +0,0 @@ -package wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; - -public class GuiWDLPlayer extends GuiScreen -{ - private String title = ""; - private GuiScreen parent; - private GuiButton healthBtn; - private GuiButton hungerBtn; - private GuiButton playerPosBtn; - private GuiButton pickPosBtn; - private boolean showPosFields = false; - private GuiTextField posX; - private GuiTextField posY; - private GuiTextField posZ; - private int posTextY; - - public GuiWDLPlayer(GuiScreen var1) - { - this.parent = var1; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - this.title = "Player Options for " + WDL.baseFolderName.replace('@', ':'); - int var1 = this.width / 2; - int var2 = this.height / 4; - int var3 = var2 - 15; - this.healthBtn = new GuiButton(1, var1 - 100, var3, "Health: ERROR"); - this.buttonList.add(this.healthBtn); - this.updateHealth(false); - var3 += 22; - this.hungerBtn = new GuiButton(2, var1 - 100, var3, "Hunger: ERROR"); - this.buttonList.add(this.hungerBtn); - this.updateHunger(false); - var3 += 22; - this.playerPosBtn = new GuiButton(3, var1 - 100, var3, "Player Position: ERROR"); - this.buttonList.add(this.playerPosBtn); - var3 += 22; - this.posTextY = var3 + 4; - this.posX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); - this.posY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); - this.posZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); - this.posX.setMaxStringLength(7); - this.posY.setMaxStringLength(7); - this.posZ.setMaxStringLength(7); - var3 += 18; - this.pickPosBtn = new GuiButton(4, var1 - 0, var3, 100, 20, "Current position"); - this.buttonList.add(this.pickPosBtn); - this.updatePlayerPos(false); - this.updatePosXYZ(false); - this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - if (var1.id == 1) - { - this.updateHealth(true); - } - else if (var1.id == 2) - { - this.updateHunger(true); - } - else if (var1.id == 3) - { - this.updatePlayerPos(true); - } - else if (var1.id == 4) - { - this.pickPlayerPos(); - } - else if (var1.id == 100) - { - if (this.showPosFields) - { - this.updatePosXYZ(true); - } - - WDL.saveProps(); - this.mc.displayGuiScreen(this.parent); - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - - if (this.showPosFields) - { - this.posX.mouseClicked(var1, var2, var3); - this.posY.mouseClicked(var1, var2, var3); - this.posZ.mouseClicked(var1, var2, var3); - } - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - this.posX.textboxKeyTyped(var1, var2); - this.posY.textboxKeyTyped(var1, var2); - this.posZ.textboxKeyTyped(var1, var2); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.posX.updateCursorCounter(); - this.posY.updateCursorCounter(); - this.posZ.updateCursorCounter(); - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); - this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); - - if (this.showPosFields) - { - this.drawString(this.fontRendererObj, "X:", this.width / 2 - 99, this.posTextY, 16777215); - this.drawString(this.fontRendererObj, "Y:", this.width / 2 - 31, this.posTextY, 16777215); - this.drawString(this.fontRendererObj, "Z:", this.width / 2 + 37, this.posTextY, 16777215); - this.posX.drawTextBox(); - this.posY.drawTextBox(); - this.posZ.drawTextBox(); - } - - super.drawScreen(var1, var2, var3); - } - - private void updateHealth(boolean var1) - { - String var2 = WDL.baseProps.getProperty("PlayerHealth"); - - if (var2.equals("keep")) - { - if (var1) - { - WDL.baseProps.setProperty("PlayerHealth", "20"); - this.updateHealth(false); - } - else - { - this.healthBtn.displayString = "Health: Don\'t change"; - } - } - else if (var2.equals("20")) - { - if (var1) - { - WDL.baseProps.setProperty("PlayerHealth", "keep"); - this.updateHealth(false); - } - else - { - this.healthBtn.displayString = "Health: Full"; - } - } - } - - private void updateHunger(boolean var1) - { - String var2 = WDL.baseProps.getProperty("PlayerFood"); - - if (var2.equals("keep")) - { - if (var1) - { - WDL.baseProps.setProperty("PlayerFood", "20"); - this.updateHunger(false); - } - else - { - this.hungerBtn.displayString = "Hunger: Don\'t change"; - } - } - else if (var2.equals("20")) - { - if (var1) - { - WDL.baseProps.setProperty("PlayerFood", "keep"); - this.updateHunger(false); - } - else - { - this.hungerBtn.displayString = "Hunger: Full"; - } - } - } - - private void updatePlayerPos(boolean var1) - { - String var2 = WDL.worldProps.getProperty("PlayerPos"); - this.showPosFields = false; - this.pickPosBtn.visible = false; - - if (var2.equals("keep")) - { - if (var1) - { - WDL.worldProps.setProperty("PlayerPos", "xyz"); - this.updatePlayerPos(false); - } - else - { - this.playerPosBtn.displayString = "Player Position: Don\'t change"; - } - } - else if (var2.equals("xyz")) - { - if (var1) - { - WDL.worldProps.setProperty("PlayerPos", "keep"); - this.updatePlayerPos(false); - } - else - { - this.playerPosBtn.displayString = "Player Position:"; - this.showPosFields = true; - this.pickPosBtn.visible = true; - } - } - } - - private void updatePosXYZ(boolean var1) - { - if (var1) - { - try - { - int var2 = Integer.parseInt(this.posX.getText()); - int var3 = Integer.parseInt(this.posY.getText()); - int var4 = Integer.parseInt(this.posZ.getText()); - WDL.worldProps.setProperty("PlayerX", String.valueOf(var2)); - WDL.worldProps.setProperty("PlayerY", String.valueOf(var3)); - WDL.worldProps.setProperty("PlayerZ", String.valueOf(var4)); - } - catch (NumberFormatException var5) - { - this.updatePlayerPos(true); - } - } - else - { - this.posX.setText(WDL.worldProps.getProperty("PlayerX")); - this.posY.setText(WDL.worldProps.getProperty("PlayerY")); - this.posZ.setText(WDL.worldProps.getProperty("PlayerZ")); - } - } - - private void pickPlayerPos() - { - int var1 = (int)Math.floor(WDL.tp.posX); - int var2 = (int)Math.floor(WDL.tp.posY); - int var3 = (int)Math.floor(WDL.tp.posZ); - this.posX.setText(String.valueOf(var1)); - this.posY.setText(String.valueOf(var2)); - this.posZ.setText(String.valueOf(var3)); - } -} diff --git a/forge/src/main/java/wdl/GuiWDLWorld.java b/forge/src/main/java/wdl/GuiWDLWorld.java deleted file mode 100644 index 8d868c2..0000000 --- a/forge/src/main/java/wdl/GuiWDLWorld.java +++ /dev/null @@ -1,444 +0,0 @@ -package wdl; - -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiTextField; - -public class GuiWDLWorld extends GuiScreen -{ - private String title = ""; - private GuiScreen parent; - private GuiButton gameModeBtn; - private GuiButton timeBtn; - private GuiButton weatherBtn; - private GuiButton spawnBtn; - private GuiButton pickSpawnBtn; - private boolean showSpawnFields = false; - private GuiTextField spawnX; - private GuiTextField spawnY; - private GuiTextField spawnZ; - private int spawnTextY; - - public GuiWDLWorld(GuiScreen var1) - { - this.parent = var1; - } - - /** - * Adds the buttons (and other controls) to the screen in question. - */ - public void initGui() - { - this.buttonList.clear(); - this.title = "World Options for " + WDL.baseFolderName.replace('@', ':'); - int var1 = this.width / 2; - int var2 = this.height / 4; - int var3 = var2 - 15; - this.gameModeBtn = new GuiButton(1, var1 - 100, var3, "Game Mode: ERROR"); - this.buttonList.add(this.gameModeBtn); - this.updateGameMode(false); - var3 += 22; - this.timeBtn = new GuiButton(2, var1 - 100, var3, "Time: ERROR"); - this.buttonList.add(this.timeBtn); - this.updateTime(false); - var3 += 22; - this.weatherBtn = new GuiButton(3, var1 - 100, var3, "Weather: ERROR"); - this.buttonList.add(this.weatherBtn); - this.updateWeather(false); - var3 += 22; - this.spawnBtn = new GuiButton(4, var1 - 100, var3, "Spawn Position: ERROR"); - this.buttonList.add(this.spawnBtn); - var3 += 22; - this.spawnTextY = var3 + 4; - this.spawnX = new GuiTextField(this.fontRendererObj, var1 - 87, var3, 50, 16); - this.spawnY = new GuiTextField(this.fontRendererObj, var1 - 19, var3, 50, 16); - this.spawnZ = new GuiTextField(this.fontRendererObj, var1 + 48, var3, 50, 16); - this.spawnX.setMaxStringLength(7); - this.spawnY.setMaxStringLength(7); - this.spawnZ.setMaxStringLength(7); - var3 += 18; - this.pickSpawnBtn = new GuiButton(5, var1 - 0, var3, 100, 20, "Current position"); - this.buttonList.add(this.pickSpawnBtn); - this.updateSpawn(false); - this.updateSpawnXYZ(false); - this.buttonList.add(new GuiButton(100, var1 - 100, var2 + 150, "Done")); - } - - /** - * Fired when a control is clicked. This is the equivalent of ActionListener.actionPerformed(ActionEvent e). - */ - protected void actionPerformed(GuiButton var1) - { - if (var1.enabled) - { - if (var1.id == 1) - { - this.updateGameMode(true); - } - else if (var1.id == 2) - { - this.updateTime(true); - } - else if (var1.id == 3) - { - this.updateWeather(true); - } - else if (var1.id == 4) - { - this.updateSpawn(true); - } - else if (var1.id == 5) - { - this.pickSpawn(); - } - else if (var1.id == 100) - { - if (this.showSpawnFields) - { - this.updateSpawnXYZ(true); - } - - WDL.saveProps(); - this.mc.displayGuiScreen(this.parent); - } - } - } - - /** - * Called when the mouse is clicked. - */ - protected void mouseClicked(int var1, int var2, int var3) - { - super.mouseClicked(var1, var2, var3); - - if (this.showSpawnFields) - { - this.spawnX.mouseClicked(var1, var2, var3); - this.spawnY.mouseClicked(var1, var2, var3); - this.spawnZ.mouseClicked(var1, var2, var3); - } - } - - /** - * Fired when a key is typed. This is the equivalent of KeyListener.keyTyped(KeyEvent e). - */ - protected void keyTyped(char var1, int var2) - { - super.keyTyped(var1, var2); - this.spawnX.textboxKeyTyped(var1, var2); - this.spawnY.textboxKeyTyped(var1, var2); - this.spawnZ.textboxKeyTyped(var1, var2); - } - - /** - * Called from the main game loop to update the screen. - */ - public void updateScreen() - { - this.spawnX.updateCursorCounter(); - this.spawnY.updateCursorCounter(); - this.spawnZ.updateCursorCounter(); - super.updateScreen(); - } - - /** - * Draws the screen and all the components in it. - */ - public void drawScreen(int var1, int var2, float var3) - { - this.drawDefaultBackground(); - this.drawCenteredString(this.fontRendererObj, this.title, this.width / 2, this.height / 4 - 40, 16777215); - - if (this.showSpawnFields) - { - this.drawString(this.fontRendererObj, "X:", this.width / 2 - 99, this.spawnTextY, 16777215); - this.drawString(this.fontRendererObj, "Y:", this.width / 2 - 31, this.spawnTextY, 16777215); - this.drawString(this.fontRendererObj, "Z:", this.width / 2 + 37, this.spawnTextY, 16777215); - this.spawnX.drawTextBox(); - this.spawnY.drawTextBox(); - this.spawnZ.drawTextBox(); - } - - super.drawScreen(var1, var2, var3); - } - - private void updateGameMode(boolean var1) - { - String var2 = WDL.baseProps.getProperty("GameType"); - - if (var2.equals("keep")) - { - if (var1) - { - WDL.baseProps.setProperty("GameType", "creative"); - this.updateGameMode(false); - } - else - { - this.gameModeBtn.displayString = "Game Mode: Don\'t change"; - } - } - else if (var2.equals("creative")) - { - if (var1) - { - WDL.baseProps.setProperty("GameType", "survival"); - this.updateGameMode(false); - } - else - { - this.gameModeBtn.displayString = "Game Mode: Creative"; - } - } - else if (var2.equals("survival")) - { - if (var1) - { - WDL.baseProps.setProperty("GameType", "hardcore"); - this.updateGameMode(false); - } - else - { - this.gameModeBtn.displayString = "Game Mode: Survival"; - } - } - else if (var2.equals("hardcore")) - { - if (var1) - { - WDL.baseProps.setProperty("GameType", "keep"); - this.updateGameMode(false); - } - else - { - this.gameModeBtn.displayString = "Game Mode: Survival Hardcore"; - } - } - } - - private void updateTime(boolean var1) - { - String var2 = WDL.baseProps.getProperty("Time"); - - if (var2.equals("keep")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "23000"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Don\'t change"; - } - } - else if (var2.equals("23000")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "0"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Sunrise"; - } - } - else if (var2.equals("0")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "6000"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Morning"; - } - } - else if (var2.equals("6000")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "11500"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Noon"; - } - } - else if (var2.equals("11500")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "12500"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Evening"; - } - } - else if (var2.equals("12500")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "18000"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Sunset"; - } - } - else if (var2.equals("18000")) - { - if (var1) - { - WDL.baseProps.setProperty("Time", "keep"); - this.updateTime(false); - } - else - { - this.timeBtn.displayString = "Time: Midnight"; - } - } - } - - private void updateWeather(boolean var1) - { - String var2 = WDL.baseProps.getProperty("Weather"); - - if (var2.equals("keep")) - { - if (var1) - { - WDL.baseProps.setProperty("Weather", "sunny"); - this.updateWeather(false); - } - else - { - this.weatherBtn.displayString = "Weather: Don\'t change"; - } - } - else if (var2.equals("sunny")) - { - if (var1) - { - WDL.baseProps.setProperty("Weather", "rain"); - this.updateWeather(false); - } - else - { - this.weatherBtn.displayString = "Weather: Sunny"; - } - } - else if (var2.equals("rain")) - { - if (var1) - { - WDL.baseProps.setProperty("Weather", "thunderstorm"); - this.updateWeather(false); - } - else - { - this.weatherBtn.displayString = "Weather: Rain"; - } - } - else if (var2.equals("thunderstorm")) - { - if (var1) - { - WDL.baseProps.setProperty("Weather", "keep"); - this.updateWeather(false); - } - else - { - this.weatherBtn.displayString = "Weather: Thunderstorm"; - } - } - } - - private void updateSpawn(boolean var1) - { - String var2 = WDL.worldProps.getProperty("Spawn"); - this.showSpawnFields = false; - this.pickSpawnBtn.visible = false; - - if (var2.equals("auto")) - { - if (var1) - { - WDL.worldProps.setProperty("Spawn", "player"); - this.updateSpawn(false); - } - else - { - this.spawnBtn.displayString = "Spawn Position: Automatic"; - } - } - else if (var2.equals("player")) - { - if (var1) - { - WDL.worldProps.setProperty("Spawn", "xyz"); - this.updateSpawn(false); - } - else - { - this.spawnBtn.displayString = "Spawn Position: Player position"; - } - } - else if (var2.equals("xyz")) - { - if (var1) - { - WDL.worldProps.setProperty("Spawn", "auto"); - this.updateSpawn(false); - } - else - { - this.spawnBtn.displayString = "Spawn Position:"; - this.showSpawnFields = true; - this.pickSpawnBtn.visible = true; - } - } - } - - private void updateSpawnXYZ(boolean var1) - { - if (var1) - { - try - { - int var2 = Integer.parseInt(this.spawnX.getText()); - int var3 = Integer.parseInt(this.spawnY.getText()); - int var4 = Integer.parseInt(this.spawnZ.getText()); - WDL.worldProps.setProperty("SpawnX", String.valueOf(var2)); - WDL.worldProps.setProperty("SpawnY", String.valueOf(var3)); - WDL.worldProps.setProperty("SpawnZ", String.valueOf(var4)); - } - catch (NumberFormatException var5) - { - this.updateSpawn(true); - } - } - else - { - this.spawnX.setText(WDL.worldProps.getProperty("SpawnX")); - this.spawnY.setText(WDL.worldProps.getProperty("SpawnY")); - this.spawnZ.setText(WDL.worldProps.getProperty("SpawnZ")); - } - } - - private void pickSpawn() - { - int var1 = (int)Math.floor(WDL.tp.posX); - int var2 = (int)Math.floor(WDL.tp.posY); - int var3 = (int)Math.floor(WDL.tp.posZ); - this.spawnX.setText(String.valueOf(var1)); - this.spawnY.setText(String.valueOf(var2)); - this.spawnZ.setText(String.valueOf(var3)); - } -} diff --git a/forge/src/main/java/wdl/WDL.java b/forge/src/main/java/wdl/WDL.java deleted file mode 100644 index 9ea5057..0000000 --- a/forge/src/main/java/wdl/WDL.java +++ /dev/null @@ -1,1450 +0,0 @@ -package wdl; - -import java.io.DataInputStream; -import java.io.File; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.FileReader; -import java.io.FileWriter; -import java.lang.reflect.Field; -import java.lang.reflect.Method; -import java.util.HashSet; -import java.util.List; -import java.util.Properties; - -import com.mojang.realmsclient.RealmsMainScreen; -import com.mojang.realmsclient.dto.McoServer; - -import net.minecraft.block.Block; -import net.minecraft.block.BlockBrewingStand; -import net.minecraft.block.BlockChest; -import net.minecraft.block.BlockDispenser; -import net.minecraft.block.BlockFurnace; -import net.minecraft.block.BlockNote; -import net.minecraft.client.Minecraft; -import net.minecraft.client.entity.EntityClientPlayerMP; -import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.GuiIngameMenu; -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.client.gui.GuiScreenRealmsProxy; -import net.minecraft.client.multiplayer.ChunkProviderClient; -import net.minecraft.client.multiplayer.WorldClient; -import net.minecraft.client.resources.I18n; -import net.minecraft.entity.Entity; -import net.minecraft.entity.EntityList; -import net.minecraft.entity.boss.EntityDragon; -import net.minecraft.entity.item.EntityBoat; -import net.minecraft.entity.item.EntityEnderEye; -import net.minecraft.entity.item.EntityEnderPearl; -import net.minecraft.entity.item.EntityExpBottle; -import net.minecraft.entity.item.EntityFallingBlock; -import net.minecraft.entity.item.EntityItem; -import net.minecraft.entity.item.EntityMinecart; -import net.minecraft.entity.item.EntityMinecartChest; -import net.minecraft.entity.item.EntityPainting; -import net.minecraft.entity.item.EntityTNTPrimed; -import net.minecraft.entity.item.EntityXPOrb; -import net.minecraft.entity.passive.EntitySquid; -import net.minecraft.entity.passive.EntityVillager; -import net.minecraft.entity.passive.IAnimals; -import net.minecraft.entity.projectile.EntityEgg; -import net.minecraft.entity.projectile.EntityFishHook; -import net.minecraft.entity.projectile.EntityPotion; -import net.minecraft.init.Blocks; -import net.minecraft.inventory.Container; -import net.minecraft.inventory.ContainerBrewingStand; -import net.minecraft.inventory.ContainerChest; -import net.minecraft.inventory.ContainerDispenser; -import net.minecraft.inventory.ContainerFurnace; -import net.minecraft.inventory.ContainerMerchant; -import net.minecraft.inventory.IInventory; -import net.minecraft.inventory.InventoryEnderChest; -import net.minecraft.item.ItemStack; -import net.minecraft.nbt.CompressedStreamTools; -import net.minecraft.nbt.NBTTagCompound; -import net.minecraft.nbt.NBTTagDouble; -import net.minecraft.nbt.NBTTagFloat; -import net.minecraft.nbt.NBTTagList; -import net.minecraft.network.NetworkManager; -import net.minecraft.realms.RealmsScreen; -import net.minecraft.tileentity.TileEntity; -import net.minecraft.tileentity.TileEntityBrewingStand; -import net.minecraft.tileentity.TileEntityChest; -import net.minecraft.tileentity.TileEntityDispenser; -import net.minecraft.tileentity.TileEntityEnderChest; -import net.minecraft.tileentity.TileEntityFurnace; -import net.minecraft.tileentity.TileEntityNote; -import net.minecraft.util.ChatComponentText; -import net.minecraft.util.LongHashMap; -import net.minecraft.util.MovingObjectPosition.MovingObjectType; -import net.minecraft.world.ChunkPosition; -import net.minecraft.world.MinecraftException; -import net.minecraft.world.chunk.Chunk; -import net.minecraft.world.chunk.storage.AnvilSaveConverter; -import net.minecraft.world.chunk.storage.IChunkLoader; -import net.minecraft.world.chunk.storage.RegionFileCache; -import net.minecraft.world.storage.ISaveHandler; -import net.minecraft.world.storage.SaveHandler; -import net.minecraft.world.storage.ThreadedFileIOBase; - -/** - * This is the main class that does most of the work. - */ -public class WDL -{ - //TODO: This class needs to be split into smaller classes. There is way too much different stuff in here. - - public static boolean DEBUG = false; // Setting to false will suppress debug output in chat console - - // References: - public static Minecraft mc; // Reference to the Minecraft object - public static WorldClient wc; // Reference to the World object that WDL uses - public static NetworkManager nm = null; // Reference to a connection specific object. Used to detect a new connection. - public static EntityClientPlayerMP tp; - - public static Container windowContainer; // Reference to the place where all the item stacks end up after receiving them. - public static int lastX = 0, lastY = 0, lastZ = 0; // Last right clicked block. Needed for TileEntity creation! - public static Entity lastEntity; // Last entity clicked (used for non-block tiles like minecarts with chests) - - public static SaveHandler saveHandler; // For player files and the level.dat file - public static IChunkLoader chunkLoader; // For the chunks (despite it's name it does also SAVE them) - - // Positions of newly created TileEntities that will overwrite the imported ones when saving: - public static HashSet newTileEntities = new HashSet(); - - // State variables: - public static boolean downloading = false; // Read-only outside of this class! - public static boolean isMultiworld = false; // Is this a multiworld server? - public static boolean propsFound = false; // Are there saved properties available? - public static boolean startOnChange = false; // Automatically restart after world changes? - - public static boolean saving = false; - public static boolean worldLoadingDeferred = false; - - // Names: - public static String worldName = "WorldDownloaderERROR"; // safe default - public static String baseFolderName = "WorldDownloaderERROR"; // safe default - - // Properties: - public static Properties baseProps; - public static Properties worldProps; - public static Properties defaultProps; - - // Initialization: - static - { - mc = Minecraft.getMinecraft(); - - // Initialize the Properties template: - defaultProps = new Properties(); - defaultProps.setProperty("ServerName", ""); - defaultProps.setProperty("WorldName", ""); - defaultProps.setProperty("LinkedWorlds", ""); - defaultProps.setProperty("AutoStart", "false"); - defaultProps.setProperty("GameType", "keep"); - defaultProps.setProperty("Time", "keep"); - defaultProps.setProperty("Weather", "keep"); - defaultProps.setProperty("MapFeatures", "false"); - defaultProps.setProperty("RandomSeed", ""); - defaultProps.setProperty("GeneratorName", "flat"); - defaultProps.setProperty("GeneratorVersion", "0"); - defaultProps.setProperty("Spawn", "player"); - defaultProps.setProperty("SpawnX", "8"); - defaultProps.setProperty("SpawnY", "127"); - defaultProps.setProperty("SpawnZ", "8"); - defaultProps.setProperty("PlayerPos", "keep"); - defaultProps.setProperty("PlayerX", "8"); - defaultProps.setProperty("PlayerY", "127"); - defaultProps.setProperty("PlayerZ", "8"); - defaultProps.setProperty("PlayerHealth", "20"); - defaultProps.setProperty("PlayerFood", "20"); - - baseProps = new Properties(defaultProps); - worldProps = new Properties(baseProps); - } - - /** Starts the download */ - public static void start() - { - wc = mc.theWorld; - if (isMultiworld && worldName.isEmpty()) - { - // Ask the user which world is loaded - mc.displayGuiScreen(new GuiWDLMultiworldSelect(null)); - return; - } - - if (!propsFound) - { - // Never seen this world before. Ask user about multiworlds: - mc.displayGuiScreen(new GuiWDLMultiworld(null)); - return; - } - - WDL.mc.displayGuiScreen((GuiScreen)null); - WDL.mc.setIngameFocus(); - - worldProps = loadWorldProps(worldName); - - saveHandler = (SaveHandler)mc.getSaveLoader().getSaveLoader(getWorldFolderName(worldName), true); - chunkLoader = saveHandler.getChunkLoader(wc.provider); - - newTileEntities = new HashSet(); - - if (baseProps.getProperty("ServerName").isEmpty()) - baseProps.setProperty("ServerName", getServerName()); - - startOnChange = true; - downloading = true; - chatMsg("Download started"); - } - - /** Stops the download */ - public static void stop() - { - if (downloading) - { - // Indicate that downloading has stopped - downloading = false; - startOnChange = false; - chatMsg("Download stopped"); - - startSaveThread(); - } - } - - private static void startSaveThread() - { - // Indicate that we are saving - WDL.chatMsg("Save started."); - WDL.saving = true; - WDLSaveAsync saver = new WDLSaveAsync(); - Thread thread = new Thread(saver, "WDL Save Thread"); - thread.start(); - } - - /** Must be called after the static World object in Minecraft has been replaced */ - public static void onWorldLoad() - { - if (mc.isIntegratedServerRunning()) - return; - - // If already downloading - if (downloading) - { - // If not currently saving, stop the current download and start saving now - if (!saving) - { - WDL.chatMsg("World change detected. Download will start once current save completes."); - // worldLoadingDeferred = true; - startSaveThread(); - } - return; - } - loadWorld(); - } - - public static void loadWorld() - { - worldName = ""; // The new (multi-)world name is unknown at the moment - wc = mc.theWorld; - tp = mc.thePlayer; - windowContainer = tp.openContainer; - - // Is this a different server? - NetworkManager newNM = tp.sendQueue.getNetworkManager(); // tp.sendQueue.getNetManager() - - if (nm != newNM) - { - // Different server, different world! - chatDebug("onWorldLoad: different server!"); - nm = newNM; - loadBaseProps(); - if (baseProps.getProperty("AutoStart").equals("true")) - start(); - else - startOnChange = false; - } - else - { - // Same server, different world! - chatDebug("onWorldLoad: same server!"); - if (startOnChange) - start(); - } - } - - /** Must be called when the world is no longer used */ - public static void onWorldUnload() - { - } - - public static void onSaveComplete() - { - WDL.mc.getSaveLoader().flushCache(); - WDL.saveHandler.flush(); - WDL.wc = null; - - // If still downloading, load the current world and keep on downloading - if (downloading) - { - WDL.chatMsg("Save complete. Starting download again."); - WDL.loadWorld(); - return; - } - - WDL.chatMsg("Save complete. Your single player file is ready to play!"); - } - - /** Must be called when a chunk is no longer needed and should be removed */ - public static void onChunkNoLongerNeeded(Chunk unneededChunk) - { - if (unneededChunk == null || unneededChunk.isModified == false) - return; - - chatDebug("onChunkNoLongerNeeded: " + unneededChunk.xPosition + ", " + unneededChunk.zPosition); - saveChunk(unneededChunk); - } - - /** Must be called when a GUI that receives item stacks from the server is shown */ - public static void onItemGuiOpened() - { - if (mc.objectMouseOver == null) - return; - - if (mc.objectMouseOver.typeOfHit == MovingObjectType.ENTITY) - { - lastEntity = mc.objectMouseOver.entityHit; - } - else - { - lastEntity = null; - lastX = mc.objectMouseOver.blockX; - lastY = mc.objectMouseOver.blockY; - lastZ = mc.objectMouseOver.blockZ; - } - } - - /** Must be called when a GUI that triggered an onItemGuiOpened is no longer shown */ - public static void onItemGuiClosed() - { - String saveName = ""; - - // If the last thing clicked was an ENTITY - if (lastEntity != null) - { - - if (lastEntity instanceof EntityMinecart && windowContainer instanceof ContainerChest) - { - EntityMinecart emc = (EntityMinecart)lastEntity; - if (emc instanceof EntityMinecartChest) - { - EntityMinecartChest emcc = (EntityMinecartChest)emc; - for (int i = 0; i < emcc.getSizeInventory(); i++) - { - emcc.setInventorySlotContents(i, windowContainer.getSlot(i).getStack()); - saveName = "Storage Minecart contents"; - } - } - } - else if (lastEntity instanceof EntityVillager && windowContainer instanceof ContainerMerchant) - { - EntityVillager ev = (EntityVillager)lastEntity; - WDL.chatDebug("Saving villager offers is not yet supported."); - saveName = "Villager offers"; - return; - } - else - { - WDL.chatMsg("Unsupported entity cannot be saved:" + EntityList.getEntityString(lastEntity)); - } - WDL.chatDebug("Saved " + saveName + "."); - return; - } - - // Else, the last thing clicked was a TILE ENTITY - // Get the tile entity which we are going to update the inventory for - TileEntity te = wc.getTileEntity(lastX, lastY, lastZ); - if (te == null) - { - WDL.chatDebug("onItemGuiClosed could not get TE at " + lastX + " " + lastY + " " + lastZ); - return; - } - - if (windowContainer instanceof ContainerChest && te instanceof TileEntityChest) - { - if (windowContainer.inventorySlots.size() > 63) - { - TileEntity te2; - ChunkPosition cp1 = new ChunkPosition(lastX, lastY, lastZ); - ChunkPosition cp2; - TileEntityChest tec1, tec2; - if ((te2 = wc.getTileEntity(lastX, lastY, lastZ + 1)) instanceof TileEntityChest && - ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) - { - tec1 = (TileEntityChest)te; - tec2 = (TileEntityChest)te2; - cp2 = new ChunkPosition(lastX, lastY, lastZ + 1); - } - else if ((te2 = wc.getTileEntity(lastX, lastY, lastZ - 1)) instanceof TileEntityChest && - ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) - { - tec1 = (TileEntityChest)te2; - tec2 = (TileEntityChest)te; - cp2 = new ChunkPosition(lastX, lastY, lastZ - 1); - } - else if ((te2 = wc.getTileEntity(lastX + 1, lastY, lastZ)) instanceof TileEntityChest && - ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) - { - tec1 = (TileEntityChest)te; - tec2 = (TileEntityChest)te2; - cp2 = new ChunkPosition(lastX + 1, lastY, lastZ); - } - else if ((te2 = wc.getTileEntity(lastX - 1, lastY, lastZ)) instanceof TileEntityChest && - ((TileEntityChest)te2).func_145980_j() == ((TileEntityChest)te).func_145980_j()) - { - tec1 = (TileEntityChest)te2; - tec2 = (TileEntityChest)te; - cp2 = new ChunkPosition(lastX - 1, lastY, lastZ); - } - else - { - WDL.chatMsg("Could not save this chest!"); - return; - } - copyItemStacks(windowContainer, (TileEntityChest)tec1, 0); - copyItemStacks(windowContainer, (TileEntityChest)tec2, 27); - newTileEntities.add(cp1); - newTileEntities.add(cp2); - saveName = "Double Chest contents"; - } - // basic chest - else - { - copyItemStacks(windowContainer, (TileEntityChest)te, 0); - newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); - saveName = "Chest contents"; - } - } - else if (windowContainer instanceof ContainerChest && te instanceof TileEntityEnderChest) - { - InventoryEnderChest inventoryEnderChest = tp.getInventoryEnderChest(); - int inventorySize = inventoryEnderChest.getSizeInventory(); - int containerSize = windowContainer.inventorySlots.size(); - for (int i = 0; i < containerSize && i < inventorySize; i++) - { - inventoryEnderChest.setInventorySlotContents(i, windowContainer.getSlot(i).getStack()); - } - saveName = "Ender Chest contents"; - } - else if (windowContainer instanceof ContainerBrewingStand) - { - copyItemStacks(windowContainer, (TileEntityBrewingStand)te, 0); - newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); - saveName = "Brewing Stand contents"; - } - else if (windowContainer instanceof ContainerDispenser) - { - copyItemStacks(windowContainer, (TileEntityDispenser)te, 0); - newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); - saveName = "Dispenser contents"; - } - else if (windowContainer instanceof ContainerFurnace) - { - copyItemStacks(windowContainer, (TileEntityFurnace)te, 0); - newTileEntities.add(new ChunkPosition(lastX, lastY, lastZ)); - saveName = "Furnace contents"; - } - else - { - WDL.chatDebug("onItemGuiClosed unhandled TE: " + te); - return; - } - - WDL.chatDebug("Saved " + saveName + "."); - return; - } - - /** - * Must be called when a block event is scheduled for the next tick. The caller has to check if WDL.downloading is true! - */ - public static void onBlockEvent(int x, int y, int z, Block block, int event, int param) - { - // if( blockID == Block.music.blockID ) - if (block == Blocks.noteblock) - { - TileEntityNote newTE = new TileEntityNote(); - newTE.note = (byte)(param % 25); - wc.setTileEntity(x, y, z, newTE); - newTileEntities.add(new ChunkPosition(x, y, z)); - chatDebug("onBlockEvent: Note Block: " + x + " " + y + " " + z + " pitch: " + param + " - " + newTE); - } - // Pistons, Chests (open, close), EnderChests, ... (see references to WorldServer.addBlockEvent) - } - - - /** - * Must be called when an entity is about to be removed from the world. - * @return true if the entity should not be removed, false if it can be - */ - public static boolean shouldKeepEntity(Entity entity) - { - // If the entity is being removed and it's outside the default tracking range, - // go ahead and remember it until the chunk is saved. - if(WDL.downloading) - { - if(entity != null) - { - int threshold = 0; - if ((entity instanceof EntityFishHook) || - //(entity instanceof EntityArrow) || - //(entity instanceof EntitySmallFireball) || - //(entity instanceof EntitySnowball) || - (entity instanceof EntityEnderPearl) || - (entity instanceof EntityEnderEye) || - (entity instanceof EntityEgg) || - (entity instanceof EntityPotion) || - (entity instanceof EntityExpBottle) || - (entity instanceof EntityItem) || - (entity instanceof EntitySquid)) - { - threshold = 64; - } - else if ((entity instanceof EntityMinecart) || - (entity instanceof EntityBoat) || - (entity instanceof IAnimals)) - { - threshold = 80; - } - else if ((entity instanceof EntityDragon) || - (entity instanceof EntityTNTPrimed) || - (entity instanceof EntityFallingBlock) || - (entity instanceof EntityPainting) || - (entity instanceof EntityXPOrb)) - { - threshold = 160; - } - double distance = entity.getDistance(WDL.tp.posX, entity.posY, WDL.tp.posZ); - if( distance > (double)threshold) - { - WDL.chatDebug("removeEntityFromWorld: Refusing to remove " + EntityList.getEntityString(entity) + " at distance " + distance); - return true; - } - WDL.chatDebug("removeEntityFromWorld: Removing " + EntityList.getEntityString(entity) + " at distance " + distance); - } - } - return false; - } - - /** Load the previously saved TileEntities and add them to the Chunk **/ - public static void importTileEntities(Chunk chunk) - { - File chunkSaveLocation = (File)stealAndGetField(chunkLoader, File.class); - DataInputStream dis = RegionFileCache.getChunkInputStream(chunkSaveLocation, chunk.xPosition, chunk.zPosition); - try - { - NBTTagCompound chunkNBT = CompressedStreamTools.read(dis); - - // NBTTagCompound levelNBT = chunkNBT.getCompoundTag( "Level" ); - NBTTagCompound levelNBT = chunkNBT.getCompoundTag("Level"); - - // The official code checks if the chunk is in the right location. Should I too?. - NBTTagList tileEntitiesNBT = levelNBT.getTagList("TileEntities", 10); - if (tileEntitiesNBT != null) - { - for (int i = 0; i < tileEntitiesNBT.tagCount(); i++) - { - NBTTagCompound tileEntityNBT = (NBTTagCompound)tileEntitiesNBT.getCompoundTagAt(i); - TileEntity te = TileEntity.createAndLoadEntity(tileEntityNBT); - String entityType = null; - if ((entityType = isImportableTileEntity(te)) != null) - { - if (!newTileEntities.contains(new ChunkPosition(te.xCoord, te.yCoord, te.zCoord))) - { - wc.setTileEntity(te.xCoord, te.yCoord, te.zCoord, te); - chatDebug("Loaded TE: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); - } - else - { - chatDebug("Dropping old TE: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); - } - } - else - { - chatDebug("Old TE is not importable: " + entityType + " at " + te.xCoord + " " + te.yCoord + " " + te.zCoord); - } - } - } - } - catch (Exception e) - { - } // Couldn't load the old chunk. Nothing unusual. Happens with every not downloaded chunk. - } - - /** Checks if the TileEntity should be imported. Only "problematic" TEs will be imported. */ - public static String isImportableTileEntity(TileEntity te) - { - Block block = wc.getBlock(te.xCoord, te.yCoord, te.zCoord); - if (block instanceof BlockChest && te instanceof TileEntityChest) - { - return "TileEntityChest"; - } - else if (block instanceof BlockDispenser && te instanceof TileEntityDispenser) - { - return "TileEntityDispenser"; - } - else if (block instanceof BlockFurnace && te instanceof TileEntityFurnace) - { - return "TileEntityFurnace"; - } - else if (block instanceof BlockNote && te instanceof TileEntityNote) - { - return "TileEntityNote"; - } - else if (block instanceof BlockBrewingStand && te instanceof TileEntityBrewingStand) - { - return "TileEntityBrewingStand"; - } - else - { - return null; - } - } - - /** Saves all remaining chunks, world info and player info. Usually called when stopping. */ - public static void saveEverything() - { - saveProps(); - - try - { - saveHandler.checkSessionLock(); - } - catch (MinecraftException e) - { - throw new RuntimeException("WorldDownloader: Couldn't get session lock for saving the world!"); - } - - NBTTagCompound playerNBT = new NBTTagCompound(); - tp.writeToNBT(playerNBT); - applyOverridesToPlayer(playerNBT); - - ISaveHandler saveHAndler = wc.getSaveHandler(); - AnvilSaveConverter saveConverter = (AnvilSaveConverter)mc.getSaveLoader(); - - wc.getWorldInfo().setSaveVersion(getSaveVersion(saveConverter)); - - NBTTagCompound worldInfoNBT = wc.getWorldInfo().cloneNBTCompound(playerNBT); - applyOverridesToWorldInfo(worldInfoNBT); - - savePlayer(playerNBT); - saveWorldInfo(worldInfoNBT); - try - { - saveChunks(); - } - catch (IllegalArgumentException e) - { - e.printStackTrace(); - } - catch (IllegalAccessException e) - { - e.printStackTrace(); - } - } - - /** Save the player (position, health, inventory, ...) into its own file in the players directory */ - public static void savePlayer(NBTTagCompound playerNBT) - { - chatDebug("Saving player data..."); - try - { - File playersDirectory = new File(saveHandler.getWorldDirectory(), "playerdata"); - File playerFile = new File(playersDirectory, tp.getUniqueID().toString() + ".dat.tmp"); - File playerFileOld = new File(playersDirectory, tp.getUniqueID().toString() + ".dat"); - - CompressedStreamTools.writeCompressed(playerNBT, new FileOutputStream(playerFile)); - - if (playerFileOld.exists()) - { - playerFileOld.delete(); - } - playerFile.renameTo(playerFileOld); - } - catch (Exception e) - { - throw new RuntimeException("Couldn't save the player!"); - } - chatDebug("Player data saved."); - } - - /** Save the world metadata (time, gamemode, seed, ...) into the level.dat file */ - public static void saveWorldInfo(NBTTagCompound worldInfoNBT) - { - chatDebug("Saving world metadata..."); - File saveDirectory = saveHandler.getWorldDirectory(); - NBTTagCompound dataNBT = new NBTTagCompound(); - dataNBT.setTag("Data", worldInfoNBT); - - try - { - File dataFile = new File(saveDirectory, "level.dat_new"); - File dataFileBackup = new File(saveDirectory, "level.dat_old"); - File dataFileOld = new File(saveDirectory, "level.dat"); - CompressedStreamTools.writeCompressed(dataNBT, new FileOutputStream(dataFile)); - - if (dataFileBackup.exists()) - { - dataFileBackup.delete(); - } - - dataFileOld.renameTo(dataFileBackup); - if (dataFileOld.exists()) - { - dataFileOld.delete(); - } - - dataFile.renameTo(dataFileOld); - if (dataFile.exists()) - { - dataFile.delete(); - } - } - catch (Exception e) - { - throw new RuntimeException("Couldn't save the world metadata!"); - } - chatDebug("World data saved."); - } - - /** - * Calls saveChunk for all currently loaded chunks - * - * @throws IllegalAccessException - * @throws IllegalArgumentException - */ - public static void saveChunks() throws IllegalArgumentException, IllegalAccessException - { - chatDebug("Saving chunks..."); - // Get the ChunkProviderClient from WorldClient - ChunkProviderClient chunkProvider = (ChunkProviderClient)wc.getChunkProvider(); - - // Get the hashArray field and set it accessible - Field hashArrayField = null; - Field[] lhmFields = LongHashMap.class.getDeclaredFields(); - //System.out.println("Looking for hashArray field..."); - for (Field f : lhmFields) - { - //System.out.println("Found field " + f.getName() + " of type " + f.getType().getName()); - if (f.getType().isArray()) - { - hashArrayField = f; - break; - } - } - if (hashArrayField == null) - { - chatMsg("Could not save chunks. Reflection error."); - return; - } - //System.out.println("Setting hashArrayField of type " + hashArrayField.getType().getName() + " accessible."); - hashArrayField.setAccessible(true); - - // Steal the instance of LongHashMap from our chunk provider - //System.out.println("Stealing field from chunkProvider (type=" + chunkProvider.getClass().getName() + ") of type " + LongHashMap.class.getName()); - LongHashMap lhm = (LongHashMap)stealAndGetField(chunkProvider, LongHashMap.class); - /* - if (lhm != null) - { - System.out.println("Successfully got lhm of type" + lhm.getClass().getName()); - } - */ - // Get the LongHashMap.Entry[] through the now accessible field using a - // LongHashMap we steal from our chunkProvider. - Object[] hashArray = (Object[])hashArrayField.get(lhm); - //System.out.println("hashArray is of type " + hashArray.getClass().getName()); - - //System.out.println("hashArray.length = " + hashArray.length); - if (hashArray.length == 0) - { - chatError("ChunkProviderClient has no chunk data!"); - return; - } - else - { - // Get the actual class for LongHashMap.Entry - Class Entry = null; - for (Object o : hashArray) - { - if(o != null) - { - Entry = o.getClass(); - break; - } - } - if(Entry == null) - { - chatError("Could not get class for LongHashMap.Entry."); - return; - } - - // Find the private fields for 'value' and 'nextEntry' in - // LongHashMap.Entry and make them accessible - Field valueField = Entry.getDeclaredFields()[1]; // value - valueField.setAccessible(true); - Field nextEntryField = Entry.getDeclaredFields()[2]; // nextEntry - nextEntryField.setAccessible(true); - - WDLSaveProgressReporter progressReporter = new WDLSaveProgressReporter(); - progressReporter.start(); - - for (int i = 0; i < hashArray.length; ++i) - { - // for (LongHashMap.Entry entry = hashArray[i]; entry != null; - // entry = entry.nextEntry) - for (Object lhme = hashArray[i]; lhme != null; lhme = nextEntryField.get(lhme)) - { - // Chunk c = (Chunk)lhme.getValue(); - Chunk c = (Chunk)valueField.get(lhme); - if (c != null && c.isModified) - { - saveChunk(c); - - try - { - ThreadedFileIOBase.threadedIOInstance.waitForFinish(); - } catch (Exception e) - { - chatMsg("Threw exception waiting for asynchronous IO to finish. Hmmm."); - } - } else - { - chatMsg("Didn\'t save chunk " + c.xPosition + " " + c.zPosition + " because isModified is false!"); - } - } - } - chatDebug("Chunk data saved."); - } - } - - /** - * Renders World Downloader save progress bar - */ - /* - * public static void renderSaveProgress() { if (saveProgress == 0) return; FontRenderer fontRendererObj = mc.fontRendererObj; ScaledResolution scaledResolution = new ScaledResolution(mc.gameSettings, - * mc.displayWidth, mc.displayHeight); int scaledWidth = scaledResolution.getScaledWidth(); short width = 182; int xPos = scaledWidth / 2 - width / 2; byte yPos = 12; - * mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 74, width, 5); mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 74, width, 5); mc.ingameGUI.drawTexturedModalRect(xPos, yPos, 0, 79, - * saveProgress * width, 5); - * - * String var9 = "Save Progress"; fontRendererObj.drawStringWithShadow(var9, scaledWidth / 2 - fontRendererObj.getStringWidth(var9) / 2, yPos - 10, 16711935); GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); - * GL11.glBindTexture(GL11.GL_TEXTURE_2D, mc.renderEngine.getTexture("/gui/icons.png")); } - */ - - /** Import all not overwritten TileEntities, then save the chunk */ - public static void saveChunk(Chunk c) - { - // chatMsg( "saveChunk at " + c.xPosition + " " + c.zPosition); - importTileEntities(c); - c.isTerrainPopulated = true; - try - { - chunkLoader.saveChunk(wc, c); - } - catch (Exception e) - { - // Better tell the player that something didn't work: - chatMsg("Chunk at chunk position " + c.xPosition + "," + c.zPosition + " can't be saved!"); - } - } - - /** Loads the server specific set of properties */ - public static void loadBaseProps() - { - baseFolderName = getBaseFolderName(); - baseProps = new Properties(defaultProps); - try - { - baseProps.load(new FileReader(new File(mc.mcDataDir, "saves/" + baseFolderName + "/WorldDownloader.txt"))); - propsFound = true; - } - catch (FileNotFoundException e) - { - propsFound = false; - } - catch (Exception e) - { - } - - if (baseProps.getProperty("LinkedWorlds").isEmpty()) - { - isMultiworld = false; - worldProps = new Properties(baseProps); - } - else - isMultiworld = true; - } - - /** Loads the world specific set of properties */ - public static Properties loadWorldProps(String theWorldName) - { - Properties ret = new Properties(baseProps); - if (!theWorldName.isEmpty()) - { - String folder = getWorldFolderName(theWorldName); - - try - { - ret.load(new FileReader(new File(mc.mcDataDir, "saves/" + folder + "/WorldDownloader.txt"))); - } - catch (Exception e) - { - return null; - } - } - return ret; - } - - /** Saves the currently used base and world properties in the corresponding folders */ - public static void saveProps() - { - saveProps(worldName, worldProps); - } - - /** Saves the specified world properties and the base properties in the corresponding folders */ - public static void saveProps(String theWorldName, Properties theWorldProps) - { - if (theWorldName.length() > 0) - { - String folder = getWorldFolderName(theWorldName); - try - { - theWorldProps.store(new FileWriter(new File(mc.mcDataDir, "saves/" + folder + "/WorldDownloader.txt")), ""); - } - catch (Exception e) - { - } - } - else if (!isMultiworld) - { - baseProps.putAll(theWorldProps); - } - - File baseFolder = new File(mc.mcDataDir, "saves/" + baseFolderName); - baseFolder.mkdirs(); - try - { - baseProps.store(new FileWriter(new File(baseFolder, "WorldDownloader.txt")), ""); - } - catch (Exception e) - { - } - } - - /** Change player specific fields according to the overrides found in the properties file */ - public static void applyOverridesToPlayer(NBTTagCompound playerNBT) - { - // Health - String health = worldProps.getProperty("PlayerHealth"); - if (!health.equals("keep")) - { - short h = Short.parseShort(health); - playerNBT.setShort("Health", h); - } - - // foodLevel, foodTimer, foodSaturationLevel, foodExhaustionLevel - String food = worldProps.getProperty("PlayerFood"); - if (!food.equals("keep")) - { - int f = Integer.parseInt(food); - playerNBT.setInteger("foodLevel", f); - playerNBT.setInteger("foodTickTimer", 0); - if (f == 20) - { - playerNBT.setFloat("foodSaturationLevel", 5.0f); - } - else - { - playerNBT.setFloat("foodSaturationLevel", 0.0f); - } - playerNBT.setFloat("foodExhaustionLevel", 0.0f); - } - - // Player Position - String playerPos = worldProps.getProperty("PlayerPos"); - if (playerPos.equals("xyz")) - { - int x = Integer.parseInt(worldProps.getProperty("PlayerX")); - int y = Integer.parseInt(worldProps.getProperty("PlayerY")); - int z = Integer.parseInt(worldProps.getProperty("PlayerZ")); - - NBTTagList pos = playerNBT.getTagList("Pos", 6); - // Out with the old, in with the new - pos.removeTag(0); // removeTag - pos.removeTag(0); - pos.removeTag(0); - pos.appendTag(new NBTTagDouble(x + 0.5D)); // appendTag - pos.appendTag(new NBTTagDouble((double)y + 0.621D)); // Player height - pos.appendTag(new NBTTagDouble(x + 0.5D)); - - NBTTagList motion = playerNBT.getTagList("Motion", 6); - // Out with the old, in with the new - motion.removeTag(0); - motion.removeTag(0); - motion.removeTag(0); - motion.appendTag(new NBTTagDouble(0.0D)); - motion.appendTag(new NBTTagDouble(-0.0001D)); // Needed to land on the ground - motion.appendTag(new NBTTagDouble(0.0D)); - - NBTTagList rotation = playerNBT.getTagList("Rotation", 5); - // Out with the old, in with the new - rotation.removeTag(0); - rotation.removeTag(0); - rotation.appendTag(new NBTTagFloat(0.0f)); - rotation.appendTag(new NBTTagFloat(0.0f)); - } - } - - /** Change world and generator specific fields according to the overrides found in the properties file */ - public static void applyOverridesToWorldInfo(NBTTagCompound worldInfoNBT) - { - // LevelName - String baseName = baseProps.getProperty("ServerName"); - String worldName = worldProps.getProperty("WorldName"); - if (worldName.isEmpty()) - { - worldInfoNBT.setString("LevelName", baseName); - } - else - { - worldInfoNBT.setString("LevelName", baseName + " - " + worldName); - } - - // GameType - String gametypeOption = worldProps.getProperty("GameType"); - if (gametypeOption.equals("keep")) - { - if (tp.capabilities.isCreativeMode) // capabilities - { - worldInfoNBT.setInteger("GameType", 1); // Creative - } - else - { - worldInfoNBT.setInteger("GameType", 0); // Survival - } - } - else if (gametypeOption.equals("survival")) - { - worldInfoNBT.setInteger("GameType", 0); - } - else if (gametypeOption.equals("creative")) - { - worldInfoNBT.setInteger("GameType", 1); - } - else if (gametypeOption.equals("hardcore")) - { - worldInfoNBT.setInteger("GameType", 0); - worldInfoNBT.setBoolean("hardcore", true); - } - - // Time - String timeOption = worldProps.getProperty("Time"); - if (!timeOption.equals("keep")) - { - long t = Integer.parseInt(timeOption); - worldInfoNBT.setLong("Time", t); - } - - // RandomSeed - String randomSeed = worldProps.getProperty("RandomSeed"); - long seed = 0; - if (!randomSeed.isEmpty()) - { - try - { - seed = Long.parseLong(randomSeed); - } - catch (NumberFormatException numberformatexception) - { - seed = randomSeed.hashCode(); - } - } - worldInfoNBT.setLong("RandomSeed", seed); - - // MapFeatures - boolean mapFeatures = Boolean.parseBoolean(worldProps.getProperty("MapFeatures")); - worldInfoNBT.setBoolean("MapFeatures", mapFeatures); - - // generatorName - String generatorName = worldProps.getProperty("GeneratorName"); - worldInfoNBT.setString("generatorName", generatorName); - - // generatorVersion - int generatorVersion = Integer.parseInt(worldProps.getProperty("GeneratorVersion")); - worldInfoNBT.setInteger("generatorVersion", generatorVersion); - - // Weather - String weather = worldProps.getProperty("Weather"); - if (weather.equals("sunny")) - { - worldInfoNBT.setBoolean("raining", false); - worldInfoNBT.setInteger("rainTime", 0); - worldInfoNBT.setBoolean("thundering", false); - worldInfoNBT.setInteger("thunderTime", 0); - } - if (weather.equals("rain")) - { - worldInfoNBT.setBoolean("raining", true); - worldInfoNBT.setInteger("rainTime", 24000); - worldInfoNBT.setBoolean("thundering", false); - worldInfoNBT.setInteger("thunderTime", 0); - } - if (weather.equals("thunderstorm")) - { - worldInfoNBT.setBoolean("raining", true); - worldInfoNBT.setInteger("rainTime", 24000); - worldInfoNBT.setBoolean("thundering", true); - worldInfoNBT.setInteger("thunderTime", 24000); - } - - // Spawn - String spawn = worldProps.getProperty("Spawn"); - if (spawn.equals("player")) - { - int x = (int)Math.floor(tp.posX); - int y = (int)Math.floor(tp.posY); - int z = (int)Math.floor(tp.posZ); - worldInfoNBT.setInteger("SpawnX", x); - worldInfoNBT.setInteger("SpawnY", y); - worldInfoNBT.setInteger("SpawnZ", z); - worldInfoNBT.setBoolean("initialized", true); - } - else if (spawn.equals("xyz")) - { - int x = Integer.parseInt(worldProps.getProperty("SpawnX")); - int y = Integer.parseInt(worldProps.getProperty("SpawnY")); - int z = Integer.parseInt(worldProps.getProperty("SpawnZ")); - worldInfoNBT.setInteger("SpawnX", x); - worldInfoNBT.setInteger("SpawnY", y); - worldInfoNBT.setInteger("SpawnZ", z); - worldInfoNBT.setBoolean("initialized", true); - } - } - - /** Get the name of the server the user specified it in the server list */ - public static String getServerName() - { - try - { - if (mc.func_147104_D() != null) // getServerData - { - String name = mc.func_147104_D().serverName; - - if(name.equals(I18n.format("selectServer.defaultName"))) - { - // Direct connection using domain name or IP (and port) - name = mc.func_147104_D().serverIP; - } - return name; - } - else - { - String realmName = getRealmName(); - if(realmName != null) - { - return realmName; - } - } - } - catch (Exception e) - { - } - return "Unidentified Server"; - } - - public static String getRealmName() - { - // Is this the only way to get the name of the Realms server? Really Mojang? - // If this function turns out to be a pain to update, just remove Realms support completely. - // I doubt anyone will need this anyway since Realms support downloading the world out of the box. - - // Try to get the value of mc.getNetHandler().guiScreenServer: - GuiScreen screen = (GuiScreen) stealAndGetField(mc.getNetHandler(), GuiScreen.class); - - // If it is not a GuiScreenRealmsProxy we are not using a Realms server - if(!(screen instanceof GuiScreenRealmsProxy)) return null; - - // Get the proxy's RealmsScreen object - GuiScreenRealmsProxy screenProxy = (GuiScreenRealmsProxy) screen; - RealmsScreen rs = screenProxy.func_154321_a(); - - // It needs to be of type RealmsMainScreen (this should always be the case) - if(!(rs instanceof RealmsMainScreen)) return null; - - RealmsMainScreen rms = (RealmsMainScreen) rs; - McoServer mcos = null; - try - { - // Find the ID of the selected Realms server. Fortunately unobfuscated names! - Field selectedServerId = rms.getClass().getDeclaredField("selectedServerId"); - selectedServerId.setAccessible(true); - Object obj = selectedServerId.get(rms); - if(!(obj instanceof Long)) return null; - long id = ((Long)obj).longValue(); - - // Get the McoServer instance that was selected - Method findServer = rms.getClass().getDeclaredMethod("findServer", long.class); - findServer.setAccessible(true); - obj = findServer.invoke(rms, id); - if(!(obj instanceof McoServer)) return null; - mcos = (McoServer)obj; - } - catch (Exception e) - { - return null; - } - - // Return its name. Not sure if this is the best naming scheme... - return mcos.name; - } - - /** Get the base folder name for the server we are connected to */ - public static String getBaseFolderName() - { - return getServerName().replaceAll("\\W+", "_"); - } - - /** Get the folder name for the specified world */ - public static String getWorldFolderName(String theWorldName) - { - if (theWorldName.isEmpty()) - { - return baseFolderName; - } - else - { - return baseFolderName + " - " + theWorldName; - } - } - - public static void copyItemStacks(Container c, IInventory i, int startInContainerAt) - { - int containerSize = c.inventorySlots.size(); - int inventorySize = i.getSizeInventory(); - int nc = startInContainerAt; - int ni = 0; - - while ((nc < containerSize) && (ni < inventorySize)) - { - ItemStack is = c.getSlot(nc).getStack(); - i.setInventorySlotContents(ni, is); - ni++; - nc++; - } - } - - /** Adds a chat message with a World Downloader prefix */ - public static void chatMsg(String msg) - { - // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A7c[WorldDL]\u00A76 " + msg)); - } - - /** Adds a chat message with a World Downloader prefix */ - public static void chatDebug(String msg) - { - if (!WDL.DEBUG) - return; - // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A76 " + msg)); - } - - /** Adds a chat message with a World Downloader prefix */ - public static void chatError(String msg) - { - // System.out.println( "WorldDownloader: " + msg ); // Just for debugging! - mc.ingameGUI.getChatGUI().printChatMessage(new ChatComponentText("\u00A72[WorldDL]\u00A74 " + msg)); - } - - - private static int getSaveVersion(AnvilSaveConverter asc) - { - int saveVersion = 0; - try - { - Method[] anvilMethods = AnvilSaveConverter.class.getDeclaredMethods(); - for (Method m : anvilMethods) - { - if (m.getParameterTypes().length == 0 && m.getReturnType().equals(int.class)) - { - m.setAccessible(true); - saveVersion = (Integer)m.invoke(asc); - break; - } - } - } catch (Throwable t) - { - t.printStackTrace(); - } - if (saveVersion == 0) - { - saveVersion = 19133; // Version for 1.7.2 just in case we can't get - // it - } - return saveVersion; - } - - - /** - * Uses Java's reflection API to get access to an unaccessible field - * - * @param typeOfClass - * Class that the field should be read from - * @param typeOfField - * The type of the field - * @return An Object of type Field - */ - public static Field stealField(Class typeOfClass, Class typeOfField) - { - //System.out.println("stealField: typeOfClass = " + typeOfClass.getName()); - //System.out.println("stealField: typeOfField = " + typeOfField.getName()); - Field[] fields = typeOfClass.getDeclaredFields(); - for (Field f : fields) - { - //System.out.println("stealField: Found field " + f.getName() + - // " of type " + f.getType()); - - if (f.getType().equals(typeOfField)) - { - try - { - f.setAccessible(true); - return f; - } - catch (Exception e) - { - break; // Throw the Exception - } - } - } - throw new RuntimeException("WorldDownloader: Couldn't steal Field of type \"" + typeOfField + "\" from class \"" + typeOfClass + "\" !"); - } - - /** - * Uses Java's reflection API to get access to an unaccessible field - * - * @param object - * Object that the field should be read from or the type of the object if the field is static - * @param typeOfField - * The type of the field - * @return The value of the field - */ - public static Object stealAndGetField(Object object, Class typeOfField) - { - Class typeOfObject; - - if (object instanceof Class) // User asked for static field: - { - typeOfObject = (Class)object; - object = null; - } - else - { - typeOfObject = object.getClass(); - } - - try - { - Field f = stealField(typeOfObject, typeOfField); - return f.get(object); - } - catch (Exception e) - { - throw new RuntimeException("WorldDownloader: Couldn't get Field of type \"" + typeOfField + "\" from object \"" + object + "\" !"); - } - } - - public static void handleServerSeedMessage(String msg) - { - if (downloading && msg.startsWith("Seed: ")) - { - String seed = msg.substring(6); - worldProps.setProperty("RandomSeed", seed); - WDL.chatMsg("Setting single-player world seed to " + seed); - } - /* - * else { WDL.chatMsg("Could not retrieve server seed"); } - */ - } - - // Add World Downloader buttons to GuiIngameMenu - public static void injectWDLButtons(GuiIngameMenu gui, List buttonList) - { - if (mc.isIntegratedServerRunning()) - { - return; // WDL not available if in singleplayer or LAN server mode - } - - int insertAtYPos = 0; - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.id == 5) // Button "Achievements" - { - insertAtYPos = btn.yPosition + 24; - break; - } - } - - // Move other buttons down one slot (= 24 height units) - for( Object obj : buttonList) - { - GuiButton btn = (GuiButton)obj; - if(btn.yPosition >= insertAtYPos) - { - btn.yPosition += 24; - } - } - - // Insert buttons... The IDs are chosen to be unique (hopefully). They are ASCII encoded strings: "WDLs" and "WDLo" - GuiButton wdlDownload = new GuiButton(0x57444C73, gui.width / 2 - 100, insertAtYPos, 170, 20, "WDL bug!"); - GuiButton wdlOptions = new GuiButton(0x57444C6F, gui.width / 2 + 71, insertAtYPos, 28, 20, "..."); - - wdlDownload.displayString = (WDL.downloading ? (WDL.saving ? "Still saving..." : "Stop download") : "Download this world"); - wdlDownload.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); - - wdlOptions.enabled = (!WDL.downloading || (WDL.downloading && !WDL.saving)); - - buttonList.add(wdlDownload); - buttonList.add(wdlOptions); - } - - public static void handleWDLButtonClick(GuiIngameMenu gui, GuiButton button) - { - if (mc.isIntegratedServerRunning()) - { - return; // WDL not available if in singleplayer or LAN server mode - } - - if(button.id == 0x57444C73) // "Start/Stop Download" - { - if (WDL.downloading) - { - WDL.stop(); - WDL.mc.displayGuiScreen((GuiScreen)null); - WDL.mc.setIngameFocus(); - } - else - { - WDL.start(); - } - } - else if( button.id == 0x57444C6F) // "..." (options) - { - WDL.mc.displayGuiScreen(new GuiWDL(gui)); - } - else if( button.id == 1) // "Disconnect" - { - WDL.stop(); - } - } -} diff --git a/forge/src/main/java/wdl/WDLSaveAsync.java b/forge/src/main/java/wdl/WDLSaveAsync.java deleted file mode 100644 index 894aa0b..0000000 --- a/forge/src/main/java/wdl/WDLSaveAsync.java +++ /dev/null @@ -1,11 +0,0 @@ -package wdl; - -public class WDLSaveAsync implements Runnable -{ - public void run() - { - WDL.saveEverything(); - WDL.saving = false; - WDL.onSaveComplete(); - } -} diff --git a/forge/src/main/java/wdl/WDLSaveProgressReporter.java b/forge/src/main/java/wdl/WDLSaveProgressReporter.java deleted file mode 100644 index 9d12652..0000000 --- a/forge/src/main/java/wdl/WDLSaveProgressReporter.java +++ /dev/null @@ -1,27 +0,0 @@ -package wdl; - -public class WDLSaveProgressReporter implements Runnable -{ - public void run() - { - while (WDL.saving) - { - WDL.chatMsg("Saving..."); - - try - { - Thread.sleep(10000L); - } - catch (InterruptedException var2) - { - var2.printStackTrace(); - } - } - } - - public void start() - { - Thread var1 = new Thread(this); - var1.start(); - } -} diff --git a/forge/src/main/java/wdl/ForgeMod.java b/forge/src/main/java/wdl_forge/ForgeMod.java similarity index 99% rename from forge/src/main/java/wdl/ForgeMod.java rename to forge/src/main/java/wdl_forge/ForgeMod.java index 9836609..af65472 100644 --- a/forge/src/main/java/wdl/ForgeMod.java +++ b/forge/src/main/java/wdl_forge/ForgeMod.java @@ -1,5 +1,6 @@ -package wdl; +package wdl_forge; +import wdl.WDL; import net.minecraft.client.gui.GuiIngameMenu; import net.minecraftforge.client.event.ClientChatReceivedEvent; import net.minecraftforge.client.event.GuiOpenEvent; diff --git a/forge/src/main/java/wdl/WDLWorldAccess.java b/forge/src/main/java/wdl_forge/WDLWorldAccess.java similarity index 95% rename from forge/src/main/java/wdl/WDLWorldAccess.java rename to forge/src/main/java/wdl_forge/WDLWorldAccess.java index fae6f5f..c06bdb4 100644 --- a/forge/src/main/java/wdl/WDLWorldAccess.java +++ b/forge/src/main/java/wdl_forge/WDLWorldAccess.java @@ -1,4 +1,4 @@ -package wdl; +package wdl_forge; import net.minecraft.entity.Entity; import net.minecraft.entity.player.EntityPlayer; From cbeee843ec352e4cfbfec1d8d52ff90bef43ad3f Mon Sep 17 00:00:00 2001 From: Florian Sonnenberger Date: Sat, 19 Jul 2014 15:39:11 +0200 Subject: [PATCH 16/16] Add Forge-specific symlinks to the scripts --- createSymLinks.bat | 1 + createSymLinks.sh | 1 + 2 files changed, 2 insertions(+) diff --git a/createSymLinks.bat b/createSymLinks.bat index 0f7e117..6b25ae4 100644 --- a/createSymLinks.bat +++ b/createSymLinks.bat @@ -8,3 +8,4 @@ REM with the exception that deleting a symlink does not delete the linked resou REM Run this script after you've cloned the repo and anytime this file was changed in a new commit. mklink /j "mcp\src\minecraft\wdl" "src\wdl" +mklink /j "forge\src\main\java\wdl" "src\wdl" diff --git a/createSymLinks.sh b/createSymLinks.sh index b75f50f..e360f63 100755 --- a/createSymLinks.sh +++ b/createSymLinks.sh @@ -10,3 +10,4 @@ # Run this script after you've cloned the repo and anytime this file was changed in a new commit. ln -sr "src/wdl" "mcp/src/minecraft/wdl" +ln -sr "src/wdl" "forge/src/main/java/wdl"