Control panels now work when connected to multiple RS ports with the same ID

fixed rotation of Jacob's Ladders
This commit is contained in:
malte0811 2017-04-02 17:16:42 +02:00
parent 4ecab259dd
commit 3641775ff5
7 changed files with 139 additions and 51 deletions

View file

@ -24,8 +24,6 @@ import blusunrize.immersiveengineering.api.energy.wires.ImmersiveNetHandler;
import blusunrize.immersiveengineering.common.blocks.IEBlockInterfaces;
import blusunrize.immersiveengineering.common.util.Utils;
import malte0811.industrialWires.IndustrialWires;
import malte0811.industrialWires.blocks.controlpanel.PropertyComponents;
import malte0811.industrialWires.blocks.controlpanel.TileEntityPanel;
import malte0811.industrialWires.util.MiscUtils;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
@ -119,7 +117,7 @@ public abstract class BlockIWBase extends Block {
((IHasDummyBlocksIW) te).breakDummies();
}
if(te instanceof IImmersiveConnectable) {
if(!worldIn.isRemote||!Minecraft.getMinecraft().isSingleplayer())//TODO fix this in IE!!!
if(!worldIn.isRemote||!Minecraft.getMinecraft().isSingleplayer())
ImmersiveNetHandler.INSTANCE.clearAllConnectionsFor(Utils.toCC(te), worldIn, !worldIn.isRemote&&worldIn.getGameRules().getBoolean("doTileDrops"));
}
super.breakBlock(worldIn, pos, state);

View file

