diff --git a/core/src/main/java/tc/oc/pgm/action/ActionParser.java b/core/src/main/java/tc/oc/pgm/action/ActionParser.java index 868a99cba1..1a13ee1933 100644 --- a/core/src/main/java/tc/oc/pgm/action/ActionParser.java +++ b/core/src/main/java/tc/oc/pgm/action/ActionParser.java @@ -1,10 +1,13 @@ package tc.oc.pgm.action; +import static net.kyori.adventure.key.Key.key; +import static net.kyori.adventure.sound.Sound.sound; import static net.kyori.adventure.text.Component.empty; import com.google.common.collect.ImmutableList; import java.lang.reflect.Method; import java.util.Map; +import net.kyori.adventure.sound.Sound; import net.kyori.adventure.text.Component; import net.kyori.adventure.title.Title; import org.bukkit.inventory.ItemStack; @@ -19,6 +22,7 @@ import tc.oc.pgm.action.actions.ReplaceItemAction; import tc.oc.pgm.action.actions.ScopeSwitchAction; import tc.oc.pgm.action.actions.SetVariableAction; +import tc.oc.pgm.action.actions.SoundAction; import tc.oc.pgm.api.feature.FeatureValidation; import tc.oc.pgm.api.filter.Filter; import tc.oc.pgm.api.filter.Filterables; @@ -239,6 +243,26 @@ public MessageAction parseChatMessage(Element el, Class scope) throws Invalid return new MessageAction(text, actionbar, title); } + @MethodParser("sound") + public SoundAction parseSoundAction(Element el, Class scope) throws InvalidXMLException { + SoundType soundType = + XMLUtils.parseEnum( + Node.fromAttr(el, "preset"), SoundType.class, "preset", SoundType.CUSTOM); + Node resourceNode = Node.fromAttr(el, "key"); + String resource = resourceNode == null ? soundType.getResource() : resourceNode.getValue(); + + float volume = + Math.min( + 1f, + XMLUtils.parseNumber(Node.fromAttr(el, "volume"), Float.class, soundType.getVolume())); + float pitch = + XMLUtils.parseNumber(Node.fromAttr(el, "pitch"), Float.class, soundType.getPitch()); + + Sound sound = sound(key(resource, ':'), Sound.Source.MASTER, volume, pitch); + + return new SoundAction(sound); + } + @MethodParser("set") public > SetVariableAction parseSetVariable(Element el, Class scope) throws InvalidXMLException { diff --git a/core/src/main/java/tc/oc/pgm/action/SoundType.java b/core/src/main/java/tc/oc/pgm/action/SoundType.java new file mode 100644 index 0000000000..cc8238c32e --- /dev/null +++ b/core/src/main/java/tc/oc/pgm/action/SoundType.java @@ -0,0 +1,38 @@ +package tc.oc.pgm.action; + +public enum SoundType { + CUSTOM("note.pling", 1f, 1f), + TIP("mob.endermen.idle", 1f, 1.2f), + ALERT("note.pling", 1f, 2f), + PORTAL("mob.endermen.portal", 1f, 1f), + SCORE("random.levelup", 1f, 1f), + OBJECTIVE_FIREWORKS_FAR("fireworks.blast_far", 0.75f, 1f), + OBJECTIVE_FIREWORKS_TWINKLE("fireworks.twinkle_far", 0.75f, 1f), + OBJECTIVE_GOOD("portal.travel", 0.7f, 2f), + OBJECTIVE_BAD("mob.blaze.death", 0.8f, 0.8f), + OBJECTIVE_MODE("mob.zombie.remedy", 0.15f, 1.2f), + DEATH_OWN("mob.irongolem.death", 1f, 1f), + DEATH_OTHER("mob.irongolem.hit", 1f, 1f); + + private final String resource; + private final float volume; + private final float pitch; + + SoundType(String resource, float volume, float pitch) { + this.resource = resource; + this.volume = volume; + this.pitch = pitch; + } + + public String getResource() { + return resource; + } + + public float getVolume() { + return volume; + } + + public float getPitch() { + return pitch; + } +} diff --git a/core/src/main/java/tc/oc/pgm/action/actions/SoundAction.java b/core/src/main/java/tc/oc/pgm/action/actions/SoundAction.java new file mode 100644 index 0000000000..f504008a32 --- /dev/null +++ b/core/src/main/java/tc/oc/pgm/action/actions/SoundAction.java @@ -0,0 +1,18 @@ +package tc.oc.pgm.action.actions; + +import net.kyori.adventure.sound.Sound; +import tc.oc.pgm.util.Audience; + +public class SoundAction extends AbstractAction { + private final Sound sound; + + public SoundAction(Sound sound) { + super(Audience.class); + this.sound = sound; + } + + @Override + public void trigger(Audience audience) { + audience.playSound(sound); + } +}