mirror of
https://github.com/songoda/EpicHoppers.git
synced 2024-11-29 13:45:24 +01:00
Merge branch 'development' into 'master'
1.14 Support See merge request Songoda/epichoppers!23
This commit is contained in:
commit
34929f241c
@ -2,6 +2,7 @@ package com.songoda.epichoppers.api.hopper.levels.modules;
|
|||||||
|
|
||||||
import com.songoda.epichoppers.api.hopper.Hopper;
|
import com.songoda.epichoppers.api.hopper.Hopper;
|
||||||
import org.bukkit.Material;
|
import org.bukkit.Material;
|
||||||
|
import org.bukkit.inventory.Inventory;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@ -9,7 +10,7 @@ public interface Module {
|
|||||||
|
|
||||||
String getName();
|
String getName();
|
||||||
|
|
||||||
void run(Hopper hopper, org.bukkit.block.Hopper hopperBlock);
|
void run(Hopper hopper, Inventory hopperInventory);
|
||||||
|
|
||||||
List<Material> getBlockedItems(Hopper hopper);
|
List<Material> getBlockedItems(Hopper hopper);
|
||||||
|
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
package com.songoda.epichoppers;
|
package com.songoda.epichoppers;
|
||||||
|
|
||||||
import com.google.common.base.Preconditions;
|
|
||||||
import com.songoda.epichoppers.api.EpicHoppers;
|
import com.songoda.epichoppers.api.EpicHoppers;
|
||||||
import com.songoda.epichoppers.api.EpicHoppersAPI;
|
import com.songoda.epichoppers.api.EpicHoppersAPI;
|
||||||
import com.songoda.epichoppers.api.hopper.HopperManager;
|
import com.songoda.epichoppers.api.hopper.HopperManager;
|
||||||
@ -12,7 +11,7 @@ import com.songoda.epichoppers.boost.BoostData;
|
|||||||
import com.songoda.epichoppers.boost.BoostManager;
|
import com.songoda.epichoppers.boost.BoostManager;
|
||||||
import com.songoda.epichoppers.command.CommandManager;
|
import com.songoda.epichoppers.command.CommandManager;
|
||||||
import com.songoda.epichoppers.enchantment.Enchantment;
|
import com.songoda.epichoppers.enchantment.Enchantment;
|
||||||
import com.songoda.epichoppers.handlers.HopHandler;
|
import com.songoda.epichoppers.tasks.HopTask;
|
||||||
import com.songoda.epichoppers.handlers.TeleportHandler;
|
import com.songoda.epichoppers.handlers.TeleportHandler;
|
||||||
import com.songoda.epichoppers.hook.HookManager;
|
import com.songoda.epichoppers.hook.HookManager;
|
||||||
import com.songoda.epichoppers.hopper.EFilter;
|
import com.songoda.epichoppers.hopper.EFilter;
|
||||||
@ -39,7 +38,6 @@ import org.bukkit.Location;
|
|||||||
import org.bukkit.Material;
|
import org.bukkit.Material;
|
||||||
import org.bukkit.command.CommandSender;
|
import org.bukkit.command.CommandSender;
|
||||||
import org.bukkit.configuration.ConfigurationSection;
|
import org.bukkit.configuration.ConfigurationSection;
|
||||||
import org.bukkit.entity.Player;
|
|
||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
import org.bukkit.inventory.meta.ItemMeta;
|
import org.bukkit.inventory.meta.ItemMeta;
|
||||||
import org.bukkit.plugin.PluginManager;
|
import org.bukkit.plugin.PluginManager;
|
||||||
@ -57,7 +55,6 @@ import java.util.ArrayList;
|
|||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
import java.util.function.Supplier;
|
|
||||||
|
|
||||||
|
|
||||||
public class EpicHoppersPlugin extends JavaPlugin implements EpicHoppers {
|
public class EpicHoppersPlugin extends JavaPlugin implements EpicHoppers {
|
||||||
@ -67,7 +64,6 @@ public class EpicHoppersPlugin extends JavaPlugin implements EpicHoppers {
|
|||||||
public References references = null;
|
public References references = null;
|
||||||
public Enchantment enchantmentHandler;
|
public Enchantment enchantmentHandler;
|
||||||
private SettingsManager settingsManager;
|
private SettingsManager settingsManager;
|
||||||
private ConfigWrapper hooksFile = new ConfigWrapper(this, "", "hooks.yml");
|
|
||||||
private ConfigWrapper levelsFile = new ConfigWrapper(this, "", "levels.yml");
|
private ConfigWrapper levelsFile = new ConfigWrapper(this, "", "levels.yml");
|
||||||
private Locale locale;
|
private Locale locale;
|
||||||
|
|
||||||
@ -142,7 +138,7 @@ public class EpicHoppersPlugin extends JavaPlugin implements EpicHoppers {
|
|||||||
// Load from file
|
// Load from file
|
||||||
loadFromFile();
|
loadFromFile();
|
||||||
|
|
||||||
new HopHandler(this);
|
new HopTask(this);
|
||||||
this.teleportHandler = new TeleportHandler(this);
|
this.teleportHandler = new TeleportHandler(this);
|
||||||
|
|
||||||
PluginManager pluginManager = Bukkit.getPluginManager();
|
PluginManager pluginManager = Bukkit.getPluginManager();
|
||||||
|
@ -1,373 +0,0 @@
|
|||||||
package com.songoda.epichoppers.handlers;
|
|
||||||
|
|
||||||
import com.songoda.epichoppers.EpicHoppersPlugin;
|
|
||||||
import com.songoda.epichoppers.api.hopper.levels.modules.Module;
|
|
||||||
import com.songoda.epichoppers.boost.BoostData;
|
|
||||||
import com.songoda.epichoppers.utils.Debugger;
|
|
||||||
import org.bukkit.Bukkit;
|
|
||||||
import org.bukkit.Location;
|
|
||||||
import org.bukkit.Material;
|
|
||||||
import org.bukkit.OfflinePlayer;
|
|
||||||
import org.bukkit.block.Block;
|
|
||||||
import org.bukkit.block.BlockState;
|
|
||||||
import org.bukkit.block.Hopper;
|
|
||||||
import org.bukkit.entity.Entity;
|
|
||||||
import org.bukkit.entity.EntityType;
|
|
||||||
import org.bukkit.entity.minecart.HopperMinecart;
|
|
||||||
import org.bukkit.entity.minecart.StorageMinecart;
|
|
||||||
import org.bukkit.inventory.*;
|
|
||||||
|
|
||||||
import java.util.*;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Created by songoda on 3/14/2017.
|
|
||||||
*/
|
|
||||||
public class HopHandler {
|
|
||||||
|
|
||||||
private EpicHoppersPlugin instance;
|
|
||||||
|
|
||||||
public HopHandler(EpicHoppersPlugin instance) {
|
|
||||||
try {
|
|
||||||
this.instance = instance;
|
|
||||||
Bukkit.getScheduler().scheduleSyncDelayedTask(instance, () ->
|
|
||||||
Bukkit.getScheduler().scheduleSyncRepeatingTask(instance, this::hopperRunner, 0,
|
|
||||||
instance.getConfig().getLong("Main.Amount of Ticks Between Hops")), 40L);
|
|
||||||
} catch (Exception e) {
|
|
||||||
Debugger.runReport(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void hopperRunner() {
|
|
||||||
try {
|
|
||||||
main:
|
|
||||||
for (com.songoda.epichoppers.api.hopper.Hopper hopper : new HashMap<>(instance.getHopperManager().getHoppers()).values()) {
|
|
||||||
Location location = hopper.getLocation();
|
|
||||||
|
|
||||||
if (!location.getWorld().isChunkLoaded(location.getBlockX() >> 4, location.getBlockZ() >> 4))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
Block block = location.getBlock();
|
|
||||||
|
|
||||||
if (block == null || block.getType() != Material.HOPPER) {
|
|
||||||
instance.getHopperManager().removeHopper(location);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.isBlockPowered() || block.isBlockIndirectlyPowered()) continue;
|
|
||||||
|
|
||||||
Hopper hopperState = (Hopper) block.getState();
|
|
||||||
|
|
||||||
List<Material> blockedMaterials = new ArrayList<>();
|
|
||||||
|
|
||||||
if (hopperState == null || hopperState.getInventory() == null) continue;
|
|
||||||
|
|
||||||
for (Module module : hopper.getLevel().getRegisteredModules()) {
|
|
||||||
// Run Module
|
|
||||||
module.run(hopper, hopperState);
|
|
||||||
|
|
||||||
// Add banned materials to list.
|
|
||||||
List<Material> materials = module.getBlockedItems(hopper);
|
|
||||||
if (materials == null || materials.isEmpty()) continue;
|
|
||||||
blockedMaterials.addAll(materials);
|
|
||||||
}
|
|
||||||
|
|
||||||
ItemStack[] hopperContents = hopperState.getInventory().getContents();
|
|
||||||
|
|
||||||
Inventory override = null;
|
|
||||||
List<Location> linked = hopper.getLinkedBlocks();
|
|
||||||
|
|
||||||
if (hopper.getLinkedBlocks() == null || hopper.getLinkedBlocks().isEmpty()) {
|
|
||||||
HopperDirection hopperDirection = HopperDirection.getDirection(hopperState.getRawData());
|
|
||||||
Location check = hopperDirection.getLocation(location);
|
|
||||||
|
|
||||||
linked.add(check);
|
|
||||||
|
|
||||||
Collection<Entity> nearbyEntities = hopper.getLocation().getWorld().getNearbyEntities(check, .5, .5, .5);
|
|
||||||
|
|
||||||
for (Entity entity : nearbyEntities) {
|
|
||||||
if (entity.getType() == EntityType.MINECART_HOPPER)
|
|
||||||
override = ((HopperMinecart) entity).getInventory();
|
|
||||||
else if (entity.getType() == EntityType.MINECART_CHEST)
|
|
||||||
override = ((StorageMinecart) entity).getInventory();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (linked.isEmpty()) continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (Location destinationLocation : linked) {
|
|
||||||
Block destinationBlock = destinationLocation.getBlock();
|
|
||||||
Inventory destinationInventory = override;
|
|
||||||
if (override == null) {
|
|
||||||
if (destinationLocation == null) continue;
|
|
||||||
|
|
||||||
if (!destinationLocation.getWorld().isChunkLoaded(destinationLocation.getBlockX() >> 4,
|
|
||||||
destinationLocation.getBlockZ() >> 4))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
destinationBlock = destinationLocation.getBlock();
|
|
||||||
BlockState state = destinationBlock.getState();
|
|
||||||
if (!(state instanceof InventoryHolder)) {
|
|
||||||
hopper.clearLinkedBlocks();
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
destinationInventory = ((InventoryHolder) state).getInventory();
|
|
||||||
}
|
|
||||||
|
|
||||||
BoostData boostData = instance.getBoostManager().getBoost(hopper.getPlacedBy());
|
|
||||||
|
|
||||||
int amount = hopper.getLevel().getAmount() * (boostData == null ? 1 : boostData.getMultiplier());
|
|
||||||
|
|
||||||
List<ItemStack> whiteList = hopper.getFilter().getWhiteList();
|
|
||||||
List<ItemStack> blackList = hopper.getFilter().getBlackList();
|
|
||||||
|
|
||||||
for (int i = 0; i < 5; i++) {
|
|
||||||
if (hopperContents[i] == null) continue;
|
|
||||||
|
|
||||||
ItemStack item = hopperContents[i].clone();
|
|
||||||
item.setAmount(1);
|
|
||||||
|
|
||||||
if (hopper.getLocation().getBlock().isBlockPowered()
|
|
||||||
|| hopperContents[i] != null && blockedMaterials.contains(hopperContents[i].getType())) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
int finalIncrement = i;
|
|
||||||
|
|
||||||
if (!whiteList.isEmpty()
|
|
||||||
&& whiteList.stream().noneMatch(itemStack -> itemStack.isSimilar(hopperContents[finalIncrement]))) {
|
|
||||||
doBlacklist(hopperState, hopper, hopperContents[i].clone(), amount, i);
|
|
||||||
continue main;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (blackList.stream().noneMatch(itemStack -> itemStack.isSimilar(hopperContents[finalIncrement]))) {
|
|
||||||
if (addItem(hopperState, hopper, destinationInventory, destinationBlock, hopperContents[i], amount, i)) {
|
|
||||||
continue main;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (blackList.stream().anyMatch(itemStack -> itemStack.isSimilar(hopperContents[finalIncrement]))) {
|
|
||||||
doBlacklist(hopperState, hopper, hopperContents[i].clone(), amount, i);
|
|
||||||
continue main;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
Debugger.runReport(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
private void doBlacklist(Hopper hopperState, com.songoda.epichoppers.api.hopper.Hopper hopper, ItemStack item, int amt, int place) {
|
|
||||||
try {
|
|
||||||
Location dest = hopper.getFilter().getEndPoint();
|
|
||||||
if (dest == null) return;
|
|
||||||
if (!dest.getWorld().isChunkLoaded(dest.getBlockX() >> 4, dest.getBlockZ() >> 4))
|
|
||||||
return;
|
|
||||||
|
|
||||||
Block destinationBlock = dest.getBlock();
|
|
||||||
BlockState state = destinationBlock.getState();
|
|
||||||
if (!(state instanceof InventoryHolder)) {
|
|
||||||
hopper.getFilter().setEndPoint(null);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
Inventory destinationInventory = ((InventoryHolder) state).getInventory();
|
|
||||||
|
|
||||||
addItem(hopperState, hopper, destinationInventory, destinationBlock, item, amt, place);
|
|
||||||
} catch (Exception e) {
|
|
||||||
Debugger.runReport(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private boolean addItem(Hopper hopperState, com.songoda.epichoppers.api.hopper.Hopper hopper, Inventory destinationInventory, Block destinationBlock, ItemStack is, int amt, int place) {
|
|
||||||
try {
|
|
||||||
ItemStack it = null;
|
|
||||||
if (is != null) {
|
|
||||||
it = is.clone();
|
|
||||||
it.setAmount(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
List<ItemStack> ovoid = new ArrayList<>(hopper.getFilter().getVoidList());
|
|
||||||
|
|
||||||
if (is.getType() == Material.AIR) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
ItemStack item = is;
|
|
||||||
ItemStack newItem = is.clone();
|
|
||||||
|
|
||||||
if ((item.getAmount() - amt) <= 0) {
|
|
||||||
amt = item.getAmount();
|
|
||||||
}
|
|
||||||
if ((item.getAmount() - amt) >= 1) {
|
|
||||||
newItem.setAmount(newItem.getAmount() - amt);
|
|
||||||
is = newItem.clone();
|
|
||||||
} else {
|
|
||||||
is = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
newItem.setAmount(amt);
|
|
||||||
|
|
||||||
if (destinationBlock.getType().equals(Material.ENDER_CHEST)) {
|
|
||||||
OfflinePlayer op = Bukkit.getOfflinePlayer(hopper.getPlacedBy());
|
|
||||||
|
|
||||||
if (op.isOnline() && canMove(op.getPlayer().getEnderChest(), newItem)) {
|
|
||||||
ItemStack finalIt = it;
|
|
||||||
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
|
||||||
op.getPlayer().getEnderChest().addItem(newItem);
|
|
||||||
}
|
|
||||||
hopperState.getInventory().setItem(place, is);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (destinationBlock.getType().name().contains("SHULKER_BOX")) {
|
|
||||||
if (item.getType().name().contains("SHULKER_BOX")) return false;
|
|
||||||
} else if (destinationBlock.getType() == Material.BREWING_STAND) {
|
|
||||||
BrewerInventory brewerInventory = (BrewerInventory) destinationInventory;
|
|
||||||
|
|
||||||
int maxSize = newItem.getMaxStackSize();
|
|
||||||
|
|
||||||
String typeStr = item.getType().name().toUpperCase();
|
|
||||||
boolean isBottle = typeStr.contains("POTION") || typeStr.contains("BOTTLE") || item.getType() == Material.DRAGON_BREATH;
|
|
||||||
boolean isLeft = item.getType() == Material.BLAZE_POWDER;
|
|
||||||
|
|
||||||
Map<Integer, ItemStack> output = new HashMap<>();
|
|
||||||
if (isBottle) {
|
|
||||||
output.put(0, brewerInventory.getItem(0));
|
|
||||||
output.put(1, brewerInventory.getItem(1));
|
|
||||||
output.put(2, brewerInventory.getItem(2));
|
|
||||||
} else if (isLeft) {
|
|
||||||
output.put(4, brewerInventory.getItem(4));
|
|
||||||
} else {
|
|
||||||
output.put(3, brewerInventory.getItem(3));
|
|
||||||
}
|
|
||||||
|
|
||||||
ItemStack finalIt = it;
|
|
||||||
for (Map.Entry<Integer, ItemStack> entry : output.entrySet()) {
|
|
||||||
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
|
||||||
ItemStack currentOutput = entry.getValue();
|
|
||||||
int currentOutputAmount = currentOutput == null ? 0 : currentOutput.getAmount();
|
|
||||||
if (currentOutput != null && (!currentOutput.isSimilar(newItem))
|
|
||||||
|| currentOutputAmount + newItem.getAmount() > maxSize) continue;
|
|
||||||
|
|
||||||
if (currentOutput != null) {
|
|
||||||
currentOutput.setAmount(currentOutputAmount + newItem.getAmount());
|
|
||||||
} else {
|
|
||||||
currentOutput = newItem.clone();
|
|
||||||
}
|
|
||||||
|
|
||||||
brewerInventory.setItem(entry.getKey(), currentOutput);
|
|
||||||
}
|
|
||||||
hopperState.getInventory().setItem(place, is);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
} else if (destinationBlock.getType() == Material.FURNACE) {
|
|
||||||
FurnaceInventory furnaceInventory = (FurnaceInventory) destinationInventory;
|
|
||||||
|
|
||||||
boolean isFuel = item.getType().isFuel() && !item.getType().name().contains("LOG");
|
|
||||||
ItemStack output = isFuel ? furnaceInventory.getFuel() : furnaceInventory.getSmelting();
|
|
||||||
if (output != null && !output.isSimilar(newItem)) return false;
|
|
||||||
int maxSize = newItem.getMaxStackSize();
|
|
||||||
int currentOutputAmount = output == null ? 0 : output.getAmount();
|
|
||||||
|
|
||||||
if (currentOutputAmount + newItem.getAmount() <= maxSize) {
|
|
||||||
ItemStack finalIt = it;
|
|
||||||
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
|
||||||
if (output != null) {
|
|
||||||
output.setAmount(currentOutputAmount + newItem.getAmount());
|
|
||||||
} else {
|
|
||||||
output = newItem.clone();
|
|
||||||
}
|
|
||||||
if (isFuel) {
|
|
||||||
furnaceInventory.setFuel(output);
|
|
||||||
} else {
|
|
||||||
furnaceInventory.setSmelting(output);
|
|
||||||
}
|
|
||||||
hopperState.getInventory().setItem(place, is);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (!canMove(destinationInventory, newItem)) return false;
|
|
||||||
ItemStack finalIt = it;
|
|
||||||
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
|
||||||
destinationInventory.addItem(newItem);
|
|
||||||
}
|
|
||||||
hopperState.getInventory().setItem(place, is);
|
|
||||||
return true;
|
|
||||||
} catch (Exception e) {
|
|
||||||
Debugger.runReport(e);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private boolean canMove(Inventory inventory, ItemStack item) {
|
|
||||||
try {
|
|
||||||
if (inventory.firstEmpty() != -1) return true;
|
|
||||||
for (ItemStack stack : inventory.getContents()) {
|
|
||||||
if (stack.isSimilar(item) && (stack.getAmount() + item.getAmount()) - 1 < stack.getMaxStackSize()) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
Debugger.runReport(e);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public enum HopperDirection {
|
|
||||||
|
|
||||||
DOWN(0, 8, 0, -1, 0),
|
|
||||||
NORTH(2, 10, 0, 0, -1),
|
|
||||||
SOUTH(3, 11, 0, 0, 1),
|
|
||||||
WEST(4, 12, -1, 0, 0),
|
|
||||||
EAST(5, 13, 1, 0, 0);
|
|
||||||
|
|
||||||
private int unpowered;
|
|
||||||
private int powered;
|
|
||||||
|
|
||||||
private int x;
|
|
||||||
private int y;
|
|
||||||
private int z;
|
|
||||||
|
|
||||||
HopperDirection(int unpowered, int powered, int x, int y, int z) {
|
|
||||||
this.unpowered = unpowered;
|
|
||||||
this.powered = powered;
|
|
||||||
|
|
||||||
this.x = x;
|
|
||||||
this.y = y;
|
|
||||||
this.z = z;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static HopperDirection getDirection(int value) {
|
|
||||||
for (HopperDirection hopperDirection : HopperDirection.values()) {
|
|
||||||
if (hopperDirection.getPowered() == value
|
|
||||||
|| hopperDirection.getUnpowered() == value) return hopperDirection;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Location getLocation(Location location) {
|
|
||||||
return location.add(getX(), getY(), getZ());
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getX() {
|
|
||||||
return x;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getY() {
|
|
||||||
return y;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getZ() {
|
|
||||||
return z;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getUnpowered() {
|
|
||||||
return unpowered;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getPowered() {
|
|
||||||
return powered;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -73,7 +73,7 @@ public class TeleportHandler {
|
|||||||
boolean empty = lastHopper.getLinkedBlocks().isEmpty();
|
boolean empty = lastHopper.getLinkedBlocks().isEmpty();
|
||||||
if (empty && i == 0) {
|
if (empty && i == 0) {
|
||||||
if (teleportFrom.containsKey(hopper.getLocation()))
|
if (teleportFrom.containsKey(hopper.getLocation()))
|
||||||
doTeleport(player, teleportFrom.get(hopper.getLocation()));
|
doTeleport(player, teleportFrom.get(hopper.getLocation()).clone());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -15,7 +15,7 @@ import java.util.Map;
|
|||||||
|
|
||||||
public class ModuleAutoCrafting implements Module {
|
public class ModuleAutoCrafting implements Module {
|
||||||
|
|
||||||
private final Map<Material, Recipe> cachedRecipes = new HashMap<>();
|
private final Map<Material, Recipes> cachedRecipes = new HashMap<>();
|
||||||
private final Map<Hopper, Material> lastMaterial = new HashMap<>();
|
private final Map<Hopper, Material> lastMaterial = new HashMap<>();
|
||||||
|
|
||||||
public static List<ItemStack> compressItemStack(List<ItemStack> target) {
|
public static List<ItemStack> compressItemStack(List<ItemStack> target) {
|
||||||
@ -38,60 +38,64 @@ public class ModuleAutoCrafting implements Module {
|
|||||||
return "AutoCrafting";
|
return "AutoCrafting";
|
||||||
}
|
}
|
||||||
|
|
||||||
public void run(Hopper hopper, org.bukkit.block.Hopper hopperBlock) {
|
public void run(Hopper hopper, Inventory hopperInventory) {
|
||||||
if (hopper.getAutoCrafting() == null || hopperBlock == null || hopperBlock.getInventory() == null) return;
|
if (hopper.getAutoCrafting() == null || hopperInventory == null) return;
|
||||||
if (hopper.getAutoCrafting() != null && canMove(hopperBlock.getInventory(), new ItemStack(hopper.getAutoCrafting()))) {
|
|
||||||
|
if (hopper.getAutoCrafting() != null && canMove(hopperInventory, new ItemStack(hopper.getAutoCrafting()))) {
|
||||||
|
|
||||||
Recipe recipe = cachedRecipes.get(hopper.getAutoCrafting());
|
if (cachedRecipes.get(hopper.getAutoCrafting()) == null) return;
|
||||||
if (!(recipe instanceof ShapedRecipe) && !(recipe instanceof ShapelessRecipe)) return;
|
|
||||||
List<ItemStack> ingredientMap = null;
|
|
||||||
if (recipe instanceof ShapelessRecipe) ingredientMap = ((ShapelessRecipe) recipe).getIngredientList();
|
|
||||||
if (recipe instanceof ShapedRecipe)
|
|
||||||
ingredientMap = new ArrayList<>(((ShapedRecipe) recipe).getIngredientMap().values());
|
|
||||||
if (hopperBlock.getInventory().getSize() == 0) return;
|
|
||||||
|
|
||||||
Map<Material, Integer> items = new HashMap<>();
|
top:
|
||||||
for (ItemStack item : ingredientMap) {
|
for (Recipe recipe : cachedRecipes.get(hopper.getAutoCrafting()).getRecipes()) {
|
||||||
if (item == null) continue;
|
if (!(recipe instanceof ShapedRecipe) && !(recipe instanceof ShapelessRecipe)) continue;
|
||||||
if (!items.containsKey(item.getType())) {
|
List<ItemStack> ingredientMap = null;
|
||||||
items.put(item.getType(), item.getAmount());
|
if (recipe instanceof ShapelessRecipe) ingredientMap = ((ShapelessRecipe) recipe).getIngredientList();
|
||||||
} else {
|
if (recipe instanceof ShapedRecipe)
|
||||||
items.put(item.getType(), items.get(item.getType()) + 1);
|
ingredientMap = new ArrayList<>(((ShapedRecipe) recipe).getIngredientMap().values());
|
||||||
}
|
if (hopperInventory.getSize() == 0) return;
|
||||||
}
|
|
||||||
|
|
||||||
for (Material material : items.keySet()) {
|
Map<Material, Integer> items = new HashMap<>();
|
||||||
int amt = 0;
|
for (ItemStack item : ingredientMap) {
|
||||||
ItemStack item = new ItemStack(material, items.get(material));
|
if (item == null) continue;
|
||||||
for (ItemStack i : hopperBlock.getInventory().getContents()) {
|
if (!items.containsKey(item.getType())) {
|
||||||
if (i == null) continue;
|
items.put(item.getType(), item.getAmount());
|
||||||
if (i.getType() != material) continue;
|
|
||||||
amt += i.getAmount();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (amt < item.getAmount()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
main2:
|
|
||||||
for (Material material : items.keySet()) {
|
|
||||||
int amtRemoved = 0;
|
|
||||||
ItemStack toRemove = new ItemStack(material, items.get(material));
|
|
||||||
for (ItemStack i : hopperBlock.getInventory().getContents()) {
|
|
||||||
if (i == null || i.getType() != material) continue;
|
|
||||||
if (toRemove.getAmount() - amtRemoved <= i.getAmount()) {
|
|
||||||
toRemove.setAmount(toRemove.getAmount() - amtRemoved);
|
|
||||||
hopperBlock.getInventory().removeItem(toRemove);
|
|
||||||
continue main2;
|
|
||||||
} else {
|
} else {
|
||||||
amtRemoved += i.getAmount();
|
items.put(item.getType(), items.get(item.getType()) + 1);
|
||||||
hopperBlock.getInventory().removeItem(i);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
hopperBlock.getInventory().addItem(recipe.getResult());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
for (Material material : items.keySet()) {
|
||||||
|
int amt = 0;
|
||||||
|
ItemStack item = new ItemStack(material, items.get(material));
|
||||||
|
for (ItemStack i : hopperInventory.getContents()) {
|
||||||
|
if (i == null) continue;
|
||||||
|
if (i.getType() != material) continue;
|
||||||
|
amt += i.getAmount();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (amt < item.getAmount()) {
|
||||||
|
continue top;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
main2:
|
||||||
|
for (Material material : items.keySet()) {
|
||||||
|
int amtRemoved = 0;
|
||||||
|
ItemStack toRemove = new ItemStack(material, items.get(material));
|
||||||
|
for (ItemStack i : hopperInventory.getContents()) {
|
||||||
|
if (i == null || i.getType() != material) continue;
|
||||||
|
if (toRemove.getAmount() - amtRemoved <= i.getAmount()) {
|
||||||
|
toRemove.setAmount(toRemove.getAmount() - amtRemoved);
|
||||||
|
hopperInventory.removeItem(toRemove);
|
||||||
|
continue main2;
|
||||||
|
} else {
|
||||||
|
amtRemoved += i.getAmount();
|
||||||
|
hopperInventory.removeItem(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
hopperInventory.addItem(recipe.getResult());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<Material> getBlockedItems(Hopper hopper) {
|
public List<Material> getBlockedItems(Hopper hopper) {
|
||||||
@ -108,20 +112,24 @@ public class ModuleAutoCrafting implements Module {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!cachedRecipes.containsKey(material)) {
|
if (!cachedRecipes.containsKey(material)) {
|
||||||
|
Recipes recipes = new Recipes();
|
||||||
for (Recipe recipe : Bukkit.getServer().getRecipesFor(new ItemStack(material))) {
|
for (Recipe recipe : Bukkit.getServer().getRecipesFor(new ItemStack(material))) {
|
||||||
cachedRecipes.put(material, recipe);
|
recipes.addRecipe(recipe);
|
||||||
}
|
}
|
||||||
|
cachedRecipes.put(material, recipes);
|
||||||
} else {
|
} else {
|
||||||
Recipe recipe = cachedRecipes.get(material);
|
Recipes recipes = cachedRecipes.get(material);
|
||||||
if (recipe instanceof ShapedRecipe) {
|
for (Recipe recipe : recipes.getRecipes()) {
|
||||||
for (ItemStack itemStack : ((ShapedRecipe) recipe).getIngredientMap().values()) {
|
if (recipe instanceof ShapedRecipe) {
|
||||||
if (itemStack == null) continue;
|
for (ItemStack itemStack : ((ShapedRecipe) recipe).getIngredientMap().values()) {
|
||||||
materials.add(itemStack.getType());
|
if (itemStack == null) continue;
|
||||||
}
|
materials.add(itemStack.getType());
|
||||||
} else if (recipe instanceof ShapelessRecipe) {
|
}
|
||||||
for (ItemStack itemStack : ((ShapelessRecipe) recipe).getIngredientList()) {
|
} else if (recipe instanceof ShapelessRecipe) {
|
||||||
if (itemStack == null) continue;
|
for (ItemStack itemStack : ((ShapelessRecipe) recipe).getIngredientList()) {
|
||||||
materials.add(itemStack.getType());
|
if (itemStack == null) continue;
|
||||||
|
materials.add(itemStack.getType());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -148,4 +156,21 @@ public class ModuleAutoCrafting implements Module {
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class Recipes {
|
||||||
|
|
||||||
|
private List<Recipe> recipes = new ArrayList<>();
|
||||||
|
|
||||||
|
public List<Recipe> getRecipes() {
|
||||||
|
return new ArrayList<>(recipes);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void addRecipe(Recipe recipe) {
|
||||||
|
this.recipes.add(recipe);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void clearRecipes() {
|
||||||
|
recipes.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,6 +7,7 @@ import com.songoda.epichoppers.hopper.EHopper;
|
|||||||
import net.milkbowl.vault.economy.Economy;
|
import net.milkbowl.vault.economy.Economy;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.Material;
|
import org.bukkit.Material;
|
||||||
|
import org.bukkit.inventory.Inventory;
|
||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
import org.bukkit.plugin.RegisteredServiceProvider;
|
import org.bukkit.plugin.RegisteredServiceProvider;
|
||||||
|
|
||||||
@ -29,8 +30,8 @@ public class ModuleAutoSell implements Module {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void run(Hopper hopper, org.bukkit.block.Hopper hopperBlock) {
|
public void run(Hopper hopper, Inventory hopperInventory) {
|
||||||
if (hopperBlock == null || hopperBlock.getInventory() == null) return;
|
if (hopperInventory == null) return;
|
||||||
|
|
||||||
if (((EHopper) hopper).getAutoSellTimer() == -9999) return;
|
if (((EHopper) hopper).getAutoSellTimer() == -9999) return;
|
||||||
|
|
||||||
@ -50,11 +51,11 @@ public class ModuleAutoSell implements Module {
|
|||||||
Material material = Material.valueOf(split[0]);
|
Material material = Material.valueOf(split[0]);
|
||||||
double price = Double.valueOf(split[1]);
|
double price = Double.valueOf(split[1]);
|
||||||
|
|
||||||
for (ItemStack itemStack : hopperBlock.getInventory().getContents()) {
|
for (ItemStack itemStack : hopperInventory.getContents()) {
|
||||||
if (itemStack == null || itemStack.getType() != material) continue;
|
if (itemStack == null || itemStack.getType() != material) continue;
|
||||||
|
|
||||||
econ.depositPlayer(Bukkit.getOfflinePlayer(hopper.getPlacedBy()), price * itemStack.getAmount());
|
econ.depositPlayer(Bukkit.getOfflinePlayer(hopper.getPlacedBy()), price * itemStack.getAmount());
|
||||||
hopperBlock.getInventory().removeItem(itemStack);
|
hopperInventory.removeItem(itemStack);
|
||||||
}
|
}
|
||||||
} catch (Exception ignored) {
|
} catch (Exception ignored) {
|
||||||
}
|
}
|
||||||
|
@ -9,6 +9,7 @@ import org.bukkit.Material;
|
|||||||
import org.bukkit.Particle;
|
import org.bukkit.Particle;
|
||||||
import org.bukkit.Sound;
|
import org.bukkit.Sound;
|
||||||
import org.bukkit.block.Block;
|
import org.bukkit.block.Block;
|
||||||
|
import org.bukkit.inventory.Inventory;
|
||||||
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@ -29,7 +30,7 @@ public class ModuleBlockBreak implements Module {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void run(Hopper hopper, org.bukkit.block.Hopper hopperBlock) {
|
public void run(Hopper hopper, Inventory hopperInventory) {
|
||||||
Block block = hopper.getLocation().getBlock();
|
Block block = hopper.getLocation().getBlock();
|
||||||
|
|
||||||
if (!((EHopper)hopper).isAutoBreaking()) return;
|
if (!((EHopper)hopper).isAutoBreaking()) return;
|
||||||
|
@ -54,7 +54,7 @@ public class ModuleSuction implements Module {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void run(Hopper hopper, org.bukkit.block.Hopper hopperBlock) {
|
public void run(Hopper hopper, Inventory hopperInventory) {
|
||||||
double radius = amount + .5;
|
double radius = amount + .5;
|
||||||
|
|
||||||
Collection<Entity> nearbyEntite = hopper.getLocation().getWorld().getNearbyEntities(hopper.getLocation().add(0.5, 0.5, 0.5), radius, radius, radius);
|
Collection<Entity> nearbyEntite = hopper.getLocation().getWorld().getNearbyEntities(hopper.getLocation().add(0.5, 0.5, 0.5), radius, radius, radius);
|
||||||
@ -82,7 +82,7 @@ public class ModuleSuction implements Module {
|
|||||||
|
|
||||||
if (item == null) continue;
|
if (item == null) continue;
|
||||||
|
|
||||||
if (!canMove(hopperBlock.getInventory(), item)) {
|
if (!canMove(hopperInventory, item)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
((Item) entity).setPickupDelay(10);
|
((Item) entity).setPickupDelay(10);
|
||||||
@ -92,7 +92,7 @@ public class ModuleSuction implements Module {
|
|||||||
float zz = (float) (0 + (Math.random() * .1));
|
float zz = (float) (0 + (Math.random() * .1));
|
||||||
entity.getLocation().getWorld().spawnParticle(Particle.FLAME, entity.getLocation(), 5, xx, yy, zz, 0);
|
entity.getLocation().getWorld().spawnParticle(Particle.FLAME, entity.getLocation(), 5, xx, yy, zz, 0);
|
||||||
|
|
||||||
for (ItemStack itemStack : hopperBlock.getInventory().addItem(hopItem).values()) {
|
for (ItemStack itemStack : hopperInventory.addItem(hopItem).values()) {
|
||||||
entity.getWorld().dropItemNaturally(entity.getLocation(), itemStack);
|
entity.getWorld().dropItemNaturally(entity.getLocation(), itemStack);
|
||||||
}
|
}
|
||||||
entity.remove();
|
entity.remove();
|
||||||
|
@ -14,6 +14,7 @@ import org.bukkit.Material;
|
|||||||
import org.bukkit.block.BlockFace;
|
import org.bukkit.block.BlockFace;
|
||||||
import org.bukkit.entity.Player;
|
import org.bukkit.entity.Player;
|
||||||
import org.bukkit.event.EventHandler;
|
import org.bukkit.event.EventHandler;
|
||||||
|
import org.bukkit.event.EventPriority;
|
||||||
import org.bukkit.event.Listener;
|
import org.bukkit.event.Listener;
|
||||||
import org.bukkit.event.block.Action;
|
import org.bukkit.event.block.Action;
|
||||||
import org.bukkit.event.player.PlayerInteractEvent;
|
import org.bukkit.event.player.PlayerInteractEvent;
|
||||||
@ -52,7 +53,7 @@ public class InteractListeners implements Listener {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@EventHandler
|
@EventHandler(priority = EventPriority.HIGHEST, ignoreCancelled = true)
|
||||||
public void onBlockInteract(PlayerInteractEvent e) {
|
public void onBlockInteract(PlayerInteractEvent e) {
|
||||||
try {
|
try {
|
||||||
Player player = e.getPlayer();
|
Player player = e.getPlayer();
|
||||||
|
@ -4,12 +4,10 @@ import com.songoda.epichoppers.EpicHoppersPlugin;
|
|||||||
import com.songoda.epichoppers.storage.Storage;
|
import com.songoda.epichoppers.storage.Storage;
|
||||||
import com.songoda.epichoppers.storage.StorageItem;
|
import com.songoda.epichoppers.storage.StorageItem;
|
||||||
import com.songoda.epichoppers.storage.StorageRow;
|
import com.songoda.epichoppers.storage.StorageRow;
|
||||||
import org.apache.commons.io.FileUtils;
|
|
||||||
import org.bukkit.configuration.ConfigurationSection;
|
import org.bukkit.configuration.ConfigurationSection;
|
||||||
import org.bukkit.configuration.MemorySection;
|
import org.bukkit.configuration.MemorySection;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.*;
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
public class StorageYaml extends Storage {
|
public class StorageYaml extends Storage {
|
||||||
@ -110,7 +108,7 @@ public class StorageYaml extends Storage {
|
|||||||
File data = new File(instance.getDataFolder(), "data.yml");
|
File data = new File(instance.getDataFolder(), "data.yml");
|
||||||
File dataClone = new File(instance.getDataFolder(), "data-backup-" + System.currentTimeMillis() + ".yml");
|
File dataClone = new File(instance.getDataFolder(), "data-backup-" + System.currentTimeMillis() + ".yml");
|
||||||
try {
|
try {
|
||||||
FileUtils.copyFile(data, dataClone);
|
copyFile(data, dataClone);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@ -129,4 +127,21 @@ public class StorageYaml extends Storage {
|
|||||||
public void closeConnection() {
|
public void closeConnection() {
|
||||||
dataFile.saveConfig();
|
dataFile.saveConfig();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static void copyFile(File source, File dest) throws IOException {
|
||||||
|
InputStream is = null;
|
||||||
|
OutputStream os = null;
|
||||||
|
try {
|
||||||
|
is = new FileInputStream(source);
|
||||||
|
os = new FileOutputStream(dest);
|
||||||
|
byte[] buffer = new byte[1024];
|
||||||
|
int length;
|
||||||
|
while ((length = is.read(buffer)) > 0) {
|
||||||
|
os.write(buffer, 0, length);
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
is.close();
|
||||||
|
os.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,372 @@
|
|||||||
|
package com.songoda.epichoppers.tasks;
|
||||||
|
|
||||||
|
import com.songoda.epichoppers.EpicHoppersPlugin;
|
||||||
|
import com.songoda.epichoppers.api.hopper.levels.modules.Module;
|
||||||
|
import com.songoda.epichoppers.boost.BoostData;
|
||||||
|
import com.songoda.epichoppers.utils.SettingsManager;
|
||||||
|
import org.bukkit.Bukkit;
|
||||||
|
import org.bukkit.Location;
|
||||||
|
import org.bukkit.Material;
|
||||||
|
import org.bukkit.OfflinePlayer;
|
||||||
|
import org.bukkit.block.Block;
|
||||||
|
import org.bukkit.block.BlockState;
|
||||||
|
import org.bukkit.block.Hopper;
|
||||||
|
import org.bukkit.entity.Entity;
|
||||||
|
import org.bukkit.entity.EntityType;
|
||||||
|
import org.bukkit.entity.minecart.HopperMinecart;
|
||||||
|
import org.bukkit.entity.minecart.StorageMinecart;
|
||||||
|
import org.bukkit.inventory.*;
|
||||||
|
import org.bukkit.scheduler.BukkitRunnable;
|
||||||
|
|
||||||
|
import java.util.*;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Created by songoda on 3/14/2017.
|
||||||
|
*/
|
||||||
|
public class HopTask extends BukkitRunnable {
|
||||||
|
|
||||||
|
private static EpicHoppersPlugin plugin;
|
||||||
|
|
||||||
|
public HopTask(EpicHoppersPlugin plug) {
|
||||||
|
plugin = plug;
|
||||||
|
runTaskTimer(plugin, 0, SettingsManager.Setting.HOP_TICKS.getInt());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
main:
|
||||||
|
for (com.songoda.epichoppers.api.hopper.Hopper hopper : new HashMap<>(plugin.getHopperManager().getHoppers()).values()) {
|
||||||
|
Location location = hopper.getLocation();
|
||||||
|
|
||||||
|
if (location.getWorld() == null || !location.getWorld().isChunkLoaded(location.getBlockX() >> 4, location.getBlockZ() >> 4))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
Block block = location.getBlock();
|
||||||
|
|
||||||
|
if (block.getType() != Material.HOPPER) {
|
||||||
|
plugin.getHopperManager().removeHopper(location);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.isBlockPowered() || block.isBlockIndirectlyPowered()) continue;
|
||||||
|
|
||||||
|
Hopper hopperState = (Hopper) block.getState();
|
||||||
|
Inventory hopperInventory = hopperState.getInventory();
|
||||||
|
|
||||||
|
List<Material> blockedMaterials = new ArrayList<>();
|
||||||
|
|
||||||
|
for (Module module : hopper.getLevel().getRegisteredModules()) {
|
||||||
|
// Run Module
|
||||||
|
module.run(hopper, hopperInventory);
|
||||||
|
|
||||||
|
// Add banned materials to list.
|
||||||
|
List<Material> materials = module.getBlockedItems(hopper);
|
||||||
|
if (materials == null || materials.isEmpty()) continue;
|
||||||
|
blockedMaterials.addAll(materials);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fetch all hopper contents.
|
||||||
|
ItemStack[] hopperContents = hopperInventory.getContents();
|
||||||
|
|
||||||
|
Inventory override = null;
|
||||||
|
List<Location> linked = hopper.getLinkedBlocks();
|
||||||
|
|
||||||
|
if (hopper.getLinkedBlocks() == null || hopper.getLinkedBlocks().isEmpty()) {
|
||||||
|
HopperDirection hopperDirection = HopperDirection.getDirection(hopperState.getRawData());
|
||||||
|
Location check = hopperDirection.getLocation(location);
|
||||||
|
|
||||||
|
linked.add(check);
|
||||||
|
|
||||||
|
Collection<Entity> nearbyEntities = hopper.getLocation().getWorld().getNearbyEntities(check, .5, .5, .5);
|
||||||
|
|
||||||
|
for (Entity entity : nearbyEntities) {
|
||||||
|
if (entity.getType() == EntityType.MINECART_HOPPER)
|
||||||
|
override = ((HopperMinecart) entity).getInventory();
|
||||||
|
else if (entity.getType() == EntityType.MINECART_CHEST)
|
||||||
|
override = ((StorageMinecart) entity).getInventory();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (linked.isEmpty()) continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (Location destinationLocation : linked) {
|
||||||
|
Block destinationBlock = destinationLocation.getBlock();
|
||||||
|
Inventory destinationInventory = override;
|
||||||
|
if (override == null) {
|
||||||
|
|
||||||
|
if (!destinationLocation.getWorld().isChunkLoaded(destinationLocation.getBlockX() >> 4,
|
||||||
|
destinationLocation.getBlockZ() >> 4))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
destinationBlock = destinationLocation.getBlock();
|
||||||
|
BlockState state = destinationBlock.getState();
|
||||||
|
if (!(state instanceof InventoryHolder)) {
|
||||||
|
hopper.clearLinkedBlocks();
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
destinationInventory = ((InventoryHolder) state).getInventory();
|
||||||
|
}
|
||||||
|
|
||||||
|
BoostData boostData = plugin.getBoostManager().getBoost(hopper.getPlacedBy());
|
||||||
|
|
||||||
|
int amount = hopper.getLevel().getAmount() * (boostData == null ? 1 : boostData.getMultiplier());
|
||||||
|
|
||||||
|
List<ItemStack> whiteList = hopper.getFilter().getWhiteList();
|
||||||
|
List<ItemStack> blackList = hopper.getFilter().getBlackList();
|
||||||
|
|
||||||
|
for (int i = 0; i < 5; i++) {
|
||||||
|
if (hopperContents[i] == null) continue;
|
||||||
|
|
||||||
|
ItemStack item = hopperContents[i].clone();
|
||||||
|
item.setAmount(1);
|
||||||
|
|
||||||
|
if (hopper.getLocation().getBlock().isBlockPowered()
|
||||||
|
|| hopperContents[i] != null && blockedMaterials.contains(hopperContents[i].getType())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
int finalIncrement = i;
|
||||||
|
|
||||||
|
if (!whiteList.isEmpty()
|
||||||
|
&& whiteList.stream().noneMatch(itemStack -> itemStack.isSimilar(hopperContents[finalIncrement]))) {
|
||||||
|
doBlacklist(hopperInventory, hopper, hopperContents[i].clone(), amount, i);
|
||||||
|
continue main;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (blackList.stream().noneMatch(itemStack -> itemStack.isSimilar(hopperContents[finalIncrement]))) {
|
||||||
|
if (addItem(hopperInventory, hopper, destinationInventory, destinationBlock, hopperContents[i], amount, i)) {
|
||||||
|
continue main;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (hopper.getFilter().getEndPoint() == null) continue;
|
||||||
|
|
||||||
|
doBlacklist(hopperInventory, hopper, hopperContents[i].clone(), amount, i);
|
||||||
|
continue main;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private void doBlacklist(Inventory hopperInventory, com.songoda.epichoppers.api.hopper.Hopper hopper, ItemStack item, int amt, int place) {
|
||||||
|
Location dest = hopper.getFilter().getEndPoint();
|
||||||
|
if (!dest.getWorld().isChunkLoaded(dest.getBlockX() >> 4, dest.getBlockZ() >> 4))
|
||||||
|
return;
|
||||||
|
|
||||||
|
Block destinationBlock = dest.getBlock();
|
||||||
|
BlockState state = destinationBlock.getState();
|
||||||
|
if (!(state instanceof InventoryHolder)) {
|
||||||
|
hopper.getFilter().setEndPoint(null);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
Inventory destinationInventory = ((InventoryHolder) state).getInventory();
|
||||||
|
|
||||||
|
addItem(hopperInventory, hopper, destinationInventory, destinationBlock, item, amt, place);
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean addItem(Inventory hopperInventory, com.songoda.epichoppers.api.hopper.Hopper hopper, Inventory destinationInventory, Block destinationBlock, ItemStack is, int amt, int place) {
|
||||||
|
ItemStack it = null;
|
||||||
|
if (is != null) {
|
||||||
|
it = is.clone();
|
||||||
|
it.setAmount(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
List<ItemStack> ovoid = new ArrayList<>(hopper.getFilter().getVoidList());
|
||||||
|
|
||||||
|
if (is.getType() == Material.AIR) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
ItemStack item = is;
|
||||||
|
ItemStack newItem = is.clone();
|
||||||
|
|
||||||
|
if ((item.getAmount() - amt) <= 0) {
|
||||||
|
amt = item.getAmount();
|
||||||
|
}
|
||||||
|
if ((item.getAmount() - amt) >= 1) {
|
||||||
|
newItem.setAmount(newItem.getAmount() - amt);
|
||||||
|
is = newItem.clone();
|
||||||
|
} else {
|
||||||
|
is = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
newItem.setAmount(amt);
|
||||||
|
|
||||||
|
if (destinationBlock.getType().equals(Material.ENDER_CHEST)) {
|
||||||
|
OfflinePlayer op = Bukkit.getOfflinePlayer(hopper.getPlacedBy());
|
||||||
|
|
||||||
|
if (op.isOnline() && canMove(op.getPlayer().getEnderChest(), newItem)) {
|
||||||
|
ItemStack finalIt = it;
|
||||||
|
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
||||||
|
op.getPlayer().getEnderChest().addItem(newItem);
|
||||||
|
}
|
||||||
|
hopperInventory.setItem(place, is);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (destinationBlock.getType()) {
|
||||||
|
case BLACK_SHULKER_BOX:
|
||||||
|
case BLUE_SHULKER_BOX:
|
||||||
|
case BROWN_SHULKER_BOX:
|
||||||
|
case CYAN_SHULKER_BOX:
|
||||||
|
case GRAY_SHULKER_BOX:
|
||||||
|
case GREEN_SHULKER_BOX:
|
||||||
|
case LIGHT_BLUE_SHULKER_BOX:
|
||||||
|
case LIGHT_GRAY_SHULKER_BOX:
|
||||||
|
case LIME_SHULKER_BOX:
|
||||||
|
case MAGENTA_SHULKER_BOX:
|
||||||
|
case ORANGE_SHULKER_BOX:
|
||||||
|
case PINK_SHULKER_BOX:
|
||||||
|
case PURPLE_SHULKER_BOX:
|
||||||
|
case RED_SHULKER_BOX:
|
||||||
|
case SHULKER_BOX:
|
||||||
|
case WHITE_SHULKER_BOX:
|
||||||
|
case YELLOW_SHULKER_BOX:
|
||||||
|
return false;
|
||||||
|
case BREWING_STAND: {
|
||||||
|
BrewerInventory brewerInventory = (BrewerInventory) destinationInventory;
|
||||||
|
|
||||||
|
int maxSize = newItem.getMaxStackSize();
|
||||||
|
|
||||||
|
String typeStr = item.getType().name().toUpperCase();
|
||||||
|
boolean isBottle = typeStr.contains("POTION") || typeStr.contains("BOTTLE") || item.getType() == Material.DRAGON_BREATH;
|
||||||
|
boolean isLeft = item.getType() == Material.BLAZE_POWDER;
|
||||||
|
|
||||||
|
Map<Integer, ItemStack> output = new HashMap<>();
|
||||||
|
if (isBottle) {
|
||||||
|
output.put(0, brewerInventory.getItem(0));
|
||||||
|
output.put(1, brewerInventory.getItem(1));
|
||||||
|
output.put(2, brewerInventory.getItem(2));
|
||||||
|
} else if (isLeft) {
|
||||||
|
output.put(4, brewerInventory.getItem(4));
|
||||||
|
} else {
|
||||||
|
output.put(3, brewerInventory.getItem(3));
|
||||||
|
}
|
||||||
|
|
||||||
|
ItemStack finalIt = it;
|
||||||
|
for (Map.Entry<Integer, ItemStack> entry : output.entrySet()) {
|
||||||
|
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
||||||
|
ItemStack currentOutput = entry.getValue();
|
||||||
|
int currentOutputAmount = currentOutput == null ? 0 : currentOutput.getAmount();
|
||||||
|
if (currentOutput != null && (!currentOutput.isSimilar(newItem))
|
||||||
|
|| currentOutputAmount + newItem.getAmount() > maxSize) continue;
|
||||||
|
|
||||||
|
if (currentOutput != null) {
|
||||||
|
currentOutput.setAmount(currentOutputAmount + newItem.getAmount());
|
||||||
|
} else {
|
||||||
|
currentOutput = newItem.clone();
|
||||||
|
}
|
||||||
|
|
||||||
|
brewerInventory.setItem(entry.getKey(), currentOutput);
|
||||||
|
}
|
||||||
|
hopperInventory.setItem(place, is);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case FURNACE: {
|
||||||
|
FurnaceInventory furnaceInventory = (FurnaceInventory) destinationInventory;
|
||||||
|
|
||||||
|
boolean isFuel = item.getType().isFuel() && !item.getType().name().contains("LOG");
|
||||||
|
ItemStack output = isFuel ? furnaceInventory.getFuel() : furnaceInventory.getSmelting();
|
||||||
|
if (output != null && !output.isSimilar(newItem)) return false;
|
||||||
|
int maxSize = newItem.getMaxStackSize();
|
||||||
|
int currentOutputAmount = output == null ? 0 : output.getAmount();
|
||||||
|
|
||||||
|
if (currentOutputAmount + newItem.getAmount() <= maxSize) {
|
||||||
|
ItemStack finalIt = it;
|
||||||
|
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
||||||
|
if (output != null) {
|
||||||
|
output.setAmount(currentOutputAmount + newItem.getAmount());
|
||||||
|
} else {
|
||||||
|
output = newItem.clone();
|
||||||
|
}
|
||||||
|
if (isFuel) {
|
||||||
|
furnaceInventory.setFuel(output);
|
||||||
|
} else {
|
||||||
|
furnaceInventory.setSmelting(output);
|
||||||
|
}
|
||||||
|
hopperInventory.setItem(place, is);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!canMove(destinationInventory, newItem)) return false;
|
||||||
|
ItemStack finalIt = it;
|
||||||
|
if (ovoid.stream().noneMatch(itemStack -> itemStack.isSimilar(finalIt))) {
|
||||||
|
destinationInventory.addItem(newItem);
|
||||||
|
}
|
||||||
|
hopperInventory.setItem(place, is);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean canMove(Inventory inventory, ItemStack item) {
|
||||||
|
if (inventory.firstEmpty() != -1) return true;
|
||||||
|
for (ItemStack stack : inventory.getContents()) {
|
||||||
|
if (stack.isSimilar(item) && (stack.getAmount() + item.getAmount()) - 1 < stack.getMaxStackSize()) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum HopperDirection {
|
||||||
|
|
||||||
|
DOWN(0, 8, 0, -1, 0),
|
||||||
|
NORTH(2, 10, 0, 0, -1),
|
||||||
|
SOUTH(3, 11, 0, 0, 1),
|
||||||
|
WEST(4, 12, -1, 0, 0),
|
||||||
|
EAST(5, 13, 1, 0, 0);
|
||||||
|
|
||||||
|
private int unpowered;
|
||||||
|
private int powered;
|
||||||
|
|
||||||
|
private int x;
|
||||||
|
private int y;
|
||||||
|
private int z;
|
||||||
|
|
||||||
|
HopperDirection(int unpowered, int powered, int x, int y, int z) {
|
||||||
|
this.unpowered = unpowered;
|
||||||
|
this.powered = powered;
|
||||||
|
|
||||||
|
this.x = x;
|
||||||
|
this.y = y;
|
||||||
|
this.z = z;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static HopperDirection getDirection(int value) {
|
||||||
|
for (HopperDirection hopperDirection : HopperDirection.values()) {
|
||||||
|
if (hopperDirection.getPowered() == value
|
||||||
|
|| hopperDirection.getUnpowered() == value) return hopperDirection;
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Location getLocation(Location location) {
|
||||||
|
return location.add(getX(), getY(), getZ());
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getX() {
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getY() {
|
||||||
|
return y;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getZ() {
|
||||||
|
return z;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getUnpowered() {
|
||||||
|
return unpowered;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getPowered() {
|
||||||
|
return powered;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -43,14 +43,14 @@ public class SettingsManager implements Listener {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (event.getInventory().getTitle().equals(pluginName + " Settings Manager")) {
|
if (event.getView().getTitle().equals(pluginName + " Settings Manager")) {
|
||||||
event.setCancelled(true);
|
event.setCancelled(true);
|
||||||
if (clickedItem.getType().name().contains("STAINED_GLASS")) return;
|
if (clickedItem.getType().name().contains("STAINED_GLASS")) return;
|
||||||
|
|
||||||
String type = ChatColor.stripColor(clickedItem.getItemMeta().getDisplayName());
|
String type = ChatColor.stripColor(clickedItem.getItemMeta().getDisplayName());
|
||||||
this.cat.put((Player) event.getWhoClicked(), type);
|
this.cat.put((Player) event.getWhoClicked(), type);
|
||||||
this.openEditor((Player) event.getWhoClicked());
|
this.openEditor((Player) event.getWhoClicked());
|
||||||
} else if (event.getInventory().getTitle().equals(pluginName + " Settings Editor")) {
|
} else if (event.getView().getTitle().equals(pluginName + " Settings Editor")) {
|
||||||
event.setCancelled(true);
|
event.setCancelled(true);
|
||||||
if (clickedItem.getType().name().contains("STAINED_GLASS")) return;
|
if (clickedItem.getType().name().contains("STAINED_GLASS")) return;
|
||||||
|
|
||||||
@ -82,7 +82,9 @@ public class SettingsManager implements Listener {
|
|||||||
config.set(value, event.getMessage());
|
config.set(value, event.getMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
this.finishEditing(player);
|
Bukkit.getScheduler().scheduleSyncDelayedTask(EpicHoppersPlugin.getInstance(), () ->
|
||||||
|
this.finishEditing(player), 0L);
|
||||||
|
|
||||||
event.setCancelled(true);
|
event.setCancelled(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -211,5 +213,20 @@ public class SettingsManager implements Listener {
|
|||||||
this.option = option;
|
this.option = option;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<String> getStringList() {
|
||||||
|
return EpicHoppersPlugin.getInstance().getConfig().getStringList(setting);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean getBoolean() {
|
||||||
|
return EpicHoppersPlugin.getInstance().getConfig().getBoolean(setting);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getInt() {
|
||||||
|
return EpicHoppersPlugin.getInstance().getConfig().getInt(setting);
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getString() {
|
||||||
|
return EpicHoppersPlugin.getInstance().getConfig().getString(setting);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,270 +0,0 @@
|
|||||||
package com.songoda.epichoppers.utils.gui;
|
|
||||||
|
|
||||||
import com.songoda.epichoppers.EpicHoppersPlugin;
|
|
||||||
import com.songoda.epichoppers.utils.version.NMSUtil;
|
|
||||||
import org.bukkit.Bukkit;
|
|
||||||
import org.bukkit.Sound;
|
|
||||||
import org.bukkit.entity.Player;
|
|
||||||
import org.bukkit.event.EventHandler;
|
|
||||||
import org.bukkit.event.HandlerList;
|
|
||||||
import org.bukkit.event.Listener;
|
|
||||||
import org.bukkit.event.inventory.InventoryClickEvent;
|
|
||||||
import org.bukkit.event.inventory.InventoryCloseEvent;
|
|
||||||
import org.bukkit.event.player.PlayerQuitEvent;
|
|
||||||
import org.bukkit.inventory.Inventory;
|
|
||||||
import org.bukkit.inventory.ItemStack;
|
|
||||||
import org.bukkit.inventory.meta.ItemMeta;
|
|
||||||
|
|
||||||
import java.lang.reflect.Constructor;
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
public class AbstractAnvilGUI {
|
|
||||||
|
|
||||||
private static Class<?> BlockPosition;
|
|
||||||
private static Class<?> PacketPlayOutOpenWindow;
|
|
||||||
private static Class<?> ContainerAnvil;
|
|
||||||
private static Class<?> ChatMessage;
|
|
||||||
private static Class<?> EntityHuman;
|
|
||||||
private static boolean loadedClasses = false;
|
|
||||||
private Player player;
|
|
||||||
@SuppressWarnings("unused")
|
|
||||||
private AnvilClickEventHandler handler;
|
|
||||||
private Map<AnvilSlot, ItemStack> items = new HashMap<>();
|
|
||||||
private OnClose onClose = null;
|
|
||||||
private Inventory inv;
|
|
||||||
private Listener listener;
|
|
||||||
|
|
||||||
private Sound closeSound = Sound.ENTITY_PLAYER_LEVELUP;
|
|
||||||
|
|
||||||
public AbstractAnvilGUI(final Player player, final AnvilClickEventHandler handler) {
|
|
||||||
loadClasses();
|
|
||||||
this.player = player;
|
|
||||||
this.handler = handler;
|
|
||||||
|
|
||||||
this.listener = new Listener() {
|
|
||||||
@EventHandler
|
|
||||||
public void onInventoryClick(InventoryClickEvent event) {
|
|
||||||
if (!(event.getWhoClicked() instanceof Player) || !event.getInventory().equals(inv)) return;
|
|
||||||
|
|
||||||
event.setCancelled(true);
|
|
||||||
|
|
||||||
ItemStack item = event.getCurrentItem();
|
|
||||||
int slot = event.getRawSlot();
|
|
||||||
String name = "";
|
|
||||||
|
|
||||||
if (item != null) {
|
|
||||||
if (item.hasItemMeta()) {
|
|
||||||
ItemMeta meta = item.getItemMeta();
|
|
||||||
|
|
||||||
if (meta.hasDisplayName()) {
|
|
||||||
name = meta.getDisplayName();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
AnvilClickEvent clickEvent = new AnvilClickEvent(AnvilSlot.bySlot(slot), name);
|
|
||||||
|
|
||||||
handler.onAnvilClick(clickEvent);
|
|
||||||
|
|
||||||
if (clickEvent.getWillClose()) {
|
|
||||||
event.getWhoClicked().closeInventory();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (clickEvent.getWillDestroy()) {
|
|
||||||
destroy();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@EventHandler
|
|
||||||
public void onInventoryClose(InventoryCloseEvent event) {
|
|
||||||
if (!(event.getPlayer() instanceof Player)) return;
|
|
||||||
Inventory inv = event.getInventory();
|
|
||||||
player.setLevel(player.getLevel() - 1);
|
|
||||||
if (!inv.equals(AbstractAnvilGUI.this.inv)) return;
|
|
||||||
inv.clear();
|
|
||||||
OnClose onClose = getOnClose();
|
|
||||||
player.playSound(player.getLocation(), closeSound, 1F, 1F);
|
|
||||||
Bukkit.getScheduler().scheduleSyncDelayedTask(EpicHoppersPlugin.getInstance(), () -> {
|
|
||||||
if (onClose != null) onClose.OnClose(player, inv);
|
|
||||||
destroy();
|
|
||||||
}, 1L);
|
|
||||||
}
|
|
||||||
|
|
||||||
@EventHandler
|
|
||||||
public void onPlayerQuit(PlayerQuitEvent event) {
|
|
||||||
if (!event.getPlayer().equals(getPlayer())) return;
|
|
||||||
player.setLevel(player.getLevel() - 1);
|
|
||||||
destroy();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
Bukkit.getPluginManager().registerEvents(listener, EpicHoppersPlugin.getInstance());
|
|
||||||
}
|
|
||||||
|
|
||||||
private void loadClasses() {
|
|
||||||
if (loadedClasses) return;
|
|
||||||
BlockPosition = NMSUtil.getNMSClass("BlockPosition");
|
|
||||||
PacketPlayOutOpenWindow = NMSUtil.getNMSClass("PacketPlayOutOpenWindow");
|
|
||||||
ContainerAnvil = NMSUtil.getNMSClass("ContainerAnvil");
|
|
||||||
EntityHuman = NMSUtil.getNMSClass("EntityHuman");
|
|
||||||
ChatMessage = NMSUtil.getNMSClass("ChatMessage");
|
|
||||||
loadedClasses = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Player getPlayer() {
|
|
||||||
return player;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setSlot(AnvilSlot slot, ItemStack item) {
|
|
||||||
items.put(slot, item);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void open() {
|
|
||||||
player.setLevel(player.getLevel() + 1);
|
|
||||||
|
|
||||||
try {
|
|
||||||
Object craftPlayer = NMSUtil.getCraftClass("entity.CraftPlayer").cast(player);
|
|
||||||
Method getHandleMethod = craftPlayer.getClass().getMethod("getHandle", new Class<?>[0]);
|
|
||||||
Object entityPlayer = getHandleMethod.invoke(craftPlayer, new Object[0]);
|
|
||||||
|
|
||||||
Object container;
|
|
||||||
|
|
||||||
if (NMSUtil.getVersionNumber() == 7) {
|
|
||||||
container = ContainerAnvil.getConstructor(new Class[]{NMSUtil.getNMSClass("PlayerInventory"), NMSUtil.getNMSClass("World"), Integer.TYPE, Integer.TYPE, Integer.TYPE, EntityHuman}).newInstance(new Object[]{NMSUtil.getFieldObject(entityPlayer, NMSUtil.getField(entityPlayer.getClass(), "inventory", false)), NMSUtil.getFieldObject(entityPlayer, NMSUtil.getField(entityPlayer.getClass(), "world", false)), Integer.valueOf(0), Integer.valueOf(0), Integer.valueOf(0), entityPlayer});
|
|
||||||
} else {
|
|
||||||
container = ContainerAnvil.getConstructor(NMSUtil.getNMSClass("PlayerInventory"), NMSUtil.getNMSClass("World"), BlockPosition, EntityHuman).newInstance(NMSUtil.getFieldObject(entityPlayer, NMSUtil.getField(entityPlayer.getClass(), "inventory", false)), NMSUtil.getFieldObject(entityPlayer, NMSUtil.getField(entityPlayer.getClass(), "world", false)), BlockPosition.getConstructor(int.class, int.class, int.class).newInstance(0, 0, 0), entityPlayer);
|
|
||||||
}
|
|
||||||
|
|
||||||
NMSUtil.getField(NMSUtil.getNMSClass("Container"), "checkReachable", true).set(container, false);
|
|
||||||
|
|
||||||
Method getBukkitViewMethod = container.getClass().getMethod("getBukkitView", new Class<?>[0]);
|
|
||||||
Object bukkitView = getBukkitViewMethod.invoke(container);
|
|
||||||
Method getTopInventoryMethod = bukkitView.getClass().getMethod("getTopInventory", new Class<?>[0]);
|
|
||||||
inv = (Inventory) getTopInventoryMethod.invoke(bukkitView);
|
|
||||||
|
|
||||||
for (AnvilSlot slot : items.keySet()) {
|
|
||||||
inv.setItem(slot.getSlot(), items.get(slot));
|
|
||||||
}
|
|
||||||
|
|
||||||
Method nextContainerCounterMethod = entityPlayer.getClass().getMethod("nextContainerCounter", new Class<?>[0]);
|
|
||||||
int c = (int) nextContainerCounterMethod.invoke(entityPlayer);
|
|
||||||
|
|
||||||
Constructor<?> chatMessageConstructor = ChatMessage.getConstructor(String.class, Object[].class);
|
|
||||||
Object packet;
|
|
||||||
|
|
||||||
if (NMSUtil.getVersionNumber() == 7) {
|
|
||||||
packet = PacketPlayOutOpenWindow.getConstructor(new Class[]{Integer.TYPE, Integer.TYPE, String.class, Integer.TYPE, Boolean.TYPE, Integer.TYPE}).newInstance(new Object[]{Integer.valueOf(c), Integer.valueOf(8), "Repairing", Integer.valueOf(0), Boolean.valueOf(true), Integer.valueOf(0)});
|
|
||||||
} else {
|
|
||||||
packet = PacketPlayOutOpenWindow.getConstructor(int.class, String.class, NMSUtil.getNMSClass("IChatBaseComponent"), int.class).newInstance(c, "minecraft:anvil", chatMessageConstructor.newInstance("Repairing", new Object[]{}), 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
NMSUtil.sendPacket(player, packet);
|
|
||||||
|
|
||||||
Field activeContainerField = NMSUtil.getField(EntityHuman, "activeContainer", true);
|
|
||||||
|
|
||||||
if (activeContainerField != null) {
|
|
||||||
activeContainerField.set(entityPlayer, container);
|
|
||||||
NMSUtil.getField(NMSUtil.getNMSClass("Container"), "windowId", true).set(activeContainerField.get(entityPlayer), c);
|
|
||||||
|
|
||||||
Method addSlotListenerMethod = activeContainerField.get(entityPlayer).getClass().getMethod("addSlotListener", NMSUtil.getNMSClass("ICrafting"));
|
|
||||||
addSlotListenerMethod.invoke(activeContainerField.get(entityPlayer), entityPlayer);
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void destroy() {
|
|
||||||
onClose = null;
|
|
||||||
player = null;
|
|
||||||
handler = null;
|
|
||||||
items = null;
|
|
||||||
|
|
||||||
HandlerList.unregisterAll(listener);
|
|
||||||
|
|
||||||
listener = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private OnClose getOnClose() {
|
|
||||||
return onClose;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setOnClose(OnClose onClose) {
|
|
||||||
this.onClose = onClose;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setCloseSound(Sound sound) {
|
|
||||||
closeSound = sound;
|
|
||||||
}
|
|
||||||
|
|
||||||
public enum AnvilSlot {
|
|
||||||
INPUT_LEFT(0),
|
|
||||||
INPUT_RIGHT(1),
|
|
||||||
OUTPUT(2);
|
|
||||||
|
|
||||||
private int slot;
|
|
||||||
|
|
||||||
private AnvilSlot(int slot) {
|
|
||||||
this.slot = slot;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static AnvilSlot bySlot(int slot) {
|
|
||||||
for (AnvilSlot anvilSlot : values()) {
|
|
||||||
if (anvilSlot.getSlot() == slot) {
|
|
||||||
return anvilSlot;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getSlot() {
|
|
||||||
return slot;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public interface AnvilClickEventHandler {
|
|
||||||
void onAnvilClick(AnvilClickEvent event);
|
|
||||||
}
|
|
||||||
|
|
||||||
public class AnvilClickEvent {
|
|
||||||
private AnvilSlot slot;
|
|
||||||
|
|
||||||
private String name;
|
|
||||||
|
|
||||||
private boolean close = true;
|
|
||||||
private boolean destroy = true;
|
|
||||||
|
|
||||||
public AnvilClickEvent(AnvilSlot slot, String name) {
|
|
||||||
this.slot = slot;
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public AnvilSlot getSlot() {
|
|
||||||
return slot;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getName() {
|
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean getWillClose() {
|
|
||||||
return close;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setWillClose(boolean close) {
|
|
||||||
this.close = close;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean getWillDestroy() {
|
|
||||||
return destroy;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setWillDestroy(boolean destroy) {
|
|
||||||
this.destroy = destroy;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -114,7 +114,7 @@ public abstract class AbstractGUI implements Listener {
|
|||||||
protected void init(String title, int slots) {
|
protected void init(String title, int slots) {
|
||||||
if (inventory == null
|
if (inventory == null
|
||||||
|| inventory.getSize() != slots
|
|| inventory.getSize() != slots
|
||||||
|| ChatColor.translateAlternateColorCodes('&', title) != inventory.getTitle()) {
|
|| !ChatColor.translateAlternateColorCodes('&', title).equals(player.getOpenInventory().getTitle())) {
|
||||||
this.inventory = Bukkit.getServer().createInventory(new GUIHolder(), slots, ChatColor.translateAlternateColorCodes('&', title));
|
this.inventory = Bukkit.getServer().createInventory(new GUIHolder(), slots, ChatColor.translateAlternateColorCodes('&', title));
|
||||||
registerClickables();
|
registerClickables();
|
||||||
registerOnCloses();
|
registerOnCloses();
|
||||||
|
@ -1,100 +0,0 @@
|
|||||||
package com.songoda.epichoppers.utils.version;
|
|
||||||
|
|
||||||
import org.bukkit.Bukkit;
|
|
||||||
import org.bukkit.entity.Player;
|
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
|
|
||||||
public class NMSUtil {
|
|
||||||
|
|
||||||
public static String getVersion() {
|
|
||||||
String name = Bukkit.getServer().getClass().getPackage().getName();
|
|
||||||
return name.substring(name.lastIndexOf('.') + 1) + ".";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getVersionNumber() {
|
|
||||||
String name = getVersion().substring(3);
|
|
||||||
return Integer.valueOf(name.substring(0, name.length() - 4));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getVersionReleaseNumber() {
|
|
||||||
String NMSVersion = getVersion();
|
|
||||||
return Integer.valueOf(NMSVersion.substring(NMSVersion.length() - 2).replace(".", ""));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Class<?> getNMSClass(String className) {
|
|
||||||
try {
|
|
||||||
String fullName = "net.minecraft.server." + getVersion() + className;
|
|
||||||
Class<?> clazz = Class.forName(fullName);
|
|
||||||
return clazz;
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Class<?> getCraftClass(String className) throws ClassNotFoundException {
|
|
||||||
try {
|
|
||||||
String fullName = "org.bukkit.craftbukkit." + getVersion() + className;
|
|
||||||
Class<?> clazz = Class.forName(fullName);
|
|
||||||
return clazz;
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Field getField(Class<?> clazz, String name, boolean declared) {
|
|
||||||
try {
|
|
||||||
Field field;
|
|
||||||
|
|
||||||
if (declared) {
|
|
||||||
field = clazz.getDeclaredField(name);
|
|
||||||
} else {
|
|
||||||
field = clazz.getField(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
field.setAccessible(true);
|
|
||||||
return field;
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Object getFieldObject(Object object, Field field) {
|
|
||||||
try {
|
|
||||||
return field.get(object);
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void setField(Object object, String fieldName, Object fieldValue, boolean declared) {
|
|
||||||
try {
|
|
||||||
Field field;
|
|
||||||
|
|
||||||
if (declared) {
|
|
||||||
field = object.getClass().getDeclaredField(fieldName);
|
|
||||||
} else {
|
|
||||||
field = object.getClass().getField(fieldName);
|
|
||||||
}
|
|
||||||
|
|
||||||
field.setAccessible(true);
|
|
||||||
field.set(object, fieldValue);
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void sendPacket(Player player, Object packet) {
|
|
||||||
try {
|
|
||||||
Object handle = player.getClass().getMethod("getHandle").invoke(player);
|
|
||||||
Object playerConnection = handle.getClass().getField("playerConnection").get(handle);
|
|
||||||
playerConnection.getClass().getMethod("sendPacket", getNMSClass("Packet")).invoke(playerConnection, packet);
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
2
pom.xml
2
pom.xml
@ -16,7 +16,7 @@
|
|||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.spigotmc</groupId>
|
<groupId>org.spigotmc</groupId>
|
||||||
<artifactId>spigot</artifactId>
|
<artifactId>spigot</artifactId>
|
||||||
<version>1.13.2</version>
|
<version>1.14-pre5</version>
|
||||||
<scope>provided</scope>
|
<scope>provided</scope>
|
||||||
</dependency>
|
</dependency>
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
Loading…
Reference in New Issue
Block a user