Merge pull request #509 from nevercast/bug-pipe-sync

Better Liquid Pipe Client Syncronization
This commit is contained in:
CovertJaguar 2012-12-15 01:04:16 -08:00
commit ff3312e1bb
3 changed files with 108 additions and 66 deletions

View file

@ -91,6 +91,8 @@ public class BuildCraftCore {
public static int itemLifespan = 1200;
public static int updateFactor = 10;
public static long longUpdateFactor = 40;
public static BuildCraftConfiguration mainConfiguration;
@ -188,6 +190,10 @@ public class BuildCraftCore {
Property factor = BuildCraftCore.mainConfiguration.get( Configuration.CATEGORY_GENERAL,"network.updateFactor", 10);
factor.comment = "increasing this number will decrease network update frequency, useful for overloaded servers";
updateFactor = factor.getInt(10);
Property longFactor = BuildCraftCore.mainConfiguration.get( Configuration.CATEGORY_GENERAL,"network.stateRefreshPeriod", 40);
longFactor.comment = "delay between full client sync packets, increasing it saves bandwidth, decreasing makes for better client syncronization.";
longUpdateFactor = longFactor.getInt(40);
String powerFrameworkClassName = "buildcraft.energy.PneumaticPowerFramework";
if (!forcePneumaticPower)

View file

@ -20,6 +20,7 @@ import buildcraft.core.utils.Utils;
import buildcraft.transport.network.PacketLiquidUpdate;
import java.util.BitSet;
import net.minecraft.src.NBTTagCompound;
import net.minecraft.src.Packet;
import net.minecraft.src.TileEntity;
import net.minecraftforge.common.ForgeDirection;
import net.minecraftforge.liquids.ILiquidTank;
@ -151,6 +152,7 @@ public class PipeTransportLiquids extends PipeTransport implements ITankContaine
private final short[] outputCooldown = new short[] {0, 0, 0, 0, 0, 0 };
private final SafeTimeTracker tracker = new SafeTimeTracker();
private int clientSyncCounter = 0;
public PipeTransportLiquids() {
@ -195,76 +197,104 @@ public class PipeTransportLiquids extends PipeTransport implements ITankContaine
if (tracker.markTimeIfDelay(worldObj, BuildCraftCore.updateFactor)) {
boolean changed = false;
BitSet delta = new BitSet(21);
if (initClient > 0) {
initClient--;
if (initClient == 1) {
changed = true;
delta.set(0, 21);
}
boolean init = false;
if(++clientSyncCounter > BuildCraftCore.longUpdateFactor){
clientSyncCounter = 0;
init = true;
}
for (ForgeDirection dir : orientations) {
LiquidStack current = internalTanks[dir.ordinal()].getLiquid();
LiquidStack prev = renderCache[dir.ordinal()];
if (prev == null && current == null) {
continue;
}
if (prev == null && current != null) {
changed = true;
renderCache[dir.ordinal()] = current.copy();
delta.set(dir.ordinal() * 3 + 0);
delta.set(dir.ordinal() * 3 + 1);
delta.set(dir.ordinal() * 3 + 2);
continue;
}
if (prev != null && current == null) {
changed = true;
renderCache[dir.ordinal()] = null;
delta.set(dir.ordinal() * 3 + 0);
delta.set(dir.ordinal() * 3 + 1);
delta.set(dir.ordinal() * 3 + 2);
continue;
}
if (prev.itemID != current.itemID) {
changed = true;
renderCache[dir.ordinal()].itemID = current.itemID;
delta.set(dir.ordinal() * 3 + 0);
}
if (prev.itemMeta != current.itemMeta) {
changed = true;
renderCache[dir.ordinal()].itemMeta = current.itemMeta;
delta.set(dir.ordinal() * 3 + 1);
}
int displayQty = (prev.amount * 4 + current.amount) / 5;
if (displayQty == 0 && current.amount > 0) {
displayQty = current.amount;
}
displayQty = Math.min(getCapacity(), displayQty);
if (prev.amount != displayQty) {
changed = true;
renderCache[dir.ordinal()].amount = displayQty;
delta.set(dir.ordinal() * 3 + 2);
}
}
if (changed) {
PacketLiquidUpdate packet = new PacketLiquidUpdate(xCoord, yCoord, zCoord);
packet.renderCache = this.renderCache;
packet.delta = delta;
PacketLiquidUpdate packet = computeLiquidUpdate(init, true);
if(packet != null){
CoreProxy.proxy.sendToPlayers(packet.getPacket(), worldObj, xCoord, yCoord, zCoord, DefaultProps.PIPE_CONTENTS_RENDER_DIST);
}
}
}
/**
* Computes the PacketLiquidUpdate packet for transmission to a client
* @param initPacket everything is sent, no delta stuff ( first packet )
* @param persistChange The render cache change is persisted
* @return PacketLiquidUpdate liquid update packet
*/
private PacketLiquidUpdate computeLiquidUpdate(boolean initPacket, boolean persistChange){
boolean changed = false;
BitSet delta = new BitSet(21);
if (initClient > 0) {
initClient--;
if (initClient == 1) {
changed = true;
delta.set(0, 21);
}
}
LiquidStack[] renderCache = this.renderCache.clone();
for (ForgeDirection dir : orientations) {
LiquidStack current = internalTanks[dir.ordinal()].getLiquid();
LiquidStack prev = renderCache[dir.ordinal()];
if (prev == null && current == null) {
continue;
}
if (prev == null && current != null) {
changed = true;
renderCache[dir.ordinal()] = current.copy();
delta.set(dir.ordinal() * 3 + 0);
delta.set(dir.ordinal() * 3 + 1);
delta.set(dir.ordinal() * 3 + 2);
continue;
}
if (prev != null && current == null) {
changed = true;
renderCache[dir.ordinal()] = null;
delta.set(dir.ordinal() * 3 + 0);
delta.set(dir.ordinal() * 3 + 1);
delta.set(dir.ordinal() * 3 + 2);
continue;
}
if (prev.itemID != current.itemID || initPacket) {
changed = true;
renderCache[dir.ordinal()].itemID = current.itemID;
delta.set(dir.ordinal() * 3 + 0);
}
if (prev.itemMeta != current.itemMeta || initPacket) {
changed = true;
renderCache[dir.ordinal()].itemMeta = current.itemMeta;
delta.set(dir.ordinal() * 3 + 1);
}
int displayQty = (prev.amount * 4 + current.amount) / 5;
if (displayQty == 0 && current.amount > 0 || initPacket) {
displayQty = current.amount;
}
displayQty = Math.min(getCapacity(), displayQty);
if (prev.amount != displayQty || initPacket) {
changed = true;
renderCache[dir.ordinal()].amount = displayQty;
delta.set(dir.ordinal() * 3 + 2);
}
}
if(persistChange){
this.renderCache = renderCache;
}
if (changed || initPacket) {
PacketLiquidUpdate packet = new PacketLiquidUpdate(xCoord, yCoord, zCoord, initPacket);
packet.renderCache = renderCache;
packet.delta = delta;
return packet;
}
return null;
}
/**
* Initializes client
@ -272,10 +302,11 @@ public class PipeTransportLiquids extends PipeTransport implements ITankContaine
@Override
public void sendDescriptionPacket() {
super.sendDescriptionPacket();
initClient = 6;
}
@Override
public void readFromNBT(NBTTagCompound nbttagcompound) {
super.readFromNBT(nbttagcompound);

View file

@ -22,6 +22,11 @@ public class PacketLiquidUpdate extends PacketCoordinates {
public PacketLiquidUpdate(int xCoord, int yCoord, int zCoord) {
super(PacketIds.PIPE_LIQUID, xCoord, yCoord, zCoord);
}
public PacketLiquidUpdate(int xCoord, int yCoord, int zCoord, boolean chunkPacket) {
super(PacketIds.PIPE_LIQUID, xCoord, yCoord, zCoord);
this.isChunkDataPacket = chunkPacket;
}
public PacketLiquidUpdate() {
}