From d0db1323288efd52034a0bf5768cea8fbfa7dd5a Mon Sep 17 00:00:00 2001 From: Jake Potrebic Date: Fri, 26 Apr 2024 16:17:13 -0700 Subject: [PATCH] fix custom potion mixes --- patches/api/Custom-Potion-Mixes.patch | 94 ++++--- patches/server/Custom-Potion-Mixes.patch | 258 ++++++++++-------- ...Folia-scheduler-and-owned-region-API.patch | 2 +- 3 files changed, 196 insertions(+), 158 deletions(-) diff --git a/patches/api/Custom-Potion-Mixes.patch b/patches/api/Custom-Potion-Mixes.patch index 0b06c2d9e8..8c68282374 100644 --- a/patches/api/Custom-Potion-Mixes.patch +++ b/patches/api/Custom-Potion-Mixes.patch @@ -195,53 +195,15 @@ diff --git a/src/main/java/org/bukkit/potion/PotionBrewer.java b/src/main/java/o index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 100644 --- a/src/main/java/org/bukkit/potion/PotionBrewer.java +++ b/src/main/java/org/bukkit/potion/PotionBrewer.java -@@ -0,0 +0,0 @@ import org.jetbrains.annotations.NotNull; - * Represents a brewer that can create {@link PotionEffect}s. +@@ -0,0 +0,0 @@ import java.util.Collection; + import org.jetbrains.annotations.NotNull; + + /** +- * Represents a brewer that can create {@link PotionEffect}s. ++ * Used to manage custom {@link io.papermc.paper.potion.PotionMix}s. */ public interface PotionBrewer { -- -+ // Paper start - keep old spigot methods, removal in 1.20.6 - /** - * Creates a {@link PotionEffect} from the given {@link PotionEffectType}, - * applying duration modifiers and checks. -@@ -0,0 +0,0 @@ public interface PotionBrewer { - * @param duration The duration in ticks - * @param amplifier The amplifier of the effect - * @return The resulting potion effect -+ * @deprecated use {@link PotionEffectType#createEffect(int, int)} instead. - */ -+ @Deprecated(forRemoval = true, since = "1.20.5") - @NotNull -- public PotionEffect createEffect(@NotNull PotionEffectType potion, int duration, int amplifier); -+ default PotionEffect createEffect(@NotNull PotionEffectType potion, int duration, int amplifier) { -+ return potion.createEffect(duration, amplifier); -+ } - /** - * Returns a collection of {@link PotionEffect} that would be applied from -@@ -0,0 +0,0 @@ public interface PotionBrewer { - * @return The list of effects - * @deprecated Non-Functional - */ -- @Deprecated -+ @Deprecated(forRemoval = true, since = "1.20.5") - @NotNull -- public Collection getEffectsFromDamage(int damage); -+ default Collection getEffectsFromDamage(final int damage) { -+ return new java.util.ArrayList<>(); -+ } -+ // Paper start - keep old spigot methods, removal in 1.20.6 - - /** - * Returns a collection of {@link PotionEffect} that would be applied from -@@ -0,0 +0,0 @@ public interface PotionBrewer { - * @deprecated Upgraded / extended potions are now their own {@link PotionType} use {@link PotionType#getPotionEffects()} instead - */ - @NotNull -- @Deprecated -+ @Deprecated(forRemoval = true, since = "1.20.5") - public Collection getEffects(@NotNull PotionType type, boolean upgraded, boolean extended); -+ + // Paper start + /** + * Adds a new potion mix recipe. @@ -262,4 +224,48 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + */ + void resetPotionMixes(); + // Paper end ++ + /** + * Creates a {@link PotionEffect} from the given {@link PotionEffectType}, + * applying duration modifiers and checks. +@@ -0,0 +0,0 @@ public interface PotionBrewer { + * @param duration The duration in ticks + * @param amplifier The amplifier of the effect + * @return The resulting potion effect ++ * @deprecated use {@link PotionEffectType#createEffect(int, int)} instead. + */ ++ @Deprecated(forRemoval = true, since = "1.20.5") // Paper + @NotNull +- public PotionEffect createEffect(@NotNull PotionEffectType potion, int duration, int amplifier); ++ // Paper start - make default ++ default PotionEffect createEffect(@NotNull PotionEffectType potion, int duration, int amplifier) { ++ return potion.createEffect(duration, amplifier); ++ } ++ // Paper end + + /** + * Returns a collection of {@link PotionEffect} that would be applied from +@@ -0,0 +0,0 @@ public interface PotionBrewer { + * @return The list of effects + * @deprecated Non-Functional + */ +- @Deprecated ++ @Deprecated(forRemoval = true, since = "1.20.5") // Paper + @NotNull +- public Collection getEffectsFromDamage(int damage); ++ // Paper start - make default ++ default Collection getEffectsFromDamage(final int damage) { ++ return new java.util.ArrayList<>(); ++ } ++ // Paper end + + /** + * Returns a collection of {@link PotionEffect} that would be applied from +@@ -0,0 +0,0 @@ public interface PotionBrewer { + * @deprecated Upgraded / extended potions are now their own {@link PotionType} use {@link PotionType#getPotionEffects()} instead + */ + @NotNull +- @Deprecated ++ @Deprecated(forRemoval = true, since = "1.20.5") // Paper + public Collection getEffects(@NotNull PotionType type, boolean upgraded, boolean extended); } diff --git a/patches/server/Custom-Potion-Mixes.patch b/patches/server/Custom-Potion-Mixes.patch index 662a02100a..8c7f5f7be8 100644 --- a/patches/server/Custom-Potion-Mixes.patch +++ b/patches/server/Custom-Potion-Mixes.patch @@ -3,7 +3,71 @@ From: Jake Potrebic Date: Thu, 7 Oct 2021 14:34:55 -0700 Subject: [PATCH] Custom Potion Mixes +== AT == +public-f net.minecraft.server.MinecraftServer potionBrewing +diff --git a/src/main/java/io/papermc/paper/potion/PaperPotionBrewer.java b/src/main/java/io/papermc/paper/potion/PaperPotionBrewer.java +new file mode 100644 +index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 +--- /dev/null ++++ b/src/main/java/io/papermc/paper/potion/PaperPotionBrewer.java +@@ -0,0 +0,0 @@ ++package io.papermc.paper.potion; ++ ++import com.google.common.base.Preconditions; ++import java.util.Collection; ++import net.minecraft.server.MinecraftServer; ++import org.bukkit.NamespacedKey; ++import org.bukkit.potion.PotionBrewer; ++import org.bukkit.potion.PotionEffect; ++import org.bukkit.potion.PotionType; ++import org.checkerframework.checker.nullness.qual.NonNull; ++import org.checkerframework.framework.qual.DefaultQualifier; ++ ++@DefaultQualifier(NonNull.class) ++public class PaperPotionBrewer implements PotionBrewer { ++ ++ private final MinecraftServer minecraftServer; ++ ++ public PaperPotionBrewer(final MinecraftServer minecraftServer) { ++ this.minecraftServer = minecraftServer; ++ } ++ ++ @Override ++ @Deprecated(forRemoval = true) ++ public Collection getEffects(PotionType type, boolean upgraded, boolean extended) { ++ final org.bukkit.NamespacedKey key = type.getKey(); ++ ++ Preconditions.checkArgument(!key.getKey().startsWith("strong_"), "Strong potion type cannot be used directly, got %s", key); ++ Preconditions.checkArgument(!key.getKey().startsWith("long_"), "Extended potion type cannot be used directly, got %s", key); ++ ++ org.bukkit.NamespacedKey effectiveKey = key; ++ if (upgraded) { ++ effectiveKey = new org.bukkit.NamespacedKey(key.namespace(), "strong_" + key.key()); ++ } else if (extended) { ++ effectiveKey = new org.bukkit.NamespacedKey(key.namespace(), "long_" + key.key()); ++ } ++ ++ final org.bukkit.potion.PotionType effectivePotionType = org.bukkit.Registry.POTION.get(effectiveKey); ++ Preconditions.checkNotNull(type, "Unknown potion type from data " + effectiveKey.asMinimalString()); // Legacy error message in 1.20.4 ++ return effectivePotionType.getPotionEffects(); ++ } ++ ++ @Override ++ public void addPotionMix(final PotionMix potionMix) { ++ this.minecraftServer.potionBrewing().addPotionMix(potionMix); ++ } ++ ++ @Override ++ public void removePotionMix(final NamespacedKey key) { ++ this.minecraftServer.potionBrewing.removePotionMix(key); ++ } ++ ++ @Override ++ public void resetPotionMixes() { ++ this.minecraftServer.potionBrewing = this.minecraftServer.potionBrewing().reload(this.minecraftServer.getWorldData().enabledFeatures()); ++ } ++} diff --git a/src/main/java/io/papermc/paper/potion/PaperPotionMix.java b/src/main/java/io/papermc/paper/potion/PaperPotionMix.java new file mode 100644 index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 @@ -35,15 +99,6 @@ diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/ index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 100644 --- a/src/main/java/net/minecraft/server/MinecraftServer.java +++ b/src/main/java/net/minecraft/server/MinecraftServer.java -@@ -0,0 +0,0 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop public (remove final) - private volatile boolean isSaving; - - // CraftBukkit start @@ -0,0 +0,0 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop containers; private final List> potionMixes; private final List> containerMixes; -+ private static final it.unimi.dsi.fastutil.objects.Object2ObjectLinkedOpenHashMap CUSTOM_MIXES = new it.unimi.dsi.fastutil.objects.Object2ObjectLinkedOpenHashMap<>(); // Paper - Custom Potion Mixes ++ private final it.unimi.dsi.fastutil.objects.Object2ObjectLinkedOpenHashMap customMixes = new it.unimi.dsi.fastutil.objects.Object2ObjectLinkedOpenHashMap<>(); // Paper - Custom Potion Mixes PotionBrewing(List potionTypes, List> potionRecipes, List> itemRecipes) { this.containers = potionTypes; @@ -82,7 +181,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public boolean isIngredient(ItemStack stack) { - return this.isContainerIngredient(stack) || this.isPotionIngredient(stack); -+ return this.isContainerIngredient(stack) || this.isPotionIngredient(stack) || isCustomIngredient(stack); // Paper - Custom Potion Mixes ++ return this.isContainerIngredient(stack) || this.isPotionIngredient(stack) || this.isCustomIngredient(stack); // Paper - Custom Potion Mixes } private boolean isContainer(ItemStack stack) { @@ -91,7 +190,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 public boolean hasMix(ItemStack input, ItemStack ingredient) { + // Paper start - Custom Potion Mixes -+ if (hasCustomMix(input, ingredient)) { ++ if (this.hasCustomMix(input, ingredient)) { + return true; + } + // Paper end - Custom Potion Mixes @@ -99,26 +198,26 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } @@ -0,0 +0,0 @@ public class PotionBrewing { + if (input.isEmpty()) { + return input; + } else { ++ // Paper start - Custom Potion Mixes ++ for (io.papermc.paper.potion.PaperPotionMix mix : this.customMixes.values()) { ++ if (mix.input().test(input) && mix.ingredient().test(ingredient)) { ++ return mix.result().copy(); ++ } ++ } ++ // Paper end - Custom Potion Mixes + Optional> optional = input.getOrDefault(DataComponents.POTION_CONTENTS, PotionContents.EMPTY).potion(); if (optional.isEmpty()) { return input; - } else { -+ // Paper start - Custom Potion Mixes -+ for (var mix : CUSTOM_MIXES.values()) { -+ if (mix.input().test(input) && mix.ingredient().test(ingredient)) { -+ return mix.result().copy(); -+ } -+ } -+ // Paper end - Custom Potion Mixes - for (PotionBrewing.Mix mix : this.containerMixes) { - if (input.is(mix.from) && mix.ingredient.test(ingredient)) { - return PotionContents.createItemStack(mix.to.value(), optional.get()); @@ -0,0 +0,0 @@ public class PotionBrewing { builder.addMix(Potions.SLOW_FALLING, Items.REDSTONE, Potions.LONG_SLOW_FALLING); } + // Paper start - Custom Potion Mixes -+ public static boolean isCustomIngredient(ItemStack stack) { -+ for (var mix : CUSTOM_MIXES.values()) { ++ public boolean isCustomIngredient(ItemStack stack) { ++ for (io.papermc.paper.potion.PaperPotionMix mix : this.customMixes.values()) { + if (mix.ingredient().test(stack)) { + return true; + } @@ -126,8 +225,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + return false; + } + -+ public static boolean isCustomInput(ItemStack stack) { -+ for (var mix : CUSTOM_MIXES.values()) { ++ public boolean isCustomInput(ItemStack stack) { ++ for (io.papermc.paper.potion.PaperPotionMix mix : this.customMixes.values()) { + if (mix.input().test(stack)) { + return true; + } @@ -135,8 +234,8 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + return false; + } + -+ private static boolean hasCustomMix(ItemStack input, ItemStack ingredient) { -+ for (var mix : CUSTOM_MIXES.values()) { ++ private boolean hasCustomMix(ItemStack input, ItemStack ingredient) { ++ for (io.papermc.paper.potion.PaperPotionMix mix : this.customMixes.values()) { + if (mix.input().test(input) && mix.ingredient().test(ingredient)) { + return true; + } @@ -144,15 +243,15 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 + return false; + } + -+ public static void addPotionMix(io.papermc.paper.potion.PotionMix mix) { -+ if (CUSTOM_MIXES.containsKey(mix.getKey())) { ++ public void addPotionMix(io.papermc.paper.potion.PotionMix mix) { ++ if (this.customMixes.containsKey(mix.getKey())) { + throw new IllegalArgumentException("Duplicate recipe ignored with ID " + mix.getKey()); + } -+ CUSTOM_MIXES.putAndMoveToFirst(mix.getKey(), new io.papermc.paper.potion.PaperPotionMix(mix)); ++ this.customMixes.putAndMoveToFirst(mix.getKey(), new io.papermc.paper.potion.PaperPotionMix(mix)); + } + -+ public static boolean removePotionMix(org.bukkit.NamespacedKey key) { -+ return CUSTOM_MIXES.remove(key) != null; ++ public boolean removePotionMix(org.bukkit.NamespacedKey key) { ++ return this.customMixes.remove(key) != null; + } + + public PotionBrewing reload(FeatureFlagSet flags) { @@ -169,10 +268,16 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 +++ b/src/main/java/net/minecraft/world/level/block/entity/BrewingStandBlockEntity.java @@ -0,0 +0,0 @@ public class BrewingStandBlockEntity extends BaseContainerBlockEntity implements + @Override + public boolean canPlaceItem(int slot, ItemStack stack) { ++ PotionBrewing potionbrewer = this.level != null ? this.level.potionBrewing() : PotionBrewing.EMPTY; // Paper - move up + if (slot == 3) { +- PotionBrewing potionbrewer = this.level != null ? this.level.potionBrewing() : PotionBrewing.EMPTY; + return potionbrewer.isIngredient(stack); } else { - return slot == 4 ? stack.is(Items.BLAZE_POWDER) : (stack.is(Items.POTION) || stack.is(Items.SPLASH_POTION) || stack.is(Items.LINGERING_POTION) || stack.is(Items.GLASS_BOTTLE)) && this.getItem(slot).isEmpty(); -+ return slot == 4 ? stack.is(Items.BLAZE_POWDER) : (stack.is(Items.POTION) || stack.is(Items.SPLASH_POTION) || stack.is(Items.LINGERING_POTION) || stack.is(Items.GLASS_BOTTLE) || PotionBrewing.isCustomInput(stack)) && this.getItem(slot).isEmpty(); // Paper - Custom Potion Mixes ++ return slot == 4 ? stack.is(Items.BLAZE_POWDER) : (stack.is(Items.POTION) || stack.is(Items.SPLASH_POTION) || stack.is(Items.LINGERING_POTION) || stack.is(Items.GLASS_BOTTLE) || potionbrewer.isCustomInput(stack)) && this.getItem(slot).isEmpty(); // Paper - Custom Potion Mixes } } @@ -184,7 +289,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 private final io.papermc.paper.datapack.PaperDatapackManager datapackManager; // Paper public static Exception excessiveVelEx; // Paper - Velocity warnings private final io.papermc.paper.logging.SysoutCatcher sysoutCatcher = new io.papermc.paper.logging.SysoutCatcher(); // Paper -+ private final org.bukkit.craftbukkit.potion.CraftPotionBrewer potionBrewer; // Paper - Custom Potion Mixes ++ private final io.papermc.paper.potion.PaperPotionBrewer potionBrewer; // Paper - Custom Potion Mixes static { ConfigurationSerialization.registerClass(CraftOfflinePlayer.class); @@ -192,7 +297,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 if (this.configuration.getBoolean("settings.use-map-color-cache")) { MapPalette.setMapColorCache(new CraftMapColorCache(this.logger)); } -+ this.potionBrewer = new org.bukkit.craftbukkit.potion.CraftPotionBrewer(playerList.getServer()); // Paper - custom potion mixes ++ this.potionBrewer = new io.papermc.paper.potion.PaperPotionBrewer(console); // Paper - custom potion mixes datapackManager = new io.papermc.paper.datapack.PaperDatapackManager(console.getPackRepository()); // Paper } @@ -201,10 +306,9 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 } + @Override -+ public org.bukkit.craftbukkit.potion.CraftPotionBrewer getPotionBrewer() { ++ public io.papermc.paper.potion.PaperPotionBrewer getPotionBrewer() { + return this.potionBrewer; + } -+ // Paper end } diff --git a/src/main/java/org/bukkit/craftbukkit/inventory/CraftRecipe.java b/src/main/java/org/bukkit/craftbukkit/inventory/CraftRecipe.java @@ -223,75 +327,3 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 Ingredient stack; if (bukkit == null) { -diff --git a/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionBrewer.java b/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionBrewer.java -new file mode 100644 -index 0000000000000000000000000000000000000000..0000000000000000000000000000000000000000 ---- /dev/null -+++ b/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionBrewer.java -@@ -0,0 +0,0 @@ -+package org.bukkit.craftbukkit.potion; -+ -+import com.google.common.base.Preconditions; -+import java.util.ArrayList; -+import java.util.Collection; -+import org.bukkit.potion.PotionBrewer; -+import org.bukkit.potion.PotionEffect; -+import org.bukkit.potion.PotionEffectType; -+import org.bukkit.potion.PotionType; -+ -+public class CraftPotionBrewer implements PotionBrewer { -+ -+ private final net.minecraft.server.MinecraftServer minecraftServer; -+ -+ public CraftPotionBrewer(net.minecraft.server.MinecraftServer minecraftServer) { -+ this.minecraftServer = minecraftServer; -+ } -+ -+ // Paper start - keep old spigot methods, removal in 1.20.6 -+ @Override -+ public Collection getEffects(PotionType type, boolean upgraded, boolean extended) { -+ final org.bukkit.NamespacedKey key = type.getKey(); -+ -+ Preconditions.checkArgument(!key.getKey().startsWith("strong_"), "Strong potion type cannot be used directly, got %s", key); -+ Preconditions.checkArgument(!key.getKey().startsWith("long_"), "Extended potion type cannot be used directly, got %s", key); -+ -+ org.bukkit.NamespacedKey effectiveKey = key; -+ if (upgraded) { -+ effectiveKey = new org.bukkit.NamespacedKey(key.namespace(), "strong_" + key.key()); -+ } else if (extended) { -+ effectiveKey = new org.bukkit.NamespacedKey(key.namespace(), "long_" + key.key()); -+ } -+ -+ final org.bukkit.potion.PotionType effectivePotionType = org.bukkit.Registry.POTION.get(effectiveKey); -+ Preconditions.checkNotNull(type, "Unknown potion type from data " + effectiveKey.asMinimalString()); // Legacy error message in 1.20.4 -+ return effectivePotionType.getPotionEffects(); -+ } -+ -+ @Override -+ public Collection getEffectsFromDamage(int damage) { -+ return new ArrayList<>(); -+ } -+ -+ @Override -+ public PotionEffect createEffect(PotionEffectType potion, int duration, int amplifier) { -+ return new PotionEffect(potion, potion.isInstant() ? 1 : duration, amplifier); -+ } -+ // Paper end - keep old spigot methods, removal in 1.20.6 -+ -+ // Paper start -+ @Override -+ public void addPotionMix(io.papermc.paper.potion.PotionMix potionMix) { -+ net.minecraft.world.item.alchemy.PotionBrewing.addPotionMix(potionMix); -+ } -+ -+ @Override -+ public void removePotionMix(org.bukkit.NamespacedKey key) { -+ net.minecraft.world.item.alchemy.PotionBrewing.removePotionMix(key); -+ } -+ -+ @Override -+ public void resetPotionMixes() { -+ this.minecraftServer.potionBrewing = this.minecraftServer.potionBrewing().reload(this.minecraftServer.getWorldData().enabledFeatures()); -+ } -+ // Paper end -+} diff --git a/patches/server/Folia-scheduler-and-owned-region-API.patch b/patches/server/Folia-scheduler-and-owned-region-API.patch index 44cb1a5d05..f0fc21fba3 100644 --- a/patches/server/Folia-scheduler-and-owned-region-API.patch +++ b/patches/server/Folia-scheduler-and-owned-region-API.patch @@ -1256,7 +1256,7 @@ index 0000000000000000000000000000000000000000..00000000000000000000000000000000 +++ b/src/main/java/org/bukkit/craftbukkit/CraftServer.java @@ -0,0 +0,0 @@ public final class CraftServer implements Server { private final io.papermc.paper.logging.SysoutCatcher sysoutCatcher = new io.papermc.paper.logging.SysoutCatcher(); // Paper - private final org.bukkit.craftbukkit.potion.CraftPotionBrewer potionBrewer; // Paper - Custom Potion Mixes + private final io.papermc.paper.potion.PaperPotionBrewer potionBrewer; // Paper - Custom Potion Mixes + // Paper start - Folia region threading API + private final io.papermc.paper.threadedregions.scheduler.FallbackRegionScheduler regionizedScheduler = new io.papermc.paper.threadedregions.scheduler.FallbackRegionScheduler();