Jump to content

[1.8.*] Trouble Setting Item to NULL


Jugbot

Recommended Posts

I am having trouble setting the item in my tile entity to null. Shortly after the item is subtracted in the slot to zero, the game crashes. Here is my code:

package com.jugbot.conquest.blocks.tileentity;

import java.util.Random;

//import com.jugbot.conquest.api.RecipeData;
import com.jugbot.conquest.util.ParticleSpawner;

import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.init.Blocks;
import net.minecraft.inventory.IInventory;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.network.NetworkManager;
import net.minecraft.network.Packet;
import net.minecraft.network.play.server.S35PacketUpdateTileEntity;
import net.minecraft.server.gui.IUpdatePlayerListBox;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.tileentity.TileEntityFurnace;
import net.minecraft.util.ChatComponentText;
import net.minecraft.util.IChatComponent;

//possible broke everything 
public class TileEntityStove extends TileEntity implements IInventory,
	IUpdatePlayerListBox {
private ItemStack item = null;
private ItemStack log = new ItemStack(Blocks.log);
private ItemStack log2 = new ItemStack(Blocks.log2);
private ItemStack planks = new ItemStack(Blocks.planks);
private String customName;
private boolean cooking = false;
public int progress = 0;
public int burnTime = 40;
public int count = 0;

public ItemStack getItem() {
	return item;
}

public void startCooking() {
	System.out.println(item);
	if (item != null) {
		// RecipeData data =
		// RecipeAPI.getMicrowaveRecipeFromIngredients(item);
		count = item.stackSize;
		if (item.isItemEqual(log) || item.isItemEqual(log2)) {
			cooking = true;
			burnTime = 80;
		} else if (item.isItemEqual(planks)) {
			cooking = true;
			burnTime = 20;
		}
	}
}

public void stopCooking() {
	this.cooking = false;
	this.progress = 0;
}

public boolean isCooking() {
	return cooking;
}

private Random rand = new Random();
private int timer = 0;

@Override
public void update()
{

	System.out.println("begin update");
	boolean flag = this.progress >= burnTime;
	boolean flag1 = false;

	if (cooking)
	{
		if (this.worldObj.isRemote)
		{
			double posX = pos.getX() + 0.35D + (rand.nextDouble() / 3);
			double posZ = pos.getZ() + 0.35D + (rand.nextDouble() / 3);
			ParticleSpawner.spawnParticle("smoke", posX, pos.getY() + 0.065D, posZ);
		}

		progress++;
		if (progress >= burnTime)
		{
			if (item != null)
			{


				this.item.stackSize--;


				if (item.stackSize <= 0)
				{
					System.out.println(item);
					this.item = null;
					//this.cooking = false;
					System.out.println(item);
				}
				//this.markDirty(); //YES!!
			}
			if (!worldObj.isRemote)
			{
				worldObj.playSoundEffect(pos.getX(), pos.getY(), pos.getZ(), "aoc:fire_finish", 0.75F, 1.0F);
			}
			timer = 0;
			progress = 0;
			if (item.stackSize == 0 ) {
				cooking = false;

			}

		}
		else //looping sound-play
		{
			if (timer == 20)
			{
				timer = 0;
			}
			if (timer == 0)
			{
				worldObj.playSoundEffect(pos.getX(), pos.getY(), pos.getZ(), "aoc:stove_burning", 0.75F, 1.0F);
			}
			timer++;
		}
	}
}

@Override
public void readFromNBT(NBTTagCompound par1NBTTagCompound) {
	super.readFromNBT(par1NBTTagCompound);
	if (par1NBTTagCompound.hasKey("Item")) {
		NBTTagCompound nbt = par1NBTTagCompound.getCompoundTag("Item");
		this.item = ItemStack.loadItemStackFromNBT(nbt);
	}
	this.cooking = par1NBTTagCompound.getBoolean("Coooking");
	this.progress = par1NBTTagCompound.getInteger("Progress");
}

@Override
public void writeToNBT(NBTTagCompound par1NBTTagCompound) {
	super.writeToNBT(par1NBTTagCompound);
	NBTTagCompound nbt = new NBTTagCompound();
	if (item != null) {
		item.writeToNBT(nbt);
	}
	par1NBTTagCompound.setTag("Item", nbt);
	par1NBTTagCompound.setBoolean("Coooking", cooking);
	par1NBTTagCompound.setInteger("Progress", progress);
}

@Override
public void onDataPacket(NetworkManager net, S35PacketUpdateTileEntity pkt) {
	NBTTagCompound tagCom = pkt.getNbtCompound();
	this.readFromNBT(tagCom);
}

@Override
public Packet getDescriptionPacket() {
	NBTTagCompound tagCom = new NBTTagCompound();
	this.writeToNBT(tagCom);
	return new S35PacketUpdateTileEntity(pos, getBlockMetadata(), tagCom);
}

@Override
public int getSizeInventory() {
	return 1;
}

@Override
public ItemStack getStackInSlot(int slot) {
	return this.item;
}

@Override
public ItemStack decrStackSize(int slot, int number) {
	if (this.item != null) {
		ItemStack itemstack;

		if (this.item.stackSize <= number) {
			itemstack = this.item;
			this.item = null;
			return itemstack;
		}
		itemstack = this.item.splitStack(number);

		if (this.item.stackSize == 0) {
			this.item = null;
		}

		return itemstack;
	}
	return null;
}

@Override
public ItemStack getStackInSlotOnClosing(int slot) {
	return item;
}

@Override
public void setInventorySlotContents(int par1, ItemStack par2ItemStack) {
	this.item = par2ItemStack;

	if (par2ItemStack != null
			&& par2ItemStack.stackSize > this.getInventoryStackLimit()) {
		par2ItemStack.stackSize = this.getInventoryStackLimit();
	}
}

@Override
public int getInventoryStackLimit() {
	return 16;
}

@Override
public boolean isUseableByPlayer(EntityPlayer entityplayer) {
	return this.worldObj.getTileEntity(pos) != this ? false : entityplayer
			.getDistanceSq(pos.getX() + 0.5D, pos.getY() + 0.5D,
					pos.getZ() + 0.5D) <= 64.0D;
}

@Override
public boolean isItemValidForSlot(int p_94041_1_, ItemStack p_94041_2_) {
	return false;
}

@Override
public void openInventory(EntityPlayer player) {
}

@Override
public void closeInventory(EntityPlayer player) {
}

@Override
public int getField(int id) {
	return 0;
}

@Override
public void setField(int id, int value) {
}

@Override
public int getFieldCount() {
	return 0;
}

@Override
public void clear() {
	item = null;
}

@Override
public String getName() {
	return hasCustomName() ? customName : "Wood Stove";
}

@Override
public boolean hasCustomName() {
	return customName != null;
}

@Override
public IChatComponent getDisplayName() {
	return new ChatComponentText(getName());
}
}

 

