9
0
mirror of https://github.com/Xiao-MoMi/Custom-Fishing.git synced 2025-12-28 03:19:12 +00:00

enchantment pool

This commit is contained in:
XiaoMoMi
2023-11-11 20:23:44 +08:00
parent eb3e9bdcb6
commit 3b0d3b9147
11 changed files with 235 additions and 7 deletions

View File

@@ -229,7 +229,9 @@ public class CustomFishingPluginImpl extends CustomFishingPlugin {
"xyz.xenondevs.invui:inventory-access-r12:1.23", "https://repo.xenondevs.xyz/releases/",
"xyz.xenondevs.invui:inventory-access-r13:1.23", "https://repo.xenondevs.xyz/releases/",
"xyz.xenondevs.invui:inventory-access-r14:1.23", "https://repo.xenondevs.xyz/releases/",
"xyz.xenondevs.invui:inventory-access-r15:1.23", "https://repo.xenondevs.xyz/releases/"
"xyz.xenondevs.invui:inventory-access-r15:1.23", "https://repo.xenondevs.xyz/releases/",
"xyz.xenondevs.invui:inventory-access-r16:1.23", "https://repo.xenondevs.xyz/releases/",
"xyz.xenondevs.invui:inventory-access-r17:1.23", "https://repo.xenondevs.xyz/releases/"
);
}

View File

