Use spigot particle API

This commit is contained in:
kaenganxt
2014-12-01 17:55:29 +01:00
parent 577c1c107a
commit babe68ec49
9 changed files with 1608 additions and 454 deletions

View File

@@ -1,281 +0,0 @@
package de.anura.core;
import de.anura.core.ReflectionUtil.DynamicPackage;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.logging.Level;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.entity.Player;
/**
* ParticleEffect Library v1.3
*
* This library was created by @DarkBlade12 based on content related to
* particles of @microgeek (names and packet values), it allows you to display
* all Minecraft particle effects on a Bukkit server
*
* You are welcome to use it, modify it and redistribute it under the following
* conditions: 1. Don't claim this class as your own 2. Don't remove this text
*
* (Would be nice if you provide credit to me)
*
* @author DarkBlade12
*/
public enum ParticleEffect {
HUGE_EXPLOSION("hugeexplosion", 0),
LARGE_EXPLODE("largeexplode", 1),
FIREWORKS_SPARK("fireworksSpark", 2),
BUBBLE("bubble", 3),
SUSPEND("suspend", 4),
DEPTH_SUSPEND("depthSuspend", 5),
TOWN_AURA("townaura", 6),
CRIT("crit", 7),
MAGIC_CRIT("magicCrit", 8),
MOB_SPELL("mobSpell", 9),
MOB_SPELL_AMBIENT("mobSpellAmbient", 10),
SPELL("spell", 11),
INSTANT_SPELL("instantSpell", 12),
WITCH_MAGIC("witchMagic", 13),
NOTE("note", 14),
PORTAL("portal", 15),
ENCHANTMENT_TABLE("enchantmenttable", 16),
EXPLODE("explode", 17),
FLAME("flame", 18),
LAVA("lava", 19),
FOOTSTEP("footstep", 20),
SPLASH("splash", 21),
LARGE_SMOKE("largesmoke", 22),
CLOUD("cloud", 23),
RED_DUST("reddust", 24),
SNOWBALL_POOF("snowballpoof", 25),
DRIP_WATER("dripWater", 26),
DRIP_LAVA("dripLava", 27),
SNOW_SHOVEL("snowshovel", 28),
SLIME("slime", 29),
HEART("heart", 30),
ANGRY_VILLAGER("angryVillager", 31),
HAPPY_VILLAGER("happyVillager", 32);
private static final Map<String, ParticleEffect> NAME_MAP = new HashMap<>();
private static final Map<Integer, ParticleEffect> ID_MAP = new HashMap<>();
private static final double MAX_RANGE = 20.0D;
private static Constructor<?> PARTICLE_PACKET_CONSTRUCTOR;
static {
for (ParticleEffect effect : values()) {
NAME_MAP.put(effect.name, effect);
ID_MAP.put(effect.id, effect);
}
try {
PARTICLE_PACKET_CONSTRUCTOR = ReflectionUtil.getConstructor(ReflectionUtil.getClass("PacketPlayOutWorldParticles", DynamicPackage.MINECRAFT_SERVER), String.class, float.class, float.class,
float.class, float.class, float.class, float.class, float.class, int.class);
} catch (Exception e) {
System.out.println(e.getStackTrace());
}
}
private String name;
private int id;
ParticleEffect(String name, int id) {
this.name = name;
this.id = id;
}
public String getName() {
return name;
}
public int getId() {
return id;
}
public static ParticleEffect fromName(String name) {
if (name != null) {
for (Entry<String, ParticleEffect> e : NAME_MAP.entrySet()) {
if (e.getKey().equalsIgnoreCase(name)) {
return e.getValue();
}
}
}
return null;
}
public static ParticleEffect fromId(int id) {
return ID_MAP.get(id);
}
private static List<Player> getPlayersInRange(Location loc, double range) {
List<Player> players = new ArrayList<>();
double sqr = range * range;
for (Player p : loc.getWorld().getPlayers()) {
if (p.getLocation().distanceSquared(loc) <= sqr) {
players.add(p);
}
}
return players;
}
private static Object createPacket(String name, Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
if (amount <= 0) {
throw new IllegalArgumentException("Amount of particles has to be greater than 0");
}
try {
Object p = PARTICLE_PACKET_CONSTRUCTOR.newInstance(name, (float) loc.getX(), (float) loc.getY(), (float) loc.getZ(), offsetX, offsetY, offsetZ, speed, amount);
return p;
} catch (IllegalAccessException | IllegalArgumentException | InstantiationException | InvocationTargetException e) {
Bukkit.getLogger().warning("[ParticleEffect] Failed to create a particle packet!");
return null;
}
}
private Object createPacket(Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
return createPacket(this.getName(), loc, offsetX, offsetY, offsetZ, speed, amount);
}
private static Object createIconCrackPacket(int id, Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
return createPacket("iconcrack_" + id, loc, offsetX, offsetY, offsetZ, speed, amount);
}
private static Object createBlockCrackPacket(int id, byte data, Location loc, float offsetX, float offsetY, float offsetZ, int amount) {
return createPacket("blockcrack_" + id + "_" + data, loc, offsetX, offsetY, offsetZ, 1.0F, amount);
}
private static Object createBlockDustPacket(int id, byte data, Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
return createPacket("blockdust_" + id + "_" + data, loc, offsetX, offsetY, offsetZ, speed, amount);
}
private static void sendPacket(Player p, Object packet) {
if (packet != null) {
try {
Object entityPlayer = ReflectionUtil.invokeMethod("getHandle", p.getClass(), p);
Object playerConnection = ReflectionUtil.getValue("playerConnection", entityPlayer);
ReflectionUtil.invokeMethod("sendPacket", playerConnection.getClass(), playerConnection, packet);
} catch (Exception e) {
Bukkit.getLogger().log(Level.WARNING, "[ParticleEffect] Failed to send a particle packet to {0}!", p.getName());
}
}
}
private static void sendPacket(Collection<Player> players, Object packet) {
for (Player p : players) {
sendPacket(p, packet);
}
}
/**
* Displays a particle effect which is only visible for specific players
*/
public void display(Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount, Player... players) {
sendPacket(Arrays.asList(players), createPacket(loc, offsetX, offsetY, offsetZ, speed, amount));
}
/**
* Displays a particle effect which is visible for all players whitin the
* maximum range of 20 blocks in the world of @param loc
*/
public void display(Location loc, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
display(loc, MAX_RANGE, offsetX, offsetY, offsetZ, speed, amount);
}
/**
* Displays a particle effect which is visible for all players whitin a
* certain range in the the world of @param loc
*/
public void display(Location loc, double range, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
if (range > MAX_RANGE) {
throw new IllegalArgumentException("Range has to be lower/equal the maximum of 20");
}
sendPacket(getPlayersInRange(loc, range), createPacket(loc, offsetX, offsetY, offsetZ, speed, amount));
}
/**
* Displays an icon crack (item break) effect which is only visible for
* specific players
*/
public static void displayIconCrack(Location loc, int id, float offsetX, float offsetY, float offsetZ, float speed, int amount, Player... players) {
sendPacket(Arrays.asList(players), createIconCrackPacket(id, loc, offsetX, offsetY, offsetZ, speed, amount));
}
/**
* Displays an icon crack (item break) effect which is visible for all
* players whitin the maximum range of 20 blocks in the world of @param loc
*/
public static void displayIconCrack(Location loc, int id, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
displayIconCrack(loc, MAX_RANGE, id, offsetX, offsetY, offsetZ, speed, amount);
}
/**
* Displays an icon crack (item break) effect which is visible for all
* players whitin a certain range in the the world of @param loc
*/
public static void displayIconCrack(Location loc, double range, int id, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
if (range > MAX_RANGE) {
throw new IllegalArgumentException("Range has to be lower/equal the maximum of 20");
}
sendPacket(getPlayersInRange(loc, range), createIconCrackPacket(id, loc, offsetX, offsetY, offsetZ, speed, amount));
}
/**
* Displays a block crack (block break) effect which is only visible for
* specific players
*/
public static void displayBlockCrack(Location loc, int id, byte data, float offsetX, float offsetY, float offsetZ, int amount, Player... players) {
sendPacket(Arrays.asList(players), createBlockCrackPacket(id, data, loc, offsetX, offsetY, offsetZ, amount));
}
/**
* Displays a block crack (block break) effect which is visible for all
* players whitin the maximum range of 20 blocks in the world of @param loc
*/
public static void displayBlockCrack(Location loc, int id, byte data, float offsetX, float offsetY, float offsetZ, int amount) {
displayBlockCrack(loc, MAX_RANGE, id, data, offsetX, offsetY, offsetZ, amount);
}
/**
* Displays a block crack (block break) effect which is visible for all
* players whitin a certain range in the the world of @param loc
*/
public static void displayBlockCrack(Location loc, double range, int id, byte data, float offsetX, float offsetY, float offsetZ, int amount) {
if (range > MAX_RANGE) {
throw new IllegalArgumentException("Range has to be lower/equal the maximum of 20");
}
sendPacket(getPlayersInRange(loc, range), createBlockCrackPacket(id, data, loc, offsetX, offsetY, offsetZ, amount));
}
/**
* Displays a block dust effect which is only visible for specific players
*/
public static void displayBlockDust(Location loc, int id, byte data, float offsetX, float offsetY, float offsetZ, float speed, int amount, Player... players) {
sendPacket(Arrays.asList(players), createBlockDustPacket(id, data, loc, offsetX, offsetY, offsetZ, speed, amount));
}
/**
* Displays a block dust effect which is visible for all players whitin the
* maximum range of 20 blocks in the world of @param loc
*/
public static void displayBlockDust(Location loc, int id, byte data, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
displayBlockDust(loc, MAX_RANGE, id, data, offsetX, offsetY, offsetZ, speed, amount);
}
/**
* Displays a block dust effect which is visible for all players whitin a
* certain range in the the world of @param loc
*/
public static void displayBlockDust(Location loc, double range, int id, byte data, float offsetX, float offsetY, float offsetZ, float speed, int amount) {
if (range > MAX_RANGE) {
throw new IllegalArgumentException("Range has to be lower/equal the maximum of 20");
}
sendPacket(getPlayersInRange(loc, range), createBlockDustPacket(id, data, loc, offsetX, offsetY, offsetZ, speed, amount));
}
}

