@CommandDescription (aliases = "data", usage = "<key> <value>", desc = "Change Entity data value")
@Permissible ("vanilla.command.data")
public void data(CommandSource source, CommandArguments args) throws CommandException {
String key = args.popString("key");
String value = args.popRemainingStrings("value");
Player player = args.popPlayerOrMe("player", source);
args.assertCompletelyParsed();
// Figure out what entity to affect
// Note: this could be put in a method in the Vanilla human component instead
// This version is rather inaccurate...
double lastDistanceToEntity = 5.0;
Point point = player.getPhysics().getPosition();
Human human = player.get(Human.class);
Vector3f direction;
if (human == null) {
direction = player.getPhysics().getRotation().getDirection();
} else {
direction = human.getHead().getLookingAt();
}
Entity nearest = null;
for (double d = 0.0; d <= 50.0; d += 0.25) {
Point pos = point.add(direction.mul(d));
Entity near = point.getWorld().getNearestEntity(pos, player, (int) lastDistanceToEntity);
if (near == null) {
continue;
}
double distance = pos.distance(near.getPhysics().getPosition());
if (distance < lastDistanceToEntity) {
lastDistanceToEntity = distance;
nearest = near;
if (distance < 0.5) {
break;
}
}
}
if (nearest == null) {
player.sendMessage("Could not find a near Entity you are looking at.");
return;
}
// Send entity information
Descriptor desc = nearest.get(Descriptor.class);
if (desc == null) {
player.sendMessage("Selected Entity: Unknown");
} else {
player.sendMessage("Selected Entity: " + desc.getDescription());
}
Object currentValue = nearest.getData().get(key);
if (value == null || value.isEmpty()) {
if (nearest.getData().containsKey(key)) {
player.sendMessage(key + " = " + currentValue);
} else {
player.sendMessage("No value is mapped to " + key + " for this Entity");
}
return;
}
// Figure out what type the key is using VanillaData
Class<?> valueType = null;
for (Field field : VanillaData.class.getDeclaredFields()) {
if (!Modifier.isStatic(field.getModifiers())) {
continue;
}
try {
Object fieldValue = field.get(null);
if (fieldValue instanceof DefaultedKey) {
DefaultedKey<?> defKey = (DefaultedKey<?>) fieldValue;
if (!defKey.getKeyString().equals(key)) {
continue;
}
Object defValue = defKey.getDefaultValue();
if (defValue != null) {
// We found our type!
valueType = defValue.getClass();
break;
}
}
} catch (Throwable t) {
// Ignore any field access issues
}
}
// Try using the current value in the datamap
if (valueType == null) {
if (currentValue == null) {
player.sendMessage("Could not figure out the type of value stored by " + key);
return;
} else {
valueType = currentValue.getClass();
}
}
// Set the value in the datamap if possible
try {
Serializable newValue;
if (Double.class.isAssignableFrom(valueType)) {
newValue = Double.parseDouble(value);
} else if (Float.class.isAssignableFrom(valueType)) {
newValue = Float.parseFloat(value);
} else if (Long.class.isAssignableFrom(valueType)) {
newValue = Long.parseLong(value);
} else if (Integer.class.isAssignableFrom(valueType)) {
newValue = Integer.parseInt(value);
} else if (Short.class.isAssignableFrom(valueType)) {
newValue = Short.parseShort(value);
} else if (Byte.class.isAssignableFrom(valueType)) {
newValue = Byte.parseByte(value);
} else if (String.class.isAssignableFrom(valueType)) {
newValue = value;
} else {
player.sendMessage("No idea how to turn " + value + " into " + valueType.getSimpleName());
return;
}
nearest.getData().put(key, newValue);
player.sendMessage("Value of " + key + " set to " + newValue);
} catch (Throwable t) {
player.sendMessage("Error occurred while parsing value " + value);
player.sendMessage(t.getMessage());
}
}