@@ -32,6 +32,7 @@ import net.momirealms.customfishing.api.mechanic.condition.FishingPreparation;
import net.momirealms.customfishing.api.mechanic.effect.EffectCarrier;
import net.momirealms.customfishing.api.mechanic.effect.EffectModifier;
import net.momirealms.customfishing.api.mechanic.effect.FishingEffect;
import org.bukkit.Material;
import java.util.ArrayList;
import java.util.List;
@@ -110,6 +111,10 @@ public class DebugCommand {
StringTooltip.ofString("false", "loots in water")
})))
.executesPlayer((player, arg) -> {
if (player.getInventory().getItemInMainHand().getType() != Material.FISHING_ROD) {
AdventureManagerImpl.getInstance().sendMessageWithPrefix(player, "<red>Please hold a fishing rod before using this command.");
return;
}
FishingEffect initialEffect = CustomFishingPlugin.get().getEffectManager().getInitialEffect();
FishingPreparation fishingPreparation = new FishingPreparation(player, CustomFishingPlugin.get());
boolean inLava = (boolean) arg.getOrDefault("lava fishing", false);

View File

@@ -42,7 +42,7 @@ public class ItemSelector implements YamlPage {
private String prefix;
private final File file;
private long coolDown;
private String type;
private final String type;
public ItemSelector(Player player, File file, String type) {
this.yaml = YamlConfiguration.loadConfiguration(file);
@@ -103,6 +103,54 @@ public class ItemSelector implements YamlPage {
window.open();
}
public void reOpenWithNewKey() {
String tempKey = "New Key";
prefix = tempKey;
var confirmIcon = new ConfirmIcon();
Item border = new SimpleItem(new ItemBuilder(Material.AIR));
Gui upperGui = Gui.normal()
.setStructure(
"a # b"
)
.addIngredient('a', new SimpleItem(new ItemBuilder(Material.NAME_TAG).setDisplayName(tempKey)))
.addIngredient('b', confirmIcon)
.addIngredient('#', border)
.build();
var gui = PagedGui.items()
.setStructure(
"x x x x x x x x x",
"x x x x x x x x x",
"x x x x x x x x x",
"# # a # c # b # #"
)
.addIngredient('x', Markers.CONTENT_LIST_SLOT_HORIZONTAL)
.addIngredient('#', new BackGroundItem())
.addIngredient('a', new PreviousPageItem())
.addIngredient('b', new NextPageItem())
.addIngredient('c', new BackToFolderItem(file.getParentFile()))
.build();
var window = AnvilWindow.split()
.setViewer(player)
.setTitle(new ShadedAdventureComponentWrapper(
AdventureManagerImpl.getInstance().getComponentFromMiniMessage("Set key name")
))
.addRenameHandler(s -> {
long current = System.currentTimeMillis();
if (current - coolDown < 100) return;
if (s.equals(tempKey)) return;
prefix = s;
coolDown = current;
confirmIcon.notifyWindows();
})
.setUpperGui(upperGui)
.setLowerGui(gui)
.build();
window.open();
}
public List<Item> getItemList() {
List<Item> itemList = new ArrayList<>();
for (Map.Entry<String, Object> entry : this.yaml.getValues(false).entrySet()) {
@@ -121,6 +169,7 @@ public class ItemSelector implements YamlPage {
}
itemList.add(new ItemInList(key, new ItemBuilder(Material.STRUCTURE_VOID), this));
}
itemList.add(new AddKey());
return itemList;
}
@@ -189,4 +238,57 @@ public class ItemSelector implements YamlPage {
}
}
}
public class AddKey extends AbstractItem {
@Override
public ItemProvider getItemProvider() {
return new ItemBuilder(Material.ANVIL).setDisplayName(new ShadedAdventureComponentWrapper(AdventureManagerImpl.getInstance().getComponentFromMiniMessage(
"<green>[+] Add a new key"
)));
}
@Override
public void handleClick(@NotNull ClickType clickType, @NotNull Player player, @NotNull InventoryClickEvent event) {
reOpenWithNewKey();
}
}
public class ConfirmIcon extends AbstractItem {
@Override
public ItemProvider getItemProvider() {
if (prefix != null && !yaml.contains(prefix) && prefix.matches("^[a-zA-Z0-9_]+$")) {
var builder = new ItemBuilder(Material.NAME_TAG)
.setDisplayName(new ShadedAdventureComponentWrapper(AdventureManagerImpl.getInstance().getComponentFromMiniMessage(
prefix
)));
builder.addLoreLines(new ShadedAdventureComponentWrapper(AdventureManagerImpl.getInstance().getComponentFromMiniMessage(
"<#00FF7F> -> Left click to confirm"
))).addLoreLines(new ShadedAdventureComponentWrapper(AdventureManagerImpl.getInstance().getComponentFromMiniMessage(
"<#00CED1> -> Right click to cancel"
)));
return builder;
} else {
return new ItemBuilder(Material.BARRIER)
.setDisplayName(new ShadedAdventureComponentWrapper(AdventureManagerImpl.getInstance().getComponentFromMiniMessage(
"<red>● Duplicated or invalid key"
)));
}
}
@Override
public void handleClick(@NotNull ClickType clickType, @NotNull Player player, @NotNull InventoryClickEvent event) {
if (clickType.isLeftClick()) {
if (prefix != null && !yaml.contains(prefix) && prefix.matches("^[a-zA-Z0-9_]+$")) {
yaml.createSection(prefix);
save();
} else {
return;
}
}
prefix = SEARCH;
reOpenWithFilter(SEARCH);
}
}
}

View File

@@ -35,9 +35,11 @@ import net.momirealms.customfishing.api.mechanic.item.ItemBuilder;
import net.momirealms.customfishing.api.mechanic.item.ItemLibrary;
import net.momirealms.customfishing.api.mechanic.loot.Loot;
import net.momirealms.customfishing.api.util.LogUtils;
import net.momirealms.customfishing.api.util.WeightUtils;
import net.momirealms.customfishing.compatibility.item.CustomFishingItemImpl;
import net.momirealms.customfishing.compatibility.item.VanillaItemImpl;
import net.momirealms.customfishing.compatibility.papi.PlaceholderManagerImpl;
import net.momirealms.customfishing.api.mechanic.misc.Value;
import net.momirealms.customfishing.setting.CFConfig;
import net.momirealms.customfishing.util.ConfigUtils;
import net.momirealms.customfishing.util.ItemUtils;
@@ -45,8 +47,10 @@ import net.momirealms.customfishing.util.NBTUtils;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.NamespacedKey;
import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.configuration.file.YamlConfiguration;
import org.bukkit.enchantments.Enchantment;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.event.Event;
@@ -263,7 +267,11 @@ public class ItemManagerImpl implements ItemManager, Listener {
String[] split = id.split(":", 2);
return itemLibraryMap.get(split[0]).buildItem(player, split[1]);
} else {
return new ItemStack(Material.valueOf(id.toUpperCase(Locale.ENGLISH)));
try {
return new ItemStack(Material.valueOf(id.toUpperCase(Locale.ENGLISH)));
} catch (IllegalArgumentException e) {
return new ItemStack(Material.COD);
}
}
}
@@ -327,6 +335,8 @@ public class ItemManagerImpl implements ItemManager, Listener {
.itemFlag(section.getStringList("item-flags").stream().map(flag -> ItemFlag.valueOf(flag.toUpperCase())).toList())
.enchantment(ConfigUtils.getEnchantmentPair(section.getConfigurationSection("enchantments")), false)
.enchantment(ConfigUtils.getEnchantmentPair(section.getConfigurationSection("stored-enchantments")), true)
.enchantmentPool(ConfigUtils.getEnchantAmountPair(section.getConfigurationSection("enchantment-pool.amount")), ConfigUtils.getEnchantPoolPair(section.getConfigurationSection("enchantment-pool.pool")), false)
.enchantmentPool(ConfigUtils.getEnchantAmountPair(section.getConfigurationSection("stored-enchantment-pool.amount")), ConfigUtils.getEnchantPoolPair(section.getConfigurationSection("stored-enchantment-pool.pool")), true)
.randomEnchantments(ConfigUtils.getEnchantmentTuple(section.getConfigurationSection("random-enchantments")), false)
.randomEnchantments(ConfigUtils.getEnchantmentTuple(section.getConfigurationSection("random-stored-enchantments")), true)
.tag(section.getBoolean("tag", true), type, id)
@@ -627,6 +637,51 @@ public class ItemManagerImpl implements ItemManager, Listener {
return this;
}
@Override
public ItemBuilder enchantmentPool(List<Pair<Integer, Value>> amountPairs, List<Pair<Pair<String, Short>, Value>> enchantments, boolean store) {
if (enchantments.size() == 0 || amountPairs.size() == 0) return this;
editors.put("enchantment-pool", (player, nbtItem, placeholders) -> {
List<Pair<Integer, Double>> parsedAmountPair = new ArrayList<>(amountPairs.size());
for (Pair<Integer, Value> rawValue : amountPairs) {
parsedAmountPair.add(Pair.of(rawValue.left(), rawValue.right().get(player)));
}
int amount = WeightUtils.getRandom(parsedAmountPair);
if (amount <= 0) return;
NBTCompoundList list = nbtItem.getCompoundList(store ? "StoredEnchantments" : "Enchantments");
HashSet<Enchantment> addedEnchantments = new HashSet<>();
List<Pair<Pair<String, Short>, Double>> cloned = new ArrayList<>(enchantments.size());
for (Pair<Pair<String, Short>, Value> rawValue : enchantments) {
cloned.add(Pair.of(rawValue.left(), rawValue.right().get(player)));
}
int i = 0;
outer:
while (i < amount && cloned.size() != 0) {
Pair<String, Short> enchantPair = WeightUtils.getRandom(cloned);
Enchantment enchantment = Enchantment.getByKey(NamespacedKey.fromString(enchantPair.left()));
if (enchantment == null) {
throw new NullPointerException("Enchantment: " + enchantPair.left() + " doesn't exist on your server.");
}
for (Enchantment added : addedEnchantments) {
if (enchantment.conflictsWith(added)) {
cloned.removeIf(pair -> pair.left().left().equals(enchantPair.left()));
continue outer;
}
}
NBTCompound nbtCompound = list.addCompound();
nbtCompound.setString("id", enchantPair.left());
nbtCompound.setShort("lvl", enchantPair.right());
addedEnchantments.add(enchantment);
cloned.removeIf(pair -> pair.left().left().equals(enchantPair.left()));
i++;
}
});
return this;
}
@Override
public ItemBuilder maxDurability(int max) {
if (max == 0) return this;

View File

@@ -17,6 +17,7 @@
package net.momirealms.customfishing.mechanic.misc.value;
import net.momirealms.customfishing.api.mechanic.misc.Value;
import net.momirealms.customfishing.util.ConfigUtils;
import org.bukkit.entity.Player;

View File

@@ -17,9 +17,10 @@
package net.momirealms.customfishing.mechanic.misc.value;
import net.momirealms.customfishing.api.mechanic.misc.Value;
import org.bukkit.entity.Player;
public class PlainValue implements Value{
public class PlainValue implements Value {
private final double value;

View File

@@ -20,9 +20,12 @@ package net.momirealms.customfishing.scheduler;
import io.papermc.paper.threadedregions.scheduler.ScheduledTask;
import net.momirealms.customfishing.api.CustomFishingPlugin;
import net.momirealms.customfishing.api.scheduler.CancellableTask;
import net.momirealms.customfishing.util.LocationUtils;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import java.util.Optional;
/**
* A scheduler implementation for "synchronous" tasks using Folia's RegionScheduler.
*/
@@ -42,7 +45,7 @@ public class FoliaSchedulerImpl implements SyncScheduler {
*/
@Override
public void runSyncTask(Runnable runnable, Location location) {
Bukkit.getRegionScheduler().execute(plugin, location, runnable);
Bukkit.getRegionScheduler().execute(plugin, Optional.ofNullable(location).orElse(LocationUtils.getAnyLocationInstance()), runnable);
}
/**

View File

@@ -24,7 +24,7 @@ import net.momirealms.customfishing.api.util.LogUtils;
import net.momirealms.customfishing.compatibility.papi.PlaceholderManagerImpl;
import net.momirealms.customfishing.mechanic.misc.value.ExpressionValue;
import net.momirealms.customfishing.mechanic.misc.value.PlainValue;
import net.momirealms.customfishing.mechanic.misc.value.Value;
import net.momirealms.customfishing.api.mechanic.misc.Value;
import net.objecthunter.exp4j.ExpressionBuilder;
import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.configuration.file.YamlConfiguration;
@@ -201,12 +201,38 @@ public class ConfigUtils {
if (section == null) return list;
for (Map.Entry<String, Object> entry : section.getValues(false).entrySet()) {
if (entry.getValue() instanceof Integer integer) {
list.add(Pair.of(entry.getKey(), Short.valueOf(String.valueOf(integer))));
list.add(Pair.of(entry.getKey(), Short.parseShort(String.valueOf(Math.max(1, Math.min(Short.MAX_VALUE, integer))))));
}
}
return list;
}
public static List<Pair<Integer, Value>> getEnchantAmountPair(ConfigurationSection section) {
List<Pair<Integer, Value>> list = new ArrayList<>();
if (section == null) return list;
for (Map.Entry<String, Object> entry : section.getValues(false).entrySet()) {
list.add(Pair.of(Integer.parseInt(entry.getKey()), getValue(entry.getValue())));
}
return list;
}
public static List<Pair<Pair<String, Short>, Value>> getEnchantPoolPair(ConfigurationSection section) {
List<Pair<Pair<String, Short>, Value>> list = new ArrayList<>();
if (section == null) return list;
for (Map.Entry<String, Object> entry : section.getValues(false).entrySet()) {
list.add(Pair.of(getEnchantmentPair(entry.getKey()), getValue(entry.getValue())));
}
return list;
}
public static Pair<String, Short> getEnchantmentPair(String value) {
int last = value.lastIndexOf(":");
if (last == -1 || last == 0 || last == value.length() - 1) {
throw new IllegalArgumentException("Invalid format of the input enchantment");
}
return Pair.of(value.substring(0, last), Short.parseShort(value.substring(last + 1)));
}
/**
* Retrieves a list of enchantment tuples from a configuration section.
*

View File

@@ -17,6 +17,7 @@
package net.momirealms.customfishing.util;
import org.bukkit.Bukkit;
import org.bukkit.Location;
public class LocationUtils {
@@ -34,4 +35,8 @@ public class LocationUtils {
Math.pow(location2.getZ() - location1.getZ(), 2)
);
}
public static Location getAnyLocationInstance() {
return new Location(Bukkit.getWorlds().get(0), 0, 64, 0);
}
}