View File

@@ -1,170 +0,0 @@
package de.anura.core;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
import org.bukkit.Bukkit;
/**
* ReflectionUtil v1.1
*
* You are welcome to use it, modify it and redistribute it under the condition
* to not claim this class as your own
*
* @author DarkBlade12
*/
public abstract class ReflectionUtil {
private static final Map<Class<?>, Class<?>> CORRESPONDING_TYPES = new HashMap<>();
static {
CORRESPONDING_TYPES.put(Byte.class, byte.class);
CORRESPONDING_TYPES.put(Short.class, short.class);
CORRESPONDING_TYPES.put(Integer.class, int.class);
CORRESPONDING_TYPES.put(Long.class, long.class);
CORRESPONDING_TYPES.put(Character.class, char.class);
CORRESPONDING_TYPES.put(Float.class, float.class);
CORRESPONDING_TYPES.put(Double.class, double.class);
CORRESPONDING_TYPES.put(Boolean.class, boolean.class);
}
public enum DynamicPackage {
MINECRAFT_SERVER {
@Override
public String toString() {
return "net.minecraft.server." + Bukkit.getServer().getClass().getPackage().getName().substring(23, 30);
}
},
CRAFTBUKKIT {
@Override
public String toString() {
return Bukkit.getServer().getClass().getPackage().getName();
}
};
}
public static class FieldEntry {
String key;
Object value;
public FieldEntry(String key, Object value) {
this.key = key;
this.value = value;
}
public String getKey() {
return this.key;
}
public Object getValue() {
return this.value;
}
}
private static Class<?> getPrimitiveType(Class<?> clazz) {
return CORRESPONDING_TYPES.containsKey(clazz) ? CORRESPONDING_TYPES.get(clazz) : clazz;
}
private static Class<?>[] toPrimitiveTypeArray(Object[] objects) {
int a = objects != null ? objects.length : 0;
Class<?>[] types = new Class<?>[a];
for (int i = 0; i < a; i++) {
types[i] = getPrimitiveType(objects[i].getClass());
}
return types;
}
private static Class<?>[] toPrimitiveTypeArray(Class<?>[] classes) {
int a = classes != null ? classes.length : 0;
Class<?>[] types = new Class<?>[a];
for (int i = 0; i < a; i++) {
types[i] = getPrimitiveType(classes[i]);
}
return types;
}
private static boolean equalsTypeArray(Class<?>[] a, Class<?>[] o) {
if (a.length != o.length) {
return false;
}
for (int i = 0; i < a.length; i++) {
if (!a[i].equals(o[i]) && !a[i].isAssignableFrom(o[i])) {
return false;
}
}
return true;
}
public static Class<?> getClass(String name, DynamicPackage pack, String subPackage) throws Exception {
return Class.forName(pack + (subPackage != null && subPackage.length() > 0 ? "." + subPackage : "") + "." + name);
}
public static Class<?> getClass(String name, DynamicPackage pack) throws Exception {
return getClass(name, pack, null);
}
public static Constructor<?> getConstructor(Class<?> clazz, Class<?>... paramTypes) {
Class<?>[] t = toPrimitiveTypeArray(paramTypes);
for (Constructor<?> c : clazz.getConstructors()) {
Class<?>[] types = toPrimitiveTypeArray(c.getParameterTypes());
if (equalsTypeArray(types, t)) {
return c;
}
}
return null;
}
public static Object newInstance(Class<?> clazz, Object... args) throws Exception {
return getConstructor(clazz, toPrimitiveTypeArray(args)).newInstance(args);
}
public static Object newInstance(String name, DynamicPackage pack, String subPackage, Object... args) throws Exception {
return newInstance(getClass(name, pack, subPackage), args);
}
public static Object newInstance(String name, DynamicPackage pack, Object... args) throws Exception {
return newInstance(getClass(name, pack, null), args);
}
public static Method getMethod(String name, Class<?> clazz, Class<?>... paramTypes) {
Class<?>[] t = toPrimitiveTypeArray(paramTypes);
for (Method m : clazz.getMethods()) {
Class<?>[] types = toPrimitiveTypeArray(m.getParameterTypes());
if (m.getName().equals(name) && equalsTypeArray(types, t)) {
return m;
}
}
return null;
}
public static Object invokeMethod(String name, Class<?> clazz, Object obj, Object... args) throws Exception {
return getMethod(name, clazz, toPrimitiveTypeArray(args)).invoke(obj, args);
}
public static Field getField(String name, Class<?> clazz) throws Exception {
return clazz.getDeclaredField(name);
}
public static Object getValue(String name, Object obj) throws Exception {
Field f = getField(name, obj.getClass());
f.setAccessible(true);
return f.get(obj);
}
public static void setValue(Object obj, FieldEntry entry) throws Exception {
Field f = getField(entry.getKey(), obj.getClass());
f.setAccessible(true);
f.set(obj, entry.getValue());
}
public static void setValues(Object obj, FieldEntry... entrys) throws Exception {
for (FieldEntry f : entrys) {
setValue(obj, f);
}
}
}

