From 1953f52da1ece0feb56dea20592c1b86616b31a5 Mon Sep 17 00:00:00 2001 From: Aikar Date: Tue, 21 Jun 2016 19:08:09 -0400 Subject: SPIGOT-2439: Consistently fire Chunk(Load|Unload)Event Clean up implementation and firing of both of these events by routing both unload and load behaviors to consistent method calls. This fixes issues where a few places would not call Load or Unload events when it should have. Additionally, reduces diff by moving the neighbor marking code into these consistent points. Additional benefits of the change include improving the neighbor marking methods to use getChunkIfLoaded instead of getLoadedChunkAt in some places, as the latter will cause chunks to be marked active and not unload. Finally, this also updates CraftWorld.loadChunk to use the new methods, as the previous logic did not properly handle the new unload queue. --- .../java/org/bukkit/craftbukkit/CraftWorld.java | 88 +++++----------------- .../craftbukkit/chunkio/ChunkIOProvider.java | 22 +----- 2 files changed, 21 insertions(+), 89 deletions(-) (limited to 'src') diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java index 3ee0b91e..2fe3eae8 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java @@ -187,47 +187,26 @@ public class CraftWorld implements World { return false; } - return unloadChunk0(x, z, save, safe); + return unloadChunk0(x, z, save); } - private boolean unloadChunk0(int x, int z, boolean save, boolean safe) { - net.minecraft.server.Chunk chunk = world.getChunkProviderServer().getChunkAt(x, z); - if (chunk.mustSave) { // If chunk had previously been queued to save, must do save to avoid loss of that data - save = true; - } - - chunk.removeEntities(); // Always remove entities - even if discarding, need to get them out of world table - - if (save) { - world.getChunkProviderServer().saveChunk(chunk); - world.getChunkProviderServer().saveChunkNOP(chunk); - } - - world.getChunkProviderServer().unloadQueue.remove(ChunkCoordIntPair.a(x, z)); - world.getChunkProviderServer().chunks.remove(ChunkCoordIntPair.a(x, z)); - - // Update neighbor counts - for (int xx = -2; xx < 3; xx++) { - for (int zz = -2; zz < 3; zz++) { - if (xx == 0 && zz == 0) { - continue; - } - - net.minecraft.server.Chunk neighbor = world.getChunkProviderServer().getChunkIfLoaded(chunk.locX + x, chunk.locZ + z); - if (neighbor != null) { - neighbor.setNeighborUnloaded(-xx, -zz); - chunk.setNeighborUnloaded(xx, zz); - } - } + private boolean unloadChunk0(int x, int z, boolean save) { + net.minecraft.server.Chunk chunk = world.getChunkProviderServer().getChunkIfLoaded(x, z); + if (chunk == null) { + return true; } - return true; + // If chunk had previously been queued to save, must do save to avoid loss of that data + return world.getChunkProviderServer().unloadChunk(chunk, chunk.mustSave || save); } public boolean regenerateChunk(int x, int z) { - unloadChunk0(x, z, false, false); + if (!unloadChunk0(x, z, false)) { + return false; + } - world.getChunkProviderServer().unloadQueue.remove(ChunkCoordIntPair.a(x, z)); + final long chunkKey = ChunkCoordIntPair.a(x, z); + world.getChunkProviderServer().unloadQueue.remove(chunkKey); net.minecraft.server.Chunk chunk = null; @@ -237,9 +216,14 @@ public class CraftWorld implements World { playerChunk.chunk = chunk; } - chunkLoadPostProcess(chunk, x, z); + if (chunk != null) { + world.getChunkProviderServer().chunks.put(chunkKey, chunk); - refreshChunk(x, z); + chunk.addEntities(); + chunk.loadNearby(world.getChunkProviderServer(), world.getChunkProviderServer().chunkGenerator, true); + + refreshChunk(x, z); + } return chunk != null; } @@ -275,39 +259,7 @@ public class CraftWorld implements World { return world.getChunkProviderServer().getChunkAt(x, z) != null; } - world.getChunkProviderServer().unloadQueue.remove(ChunkCoordIntPair.a(x, z)); - net.minecraft.server.Chunk chunk = world.getChunkProviderServer().chunks.get(ChunkCoordIntPair.a(x, z)); - - if (chunk == null) { - chunk = world.getChunkProviderServer().getOrLoadChunkAt(x, z); - } - return chunk != null; - } - - private void chunkLoadPostProcess(net.minecraft.server.Chunk chunk, int cx, int cz) { - if (chunk != null) { - world.getChunkProviderServer().chunks.put(ChunkCoordIntPair.a(cx, cz), chunk); - - chunk.addEntities(); - - // Update neighbor counts - for (int x = -2; x < 3; x++) { - for (int z = -2; z < 3; z++) { - if (x == 0 && z == 0) { - continue; - } - - net.minecraft.server.Chunk neighbor = world.getChunkProviderServer().getLoadedChunkAt(chunk.locX + x, chunk.locZ + z); - if (neighbor != null) { - neighbor.setNeighborLoaded(-x, -z); - chunk.setNeighborLoaded(x, z); - } - } - } - // CraftBukkit end - - chunk.loadNearby(world.getChunkProviderServer(), world.getChunkProviderServer().chunkGenerator); - } + return world.getChunkProviderServer().getOrLoadChunkAt(x, z) != null; } public boolean isChunkLoaded(Chunk chunk) { diff --git a/src/main/java/org/bukkit/craftbukkit/chunkio/ChunkIOProvider.java b/src/main/java/org/bukkit/craftbukkit/chunkio/ChunkIOProvider.java index 1632f136..f1c1dc49 100644 --- a/src/main/java/org/bukkit/craftbukkit/chunkio/ChunkIOProvider.java +++ b/src/main/java/org/bukkit/craftbukkit/chunkio/ChunkIOProvider.java @@ -48,27 +48,7 @@ class ChunkIOProvider implements AsynchronousExecutor.CallBackProvider