I am having a few issues with getting an NBT to save and load an int.
What I need to do:
Have an int that is specific to each instance of the block (reason for using an entity). That int needs to be saved when a gui is closed then loaded again when the gui is reopened.
The problem:
The int simply doesn't save. I haven't had any experience with NBTs before so I could be doing something obvious wrong.
The Code:
package techguy.mods.cctv.common;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
public class CCTVTileEntityCamera extends TileEntity
{
public int channel;
public CCTVTileEntityCamera()
{
}
public void readFromNBT(NBTTagCompound par1NBTTagCompound)
{
super.readFromNBT(par1NBTTagCompound);
this.channel = par1NBTTagCompound.getInteger("channel");
}
public void writeToNBT(NBTTagCompound par1NBTTagCompound)
{
super.writeToNBT(par1NBTTagCompound);
par1NBTTagCompound.setInteger("channel", channel);
}
public Packet getDescriptionPacket() //Not sure if I need this
{
NBTTagCompound var1 = new NBTTagCompound();
this.writeToNBT(var1);
return new Packet132TileEntityData(this.xCoord, this.yCoord, this.zCoord, 2, var1);
}
}
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
No, doesn't work. I don't understand what I'm doing wrong. The command block does the exact same thing but with a String rather than an Int and it works perfectly.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
If you are trying to input a number into a gui and then have that go to the tile entity you will need to use packets to send the client data to the server. Guis are strictly client side and because of that any inputs that they are given are only client side as well.
If you are trying to input a number into a gui and then have that go to the tile entity you will need to use packets to send the client data to the server. Guis are strictly client side and because of that any inputs that they are given are only client side as well.
That is what is done. When you click a button in the Gui, it changes the int in the tile entity. It isn't saved though.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
As you know I am unfamiliar with the Minecraft code structure, but when approaching such problems the best solution is always to read into what you want to do.
Notches NBT format is quite interesting actually; really worth looking into
As far as I know, you need to use the @Override annotation, since your using super. Not sure.
The @Override annotation does not affect code. All it does is give a hint to the compiler saying "the following method overrides a superclass". This is helpful when you are working on an API as it will throw an error when the method defined below the @Override annotation is NOT predefined.
Tl;dr:
@Override
public Packet getDescriptionPacket()
{
/* Statement */
}
and
public Packet getDescriptionPacket()
{
/* Statement */
}
As you know I am unfamiliar with the Minecraft code structure, but when approaching such problems the best solution is always to read into what you want to do.
Notch's NBT format is quite interesting actually; really worth looking into
I've looked at all the vanilla blocks that do this. My code is the same but doesn't seem to work.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
I've looked at all the vanilla blocks that do this. My code is the same but doesn't seem to work.
I have this issue too. It seems to me the issue is that the tile entity in the gui and the actual tile entity are the same except when saving, somehow somewhere they get out of sync when saved. The saving works its just it isnt saving the right data. Because when it saves I have it print the data and it says it is all 0's yet when i print the data in the gui it gives it the correct values
I added some prints to my NBT methods and it seems they are never even called. Do you have to call them or is that done automatically in another class? They should just call from super shouldn't they?
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
Yes, both the block and TileEntity are registered.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
These NBT methods in TileEntity are usually not called if the tile has not been registered. Are you using GameRegistry.registerTileEntity in your load method. If you have make sure that updateEntity is been called in your tile. And also:
Make sure you have createNewTileEntity in your block file as well
Also need to be syncing your data from client to server using Container.class
These NBT methods in TileEntity are usually not called if the tile has not been registered. Are you using GameRegistry.registerTileEntity in your load method. If you have make sure that updateEntity is been called in your tile. And also:
Make sure you have createNewTileEntity in your block file as well
Also need to be syncing your data from client to server using Container.class
It is registered and createNewTileEntity is being used. I'll give updateEntity a go but I don't specifically require its use. I'm not using a Container.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
that just syncs the game to the servers data, the issue is, to my understanding, is that the server is not getting any data from the gui, the client is which gives the appearance that it is working. So basically since the server isnt getting data from the client then when it syncs the server data it syncs nothing.
Here's the rest of my code, there would be a problem somewhere else no doubt.
Registry:
package techguy.mods.cctv.common;
import net.minecraft.block.Block;
import net.minecraft.creativetab.CreativeTabs;
import net.minecraft.item.Item;
import net.minecraftforge.common.Configuration;
import cpw.mods.fml.common.Mod;
import cpw.mods.fml.common.Mod.Init;
import cpw.mods.fml.common.Mod.PostInit;
import cpw.mods.fml.common.Mod.PreInit;
import cpw.mods.fml.common.event.FMLInitializationEvent;
import cpw.mods.fml.common.event.FMLPostInitializationEvent;
import cpw.mods.fml.common.event.FMLPreInitializationEvent;
import cpw.mods.fml.common.network.NetworkMod;
import cpw.mods.fml.common.registry.GameRegistry;
import cpw.mods.fml.common.registry.LanguageRegistry;
@Mod(modid="techguy543CCTV", name="TechGuy's CCTV", version="[MC1.4.7] v0.0.1")
@NetworkMod
(
clientSideRequired = true,
serverSideRequired = false,
channels = {"techguy_cctv"},
packetHandler = CCTVPacketHandler.class
)
public class CCTVMainRegistry
{
public static int cameraID = 150;
public static int monitorID = 151;
public static final Block camera = new CCTVBlockCamera(cameraID, 1).setBlockName("cctvCamera").setHardness(1.3F).setCreativeTab(CreativeTabs.tabDecorations);
public static final Item monitor = new CCTVItemMonitor(monitorID, CCTVEntityMonitor.class).setItemName("cctvMonitor").setCreativeTab(CreativeTabs.tabDecorations).setIconIndex(0);
@PreInit
public void preInit(FMLPreInitializationEvent evt)
{
/*Configuration config = new Configuration(evt.getSuggestedConfigurationFile());
config.load();
cameraID = config.getBlock(Configuration.CATEGORY_BLOCK, "Camera", 3500).getInt();
config.save();*/
}
@Init
public void init(FMLInitializationEvent evt)
{
GameRegistry.registerTileEntity(CCTVTileEntityCamera.class, "CCTVCameraEntity");
GameRegistry.registerBlock(camera, "cctvCamera");
LanguageRegistry.addName(camera, "CCTV Camera");
LanguageRegistry.addName(monitor, "CCTV Monitor");
CCTVCommonProxy.registerRenderInformation();
}
@PostInit
public void postInit(FMLPostInitializationEvent evt)
{
}
}
Block:
package techguy.mods.cctv.common;
import techguy.mods.cctv.client.CCTVGuiCamera;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.client.Minecraft;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.MathHelper;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
public class CCTVBlockCamera extends Block
{
public int channel;
public CCTVBlockCamera(int i, int j)
{
super(i, j, Material.wood);
}
public boolean onBlockActivated(World par1World, int par2, int par3, int par4, EntityPlayer par5EntityPlayer, int par6, float par7, float par8, float par9)
{
Minecraft.getMinecraft().displayGuiScreen(new CCTVGuiCamera(par1World, par5EntityPlayer, Minecraft.getMinecraft()));
TileEntity tile1 = Minecraft.getMinecraft().getIntegratedServer().worldServers[par5EntityPlayer.dimension].getBlockTileEntity(par2, par3, par4);
return true;
}
public void onBlockPlacedBy(World world, int i, int j, int k, EntityLiving entityliving)
{
int l = MathHelper.floor_double((double)((entityliving.rotationYaw * 4F) / 360F) + 0.5D) & 3;
switch (l)
{
case 0:
world.setBlockMetadataWithNotify(i, j, k, 2);
break;
case 1:
world.setBlockMetadataWithNotify(i, j, k, 5);
break;
case 2:
world.setBlockMetadataWithNotify(i, j, k, 3);
break;
case 3:
world.setBlockMetadataWithNotify(i, j, k, 4);
break;
}
}
public int getBlockTexture(IBlockAccess iblockaccess, int i, int j, int k, int l)
{
return l != iblockaccess.getBlockMetadata(i, j, k) ? blockIndexInTexture : 0;
}
/**
* Returns the block texture based on the side being looked at. Args: side
*/
public int getBlockTextureFromSide(int i)
{
return i != 3 ? blockIndexInTexture : 0;
}
public TileEntity createNewTileEntity(World par1World)
{
return new CCTVTileEntityCamera();
}
public String getTextureFile()
{
return "/CCTV/terrain.png";
}
}
TileEntity:
package techguy.mods.cctv.common;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.network.packet.Packet;
import net.minecraft.network.packet.Packet132TileEntityData;
import net.minecraft.tileentity.TileEntity;
public class CCTVTileEntityCamera extends TileEntity
{
public int channel;
public CCTVTileEntityCamera()
{
}
public void writeToNBT(NBTTagCompound par1NBTTagCompound)
{
super.writeToNBT(par1NBTTagCompound);
par1NBTTagCompound.setInteger("channel", this.channel);
System.out.println("writing NBT");
}
public void readFromNBT(NBTTagCompound par1NBTTagCompound)
{
super.readFromNBT(par1NBTTagCompound);
this.channel = par1NBTTagCompound.getInteger("channel");
System.out.println("reading NBT");
}
public Packet getDescriptionPacket() //Not sure if I need this
{
NBTTagCompound var1 = new NBTTagCompound();
this.writeToNBT(var1);
return new Packet132TileEntityData(this.xCoord, this.yCoord, this.zCoord, 2, var1);
}
public void updateEntity()
{
System.out.println("updateTE");
}
}
Gui:
package techguy.mods.cctv.client;
import net.minecraft.client.Minecraft;
import net.minecraft.client.gui.GuiButton;
import net.minecraft.client.gui.GuiScreen;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.world.World;
import techguy.mods.cctv.common.CCTVTileEntityCamera;
public class CCTVGuiCamera extends GuiScreen
{
CCTVTileEntityCamera tile = new CCTVTileEntityCamera();
private Minecraft mc;
private World world;
private EntityPlayer entityPlayer;
public CCTVGuiCamera(World world1, EntityPlayer entityPlayer1, Minecraft minecraft)
{
world = world1;
entityPlayer = entityPlayer1;
mc = minecraft;
}
public GuiButton channelPlusOne;
public GuiButton channelPlusTen;
public GuiButton channelPlusHundred;
public GuiButton channelSubtractOne;
public GuiButton channelSubtractTen;
public GuiButton channelSubtractHundred;
public void initGui()
{
controlList.clear();
channelPlusOne = new GuiButton(0, width / 2 + 3, height / 2 - 20, 25, 20, "+");
controlList.add(channelPlusOne);
channelPlusTen = new GuiButton(1, width / 2 + 29, height / 2 - 20, 27, 20, "+10");
controlList.add(channelPlusTen);
channelPlusHundred = new GuiButton(2, width / 2 + 57, height / 2 - 20, 31, 20, "+100");
controlList.add(channelPlusHundred);
channelSubtractOne = new GuiButton(3, width / 2 - 28, height / 2 - 20, 25, 20, "-");
controlList.add(channelSubtractOne);
channelSubtractTen = new GuiButton(4, width / 2 - 56, height / 2 - 20, 27, 20, "-10");
controlList.add(channelSubtractTen);
channelSubtractHundred = new GuiButton(5, width / 2 - 88, height / 2 - 20, 31, 20, "-100");
controlList.add(channelSubtractHundred);
}
public void updateScreen()
{
if(tile.channel < 0)
tile.channel = 0;
}
protected void actionPerformed(GuiButton guibutton)
{
if (guibutton.id == 0)
{
tile.channel++;
}
if (guibutton.id == 1)
{
for( int l = 0; l < 10; l++)
{
tile.channel++;
}
}
if (guibutton.id == 2)
{
for( int l = 0; l < 100; l++)
{
tile.channel++;
}
}
if (guibutton.id == 3)
{
tile.channel--;
}
if (guibutton.id == 4)
{
for( int l = 0; l < 10; l++)
{
tile.channel--;
}
}
if (guibutton.id == 5)
{
for( int l = 0; l < 100; l++)
{
tile.channel--;
}
}
}
public boolean doesGuiPauseGame()
{
return false;
}
public void drawScreen(int i, int j, float f)
{
mc.renderEngine.bindTexture(mc.renderEngine.getTexture("/CCTV/cameraGui.png"));
drawTexturedModalRect(width / 2 - 100, height / 2 - 64, 0, 0, 256, 177);
drawCenteredString(fontRenderer, "CCTV Camera", width / 2, height / 2 - 55, 0xffffff);
drawCenteredString(fontRenderer, "Channel: " + tile.channel, width / 2, height / 2 - 40, 0xffffff);
for( int l = 0; l < controlList.size(); l++)
{
GuiButton guibutton = (GuiButton)controlList.get(l);
guibutton.drawButton(mc, i, j);
}
}
}
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
Try to use System.err.println(); instead, does it still print out in the console?
As for your actual problem, try to give channel a value in the constructor, and use an if statement in readEntityFromNBT like this:
if (par1NBTTagCompound.hasKey("channel")) {
System.err.println("channel exists in NBT");
this.channel = par1NBTTagCompound.getInteger("channel");
}
Does it print channel exists in NBT?
The methods aren't called at all so this will not show anything anyway. I did test it just to make sure but nothing is printed at all, not even from prints in the latest code I posted on the previous page.
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
Meh, your NBT-methods never get called because your TileEntity never gets created, it's that easy. You use createNewTileEntity in a class that extends Block but the method is actually from BlockContainer. So you have to switch Block to BlockContainer or find another way to create your TileEntity on creation of your block.
(You would've seen that if you'd use @Override btw, it gives you an error everytime you try to use a method from a parent-class that isn't actually there.)
Forgot about that... Thanks
Rollback Post to RevisionRollBack
“Computers are incredibly fast, accurate and stupid; humans are incredibly slow, inaccurate and brilliant; together they are powerful beyond imagination."
I am having a few issues with getting an NBT to save and load an int.
What I need to do:
Have an int that is specific to each instance of the block (reason for using an entity). That int needs to be saved when a gui is closed then loaded again when the gui is reopened.
The problem:
The int simply doesn't save. I haven't had any experience with NBTs before so I could be doing something obvious wrong.
The Code:
together they are powerful beyond imagination."
together they are powerful beyond imagination."
That is what is done. When you click a button in the Gui, it changes the int in the tile entity. It isn't saved though.
together they are powerful beyond imagination."
Notches NBT format is quite interesting actually; really worth looking into
The @Override annotation does not affect code. All it does is give a hint to the compiler saying "the following method overrides a superclass". This is helpful when you are working on an API as it will throw an error when the method defined below the @Override annotation is NOT predefined.
Tl;dr:
and
are not different at all.
I've looked at all the vanilla blocks that do this. My code is the same but doesn't seem to work.
together they are powerful beyond imagination."
I have this issue too. It seems to me the issue is that the tile entity in the gui and the actual tile entity are the same except when saving, somehow somewhere they get out of sync when saved. The saving works its just it isnt saving the right data. Because when it saves I have it print the data and it says it is all 0's yet when i print the data in the gui it gives it the correct values
Follow @jamolnng
The best way to contact me is via twitter.
together they are powerful beyond imagination."
together they are powerful beyond imagination."
Make sure you have createNewTileEntity in your block file as well
Also need to be syncing your data from client to server using Container.class
It is registered and createNewTileEntity is being used. I'll give updateEntity a go but I don't specifically require its use. I'm not using a Container.
together they are powerful beyond imagination."
that just syncs the game to the servers data, the issue is, to my understanding, is that the server is not getting any data from the gui, the client is which gives the appearance that it is working. So basically since the server isnt getting data from the client then when it syncs the server data it syncs nothing.
Follow @jamolnng
The best way to contact me is via twitter.
How did you do that for a tile entity though, I know how to do it with things that aren't tile entities?
Also for reference here is my print out from what I was talking about in the previous reply
2013-01-20 11:13:21 [INFO] [STDOUT] wrote 0.17647052 3 54
2013-01-20 11:13:21 [INFO] [STDOUT] read 0.17647052 3 54
2013-01-20 11:13:30 [INFO] [STDOUT] wrote 0.0 0 0
the last line is what the server called while the first two are from the client
EDIT: I be derpin. FOR FUTURE REFERENCE! instead of this in your onBlockActivated method
TileEntity tile1 = par1World.getBlockTileEntity(par2, par3, par4);
Use this
TileEntity tile1 = ModLoader.getMinecraftServerInstance().worldServers[par5EntityPlayer.dimension].getBlockTileEntity(par2, par3, par4);
Follow @jamolnng
The best way to contact me is via twitter.
Registry:
Block:
TileEntity:
Gui:
together they are powerful beyond imagination."
I'll give it a go now. The ids are not in use till the 1.5 update. They're only really testing ids anyway, no plan to actually use them in a release.
Edit: Adding that method didn't work.
together they are powerful beyond imagination."
The methods aren't called at all so this will not show anything anyway. I did test it just to make sure but nothing is printed at all, not even from prints in the latest code I posted on the previous page.
together they are powerful beyond imagination."
Forgot about that... Thanks
together they are powerful beyond imagination."