mirror of
https://github.com/JEFF-Media-GbR/ChestSort.git
synced 2024-12-04 16:44:00 +01:00
8.15.0 release
This commit is contained in:
parent
1cfdea420d
commit
1692a7008d
@ -1,5 +1,8 @@
|
|||||||
# Changelog
|
# Changelog
|
||||||
|
|
||||||
|
## 8.15.0
|
||||||
|
- Enabled left-click and right-click hotkey for 3rd party plugins implementing the ISortable interface from ChestSort's API (You only need this update if you use plugins depending on the ChestSortAPI)
|
||||||
|
|
||||||
## 8.14.2
|
## 8.14.2
|
||||||
- Made CrateReloaded hook and HeadDatabase hook toggleable
|
- Made CrateReloaded hook and HeadDatabase hook toggleable
|
||||||
- Fixed wrong version number in plugin.yml
|
- Fixed wrong version number in plugin.yml
|
||||||
|
2
pom.xml
2
pom.xml
@ -9,7 +9,7 @@
|
|||||||
<name>ChestSort</name>
|
<name>ChestSort</name>
|
||||||
<url>https://www.chestsort.de</url>
|
<url>https://www.chestsort.de</url>
|
||||||
<description>Automatically sorts your chests!</description>
|
<description>Automatically sorts your chests!</description>
|
||||||
<version>9.0.0-SNAPSHOT</version>
|
<version>8.15.0</version>
|
||||||
<packaging>jar</packaging>
|
<packaging>jar</packaging>
|
||||||
|
|
||||||
<properties>
|
<properties>
|
||||||
|
@ -479,7 +479,8 @@ public class ChestSortListener implements Listener {
|
|||||||
&& e.getInventory().getType() != InventoryType.DROPPER
|
&& e.getInventory().getType() != InventoryType.DROPPER
|
||||||
&& e.getInventory().getType() != InventoryType.ENDER_CHEST
|
&& e.getInventory().getType() != InventoryType.ENDER_CHEST
|
||||||
&& !e.getInventory().getType().name().equalsIgnoreCase("SHULKER_BOX")
|
&& !e.getInventory().getType().name().equalsIgnoreCase("SHULKER_BOX")
|
||||||
&& (e.getInventory().getHolder() == null || !e.getInventory().getHolder().getClass().toString().endsWith(".CraftBarrel"))) {
|
&& (e.getInventory().getHolder() == null || !e.getInventory().getHolder().getClass().toString().endsWith(".CraftBarrel"))
|
||||||
|
&& !(e.getInventory().getHolder() instanceof ISortable)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -462,7 +462,6 @@ public class ChestSortPlugin extends JavaPlugin implements de.jeff_media.ChestSo
|
|||||||
sortingMethod = getConfig().getString("sorting-method");
|
sortingMethod = getConfig().getString("sorting-method");
|
||||||
getServer().getPluginManager().registerEvents(listener, this);
|
getServer().getPluginManager().registerEvents(listener, this);
|
||||||
getServer().getPluginManager().registerEvents(settingsGUI, this);
|
getServer().getPluginManager().registerEvents(settingsGUI, this);
|
||||||
getServer().getPluginManager().registerEvents(new ToolUtils(), this);
|
|
||||||
ChestSortChestSortCommand chestsortCommandExecutor = new ChestSortChestSortCommand(this);
|
ChestSortChestSortCommand chestsortCommandExecutor = new ChestSortChestSortCommand(this);
|
||||||
ChestSortTabCompleter tabCompleter = new ChestSortTabCompleter();
|
ChestSortTabCompleter tabCompleter = new ChestSortTabCompleter();
|
||||||
this.getCommand("sort").setExecutor(chestsortCommandExecutor);
|
this.getCommand("sort").setExecutor(chestsortCommandExecutor);
|
||||||
|
@ -1,338 +0,0 @@
|
|||||||
package de.jeff_media.ChestSort;
|
|
||||||
|
|
||||||
import org.bukkit.Material;
|
|
||||||
import org.bukkit.Tag;
|
|
||||||
import org.bukkit.block.Block;
|
|
||||||
import org.bukkit.event.EventHandler;
|
|
||||||
import org.bukkit.event.Listener;
|
|
||||||
import org.bukkit.event.block.Action;
|
|
||||||
import org.bukkit.event.player.PlayerInteractEvent;
|
|
||||||
import org.bukkit.inventory.ItemStack;
|
|
||||||
import org.bukkit.inventory.PlayerInventory;
|
|
||||||
import org.bukkit.inventory.meta.Damageable;
|
|
||||||
import org.bukkit.inventory.meta.ItemMeta;
|
|
||||||
import org.jetbrains.annotations.NotNull;
|
|
||||||
import org.jetbrains.annotations.Nullable;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Objects;
|
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
public class ToolUtils implements Listener {
|
|
||||||
|
|
||||||
// Configurable
|
|
||||||
boolean hotbarOnly = false;
|
|
||||||
|
|
||||||
static int hotbarSize = 9;
|
|
||||||
static int inventorySize = 36;
|
|
||||||
static int favoriteSlot = hotbarSize-1;
|
|
||||||
|
|
||||||
HashMap<Material,Tool> toolMap = new HashMap<>();
|
|
||||||
ArrayList<Tag> usedTags = new ArrayList<>();
|
|
||||||
final Material[] pickaxes = {
|
|
||||||
Material.NETHERITE_PICKAXE,
|
|
||||||
Material.DIAMOND_PICKAXE,
|
|
||||||
Material.IRON_PICKAXE,
|
|
||||||
Material.STONE_PICKAXE,
|
|
||||||
Material.WOODEN_PICKAXE};
|
|
||||||
final Material[] axes = {
|
|
||||||
Material.NETHERITE_AXE,
|
|
||||||
Material.DIAMOND_AXE,
|
|
||||||
Material.IRON_AXE,
|
|
||||||
Material.STONE_AXE,
|
|
||||||
Material.WOODEN_AXE};
|
|
||||||
final Material[] shovels = {
|
|
||||||
Material.NETHERITE_SHOVEL,
|
|
||||||
Material.DIAMOND_SHOVEL,
|
|
||||||
Material.IRON_SHOVEL,
|
|
||||||
Material.STONE_SHOVEL,
|
|
||||||
Material.WOODEN_SHOVEL};
|
|
||||||
|
|
||||||
final Material[] hoes = {
|
|
||||||
Material.NETHERITE_HOE,
|
|
||||||
Material.DIAMOND_HOE,
|
|
||||||
Material.IRON_HOE,
|
|
||||||
Material.STONE_HOE,
|
|
||||||
Material.WOODEN_HOE};
|
|
||||||
|
|
||||||
ToolUtils() {
|
|
||||||
initMap();
|
|
||||||
}
|
|
||||||
|
|
||||||
enum Tool {
|
|
||||||
PICKAXE,
|
|
||||||
SHOVEL,
|
|
||||||
SHEARS,
|
|
||||||
AXE,
|
|
||||||
HOE,
|
|
||||||
NONE
|
|
||||||
}
|
|
||||||
|
|
||||||
private void initMap() {
|
|
||||||
long startTime = System.nanoTime();
|
|
||||||
tagToMap(Tag.ANVIL,Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.BEEHIVES,Tool.AXE);
|
|
||||||
tagToMap(Tag.CRIMSON_STEMS,Tool.AXE);
|
|
||||||
tagToMap(Tag.BAMBOO_PLANTABLE_ON,Tool.SHOVEL);
|
|
||||||
tagToMap(Tag.ICE,Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.LOGS,Tool.AXE);
|
|
||||||
tagToMap(Tag.PLANKS,Tool.AXE);
|
|
||||||
tagToMap(Tag.RAILS,Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.SIGNS,Tool.AXE);
|
|
||||||
|
|
||||||
tagToMap(Tag.WALLS,Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.WOOL,Tool.SHEARS);
|
|
||||||
|
|
||||||
tagToMap(Tag.CROPS,Tool.NONE);
|
|
||||||
tagToMap(Tag.FENCE_GATES,Tool.AXE);
|
|
||||||
tagToMap(Tag.FENCES,Tool.AXE);
|
|
||||||
tagToMap(Tag.FLOWERS,Tool.NONE);
|
|
||||||
tagToMap(Tag.LEAVES,Tool.SHEARS);
|
|
||||||
|
|
||||||
// Order is important
|
|
||||||
tagToMap(Tag.PRESSURE_PLATES, Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.WOODEN_PRESSURE_PLATES,Tool.AXE);
|
|
||||||
tagToMap(Tag.DOORS,Tool.AXE);
|
|
||||||
tagToMap(Tag.DOORS,Tool.PICKAXE,"IRON");
|
|
||||||
tagToMap(Tag.TRAPDOORS,Tool.AXE);
|
|
||||||
tagToMap(Tag.TRAPDOORS,Tool.PICKAXE,"IRON");
|
|
||||||
tagToMap(Tag.BUTTONS,Tool.AXE);
|
|
||||||
tagToMap(Tag.BUTTONS,Tool.PICKAXE,"STONE");
|
|
||||||
|
|
||||||
tagToMap(Tag.SAND,Tool.SHOVEL);
|
|
||||||
tagToMap(Tag.SHULKER_BOXES,Tool.PICKAXE);
|
|
||||||
tagToMap(Tag.STONE_BRICKS,Tool.PICKAXE);
|
|
||||||
|
|
||||||
addToMap(Material.VINE,Tool.SHEARS);
|
|
||||||
long endTime = System.nanoTime();
|
|
||||||
printMap();
|
|
||||||
System.out.println(String.format("Building the map took %d ms",(endTime-startTime)/1000000));
|
|
||||||
}
|
|
||||||
|
|
||||||
private void printMap() {
|
|
||||||
toolMap.forEach((mat, tool) -> System.out.println(String.format("%0$30s -> %s", mat.name(), tool.name())));
|
|
||||||
}
|
|
||||||
|
|
||||||
private void addToMap(Material mat, Tool tool) {
|
|
||||||
toolMap.put(mat, tool);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void tagToMap(Tag<Material> tag, Tool tool) {
|
|
||||||
/*for(Material mat : tag.getValues() ) {
|
|
||||||
addToMap(mat,tool);
|
|
||||||
}*/
|
|
||||||
tagToMap(tag,tool,null);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void tagToMap(Tag<Material> tag, Tool tool, @Nullable String match) {
|
|
||||||
for(Material mat : tag.getValues()) {
|
|
||||||
if(match==null) {
|
|
||||||
addToMap(mat,tool);
|
|
||||||
} else {
|
|
||||||
if (mat.name().contains(match)) {
|
|
||||||
addToMap(mat,tool);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
usedTags.add(tag);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the best tool type for a material
|
|
||||||
* @param mat The block's material
|
|
||||||
* @return Best tool type for that material
|
|
||||||
*/
|
|
||||||
@NotNull
|
|
||||||
Tool getBestToolType(Material mat) {
|
|
||||||
Tool bestTool = toolMap.get(mat);
|
|
||||||
if(bestTool == null) bestTool = Tool.NONE;
|
|
||||||
System.out.println("Best ToolType for "+mat+" is "+bestTool.name());
|
|
||||||
return bestTool;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Searches through and array and returns the ItemStack that matches this material
|
|
||||||
* @param mat Material to look for
|
|
||||||
* @param items Player's items (whole inventory or hotbar)
|
|
||||||
* @return Matching ItemStack
|
|
||||||
*/
|
|
||||||
@Nullable
|
|
||||||
ItemStack getItemStackFromArray(Material mat, ItemStack[] items) {
|
|
||||||
for(ItemStack item : items) {
|
|
||||||
if(item==null) continue;
|
|
||||||
if(item.getType()==mat) return item;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Searches the player's inventory for the best matching tool and returns its ItemStack
|
|
||||||
* @param type Tool type
|
|
||||||
* @param items Player's items (whole inventory or hotbar)
|
|
||||||
* @return
|
|
||||||
*/
|
|
||||||
@Nullable
|
|
||||||
ItemStack typeToItem(Tool type, ItemStack[] items) {
|
|
||||||
|
|
||||||
Objects.requireNonNull(type,"type cannot be null.");
|
|
||||||
|
|
||||||
switch(type) {
|
|
||||||
|
|
||||||
case PICKAXE:
|
|
||||||
for(Material pickaxe : pickaxes) {
|
|
||||||
ItemStack itemStack = getItemStackFromArray(pickaxe, items);
|
|
||||||
if(itemStack != null) return itemStack;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
|
|
||||||
case AXE:
|
|
||||||
for(Material axe : axes) {
|
|
||||||
ItemStack itemStack = getItemStackFromArray(axe, items);
|
|
||||||
if(itemStack != null) return itemStack;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
|
|
||||||
case SHOVEL:
|
|
||||||
for(Material shovel : shovels) {
|
|
||||||
ItemStack itemStack = getItemStackFromArray(shovel, items);
|
|
||||||
if(itemStack != null) return itemStack;
|
|
||||||
}
|
|
||||||
System.out.println("typeToItem -> shovel -> null");
|
|
||||||
return null;
|
|
||||||
|
|
||||||
case HOE:
|
|
||||||
for(Material hoe : hoes) {
|
|
||||||
ItemStack itemStack = getItemStackFromArray(hoe, items);
|
|
||||||
if(itemStack != null) return itemStack;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
|
|
||||||
case SHEARS:
|
|
||||||
return getItemStackFromArray(Material.SHEARS, items);
|
|
||||||
|
|
||||||
default:
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Tries to get the ItemStack that is the best for this block
|
|
||||||
* @param mat The block's material
|
|
||||||
* @param inv Player's inventory
|
|
||||||
* @return
|
|
||||||
*/
|
|
||||||
@Nullable
|
|
||||||
ItemStack getBestToolFromInventory(Material mat, PlayerInventory inv) {
|
|
||||||
ItemStack[] hotbar = new ItemStack[(hotbarOnly ? hotbarSize : inventorySize)];
|
|
||||||
Tool bestType = getBestToolType(mat);
|
|
||||||
for(int i = 0; i < (hotbarOnly ? hotbarSize : inventorySize); i++) {
|
|
||||||
hotbar[i] = inv.getItem(i);
|
|
||||||
}
|
|
||||||
ItemStack debug = typeToItem(bestType,hotbar);
|
|
||||||
if(debug == null) System.out.println("debug == null");
|
|
||||||
return debug;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@EventHandler
|
|
||||||
public void onPlayerInteract(PlayerInteractEvent event) {
|
|
||||||
if (event.getAction() != Action.LEFT_CLICK_BLOCK) return;
|
|
||||||
/*if (event.getHand() != EquipmentSlot.HAND)
|
|
||||||
return;*/
|
|
||||||
|
|
||||||
PlayerInventory inv = event.getPlayer().getInventory();
|
|
||||||
Block block = event.getClickedBlock();
|
|
||||||
if (block == null) return;
|
|
||||||
|
|
||||||
ItemStack bestTool = getBestToolFromInventory(block.getType(), inv);
|
|
||||||
if(bestTool == null) {
|
|
||||||
freeSlot(favoriteSlot,inv);
|
|
||||||
//System.out.println("Could not find any appropiate tool");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
int positionInInventory = getPositionInInventory(bestTool,inv) ;
|
|
||||||
if(positionInInventory != 0) {
|
|
||||||
moveToolToSlot(positionInInventory,favoriteSlot,inv);
|
|
||||||
} else {
|
|
||||||
freeSlot(favoriteSlot,inv);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the slot number of a given ItemStack
|
|
||||||
* @param item ItemStack that we need the slot number of
|
|
||||||
* @param inv Player's inventory
|
|
||||||
* @return
|
|
||||||
*/
|
|
||||||
int getPositionInInventory(ItemStack item, PlayerInventory inv) {
|
|
||||||
for(int i = 0; i < inv.getSize(); i++) {
|
|
||||||
ItemStack currentItem = inv.getItem(i);
|
|
||||||
if(currentItem==null) continue;
|
|
||||||
if(currentItem.equals(item)) {
|
|
||||||
System.out.println(String.format("Found perfect tool %s at slot %d",currentItem.getType().name(),i));
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Moves a tool to the given slot
|
|
||||||
* @param source Slot where the tool is
|
|
||||||
* @param dest Slot where the tool should be
|
|
||||||
* @param inv Player's inventory
|
|
||||||
*/
|
|
||||||
private void moveToolToSlot(int source, int dest, PlayerInventory inv) {
|
|
||||||
System.out.println(String.format("Moving item from slot %d to %d",source,dest));
|
|
||||||
inv.setHeldItemSlot(dest);
|
|
||||||
if(source==dest) return;
|
|
||||||
ItemStack sourceItem = inv.getItem(source);
|
|
||||||
ItemStack destItem = inv.getItem(dest);
|
|
||||||
if(source < hotbarSize) {
|
|
||||||
inv.setHeldItemSlot(source);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if(destItem == null) {
|
|
||||||
inv.setItem(dest,sourceItem);
|
|
||||||
inv.setItem(source,null);
|
|
||||||
} else {
|
|
||||||
inv.setItem(source, destItem);
|
|
||||||
inv.setItem(dest, sourceItem);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Tries to free the slot if it is occupied with a damageable item
|
|
||||||
* @param source Slot to free
|
|
||||||
* @param inv Player's inventory
|
|
||||||
*/
|
|
||||||
private void freeSlot(int source, PlayerInventory inv) {
|
|
||||||
System.out.println(String.format("Trying to free slot %d",source));
|
|
||||||
ItemStack item = inv.getItem(source);
|
|
||||||
|
|
||||||
// If current slot is empty, we don't have to change it
|
|
||||||
if(item == null) return;
|
|
||||||
|
|
||||||
// If the item is not damageable, we don't have to move it
|
|
||||||
ItemMeta meta = item.getItemMeta();
|
|
||||||
if(!(meta instanceof Damageable)) return;
|
|
||||||
|
|
||||||
// Try to combine the item with existing stacks
|
|
||||||
inv.setItem(source, null);
|
|
||||||
inv.addItem(item);
|
|
||||||
|
|
||||||
// If the item was moved to the same slot, we have to move it somewhere else
|
|
||||||
if(inv.getItem(source)==null) return;
|
|
||||||
for(int i = source; i < inventorySize; i++) {
|
|
||||||
if(inv.getItem(i)==null) {
|
|
||||||
inv.setItem(i,item);
|
|
||||||
inv.setItem(source,null);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// TODO: If all of that didn't work, change to some block that is not damageable
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,6 +1,6 @@
|
|||||||
main: de.jeff_media.ChestSort.ChestSortPlugin
|
main: de.jeff_media.ChestSort.ChestSortPlugin
|
||||||
name: ChestSort
|
name: ChestSort
|
||||||
version: 9.0.0-SNAPSHOT
|
version: 8.15.0
|
||||||
api-version: "1.13"
|
api-version: "1.13"
|
||||||
description: Allows automatic chest sorting
|
description: Allows automatic chest sorting
|
||||||
author: mfnalex
|
author: mfnalex
|
||||||
|
Loading…
Reference in New Issue
Block a user