I know that the item is in fact set to null, its just that it messes something up god knows where...

For me I somehow suspect writeToNBT()

 

If you need any other files, just ask PLEASE ;)

Link to comment
Share on other sites

Hey, its hard to solve this without the container class. But I found one methode wich seems to make problems.

its clear(). You just said itemsack = null. although there is just one slot. You still need to specify wich stack from wich slott = null.

Projects:

Discontinued:

- N2ConfigAPI

- Meachanical Crafting Table

 

Latest:

- CollectionUtils

 

Coöperations:

- InGameConfigManager

Link to comment
Share on other sites

Great! Here you go:

package com.jugbot.conquest.gui.container;

import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.inventory.Container;
import net.minecraft.inventory.IInventory;
import net.minecraft.inventory.Slot;
import net.minecraft.item.ItemStack;

import com.jugbot.conquest.blocks.tileentity.TileEntityStove;
import com.jugbot.conquest.gui.slot.SlotStove;

public class ContainerStove extends Container
{
private IInventory stoveInventory;

public ContainerStove(IInventory playerInventory, TileEntityStove stoveInventory)
{
	System.out.println("I came for the cake");
	this.stoveInventory = stoveInventory;

	this.addSlotToContainer(new SlotStove(stoveInventory, 0, 65, 43));
	System.out.println("Main slot added");

	for (int i = 0; i < 3; i++)
	{
		for (int j = 0; j < 9; ++j)
		{
			this.addSlotToContainer(new Slot(playerInventory, j + i * 9 + 9, j * 18 + 8, i * 18 + 92));
			System.out.println(i + " Slot inv added");
		}
	}

	for (int i = 0; i < 9; i++)
	{
		this.addSlotToContainer(new Slot(playerInventory, i, i * 18 + 8, 150));
		System.out.println(i + " Slot bar added");
	}
}

@Override
public boolean canInteractWith(EntityPlayer player)
{
	return this.stoveInventory.isUseableByPlayer(player);
}

@Override
public ItemStack transferStackInSlot(EntityPlayer player, int slotNum)
{
	ItemStack itemCopy = null;
	Slot slot = (Slot) this.inventorySlots.get(slotNum);

	if (slot != null && slot.getHasStack())
	{
		ItemStack item = slot.getStack();
		itemCopy = item.copy();

		if (slotNum < 1)
		{
			if (!this.mergeItemStack(item, 1, this.inventorySlots.size(), false))
			{
				return null;
			}
		}
		else if (slotNum > 0 && slotNum < 27)
		{
			if (!this.mergeItemStack(item, 27, this.inventorySlots.size(), true))
			{
				return null;
			}
		}
		else if (!this.mergeItemStack(item, 1, 27, false))
		{
			return null;
		}

		if (item.stackSize == 0)
		{
			slot.putStack((ItemStack) null);
		}
		else
		{
			slot.onSlotChanged();
		}
	}
	return null;
}

@Override
public void onContainerClosed(EntityPlayer player)
{
	super.onContainerClosed(player);
	this.stoveInventory.closeInventory(player);
}
}

 

