Added a couple of useful methods to the wrappers.
Dieser Commit ist enthalten in:
Ursprung
ad69b0caac
Commit
fec2734fe2
@ -19,8 +19,10 @@ import com.comphenix.protocol.reflect.compiler.StructureCompiler;
|
||||
import com.comphenix.protocol.reflect.instances.CollectionGenerator;
|
||||
import com.comphenix.protocol.reflect.instances.DefaultInstances;
|
||||
import com.comphenix.protocol.reflect.instances.PrimitiveGenerator;
|
||||
import com.comphenix.protocol.wrappers.BukkitConverters;
|
||||
import com.comphenix.protocol.wrappers.ChunkPosition;
|
||||
import com.comphenix.protocol.wrappers.WrappedDataWatcher;
|
||||
import com.comphenix.protocol.wrappers.WrappedWatchableObject;
|
||||
|
||||
/**
|
||||
* Used to fix ClassLoader leaks that may lead to filling up the permanent generation.
|
||||
@ -48,7 +50,8 @@ class CleanupStaticMembers {
|
||||
PrimitiveGenerator.class, FuzzyReflection.class, MethodUtils.class,
|
||||
BackgroundCompiler.class, StructureCompiler.class,
|
||||
ObjectCloner.class, Packets.Server.class, Packets.Client.class,
|
||||
ChunkPosition.class, WrappedDataWatcher.class
|
||||
ChunkPosition.class, WrappedDataWatcher.class, WrappedWatchableObject.class,
|
||||
BukkitConverters.class
|
||||
};
|
||||
|
||||
String[] internalClasses = {
|
||||
@ -65,8 +68,7 @@ class CleanupStaticMembers {
|
||||
"com.comphenix.protocol.injector.ReadPacketModifier",
|
||||
"com.comphenix.protocol.injector.StructureCache",
|
||||
"com.comphenix.protocol.reflect.compiler.BoxingHelper",
|
||||
"com.comphenix.protocol.reflect.compiler.MethodDescriptor",
|
||||
"com.comphenix.protocol.wrappers.WrappedWatchableObject"
|
||||
"com.comphenix.protocol.reflect.compiler.MethodDescriptor"
|
||||
};
|
||||
|
||||
resetClasses(publicClasses);
|
||||
|
@ -3,6 +3,7 @@ package com.comphenix.protocol.wrappers;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
@ -10,6 +11,7 @@ import java.util.Set;
|
||||
import java.util.concurrent.locks.ReadWriteLock;
|
||||
import java.util.concurrent.locks.ReentrantReadWriteLock;
|
||||
|
||||
import org.bukkit.entity.Entity;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
|
||||
import com.comphenix.protocol.reflect.FieldAccessException;
|
||||
@ -42,6 +44,9 @@ public class WrappedDataWatcher {
|
||||
private static Method updateKeyValueMethod;
|
||||
private static Method getKeyValueMethod;
|
||||
|
||||
// Entity methods
|
||||
private static Field entityDataField;
|
||||
|
||||
/**
|
||||
* Whether or not this class has already been initialized.
|
||||
*/
|
||||
@ -80,6 +85,20 @@ public class WrappedDataWatcher {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new data watcher from a list of watchable objects.
|
||||
* @param watchableObjects - list of watchable objects that will be copied.
|
||||
* @throws FieldAccessException Unable to read watchable objects.
|
||||
*/
|
||||
public WrappedDataWatcher(List<WrappedWatchableObject> watchableObjects) throws FieldAccessException {
|
||||
this();
|
||||
|
||||
// Fill the underlying map
|
||||
for (WrappedWatchableObject watched : watchableObjects) {
|
||||
setObject(watched.getIndex(), watched.getValue());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves the underlying data watcher.
|
||||
* @return The underlying data watcher.
|
||||
@ -223,6 +242,32 @@ public class WrappedDataWatcher {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve every watchable object in this watcher.
|
||||
* @return Every watchable object.
|
||||
* @throws FieldAccessException If reflection failed.
|
||||
*/
|
||||
public List<WrappedWatchableObject> getWatchableObjects() throws FieldAccessException {
|
||||
try {
|
||||
getReadWriteLock().readLock().lock();
|
||||
|
||||
List<WrappedWatchableObject> result = new ArrayList<WrappedWatchableObject>();
|
||||
|
||||
// Add each watchable object to the list
|
||||
for (Object watchable : getWatchableObjectMap().values()) {
|
||||
if (watchable != null) {
|
||||
result.add(new WrappedWatchableObject((WatchableObject) watchable));
|
||||
} else {
|
||||
result.add(null);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
|
||||
} finally {
|
||||
getReadWriteLock().readLock().unlock();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve a copy of every index associated with a watched object.
|
||||
* @return Every watched object index.
|
||||
@ -361,6 +406,29 @@ public class WrappedDataWatcher {
|
||||
return watchableObjects;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve the data watcher associated with an entity.
|
||||
* @param entity - the entity to read from.
|
||||
* @return Associated data watcher.
|
||||
* @throws FieldAccessException Reflection failed.
|
||||
*/
|
||||
public static WrappedDataWatcher getEntityWatcher(Entity entity) throws FieldAccessException {
|
||||
if (entityDataField == null)
|
||||
entityDataField = FuzzyReflection.fromClass(Entity.class, true).getFieldByType("datawatcher", DataWatcher.class);
|
||||
|
||||
try {
|
||||
Object nsmWatcher = FieldUtils.readField(entityDataField, entity, true);
|
||||
|
||||
if (nsmWatcher != null)
|
||||
return new WrappedDataWatcher((DataWatcher) nsmWatcher);
|
||||
else
|
||||
return null;
|
||||
|
||||
} catch (IllegalAccessException e) {
|
||||
throw new FieldAccessException("Cannot access DataWatcher field.", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Invoked when a data watcher is first used.
|
||||
*/
|
||||
|
@ -53,7 +53,7 @@ public class WrappedWatchableObject {
|
||||
* @return Super type.
|
||||
* @throws FieldAccessException Unable to read values.
|
||||
*/
|
||||
public Class<?> getValueType() throws FieldAccessException {
|
||||
public Class<?> getType() throws FieldAccessException {
|
||||
if (typeClass == null) {
|
||||
typeClass = WrappedDataWatcher.getTypeClass(getTypeID());
|
||||
|
||||
@ -120,8 +120,8 @@ public class WrappedWatchableObject {
|
||||
// Verify a few quick things
|
||||
if (newValue == null)
|
||||
throw new IllegalArgumentException("Cannot watch a NULL value.");
|
||||
if (!getValueType().isAssignableFrom(newValue.getClass()))
|
||||
throw new IllegalArgumentException("Object " + newValue + " must be of type " + getValueType().getName());
|
||||
if (!getType().isAssignableFrom(newValue.getClass()))
|
||||
throw new IllegalArgumentException("Object " + newValue + " must be of type " + getType().getName());
|
||||
|
||||
// See if we should update the client to
|
||||
if (updateClient)
|
||||
|
In neuem Issue referenzieren
Einen Benutzer sperren