diff --git a/paper/src/main/java/com/denizenscript/denizen/paper/PaperModule.java b/paper/src/main/java/com/denizenscript/denizen/paper/PaperModule.java index 58ff60ed66..3cf01c2b26 100644 --- a/paper/src/main/java/com/denizenscript/denizen/paper/PaperModule.java +++ b/paper/src/main/java/com/denizenscript/denizen/paper/PaperModule.java @@ -100,6 +100,9 @@ public static void init() { ScriptEvent.registerScriptEvent(TNTPrimesScriptEvent.class); } ScriptEvent.registerScriptEvent(UnknownCommandScriptEvent.class); + if (NMSHandler.getVersion().isAtLeast(NMSVersion.v1_21)) { + ScriptEvent.registerScriptEvent(VaultChangeStateScriptEvent.class); + } if (NMSHandler.getVersion().isAtLeast(NMSVersion.v1_19)) { ScriptEvent.registerScriptEvent(WardenChangesAngerLevelScriptEvent.class); } diff --git a/paper/src/main/java/com/denizenscript/denizen/paper/events/VaultChangeStateScriptEvent.java b/paper/src/main/java/com/denizenscript/denizen/paper/events/VaultChangeStateScriptEvent.java new file mode 100644 index 0000000000..aa11288539 --- /dev/null +++ b/paper/src/main/java/com/denizenscript/denizen/paper/events/VaultChangeStateScriptEvent.java @@ -0,0 +1,67 @@ +package com.denizenscript.denizen.paper.events; + +import com.denizenscript.denizen.events.BukkitScriptEvent; +import com.denizenscript.denizen.objects.LocationTag; +import com.denizenscript.denizencore.objects.ObjectTag; +import com.denizenscript.denizencore.objects.core.ElementTag; +import io.papermc.paper.event.block.VaultChangeStateEvent; +import org.bukkit.event.EventHandler; +import org.bukkit.event.Listener; + +public class VaultChangeStateScriptEvent extends BukkitScriptEvent implements Listener { + + // <--[event] + // @Events + // vault changes state + // + // @Plugin Paper + // + // @Group Block + // + // @Cancellable true + // + // @Location true + // + // @Triggers when a vault block state changes + // + // @Context + // returns the LocationTag of the vault block. + // returns the ElementTag of the vault state on change. + // returns the ElementTag of the new vault state. + // + // @Player when the entity who triggered the change is a player. + // + // --> + + public VaultChangeStateScriptEvent() { + registerCouldMatcher("vault changes state"); + } + + public LocationTag location; + public VaultChangeStateEvent event; + + @Override + public boolean matches(ScriptPath path) { + if (!runInCheck(path, location)) { + return false; + } + return super.matches(path); + } + + @Override + public ObjectTag getContext(String name) { + return switch (name) { + case "current_state" -> new ElementTag(event.getCurrentState().toString().toLowerCase()); + case "new_state" -> new ElementTag(event.getNewState().toString().toLowerCase()); + case "location" -> location; + default -> super.getContext(name); + }; + } + + @EventHandler + public void onVaultChangeStateEvent(VaultChangeStateEvent event) { + location = new LocationTag(event.getBlock().getLocation()); + this.event = event; + fire(event); + } +} diff --git a/plugin/src/main/java/com/denizenscript/denizen/events/ScriptEventRegistry.java b/plugin/src/main/java/com/denizenscript/denizen/events/ScriptEventRegistry.java index a3e71d4ec1..c9c46dc9bc 100644 --- a/plugin/src/main/java/com/denizenscript/denizen/events/ScriptEventRegistry.java +++ b/plugin/src/main/java/com/denizenscript/denizen/events/ScriptEventRegistry.java @@ -17,6 +17,7 @@ import com.denizenscript.denizen.utilities.depends.Depends; import com.denizenscript.denizencore.events.ScriptEvent; import com.denizenscript.denizencore.events.ScriptEventCouldMatcher; +import org.bukkit.event.entity.TrialSpawnerSpawnEvent; import java.util.Arrays; @@ -100,6 +101,8 @@ public static void registerMainEvents() { } if (NMSHandler.getVersion().isAtLeast(NMSVersion.v1_21)) { ScriptEvent.registerScriptEvent(CrafterCraftsScriptEvent.class); + ScriptEvent.registerScriptEvent(EntityTrialSpawnerSpawnScriptEvent.class); + ScriptEvent.registerScriptEvent(VaultDisplayItemScriptEvent.class); } // Entity events diff --git a/plugin/src/main/java/com/denizenscript/denizen/events/block/VaultDisplayItemScriptEvent.java b/plugin/src/main/java/com/denizenscript/denizen/events/block/VaultDisplayItemScriptEvent.java new file mode 100644 index 0000000000..06e20e3c11 --- /dev/null +++ b/plugin/src/main/java/com/denizenscript/denizen/events/block/VaultDisplayItemScriptEvent.java @@ -0,0 +1,72 @@ +package com.denizenscript.denizen.events.block; + +import com.denizenscript.denizen.events.BukkitScriptEvent; +import com.denizenscript.denizen.objects.ItemTag; +import com.denizenscript.denizen.objects.LocationTag; +import com.denizenscript.denizencore.objects.ObjectTag; +import org.bukkit.event.EventHandler; +import org.bukkit.event.Listener; +import org.bukkit.event.block.VaultDisplayItemEvent; + +public class VaultDisplayItemScriptEvent extends BukkitScriptEvent implements Listener { + + // <--[event] + // @Events + // vault displays + // + // @Group Block + // + // @Location true + // + // @Cancellable true + // + // @Triggers when a vault block displays an item. + // + // @Context + // returns the LocationTag of the vault block. + // returns the ItemTag being displayed. + // + // @Determine + // "ITEM:" to set the item being displayed. + // + // --> + + public VaultDisplayItemScriptEvent() { + registerCouldMatcher("vault displays "); + this.registerDetermination("item", ItemTag.class, (evt, context, item) -> { + event.setDisplayItem(item.getItemStack()); + }); + } + + public LocationTag location; + public ItemTag item; + public VaultDisplayItemEvent event; + + @Override + public boolean matches(ScriptPath path) { + if (!runInCheck(path, location)) { + return false; + } + if (!path.tryArgObject(2, item)) { + return false; + } + return super.matches(path); + } + + @Override + public ObjectTag getContext(String name) { + return switch (name) { + case "item" -> new ItemTag(event.getDisplayItem()); + case "location" -> location; + default -> super.getContext(name); + }; + } + + @EventHandler + public void onVaultDisplayItemEvent(VaultDisplayItemEvent event) { + location = new LocationTag(event.getBlock().getLocation()); + item = new ItemTag(event.getDisplayItem()); + this.event = event; + fire(event); + } +} diff --git a/plugin/src/main/java/com/denizenscript/denizen/events/entity/EntityTrialSpawnerSpawnScriptEvent.java b/plugin/src/main/java/com/denizenscript/denizen/events/entity/EntityTrialSpawnerSpawnScriptEvent.java new file mode 100644 index 0000000000..0aa05187b8 --- /dev/null +++ b/plugin/src/main/java/com/denizenscript/denizen/events/entity/EntityTrialSpawnerSpawnScriptEvent.java @@ -0,0 +1,85 @@ +package com.denizenscript.denizen.events.entity; + +import com.denizenscript.denizen.objects.EntityTag; +import com.denizenscript.denizen.objects.LocationTag; +import com.denizenscript.denizen.utilities.implementation.BukkitScriptEntryData; +import com.denizenscript.denizen.events.BukkitScriptEvent; +import com.denizenscript.denizencore.objects.ObjectTag; +import com.denizenscript.denizencore.scripts.ScriptEntryData; +import org.bukkit.entity.Entity; +import org.bukkit.event.EventHandler; +import org.bukkit.event.Listener; +import org.bukkit.event.entity.TrialSpawnerSpawnEvent; + +public class EntityTrialSpawnerSpawnScriptEvent extends BukkitScriptEvent implements Listener { + + // <--[event] + // @Events + // trial_spawner spawns + // + // @Group Entity + // + // @Location true + // + // @Cancellable true + // + // @Triggers when an entity spawns from a trial spawner. + // + // @Switch spawner: to only process the event if the trial spawner's location matches. + // + // @Context + // returns the EntityTag that spawned. + // returns the LocationTag the entity will spawn at. + // returns the LocationTag of the trial spawner. + // + // --> + + public EntityTrialSpawnerSpawnScriptEvent() { + registerCouldMatcher("trial_spawner spawns "); + registerSwitches("spawner"); + } + + private EntityTag entity; + private LocationTag location; + private LocationTag trialSpawnerLocation; + + @Override + public boolean matches(ScriptPath path) { + if (!path.tryArgObject(2, entity)) { + return false; + } + if (!path.tryObjectSwitch("spawner", trialSpawnerLocation)) { + return false; + } + if (!runInCheck(path, location)) { + return false; + } + return super.matches(path); + } + + @Override + public ScriptEntryData getScriptEntryData() { + return new BukkitScriptEntryData(entity); + } + + @Override + public ObjectTag getContext(String name) { + return switch (name) { + case "entity" -> entity; + case "location" -> location; + case "spawner_location" -> trialSpawnerLocation; + default -> super.getContext(name); + }; + } + + @EventHandler + public void onTrialSpawnerSpawn(TrialSpawnerSpawnEvent event) { + Entity entity = event.getEntity(); + this.entity = new EntityTag(entity); + location = new LocationTag(event.getLocation()); + trialSpawnerLocation = new LocationTag(event.getTrialSpawner().getLocation()); + EntityTag.rememberEntity(entity); + fire(event); + EntityTag.forgetEntity(entity); + } +} diff --git a/plugin/src/main/java/com/denizenscript/denizen/objects/properties/PropertyRegistry.java b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/PropertyRegistry.java index 477c8bb129..b46f6504aa 100644 --- a/plugin/src/main/java/com/denizenscript/denizen/objects/properties/PropertyRegistry.java +++ b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/PropertyRegistry.java @@ -296,6 +296,9 @@ public static void registerMainProperties() { PropertyParser.registerProperty(MaterialLightable.class, MaterialTag.class); PropertyParser.registerProperty(MaterialMode.class, MaterialTag.class); PropertyParser.registerProperty(MaterialNote.class, MaterialTag.class); + if (NMSHandler.getVersion().isAtLeast(NMSVersion.v1_21)) { + PropertyParser.registerProperty(MaterialOminous.class, MaterialTag.class); + } PropertyParser.registerProperty(MaterialPersistent.class, MaterialTag.class); PropertyParser.registerProperty(MaterialPower.class, MaterialTag.class); PropertyParser.registerProperty(MaterialShape.class, MaterialTag.class); @@ -303,6 +306,9 @@ public static void registerMainProperties() { PropertyParser.registerProperty(MaterialSnowable.class, MaterialTag.class); PropertyParser.registerProperty(MaterialSwitchable.class, MaterialTag.class); PropertyParser.registerProperty(MaterialUnstable.class, MaterialTag.class); + if (NMSHandler.getVersion().isAtLeast(NMSVersion.v1_21)) { + PropertyParser.registerProperty(MaterialVaultState.class, MaterialTag.class); + } PropertyParser.registerProperty(MaterialWaterlogged.class, MaterialTag.class); // register core TradeTag properties diff --git a/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialOminous.java b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialOminous.java new file mode 100644 index 0000000000..b607c481ce --- /dev/null +++ b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialOminous.java @@ -0,0 +1,98 @@ +package com.denizenscript.denizen.objects.properties.material; + +import com.denizenscript.denizen.objects.MaterialTag; +import com.denizenscript.denizencore.objects.Mechanism; +import com.denizenscript.denizencore.objects.ObjectTag; +import com.denizenscript.denizencore.objects.core.ElementTag; +import com.denizenscript.denizencore.objects.properties.Property; +import com.denizenscript.denizencore.objects.properties.PropertyParser; +import org.bukkit.block.data.type.TrialSpawner; +import org.bukkit.block.data.type.Vault; + +public class MaterialOminous implements Property { + + public static boolean describes(ObjectTag material) { + return material instanceof MaterialTag + && ((MaterialTag) material).hasModernData() + && (((MaterialTag) material).getModernData() instanceof Vault + || ((MaterialTag) material).getModernData() instanceof TrialSpawner); + } + + public static MaterialOminous getFrom(ObjectTag _material) { + if (!describes(_material)) { + return null; + } else { + return new MaterialOminous((MaterialTag) _material); + } + } + + public static final String[] handledMechs = new String[]{ + "ominous" + }; + + public MaterialOminous(MaterialTag _material) { + material = _material; + } + + MaterialTag material; + + public static void register() { + + // <--[tag] + // @attribute + // @returns ElementTag(Boolean) + // @mechanism MaterialTag.ominous + // @group properties + // @description + // Returns whether the block is ominous or not. + // Currently supports Vault and Trial Spawner blocks. + // --> + PropertyParser.registerStaticTag(MaterialOminous.class, ElementTag.class, "is_ominous", (attribute, material) -> { + return new ElementTag(material.getOminous()); + }); + } + + public boolean getOminous() { + if (material.getModernData() instanceof Vault) { + return ((Vault) material.getModernData()).isOminous(); + } else if (material.getModernData() instanceof TrialSpawner) { + return ((TrialSpawner) material.getModernData()).isOminous(); + } + return false; + } + + public void setOminous(boolean ominous) { + if (material.getModernData() instanceof Vault vault) { + vault.setOminous(ominous); + } else if (material.getModernData() instanceof TrialSpawner spawner) { + spawner.setOminous(ominous); + } + } + + @Override + public String getPropertyString() { + return String.valueOf(getOminous()); + } + + @Override + public String getPropertyId() { + return "ominous"; + } + + @Override + public void adjust(Mechanism mechanism) { + + // <--[mechanism] + // @object MaterialTag + // @name ominous + // @input ElementTag(Boolean) + // @description + // Sets the ominousness of the block (trial spawner or vault). + // @tags + // + // --> + if (mechanism.matches("ominous") && mechanism.requireBoolean()) { + setOminous(mechanism.getValue().asBoolean()); + } + } +} diff --git a/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialVaultState.java b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialVaultState.java new file mode 100644 index 0000000000..3aca5c6da2 --- /dev/null +++ b/plugin/src/main/java/com/denizenscript/denizen/objects/properties/material/MaterialVaultState.java @@ -0,0 +1,90 @@ +package com.denizenscript.denizen.objects.properties.material; + +import com.denizenscript.denizen.objects.MaterialTag; +import com.denizenscript.denizencore.objects.Mechanism; +import com.denizenscript.denizencore.objects.ObjectTag; +import com.denizenscript.denizencore.objects.core.ElementTag; +import com.denizenscript.denizencore.objects.properties.Property; +import com.denizenscript.denizencore.objects.properties.PropertyParser; +import org.bukkit.block.data.type.Vault; + +public class MaterialVaultState implements Property { + + public static boolean describes(ObjectTag material) { + return material instanceof MaterialTag + && ((MaterialTag) material).hasModernData() + && ((MaterialTag) material).getModernData() instanceof Vault; + } + + public static MaterialVaultState getFrom(ObjectTag _material) { + if (!describes(_material)) { + return null; + } else { + return new MaterialVaultState((MaterialTag) _material); + } + } + + public static final String[] handledMechs = new String[]{ + "state" + }; + + public MaterialVaultState(MaterialTag _material) { + material = _material; + } + + MaterialTag material; + + public static void register() { + + // <--[tag] + // @attribute + // @returns ElementTag + // @mechanism MaterialTag.state + // @group properties + // @description + // Returns the current state of this vault block. + // --> + PropertyParser.registerStaticTag(MaterialVaultState.class, ElementTag.class, "state", (attribute, material) -> { + return material.getState(); + }); + } + + public Vault getVault() { + return (Vault) material.getModernData(); + } + + public ElementTag getState() { + return new ElementTag(getVault().getVaultState()); + } + + @Override + public String getPropertyString() { + return getState().identify(); + } + + @Override + public String getPropertyId() { + return "state"; + } + + @Override + public void adjust(Mechanism mechanism) { + + // <--[mechanism] + // @object MaterialTag + // @name state + // @input ElementTag + // @description + // Sets the vault block state. + // @tags + // + // --> + if (mechanism.matches("state")) { + if (mechanism.requireEnum(Vault.State.class)) { + getVault().setVaultState(Vault.State.valueOf(mechanism.getValue().asString().toUpperCase())); + } else { + mechanism.echoError("MaterialTag.State mechanism has bad input: vault state value '" + mechanism.getValue().asString() + "' is invalid."); + } + } + } +}