diff --git a/src/main/java/ch/njol/skript/conditions/CondIsSheared.java b/src/main/java/ch/njol/skript/conditions/CondIsSheared.java
new file mode 100644
index 00000000000..f667f292899
--- /dev/null
+++ b/src/main/java/ch/njol/skript/conditions/CondIsSheared.java
@@ -0,0 +1,73 @@
+/**
+ * This file is part of Skript.
+ *
+ * Skript is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * Skript is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Skript. If not, see .
+ *
+ * Copyright Peter Güttinger, SkriptLang team and contributors
+ */
+package ch.njol.skript.conditions;
+
+import ch.njol.skript.Skript;
+import ch.njol.skript.conditions.base.PropertyCondition;
+import ch.njol.skript.doc.Description;
+import ch.njol.skript.doc.Examples;
+import ch.njol.skript.doc.Name;
+import ch.njol.skript.doc.RequiredPlugins;
+import ch.njol.skript.doc.Since;
+import io.papermc.paper.entity.Shearable;
+import org.bukkit.entity.Cow;
+import org.bukkit.entity.LivingEntity;
+import org.bukkit.entity.Sheep;
+import org.bukkit.entity.Snowman;
+import org.bukkit.event.entity.CreatureSpawnEvent;
+
+@Name("Entity Is Sheared")
+@Description("Checks whether entities are sheared. This condition only works on cows, sheep and snowmen for versions below 1.19.4.")
+@Examples({
+ "if targeted entity of player is sheared:",
+ "\tsend \"This entity has nothing left to shear!\" to player"
+})
+@Since("INSERT VERSION")
+@RequiredPlugins("MC 1.13+ (cows, sheep & snowmen), Paper 1.19.4+ (all shearable entities)")
+public class CondIsSheared extends PropertyCondition {
+
+ private static final boolean INTERFACE_METHOD = Skript.classExists("io.papermc.paper.entity.Shearable");
+
+ static {
+ register(CondIsSheared.class, "(sheared|shorn)", "livingentities");
+ }
+
+ @Override
+ public boolean check(LivingEntity entity) {
+ if (entity instanceof Cow) {
+ return entity.getEntitySpawnReason() == CreatureSpawnEvent.SpawnReason.SHEARED;
+ } else if (INTERFACE_METHOD) {
+ if (!(entity instanceof Shearable)) {
+ return false;
+ }
+ return !((Shearable) entity).readyToBeSheared();
+ } else if (entity instanceof Sheep) {
+ return ((Sheep) entity).isSheared();
+ } else if (entity instanceof Snowman) {
+ return ((Snowman) entity).isDerp();
+ }
+ return false;
+ }
+
+ @Override
+ protected String getPropertyName() {
+ return "sheared";
+ }
+
+}
diff --git a/src/main/java/ch/njol/skript/effects/EffShear.java b/src/main/java/ch/njol/skript/effects/EffShear.java
index 467aebeb70a..5bb6bf3d991 100644
--- a/src/main/java/ch/njol/skript/effects/EffShear.java
+++ b/src/main/java/ch/njol/skript/effects/EffShear.java
@@ -18,60 +18,86 @@
*/
package ch.njol.skript.effects;
-import org.bukkit.entity.LivingEntity;
-import org.bukkit.entity.Sheep;
-import org.bukkit.event.Event;
-import org.eclipse.jdt.annotation.Nullable;
-
import ch.njol.skript.Skript;
import ch.njol.skript.doc.Description;
import ch.njol.skript.doc.Examples;
import ch.njol.skript.doc.Name;
+import ch.njol.skript.doc.RequiredPlugins;
import ch.njol.skript.doc.Since;
import ch.njol.skript.lang.Effect;
import ch.njol.skript.lang.Expression;
import ch.njol.skript.lang.SkriptParser.ParseResult;
import ch.njol.util.Kleenean;
-/**
- * @author Peter Güttinger
- */
+import io.papermc.paper.entity.Shearable;
+
+import org.bukkit.entity.LivingEntity;
+import org.bukkit.entity.Sheep;
+import org.bukkit.entity.Snowman;
+import org.bukkit.event.Event;
+import org.jetbrains.annotations.Nullable;
+
@Name("Shear")
-@Description("Shears or 'un-shears' a sheep. Please note that no wool is dropped, this only sets the 'sheared' state of the sheep.")
-@Examples({"on rightclick on a sheep holding a sword:",
- " shear the clicked sheep"})
-@Since("2.0")
+@Description({
+ "Shears or un-shears a shearable entity with drops by shearing and a 'sheared' sound. Using with 'force' will force this effect despite the entity's 'shear state'.",
+ "\nPlease note that..:",
+ "\n- If your server is not running with Paper 1.19.4 or higher, this effect will only change its 'shear state', and the 'force' effect is unavailable",
+ "\n- Force-shearing or un-shearing on a sheared mushroom cow is not possible"
+})
+@Examples({
+ "on rightclick on a sheep holding a sword:",
+ "\tshear the clicked sheep",
+ "\tchance of 10%",
+ "\tforce shear the clicked sheep"
+})
+@Since("2.0 (cows, sheep & snowmen), INSERT VERSION (all shearable entities)")
+@RequiredPlugins("Paper 1.19.4+ (all shearable entities)")
public class EffShear extends Effect {
+
+ private static final boolean INTERFACE_METHOD = Skript.classExists("io.papermc.paper.entity.Shearable");
+
static {
Skript.registerEffect(EffShear.class,
- "shear %livingentities%",
+ (INTERFACE_METHOD ? "[:force] " : "") + "shear %livingentities%",
"un[-]shear %livingentities%");
}
-
- @SuppressWarnings("null")
- private Expression sheep;
+
+ private Expression entity;
+ private boolean force;
private boolean shear;
-
- @SuppressWarnings({"unchecked", "null"})
+
@Override
- public boolean init(final Expression>[] exprs, final int matchedPattern, final Kleenean isDelayed, final ParseResult parseResult) {
- sheep = (Expression) exprs[0];
+ @SuppressWarnings("unchecked")
+ public boolean init(Expression>[] exprs, int matchedPattern, Kleenean isDelayed, ParseResult parseResult) {
+ entity = (Expression) exprs[0];
+ force = parseResult.hasTag("force");
shear = matchedPattern == 0;
return true;
}
@Override
- protected void execute(final Event e) {
- for (final LivingEntity en : sheep.getArray(e)) {
- if (en instanceof Sheep) {
- ((Sheep) en).setSheared(shear);
+ protected void execute(Event event) {
+ for (LivingEntity entity : entity.getArray(event)) {
+ if (shear && INTERFACE_METHOD) {
+ if (!(entity instanceof Shearable))
+ continue;
+ Shearable shearable = ((Shearable) entity);
+ if (!force && !shearable.readyToBeSheared())
+ continue;
+ shearable.shear();
+ continue;
+ }
+ if (entity instanceof Sheep) {
+ ((Sheep) entity).setSheared(shear);
+ } else if (entity instanceof Snowman) {
+ ((Snowman) entity).setDerp(shear);
}
}
}
@Override
- public String toString(final @Nullable Event e, final boolean debug) {
- return (shear ? "" : "un") + "shear " + sheep.toString(e, debug);
+ public String toString(@Nullable Event event, boolean debug) {
+ return (shear ? "" : "un") + "shear " + entity.toString(event, debug);
}
}