From 42ab196b06eab29cee02219d187af5b1e5ef2de1 Mon Sep 17 00:00:00 2001 From: George Paton Date: Mon, 1 Dec 2025 13:36:31 +1100 Subject: [PATCH] structure block! --- src/main/java/com/hbm/blocks/ModBlocks.java | 27 +- .../hbm/blocks/generic/BlockWandJigsaw.java | 12 +- .../com/hbm/blocks/generic/BlockWandLoot.java | 18 +- .../blocks/generic/BlockWandStructure.java | 573 ++++++++++++++++++ .../hbm/blocks/generic/BlockWandTandem.java | 12 +- .../inventory/gui/element/GuiFileList.java | 99 +++ .../java/com/hbm/items/tool/ItemWandS.java | 157 ++--- src/main/java/com/hbm/main/ClientProxy.java | 13 +- .../tileentity/RenderWandStructure.java | 92 +++ .../java/com/hbm/tileentity/TileMappings.java | 6 +- .../com/hbm/world/gen/nbt/NBTStructure.java | 57 +- src/main/resources/assets/hbm/lang/en_US.lang | 2 + .../textures/blocks/wand_structure_load.png | Bin 0 -> 289 bytes .../textures/blocks/wand_structure_save.png | Bin 0 -> 285 bytes 14 files changed, 951 insertions(+), 117 deletions(-) create mode 100644 src/main/java/com/hbm/blocks/generic/BlockWandStructure.java create mode 100644 src/main/java/com/hbm/inventory/gui/element/GuiFileList.java create mode 100644 src/main/java/com/hbm/render/tileentity/RenderWandStructure.java create mode 100644 src/main/resources/assets/hbm/textures/blocks/wand_structure_load.png create mode 100644 src/main/resources/assets/hbm/textures/blocks/wand_structure_save.png diff --git a/src/main/java/com/hbm/blocks/ModBlocks.java b/src/main/java/com/hbm/blocks/ModBlocks.java index 55b3c4ad3..b5d2d72b3 100644 --- a/src/main/java/com/hbm/blocks/ModBlocks.java +++ b/src/main/java/com/hbm/blocks/ModBlocks.java @@ -1263,6 +1263,7 @@ public class ModBlocks { public static Block wand_jigsaw; public static Block wand_logic; public static Block wand_tandem; + public static Block wand_structure; public static Block logic_block; @@ -2070,7 +2071,7 @@ public class ModBlocks { fusion_boiler = new MachineFusionBoiler().setBlockName("fusion_boiler").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":block_steel"); fusion_mhdt = new MachineFusionMHDT().setBlockName("fusion_mhdt").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":block_steel"); fusion_coupler = new MachineFusionCoupler().setBlockName("fusion_coupler").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":block_steel"); - + machine_icf_press = new MachineICFPress().setBlockName("machine_icf_press").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":block_steel"); icf = new MachineICF().setBlockName("icf").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":block_steel"); icf_component = new BlockICFComponent().setBlockName("icf_component").setHardness(5.0F).setResistance(60.0F).setCreativeTab(MainRegistry.machineTab).setBlockTextureName(RefStrings.MODID + ":icf_component"); @@ -2434,6 +2435,7 @@ public class ModBlocks { wand_jigsaw = new BlockWandJigsaw().setBlockName("wand_jigsaw").setBlockTextureName(RefStrings.MODID + ":wand_jigsaw"); wand_logic = new BlockWandLogic().setBlockName("wand_logic").setBlockTextureName(RefStrings.MODID + ":wand_logic"); wand_tandem = new BlockWandTandem().setBlockName("wand_tandem").setBlockTextureName(RefStrings.MODID + ":wand_tandem"); + wand_structure = new BlockWandStructure().setBlockName("wand_structure"); logic_block = new LogicBlock().setBlockName("logic_block").setBlockTextureName(RefStrings.MODID + ":logic_block"); @@ -3454,7 +3456,7 @@ public class ModBlocks { GameRegistry.registerBlock(plasma, ItemBlockLore.class, plasma.getUnlocalizedName()); GameRegistry.registerBlock(iter, iter.getUnlocalizedName()); GameRegistry.registerBlock(plasma_heater, plasma_heater.getUnlocalizedName()); - + register(fusion_component); register(fusion_torus); register(fusion_klystron); @@ -3609,6 +3611,7 @@ public class ModBlocks { register(wand_jigsaw); register(wand_logic); register(wand_tandem); + register(wand_structure); register(logic_block); } @@ -3641,4 +3644,24 @@ public class ModBlocks { return ret; } + + public static Block getBlockFromStack(ItemStack stack) { + if(stack == null) return null; + if(!(stack.getItem() instanceof ItemBlock)) return null; + + return ((ItemBlock) stack.getItem()).field_150939_a; + } + + // Is this block a special structure handling block, so we can ignore it for blacklist selection, etc. + public static boolean isStructureBlock(Block block, boolean includeAir) { + if(block == null) return false; + if(block == wand_air) return includeAir; + if(block == wand_structure) return true; + if(block == wand_jigsaw) return true; + if(block == wand_logic) return true; + if(block == wand_tandem) return true; + if(block == wand_loot) return true; + return false; + } + } diff --git a/src/main/java/com/hbm/blocks/generic/BlockWandJigsaw.java b/src/main/java/com/hbm/blocks/generic/BlockWandJigsaw.java index d64470934..2c927fac1 100644 --- a/src/main/java/com/hbm/blocks/generic/BlockWandJigsaw.java +++ b/src/main/java/com/hbm/blocks/generic/BlockWandJigsaw.java @@ -37,7 +37,6 @@ import net.minecraft.entity.EntityLivingBase; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.init.Blocks; import net.minecraft.inventory.Container; -import net.minecraft.item.ItemBlock; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.tileentity.TileEntity; @@ -135,10 +134,10 @@ public class BlockWandJigsaw extends BlockContainer implements IBlockSideRotatio TileEntityWandJigsaw jigsaw = (TileEntityWandJigsaw) te; if(!player.isSneaking()) { - Block block = getBlock(world, player.getHeldItem()); + Block block = ModBlocks.getBlockFromStack(player.getHeldItem()); if(block == ModBlocks.wand_air) block = Blocks.air; - if(block != null && block != ModBlocks.wand_jigsaw && block != ModBlocks.wand_loot) { + if(block != null && !ModBlocks.isStructureBlock(block, false)) { jigsaw.replaceBlock = block; jigsaw.replaceMeta = player.getHeldItem().getItemDamage(); @@ -155,13 +154,6 @@ public class BlockWandJigsaw extends BlockContainer implements IBlockSideRotatio return false; } - private Block getBlock(World world, ItemStack stack) { - if(stack == null) return null; - if(!(stack.getItem() instanceof ItemBlock)) return null; - - return ((ItemBlock) stack.getItem()).field_150939_a; - } - @Override @SideOnly(Side.CLIENT) public Object provideGUI(int ID, EntityPlayer player, World world, int x, int y, int z) { diff --git a/src/main/java/com/hbm/blocks/generic/BlockWandLoot.java b/src/main/java/com/hbm/blocks/generic/BlockWandLoot.java index cf5cebce0..715da81a5 100644 --- a/src/main/java/com/hbm/blocks/generic/BlockWandLoot.java +++ b/src/main/java/com/hbm/blocks/generic/BlockWandLoot.java @@ -33,7 +33,6 @@ import net.minecraft.client.renderer.texture.IIconRegister; import net.minecraft.entity.EntityLivingBase; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.inventory.IInventory; -import net.minecraft.item.ItemBlock; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.tileentity.TileEntity; @@ -82,7 +81,7 @@ public class BlockWandLoot extends BlockContainer implements ILookOverlay, ITool @Override public void onBlockPlacedBy(World world, int x, int y, int z, EntityLivingBase player, ItemStack itemStack) { - int i = MathHelper.floor_double(player.rotationYaw * 4.0F / 360.0F + 0.5D) & 3; + int i = MathHelper.floor_double(player.rotationYaw * 4.0F / 360.0F + 0.5D) & 3; if(i == 0) world.setBlockMetadataWithNotify(x, y, z, 3, 2); if(i == 1) world.setBlockMetadataWithNotify(x, y, z, 2, 2); @@ -153,17 +152,14 @@ public class BlockWandLoot extends BlockContainer implements ILookOverlay, ITool } private Block getLootableBlock(World world, ItemStack stack) { - if(stack == null) return null; + Block block = ModBlocks.getBlockFromStack(stack); + if(block == null) return null; - if(stack.getItem() instanceof ItemBlock) { - Block block = ((ItemBlock) stack.getItem()).field_150939_a; + if(block == ModBlocks.deco_loot) return block; - if(block == ModBlocks.deco_loot) return block; - - if(block instanceof ITileEntityProvider) { - TileEntity te = ((ITileEntityProvider) block).createNewTileEntity(world, 12); - if(te instanceof IInventory) return block; - } + if(block instanceof ITileEntityProvider) { + TileEntity te = ((ITileEntityProvider) block).createNewTileEntity(world, 12); + if(te instanceof IInventory) return block; } return null; diff --git a/src/main/java/com/hbm/blocks/generic/BlockWandStructure.java b/src/main/java/com/hbm/blocks/generic/BlockWandStructure.java new file mode 100644 index 000000000..07d68da44 --- /dev/null +++ b/src/main/java/com/hbm/blocks/generic/BlockWandStructure.java @@ -0,0 +1,573 @@ +package com.hbm.blocks.generic; + +import java.io.File; +import java.io.FileFilter; +import java.io.FileNotFoundException; +import java.util.ArrayList; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +import org.lwjgl.input.Keyboard; + +import com.hbm.blocks.IBlockMulti; +import com.hbm.blocks.ILookOverlay; +import com.hbm.blocks.ModBlocks; +import com.hbm.config.StructureConfig; +import com.hbm.interfaces.IControlReceiver; +import com.hbm.inventory.gui.element.GuiFileList; +import com.hbm.lib.RefStrings; +import com.hbm.main.MainRegistry; +import com.hbm.packet.PacketDispatcher; +import com.hbm.packet.toserver.NBTControlPacket; +import com.hbm.tileentity.IGUIProvider; +import com.hbm.tileentity.TileEntityLoadedBase; +import com.hbm.util.BufferUtil; +import com.hbm.util.Tuple.Pair; +import com.hbm.util.i18n.I18nUtil; +import com.hbm.world.gen.nbt.NBTStructure; + +import cpw.mods.fml.common.network.internal.FMLNetworkHandler; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; +import io.netty.buffer.ByteBuf; +import net.minecraft.block.Block; +import net.minecraft.block.BlockContainer; +import net.minecraft.block.material.Material; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.client.gui.GuiTextField; +import net.minecraft.client.renderer.texture.IIconRegister; +import net.minecraft.creativetab.CreativeTabs; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.event.ClickEvent; +import net.minecraft.init.Blocks; +import net.minecraft.inventory.Container; +import net.minecraft.item.Item; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.tileentity.TileEntity; +import net.minecraft.util.AxisAlignedBB; +import net.minecraft.util.ChatComponentText; +import net.minecraft.util.EnumChatFormatting; +import net.minecraft.util.IIcon; +import net.minecraft.world.World; +import net.minecraftforge.client.event.RenderGameOverlayEvent.Pre; + +public class BlockWandStructure extends BlockContainer implements IBlockMulti, IGUIProvider, ILookOverlay { + + private IIcon saveIcon; + private IIcon loadIcon; + + public BlockWandStructure() { + super(Material.iron); + } + + @Override + public TileEntity createNewTileEntity(World worldIn, int meta) { + return new TileEntityWandStructure(); + } + + @Override + @SideOnly(Side.CLIENT) + public void registerBlockIcons(IIconRegister iconRegister) { + saveIcon = iconRegister.registerIcon(RefStrings.MODID + ":wand_structure_save"); + loadIcon = iconRegister.registerIcon(RefStrings.MODID + ":wand_structure_load"); + } + + @Override + public IIcon getIcon(int side, int meta) { + if(meta == 1) return loadIcon; + return saveIcon; + } + + @Override + public boolean onBlockActivated(World world, int x, int y, int z, EntityPlayer player, int side, float hitX, float hitY, float hitZ) { + TileEntity te = world.getTileEntity(x, y, z); + + if(!(te instanceof TileEntityWandStructure)) return false; + + TileEntityWandStructure structure = (TileEntityWandStructure) te; + + if(!player.isSneaking()) { + Block block = ModBlocks.getBlockFromStack(player.getHeldItem()); + if(block != null && !ModBlocks.isStructureBlock(block, true)) { + Pair bm = new Pair(block, player.getHeldItem().getItemDamage()); + + if(structure.blacklist.contains(bm)) { + structure.blacklist.remove(bm); + } else { + structure.blacklist.add(bm); + } + + return true; + } + + if(world.isRemote) FMLNetworkHandler.openGui(player, MainRegistry.instance, 0, world, x, y, z); + + return true; + } + + return false; + } + + @SuppressWarnings({ "unchecked", "rawtypes" }) + @Override + @SideOnly(Side.CLIENT) + public void getSubBlocks(Item itemIn, CreativeTabs tab, List list) { + list.add(new ItemStack(itemIn, 1, 0)); + list.add(new ItemStack(itemIn, 1, 1)); + } + + @Override + public int getSubCount() { + return 2; + } + + @Override + public String getUnlocalizedName(ItemStack stack) { + int meta = stack.getItemDamage(); + if(meta == 1) return getUnlocalizedName() + ".load"; + return getUnlocalizedName() + ".save"; + } + + @Override + public int damageDropped(int meta) { + return meta; + } + + @Override + public Container provideContainer(int ID, EntityPlayer player, World world, int x, int y, int z) { + return null; + } + + @Override + public Object provideGUI(int ID, EntityPlayer player, World world, int x, int y, int z) { + int meta = world.getBlockMetadata(x, y, z); + TileEntityWandStructure structure = (TileEntityWandStructure) world.getTileEntity(x, y, z); + if(meta == 1) return new GuiStructureLoad(structure); + return new GuiStructureSave(structure); + } + + @Override + public void printHook(Pre event, World world, int x, int y, int z) { + if(world.getBlockMetadata(x, y, z) != 0) return; + + TileEntity te = world.getTileEntity(x, y, z); + if(!(te instanceof TileEntityWandStructure)) return; + TileEntityWandStructure structure = (TileEntityWandStructure) te; + + List text = new ArrayList(); + + text.add(EnumChatFormatting.GRAY + "Name: " + EnumChatFormatting.RESET + structure.name); + + text.add(EnumChatFormatting.GRAY + "Blacklist:"); + for (Pair bm : structure.blacklist) { + text.add(EnumChatFormatting.RED + "- " + bm.getKey().getUnlocalizedName() + " : " + bm.getValue()); + } + + ILookOverlay.printGeneric(event, I18nUtil.resolveKey(getUnlocalizedName() + ".save.name"), 0xffff00, 0x404000, text); + } + + public static class TileEntityWandStructure extends TileEntityLoadedBase implements IControlReceiver { + + public String name = ""; + + public int sizeX = 1; + public int sizeY = 1; + public int sizeZ = 1; + + public Set> blacklist = new HashSet<>(); + + @Override + public void updateEntity() { + if(!worldObj.isRemote) { + networkPackNT(256); + } + } + + public void saveStructure(EntityPlayer player) { + if(name.isEmpty()) { + player.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Could not save: invalid name")); + return; + } + + if(sizeX <= 0 || sizeY <= 0 || sizeZ <= 0) { + player.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Could not save: invalid dimensions")); + return; + } + + Pair air = new Pair(Blocks.air, 0); + blacklist.add(air); + + File file = NBTStructure.quickSaveArea(name + ".nbt", worldObj, xCoord, yCoord + 1, zCoord, xCoord + sizeX - 1, yCoord + sizeY, zCoord + sizeZ - 1, blacklist); + + blacklist.remove(air); + + if(file == null) { + player.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Failed to save structure")); + return; + } + + ChatComponentText fileText = new ChatComponentText(file.getName()); + fileText.getChatStyle().setChatClickEvent(new ClickEvent(ClickEvent.Action.OPEN_FILE, file.getParentFile().getAbsolutePath())); + fileText.getChatStyle().setUnderlined(true); + + player.addChatMessage(new ChatComponentText("Saved structure as ").appendSibling(fileText)); + } + + public void loadStructure(EntityPlayer player) { + if(name.isEmpty()) { + player.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Could not load: no filename specified")); + return; + } + + File structureDirectory = new File(Minecraft.getMinecraft().mcDataDir, "structures"); + structureDirectory.mkdir(); + + File structureFile = new File(structureDirectory, name + ".nbt"); + + boolean previousDebug = StructureConfig.debugStructures; + StructureConfig.debugStructures = true; + + try { + NBTStructure structure = new NBTStructure(structureFile); + + sizeX = structure.getSizeX(); + sizeY = structure.getSizeY(); + sizeZ = structure.getSizeZ(); + + structure.build(worldObj, xCoord, yCoord + 1, zCoord, 0, false, true); + + worldObj.setBlockMetadataWithNotify(xCoord, yCoord, zCoord, 0, 3); + + player.addChatMessage(new ChatComponentText("Structure loaded")); + + } catch (FileNotFoundException ex) { + player.addChatMessage(new ChatComponentText(EnumChatFormatting.RED + "Could not load: file not found")); + } finally { + StructureConfig.debugStructures = previousDebug; + } + } + + @Override + public void serialize(ByteBuf buf) { + BufferUtil.writeString(buf, name); + + buf.writeInt(sizeX); + buf.writeInt(sizeY); + buf.writeInt(sizeZ); + + buf.writeInt(blacklist.size()); + for(Pair bm : blacklist) { + buf.writeInt(Block.getIdFromBlock(bm.getKey())); + buf.writeInt(bm.getValue()); + } + } + + @Override + public void deserialize(ByteBuf buf) { + name = BufferUtil.readString(buf); + + sizeX = buf.readInt(); + sizeY = buf.readInt(); + sizeZ = buf.readInt(); + + int count = buf.readInt(); + blacklist = new HashSet<>(); + for(int i = 0; i < count; i++) { + Block block = Block.getBlockById(buf.readInt()); + int meta = buf.readInt(); + blacklist.add(new Pair(block, meta)); + } + } + + @Override + public void readFromNBT(NBTTagCompound nbt) { + super.readFromNBT(nbt); + + name = nbt.getString("name"); + + sizeX = nbt.getInteger("sizeX"); + sizeY = nbt.getInteger("sizeY"); + sizeZ = nbt.getInteger("sizeZ"); + + int[] blocks = nbt.getIntArray("blocks"); + int[] metas = nbt.getIntArray("metas"); + + blacklist = new HashSet<>(); + for (int i = 0; i < blocks.length; i++) { + blacklist.add(new Pair(Block.getBlockById(blocks[i]), metas[i])); + } + } + + @Override + public void writeToNBT(NBTTagCompound nbt) { + super.writeToNBT(nbt); + + nbt.setString("name", name); + + nbt.setInteger("sizeX", sizeX); + nbt.setInteger("sizeY", sizeY); + nbt.setInteger("sizeZ", sizeZ); + + nbt.setIntArray("blocks", blacklist.stream().mapToInt(b -> Block.getIdFromBlock(b.getKey())).toArray()); + nbt.setIntArray("metas", blacklist.stream().mapToInt(b -> b.getValue()).toArray()); + } + + @Override + public boolean hasPermission(EntityPlayer player) { + return true; + } + + public void receiveControl(NBTTagCompound data) {} + + @Override + public void receiveControl(EntityPlayer player, NBTTagCompound nbt) { + readFromNBT(nbt); + markDirty(); + + if(nbt.getBoolean("save")) { + saveStructure(player); + } + + if(nbt.getBoolean("load")) { + loadStructure(player); + } + } + + @Override + @SideOnly(Side.CLIENT) + public AxisAlignedBB getRenderBoundingBox() { + return INFINITE_EXTENT_AABB; + } + + @Override + @SideOnly(Side.CLIENT) + public double getMaxRenderDistanceSquared() { + return 65536.0D; + } + + } + + @SideOnly(Side.CLIENT) + public static class GuiStructureSave extends GuiScreen { + + private final TileEntityWandStructure tile; + + private GuiTextField textName; + + private GuiTextField textSizeX; + private GuiTextField textSizeY; + private GuiTextField textSizeZ; + + private GuiButton performAction; + + private boolean saveOnClose = false; + + public GuiStructureSave(TileEntityWandStructure tile) { + this.tile = tile; + } + + @Override + public void initGui() { + Keyboard.enableRepeatEvents(true); + + textName = new GuiTextField(fontRendererObj, width / 2 - 150, 50, 300, 20); + textName.setText(tile.name); + + textSizeX = new GuiTextField(fontRendererObj, width / 2 - 150, 100, 50, 20); + textSizeX.setText("" + tile.sizeX); + textSizeY = new GuiTextField(fontRendererObj, width / 2 - 100, 100, 50, 20); + textSizeY.setText("" + tile.sizeY); + textSizeZ = new GuiTextField(fontRendererObj, width / 2 - 50, 100, 50, 20); + textSizeZ.setText("" + tile.sizeZ); + + performAction = new GuiButton(0, width / 2 - 150, 150, 300, 20, "SAVE"); + } + + @Override + public void drawScreen(int mouseX, int mouseY, float partialTicks) { + drawDefaultBackground(); + + textName.drawTextBox(); + + textSizeX.drawTextBox(); + textSizeY.drawTextBox(); + textSizeZ.drawTextBox(); + + performAction.drawButton(mc, mouseX, mouseY); + + super.drawScreen(mouseX, mouseY, partialTicks); + } + + @Override + public void onGuiClosed() { + Keyboard.enableRepeatEvents(false); + + NBTTagCompound data = new NBTTagCompound(); + tile.writeToNBT(data); + + data.setString("name", textName.getText()); + + try { data.setInteger("sizeX", Integer.parseInt(textSizeX.getText())); } catch (Exception ex) {} + try { data.setInteger("sizeY", Integer.parseInt(textSizeY.getText())); } catch (Exception ex) {} + try { data.setInteger("sizeZ", Integer.parseInt(textSizeZ.getText())); } catch (Exception ex) {} + + if(saveOnClose) data.setBoolean("save", true); + + PacketDispatcher.wrapper.sendToServer(new NBTControlPacket(data, tile.xCoord, tile.yCoord, tile.zCoord)); + } + + @Override + protected void keyTyped(char typedChar, int keyCode) { + super.keyTyped(typedChar, keyCode); + + textName.textboxKeyTyped(typedChar, keyCode); + + textSizeX.textboxKeyTyped(typedChar, keyCode); + textSizeY.textboxKeyTyped(typedChar, keyCode); + textSizeZ.textboxKeyTyped(typedChar, keyCode); + } + + @Override + protected void mouseClicked(int mouseX, int mouseY, int mouseButton) { + super.mouseClicked(mouseX, mouseY, mouseButton); + textName.mouseClicked(mouseX, mouseY, mouseButton); + + textSizeX.mouseClicked(mouseX, mouseY, mouseButton); + textSizeY.mouseClicked(mouseX, mouseY, mouseButton); + textSizeZ.mouseClicked(mouseX, mouseY, mouseButton); + + if(performAction.mousePressed(mc, mouseX, mouseY)) { + saveOnClose = true; + + mc.displayGuiScreen(null); + mc.setIngameFocus(); + } + } + + @Override + public boolean doesGuiPauseGame() { + return false; + } + + } + + @SideOnly(Side.CLIENT) + public static class GuiStructureLoad extends GuiScreen { + + private final TileEntityWandStructure tile; + + private GuiTextField textName; + + private GuiFileList fileList; + + private GuiButton performAction; + + private boolean loadOnClose = false; + + private static File structureDirectory = new File(Minecraft.getMinecraft().mcDataDir, "structures"); + private static String nameFilter = ""; + private static final FileFilter structureFilter = new FileFilter() { + + public boolean accept(File file) { + if(!file.isFile() || !file.getName().endsWith(".nbt")) return false; + return nameFilter.isEmpty() || file.getName().contains(nameFilter); + } + + }; + + public GuiStructureLoad(TileEntityWandStructure tile) { + this.tile = tile; + } + + @Override + public void initGui() { + Keyboard.enableRepeatEvents(true); + + textName = new GuiTextField(fontRendererObj, width / 2 - 150, 50, 300, 20); + textName.setText(tile.name); + nameFilter = tile.name; + + structureDirectory.mkdir(); + + fileList = new GuiFileList(mc, structureDirectory.listFiles(structureFilter), this::selectFile, nameFilter, width, height, 70, height - 90, 16); + + performAction = new GuiButton(0, width / 2 - 150, height - 70, 300, 20, "LOAD"); + } + + public void selectFile(File file) { + String fileName = file.getName(); + textName.setText(fileName.substring(0, fileName.length() - 4)); + } + + @Override + public void drawScreen(int mouseX, int mouseY, float partialTicks) { + fileList.drawScreen(mouseX, mouseY, partialTicks); + + textName.drawTextBox(); + + performAction.drawButton(mc, mouseX, mouseY); + + super.drawScreen(mouseX, mouseY, partialTicks); + } + + @Override + public void onGuiClosed() { + Keyboard.enableRepeatEvents(false); + + NBTTagCompound data = new NBTTagCompound(); + tile.writeToNBT(data); + + data.setString("name", textName.getText()); + + if(loadOnClose) data.setBoolean("load", true); + + PacketDispatcher.wrapper.sendToServer(new NBTControlPacket(data, tile.xCoord, tile.yCoord, tile.zCoord)); + } + + @Override + protected void keyTyped(char typedChar, int keyCode) { + super.keyTyped(typedChar, keyCode); + + textName.textboxKeyTyped(typedChar, keyCode); + + if(!nameFilter.equals(textName.getText())) { + nameFilter = textName.getText(); + fileList = new GuiFileList(mc, structureDirectory.listFiles(structureFilter), this::selectFile, nameFilter, width, height, 70, height - 90, 16); + } + } + + @Override + protected void mouseClicked(int mouseX, int mouseY, int mouseButton) { + super.mouseClicked(mouseX, mouseY, mouseButton); + textName.mouseClicked(mouseX, mouseY, mouseButton); + + fileList.func_148179_a(mouseX, mouseY, mouseButton); + + fileList.select(textName.getText()); + + if(performAction.mousePressed(mc, mouseX, mouseY)) { + loadOnClose = true; + + mc.displayGuiScreen(null); + mc.setIngameFocus(); + } + } + + @Override + protected void mouseMovedOrUp(int mouseX, int mouseY, int state) { + super.mouseMovedOrUp(mouseX, mouseY, state); + fileList.func_148181_b(mouseX, mouseY, state); + } + + @Override + public boolean doesGuiPauseGame() { + return false; + } + + } + +} diff --git a/src/main/java/com/hbm/blocks/generic/BlockWandTandem.java b/src/main/java/com/hbm/blocks/generic/BlockWandTandem.java index 1ad176e63..2a9342454 100644 --- a/src/main/java/com/hbm/blocks/generic/BlockWandTandem.java +++ b/src/main/java/com/hbm/blocks/generic/BlockWandTandem.java @@ -44,7 +44,6 @@ import net.minecraft.entity.player.EntityPlayer; import net.minecraft.init.Blocks; import net.minecraft.init.Items; import net.minecraft.inventory.Container; -import net.minecraft.item.ItemBlock; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.tileentity.TileEntity; @@ -175,10 +174,10 @@ public class BlockWandTandem extends BlockContainer implements IBlockSideRotatio } if(!player.isSneaking()) { - Block block = getBlock(world, player.getHeldItem()); + Block block = ModBlocks.getBlockFromStack(player.getHeldItem()); if(block == ModBlocks.wand_air) block = Blocks.air; - if(block != null && block != ModBlocks.wand_jigsaw && block != ModBlocks.wand_loot) { + if(block != null && !ModBlocks.isStructureBlock(block, false)) { jigsaw.replaceBlock = block; jigsaw.replaceMeta = player.getHeldItem().getItemDamage(); jigsaw.markDirty(); @@ -196,13 +195,6 @@ public class BlockWandTandem extends BlockContainer implements IBlockSideRotatio return false; } - private Block getBlock(World world, ItemStack stack) { - if(stack == null) return null; - if(!(stack.getItem() instanceof ItemBlock)) return null; - - return ((ItemBlock) stack.getItem()).field_150939_a; - } - @Override @SideOnly(Side.CLIENT) public Object provideGUI(int ID, EntityPlayer player, World world, int x, int y, int z) { diff --git a/src/main/java/com/hbm/inventory/gui/element/GuiFileList.java b/src/main/java/com/hbm/inventory/gui/element/GuiFileList.java new file mode 100644 index 000000000..63364f3d4 --- /dev/null +++ b/src/main/java/com/hbm/inventory/gui/element/GuiFileList.java @@ -0,0 +1,99 @@ +package com.hbm.inventory.gui.element; + +import java.io.File; +import java.util.ArrayList; +import java.util.List; +import java.util.function.Consumer; + +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.GuiListExtended; +import net.minecraft.client.renderer.Tessellator; + +@SideOnly(Side.CLIENT) +public class GuiFileList extends GuiListExtended { + + private List rows = new ArrayList<>(); + private int selectedId = -1; + + public GuiFileList(Minecraft mc, File[] files, Consumer onSelect, String nameFilter, int width, int height, int top, int bottom, int slotHeight) { + super(mc, width, height, top, bottom, slotHeight); + + for(File file : files) { + if(file.getName().equals(nameFilter + ".nbt")) { + selectedId = rows.size(); + } + rows.add(new Row(file, onSelect, width, slotHeight)); + } + } + + @Override + public IGuiListEntry getListEntry(int id) { + return rows.get(id); + } + + @Override + protected int getSize() { + return rows.size(); + } + + @Override + protected boolean isSelected(int id) { + return id == selectedId; + } + + public void select(String nameFilter) { + for(int i = 0; i < rows.size(); i++) { + Row row = rows.get(i); + if(row.file.getName().equals(nameFilter + ".nbt")) { + selectedId = i; + return; + } + } + } + + @SideOnly(Side.CLIENT) + public static class Row implements IGuiListEntry { + + private final Minecraft mc; + private final File file; + + private final int width; + private final int height; + + private final Consumer onSelect; + + public Row(File file, Consumer onSelect, int width, int height) { + this.mc = Minecraft.getMinecraft(); + this.file = file; + + this.width = width; + this.height = height; + + this.onSelect = onSelect; + } + + @Override + public void drawEntry(int id, int x, int y, int width, int height, Tessellator tess, int mouseX, int mouseY, boolean isVisible) { + mc.fontRenderer.drawString(file.getName(), x + 20, y + 1, 0xFFFFFF); + } + + @Override + public boolean mousePressed(int id, int mouseX, int mouseY, int button, int hoverX, int hoverY) { + if(hoverX < 0 || hoverX > width) return false; + if(hoverY < 0 || hoverY > height) return false; + + onSelect.accept(file); + + return true; + } + + @Override + public void mouseReleased(int id, int mouseX, int mouseY, int button, int hoverX, int hoverY) { + + } + + } + +} diff --git a/src/main/java/com/hbm/items/tool/ItemWandS.java b/src/main/java/com/hbm/items/tool/ItemWandS.java index 55de41e9a..0a98cde19 100644 --- a/src/main/java/com/hbm/items/tool/ItemWandS.java +++ b/src/main/java/com/hbm/items/tool/ItemWandS.java @@ -1,6 +1,5 @@ package com.hbm.items.tool; -import java.util.Date; import java.util.HashSet; import java.util.List; import java.util.Set; @@ -8,23 +7,23 @@ import java.text.DateFormat; import java.text.SimpleDateFormat; import com.hbm.blocks.ModBlocks; +import com.hbm.blocks.generic.BlockWandStructure.TileEntityWandStructure; import com.hbm.util.BobMathUtil; import com.hbm.util.Tuple.Pair; -import com.hbm.world.gen.nbt.NBTStructure; import net.minecraft.block.Block; import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.init.Blocks; import net.minecraft.item.Item; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.tileentity.TileEntity; import net.minecraft.util.ChatComponentText; import net.minecraft.util.EnumChatFormatting; import net.minecraft.world.World; public class ItemWandS extends Item { - private static final DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd_HH.mm.ss"); + private static final DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd_HH.mm.ss"); @Override public void addInformation(ItemStack stack, EntityPlayer player, List list, boolean bool) { @@ -34,106 +33,124 @@ public class ItemWandS extends Item { list.add("adds a block to the blacklist by crouch right-clicking!)"); if(stack.stackTagCompound != null) { - int px = stack.stackTagCompound.getInteger("x"); - int py = stack.stackTagCompound.getInteger("y"); - int pz = stack.stackTagCompound.getInteger("z"); + int px = stack.stackTagCompound.getInteger("x"); + int py = stack.stackTagCompound.getInteger("y"); + int pz = stack.stackTagCompound.getInteger("z"); if(px != 0 || py != 0 || pz != 0) { - list.add(EnumChatFormatting.AQUA + "From: " + px + ", " + py + ", " + pz); - } else { - list.add(EnumChatFormatting.AQUA + "No start position set"); - } + list.add(EnumChatFormatting.AQUA + "From: " + px + ", " + py + ", " + pz); + } else { + list.add(EnumChatFormatting.AQUA + "No start position set"); + } - Set> blocks = getBlocks(stack); + Set> blocks = getBlocks(stack); - if(blocks.size() > 0) { - list.add("Blacklist:"); - for(Pair block : blocks) { - list.add(EnumChatFormatting.RED + "- " + block.key.getUnlocalizedName()); - } - } - } + if(blocks.size() > 0) { + list.add("Blacklist:"); + for(Pair block : blocks) { + list.add(EnumChatFormatting.RED + "- " + block.key.getUnlocalizedName()); + } + } + } } - // why the fuck ye'd leave this whole thing obfuscated is beyond me - @Override - public boolean onItemUse(ItemStack stack, EntityPlayer player, World world, int x, int y, int z, int side, float fx, float fy, float fz) { + // why the fuck ye'd leave this whole thing obfuscated is beyond me + @Override + public boolean onItemUse(ItemStack stack, EntityPlayer player, World world, int x, int y, int z, int side, float fx, float fy, float fz) { if(stack.stackTagCompound == null) { stack.stackTagCompound = new NBTTagCompound(); } if(player.isSneaking()) { - Pair target = new Pair(world.getBlock(x, y, z), world.getBlockMetadata(x, y, z)); - Set> blocks = getBlocks(stack); + Pair target = new Pair(world.getBlock(x, y, z), world.getBlockMetadata(x, y, z)); + Set> blocks = getBlocks(stack); - if(blocks.contains(target)) { - blocks.remove(target); - if(world.isRemote) player.addChatMessage(new ChatComponentText("Removed from blacklist " + target.key.getUnlocalizedName())); - } else { - blocks.add(target); - if(world.isRemote) player.addChatMessage(new ChatComponentText("Added to blacklist " + target.key.getUnlocalizedName())); - } + if(blocks.contains(target)) { + blocks.remove(target); + if(world.isRemote) player.addChatMessage(new ChatComponentText("Removed from blacklist " + target.key.getUnlocalizedName())); + } else { + blocks.add(target); + if(world.isRemote) player.addChatMessage(new ChatComponentText("Added to blacklist " + target.key.getUnlocalizedName())); + } - setBlocks(stack, blocks); + setBlocks(stack, blocks); } else { - int px = stack.stackTagCompound.getInteger("x"); - int py = stack.stackTagCompound.getInteger("y"); - int pz = stack.stackTagCompound.getInteger("z"); + int px = stack.stackTagCompound.getInteger("x"); + int py = stack.stackTagCompound.getInteger("y"); + int pz = stack.stackTagCompound.getInteger("z"); if(px == 0 && py == 0 && pz == 0) { - setPosition(stack, x, y, z); + setPosition(stack, x, y, z); if(world.isRemote) player.addChatMessage(new ChatComponentText("First position set!")); } else { - setPosition(stack, 0, 0, 0); + setPosition(stack, 0, 0, 0); - Set> blocks = getBlocks(stack); - blocks.add(new Pair(Blocks.air, 0)); - blocks.add(new Pair(ModBlocks.spotlight_beam, 0)); + int minX = Math.min(x, px); + int minY = Math.min(y, py) - 1; + int minZ = Math.min(z, pz); - String filename = "structure_" + dateFormat.format(new Date()).toString() + ".nbt"; + int sizeX = Math.abs(x - px) + 1; + int sizeY = Math.abs(y - py) + 1; + int sizeZ = Math.abs(z - pz) + 1; - NBTStructure.saveArea(filename, world, x, y, z, px, py, pz, blocks); + world.setBlock(minX, minY, minZ, ModBlocks.wand_structure); - if(world.isRemote) player.addChatMessage(new ChatComponentText("Structure saved to: .minecraft/structures/" + filename)); + TileEntity te = world.getTileEntity(minX, minY, minZ); + if (te instanceof TileEntityWandStructure) { + TileEntityWandStructure structure = (TileEntityWandStructure) te; + + structure.sizeX = sizeX; + structure.sizeY = sizeY; + structure.sizeZ = sizeZ; + + structure.blacklist = getBlocks(stack); + } else { + if (world.isRemote) + player.addChatMessage(new ChatComponentText("Could not add a structure block!")); + return true; + } + + if (world.isRemote) + player.addChatMessage(new ChatComponentText("Structure block configured and added at: " + minX + ", " + minY + ", " + minZ)); } } - return true; - } + return true; + } - private void setPosition(ItemStack stack, int x, int y, int z) { - stack.stackTagCompound.setInteger("x", x); - stack.stackTagCompound.setInteger("y", y); - stack.stackTagCompound.setInteger("z", z); - } + private void setPosition(ItemStack stack, int x, int y, int z) { + stack.stackTagCompound.setInteger("x", x); + stack.stackTagCompound.setInteger("y", y); + stack.stackTagCompound.setInteger("z", z); + } - private Set> getBlocks(ItemStack stack) { - if(stack.stackTagCompound == null) { - return new HashSet<>(); - } + private Set> getBlocks(ItemStack stack) { + if(stack.stackTagCompound == null) { + return new HashSet<>(); + } - int[] blockIds = stack.stackTagCompound.getIntArray("blocks"); - int[] metas = stack.stackTagCompound.getIntArray("metas"); - Set> blocks = new HashSet<>(blockIds.length); + int[] blockIds = stack.stackTagCompound.getIntArray("blocks"); + int[] metas = stack.stackTagCompound.getIntArray("metas"); + Set> blocks = new HashSet<>(blockIds.length); - for(int i = 0; i < blockIds.length; i++) { - blocks.add(new Pair(Block.getBlockById(blockIds[i]), metas[i])); - } + for(int i = 0; i < blockIds.length; i++) { + blocks.add(new Pair(Block.getBlockById(blockIds[i]), metas[i])); + } - return blocks; - } + return blocks; + } @SuppressWarnings("unchecked") - private void setBlocks(ItemStack stack, Set> blocks) { - if(stack.stackTagCompound == null) { - stack.stackTagCompound = new NBTTagCompound(); - } + private void setBlocks(ItemStack stack, Set> blocks) { + if(stack.stackTagCompound == null) { + stack.stackTagCompound = new NBTTagCompound(); + } - stack.stackTagCompound.setIntArray("blocks", BobMathUtil.collectionToIntArray(blocks, i -> Block.getIdFromBlock(((Pair)i).getKey()))); - stack.stackTagCompound.setIntArray("metas", BobMathUtil.collectionToIntArray(blocks, i -> ((Pair)i).getValue())); - } + stack.stackTagCompound.setIntArray("blocks", BobMathUtil.collectionToIntArray(blocks, i -> Block.getIdFromBlock(((Pair)i).getKey()))); + stack.stackTagCompound.setIntArray("metas", BobMathUtil.collectionToIntArray(blocks, i -> ((Pair)i).getValue())); + } @Override public ItemStack onItemRightClick(ItemStack stack, World world, EntityPlayer player) { @@ -147,7 +164,7 @@ public class ItemWandS extends Item { if(world.isRemote) { player.addChatMessage(new ChatComponentText("Cleared blacklist")); - } + } } return stack; diff --git a/src/main/java/com/hbm/main/ClientProxy.java b/src/main/java/com/hbm/main/ClientProxy.java index e662f64e4..ce7765cbf 100644 --- a/src/main/java/com/hbm/main/ClientProxy.java +++ b/src/main/java/com/hbm/main/ClientProxy.java @@ -8,6 +8,7 @@ import com.hbm.blocks.generic.BlockPedestal.TileEntityPedestal; import com.hbm.blocks.generic.BlockPlushie.TileEntityPlushie; import com.hbm.blocks.generic.BlockSkeletonHolder.TileEntitySkeletonHolder; import com.hbm.blocks.generic.BlockSnowglobe.TileEntitySnowglobe; +import com.hbm.blocks.generic.BlockWandStructure.TileEntityWandStructure; import com.hbm.blocks.machine.Floodlight.TileEntityFloodlight; import com.hbm.blocks.machine.MachineFan.TileEntityFan; import com.hbm.blocks.machine.PistonInserter.TileEntityPistonInserter; @@ -130,18 +131,18 @@ import java.util.*; import java.util.Map.Entry; public class ClientProxy extends ServerProxy { - + private static final I18nClient I18N = new I18nClient(); public RenderInfoSystem theInfoSystem = new RenderInfoSystem(); - + public ITranslate getI18n() { return I18N; } /** Runs just before item an block init */ @Override public void registerPreRenderInfo() { AdvancedModelLoader.registerModelHandler(new HmfModelLoader()); - + QMAWLoader.registerModFileURL(FMLCommonHandler.instance().findContainerFor(RefStrings.MODID).getSource()); } @@ -440,6 +441,8 @@ public class ClientProxy extends ServerProxy { ClientRegistry.bindTileEntitySpecialRenderer(TileEntityVaultDoor.class, new RenderVaultDoor()); ClientRegistry.bindTileEntitySpecialRenderer(TileEntityBlastDoor.class, new RenderBlastDoor()); ClientRegistry.bindTileEntitySpecialRenderer(TileEntityDoorGeneric.class, new RenderDoorGeneric()); + //NBTStructure + ClientRegistry.bindTileEntitySpecialRenderer(TileEntityWandStructure.class, new RenderWandStructure()); } @Override @@ -461,7 +464,7 @@ public class ClientProxy extends ServerProxy { } } } - + // same crap but for items directly because why invent a new solution when this shit works just fine Iterator itItems = Item.itemRegistry.iterator(); while(itItems.hasNext()) { @@ -789,7 +792,7 @@ public class ClientProxy extends ServerProxy { public void registerBlockRenderer() { RenderingRegistry.registerBlockHandler(new RenderISBRHUniversal()); - + /// STOP DOING THIS /// RenderingRegistry.registerBlockHandler(new RenderScaffoldBlock()); RenderingRegistry.registerBlockHandler(new RenderTapeBlock()); diff --git a/src/main/java/com/hbm/render/tileentity/RenderWandStructure.java b/src/main/java/com/hbm/render/tileentity/RenderWandStructure.java new file mode 100644 index 000000000..fd6b0dced --- /dev/null +++ b/src/main/java/com/hbm/render/tileentity/RenderWandStructure.java @@ -0,0 +1,92 @@ +package com.hbm.render.tileentity; + +import org.lwjgl.opengl.GL11; + +import com.hbm.blocks.generic.BlockWandStructure.TileEntityWandStructure; + +import net.minecraft.client.renderer.Tessellator; +import net.minecraft.client.renderer.tileentity.TileEntitySpecialRenderer; +import net.minecraft.tileentity.TileEntity; + +public class RenderWandStructure extends TileEntitySpecialRenderer { + + @Override + public void renderTileEntityAt(TileEntity tile, double x, double y, double z, float interp) { + if(!(tile instanceof TileEntityWandStructure)) return; + TileEntityWandStructure structure = (TileEntityWandStructure) tile; + + if(tile.getBlockMetadata() != 0) return; + + GL11.glPushMatrix(); + { + + double x1 = x; + double y1 = y + 1; + double z1 = z; + + double x2 = x + structure.sizeX; + double y2 = y + structure.sizeY + 1; + double z2 = z + structure.sizeZ; + + + GL11.glDisable(GL11.GL_LIGHTING); + GL11.glDisable(GL11.GL_TEXTURE_2D); + GL11.glColor3f(1F, 1F, 1F); + + + + Tessellator tess = Tessellator.instance; + tess.startDrawing(GL11.GL_LINES); + tess.setBrightness(240); + tess.setColorRGBA_F(1F, 1F, 1F, 1F); + + // top + tess.addVertex(x1, y2, z1); + tess.addVertex(x1, y2, z2); + + tess.addVertex(x1, y2, z2); + tess.addVertex(x2, y2, z2); + + tess.addVertex(x2, y2, z2); + tess.addVertex(x2, y2, z1); + + tess.addVertex(x2, y2, z1); + tess.addVertex(x1, y2, z1); + + // bottom + tess.addVertex(x1, y1, z1); + tess.addVertex(x1, y1, z2); + + tess.addVertex(x1, y1, z2); + tess.addVertex(x2, y1, z2); + + tess.addVertex(x2, y1, z2); + tess.addVertex(x2, y1, z1); + + tess.addVertex(x2, y1, z1); + tess.addVertex(x1, y1, z1); + + // sides + tess.addVertex(x1, y1, z1); + tess.addVertex(x1, y2, z1); + + tess.addVertex(x2, y1, z1); + tess.addVertex(x2, y2, z1); + + tess.addVertex(x2, y1, z2); + tess.addVertex(x2, y2, z2); + + tess.addVertex(x1, y1, z2); + tess.addVertex(x1, y2, z2); + + tess.draw(); + + + GL11.glEnable(GL11.GL_TEXTURE_2D); + GL11.glDisable(GL11.GL_LIGHTING); + + } + GL11.glPopMatrix(); + } + +} diff --git a/src/main/java/com/hbm/tileentity/TileMappings.java b/src/main/java/com/hbm/tileentity/TileMappings.java index e0598f326..34107199c 100644 --- a/src/main/java/com/hbm/tileentity/TileMappings.java +++ b/src/main/java/com/hbm/tileentity/TileMappings.java @@ -20,6 +20,7 @@ import com.hbm.blocks.generic.BlockSnowglobe.TileEntitySnowglobe; import com.hbm.blocks.generic.BlockSupplyCrate.TileEntitySupplyCrate; import com.hbm.blocks.generic.BlockWandJigsaw.TileEntityWandJigsaw; import com.hbm.blocks.generic.BlockWandLoot.TileEntityWandLoot; +import com.hbm.blocks.generic.BlockWandStructure.TileEntityWandStructure; import com.hbm.blocks.generic.BlockWandTandem.TileEntityWandTandem; import com.hbm.blocks.generic.BlockWandLogic.TileEntityWandLogic; import com.hbm.blocks.generic.DungeonSpawner.TileEntityDungeonSpawner; @@ -247,6 +248,7 @@ public class TileMappings { put(TileEntityWandJigsaw.class, "tileentity_wand_jigsaw"); put(TileEntityWandLogic.class, "tileentity_wand_spawner"); put(TileEntityWandTandem.class, "tileentity_wand_tandem"); + put(TileEntityWandStructure.class, "tileentity_wand_structure"); putNetwork(); putBombs(); @@ -444,7 +446,7 @@ public class TileMappings { put(TileEntityPipeExhaustPaintable.class, "tileentity_pipe_exhaust_paintable"); put(TileEntityFluidValve.class, "tileentity_pipe_valve"); put(TileEntityFluidPump.class, "tileentity_pipe_pump"); - + put(TileEntityPipeAnchor.class, "tileentity_pioe_anchor"); put(TileEntityCraneInserter.class, "tileentity_inserter"); @@ -498,7 +500,7 @@ public class TileMappings { if(IConfigurableMachine.class.isAssignableFrom(clazz)) { configurables.add((Class) clazz); } - + /** * Causes problems with most machines where two independently acting tiles work together (TU machines, RBMKs, fluid transfer) * Also breaks due to some sort of buffer leak in the threaded packets, if a boiler is involved (which uses a ByteBuf instead of the usual serializing) it crashes diff --git a/src/main/java/com/hbm/world/gen/nbt/NBTStructure.java b/src/main/java/com/hbm/world/gen/nbt/NBTStructure.java index 5c3b50d25..04a7dda65 100644 --- a/src/main/java/com/hbm/world/gen/nbt/NBTStructure.java +++ b/src/main/java/com/hbm/world/gen/nbt/NBTStructure.java @@ -1,12 +1,16 @@ package com.hbm.world.gen.nbt; import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.util.*; import java.util.function.Predicate; +import org.apache.commons.io.IOUtils; + import com.hbm.blocks.ModBlocks; import com.hbm.blocks.generic.BlockWand; import com.hbm.blocks.generic.BlockWandTandem.TileEntityWandTandem; @@ -92,10 +96,29 @@ public class NBTStructure { loadStructure(stream); } + public NBTStructure(File file) throws FileNotFoundException { + this.name = file.getName(); + InputStream stream = new FileInputStream(file); + loadStructure(stream); + IOUtils.closeQuietly(stream); + } + public String getName() { return name.substring(0, name.length() - 4); // trim .nbt } + public int getSizeX() { + return size.x; + } + + public int getSizeY() { + return size.y; + } + + public int getSizeZ() { + return size.z; + } + public static void register() { MapGenStructureIO.registerStructure(Start.class, "NBTStructures"); MapGenStructureIO.func_143031_a(Component.class, "NBTComponents"); @@ -150,7 +173,7 @@ public class NBTStructure { } // Saves a selected area into an NBT structure (+ some of our non-standard stuff to support 1.7.10) - public static void saveArea(String filename, World world, int x1, int y1, int z1, int x2, int y2, int z2, Set> exclude) { + public static NBTTagCompound saveArea(World world, int x1, int y1, int z1, int x2, int y2, int z2, Set> exclude) { NBTTagCompound structure = new NBTTagCompound(); NBTTagList nbtBlocks = new NBTTagList(); NBTTagList nbtPalette = new NBTTagList(); @@ -257,6 +280,13 @@ public class NBTStructure { structure.setTag("entities", new NBTTagList()); + return structure; + } + + // Writes out a specified area to an .nbt file with a given name + public static File quickSaveArea(String filename, World world, int x1, int y1, int z1, int x2, int y2, int z2, Set> exclude) { + NBTTagCompound structure = saveArea(world, x1, y1, z1, x2, y2, z2, exclude); + try { File structureDirectory = new File(Minecraft.getMinecraft().mcDataDir, "structures"); structureDirectory.mkdir(); @@ -264,8 +294,12 @@ public class NBTStructure { File structureFile = new File(structureDirectory, filename); CompressedStreamTools.writeCompressed(structure, new FileOutputStream(structureFile)); + + return structureFile; } catch (Exception ex) { MainRegistry.logger.warn("Failed to save NBT structure", ex); + + return null; } } @@ -449,10 +483,14 @@ public class NBTStructure { } public void build(World world, int x, int y, int z) { - build(world, x, y, z, 0); + build(world, x, y, z, 0, true, false); } public void build(World world, int x, int y, int z, int coordBaseMode) { + build(world, x, y, z, coordBaseMode, true, false); + } + + public void build(World world, int x, int y, int z, int coordBaseMode, boolean center, boolean wipeExisting) { if(!isLoaded) { MainRegistry.logger.info("NBTStructure is invalid"); return; @@ -460,9 +498,11 @@ public class NBTStructure { HashMap worldItemPalette = getWorldItemPalette(); - boolean swizzle = coordBaseMode == 1 || coordBaseMode == 3; - x -= (swizzle ? size.z : size.x) / 2; - z -= (swizzle ? size.x : size.z) / 2; + if(center) { + boolean swizzle = coordBaseMode == 1 || coordBaseMode == 3; + x -= (swizzle ? size.z : size.x) / 2; + z -= (swizzle ? size.x : size.z) / 2; + } int maxX = size.x; int maxZ = size.z; @@ -474,7 +514,10 @@ public class NBTStructure { for(int by = 0; by < size.y; by++) { BlockState state = blockArray[bx][by][bz]; - if(state == null) continue; + if(state == null) { + if(wipeExisting) world.setBlock(rx, by + y, rz, Blocks.air, 0, 2); + continue; + } int ry = by + y; @@ -634,7 +677,7 @@ public class NBTStructure { for(int i = 0; i < items.tagCount(); i++) { NBTTagCompound item = items.getCompoundTagAt(i); - item.setShort("id", palette.get(item.getShort("id"))); + item.setShort("id", palette.getOrDefault(item.getShort("id"), (short)0)); } } diff --git a/src/main/resources/assets/hbm/lang/en_US.lang b/src/main/resources/assets/hbm/lang/en_US.lang index d57956ab1..d043aa396 100644 --- a/src/main/resources/assets/hbm/lang/en_US.lang +++ b/src/main/resources/assets/hbm/lang/en_US.lang @@ -6349,6 +6349,8 @@ tile.wand_air.name=Structure Wand Block (Air) tile.wand_loot.name=Structure Wand Block (Lootable) tile.wand_jigsaw.name=Structure Wand Block (Jigsaw) tile.wand_logic.name=Structure Wand Block (Logic) +tile.wand_structure.load.name=Structure Loading Block +tile.wand_structure.save.name=Structure Saving Block tile.waste_earth.name=Dead Grass tile.waste_leaves.name=Dead Leaves tile.waste_log.name=Charred Log diff --git a/src/main/resources/assets/hbm/textures/blocks/wand_structure_load.png b/src/main/resources/assets/hbm/textures/blocks/wand_structure_load.png new file mode 100644 index 0000000000000000000000000000000000000000..fbebc58e9cce7e38ef97cc0c9d1d5fd9ea91d534 GIT binary patch literal 289 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jPK-BC>eK@{Ea{HEjtmSN z`?>!lvI6-E$sR$z3=CCj3=9n|3=F@3LJcn%7)lKo7+xhXFj&oCU=S~uvn$XBD8X6a z5n0T@z%2~Ij105pNB{-dOFVsD*UsNwxmhhq!=mZ8&S3j3^P6 literal 0 HcmV?d00001 diff --git a/src/main/resources/assets/hbm/textures/blocks/wand_structure_save.png b/src/main/resources/assets/hbm/textures/blocks/wand_structure_save.png new file mode 100644 index 0000000000000000000000000000000000000000..9773d70e4b7da075c89be033bc61cc4ba4de8625 GIT binary patch literal 285 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jPK-BC>eK@{Ea{HEjtmSN z`?>!lvI6-E$sR$z3=CCj3=9n|3=F@3LJcn%7)lKo7+xhXFj&oCU=S~uvn$XBD8X6a z5n0T@z%2~Ij105pNB{-dOFVsD*jwRx+LP+A;K6bZDxiotBS-kji0}DJth{rZs=n zesT9zXwv2d;+rEkAOCZk_5EU{V{QjD(l#%+ee8HnInTVE3l-MxDX*N8KINVEu3hKY YWlD3zx+e+N0Ig^6boFyt=akR{05hOn761SM literal 0 HcmV?d00001