I don't see the need to select a certain slot if there is only one there 0.o Not even quite sure how I'm supposed to do that...

Link to comment
Share on other sites

Without a crash report it's hard to say but, it may be that your NBT is still writing the null item? Or reads it while the item is null? If not that, maybe you need to use a preset method to consume the item in slot. :P

I am not a cat. I know my profile picture is sexy and amazing beyond anything you could imagine but my cat like features only persist in my fierce eyes. I might be a cat.

Link to comment
Share on other sites

From your first post you have

 

this.item = null;

 

Please note that this does absolutely nothing of the sort what you want and makes you kill all code that uses that specific itemstack.

 

What it does is clear your reference to the itemstack object, but also all references all other objects have to that memory space, which throws the nullpointer exceptions.

 

Now, you are trying to clean up the itemstack I gather, don' t set it to null. It's like taking a sledgehammer to make a birdhouse. Plus the code doesn't expect things to go 0 at unexpected times(thats why the nullpointer exceptions). Just use the code as it's designed. Look at how the crafting tables do it when something is crafted. Look at how the furnace does it when it smelts an item.

 

Just set the stacksize to 0, It will clean itself up.

 

Or if you need it to be NULL for one reason or another, do Itemstack.copy() when passing it to another object. That way the other object won't hold a reference to your Itemstack, that you set to null.

 

Your object.itemstack is the "Master" key. if you set that to null it will get cleaned up even though you have references somewhere else to that itemstack.

 

Use itemstack.copy() when transferring itemstacks between slots if you have a direct link to that itemstack. That way you know there is a clean cut from the reference and you don't have to worry about that anymore.

 

itemstack = this.item;

 

is the cause of your trouble. You are making a reference to your itemstack object. That you clear.

 

Better would be

 

itemstack = this.item.copy();

How much wood could a woodchuck chuck if a wood chuck could chuck wood - Guybrush Treepwood

 

I wrote my own mod ish... still a few bugs to fix. http://thaumcraft.duckdns.org/downloads/MagicCookies-1.0.6.4.jar

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.