From 61efa519c29a72aba7a8f70a4eb37c7f714fca69 Mon Sep 17 00:00:00 2001 From: Jules Date: Fri, 26 Jul 2024 15:32:48 -0700 Subject: [PATCH] Minor performance improvement for custom mining --- .../Indyuce/mmocore/api/block/BlockInfo.java | 5 +- .../Indyuce/mmocore/api/block/BlockType.java | 40 +++---- .../mmocore/api/block/SkullBlockType.java | 87 ++++++++------ .../mmocore/api/block/VanillaBlockType.java | 106 ++++++++++-------- .../mmocore/manager/RestrictionManager.java | 14 +-- .../profession/CustomBlockManager.java | 12 +- 6 files changed, 146 insertions(+), 118 deletions(-) diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockInfo.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockInfo.java index 204808c4..c56047e2 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockInfo.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockInfo.java @@ -43,7 +43,7 @@ public class BlockInfo { options.put(option, config.getBoolean("options." + key)); } catch (IllegalArgumentException exception) { MMOCore.plugin.getLogger().log(Level.WARNING, - "Could not load option '" + key + "' from block info '" + block.generateKey() + "': " + exception.getMessage()); + "Could not load option '" + key + "' from block info '" + block.display() + "': " + exception.getMessage()); } if (config.contains("triggers")) { @@ -55,7 +55,7 @@ public class BlockInfo { triggers.add(MMOCore.plugin.loadManager.loadTrigger(new MMOLineConfig(key))); } catch (IllegalArgumentException exception) { MMOCore.plugin.getLogger().log(Level.WARNING, - "Could not load trigger '" + key + "' from block info '" + block.generateKey() + "': " + exception.getMessage()); + "Could not load trigger '" + key + "' from block info '" + block.display() + "': " + exception.getMessage()); } } @@ -71,6 +71,7 @@ public class BlockInfo { return options.getOrDefault(option, option.getDefault()); } + @NotNull public BlockType getBlock() { return block; } diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockType.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockType.java index f375f96f..7626c0b3 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockType.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/BlockType.java @@ -1,29 +1,31 @@ package net.Indyuce.mmocore.api.block; import org.bukkit.block.Block; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; public interface BlockType { - /** - * Called when placing temporary blocks - */ - void place(BlockInfo.RegeneratingBlock placed); + /** + * Called when placing temporary blocks + */ + void place(@NotNull BlockInfo.RegeneratingBlock placed); - /** - * Called when regenerating an older block with block regen - */ - void regenerate(BlockInfo.RegeneratingBlock regenerating); + /** + * Called when regenerating an older block with block regen + */ + void regenerate(@NotNull BlockInfo.RegeneratingBlock regenerating); - /** - * Generates a key used to store the BlockInfo instance in the manager map, - * the key depends on the block type to make sure there is no interference - */ - String generateKey(); + @NotNull String display(); - /** - * Applies some extra break restrictions; returns TRUE if the block can be - * broken. This method is used to prevent non mature crops from being broken - * for example - */ - boolean breakRestrictions(Block block); + /** + * Applies some extra break restrictions; returns TRUE if the block can be + * broken. This method is used to prevent non mature crops from being broken + * for example + */ + boolean breakRestrictions(@NotNull Block block); + + int hashCode(); + + boolean equals(@Nullable Object obj); } diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/SkullBlockType.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/SkullBlockType.java index 02474f10..61d2cac5 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/SkullBlockType.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/SkullBlockType.java @@ -8,51 +8,66 @@ import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.block.Block; +import java.util.Objects; + public class SkullBlockType implements BlockType { - private final String value; + private final String value; - public SkullBlockType(MMOLineConfig config) { - config.validate("value"); + public SkullBlockType(MMOLineConfig config) { + config.validate("value"); - value = config.getString("value"); - } + value = config.getString("value"); + } - public SkullBlockType(Block block) { - value = MythicLib.plugin.getVersion().getWrapper().getSkullValue(block); - } + public SkullBlockType(Block block) { + value = MythicLib.plugin.getVersion().getWrapper().getSkullValue(block); + } - public String getValue() { - return value; - } + public String getValue() { + return value; + } - @Override - public void place(RegeneratingBlock block) { - Location loc = block.getLocation(); - loc.getBlock().setType(Material.PLAYER_HEAD); + @Override + public void place(RegeneratingBlock block) { + Location loc = block.getLocation(); + loc.getBlock().setType(Material.PLAYER_HEAD); - // save skull orientation if replaced block is a player head - if (MMOCoreUtils.isPlayerHead(block.getBlockData().getMaterial())) - loc.getBlock().setBlockData(block.getBlockData()); + // save skull orientation if replaced block is a player head + if (MMOCoreUtils.isPlayerHead(block.getBlockData().getMaterial())) + loc.getBlock().setBlockData(block.getBlockData()); - MythicLib.plugin.getVersion().getWrapper().setSkullValue(loc.getBlock(), value); - } + MythicLib.plugin.getVersion().getWrapper().setSkullValue(loc.getBlock(), value); + } - @Override - public void regenerate(RegeneratingBlock block) { - Location loc = block.getLocation(); - // This makes sure that if a skull loses its original rotation - // it can revert back to it when the base block is regenerated - loc.getBlock().setBlockData(block.getBlockData()); - MythicLib.plugin.getVersion().getWrapper().setSkullValue(loc.getBlock(), value); - } + @Override + public void regenerate(RegeneratingBlock block) { + Location loc = block.getLocation(); + // This makes sure that if a skull loses its original rotation + // it can revert back to it when the base block is regenerated + loc.getBlock().setBlockData(block.getBlockData()); + MythicLib.plugin.getVersion().getWrapper().setSkullValue(loc.getBlock(), value); + } - @Override - public String generateKey() { - return "vanilla-skull-" + value; - } + @Override + public String display() { + return "Skull{" + value + "}"; + } - @Override - public boolean breakRestrictions(Block block) { - return true; - } + @Override + public boolean breakRestrictions(Block block) { + return true; + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + SkullBlockType that = (SkullBlockType) o; + return Objects.equals(value, that.value); + } + + @Override + public int hashCode() { + return Objects.hash(value); + } } diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/VanillaBlockType.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/VanillaBlockType.java index e0076cf0..84dafe93 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/VanillaBlockType.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/api/block/VanillaBlockType.java @@ -1,5 +1,7 @@ package net.Indyuce.mmocore.api.block; +import io.lumine.mythic.lib.api.MMOLineConfig; +import net.Indyuce.mmocore.api.block.BlockInfo.RegeneratingBlock; import org.apache.commons.lang.Validate; import org.bukkit.Location; import org.bukkit.Material; @@ -7,63 +9,75 @@ import org.bukkit.block.Block; import org.bukkit.block.data.Ageable; import org.bukkit.block.data.BlockData; -import net.Indyuce.mmocore.api.block.BlockInfo.RegeneratingBlock; -import io.lumine.mythic.lib.api.MMOLineConfig; +import java.util.Objects; public class VanillaBlockType implements BlockType { - private final Material type; + private final Material type; - /* - * allows to plant back crops with a custom age so that it does not always - * have to full grow again- - */ - private final int age; + /* + * allows to plant back crops with a custom age so that it does not always + * have to full grow again- + */ + private final int age; - public VanillaBlockType(MMOLineConfig config) { - config.validate("type"); + public VanillaBlockType(MMOLineConfig config) { + config.validate("type"); - type = Material.valueOf(config.getString("type").toUpperCase().replace("-", "_").replace(" ", "_")); - age = config.getInt("age", 0); + type = Material.valueOf(config.getString("type").toUpperCase().replace("-", "_").replace(" ", "_")); + age = config.getInt("age", 0); - Validate.isTrue(age >= 0 && age < 8, "Age must be between 0 and 7"); - } + Validate.isTrue(age >= 0 && age < 8, "Age must be between 0 and 7"); + } - public VanillaBlockType(Block block) { - type = block.getType(); - age = 0; - } + public VanillaBlockType(Block block) { + type = block.getType(); + age = 0; + } - public Material getType() { - return type; - } + public Material getType() { + return type; + } - @Override - public void place(RegeneratingBlock block) { - Location loc = block.getLocation(); - block.getLocation().getBlock().setType(type); + @Override + public void place(RegeneratingBlock block) { + Location loc = block.getLocation(); + block.getLocation().getBlock().setType(type); - BlockData state = block.getLocation().getBlock().getBlockData(); - if (age > 0 && state instanceof Ageable) { - ((Ageable) state).setAge(age); - loc.getBlock().setBlockData(state); - } - } + BlockData state = block.getLocation().getBlock().getBlockData(); + if (age > 0 && state instanceof Ageable) { + ((Ageable) state).setAge(age); + loc.getBlock().setBlockData(state); + } + } - @Override - public void regenerate(RegeneratingBlock block) { - Location loc = block.getLocation(); - loc.getBlock().setType(type); - // Sets the original blocks old data (only when regenerating) - loc.getBlock().setBlockData(block.getBlockData()); - } + @Override + public void regenerate(RegeneratingBlock block) { + Location loc = block.getLocation(); + loc.getBlock().setType(type); + // Sets the original blocks old data (only when regenerating) + loc.getBlock().setBlockData(block.getBlockData()); + } - @Override - public String generateKey() { - return "vanilla-block-" + type.name(); - } + @Override + public String display() { + return "Vanilla{" + type.name() + "}"; + } - @Override - public boolean breakRestrictions(Block block) { - return age == 0 || (block.getBlockData() instanceof Ageable && ((Ageable) block.getBlockData()).getAge() >= age); - } + @Override + public boolean breakRestrictions(Block block) { + return age == 0 || (block.getBlockData() instanceof Ageable && ((Ageable) block.getBlockData()).getAge() >= age); + } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + VanillaBlockType that = (VanillaBlockType) o; + return type == that.type; + } + + @Override + public int hashCode() { + return Objects.hash(type); + } } diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/RestrictionManager.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/RestrictionManager.java index ef791afa..2dd9b5e9 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/RestrictionManager.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/RestrictionManager.java @@ -91,13 +91,7 @@ public class RestrictionManager implements MMOCoreManager { } public class ToolPermissions implements PreloadedObject { - - /** - * Now saving string keys using {@link BlockType#generateKey()} instead - * of iterating through the set to take advantage of the O(1) time - * complexity of hash sets. - */ - private final Set mineable = new HashSet<>(); + private final Set mineable = new HashSet<>(); private final ItemType tool; private final boolean defaultSet; @@ -112,7 +106,7 @@ public class RestrictionManager implements MMOCoreManager { } if (config.contains("can-mine")) for (String key : config.getStringList("can-mine")) - mineable.add(MMOCore.plugin.loadManager.loadBlockType(new MMOLineConfig(key)).generateKey()); + mineable.add(MMOCore.plugin.loadManager.loadBlockType(new MMOLineConfig(key))); }); public ToolPermissions(ConfigurationSection config) { @@ -138,9 +132,9 @@ public class RestrictionManager implements MMOCoreManager { * @param type Block being broken * @return If the given block can be broken */ - public boolean canMine(BlockType type) { + public boolean canMine(@NotNull BlockType type) { ToolPermissions parent; - return mineable.contains(type.generateKey()) || ((parent = getParent()) != null && parent.canMine(type)); + return mineable.contains(type) || ((parent = getParent()) != null && parent.canMine(type)); } /** diff --git a/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/profession/CustomBlockManager.java b/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/profession/CustomBlockManager.java index cbdd0ec4..20a4d11b 100644 --- a/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/profession/CustomBlockManager.java +++ b/MMOCore-API/src/main/java/net/Indyuce/mmocore/manager/profession/CustomBlockManager.java @@ -15,6 +15,7 @@ import org.bukkit.Location; import org.bukkit.block.Block; import org.bukkit.configuration.ConfigurationSection; import org.bukkit.entity.Entity; +import org.jetbrains.annotations.NotNull; import javax.annotation.Nullable; import java.util.*; @@ -26,7 +27,7 @@ public class CustomBlockManager extends SpecificProfessionManager { /** * Registered block infos */ - private final Map map = new HashMap<>(); + private final Map map = new HashMap<>(); /** * Blocks that are regenerating and that must be refreshed whenever the @@ -57,8 +58,8 @@ public class CustomBlockManager extends SpecificProfessionManager { blockTypes.add(function); } - public void register(BlockInfo regen) { - map.put(regen.getBlock().generateKey(), regen); + public void register(@NotNull BlockInfo regen) { + map.put(regen.getBlock(), regen); } /** @@ -68,10 +69,11 @@ public class CustomBlockManager extends SpecificProfessionManager { * @param block Block to check * @return The new block behaviour or null if no new behaviour */ - public @Nullable BlockInfo getInfo(Block block) { - return map.get(findBlockType(block).generateKey()); + public @Nullable BlockInfo getInfo(@NotNull Block block) { + return map.get(findBlockType(block)); } + @NotNull public BlockType findBlockType(Block block) { for (Function> blockType : blockTypes) { Optional type = blockType.apply(block);