Archiviert
13
0

Make Sound handling more robust

Fixes aadnk#119
Dieser Commit ist enthalten in:
Dan Mulloy 2016-12-22 11:42:52 -05:00
Ursprung 27047f83a5
Commit 540a5e53c4
3 geänderte Dateien mit 47 neuen und 11 gelöschten Zeilen

Datei anzeigen

@ -1847,6 +1847,10 @@ public class MinecraftReflection {
return getMinecraftClass("NonNullList"); return getMinecraftClass("NonNullList");
} }
public static Class<?> getCraftSoundClass() {
return getCraftBukkitClass("CraftSound");
}
// ---- ItemStack conversions // ---- ItemStack conversions
private static Method asNMSCopy = null; private static Method asNMSCopy = null;

Datei anzeigen

@ -29,6 +29,7 @@ import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Map.Entry; import java.util.Map.Entry;
import java.util.Set; import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import org.bukkit.Material; import org.bukkit.Material;
import org.bukkit.Sound; import org.bukkit.Sound;
@ -964,10 +965,21 @@ public class BukkitConverters {
}; };
} }
private static MethodAccessor soundGetter = null; private static MethodAccessor getSound = null;
private static MethodAccessor getSoundEffect = null;
private static FieldAccessor soundKey = null; private static FieldAccessor soundKey = null;
private static Map<String, Sound> soundIndex = null;
public static EquivalentConverter<Sound> getSoundConverter() { public static EquivalentConverter<Sound> getSoundConverter() {
if (getSound == null || getSoundEffect == null) {
Class<?> craftSound = MinecraftReflection.getCraftSoundClass();
FuzzyReflection fuzzy = FuzzyReflection.fromClass(craftSound, true);
getSound = Accessors.getMethodAccessor(fuzzy.getMethodByParameters("getSound", String.class, new Class<?>[] { Sound.class }));
getSoundEffect = Accessors.getMethodAccessor(fuzzy.getMethodByParameters("getSoundEffect",
MinecraftReflection.getSoundEffectClass(), new Class<?>[] { String.class }));
}
return new IgnoreNullConverter<Sound>() { return new IgnoreNullConverter<Sound>() {
@Override @Override
@ -977,26 +989,42 @@ public class BukkitConverters {
@Override @Override
protected Object getGenericValue(Class<?> genericType, Sound specific) { protected Object getGenericValue(Class<?> genericType, Sound specific) {
if (soundGetter == null) { // Getting the SoundEffect is easy, Bukkit provides us the methods
Class<?> soundEffects = MinecraftReflection.getMinecraftClass("SoundEffects"); String key = (String) getSound.invoke(null, specific);
FuzzyReflection fuzzy = FuzzyReflection.fromClass(soundEffects, true); return getSoundEffect.invoke(null, key);
soundGetter = Accessors.getMethodAccessor(fuzzy.getMethodByParameters("getSound", MinecraftReflection.getSoundEffectClass(), new Class<?>[] { String.class }));
}
MinecraftKey key = MinecraftKey.fromEnum(specific);
return soundGetter.invoke(null, key.getFullKey());
} }
@Override @Override
protected Sound getSpecificValue(Object generic) { protected Sound getSpecificValue(Object generic) {
// Getting the Sound is a bit more complicated...
if (soundKey == null) { if (soundKey == null) {
Class<?> soundEffect = generic.getClass(); Class<?> soundEffect = generic.getClass();
FuzzyReflection fuzzy = FuzzyReflection.fromClass(soundEffect, true); FuzzyReflection fuzzy = FuzzyReflection.fromClass(soundEffect, true);
soundKey = Accessors.getFieldAccessor(fuzzy.getFieldByType("key", MinecraftReflection.getMinecraftKeyClass())); soundKey = Accessors.getFieldAccessor(fuzzy.getFieldByType("key", MinecraftReflection.getMinecraftKeyClass()));
} }
MinecraftKey key = MinecraftKey.fromHandle(soundKey.get(generic)); MinecraftKey minecraftKey = MinecraftKey.fromHandle(soundKey.get(generic));
return Sound.valueOf(key.getEnumFormat()); String key = minecraftKey.getKey();
// Use our index if it already exists
if (soundIndex != null) {
return soundIndex.get(key);
}
// If it doesn't, try to guess the enum name
try {
return Sound.valueOf(minecraftKey.getEnumFormat());
} catch (IllegalArgumentException ignored) {
}
// Worst case we index all the sounds and use it later
soundIndex = new ConcurrentHashMap<>();
for (Sound sound : Sound.values()) {
String index = (String) getSound.invoke(null, sound);
soundIndex.put(index, sound);
}
return soundIndex.get(key);
} }
}; };
} }

Datei anzeigen

@ -69,7 +69,9 @@ public class MinecraftKey {
* is lower case, with underscores replaced by periods. * is lower case, with underscores replaced by periods.
* @param value The value * @param value The value
* @return The resulting key * @return The resulting key
* @deprecated This isn't accurate in all cases
*/ */
@Deprecated
public static MinecraftKey fromEnum(Enum<?> value) { public static MinecraftKey fromEnum(Enum<?> value) {
return new MinecraftKey(value.name().toLowerCase(Locale.ENGLISH).replace("_", ".")); return new MinecraftKey(value.name().toLowerCase(Locale.ENGLISH).replace("_", "."));
} }
@ -103,7 +105,9 @@ public class MinecraftKey {
* Returns this key back into Enum format, upper case with periods replaced * Returns this key back into Enum format, upper case with periods replaced
* by underscores. * by underscores.
* @return The enum format * @return The enum format
* @deprecated This isn't accurate in all cases
*/ */
@Deprecated
public String getEnumFormat() { public String getEnumFormat() {
return key.toUpperCase(Locale.ENGLISH).replace(".", "_"); return key.toUpperCase(Locale.ENGLISH).replace(".", "_");
} }