From 03f284948e965bdfcecbb55e2c3ff711e6a6ec93 Mon Sep 17 00:00:00 2001 From: LemADEC Date: Mon, 27 Jun 2016 03:22:23 +0200 Subject: [PATCH] Implemented projector LUA API (wip) Fixed SMP support Fixed CME when changing shape parameters Improved projector guide messages Fixed server lag issue (wip) --- .../forcefield/BlockForceFieldRelay.java | 6 +- .../TileEntityAbstractForceField.java | 4 +- .../TileEntityForceFieldProjector.java | 101 ++++++++++++++---- .../warpdrive/data/EnumForceFieldUpgrade.java | 26 ++--- .../cr0s/warpdrive/data/ForceFieldSetup.java | 2 +- 5 files changed, 100 insertions(+), 39 deletions(-) diff --git a/src/main/java/cr0s/warpdrive/block/forcefield/BlockForceFieldRelay.java b/src/main/java/cr0s/warpdrive/block/forcefield/BlockForceFieldRelay.java index 30567fd3..a4b7deb8 100644 --- a/src/main/java/cr0s/warpdrive/block/forcefield/BlockForceFieldRelay.java +++ b/src/main/java/cr0s/warpdrive/block/forcefield/BlockForceFieldRelay.java @@ -18,19 +18,19 @@ import net.minecraft.world.World; public class BlockForceFieldRelay extends BlockAbstractForceField { @SideOnly(Side.CLIENT) - private final IIcon[] icons; + private IIcon[] icons; public BlockForceFieldRelay(final byte tier) { super(tier, Material.iron); isRotating = false; setBlockName("warpdrive.forcefield.relay" + tier); setBlockTextureName("warpdrive:forcefield/relay"); - - icons = new IIcon[EnumForceFieldUpgrade.length + 1]; } @Override public void registerBlockIcons(IIconRegister iconRegister) { + icons = new IIcon[EnumForceFieldUpgrade.length + 1]; + for (EnumForceFieldUpgrade enumForceFieldUpgrade : EnumForceFieldUpgrade.values()) { if (enumForceFieldUpgrade.maxCountOnRelay > 0) { icons[enumForceFieldUpgrade.ordinal()] = iconRegister.registerIcon("warpdrive:forcefield/relay" + "_" + enumForceFieldUpgrade.unlocalizedName); diff --git a/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityAbstractForceField.java b/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityAbstractForceField.java index 21f55bb7..c4a4b9f3 100644 --- a/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityAbstractForceField.java +++ b/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityAbstractForceField.java @@ -112,8 +112,8 @@ public class TileEntityAbstractForceField extends TileEntityAbstractEnergy imple public String getStatus() { String strEnergyStatus = getEnergyStatus(); return (worldObj != null ? StatCollector.translateToLocalFormatted("warpdrive.guide.prefix", getBlockType().getLocalizedName()) : "") - + getBeamFrequencyStatus() - + (strEnergyStatus.isEmpty() ? "" : "\n" + strEnergyStatus); + + (strEnergyStatus.isEmpty() ? "" : "\n" + strEnergyStatus + + "\n" + getBeamFrequencyStatus()); } @Override diff --git a/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityForceFieldProjector.java b/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityForceFieldProjector.java index d269ca9c..207cf113 100644 --- a/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityForceFieldProjector.java +++ b/src/main/java/cr0s/warpdrive/block/forcefield/TileEntityForceFieldProjector.java @@ -6,6 +6,11 @@ import cr0s.warpdrive.api.IForceFieldShape; import cr0s.warpdrive.config.*; import cr0s.warpdrive.config.Dictionary; import cr0s.warpdrive.data.*; +import dan200.computercraft.api.lua.ILuaContext; +import dan200.computercraft.api.peripheral.IComputerAccess; +import li.cil.oc.api.machine.Arguments; +import li.cil.oc.api.machine.Callback; +import li.cil.oc.api.machine.Context; import net.minecraft.block.Block; import net.minecraft.block.BlockLiquid; import net.minecraft.block.BlockStaticLiquid; @@ -29,7 +34,7 @@ import java.util.concurrent.atomic.AtomicBoolean; public class TileEntityForceFieldProjector extends TileEntityAbstractForceField { private static final int PROJECTOR_MAX_ENERGY_STORED = 10000; - private static final int PROJECTOR_COOLDOWN_TICKS = 20; + private static final int PROJECTOR_COOLDOWN_TICKS = 100; public static final int PROJECTOR_PROJECTION_UPDATE_TICKS = 8; private static final int PROJECTOR_SETUP_TICKS = 20; private static final int PROJECTOR_SOUND_UPDATE_TICKS = 100; @@ -76,7 +81,8 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField peripheralName = "warpdriveForceFieldProjector"; addMethods(new String[] { - "status" // isConnected, isPowered, shape + "rotation", + "state" }); for (EnumForceFieldUpgrade enumForceFieldUpgrade : EnumForceFieldUpgrade.values()) { @@ -243,11 +249,15 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField return calculated_forceField.contains(vector); } - private Set getInteriorPoints() { - if (!isCalculated()) { - throw new ConcurrentModificationException("Calculation ongoing..."); + private boolean isPartOfInterior(VectorI vector) { + if (!isEnabled || !isValid()) { + return false; } - return calculated_interiorField; + if (!isCalculated()) { + return false; + } + // only consider the forcefield interior + return calculated_interiorField.contains(vector); } private void projectForceField() { @@ -296,7 +306,7 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField // skip if fusion upgrade is present and it's inside another projector area if (forceFieldSetup.hasFusion) { for (TileEntityForceFieldProjector projector : forceFieldSetup.projectors) { - if (projector.getInteriorPoints().contains(vector)) { + if (projector.isPartOfInterior(vector)) { doProjectThisBlock = false; break; } @@ -359,7 +369,7 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField if (doProjectThisBlock) { if (forceFieldSetup.breaking_maxHardness > 0) { doProjectThisBlock = ! isBlockBreakCanceled(null, worldObj, vector.x, vector.y, vector.z); - } else { + } else if (!(block instanceof BlockForceField)) { doProjectThisBlock = ! isBlockPlaceCanceled(null, worldObj, vector.x, vector.y, vector.z, WarpDrive.blockForceFields[tier - 1], metadataForceField); } } @@ -571,6 +581,23 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField } } + public EnumForceFieldShape getShape() { + if (shape == null) { + return EnumForceFieldShape.NONE; + } + return shape; + } + + void setShape(EnumForceFieldShape shape) { + this.shape = shape; + cache_forceFieldSetup = null; + isDirty.set(true); + markDirty(); + if (worldObj != null) { + destroyForceField(false); + } + } + @Override public boolean mountUpgrade(Object upgrade) { if (super.mountUpgrade(upgrade)) { @@ -693,21 +720,55 @@ public class TileEntityForceFieldProjector extends TileEntityAbstractForceField return true; } - public EnumForceFieldShape getShape() { - if (shape == null) { - return EnumForceFieldShape.NONE; - } - return shape; + // OpenComputer callback methods + @Callback + @cpw.mods.fml.common.Optional.Method(modid = "OpenComputers") + public Object[] state(Context context, Arguments arguments) { + return state(); } - void setShape(EnumForceFieldShape shape) { - this.shape = shape; - cache_forceFieldSetup = null; - isDirty.set(true); - markDirty(); - if (worldObj != null) { - destroyForceField(false); + @Callback + @cpw.mods.fml.common.Optional.Method(modid = "OpenComputers") + public Object[] rotation(Context context, Arguments arguments) { + if (arguments.count() == 1) { + setRotation((float)arguments.checkDouble(0), rotationPitch, rotationRoll); + } else if (arguments.count() == 2) { + setRotation((float)arguments.checkDouble(0), (float)arguments.checkDouble(1), rotationRoll); + } else if (arguments.count() == 3) { + setRotation((float)arguments.checkDouble(0), (float)arguments.checkDouble(1), (float)arguments.checkDouble(2)); } + return new Float[] { rotationYaw, rotationPitch, rotationRoll }; + } + + // Common OC/CC methods + private Object[] state() { // isConnected, isPowered, shape + int energy = getEnergyStored(); + String status = getStatus(); + return new Object[] { status, isEnabled, isConnected, isPowered, getShape().name(), energy }; + } + + // ComputerCraft IPeripheral methods implementation + @Override + @cpw.mods.fml.common.Optional.Method(modid = "ComputerCraft") + public Object[] callMethod(IComputerAccess computer, ILuaContext context, int method, Object[] arguments) { + String methodName = getMethodName(method); + + switch (methodName) { + case "rotation": + if (arguments.length == 1) { + setRotation(toFloat(arguments[0]), rotationPitch, rotationRoll); + } else if (arguments.length == 2) { + setRotation(toFloat(arguments[0]), toFloat(arguments[1]), rotationRoll); + } else if (arguments.length == 3) { + setRotation(toFloat(arguments[0]), toFloat(arguments[1]), toFloat(arguments[2])); + } + return new Float[] { rotationYaw, rotationPitch, rotationRoll }; + + case "state": + return state(); + } + + return super.callMethod(computer, context, method, arguments); } private class ThreadCalculation extends Thread { diff --git a/src/main/java/cr0s/warpdrive/data/EnumForceFieldUpgrade.java b/src/main/java/cr0s/warpdrive/data/EnumForceFieldUpgrade.java index 3bd9e88a..be86ea1d 100644 --- a/src/main/java/cr0s/warpdrive/data/EnumForceFieldUpgrade.java +++ b/src/main/java/cr0s/warpdrive/data/EnumForceFieldUpgrade.java @@ -15,20 +15,20 @@ public enum EnumForceFieldUpgrade implements IForceFieldUpgrade, IForceFieldUpgr // Upgrade - Compatibility - ----- Value ----- -- Scan speed -- -- Place speed -- ------- Energy costs ------- comment // name projector relay incr. cap minimum maximum minimum maximum startup scan place entity NONE ("none" , 0, 0, 0.0F, 0.0F, 0.000F, 0.000F, 0.000F, 0.000F, 0.0F, 0.000F, 0.000F, 0.0F, ""), - BREAKING ("breaking" , 0, 1, 1.0F, 25.0F, 0.400F, 0.500F, 0.010F, 0.100F, 70.0F, 0.020F, 1.000F, 0.0F, "value is hardness level"), - CAMOUFLAGE ("camouflage" , 0, 1, 1.0F, 3.0F, 0.600F, 0.850F, 0.700F, 0.950F, 100.0F, 0.100F, 0.300F, 0.0F, "value is boolean"), - COOLING ("cooling" , 3, 1, 30.0F, 300.0F, 0.000F, 0.000F, 0.900F, 0.900F, 15.0F, 0.020F, 0.500F, 10.0F, "value is heat units"), - FUSION ("fusion" , 1, 1, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 100.0F, 0.050F, 0.050F, 0.0F, "value is boolean"), - HEATING ("heating" , 3, 1, 100.0F, 10000.0F, 0.000F, 0.000F, 0.900F, 0.900F, 15.0F, 0.100F, 1.000F, 5.0F, "value is heat units"), - INVERSION ("inversion" , 1, 0, 1.0F, 1.0F, 0.250F, 0.250F, 0.000F, 0.000F, 150.0F, 0.050F, 0.050F, 1.0F, "value is boolean"), - PUMPING ("pumping" , 0, 1, 1000.0F, 50000.0F, 0.800F, 1.000F, 0.400F, 1.000F, 80.0F, 0.010F, 0.500F, 0.0F, "value is viscosity"), - RANGE ("range" , 4, 1, 8.0F, 56.0F, 1.100F, 0.800F, 1.100F, 0.800F, 1.0F, 0.100F, 0.250F, 4.0F, "value is bonus blocks"), + BREAKING ("breaking" , 0, 1, 1.0F, 25.0F, 0.400F, 0.500F, 0.010F, 0.100F, 70.0F, 0.080F, 4.000F, 0.0F, "value is hardness level"), + CAMOUFLAGE ("camouflage" , 0, 1, 1.0F, 3.0F, 0.600F, 0.850F, 0.700F, 0.950F, 100.0F, 0.400F, 1.200F, 0.0F, "value is boolean"), + COOLING ("cooling" , 3, 1, 30.0F, 300.0F, 0.000F, 0.000F, 0.900F, 0.900F, 15.0F, 0.060F, 1.500F, 100.0F, "value is heat units"), + FUSION ("fusion" , 1, 1, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 100.0F, 0.150F, 0.150F, 0.0F, "value is boolean"), + HEATING ("heating" , 3, 1, 100.0F, 10000.0F, 0.000F, 0.000F, 0.900F, 0.900F, 15.0F, 0.300F, 3.000F, 50.0F, "value is heat units"), + INVERSION ("inversion" , 1, 0, 1.0F, 1.0F, 0.250F, 0.250F, 0.000F, 0.000F, 150.0F, 0.150F, 0.150F, 10.0F, "value is boolean"), + PUMPING ("pumping" , 0, 1, 1000.0F, 50000.0F, 0.800F, 1.000F, 0.400F, 1.000F, 80.0F, 0.050F, 1.500F, 0.0F, "value is viscosity"), + RANGE ("range" , 4, 1, 8.0F, 56.0F, 1.100F, 0.800F, 1.100F, 0.800F, 1.0F, 0.300F, 0.750F, 40.0F, "value is bonus blocks"), ROTATION ("rotation" , 1, 0, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 10.0F, 0.000F, 0.000F, 0.0F, "value is boolean"), - SHOCK ("shock" , 3, 1, 1.0F, 10.0F, 0.800F, 0.800F, 0.800F, 0.800F, 30.0F, 0.100F, 2.000F, 30.0F, "value is damage points"), - SILENCER ("silencer" , 1, 0, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 0.0F, 0.010F, 0.020F, 0.0F, "value is boolean"), - SPEED ("speed" , 4, 1, 1.0F, 20.0F, 1.250F, 6.000F, 1.200F, 5.000F, 20.0F, 0.100F, 1.000F, 5.0F, "value is not used (just a counter)"), - STABILIZATION("stabilization", 0, 1, 1.0F, 6.0F, 0.450F, 0.550F, 0.050F, 0.150F, 40.0F, 0.100F, 1.000F, 0.0F, "value is boolean"), - THICKNESS ("thickness" , 5, 1, 0.2F, 1.0F, 0.800F, 1.600F, 0.000F, 0.000F, 10.0F, 0.100F, 1.000F, 1.0F, "value is bonus ratio"), + SHOCK ("shock" , 3, 1, 1.0F, 10.0F, 0.800F, 0.800F, 0.800F, 0.800F, 30.0F, 0.300F, 4.000F, 300.0F, "value is damage points"), + SILENCER ("silencer" , 1, 0, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 0.0F, 0.030F, 0.060F, 0.0F, "value is boolean"), + SPEED ("speed" , 4, 1, 1.0F, 20.0F, 1.250F, 6.000F, 1.200F, 5.000F, 20.0F, 0.100F, 1.000F, 50.0F, "value is not used (just a counter)"), + STABILIZATION("stabilization", 0, 1, 1.0F, 6.0F, 0.450F, 0.550F, 0.050F, 0.150F, 40.0F, 0.250F, 3.200F, 0.0F, "value is boolean"), + THICKNESS ("thickness" , 5, 1, 0.2F, 1.0F, 0.800F, 1.600F, 0.000F, 0.000F, 10.0F, 0.450F, 2.400F, 10.0F, "value is bonus ratio"), TRANSLATION ("translation" , 1, 0, 1.0F, 1.0F, 0.000F, 0.000F, 0.000F, 0.000F, 10.0F, 0.000F, 0.000F, 0.0F, "value is boolean"), ; diff --git a/src/main/java/cr0s/warpdrive/data/ForceFieldSetup.java b/src/main/java/cr0s/warpdrive/data/ForceFieldSetup.java index 0e082fca..4fe0c5e8 100644 --- a/src/main/java/cr0s/warpdrive/data/ForceFieldSetup.java +++ b/src/main/java/cr0s/warpdrive/data/ForceFieldSetup.java @@ -184,7 +184,7 @@ public class ForceFieldSetup extends GlobalPosition { if (isValidCamouflage(blockCandidate)) { blockCamouflage = blockCandidate; metadataCamouflage = tileEntity.getWorldObj().getBlockMetadata(tileEntity.xCoord, tileEntity.yCoord + 1, tileEntity.zCoord); - colorMultiplierCamouflage = blockCandidate.colorMultiplier(tileEntity.getWorldObj(), tileEntity.xCoord, tileEntity.yCoord + 1, tileEntity.zCoord); + colorMultiplierCamouflage = 0x808080; // blockCandidate.colorMultiplier(tileEntity.getWorldObj(), tileEntity.xCoord, tileEntity.yCoord + 1, tileEntity.zCoord); lightCamouflage = blockCandidate.getLightValue(tileEntity.getWorldObj(), tileEntity.xCoord, tileEntity.yCoord + 1, tileEntity.zCoord); } }