View File

@@ -2,8 +2,8 @@ package de.anura.core.events;
import de.anura.core.API.Errors;
import de.anura.core.AnuraCore;
import de.anura.core.ParticleEffect;
import java.sql.ResultSet;
import org.bukkit.Effect;
import org.bukkit.Material;
import org.bukkit.Sound;
import org.bukkit.block.Block;
@@ -46,7 +46,7 @@ public class PlayerMove implements Listener {
rs.last();
if (rs.getRow() > 0) {
p.setVelocity(new Vector(0, rs.getDouble("height"), 0));
ParticleEffect.FIREWORKS_SPARK.display(p.getLocation(), (float) 0.1, (float) 0.1, (float) 0.1, (float) 0.3, 10);
p.getWorld().spigot().playEffect(p.getLocation(), Effect.FIREWORKS_SPARK, 0, 0, (float) 0.1, (float) 0.1, (float) 0.1, (float) 0.3, 10, 1);
}
p.setWalkSpeed(0.2F);
@@ -61,7 +61,7 @@ public class PlayerMove implements Listener {
if (rs.getRow() > 0) {
p.setVelocity(p.getLocation().getDirection().multiply(new Vector(rs.getDouble("height"), 1, rs.getDouble("height"))));
p.setVelocity(p.getVelocity().setY(1.3));
ParticleEffect.LAVA.display(p.getLocation(), (float) 0.1, (float) 0.1, (float) 0.1, (float) 0.3, 10);
p.getWorld().spigot().playEffect(p.getLocation(), Effect.LAVA_POP, 0, 0, (float) 0.1, (float) 0.1, (float) 0.1, (float) 0.3, 10, 1);
p.playSound(p.getLocation(), Sound.EXPLODE, 1, 1);
}
p.setWalkSpeed(0.2F);