package com.dre.brewery; import com.dre.brewery.utility.BUtil; import com.dre.brewery.utility.BoundingBox; import com.dre.brewery.utility.LegacyUtil; import org.bukkit.Material; import org.bukkit.block.Block; import org.bukkit.configuration.ConfigurationSection; import org.jetbrains.annotations.NotNull; import java.util.Objects; // The Blocks that make up a Barrel in the World public class BarrelBody { private final Barrel barrel; private final Block spigot; private BoundingBox bounds; private byte signoffset; public BarrelBody(Barrel barrel, byte signoffset) { this.barrel = barrel; this.signoffset = signoffset; spigot = barrel.getSpigot(); this.bounds = new BoundingBox(0, 0, 0, 0, 0, 0); } // Loading from file public BarrelBody(Barrel barrel, byte signoffset, BoundingBox bounds) { this(barrel, signoffset); if (bounds == null || bounds.area() > 64 ) { // If loading from old data, or block locations are missing, or other error, regenerate BoundingBox // This will only be done in those extreme cases. Block broken = getBrokenBlock(true); if (broken != null) { barrel.remove(broken, null); } } else { this.bounds = bounds; } } public Barrel getBarrel() { return barrel; } public Block getSpigot() { return spigot; } @NotNull public BoundingBox getBounds() { return bounds; } public void setBounds(@NotNull BoundingBox bounds) { Objects.requireNonNull(bounds); this.bounds = bounds; } public byte getSignoffset() { return signoffset; } public void setSignoffset(byte signoffset) { this.signoffset = signoffset; } // If the Sign of a Large Barrel gets destroyed, set signOffset to 0 public void destroySign() { signoffset = 0; } // direction of the barrel from the spigot public static int getDirection(Block spigot) { int direction = 0;// 1=x+ 2=x- 3=z+ 4=z- Material type = spigot.getRelative(0, 0, 1).getType(); if (LegacyUtil.isWoodPlanks(type) || LegacyUtil.isWoodStairs(type)) { direction = 3; } type = spigot.getRelative(0, 0, -1).getType(); if (LegacyUtil.isWoodPlanks(type) || LegacyUtil.isWoodStairs(type)) { if (direction == 0) { direction = 4; } else { return 0; } } type = spigot.getRelative(1, 0, 0).getType(); if (LegacyUtil.isWoodPlanks(type) || LegacyUtil.isWoodStairs(type)) { if (direction == 0) { direction = 1; } else { return 0; } } type = spigot.getRelative(-1, 0, 0).getType(); if (LegacyUtil.isWoodPlanks(type) || LegacyUtil.isWoodStairs(type)) { if (direction == 0) { direction = 2; } else { return 0; } } return direction; } // is this a Large barrel? public boolean isLarge() { return barrel.isLarge(); } // is this a Small barrel? public boolean isSmall() { return barrel.isSmall(); } // woodtype of the block the spigot is attached to public byte getWood() { Block wood; switch (getDirection(spigot)) { // 1=x+ 2=x- 3=z+ 4=z- case 0: return 0; case 1: wood = spigot.getRelative(1, 0, 0); break; case 2: wood = spigot.getRelative(-1, 0, 0); break; case 3: wood = spigot.getRelative(0, 0, 1); break; default: wood = spigot.getRelative(0, 0, -1); } try { return LegacyUtil.getWoodType(wood); } catch (NoSuchFieldError | NoClassDefFoundError noSuchFieldError) { // Using older minecraft versions some fields and classes do not exist return 0; } } /** * Returns true if this Block is part of this Barrel * * @param block the block to check * @return true if the given block is part of this Barrel */ public boolean hasBlock(Block block) { if (block != null) { if (spigot.getWorld().equals(block.getWorld())) { return bounds != null && bounds.contains(block.getX(), block.getY(), block.getZ()); } } return false; } // Returns true if the Offset of the clicked Sign matches the Barrel. // This prevents adding another sign to the barrel and clicking that. public boolean isSignOfBarrel(byte offset) { return offset == 0 || signoffset == 0 || signoffset == offset; } // returns the Sign of a large barrel, the spigot if there is none public Block getSignOfSpigot() { if (signoffset != 0) { if (LegacyUtil.isSign(spigot.getType())) { return spigot; } if (LegacyUtil.isSign(spigot.getRelative(0, signoffset, 0).getType())) { return spigot.getRelative(0, signoffset, 0); } else { signoffset = 0; } } return spigot; } // returns the fence above/below a block, itself if there is none public static Block getSpigotOfSign(Block block) { int y = -2; while (y <= 1) { // Fence and Netherfence Block relative = block.getRelative(0, y, 0); if (LegacyUtil.isFence(relative.getType())) { return (relative); } y++; } return block; } // returns null if Barrel is correctly placed; the block that is missing when not // the barrel needs to be formed correctly // flag force to also check if chunk is not loaded public Block getBrokenBlock(boolean force) { if (force || BUtil.isChunkLoaded(spigot)) { //spigot = getSpigotOfSign(spigot); if (LegacyUtil.isSign(spigot.getType())) { return checkSBarrel(); } else { return checkLBarrel(); } } return null; } public Block checkSBarrel() { int direction = getDirection(spigot);// 1=x+ 2=x- 3=z+ 4=z- if (direction == 0) { return spigot; } int startX; int startZ; int endX; int endZ; if (direction == 1) { startX = 1; startZ = -1; } else if (direction == 2) { startX = -2; startZ = 0; } else if (direction == 3) { startX = 0; startZ = 1; } else { startX = -1; startZ = -2; } endX = startX + 1; endZ = startZ + 1; Material type; int x = startX; int y = 0; int z = startZ; while (y <= 1) { while (x <= endX) { while (z <= endZ) { Block block = spigot.getRelative(x, y, z); type = block.getType(); if (LegacyUtil.isWoodStairs(type)) { if (y == 0) { // stairs have to be upside down if (!LegacyUtil.areStairsInverted(block)) { return block; } } z++; } else { return spigot.getRelative(x, y, z); } } z = startZ; x++; } z = startZ; x = startX; y++; } bounds = new BoundingBox( spigot.getX() + startX, spigot.getY(), spigot.getZ() + startZ, spigot.getX() + endX, spigot.getY() + 1, spigot.getZ() + endZ); return null; } public Block checkLBarrel() { int direction = getDirection(spigot);// 1=x+ 2=x- 3=z+ 4=z- if (direction == 0) { return spigot; } int startX; int startZ; int endX; int endZ; if (direction == 1) { startX = 1; startZ = -1; } else if (direction == 2) { startX = -4; startZ = -1; } else if (direction == 3) { startX = -1; startZ = 1; } else { startX = -1; startZ = -4; } if (direction == 1 || direction == 2) { endX = startX + 3; endZ = startZ + 2; } else { endX = startX + 2; endZ = startZ + 3; } Material type; int x = startX; int y = 0; int z = startZ; while (y <= 2) { while (x <= endX) { while (z <= endZ) { Block block = spigot.getRelative(x, y, z); type = block.getType(); if (direction == 1 || direction == 2) { if (y == 1 && z == 0) { z++; continue; } } else { if (y == 1 && x == 0) { z++; continue; } } if (LegacyUtil.isWoodPlanks(type) || LegacyUtil.isWoodStairs(type)) { z++; } else { return block; } } z = startZ; x++; } z = startZ; x = startX; y++; } bounds = new BoundingBox( spigot.getX() + startX, spigot.getY(), spigot.getZ() + startZ, spigot.getX() + endX, spigot.getY() + 2, spigot.getZ() + endZ); return null; } public void save(ConfigurationSection config, String prefix) { if (signoffset != 0) { config.set(prefix + ".sign", signoffset); } config.set(prefix + ".bounds", bounds.serialize()); } }