From bcf0a61121a5417e8736527ea38aa39e4ec9167c Mon Sep 17 00:00:00 2001 From: Richard Date: Sun, 7 Feb 2016 22:49:09 -0200 Subject: [PATCH] New effect, two more pathfinder goals. Still needing test. --- src/me/TheBukor/SkStuff/SkStuff.java | 9 ++- .../TheBukor/SkStuff/effects/EffMakeJump.java | 29 ++++---- .../SkStuff/effects/EffRemovePathGoal.java | 23 ++++++ .../SkStuff/effects/EffSetPathGoal.java | 71 +++++++++++++++++-- .../SkStuff/effects/EffShowEntityEffect.java | 57 +++++++++++++++ 5 files changed, 166 insertions(+), 23 deletions(-) create mode 100644 src/me/TheBukor/SkStuff/effects/EffShowEntityEffect.java diff --git a/src/me/TheBukor/SkStuff/SkStuff.java b/src/me/TheBukor/SkStuff/SkStuff.java index a6146af..71cb897 100644 --- a/src/me/TheBukor/SkStuff/SkStuff.java +++ b/src/me/TheBukor/SkStuff/SkStuff.java @@ -40,6 +40,7 @@ import me.TheBukor.SkStuff.effects.EffRemovePathGoal; import me.TheBukor.SkStuff.effects.EffReplaceBlocksWE; import me.TheBukor.SkStuff.effects.EffSetBlocksWE; import me.TheBukor.SkStuff.effects.EffSetPathGoal; +import me.TheBukor.SkStuff.effects.EffShowEntityEffect; import me.TheBukor.SkStuff.effects.EffSimulateSnow; import me.TheBukor.SkStuff.effects.EffToggleVanish; import me.TheBukor.SkStuff.effects.EffUndoRedoSession; @@ -93,9 +94,10 @@ public class SkStuff extends JavaPlugin { getLogger().info("Trying to register version specific stuff..."); Skript.registerEffect(EffClearPathGoals.class, "(clear|delete) [all] pathfind[er] goals (of|from) %livingentity%"); - Skript.registerEffect(EffRemovePathGoal.class, "remove pathfind[er] goal (0¦(avoid|run away from) entit(y|ies)|1¦break door[s]|2¦breed|3¦eat grass|4¦(flee from the sun|seek shad(e|ow))|5¦float (in[side]|on) water|6¦follow (owner|tamer)|7¦follow (adult|parent)[s]|8¦(fight back|react to|target) (damager|attacker)|9¦o(c|z)elot jump on blocks|10¦leap at target|11¦look at entit(y|ies)|12¦melee attack entit(y|ies)|13¦move to[wards] target|14¦attack nearest entity|15¦o(c|z)elot attack [chicken[s]]|16¦open door[s]|17¦(panic|flee)|18¦look around randomly|19¦(walk around randomly|wander)|20¦sit|21¦[creeper] swell) from %livingentity%"); - Skript.registerEffect(EffSetPathGoal.class, "add pathfind[er] goal [[with] priority %-integer%] (0¦(avoid|run away from) %entitydata%,[ ]radius %number%,[ ][at] speed %number%,[ ][at] speed if close %number%|1¦break door[s]|2¦breed,[ ][move to[wards] lover at] speed %number%|3¦eat grass|4¦(flee from the sun|seek shad(e|ow)),[ ][at] speed %number%|5¦float (in[side]|on) water|6¦follow (owner|tamer),[ ][at] speed %number%|7¦follow (adult|parent)[s],[ ][at] speed %number%|8¦(fight back|react to|target) (damager|attacker) [[of] type] %entitydata%|9¦o(c|z)elot jump on blocks,[ ][at] speed %number%|10¦leap at target [with [leap]] height %number%|11¦look at %entitydata%,[ ]radius %number%|12¦melee attack %entitydata%,[ ][at] speed %number%|13¦move to[wards] target,[ ][at] speed %number%,[ ]radius %number%|14¦attack nearest [entity [of] type] %entitydata%|15¦o(c|z)elot attack [chicken]|16¦open door[s]|17¦(panic|flee),[ ][at] speed %number%|18¦look around randomly|19¦(walk around randomly|wander),[ ][at] speed %number%,[ ][with] min[imum] [of] %-timespan% between mov(e[ment][s]|ing)|20¦sit|21¦[creeper] swell) to %livingentity%"); - Skript.registerEffect(EffMakeJump.class, "make %livingentity% jump"); + Skript.registerEffect(EffRemovePathGoal.class, "remove pathfind[er] goal (0¦(avoid|run away from) entit(y|ies)|1¦break door[s]|2¦breed|3¦eat grass|4¦(flee from the sun|seek shad(e|ow))|5¦float (in[side]|on) water|6¦follow (owner|tamer)|7¦follow (adult|parent)[s]|8¦(fight back|react to|target) (damager|attacker)|9¦o(c|z)elot jump on blocks|10¦leap at target|11¦look at entit(y|ies)|12¦melee attack entit(y|ies)|13¦move to[wards] target|14¦attack nearest entity|15¦o(c|z)elot attack [chicken[s]]|16¦open door[s]|17¦(panic|flee)|18¦look around randomly|19¦(walk around randomly|wander)|20¦sit|21¦[creeper] swell|22¦squid (swim|wander)|23¦[blaze] shoot fireball[s]) from %livingentity%"); + Skript.registerEffect(EffSetPathGoal.class, "add pathfind[er] goal [[with] priority %-integer%] (0¦(avoid|run away from) %entitydata%,[ ]radius %number%,[ ][at] speed %number%,[ ][at] speed if close %number%|1¦break door[s]|2¦breed,[ ][move to[wards] lover at] speed %number%|3¦eat grass|4¦(flee from the sun|seek shad(e|ow)),[ ][at] speed %number%|5¦float (in[side]|on) water|6¦follow (owner|tamer),[ ][at] speed %number%|7¦follow (adult|parent)[s],[ ][at] speed %number%|8¦(fight back|react to|target) (damager|attacker) [[of] type] %entitydata%|9¦o(c|z)elot jump on blocks,[ ][at] speed %number%|10¦leap at target [with [leap]] height %number%|11¦look at %entitydata%,[ ]radius %number%|12¦melee attack %entitydata%,[ ][at] speed %number%|13¦move to[wards] target,[ ][at] speed %number%,[ ]radius %number%|14¦attack nearest [entity [of] type] %entitydata%|15¦o(c|z)elot attack [chicken]|16¦open door[s]|17¦(panic|flee),[ ][at] speed %number%|18¦look around randomly|19¦(walk around randomly|wander),[ ][at] speed %number%,[ ][with] min[imum] [of] %-timespan% between mov(e[ment][s]|ing)|20¦sit|21¦[creeper] swell|22¦squid (swim|wander)|23¦[blaze] shoot fireball[s]) to %livingentity%"); + Skript.registerEffect(EffMakeJump.class, "make %livingentities% jump"); + Skript.registerEffect(EffShowEntityEffect.class, "(display|play|show) entity effect (0¦firework[s] explo(de|sion)|1¦hurt|2¦[[iron] golem] (give|offer) (rose|poppy)|3¦[sheep] eat grass|4¦wolf shake) at %entity%"); Skript.registerExpression(ExprNBTOf.class, Object.class, ExpressionType.PROPERTY, "nbt[[ ]tag[s]] of %entity/block/itemstack%", "%entity/block/itemstack%'s nbt[[ ]tag[s]]"); Skript.registerExpression(ExprItemNBT.class, ItemStack.class, ExpressionType.SIMPLE, "%itemstack% with [custom] nbt[[ ]tag[s]] %string%"); Skript.registerExpression(ExprTagOf.class, Object.class, ExpressionType.PROPERTY, "[nbt[ ]]tag %string% of [[nbt] compound] %compound%"); @@ -274,6 +276,7 @@ public class SkStuff extends JavaPlugin { } })); typeAmount += 2; + effAmount += 5; exprAmount += 6; if (Bukkit.getPluginManager().getPlugin("WorldEdit") != null) { getLogger().info("WorldEdit found! Registering WorldEdit stuff..."); diff --git a/src/me/TheBukor/SkStuff/effects/EffMakeJump.java b/src/me/TheBukor/SkStuff/effects/EffMakeJump.java index 2b68720..a4fb85f 100644 --- a/src/me/TheBukor/SkStuff/effects/EffMakeJump.java +++ b/src/me/TheBukor/SkStuff/effects/EffMakeJump.java @@ -2,6 +2,7 @@ package me.TheBukor.SkStuff.effects; import javax.annotation.Nullable; +import org.bukkit.entity.Entity; import org.bukkit.entity.LivingEntity; import org.bukkit.entity.Player; import org.bukkit.event.Event; @@ -13,7 +14,7 @@ import ch.njol.util.Kleenean; import me.TheBukor.SkStuff.util.ReflectionUtils; public class EffMakeJump extends Effect { - private Expression entity; + private Expression entities; private Class entInsent = ReflectionUtils.getNMSClass("EntityInsentient", false); private Class craftLivEnt = ReflectionUtils.getOBCClass("entity.CraftLivingEntity"); @@ -21,27 +22,29 @@ public class EffMakeJump extends Effect { @SuppressWarnings("unchecked") @Override public boolean init(Expression[] expr, int matchedPattern, Kleenean arg2, ParseResult result) { - entity = (Expression) expr[0]; + entities = (Expression) expr[0]; return true; } @Override public String toString(@Nullable Event e, boolean arg1) { - return "make ent jump"; + return "make " + entities.toString(e, false) + " jump"; } @Override protected void execute(Event e) { - LivingEntity ent = entity.getSingle(e); - if (ent instanceof Player || ent == null) - return; - Object obcEnt = craftLivEnt.cast(ent); - try { - Object nmsEnt = entInsent.cast(obcEnt.getClass().getMethod("getHandle").invoke(obcEnt)); - Object controllerJump = nmsEnt.getClass().getMethod("getControllerJump").invoke(nmsEnt); - controllerJump.getClass().getMethod("a").invoke(controllerJump); - } catch (Exception ex) { - ex.printStackTrace(); + LivingEntity[] ents = entities.getAll(e); + for (Entity ent : ents) { + if (ent instanceof Player || ent == null) + continue; + Object obcEnt = craftLivEnt.cast(ent); + try { + Object nmsEnt = entInsent.cast(obcEnt.getClass().getMethod("getHandle").invoke(obcEnt)); + Object controllerJump = nmsEnt.getClass().getMethod("getControllerJump").invoke(nmsEnt); + controllerJump.getClass().getMethod("a").invoke(controllerJump); + } catch (Exception ex) { + ex.printStackTrace(); + } } } } \ No newline at end of file diff --git a/src/me/TheBukor/SkStuff/effects/EffRemovePathGoal.java b/src/me/TheBukor/SkStuff/effects/EffRemovePathGoal.java index 3611cd1..ab11a05 100644 --- a/src/me/TheBukor/SkStuff/effects/EffRemovePathGoal.java +++ b/src/me/TheBukor/SkStuff/effects/EffRemovePathGoal.java @@ -5,6 +5,7 @@ import java.util.List; import javax.annotation.Nullable; +import org.bukkit.Bukkit; import org.bukkit.entity.LivingEntity; import org.bukkit.entity.Player; import org.bukkit.event.Event; @@ -44,7 +45,9 @@ public class EffRemovePathGoal extends Effect { private Class goalSit = ReflectionUtils.getNMSClass("PathfinderGoalSit", false); private Class goalSwell = ReflectionUtils.getNMSClass("PathfinderGoalSwell", false); + private Class entBlaze = ReflectionUtils.getNMSClass("EntityBlaze", false); private Class entInsent = ReflectionUtils.getNMSClass("EntityInsentient", false); + private Class entSquid = ReflectionUtils.getNMSClass("EntitySquid", false); private Class craftLivEnt = ReflectionUtils.getOBCClass("entity.CraftLivingEntity"); @SuppressWarnings("unchecked") @@ -116,7 +119,27 @@ public class EffRemovePathGoal extends Effect { toRemove = goalSit; } else if (mark == 21) { toRemove = goalSwell; + } else if (mark == 22) { + Class[] classes = entSquid.getDeclaredClasses(); + for (Class c : classes) { + Bukkit.broadcastMessage("\u00A79loop-class: \u00A7b" + c); + if (c.getSimpleName().equals("PathfinderGoalSquid")) { + toRemove = c; + break; + } + } + } else if (mark == 23) { + Class[] classes = entBlaze.getDeclaredClasses(); + for (Class c : classes) { + Bukkit.broadcastMessage("\u00A79loop-class: \u00A7b" + c); + if (c.getSimpleName().equals("PathfinderGoalBlazeFireball")) { + toRemove = c; + break; + } + } } + if (toRemove == null) + return; Iterator goals = ((List) ReflectionUtils.getField("b", goalSelectorClass, goalSelector)).iterator(); Iterator goalPriorities = ((List) ReflectionUtils.getField("c", goalSelectorClass, goalSelector)).iterator(); while (goals.hasNext()) { diff --git a/src/me/TheBukor/SkStuff/effects/EffSetPathGoal.java b/src/me/TheBukor/SkStuff/effects/EffSetPathGoal.java index 7011540..eb372ed 100644 --- a/src/me/TheBukor/SkStuff/effects/EffSetPathGoal.java +++ b/src/me/TheBukor/SkStuff/effects/EffSetPathGoal.java @@ -4,9 +4,12 @@ import javax.annotation.Nullable; import org.bukkit.Bukkit; import org.bukkit.entity.Animals; +import org.bukkit.entity.Blaze; import org.bukkit.entity.Creeper; import org.bukkit.entity.LivingEntity; +import org.bukkit.entity.Ocelot; import org.bukkit.entity.Player; +import org.bukkit.entity.Squid; import org.bukkit.entity.Tameable; import org.bukkit.event.Event; @@ -70,12 +73,11 @@ public class EffSetPathGoal extends Effect { private Class goalSit = ReflectionUtils.getNMSClass("PathfinderGoalSit", false); private Class goalSwell = ReflectionUtils.getNMSClass("PathfinderGoalSwell", false); + private Class craftLivEnt = ReflectionUtils.getOBCClass("entity.CraftLivingEntity"); private Class entAnimal = ReflectionUtils.getNMSClass("EntityAnimal", false); private Class entCreature = ReflectionUtils.getNMSClass("EntityCreature", false); private Class entInsent = ReflectionUtils.getNMSClass("EntityInsentient", false); - private Class entOcelot = ReflectionUtils.getNMSClass("EntityOcelot", false); private Class entTameable = ReflectionUtils.getNMSClass("EntityTameableAnimal", false); - private Class craftLivEnt = ReflectionUtils.getOBCClass("entity.CraftLivingEntity"); @SuppressWarnings("unchecked") @Override @@ -145,10 +147,12 @@ public class EffSetPathGoal extends Effect { if (ent instanceof Player || ent == null) return; Object obcEnt = craftLivEnt.cast(ent); + Object nmsEnt = null; + Class clazz = null; try { boolean target = false; Object newGoal = null; - Object nmsEnt = entInsent.cast(obcEnt.getClass().getMethod("getHandle").invoke(obcEnt)); + nmsEnt = entInsent.cast(obcEnt.getClass().getMethod("getHandle").invoke(obcEnt)); Object goals = ReflectionUtils.getField("goalSelector", entInsent, nmsEnt); Object targets = ReflectionUtils.getField("targetSelector", entInsent, nmsEnt); if (mark == 0) { @@ -217,9 +221,9 @@ public class EffSetPathGoal extends Effect { newGoal = goalReactAttack.getConstructor(entCreature, boolean.class, Class[].class).newInstance(nmsEnt, false, nmsClass[0]); } else if (mark == 9) { double spd = jumpOnBlockSpeed.getSingle(e).doubleValue(); - if (nmsEnt.getClass() != entOcelot) + if (!(ent instanceof Ocelot)) return; - newGoal = goalJumpOnBlock.getConstructor(entOcelot, double.class).newInstance(nmsEnt, spd); + newGoal = goalJumpOnBlock.getConstructor(nmsEnt.getClass(), double.class).newInstance(nmsEnt, spd); } else if (mark == 10) { float height = leapHeight.getSingle(e).floatValue(); newGoal = goalLeapTarget.getConstructor(entInsent, float.class).newInstance(nmsEnt, height); @@ -300,14 +304,67 @@ public class EffSetPathGoal extends Effect { return; } newGoal = goalSwell.getConstructor(nmsEnt.getClass()).newInstance(nmsEnt); + } else if (mark == 22) { + if (!(ent instanceof Squid)) { + Bukkit.broadcastMessage("\u00A7c" + ent.getType().toString() + " is not a squid - \u00A7e[DEBUG MESSAGE]"); + return; + } + Class[] classes = nmsEnt.getClass().getDeclaredClasses(); + for (Class c : classes) { + Bukkit.broadcastMessage("\u00A79loop-class: \u00A7b" + c); + if (c.getSimpleName().equals("PathfinderGoalSquid")) { + clazz = c; + clazz.getConstructor(nmsEnt.getClass()).setAccessible(true); + break; + } + } + if (clazz == null) + return; + newGoal = clazz.getConstructor(nmsEnt.getClass()).newInstance(nmsEnt); + clazz.getConstructor(nmsEnt.getClass()).setAccessible(false); + } else if (mark == 23) { + if (!(ent instanceof Blaze)) { + Bukkit.broadcastMessage("\u00A7c" + ent.getType().toString() + " is not a blaze - \u00A7e[DEBUG MESSAGE]"); + return; + } + Class[] classes = nmsEnt.getClass().getDeclaredClasses(); + for (Class c : classes) { + Bukkit.broadcastMessage("\u00A79loop-class: \u00A7b" + c); + if (c.getSimpleName().equals("PathfinderGoalBlazeFireball")) { + clazz = c; + clazz.getConstructor(nmsEnt.getClass()).setAccessible(true); + break; + } + } + if (clazz == null) + return; + newGoal = clazz.getConstructor(nmsEnt.getClass()).newInstance(nmsEnt); + clazz.getConstructor(nmsEnt.getClass()).setAccessible(false); + } else if (mark == 24) { + // TODO: Add more goal/target selectors + + /* Classes that have their own pathfinder goals: + * Enderman, 3 goals, place blocks, pickup blocks and player who looked (?). + * Ghast, 3 goals, all copy of existing ones, but adapted to a flying ghast. + * Rabbit, 3 goals, 2 adapted copies, 1 new (eat carrot crops) + * Silverfish, 2 goals, hide in block and wake other silverfish blocks. + * Slime, 4 goals, random jump, go to near player, go in random direction and idle. + * Spider, 2 goals, adapted copies of melee and nearest attackable. + */ } if (target) { newGoal = goalSelector.getMethod("a", int.class, goal).invoke(targets, priority, newGoal); } else { newGoal = goalSelector.getMethod("a", int.class, goal).invoke(goals, priority, newGoal); } - } catch (Exception ex) { - ex.printStackTrace(); + } catch (Exception ex1) { + if (clazz != null) + try { + clazz.getConstructor(nmsEnt.getClass()).setAccessible(true); + } catch (SecurityException | NoSuchMethodException ex2) { + ex2.printStackTrace(); + } + ex1.printStackTrace(); } } } \ No newline at end of file diff --git a/src/me/TheBukor/SkStuff/effects/EffShowEntityEffect.java b/src/me/TheBukor/SkStuff/effects/EffShowEntityEffect.java new file mode 100644 index 0000000..2e320cd --- /dev/null +++ b/src/me/TheBukor/SkStuff/effects/EffShowEntityEffect.java @@ -0,0 +1,57 @@ +package me.TheBukor.SkStuff.effects; + +import javax.annotation.Nullable; + +import org.bukkit.EntityEffect; +import org.bukkit.entity.Entity; +import org.bukkit.event.Event; + +import ch.njol.skript.lang.Effect; +import ch.njol.skript.lang.Expression; +import ch.njol.skript.lang.SkriptParser.ParseResult; +import ch.njol.util.Kleenean; + +public class EffShowEntityEffect extends Effect { + private Expression entity; + + private int mark; + private String toStringMark; + + private EntityEffect effect; + + @SuppressWarnings("unchecked") + @Override + public boolean init(Expression[] expr, int matchedPattern, Kleenean arg2, ParseResult result) { + entity = (Expression) expr[0]; + mark = result.mark; + if (mark == 0) { + effect = EntityEffect.FIREWORK_EXPLODE; + toStringMark = "fireworks explosion"; + } else if (mark == 1) { + effect = EntityEffect.HURT; + toStringMark = "hurt"; + } else if (mark == 2) { + effect = EntityEffect.IRON_GOLEM_ROSE; + toStringMark = "iron golem offer rose"; + } else if (mark == 3) { + effect = EntityEffect.SHEEP_EAT; + toStringMark = "sheep eat grass"; + } else if (mark == 4) { + effect = EntityEffect.WOLF_SHAKE; + toStringMark = "wolf shake"; + } + return true; + } + + @Override + public String toString(@Nullable Event e, boolean arg1) { + return "play entity effect " + toStringMark + "at" + entity.toString(e, false); + } + + @Override + protected void execute(Event e) { + Entity ent = entity.getSingle(e); + if (ent != null) + ent.playEffect(effect); + } +} \ No newline at end of file