From 7978121c7cdb9c76023482c9fbb24b662d3cbea8 Mon Sep 17 00:00:00 2001 From: Jake Potrebic Date: Sun, 23 Jan 2022 10:42:38 -0800 Subject: [PATCH] More PotionEffectType API (#5737) --- .../api/0362-More-PotionEffectType-API.patch | 143 ++++++++++++++++++ .../0859-More-PotionEffectType-API.patch | 91 +++++++++++ 2 files changed, 234 insertions(+) create mode 100644 patches/api/0362-More-PotionEffectType-API.patch create mode 100644 patches/server/0859-More-PotionEffectType-API.patch diff --git a/patches/api/0362-More-PotionEffectType-API.patch b/patches/api/0362-More-PotionEffectType-API.patch new file mode 100644 index 0000000000..4e999e136c --- /dev/null +++ b/patches/api/0362-More-PotionEffectType-API.patch @@ -0,0 +1,143 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Jake Potrebic +Date: Thu, 27 May 2021 21:58:33 -0700 +Subject: [PATCH] More PotionEffectType API + + +diff --git a/src/main/java/org/bukkit/Registry.java b/src/main/java/org/bukkit/Registry.java +index a696fcaffa03af9e6c92e2ef3e12b38eb59e5db4..6242336de18fdd708cc3d7b745cbbace13140bc0 100644 +--- a/src/main/java/org/bukkit/Registry.java ++++ b/src/main/java/org/bukkit/Registry.java +@@ -189,6 +189,27 @@ public interface Registry extends Iterable { + return GameEvent.getByKey(key); + } + }; ++ // Paper start ++ /** ++ * Potion effect types. ++ * ++ * @see org.bukkit.potion.PotionEffectType ++ */ ++ Registry POTION_EFFECT_TYPE = new Registry() { ++ ++ @Nullable ++ @Override ++ public org.bukkit.potion.PotionEffectType get(@NotNull NamespacedKey key) { ++ return org.bukkit.potion.PotionEffectType.getByKey(key); ++ } ++ ++ @NotNull ++ @Override ++ public Iterator iterator() { ++ return Arrays.stream(org.bukkit.potion.PotionEffectType.values()).iterator(); ++ } ++ }; ++ // Paper end + + /** + * Get the object by its key. +diff --git a/src/main/java/org/bukkit/potion/PotionEffectType.java b/src/main/java/org/bukkit/potion/PotionEffectType.java +index 22c28a503732671bc84c51372262e909d035c1fa..06e0f13d658b63b1fa984abb515eb0de704f9215 100644 +--- a/src/main/java/org/bukkit/potion/PotionEffectType.java ++++ b/src/main/java/org/bukkit/potion/PotionEffectType.java +@@ -14,7 +14,7 @@ import org.jetbrains.annotations.Nullable; + /** + * Represents a type of potion and its effect on an entity. + */ +-public abstract class PotionEffectType implements Keyed { ++public abstract class PotionEffectType implements Keyed, net.kyori.adventure.translation.Translatable { // Paper - implement Translatable + /** + * Increases movement speed. + */ +@@ -358,4 +358,56 @@ public abstract class PotionEffectType implements Keyed { + public static PotionEffectType[] values() { + return Arrays.copyOfRange(byId, 1, byId.length); + } ++ // Paper start ++ /** ++ * Gets the effect attributes in an immutable map. ++ * ++ * @return the attribute map ++ */ ++ public abstract @NotNull Map getEffectAttributes(); ++ ++ /** ++ * Gets the true modifier amount based on the effect amplifier. ++ * ++ * @param attribute the attribute ++ * @param effectAmplifier the effect amplifier (0 indexed) ++ * @return the modifier amount ++ * @throws IllegalArgumentException if the supplied attribute is not present in the map from {@link #getEffectAttributes()} ++ */ ++ public abstract double getAttributeModifierAmount(@NotNull org.bukkit.attribute.Attribute attribute, int effectAmplifier); ++ ++ /** ++ * Gets the category of this effect ++ * ++ * @return the category ++ */ ++ public abstract @NotNull PotionEffectType.Category getEffectCategory(); ++ ++ /** ++ * Category of {@link PotionEffectType}s ++ */ ++ public enum Category { ++ ++ BENEFICIAL(net.kyori.adventure.text.format.NamedTextColor.BLUE), ++ HARMFUL(net.kyori.adventure.text.format.NamedTextColor.RED), ++ NEUTRAL(net.kyori.adventure.text.format.NamedTextColor.BLUE); ++ ++ private final net.kyori.adventure.text.format.TextColor color; ++ ++ Category(net.kyori.adventure.text.format.TextColor color) { ++ this.color = color; ++ } ++ ++ /** ++ * Gets the text color used when displaying potions ++ * of this category. ++ * ++ * @return the text color ++ */ ++ @NotNull ++ public net.kyori.adventure.text.format.TextColor getColor() { ++ return color; ++ } ++ } ++ // Paper end + } +diff --git a/src/main/java/org/bukkit/potion/PotionEffectTypeWrapper.java b/src/main/java/org/bukkit/potion/PotionEffectTypeWrapper.java +index c3a86bb1910158a8d13a675dfa7236dd6a3f397c..a7653806c0fa76f4b3342ea199fe892c514a4c27 100644 +--- a/src/main/java/org/bukkit/potion/PotionEffectTypeWrapper.java ++++ b/src/main/java/org/bukkit/potion/PotionEffectTypeWrapper.java +@@ -40,4 +40,30 @@ public class PotionEffectTypeWrapper extends PotionEffectType { + public Color getColor() { + return getType().getColor(); + } ++ // Paper start ++ @Override ++ public @NotNull org.bukkit.NamespacedKey getKey() { ++ return this.getType().getKey(); ++ } ++ ++ @Override ++ public @NotNull java.util.Map getEffectAttributes() { ++ return this.getType().getEffectAttributes(); ++ } ++ ++ @Override ++ public double getAttributeModifierAmount(@NotNull org.bukkit.attribute.Attribute attribute, int effectAmplifier) { ++ return this.getType().getAttributeModifierAmount(attribute, effectAmplifier); ++ } ++ ++ @Override ++ public @NotNull PotionEffectType.Category getEffectCategory() { ++ return this.getType().getEffectCategory(); ++ } ++ ++ @Override ++ public @NotNull String translationKey() { ++ return this.getType().translationKey(); ++ } ++ // Paper end + } diff --git a/patches/server/0859-More-PotionEffectType-API.patch b/patches/server/0859-More-PotionEffectType-API.patch new file mode 100644 index 0000000000..14fb482187 --- /dev/null +++ b/patches/server/0859-More-PotionEffectType-API.patch @@ -0,0 +1,91 @@ +From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 +From: Jake Potrebic +Date: Thu, 27 May 2021 21:58:24 -0700 +Subject: [PATCH] More PotionEffectType API + + +diff --git a/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionEffectType.java b/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionEffectType.java +index fdd8e353bcbd2faace59288810d1a5121f174b56..82a6702a2ddc35222f5a416364de8c397c85d5bb 100644 +--- a/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionEffectType.java ++++ b/src/main/java/org/bukkit/craftbukkit/potion/CraftPotionEffectType.java +@@ -102,4 +102,46 @@ public class CraftPotionEffectType extends PotionEffectType { + public Color getColor() { + return Color.fromRGB(this.handle.getColor()); + } ++ // Paper start ++ @Override ++ public org.bukkit.NamespacedKey getKey() { ++ return org.bukkit.craftbukkit.util.CraftNamespacedKey.fromMinecraft(net.minecraft.core.Registry.MOB_EFFECT.getKey(this.handle)); ++ } ++ ++ @Override ++ public java.util.Map getEffectAttributes() { ++ // re-create map each time because a nms MobEffect can have its attributes modified ++ final java.util.Map attributeMap = new java.util.HashMap<>(); ++ this.handle.getAttributeModifiers().forEach((attribute, attributeModifier) -> { ++ attributeMap.put(org.bukkit.craftbukkit.attribute.CraftAttributeMap.fromMinecraft(attribute.toString()), org.bukkit.craftbukkit.attribute.CraftAttributeInstance.convert(attributeModifier)); ++ }); ++ return java.util.Map.copyOf(attributeMap); ++ } ++ ++ @Override ++ public double getAttributeModifierAmount(org.bukkit.attribute.Attribute attribute, int effectAmplifier) { ++ com.google.common.base.Preconditions.checkArgument(effectAmplifier >= 0, "effectAmplifier must be greater than or equal to 0"); ++ net.minecraft.world.entity.ai.attributes.Attribute nmsAttribute = org.bukkit.craftbukkit.attribute.CraftAttributeMap.toMinecraft(attribute); ++ com.google.common.base.Preconditions.checkArgument(this.handle.getAttributeModifiers().containsKey(nmsAttribute), attribute + " is not present on " + this.getKey()); ++ return this.handle.getAttributeModifierValue(effectAmplifier, this.handle.getAttributeModifiers().get(nmsAttribute)); ++ } ++ ++ @Override ++ public PotionEffectType.Category getEffectCategory() { ++ return fromNMS(handle.getCategory()); ++ } ++ ++ @Override ++ public String translationKey() { ++ return this.handle.getDescriptionId(); ++ } ++ ++ public static PotionEffectType.Category fromNMS(net.minecraft.world.effect.MobEffectCategory mobEffectInfo) { ++ return switch (mobEffectInfo) { ++ case BENEFICIAL -> PotionEffectType.Category.BENEFICIAL; ++ case HARMFUL -> PotionEffectType.Category.HARMFUL; ++ case NEUTRAL -> PotionEffectType.Category.NEUTRAL; ++ }; ++ } ++ // Paper end + } +diff --git a/src/test/java/io/papermc/paper/effects/EffectCategoryTest.java b/src/test/java/io/papermc/paper/effects/EffectCategoryTest.java +new file mode 100644 +index 0000000000000000000000000000000000000000..a5012bc0469ba03cde66749a11f4e7d93206bfd7 +--- /dev/null ++++ b/src/test/java/io/papermc/paper/effects/EffectCategoryTest.java +@@ -0,0 +1,28 @@ ++package io.papermc.paper.effects; ++ ++import io.papermc.paper.adventure.PaperAdventure; ++import net.minecraft.world.effect.MobEffectCategory; ++import org.bukkit.craftbukkit.potion.CraftPotionEffectType; ++import org.bukkit.potion.PotionEffectType; ++import org.junit.Test; ++ ++import static org.junit.Assert.assertEquals; ++import static org.junit.Assert.assertNotNull; ++ ++public class EffectCategoryTest { ++ ++ @Test ++ public void testEffectCategoriesExist() { ++ for (MobEffectCategory mobEffectInfo : MobEffectCategory.values()) { ++ assertNotNull(mobEffectInfo + " is missing a bukkit equivalent", CraftPotionEffectType.fromNMS(mobEffectInfo)); ++ } ++ } ++ ++ @Test ++ public void testCategoryHasEquivalentColors() { ++ for (MobEffectCategory mobEffectInfo : MobEffectCategory.values()) { ++ PotionEffectType.Category bukkitEffectCategory = CraftPotionEffectType.fromNMS(mobEffectInfo); ++ assertEquals(mobEffectInfo.getTooltipFormatting().name() + " doesn't equal " + bukkitEffectCategory.getColor(), bukkitEffectCategory.getColor(), PaperAdventure.asAdventure(mobEffectInfo.getTooltipFormatting())); ++ } ++ } ++}