Jump to content

ErnstLustig

Members
  • Posts

    25
  • Joined

  • Last visited

Converted

  • Gender
    Undisclosed
  • Personal Text
    I am new!

Recent Profile Visitors

The recent visitors block is disabled and is not being shown to other users.

ErnstLustig's Achievements

Tree Puncher

Tree Puncher (2/8)

0

Reputation

  1. Try looking for a packet. I added packets and it solved the problem. Thanks.
  2. I wanted to look into packets now, but before that I wondered if this is even a client and server sync issue. Because I open the GUI only on the server side, right? But it still doesn't recognize the fluids correctly. Is this how this works? Is there maybe a command to force a block to synchronize with server and client, just to check if this is even the problem? Or what would be the best way to debug that?
  3. Man, I'm not sure. I get what you are saying, but I have a hard time believing this is needed to implement it like that. I just tried to look at the EnderIO Tank code which also renders the tank content in the GUI and I couldn't find any code like that in there. It just accesses the TE's FluidStack directly and renders it, just like I did it (at least it looks like it). I must be missing something totally terribly.
  4. I just only saw your edit. Makes sense. But where is the code actually used. As the GuiFurnace doesn't actually use it, that's my question.
  5. Ah, I named it GuiProxy, forgot that it implements GuiHandler. @Override public Object getServerGuiElement( int ID, EntityPlayer player, World world, int x, int y, int z ){ BlockPos pos = new BlockPos( x, y, z ); TileEntity te = world.getTileEntity( pos ); //other stuff if( te instanceof TileEntitySqueezer ){ return new ContainerSqueezer( player.inventory, (TileEntitySqueezer) te ); } } @Override public Object getClientGuiElement( int ID, EntityPlayer player, World world, int x, int y, int z ){ BlockPos pos = new BlockPos( x, y, z ); TileEntity te = world.getTileEntity( pos ); //other stuff if( te instanceof TileEntitySqueezer ){ TileEntitySqueezer containerTileEntity = (TileEntitySqueezer) te; return new GuiSqueezer( containerTileEntity, new ContainerSqueezer( player.inventory, containerTileEntity ) ); } }
  6. Yeah, but what is the advantage of that? If you look in the GuiFurnace code, it accesses as I said the fields directly from the TileEntity, not from the container. Why two containers and sync the data of them there when they are never used (or I at least can't find the use)? Also it works in my code just fine without those, only the fluidstack is giving me problems. Before I blindly try to implement listeners and such, I like to understand first what they are useful for as I don't see the use for them now. Also not sure what you mean with GuiHandler as I can't find a mention of that in the code.
  7. Well, I looked into it and I'm not sure how this should help me. In my TEs ItemStacks get updated correctly no matter if input manually or with Hoppers or Item Conduits, also the progress bars I implemented in my machines work fine even without adding listeners (beside that I don't understand the code in ContainerFurnace, the listeners basically update local variable copies for the progress bar, but GuiFurnace accesses the variables from the TE directly not from the Container, not sure what the Container variables are even there for). So ItemStacks and progress bars works fine for, only the FluidStack doesn't get synced correctly. I'm not really understanding.
  8. So, I'm still having troubles figuring out the syncing between server and client. I added a block with a tank and to try it out I added the funcionality to right click a bucket to add/get fluids to/from the tank. I adapted the code mostly from TiCo. And it works. Now I tried EnderIO Fluid conduits and if fluids get added or removed the GUI doesn't get updated. But the fluid is in there as I can still get it out with a bucket. I'm guessing because this only done server-side and I have to tell the client something has changed. Not sure how to do that though. Do I have to use packets for that? Here the most relevant code: public class BlockSqueezer extends BlockFaeries implements ITileEntityProvider { @Override public boolean onBlockActivated( World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, ItemStack heldItem, EnumFacing side, float hitX, float hitY, float hitZ ){ TileEntity te = world.getTileEntity( pos ); if ( !( te instanceof TileEntitySqueezer ) ) { return false; } if( te.hasCapability( CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY, side ) ){ IFluidHandler fluidHandler = te.getCapability( CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY, side ); boolean success = FluidUtil.interactWithFluidHandler( heldItem, fluidHandler, player ); if( success ){ return true; } } if( !world.isRemote ){ player.openGui( Faeries.instance, GUI_ID, world, pos.getX(), pos.getY(), pos.getZ() ); } return true; } } public class TileEntitySqueezer extends TileEntity implements ITickable { private FluidTank tank = new FluidTank( CAPACITY ) { @Override protected void onContentsChanged(){ TileEntitySqueezer.this.markDirty(); } }; @Override public void readFromNBT( NBTTagCompound compound ){ super.readFromNBT( compound ); if( compound.hasKey( "input" ) ){ inputStack.deserializeNBT( (NBTTagCompound) compound.getTag( "input" ) ); } tank.readFromNBT( compound ); } public NBTTagCompound getUpdateTag() { return this.writeToNBT( new NBTTagCompound() ); } @Override public NBTTagCompound writeToNBT( NBTTagCompound compound ){ super.writeToNBT( compound ); compound.setTag( "input", inputStack.serializeNBT() ); tank.writeToNBT( compound ); return compound; } @Override public boolean hasCapability( Capability<?> capability, EnumFacing facing ){ if( capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY || capability == CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY ){ return true; } return super.hasCapability( capability, facing ); } @Override public <T> T getCapability( Capability<T> capability, EnumFacing facing ){ if( capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY ){ if( facing == null ){ return (T) inputStack; } return (T) new InsertItemStackHandler( inputStack ); } if( capability == CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY ){ return (T) tank; } return super.getCapability( capability, facing ); } public FluidTank getFluidTank(){ return tank; } } public class GuiSqueezer extends GuiContainer { public static final int WIDTH = 180; public static final int HEIGHT = 152; private final TileEntitySqueezer te; private static final ResourceLocation background = new ResourceLocation( Reference.MOD_ID, "textures/gui/guisqueezer.png" ); public GuiSqueezer( TileEntitySqueezer tileEntity, ContainerSqueezer container ){ super( container ); xSize = WIDTH; ySize = HEIGHT; te = tileEntity; } @Override protected void drawGuiContainerBackgroundLayer( float partialTicks, int mouseX, int mouseY ){ mc.getTextureManager().bindTexture( background ); drawTexturedModalRect( guiLeft, guiTop, 0, 0, xSize, ySize ); FluidStack fluid = te.getFluidTank().getFluid(); if( fluid != null && fluid.amount != 0 ) { ResourceLocation location = te.getFluidTank().getFluid().getFluid().getStill(); TextureAtlasSprite sprite = mc.getTextureMapBlocks().getAtlasSprite( location.toString() ); mc.renderEngine.bindTexture( TextureMap.LOCATION_BLOCKS_TEXTURE ); float filllevel = (float)fluid.amount * 48 / te.CAPACITY; drawTexturedModalRect( guiLeft + 82, guiTop + 54 - Math.round( filllevel ), sprite, 16, Math.round( filllevel ) ); } } }
  9. Ugh, this is terrible. I didn't know that. What would be an example of that?
  10. Well I don't know how to do it better, that's why I asked. I needed two StackHandlers because I need one to be a subclass of the other with the added restriction of not extracting items, but I can't copy the StackHandler because I can't access the ItemStacks. So I need to add the method of getStacks. Not sure what you mean with not using the capability at all, you mean in the Container to access the ItemStacks? But that seems like even more work to me.
  11. Well I implemented this now and it seems to work. I tried a block where for the input only a certain item type is allowed (both manual and automatic), but it can be removed manually, but not automatically. But it seems rather hacked than a clean simple solution. I think this can be made way more simple. What do you think? public class TileEntitySqueezer extends TileEntity implements ITickable { public static final int INPUT_SIZE = 1; public static final int CAPACITY = Fluid.BUCKET_VOLUME * 8; private FluidTank tank = new FluidTank( CAPACITY ) { @Override protected void onContentsChanged(){ TileEntitySqueezer.this.markDirty(); } }; private SqueezerItemStackHandler inputStack = new SqueezerItemStackHandler( INPUT_SIZE ); [...] @Override public boolean hasCapability( Capability<?> capability, EnumFacing facing ){ if( capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY || capability == CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY ){ return true; } return super.hasCapability( capability, facing ); } @Override public <T> T getCapability( Capability<T> capability, EnumFacing facing ){ if( capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY ){ if( facing == null ){ return (T) inputStack; } return (T) new InsertItemStackHandler( inputStack ); } if( capability == CapabilityFluidHandler.FLUID_HANDLER_CAPABILITY ){ return (T) tank; } return super.getCapability( capability, facing ); } public class SqueezerItemStackHandler extends ItemStackHandler{ public SqueezerItemStackHandler(){ super( 1 ); } public SqueezerItemStackHandler( int size ){ super( size ); } @Override protected void onContentsChanged( int slot ){ TileEntitySqueezer.this.markDirty(); } @Override public ItemStack insertItem( int slot, ItemStack stack, boolean simulate ){ if( !( stack.getItem() instanceof ItemDrop ) ){ return stack; } return super.insertItem( slot, stack, simulate ); } public ItemStack[] getStacks(){ return stacks; } } public class InsertItemStackHandler extends SqueezerItemStackHandler{ public InsertItemStackHandler( SqueezerItemStackHandler stackhandler ){ this.stacks = stackhandler.getStacks(); } @Override public ItemStack extractItem( int slot, int amount, boolean simulate ){ return null; } }
  12. Ah I didn't know that. Thanks I will try to do that.
  13. I'm still not fully understanding the new Capability system. I know how to define what to access from which side, but what I care about is what to access depending on input or output. What I mean by that is that I might want to allow to put items in with a hopper for a specific slot, but not allow a hopper to pull the items out of that slot. How do I do that? Any examples you can point me at? I looked at a lot of code, but couldn't find the specific part where to define that. Also it doesn't seem to check isItemValid if it's inserted with a hopper. So I'm not allowed to manually put items in the slot, but disallowed items land in the slot if accessed with a hopper. For reference, here is how I define the slot in the container. IItemHandler itemHandler = this.te.getCapability( CapabilityItemHandler.ITEM_HANDLER_CAPABILITY, null ); addSlotToContainer( new SlotItemHandler( itemHandler, 0, 18, 24 ){ @Override public boolean isItemValid( ItemStack stack ){ return stack.getItem() instanceof ItemDrop; } });
  14. Cool thanks, I'll try that.
  15. I'm currently messing with ticking Tile Entities and try to learn them. I try to copy the furnace code as best as I can. First I tried to spawn an item after a certain amount of time which worked great. Then I added the same Progress Bar of the GUI as the furnace. Works also great. But now I noticed that if I quit my single player world and rejoin, the GUI isn't in sync with the spawning anymore, the GUI Progress Bar gets reset every time I rejoin. I think this means that the Server and the Client aren't in sync. I think I'm missing some background info here. Can anyone help me? Here's part of my TileEntity Code: @Override public void update() { if( !hasFaery() ){ time = 0; flag = false; } if( time <= 0 && hasFaery() ){ if( flag && !worldObj.isRemote ){ EntityItem produce = new EntityItem( worldObj, pos.getX(), pos.getY()+1, pos.getZ(), new ItemStack( Items.STICK ) ); worldObj.spawnEntityInWorld( produce ); } time = MAX_TIME; flag = true; } time--; if( hasFaery() ){ markDirty(); } } @Override public void readFromNBT( NBTTagCompound compound ){ super.readFromNBT( compound ); if( compound.hasKey( "input" ) ){ inputStack.deserializeNBT( (NBTTagCompound) compound.getTag( "input" ) ); } if( compound.hasKey( "output" ) ){ outputStack.deserializeNBT( (NBTTagCompound) compound.getTag( "output" ) ); } if( compound.hasKey( "time" ) ){ time = compound.getInteger( "time" ); } } @Override public NBTTagCompound writeToNBT( NBTTagCompound compound ){ super.writeToNBT( compound ); compound.setTag( "input", inputStack.serializeNBT() ); compound.setTag( "output", outputStack.serializeNBT() ); compound.setInteger( "time", time ); return compound; } public int getTime(){ return time; } public boolean hasFaery(){ return ( inputStack.getStackInSlot(0) != null ); } and here my GUI code: @Override protected void drawGuiContainerBackgroundLayer( float partialTicks, int mouseX, int mouseY ){ mc.getTextureManager().bindTexture( background ); drawTexturedModalRect( guiLeft, guiTop, 0, 0, xSize, ySize ); if( te.hasFaery() ){ float progress = 22 - ( te.getTime() * 22 / te.MAX_TIME ); drawTexturedModalRect( guiLeft + 43, guiTop + 7, 180, 0, Math.round( progress ), 15 ); } }
×
×
  • Create New...

Important Information

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