use of micdoodle8.mods.galacticraft.core.fluid.ThreadFindSeal in project Galacticraft by micdoodle8.
the class TickHandlerServer method onWorldTick.
@SubscribeEvent
public void onWorldTick(WorldTickEvent event) {
if (event.phase == Phase.START) {
final WorldServer world = (WorldServer) event.world;
CopyOnWriteArrayList<ScheduledBlockChange> changeList = TickHandlerServer.scheduledBlockChanges.get(GCCoreUtil.getDimensionID(world));
if (changeList != null && !changeList.isEmpty()) {
int blockCount = 0;
int blockCountMax = Math.max(this.MAX_BLOCKS_PER_TICK, changeList.size() / 4);
List<ScheduledBlockChange> newList = new ArrayList<ScheduledBlockChange>(Math.max(0, changeList.size() - blockCountMax));
for (ScheduledBlockChange change : changeList) {
if (++blockCount > blockCountMax) {
newList.add(change);
} else {
if (change != null) {
BlockPos changePosition = change.getChangePosition();
Block block = world.getBlockState(changePosition).getBlock();
// Only replace blocks of type BlockAir or fire - this is to prevent accidents where other mods have moved blocks
if (changePosition != null && (block instanceof BlockAir || block == Blocks.fire)) {
world.setBlockState(changePosition, change.getChangeID().getStateFromMeta(change.getChangeMeta()), change.getChangeUpdateFlag());
}
}
}
}
changeList.clear();
TickHandlerServer.scheduledBlockChanges.remove(GCCoreUtil.getDimensionID(world));
if (newList.size() > 0) {
TickHandlerServer.scheduledBlockChanges.put(GCCoreUtil.getDimensionID(world), new CopyOnWriteArrayList<ScheduledBlockChange>(newList));
}
}
CopyOnWriteArrayList<BlockVec3> torchList = TickHandlerServer.scheduledTorchUpdates.get(GCCoreUtil.getDimensionID(world));
if (torchList != null && !torchList.isEmpty()) {
for (BlockVec3 torch : torchList) {
if (torch != null) {
BlockPos pos = new BlockPos(torch.x, torch.y, torch.z);
Block b = world.getBlockState(pos).getBlock();
if (b instanceof BlockUnlitTorch) {
world.scheduleUpdate(pos, b, 2 + world.rand.nextInt(30));
}
}
}
torchList.clear();
TickHandlerServer.scheduledTorchUpdates.remove(GCCoreUtil.getDimensionID(world));
}
if (world.provider instanceof IOrbitDimension) {
try {
int dim = GCCoreUtil.getDimensionID(WorldUtil.getProviderForNameServer(((IOrbitDimension) world.provider).getPlanetToOrbit()));
int minY = ((IOrbitDimension) world.provider).getYCoordToTeleportToPlanet();
final Entity[] entityList = world.loadedEntityList.toArray(new Entity[world.loadedEntityList.size()]);
for (final Entity e : entityList) {
if (e.posY <= minY && e.worldObj == world) {
WorldUtil.transferEntityToDimension(e, dim, world, false, null);
}
}
} catch (Exception ex) {
}
}
int dimensionID = GCCoreUtil.getDimensionID(world);
if (worldsNeedingUpdate.contains(dimensionID)) {
worldsNeedingUpdate.remove(dimensionID);
for (Object obj : event.world.loadedTileEntityList) {
TileEntity tile = (TileEntity) obj;
if (tile instanceof TileEntityFluidTank) {
((TileEntityFluidTank) tile).updateClient = true;
}
}
}
} else if (event.phase == Phase.END) {
final WorldServer world = (WorldServer) event.world;
for (GalacticraftPacketHandler handler : packetHandlers) {
handler.tick(world);
}
int dimID = GCCoreUtil.getDimensionID(world);
Set<BlockPos> edgesList = TickHandlerServer.edgeChecks.get(dimID);
final HashSet<BlockPos> checkedThisTick = new HashSet<>();
if (edgesList != null && !edgesList.isEmpty()) {
List<BlockPos> edgesListCopy = new ArrayList<>();
edgesListCopy.addAll(edgesList);
for (BlockPos edgeBlock : edgesListCopy) {
if (edgeBlock != null && !checkedThisTick.contains(edgeBlock)) {
if (TickHandlerServer.scheduledForChange(dimID, edgeBlock)) {
continue;
}
ThreadFindSeal done = new ThreadFindSeal(world, edgeBlock, 0, new ArrayList<TileEntityOxygenSealer>());
checkedThisTick.addAll(done.checkedAll());
}
}
TickHandlerServer.edgeChecks.remove(GCCoreUtil.getDimensionID(world));
}
}
}
use of micdoodle8.mods.galacticraft.core.fluid.ThreadFindSeal in project Galacticraft by micdoodle8.
the class TileEntityArclamp method lightArea.
public void lightArea() {
if (this.usingBuckets.getAndSet(true) || this.usingLightList.getAndSet(true)) {
return;
}
// long time1 = System.nanoTime();
int index = 0;
Block air = Blocks.air;
Block breatheableAirID = GCBlocks.breatheableAir;
IBlockState brightAir = GCBlocks.brightAir.getDefaultState();
IBlockState brightBreatheableAir = GCBlocks.brightBreatheableAir.getDefaultState();
boolean dirty = false;
checkedClear();
HashSet<BlockVec3> airToRevert = new HashSet<>();
airToRevert.addAll(airToRestore);
LinkedList<BlockVec3> airNew = new LinkedList<>();
LinkedList<BlockVec3> currentLayer = new LinkedList<>();
LinkedList<BlockVec3> nextLayer = new LinkedList<>();
BlockVec3 thisvec = new BlockVec3(this);
currentLayer.add(thisvec);
World world = this.worldObj;
int sideskip1 = this.sideRear;
int sideskip2 = this.facingSide ^ 1;
int side, bits;
for (int i = 0; i < 6; i++) {
if (i != sideskip1 && i != sideskip2 && i != (sideskip1 ^ 1) && i != (sideskip2 ^ 1)) {
BlockVec3 onEitherSide = thisvec.newVecSide(i);
Block b = onEitherSide.getBlockIDsafe_noChunkLoad(world);
if (b != null && b.getLightOpacity() < 15) {
currentLayer.add(onEitherSide);
}
}
}
BlockVec3 inFront = new BlockVec3(this);
for (int i = 0; i < 4; i++) {
inFront = inFront.newVecSide(this.facingSide);
Block b = inFront.getBlockIDsafe_noChunkLoad(world);
if (b == null || b.getLightOpacity() == 15) {
break;
}
inFront = inFront.newVecSide(sideskip1 ^ 1);
b = inFront.getBlockIDsafe_noChunkLoad(world);
if (b != null && b.getLightOpacity() < 15) {
currentLayer.add(inFront);
} else {
break;
}
}
inFront = new BlockVec3(this).newVecSide(this.facingSide);
for (int count = 0; count < LIGHTRANGE; count++) {
for (BlockVec3 vec : currentLayer) {
// Shape the arc lamp lighted area to more of a cone in front of it
if (count > 1) {
int offset = 0;
switch(this.facingSide) {
case 0:
offset = inFront.y - vec.y;
break;
case 1:
offset = vec.y - inFront.y;
break;
case 2:
offset = inFront.z - vec.z;
break;
case 3:
offset = vec.z - inFront.z;
break;
case 4:
offset = inFront.x - vec.x;
break;
case 5:
offset = vec.x - inFront.x;
break;
}
int offset2 = 0;
switch(this.sideRear ^ 1) {
case 0:
offset2 = inFront.y - vec.y;
break;
case 1:
offset2 = vec.y - inFront.y;
break;
case 2:
offset2 = inFront.z - vec.z;
break;
case 3:
offset2 = vec.z - inFront.z;
break;
case 4:
offset2 = inFront.x - vec.x;
break;
case 5:
offset2 = vec.x - inFront.x;
break;
}
if (offset2 - 2 > offset)
offset = offset2 - 2;
if (Math.abs(vec.x - inFront.x) > offset + 2)
continue;
if (Math.abs(vec.y - inFront.y) > offset + 2)
continue;
if (Math.abs(vec.z - inFront.z) > offset + 2)
continue;
}
// Now process each layer outwards from the source, finding new blocks to light (similar to ThreadFindSeal)
// This is high performance code using our own custom HashSet (that's intBucket)
side = 0;
bits = vec.sideDoneBits;
boolean doShine = false;
do {
// and never go 'backwards'
if ((bits & (1 << side)) == 0) {
BlockVec3 sideVec = vec.newVecSide(side);
boolean toAdd = false;
if (!checkedContains(vec, side)) {
checkedAdd(sideVec);
toAdd = true;
}
Block b = sideVec.getBlockIDsafe_noChunkLoad(world);
if (b instanceof BlockAir) {
if (toAdd && side != sideskip1 && side != sideskip2) {
nextLayer.add(sideVec);
}
} else {
doShine = true;
// Glass blocks go through to the next layer as well
if (side != sideskip1 && side != sideskip2) {
if (toAdd && b != null && b.getLightOpacity(world, sideVec.toBlockPos()) == 0) {
nextLayer.add(sideVec);
}
}
}
}
side++;
} while (side < 6);
if (doShine) {
airNew.add(vec);
Block id = vec.getBlockIDsafe_noChunkLoad(world);
if (Blocks.air == id) {
this.brightenAir(world, vec, brightAir);
index = this.checkLightPartA(EnumSkyBlock.BLOCK, vec.toBlockPos(), index);
dirty = true;
} else if (id == breatheableAirID) {
this.brightenAir(world, vec, brightBreatheableAir);
index = this.checkLightPartA(EnumSkyBlock.BLOCK, vec.toBlockPos(), index);
dirty = true;
}
}
}
if (nextLayer.size() == 0) {
break;
}
currentLayer = nextLayer;
nextLayer = new LinkedList<BlockVec3>();
}
if (dirty) {
this.markDirty();
this.checkLightPartB(EnumSkyBlock.BLOCK, index);
}
// Look for any holdover bright blocks which are no longer lit (e.g. because the Arc Lamp became blocked in a tunnel)
airToRevert.removeAll(airNew);
index = 0;
dirty = false;
for (Object obj : airToRevert) {
BlockVec3 vec = (BlockVec3) obj;
this.setDarkerAir(vec);
index = this.checkLightPartA(EnumSkyBlock.BLOCK, vec.toBlockPos(), index);
this.airToRestore.remove(vec);
dirty = true;
}
if (dirty) {
this.markDirty();
this.checkLightPartB(EnumSkyBlock.BLOCK, index);
}
// long time3 = System.nanoTime();
// float total = (time3 - time1) / 1000000.0F;
// GCLog.info(" Total Time taken: " + String.format("%.2f", total) + "ms");
this.usingBuckets.set(false);
this.usingLightList.set(false);
}
Aggregations