added End Crystal and its properties
This commit is contained in:
parent
f519020c5b
commit
f3c0df41dc
8 changed files with 201 additions and 5 deletions
46
api/src/main/java/lol/pyr/znpcsplus/util/Vector3i.java
Normal file
46
api/src/main/java/lol/pyr/znpcsplus/util/Vector3i.java
Normal file
|
@ -0,0 +1,46 @@
|
|||
package lol.pyr.znpcsplus.util;
|
||||
|
||||
public class Vector3i {
|
||||
private final int x;
|
||||
private final int y;
|
||||
private final int z;
|
||||
|
||||
public Vector3i(int x, int y, int z) {
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.z = z;
|
||||
}
|
||||
|
||||
public int getX() {
|
||||
return this.x;
|
||||
}
|
||||
|
||||
public int getY() {
|
||||
return this.y;
|
||||
}
|
||||
|
||||
public int getZ() {
|
||||
return this.z;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return this.x + "," + this.y + "," + this.z;
|
||||
}
|
||||
|
||||
public String toPrettyString() {
|
||||
return "(" + this.x + ", " + this.y + ", " + this.z + ")";
|
||||
}
|
||||
|
||||
public static Vector3i fromString(String s) {
|
||||
String[] split = s.split(",");
|
||||
if (split.length < 3) {
|
||||
return null;
|
||||
} else {
|
||||
try {
|
||||
return new Vector3i(Integer.parseInt(split[0]), Integer.parseInt(split[1]), Integer.parseInt(split[2]));
|
||||
} catch (NumberFormatException var3) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -251,6 +251,7 @@ public class ZNpcsPlus extends JavaPlugin {
|
|||
manager.registerParser(Color.class, new ColorParser(incorrectUsageMessage));
|
||||
manager.registerParser(Vector3f.class, new Vector3fParser(incorrectUsageMessage));
|
||||
manager.registerParser(String.class, new StringParser(incorrectUsageMessage));
|
||||
manager.registerParser(Vector3i.class, new Vector3iParser(incorrectUsageMessage));
|
||||
|
||||
// TODO: Need to find a better way to do this
|
||||
registerEnumParser(manager, NpcPose.class, incorrectUsageMessage);
|
||||
|
|
|
@ -19,6 +19,9 @@ import net.kyori.adventure.text.Component;
|
|||
import net.kyori.adventure.text.format.NamedTextColor;
|
||||
import org.bukkit.Color;
|
||||
import com.github.retrooper.packetevents.protocol.item.ItemStack;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
|
@ -117,9 +120,20 @@ public class PropertySetCommand implements CommandHandler {
|
|||
value = context.parse(type);
|
||||
valueName = value == null ? "NONE" : ((NpcEntryImpl) value).getId();
|
||||
}
|
||||
else {
|
||||
else if (type == Vector3i.class) {
|
||||
value = context.parse(type);
|
||||
valueName = String.valueOf(value);
|
||||
valueName = value == null ? "NONE" : ((Vector3i) value).toPrettyString();
|
||||
}
|
||||
else {
|
||||
try {
|
||||
value = context.parse(type);
|
||||
valueName = String.valueOf(value);
|
||||
} catch (NullPointerException e) {
|
||||
context.send(Component.text("An error occurred while trying to parse the value. Please report this to the plugin author.",
|
||||
NamedTextColor.RED));
|
||||
e.printStackTrace();
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
npc.UNSAFE_setProperty(property, value);
|
||||
|
@ -144,6 +158,17 @@ public class PropertySetCommand implements CommandHandler {
|
|||
context.suggestEnum(Arrays.stream(SpellType.values()).filter(spellType -> spellType.ordinal() <= 3).toArray(SpellType[]::new)) :
|
||||
context.suggestEnum(SpellType.values());
|
||||
|
||||
if (type == Vector3i.class) {
|
||||
if (context.getSender() instanceof Player) {
|
||||
Player player = (Player) context.getSender();
|
||||
Block targetBlock = player.getTargetBlock(Collections.singleton(Material.AIR), 5);
|
||||
if (targetBlock.getType().equals(Material.AIR)) return Collections.emptyList();
|
||||
return context.suggestLiteral(
|
||||
targetBlock.getX() + "",
|
||||
targetBlock.getX() + " " + targetBlock.getY(),
|
||||
targetBlock.getX() + " " + targetBlock.getY() + " " + targetBlock.getZ());
|
||||
}
|
||||
}
|
||||
// Suggest enum values directly
|
||||
if (type.isEnum()) {
|
||||
return context.suggestEnum((Enum<?>[]) type.getEnumConstants());
|
||||
|
@ -154,6 +179,25 @@ public class PropertySetCommand implements CommandHandler {
|
|||
// TODO: suggest block with nbt like minecraft setblock command
|
||||
return context.suggestionParse(2, String.class).equals("block") ? context.suggestStream(StateTypes.values().stream().map(StateType::getName)) : Collections.emptyList();
|
||||
}
|
||||
if (type == Vector3i.class) {
|
||||
if (context.getSender() instanceof Player) {
|
||||
Player player = (Player) context.getSender();
|
||||
Block targetBlock = player.getTargetBlock(Collections.singleton(Material.AIR), 5);
|
||||
if (targetBlock.getType().equals(Material.AIR)) return Collections.emptyList();
|
||||
return context.suggestLiteral(
|
||||
targetBlock.getY() + "",
|
||||
targetBlock.getY() + " " + targetBlock.getZ());
|
||||
}
|
||||
}
|
||||
} else if (context.argSize() == 5) {
|
||||
if (type == Vector3i.class) {
|
||||
if (context.getSender() instanceof Player) {
|
||||
Player player = (Player) context.getSender();
|
||||
Block targetBlock = player.getTargetBlock(Collections.singleton(Material.AIR), 5);
|
||||
if (targetBlock.getType().equals(Material.AIR)) return Collections.emptyList();
|
||||
return context.suggestLiteral(targetBlock.getZ() + "");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return Collections.emptyList();
|
||||
|
|
|
@ -56,6 +56,7 @@ public class EntityPropertyRegistryImpl implements EntityPropertyRegistry {
|
|||
registerSerializer(new Vector3fPropertySerializer());
|
||||
registerSerializer(new BlockStatePropertySerializer());
|
||||
registerSerializer(new LookTypeSerializer());
|
||||
registerSerializer(new GenericSerializer<>(Vector3i::toString, Vector3i::fromString, Vector3i.class));
|
||||
|
||||
registerEnumSerializer(NpcPose.class);
|
||||
registerEnumSerializer(DyeColor.class);
|
||||
|
@ -251,6 +252,17 @@ public class EntityPropertyRegistryImpl implements EntityPropertyRegistry {
|
|||
register(new BitsetProperty("is_rearing", horseIndex, horseEating << 1, false, legacyBooleans));
|
||||
register(new BitsetProperty("has_mouth_open", horseIndex, horseEating << 2, false, legacyBooleans));
|
||||
|
||||
// End Crystal
|
||||
if (ver.isNewerThanOrEquals(ServerVersion.V_1_9)) {
|
||||
int endCrystalIndex;
|
||||
if (ver.isNewerThanOrEquals(ServerVersion.V_1_17)) endCrystalIndex = 8;
|
||||
else if (ver.isNewerThanOrEquals(ServerVersion.V_1_15)) endCrystalIndex = 7;
|
||||
else if (ver.isNewerThanOrEquals(ServerVersion.V_1_10)) endCrystalIndex = 6;
|
||||
else endCrystalIndex = 5;
|
||||
register(new OptionalBlockPosProperty("beam_target", null, endCrystalIndex++));
|
||||
register(new BooleanProperty("show_base", endCrystalIndex, true, false));
|
||||
}
|
||||
|
||||
// Horse
|
||||
if (ver.isNewerThanOrEquals(ServerVersion.V_1_8) && ver.isOlderThan(ServerVersion.V_1_9)) {
|
||||
register(new EncodedByteProperty<>("horse_type", HorseType.HORSE, 19, obj -> (byte) obj.ordinal()));
|
||||
|
@ -367,7 +379,7 @@ public class EntityPropertyRegistryImpl implements EntityPropertyRegistry {
|
|||
else if (ver.isNewerThanOrEquals(ServerVersion.V_1_9)) witherIndex = 11;
|
||||
else witherIndex = 17;
|
||||
witherIndex += 3; // skip the first 3 indexes, will be used for the other properties later
|
||||
register(new IntegerProperty("invulnerable_time", witherIndex++, 0, false));
|
||||
register(new IntegerProperty("invulnerable_time", witherIndex, 0, false));
|
||||
|
||||
if (!ver.isNewerThanOrEquals(ServerVersion.V_1_9)) return;
|
||||
// Shulker
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
package lol.pyr.znpcsplus.entity.properties;
|
||||
|
||||
import com.github.retrooper.packetevents.protocol.entity.data.EntityData;
|
||||
import com.github.retrooper.packetevents.protocol.entity.data.EntityDataTypes;
|
||||
import lol.pyr.znpcsplus.entity.EntityPropertyImpl;
|
||||
import lol.pyr.znpcsplus.entity.PacketEntity;
|
||||
import lol.pyr.znpcsplus.util.Vector3i;
|
||||
import org.bukkit.entity.Player;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
public class OptionalBlockPosProperty extends EntityPropertyImpl<Vector3i> {
|
||||
private final int index;
|
||||
|
||||
public OptionalBlockPosProperty(String name, Vector3i defaultValue, int index) {
|
||||
super(name, defaultValue, Vector3i.class);
|
||||
this.index = index;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void apply(Player player, PacketEntity entity, boolean isSpawned, Map<Integer, EntityData> properties) {
|
||||
Vector3i value = entity.getProperty(this);
|
||||
if (value == null) properties.put(index, new EntityData(index, EntityDataTypes.OPTIONAL_BLOCK_POSITION, Optional.empty()));
|
||||
else properties.put(index, new EntityData(index, EntityDataTypes.OPTIONAL_BLOCK_POSITION,
|
||||
Optional.of(new com.github.retrooper.packetevents.util.Vector3i(value.getX(), value.getY(), value.getZ()))));
|
||||
}
|
||||
}
|
|
@ -0,0 +1,32 @@
|
|||
package lol.pyr.znpcsplus.entity.serializers;
|
||||
|
||||
import lol.pyr.znpcsplus.entity.PropertySerializer;
|
||||
|
||||
import java.util.function.Function;
|
||||
|
||||
public class GenericSerializer<T> implements PropertySerializer<T> {
|
||||
private final Function<T, String> encoder;
|
||||
private final Function<String, T> decoder;
|
||||
private final Class<T> typeClass;
|
||||
|
||||
public GenericSerializer(Function<T, String> encoder, Function<String, T> decoder, Class<T> typeClass) {
|
||||
this.encoder = encoder;
|
||||
this.decoder = decoder;
|
||||
this.typeClass = typeClass;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String serialize(T property) {
|
||||
return encoder.apply(property);
|
||||
}
|
||||
|
||||
@Override
|
||||
public T deserialize(String property) {
|
||||
return decoder.apply(property);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<T> getTypeClass() {
|
||||
return typeClass;
|
||||
}
|
||||
}
|
|
@ -73,6 +73,10 @@ public class NpcTypeRegistryImpl implements NpcTypeRegistry {
|
|||
.setHologramOffset(-0.275)
|
||||
.addProperties("creeper_state", "creeper_charged"));
|
||||
|
||||
register(builder(p, "end_crystal", EntityTypes.END_CRYSTAL)
|
||||
.setHologramOffset(0.025)
|
||||
.addProperties("beam_target", "show_base"));
|
||||
|
||||
register(builder(p, "ender_dragon", EntityTypes.ENDER_DRAGON)
|
||||
.setHologramOffset(6.0245));
|
||||
|
||||
|
@ -206,8 +210,7 @@ public class NpcTypeRegistryImpl implements NpcTypeRegistry {
|
|||
.addEquipmentProperties());
|
||||
|
||||
register(builder(p, "evoker", EntityTypes.EVOKER)
|
||||
.setHologramOffset(-0.025)
|
||||
.addProperties("evoker_spell"));
|
||||
.setHologramOffset(-0.025));
|
||||
|
||||
register(builder(p, "llama", EntityTypes.LLAMA)
|
||||
.setHologramOffset(-0.105)
|
||||
|
|
|
@ -0,0 +1,30 @@
|
|||
package lol.pyr.znpcsplus.parsers;
|
||||
|
||||
import lol.pyr.director.adventure.command.CommandContext;
|
||||
import lol.pyr.director.adventure.parse.ParserType;
|
||||
import lol.pyr.director.common.command.CommandExecutionException;
|
||||
import lol.pyr.director.common.message.Message;
|
||||
import lol.pyr.znpcsplus.util.Vector3i;
|
||||
|
||||
import java.util.Deque;
|
||||
|
||||
public class Vector3iParser extends ParserType<Vector3i> {
|
||||
public Vector3iParser(Message<CommandContext> message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Vector3i parse(Deque<String> deque) throws CommandExecutionException {
|
||||
if (deque.size() == 0) {
|
||||
return null;
|
||||
}
|
||||
try {
|
||||
return new Vector3i(
|
||||
Integer.parseInt(deque.pop()),
|
||||
Integer.parseInt(deque.pop()),
|
||||
Integer.parseInt(deque.pop()));
|
||||
} catch (NumberFormatException e) {
|
||||
throw new CommandExecutionException();
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue