-
Moving chests
Thanks, that worked. Here's what I ended up doing: if (tileEntity != null && tileEntity instanceof IInventory) { IInventory inventory = (IInventory)tileEntity; int count = inventory.getSizeInventory(); for (int i = 0; i < count; ++i) { ItemStack itemStack = inventory.getStackInSlot(i); if (itemStack != null) { inventory.decrStackSize(i, itemStack.stackSize); } } } I do this AFTER serializing all the TileEntity objects I find, but before destroying the objects containing them.
-
Moving chests
I've implemented a command in my mod that lets the user move all of the blocks in a selected volume (represented as a cuboid). If the volume contains a chest, I correctly save the chests contents, but when the chest is moved, the contents spill out into the world (as if the user had destroyed the chest), and the chest is moved and still has its contents. I'm wondering if there's a way to inhibit the contents spilling behavior. My mod currently runs in 1.5.2, 1.6.4, and 1.7.2 (hooray for git cherry-pick). I'm primarily looking for a solution for 1.7.2, but anything that works across all versions would be great too.
-
[1.7.2] Obfuscated name issue
My technique of diffing the old and new sources works reasonably well. Although names have changed, a lot still seems to be same.
-
[1.5.2] Backporting a mod to 1.5.2 (lesson's learned)
I started dabbling with mods in 1.6.4, ported my mods (a couple of server commands) to 1.7.2, and recently got interested in making my commands work in 1.5.2 to have them in Hexxit. My mods are simple enough to make the port from 1.6.4 pretty fast. Here's what I had to do. 1. In my mod main class, I had to change @EventHandler annotations to: @PreInit public void load(FMLInitializationEvent event) {} @PostInit public void postInit(FMLPostInitializationEvent event) {} @ServerStarting public void serverLoad(FMLServerStartingEvent event) {} 2. In my commands I had to change all calls of ICommandSender.getEntityWorld() to Entity.worldObj (after suitable casting). 3. I also had to change the type I pass to ICommandSender.sendChatToPlayer() from ChatMessageComponent to String. 4. In my custom block, I had to remove calls to Block.setTextureName() which didn't exist in 1.5.2. 5. In my custom block's override of onBlockPlacedBy(), the type of the player parameter changed from EntityLivingBase to EntityLiving. Lastly, my mod uses the GSON code that is bundled with MinecraftForge for 1.6.4 and later. So, I had to explicitly include the contents of that jar file in my mod's jar file. Is there a better way to handle dependencies like this? I would prefer sticking to JDK-classes if possible, but I don't believe Sun's JSON support is bundled by default in the 1.6 JDK, which I am targeting.
-
[1.7.2] Changing a block at an (x, y, z)
I did try to generate some queries with the mcp bot. The IRC experience has never been my cup of tea. I'd much prefer having a git repository somewhere that holds the mappings. If that's not practical, sigh.
-
How to fix "scala-library.jar; cannot read zip file"
Very helpful for those of us backporting our mods.
-
[1.7.2] Getting Started with Modding (again)
My advice would be to first build a mod for 1.6.4, since the tutorials exist, and the code will be much easier for you to understand. Once you get it working to your satisfaction, then try porting to 1.7.2. Many names have changed, even class names, so it really will be a port. Another piece of advice, use git and maintain your versions in branches. I've been playing a lot with the Technic launcher and specifically Hexxit, and am now considering backporting my mods to 1.5.2 because they will be so useful in the Hexxit mod collection.
-
[1.7.2] Progress on unobfuscation?
I have sort of been expecting to see fewer obfuscated symbols as new versions of MinecraftForge and FML come out. Am I missing something? I'd really like to get out of the business of coding using obfuscated names.
-
[1.7.2]Sending a packet to the server with the new netty system
Thanks for writing this tutorial. That's a lot of boilerplate to understand. One conceptual question I have is about thread-safety. Is it safe to call public void sendToAll(AbstractPacket message) { this.channels.get(Side.SERVER).attr(FMLOutboundHandler.FML_MESSAGETARGET).set(FMLOutboundHandler.OutboundTarget.ALL); this.channels.get(Side.SERVER).writeAndFlush(message); } from multiple threads? I assume this.channels.get(Side.SERVER).attr() is returning an object, whose value affects the behavior of writeAndFlush().
-
[1.7.2]Sending a packet to the server with the new netty system
How does one send the packet then? In my code above, I'm writing: ByteBuf data = buffer(4); data.writeInt(42); C17PacketCustomPayload packet = new C17PacketCustomPayload("NetworkExample", data); EntityClientPlayerMP player = (EntityClientPlayerMP)updateEvent.entityLiving; player.sendQueue.func_147297_a(packet); Would I just change the packet class to ServerCustomPacketEvent when sending from client to server?
-
[1.6.4] how do i move parts of the world?
I have written a couple of mods that do pretty much what you're asking (both teleportation and volume manipulation). However, the approach I'm taking is more like 3D copy & paste. But others have pointed out that I'm doing both character and matter teleportation in a sense. I also provide a way to archive an arbitrary volume as a JSON file that you can reload later, perhaps into another world. My approach to copying is to define a boundary cuboid, and copy all of the blocks I find in that cuboid into an internal representation. I use JSON serialization to save, and deserialization to load. To save the contents of chests, etc. you have to serialize the contents of TileEntity objects. Generalizing to a sphere is certainly doable, but a cuboid is usually good enough.
-
[1.7.2]Sending a packet to the server with the new netty system
Here's how I identify the player on the client side: @SubscribeEvent(priority = EventPriority.NORMAL) public void onEntityUpdated(LivingEvent.LivingUpdateEvent updateEvent) { EntityClientPlayerMP player = (EntityClientPlayerMP)updateEvent.entityLiving; ByteBuf data = buffer(4); data.writeInt(player.func_145782_y()); // Entity.getEntityID() data.writeInt(42); C17PacketCustomPayload packet = new C17PacketCustomPayload("NetworkExample", data); player.sendQueue.func_147297_a(packet); } On the server side I simply use that entity ID to look up something in a hash table to do the player matching.
-
[1.7.2] multiple line chat question
Looking further at the core commands (e.g. /help), it looks like each line has to be a sent as a separate call to ICommandSender.func_145747_a() (e.g. ICommandSender.sendChatToPlayer()). So, I simply wrote a line-breaking routine that my code calls to send chat messages: public static void sendMessageToPlayer(EntityPlayer player, String message) { ArrayIterator<String> lines = new ArrayIterator<String>(message.split("\n")); while (lines.hasNext()) player.func_145747_a(new ChatComponentText(lines.next())); }
-
exceptions thrown during gradle builds using git sources
Tossing all those ForgeGradle-1.1-SNAPSHOT.jar files apparently fixed the problem for me.
-
exceptions thrown during gradle builds using git sources
Just today, I started to see the following exceptions being thrown while running gradle setupForge: java.lang.IllegalArgumentException: object is not an instance of declaring class at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:606) at net.minecraftforge.gradle.tasks.abstractutil.CachedTask$Annotated.getValue(CachedTask.java:281) at net.minecraftforge.gradle.tasks.abstractutil.CachedTask$1.getFile(CachedTask.java:137) at net.minecraftforge.gradle.tasks.abstractutil.CachedTask$1.call(CachedTask.java:92) at net.minecraftforge.gradle.tasks.abstractutil.CachedTask$1.call(CachedTask.java:72) at groovy.lang.Closure.call(Closure.java:425) at org.gradle.api.specs.internal.ClosureSpec.isSatisfiedBy(ClosureSpec.java:32) at org.gradle.api.specs.AndSpec.isSatisfiedBy(AndSpec.java:42) at org.gradle.api.internal.tasks.execution.SkipOnlyIfTaskExecuter.execute(SkipOnlyIfTaskExecuter.java:41) at org.gradle.api.internal.tasks.execution.ExecuteAtMostOnceTaskExecuter.execute(ExecuteAtMostOnceTaskExecuter.java:43) at org.gradle.api.internal.AbstractTask.executeWithoutThrowingTaskFailure(AbstractTask.java:289) at org.gradle.execution.taskgraph.AbstractTaskPlanExecutor$TaskExecutorWorker.executeTask(AbstractTaskPlanExecutor.java:79) at org.gradle.execution.taskgraph.AbstractTaskPlanExecutor$TaskExecutorWorker.processTask(AbstractTaskPlanExecutor.java:63) at org.gradle.execution.taskgraph.AbstractTaskPlanExecutor$TaskExecutorWorker.run(AbstractTaskPlanExecutor.java:51) at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor$1.run(DefaultTaskPlanExecutor.java:33) at org.gradle.internal.Factories$1.create(Factories.java:22) at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:198) at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:266) at org.gradle.cache.internal.DefaultPersistentDirectoryStore.longRunningOperation(DefaultPersistentDirectoryStore.java:135) at org.gradle.api.internal.changedetection.state.DefaultTaskArtifactStateCacheAccess.longRunningOperation(DefaultTaskArtifactStateCacheAccess.java:95) at org.gradle.execution.taskgraph.DefaultTaskPlanExecutor.process(DefaultTaskPlanExecutor.java:31) at org.gradle.execution.taskgraph.DefaultTaskGraphExecuter.execute(DefaultTaskGraphExecuter.java:86) at org.gradle.execution.SelectedTaskExecutionAction.execute(SelectedTaskExecutionAction.java:29) at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61) at org.gradle.execution.DefaultBuildExecuter.access$200(DefaultBuildExecuter.java:23) at org.gradle.execution.DefaultBuildExecuter$2.proceed(DefaultBuildExecuter.java:67) at org.gradle.execution.DryRunBuildExecutionAction.execute(DryRunBuildExecutionAction.java:32) at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61) at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:54) at org.gradle.initialization.DefaultGradleLauncher.doBuildStages(DefaultGradleLauncher.java:166) at org.gradle.initialization.DefaultGradleLauncher.doBuild(DefaultGradleLauncher.java:113) at org.gradle.initialization.DefaultGradleLauncher.run(DefaultGradleLauncher.java:81) at org.gradle.launcher.exec.InProcessBuildActionExecuter$DefaultBuildController.run(InProcessBuildActionExecuter.java:64) at org.gradle.launcher.cli.ExecuteBuildAction.run(ExecuteBuildAction.java:33) at org.gradle.launcher.cli.ExecuteBuildAction.run(ExecuteBuildAction.java:24) at org.gradle.launcher.exec.InProcessBuildActionExecuter.execute(InProcessBuildActionExecuter.java:35) at org.gradle.launcher.exec.InProcessBuildActionExecuter.execute(InProcessBuildActionExecuter.java:26) at org.gradle.launcher.cli.RunBuildAction.run(RunBuildAction.java:50) at org.gradle.internal.Actions$RunnableActionAdapter.execute(Actions.java:171) at org.gradle.launcher.cli.CommandLineActionFactory$ParseAndBuildAction.execute(CommandLineActionFactory.java:201) at org.gradle.launcher.cli.CommandLineActionFactory$ParseAndBuildAction.execute(CommandLineActionFactory.java:174) at org.gradle.launcher.cli.CommandLineActionFactory$WithLogging.execute(CommandLineActionFactory.java:170) at org.gradle.launcher.cli.CommandLineActionFactory$WithLogging.execute(CommandLineActionFactory.java:139) at org.gradle.launcher.cli.ExceptionReportingAction.execute(ExceptionReportingAction.java:33) at org.gradle.launcher.cli.ExceptionReportingAction.execute(ExceptionReportingAction.java:22) at org.gradle.launcher.Main.doAction(Main.java:46) at org.gradle.launcher.bootstrap.EntryPoint.run(EntryPoint.java:45) at org.gradle.launcher.Main.main(Main.java:37) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:606) at org.gradle.launcher.bootstrap.ProcessBootstrap.runNoExit(ProcessBootstrap.java:50) at org.gradle.launcher.bootstrap.ProcessBootstrap.run(ProcessBootstrap.java:32) at org.gradle.launcher.GradleMain.main(GradleMain.java:23) I've tried lots of things, such as gradle --recompile-scripts --refresh-dependencies setupForge Any idea what's causing this? Poking around in my ~/.gradle directory, I found the classes in question here: strings -- ./caches/modules-2/files-2.1/net.minecraftforge.gradle/ForgeGradle/1.1-SNAPSHOT/9ea951d3ffbe791b762e203b2027d76afd1dd625/ForgeGradle-1.1-SNAPSHOT.jar strings -- ./caches/modules-2/files-2.1/net.minecraftforge.gradle/ForgeGradle/1.1-SNAPSHOT/de2903f5bc25b324ac65c0ab38032746c79a4643/ForgeGradle-1.1-SNAPSHOT.jar The referenced classes are in there. So, there's some kind of problem with these new snapshots.
IPS spam blocked by CleanTalk.