diff --git a/src/main/java/net/minecraft/server/BlockSapling.java b/src/main/java/net/minecraft/server/BlockSapling.java index 7b3d773955..0040474b2d 100644 --- a/src/main/java/net/minecraft/server/BlockSapling.java +++ b/src/main/java/net/minecraft/server/BlockSapling.java @@ -1,12 +1,12 @@ package net.minecraft.server; -import java.util.ArrayList; import java.util.Random; // CraftBukkit start -import org.bukkit.BlockChangeDelegate; +import org.bukkit.Bukkit; import org.bukkit.Location; import org.bukkit.TreeType; import org.bukkit.block.BlockState; +import org.bukkit.craftbukkit.util.StructureGrowDelegate; import org.bukkit.entity.Player; import org.bukkit.event.world.StructureGrowEvent; // CraftBukkit end @@ -45,34 +45,44 @@ public class BlockSapling extends BlockFlower { int l = world.getData(i, j, k) & 3; world.setRawTypeId(i, j, k, 0); - // CraftBukkit start - fixes client updates on recently grown trees + // CraftBukkit start - records tree generation and calls StructureGrowEvent + StructureGrowDelegate delegate = new StructureGrowDelegate(world); + TreeType treeType; boolean grownTree; - BlockChangeWithNotify delegate = new BlockChangeWithNotify(world); - StructureGrowEvent event = null; - Location location = new Location(world.getWorld(), i, j, k); // All of these are 'false' because we need the 'raw' calls so the block-delegate works if (l == 1) { - event = new StructureGrowEvent(location, TreeType.REDWOOD, bonemeal, player, new ArrayList()); - grownTree = new WorldGenTaiga2(false).generate(delegate, random, i, j, k, event, itemstack, world.getWorld()); + treeType = TreeType.REDWOOD; + grownTree = new WorldGenTaiga2(false).generate(delegate, random, i, j, k); } else if (l == 2) { - event = new StructureGrowEvent(location, TreeType.BIRCH, bonemeal, player, new ArrayList()); - grownTree = new WorldGenForest(false).generate(delegate, random, i, j, k, event, itemstack, world.getWorld()); + treeType = TreeType.BIRCH; + grownTree = new WorldGenForest(false).generate(delegate, random, i, j, k); } else { if (random.nextInt(10) == 0) { - event = new StructureGrowEvent(location, TreeType.BIG_TREE, bonemeal, player, new ArrayList()); - grownTree = new WorldGenBigTree(false).generate(delegate, random, i, j, k, event, itemstack, world.getWorld()); + treeType = TreeType.BIG_TREE; + grownTree = new WorldGenBigTree(false).generate(delegate, random, i, j, k); } else { - event = new StructureGrowEvent(location, TreeType.TREE, bonemeal, player, new ArrayList()); - grownTree = new WorldGenTrees(false).generate(delegate, random, i, j, k, event, itemstack, world.getWorld()); + treeType = TreeType.TREE; + grownTree = new WorldGenTrees(false).generate(delegate, random, i, j, k); } } - if (event == null) { - return; + + if (grownTree) { + Location location = new Location(world.getWorld(), i, j, k); + StructureGrowEvent event = new StructureGrowEvent(location, treeType, bonemeal, player, delegate.getBlocks()); + Bukkit.getPluginManager().callEvent(event); + if (event.isCancelled()) { + grownTree = false; + } else { + for (BlockState state : event.getBlocks()) { + state.update(true); + } + if (event.isFromBonemeal() && itemstack != null) { + --itemstack.count; + } + } } - if (event.isFromBonemeal() && itemstack != null) { - --itemstack.count; - } - if (!grownTree || event.isCancelled()) { + + if (!grownTree) { // CraftBukkit end world.setRawTypeIdAndData(i, j, k, this.id, l); } @@ -81,31 +91,4 @@ public class BlockSapling extends BlockFlower { protected int getDropData(int i) { return i & 3; } - - // CraftBukkit start - private class BlockChangeWithNotify implements BlockChangeDelegate { - - World world; - - BlockChangeWithNotify(World world) { - this.world = world; - } - - public boolean setRawTypeId(int x, int y, int z, int type) { - return this.world.setTypeId(x, y, z, type); - } - - public boolean setRawTypeIdAndData(int x, int y, int z, int type, int data) { - return this.world.setTypeIdAndData(x, y, z, type, data); - } - - public int getTypeId(int x, int y, int z) { - return this.world.getTypeId(x, y, z); - } - - public int getHeight() { - return world.height; - } - } - // CraftBukkit end } diff --git a/src/main/java/net/minecraft/server/WorldGenBigTree.java b/src/main/java/net/minecraft/server/WorldGenBigTree.java index 27b00ef324..c4d3f17a6a 100644 --- a/src/main/java/net/minecraft/server/WorldGenBigTree.java +++ b/src/main/java/net/minecraft/server/WorldGenBigTree.java @@ -2,23 +2,13 @@ package net.minecraft.server; import java.util.Random; -// CraftBukkit start -import org.bukkit.BlockChangeDelegate; -import org.bukkit.Bukkit; -import org.bukkit.block.BlockState; -import org.bukkit.craftbukkit.CraftWorld; -import org.bukkit.event.world.StructureGrowEvent; -// CraftBukkit end +import org.bukkit.BlockChangeDelegate; // CraftBukkit public class WorldGenBigTree extends WorldGenerator { static final byte[] a = new byte[] { (byte) 2, (byte) 0, (byte) 0, (byte) 1, (byte) 2, (byte) 1}; Random b = new Random(); - // CraftBukkit start - BlockChangeDelegate world; - StructureGrowEvent event; - CraftWorld bukkitWorld; - // CraftBukkit end + BlockChangeDelegate world; // CraftBukkit int[] d = new int[] { 0, 0, 0}; int e = 0; int f; @@ -131,15 +121,7 @@ public class WorldGenBigTree extends WorldGenerator { if (l1 != 0 && l1 != 18) { ++k1; } else { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(this.world, aint1[0], aint1[1], aint1[2], l, 0); - } else { - BlockState state = bukkitWorld.getBlockAt(aint1[0], aint1[1], aint1[2]).getState(); - state.setTypeId(l); - event.getBlocks().add(state); - } - // CraftBukkit end + this.setTypeAndData(this.world, aint1[0], aint1[1], aint1[2], l, 0); ++k1; } } @@ -215,15 +197,7 @@ public class WorldGenBigTree extends WorldGenerator { aint3[b1] = MathHelper.floor((double) (aint[b1] + j) + 0.5D); aint3[b2] = MathHelper.floor((double) aint[b2] + (double) j * d0 + 0.5D); aint3[b3] = MathHelper.floor((double) aint[b3] + (double) j * d1 + 0.5D); - // CraftBukkit start - if (event == null) { - this.setTypeAndData(this.world, aint3[0], aint3[1], aint3[2], i, 0); - } else { - BlockState state = bukkitWorld.getBlockAt(aint3[0], aint3[1], aint3[2]).getState(); - state.setTypeId(i); - event.getBlocks().add(state); - } - // CraftBukkit end + this.setTypeAndData(this.world, aint3[0], aint3[1], aint3[2], i, 0); } } } @@ -368,12 +342,10 @@ public class WorldGenBigTree extends WorldGenerator { // BlockChangeDelegate and then we can implicitly cast World to // WorldServer (a safe cast, AFAIK) and no code will be broken. This // then allows plugins to catch manually-invoked generation events - return this.generate((BlockChangeDelegate) world, random, i, j, k, null, null, world.getWorld()); + return this.generate((BlockChangeDelegate) world, random, i, j, k); } - public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k, StructureGrowEvent event, ItemStack itemstack, CraftWorld bukkitWorld) { - this.event = event; - this.bukkitWorld = bukkitWorld; + public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k) { // CraftBukkit end this.world = world; long l = random.nextLong(); @@ -393,17 +365,6 @@ public class WorldGenBigTree extends WorldGenerator { this.b(); this.c(); this.d(); - // CraftBukkit start - if (event != null) { - Bukkit.getPluginManager().callEvent(event); - if (!event.isCancelled()) { - world.setRawTypeId(i, j, k, 0); - for (BlockState state : event.getBlocks()) { - state.update(true); - } - } - } - // CraftBukkit end return true; } } diff --git a/src/main/java/net/minecraft/server/WorldGenForest.java b/src/main/java/net/minecraft/server/WorldGenForest.java index b3d8113ba3..831a3b2598 100644 --- a/src/main/java/net/minecraft/server/WorldGenForest.java +++ b/src/main/java/net/minecraft/server/WorldGenForest.java @@ -2,14 +2,7 @@ package net.minecraft.server; import java.util.Random; -// CraftBukkit start -import org.bukkit.BlockChangeDelegate; -import org.bukkit.Bukkit; -import org.bukkit.block.BlockState; -import org.bukkit.craftbukkit.CraftWorld; -import org.bukkit.event.world.StructureGrowEvent; -import org.bukkit.material.MaterialData; -// CraftBukkit end +import org.bukkit.BlockChangeDelegate; // CraftBukkit public class WorldGenForest extends WorldGenerator { @@ -23,10 +16,10 @@ public class WorldGenForest extends WorldGenerator { // BlockChangeDelegate and then we can implicitly cast World to // WorldServer (a safe cast, AFAIK) and no code will be broken. This // then allows plugins to catch manually-invoked generation events - return this.generate((BlockChangeDelegate) world, random, i, j, k, null, null, world.getWorld()); + return this.generate((BlockChangeDelegate) world, random, i, j, k); } - public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k, StructureGrowEvent event, ItemStack itemstack, CraftWorld bukkitWorld) { + public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k) { // CraftBukkit end int l = random.nextInt(3) + 5; boolean flag = true; @@ -67,15 +60,7 @@ public class WorldGenForest extends WorldGenerator { } else { i1 = world.getTypeId(i, j - 1, k); if ((i1 == Block.GRASS.id || i1 == Block.DIRT.id) && j < world.getHeight() - l - 1) { // CraftBukkit - // CraftBukkit start - if (event == null) { - world.setRawTypeId(i, j - 1, k, Block.DIRT.id); - } else { - BlockState dirtState = bukkitWorld.getBlockAt(i, j - 1, k).getState(); - dirtState.setTypeId(Block.DIRT.id); - event.getBlocks().add(dirtState); - } - // CraftBukkit end + world.setRawTypeId(i, j - 1, k, Block.DIRT.id); int i2; for (i2 = j - 3 + l; i2 <= j + l; ++i2) { @@ -89,16 +74,7 @@ public class WorldGenForest extends WorldGenerator { int l2 = k2 - k; if ((Math.abs(j2) != k1 || Math.abs(l2) != k1 || random.nextInt(2) != 0 && j1 != 0) && !Block.o[world.getTypeId(l1, i2, k2)]) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, l1, i2, k2, Block.LEAVES.id, 2); - } else { - BlockState leavesState = bukkitWorld.getBlockAt(l1, i2, k2).getState(); - leavesState.setTypeId(Block.LEAVES.id); - leavesState.setData(new MaterialData(Block.LEAVES.id, (byte) 2)); - event.getBlocks().add(leavesState); - } - // CraftBukkit end + this.setTypeAndData(world, l1, i2, k2, Block.LEAVES.id, 2); } } } @@ -107,28 +83,10 @@ public class WorldGenForest extends WorldGenerator { for (i2 = 0; i2 < l; ++i2) { j1 = world.getTypeId(i, j + i2, k); if (j1 == 0 || j1 == Block.LEAVES.id) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, i, j + i2, k, Block.LOG.id, 2); - } else { - BlockState logState = bukkitWorld.getBlockAt(i, j + i2, k).getState(); - logState.setTypeId(Block.LOG.id); - logState.setData(new MaterialData(Block.LOG.id, (byte) 2)); - event.getBlocks().add(logState); - } - // CraftBukkit end + this.setTypeAndData(world, i, j + i2, k, Block.LOG.id, 2); } } - // CraftBukkit start - if (event != null) { - Bukkit.getPluginManager().callEvent(event); - if (!event.isCancelled()) { - for (BlockState state : event.getBlocks()) { - state.update(true); - } - } - } - // CraftBukkit end + return true; } else { return false; diff --git a/src/main/java/net/minecraft/server/WorldGenTaiga2.java b/src/main/java/net/minecraft/server/WorldGenTaiga2.java index 9e13dc7557..f7f92159d9 100644 --- a/src/main/java/net/minecraft/server/WorldGenTaiga2.java +++ b/src/main/java/net/minecraft/server/WorldGenTaiga2.java @@ -2,14 +2,7 @@ package net.minecraft.server; import java.util.Random; -// CraftBukkit start -import org.bukkit.BlockChangeDelegate; -import org.bukkit.Bukkit; -import org.bukkit.block.BlockState; -import org.bukkit.craftbukkit.CraftWorld; -import org.bukkit.event.world.StructureGrowEvent; -import org.bukkit.material.MaterialData; -// CraftBukkit end +import org.bukkit.BlockChangeDelegate; // CraftBukkit public class WorldGenTaiga2 extends WorldGenerator { @@ -23,10 +16,10 @@ public class WorldGenTaiga2 extends WorldGenerator { // BlockChangeDelegate and then we can implicitly cast World to // WorldServer (a safe cast, AFAIK) and no code will be broken. This // then allows plugins to catch manually-invoked generation events - return this.generate((BlockChangeDelegate) world, random, i, j, k, null, null, world.getWorld()); + return this.generate((BlockChangeDelegate) world, random, i, j, k); } - public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k, StructureGrowEvent event, ItemStack itemstack, CraftWorld bukkitWorld) { + public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k) { // CraftBukkit end int l = random.nextInt(4) + 6; int i1 = 1 + random.nextInt(2); @@ -68,15 +61,7 @@ public class WorldGenTaiga2 extends WorldGenerator { } else { l1 = world.getTypeId(i, j - 1, k); if ((l1 == Block.GRASS.id || l1 == Block.DIRT.id) && j < world.getHeight() - l - 1) { // CraftBukkit - // CraftBukkit start - if (event == null) { - world.setRawTypeId(i, j - 1, k, Block.DIRT.id); - } else { - BlockState dirtState = bukkitWorld.getBlockAt(i, j - 1, k).getState(); - dirtState.setTypeId(Block.DIRT.id); - event.getBlocks().add(dirtState); - } - // CraftBukkit end + world.setRawTypeId(i, j - 1, k, Block.DIRT.id); k2 = random.nextInt(2); i2 = 1; byte b0 = 0; @@ -94,16 +79,7 @@ public class WorldGenTaiga2 extends WorldGenerator { int i4 = l3 - k; if ((Math.abs(k3) != k2 || Math.abs(i4) != k2 || k2 <= 0) && !Block.o[world.getTypeId(i3, j3, l3)]) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, i3, j3, l3, Block.LEAVES.id, 1); - } else { - BlockState leavesState = bukkitWorld.getBlockAt(i3, j3, l3).getState(); - leavesState.setTypeId(Block.LEAVES.id); - leavesState.setData(new MaterialData(Block.LEAVES.id, (byte) 1)); - event.getBlocks().add(leavesState); - } - // CraftBukkit end + this.setTypeAndData(world, i3, j3, l3, Block.LEAVES.id, 1); } } } @@ -125,28 +101,10 @@ public class WorldGenTaiga2 extends WorldGenerator { for (j3 = 0; j3 < l - j2; ++j3) { i3 = world.getTypeId(i, j + j3, k); if (i3 == 0 || i3 == Block.LEAVES.id) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, i, j + j3, k, Block.LOG.id, 1); - } else { - BlockState logState = bukkitWorld.getBlockAt(i, j + j3, k).getState(); - logState.setTypeId(Block.LOG.id); - logState.setData(new MaterialData(Block.LOG.id, (byte) 1)); - event.getBlocks().add(logState); - } - // CraftBukkit end + this.setTypeAndData(world, i, j + j3, k, Block.LOG.id, 1); } } - // CraftBukkit start - if (event != null) { - Bukkit.getPluginManager().callEvent(event); - if (!event.isCancelled()) { - for (BlockState state : event.getBlocks()) { - state.update(true); - } - } - } - // CraftBukkit end + return true; } else { return false; diff --git a/src/main/java/net/minecraft/server/WorldGenTrees.java b/src/main/java/net/minecraft/server/WorldGenTrees.java index 899cc9641a..630f619bab 100644 --- a/src/main/java/net/minecraft/server/WorldGenTrees.java +++ b/src/main/java/net/minecraft/server/WorldGenTrees.java @@ -2,13 +2,7 @@ package net.minecraft.server; import java.util.Random; -// CraftBukkit start -import org.bukkit.BlockChangeDelegate; -import org.bukkit.Bukkit; -import org.bukkit.block.BlockState; -import org.bukkit.craftbukkit.CraftWorld; -import org.bukkit.event.world.StructureGrowEvent; -// CraftBukkit end +import org.bukkit.BlockChangeDelegate; // CraftBukkit public class WorldGenTrees extends WorldGenerator { @@ -22,10 +16,10 @@ public class WorldGenTrees extends WorldGenerator { // BlockChangeDelegate and then we can implicitly cast World to // WorldServer (a safe cast, AFAIK) and no code will be broken. This // then allows plugins to catch manually-invoked generation events - return this.generate((BlockChangeDelegate) world, random, i, j, k, null, null, world.getWorld()); + return this.generate((BlockChangeDelegate) world, random, i, j, k); } - public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k, StructureGrowEvent event, ItemStack itemstack, CraftWorld bukkitWorld) { + public boolean generate(BlockChangeDelegate world, Random random, int i, int j, int k) { // CraftBukkit end int l = random.nextInt(3) + 4; boolean flag = true; @@ -66,15 +60,7 @@ public class WorldGenTrees extends WorldGenerator { } else { i1 = world.getTypeId(i, j - 1, k); if ((i1 == Block.GRASS.id || i1 == Block.DIRT.id) && j < world.getHeight() - l - 1) { // CraftBukkit - // CraftBukkit start - if (event == null) { - world.setRawTypeId(i, j - 1, k, Block.DIRT.id); - } else { - BlockState dirtState = bukkitWorld.getBlockAt(i, j - 1, k).getState(); - dirtState.setTypeId(Block.DIRT.id); - event.getBlocks().add(dirtState); - } - // CraftBukkit end + world.setRawTypeId(i, j - 1, k, Block.DIRT.id); int i2; @@ -89,15 +75,7 @@ public class WorldGenTrees extends WorldGenerator { int l2 = k2 - k; if ((Math.abs(j2) != k1 || Math.abs(l2) != k1 || random.nextInt(2) != 0 && j1 != 0) && !Block.o[world.getTypeId(l1, i2, k2)]) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, l1, i2, k2, Block.LEAVES.id, 0); - } else { - BlockState leavesState = bukkitWorld.getBlockAt(l1, i2, k2).getState(); - leavesState.setTypeId(Block.LEAVES.id); - event.getBlocks().add(leavesState); - } - // CraftBukkit end + this.setTypeAndData(world, l1, i2, k2, Block.LEAVES.id, 0); } } } @@ -106,27 +84,10 @@ public class WorldGenTrees extends WorldGenerator { for (i2 = 0; i2 < l; ++i2) { j1 = world.getTypeId(i, j + i2, k); if (j1 == 0 || j1 == Block.LEAVES.id) { - // CraftBukkit start - if (event == null) { - this.setTypeAndData(world, i, j + i2, k, Block.LOG.id, 0); - } else { - BlockState logState = bukkitWorld.getBlockAt(i, j + i2, k).getState(); - logState.setTypeId(Block.LOG.id); - event.getBlocks().add(logState); - } - // CraftBukkit end + this.setTypeAndData(world, i, j + i2, k, Block.LOG.id, 0); } } - // CraftBukkit start - if (event != null) { - Bukkit.getPluginManager().callEvent(event); - if (!event.isCancelled()) { - for (BlockState state : event.getBlocks()) { - state.update(true); - } - } - } - // CraftBukkit end + return true; } else { return false; diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java index 744113b735..0b434f32cf 100644 --- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java @@ -365,16 +365,16 @@ public class CraftWorld implements World { public boolean generateTree(Location loc, TreeType type, BlockChangeDelegate delegate) { switch (type) { case BIG_TREE: - return new WorldGenBigTree(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), null, null, null); + return new WorldGenBigTree(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ()); case BIRCH: - return new WorldGenForest(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), null, null, null); + return new WorldGenForest(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ()); case REDWOOD: - return new WorldGenTaiga2(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), null, null, null); + return new WorldGenTaiga2(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ()); case TALL_REDWOOD: return new WorldGenTaiga1().generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ()); case TREE: default: - return new WorldGenTrees(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), null, null, null); + return new WorldGenTrees(false).generate(delegate, rand, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ()); } } diff --git a/src/main/java/org/bukkit/craftbukkit/util/StructureGrowDelegate.java b/src/main/java/org/bukkit/craftbukkit/util/StructureGrowDelegate.java new file mode 100644 index 0000000000..125772d41d --- /dev/null +++ b/src/main/java/org/bukkit/craftbukkit/util/StructureGrowDelegate.java @@ -0,0 +1,48 @@ +package org.bukkit.craftbukkit.util; + +import java.util.ArrayList; +import java.util.List; + +import net.minecraft.server.World; + +import org.bukkit.BlockChangeDelegate; +import org.bukkit.block.BlockState; +import org.bukkit.craftbukkit.CraftWorld; +import org.bukkit.material.MaterialData; + +public class StructureGrowDelegate implements BlockChangeDelegate { + private final CraftWorld world; + private final List blocks = new ArrayList(); + + public StructureGrowDelegate(World world) { + this.world = world.getWorld(); + } + + @Override + public boolean setRawTypeId(int x, int y, int z, int type) { + return setRawTypeIdAndData(x, y, z, type, 0); + } + + @Override + public boolean setRawTypeIdAndData(int x, int y, int z, int type, int data) { + BlockState state = world.getBlockAt(x, y, z).getState(); + state.setTypeId(type); + state.setData(new MaterialData(type, (byte) data)); + blocks.add(state); + return true; + } + + @Override + public int getTypeId(int x, int y, int z) { + return world.getBlockTypeIdAt(x, y, z); + } + + @Override + public int getHeight() { + return world.getMaxHeight(); + } + + public List getBlocks() { + return blocks; + } +}