@ -19,6 +19,7 @@
package malte0811.industrialWires.blocks;
import blusunrize.immersiveengineering.api.ApiUtils;
import blusunrize.immersiveengineering.common.blocks.IEBlockInterfaces.IDirectionalTile;
import blusunrize.immersiveengineering.common.blocks.TileEntityIEBase;
import ic2.api.energy.event.EnergyTileLoadEvent;
import ic2.api.energy.event.EnergyTileUnloadEvent;
@ -33,6 +34,7 @@ import net.minecraft.block.Block;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
@ -50,7 +52,7 @@ import net.minecraftforge.energy.IEnergyStorage;
import javax.annotation.Nullable;
public class TileEntityJacobsLadder extends TileEntityIEBase implements ITickable, IHasDummyBlocksIW, ISyncReceiver, IEnergySink, IBlockBoundsIW {
public class TileEntityJacobsLadder extends TileEntityIEBase implements ITickable, IHasDummyBlocksIW, ISyncReceiver, IEnergySink, IBlockBoundsIW, IDirectionalTile {
public EnumFacing facing = EnumFacing.NORTH;
private DualEnergyStorage energy;
public LadderSize size;
@ -470,6 +472,36 @@ public class TileEntityJacobsLadder extends TileEntityIEBase implements ITickabl
}
}
@Override
public EnumFacing getFacing() {
return facing;
}
@Override
public void setFacing(EnumFacing facing) {
this.facing = facing;
}
@Override
public int getFacingLimitation() {
return 2;
}
@Override
public boolean mirrorFacingOnPlacement(EntityLivingBase placer) {
return true;
}
@Override
public boolean canHammerRotate(EnumFacing side, float hitX, float hitY, float hitZ, EntityLivingBase entity) {
return false;
}
@Override
public boolean canRotate(EnumFacing axis) {
return false;
}
public enum LadderSize implements IStringSerializable {
/*

View file

@ -21,7 +21,6 @@ package malte0811.industrialWires.blocks.controlpanel;
import blusunrize.immersiveengineering.api.IEProperties;
import malte0811.industrialWires.blocks.BlockIWBase;
import malte0811.industrialWires.blocks.IMetaEnum;
import malte0811.industrialWires.blocks.IPlacementCheck;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.IProperty;
import net.minecraft.block.properties.PropertyEnum;
@ -41,7 +40,7 @@ import net.minecraftforge.common.property.IUnlistedProperty;
import java.util.List;
public class BlockPanel extends BlockIWBase implements IPlacementCheck, IMetaEnum {
public class BlockPanel extends BlockIWBase implements IMetaEnum {
public static final PropertyEnum<BlockTypes_Panel> type = PropertyEnum.create("type", BlockTypes_Panel.class);
public BlockPanel() {
super(Material.IRON, "control_panel");
@ -59,11 +58,6 @@ public class BlockPanel extends BlockIWBase implements IPlacementCheck, IMetaEnu
return super.canRenderInLayer(state, layer);
}
@Override
public boolean canPlaceBlockAt(World w, BlockPos pos, ItemStack stack) {
return true;//TODO actually check for space
}
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
switch(state.getValue(type)) {

View file

@ -1,14 +1,11 @@
package malte0811.industrialWires.blocks.controlpanel;
import blusunrize.immersiveengineering.common.util.IELogger;
import com.google.common.collect.ImmutableList;
import malte0811.industrialWires.client.RawQuad;
import malte0811.industrialWires.client.panelmodel.PanelUtils;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.Vec3d;
import net.minecraftforge.client.model.ModelLoader;
import org.lwjgl.util.vector.Vector3f;
import javax.annotation.Nonnull;
@ -18,10 +15,10 @@ import java.util.List;
import java.util.function.Consumer;
public class IndicatorLight extends PanelComponent {
int rsInputId;
int rsInputChannel;
int colorA;
byte rsInput;
private int rsInputId;
private int rsInputChannel;
private int colorA;
private byte rsInput;
public IndicatorLight() {
super("indicator_light");
}
@ -32,7 +29,6 @@ public class IndicatorLight extends PanelComponent {
rsInputId = rsId;
}
@Override
protected void writeCustomNBT(NBTTagCompound nbt) {
nbt.setInteger("rsId", rsInputId);
@ -88,18 +84,20 @@ public class IndicatorLight extends PanelComponent {
public void update(TileEntityPanel tile) {
}
private TileEntityPanel panel;
private Consumer<byte[]> handler = (input)->{
if (input[rsInputChannel]!=rsInput) {
rsInput = input[rsInputChannel];
panel.markDirty();
panel.triggerRenderUpdate();
}
};
@Nullable
@Override
public Consumer<byte[]> getRSInputHandler(int id, TileEntityPanel panel) {
if (id==rsInputId) {
return (input)->{
if (input[rsInputChannel]!=rsInput) {
rsInput = input[rsInputChannel];
panel.markDirty();
panel.triggerRenderUpdate();
}
};
this.panel = panel;
return handler;
}
return null;
}
@ -123,5 +121,4 @@ public class IndicatorLight extends PanelComponent {
result = 31 * result + (int) rsInput;
return result;
}
}
//TODO optimize RS net in IE, updates multiple times per tick. 0-length pulses?
}

View file

@ -27,7 +27,9 @@ import org.lwjgl.util.vector.Vector3f;
import javax.annotation.Nonnull;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.function.BiConsumer;
public class LightedButton extends PanelComponent {
@ -38,7 +40,7 @@ public class LightedButton extends PanelComponent {
public int rsOutputChannel;
private AxisAlignedBB aabb;
private int ticksTillOff;
private BiConsumer<Integer, Byte> rsOut;
private Set<BiConsumer<Integer, Byte>> rsOut = new HashSet<>();
public LightedButton() {
super("lightedButton");
}
@ -130,8 +132,15 @@ public class LightedButton extends PanelComponent {
@Override
public void registerRSOutput(int id, @Nonnull BiConsumer<Integer, Byte> out) {
if (id==rsOutputId) {
rsOut = out;
rsOut.accept(rsOutputChannel, (byte) (active?15:0));
rsOut.add(out);
out.accept(rsOutputChannel, (byte) (active?15:0));
}
}
@Override
public void unregisterRSOutput(int id, @Nonnull BiConsumer<Integer, Byte> out) {
if (id==rsOutputId) {
rsOut.remove(out);
}
}
@ -139,8 +148,8 @@ public class LightedButton extends PanelComponent {
active = on;
tile.markDirty();
tile.triggerRenderUpdate();
if (rsOut!=null) {
rsOut.accept(rsOutputChannel, (byte)(active?15:0));
for (BiConsumer<Integer, Byte> rs:rsOut) {
rs.accept(rsOutputChannel, (byte)(active?15:0));
}
}

View file

@ -20,7 +20,6 @@ package malte0811.industrialWires.blocks.controlpanel;
import blusunrize.immersiveengineering.common.blocks.IEBlockInterfaces.IDirectionalTile;
import blusunrize.immersiveengineering.common.blocks.IEBlockInterfaces.IPlayerInteraction;
import blusunrize.immersiveengineering.common.util.IELogger;
import blusunrize.immersiveengineering.common.util.chickenbones.Matrix4;
import malte0811.industrialWires.blocks.IBlockBoundsIW;
import malte0811.industrialWires.blocks.TileEntityIWBase;
@ -33,7 +32,6 @@ import net.minecraft.item.EnumDyeColor;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList;
import net.minecraft.nbt.NBTTagLong;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
@ -46,15 +44,15 @@ import org.apache.commons.lang3.tuple.ImmutablePair;
import org.apache.commons.lang3.tuple.Pair;
import javax.annotation.Nullable;
import java.util.*;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
public class TileEntityPanel extends TileEntityIWBase implements IDirectionalTile, IBlockBoundsIW, IPlayerInteraction, ITickable {
private PropertyComponents.PanelRenderProperties components = new PropertyComponents.PanelRenderProperties();
boolean firstTick = true;
private boolean firstTick = true;
// non-rendered properties
//TODO does the lambda stuff cause GC issues?
Set<TileEntityRSPanelConn> rsPorts = new HashSet<>();
{
for (int i = 0;i<16;i++) {
int color = EnumDyeColor.byMetadata(i).getMapColor().colorValue;
@ -87,8 +85,7 @@ public class TileEntityPanel extends TileEntityIWBase implements IDirectionalTil
for (BlockPos bp:parts) {
TileEntity te = worldObj.getTileEntity(bp);
if (te instanceof TileEntityRSPanelConn) {
//TODO deal with people adding 2 RS ports with the same ID!
((TileEntityRSPanelConn) te).requestRSConn(this);
((TileEntityRSPanelConn) te).registerPanel(this);
}
}
firstTick = false;
@ -194,6 +191,7 @@ public class TileEntityPanel extends TileEntityIWBase implements IDirectionalTil
max = mat.apply(max);
return new AxisAlignedBB(min, max);
}
@Nullable
public Pair<PanelComponent, RayTraceResult> getSelectedComponent(EntityPlayer player, Vec3d hit, boolean hitAbs) {
Matrix4 mat = components.getPanelTopTransform();
@ -223,4 +221,27 @@ public class TileEntityPanel extends TileEntityIWBase implements IDirectionalTil
worldObj.notifyBlockUpdate(pos,state,state,3);
worldObj.addBlockEvent(pos, state.getBlock(), 255, 0);
}
public void registerRS(TileEntityRSPanelConn te) {
rsPorts.add(te);
}
public void unregisterRS(TileEntityRSPanelConn te) {
rsPorts.remove(te);
}
@Override
public void onChunkUnload() {
super.onChunkUnload();
for (TileEntityRSPanelConn rs:rsPorts) {
rs.unregisterPanel(this, true);
}
}
@Override
public void invalidate() {
super.invalidate();
for (TileEntityRSPanelConn rs:rsPorts) {
rs.unregisterPanel(this, true);
}
}
}

View file

@ -21,6 +21,7 @@ import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
public class TileEntityRSPanelConn extends TileEntityImmersiveConnectable implements IRedstoneConnector, ITickable {
@ -28,6 +29,7 @@ public class TileEntityRSPanelConn extends TileEntityImmersiveConnectable implem
private boolean dirty = true;
private byte[] oldInput = new byte[16];
private Set<Consumer<byte[]>> changeListeners = new HashSet<>();
private Set<TileEntityPanel> connectedPanels = new HashSet<>();
@Nonnull
private RedstoneWireNetwork network = new RedstoneWireNetwork().add(this);
private boolean hasConn = false;
@ -50,7 +52,7 @@ public class TileEntityRSPanelConn extends TileEntityImmersiveConnectable implem
for (BlockPos bp:parts) {
TileEntity te = worldObj.getTileEntity(bp);
if (te instanceof TileEntityPanel) {
requestRSConn(((TileEntityPanel) te));
registerPanel(((TileEntityPanel) te));
}
}
}
@ -76,19 +78,38 @@ public class TileEntityRSPanelConn extends TileEntityImmersiveConnectable implem
id = in.getInteger("rsId");
}
public void requestRSConn(TileEntityPanel panel) {
private BiConsumer<Integer, Byte> rsOut = (channel, value)->{
if (value!=out[channel]) {
dirty = true;
out[channel] = value;
}
};
public void registerPanel(TileEntityPanel panel) {
PropertyComponents.PanelRenderProperties p = panel.getComponents();
for (PanelComponent pc:p) {
Consumer<byte[]> listener = pc.getRSInputHandler(id, panel);
if (listener!=null) {
changeListeners.add(listener);
}
pc.registerRSOutput(id, (channel, value)->{
if (value!=out[channel]) {
dirty = true;
out[channel] = value;
}
});
pc.registerRSOutput(id, rsOut);
}
panel.registerRS(this);
connectedPanels.add(panel);
}
public void unregisterPanel(TileEntityPanel panel, boolean remove) {
PropertyComponents.PanelRenderProperties p = panel.getComponents();
for (PanelComponent pc:p) {
Consumer<byte[]> listener = pc.getRSInputHandler(id, panel);
if (listener!=null) {
changeListeners.remove(listener);
}
pc.unregisterRSOutput(id, rsOut);
}
panel.unregisterRS(this);
if (remove) {
connectedPanels.remove(panel);
}
}
@ -168,4 +189,20 @@ public class TileEntityRSPanelConn extends TileEntityImmersiveConnectable implem
public Vec3d getConnectionOffset(ImmersiveNetHandler.Connection connection) {
return new Vec3d(.5, .5, .5);//TODO better values
}
@Override
public void onChunkUnload() {
super.onChunkUnload();
for (TileEntityPanel panel:connectedPanels) {
unregisterPanel(panel, false);
}
}
@Override
public void invalidate() {
super.invalidate();
for (TileEntityPanel panel:connectedPanels) {
unregisterPanel(panel, false);
}
}
}