mirror of
https://github.com/Sollace/Unicopia.git
synced 2024-11-24 05:47:59 +01:00
Implement networking, reimplement pega-reach
This commit is contained in:
parent
2536872aad
commit
5708f9c80f
36 changed files with 367 additions and 608 deletions
|
@ -1,23 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
import java.util.UUID;
|
|
||||||
|
|
||||||
import javax.annotation.Nullable;
|
|
||||||
|
|
||||||
import com.minelittlepony.jumpingcastle.api.payload.BinaryPayload;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Implementor for a Jumping Castle API bus.
|
|
||||||
*/
|
|
||||||
public interface Bus {
|
|
||||||
void sendToServer(String channel, long id, Message message, Target target);
|
|
||||||
|
|
||||||
void sendToClient(String channel, long id, Message message, UUID playerId);
|
|
||||||
|
|
||||||
void sendToClient(UUID playerId, BinaryPayload forwarded);
|
|
||||||
|
|
||||||
@Nullable
|
|
||||||
Object getMinecraftServer();
|
|
||||||
|
|
||||||
Server getServer();
|
|
||||||
}
|
|
|
@ -1,60 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
import java.util.UUID;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A channel for sending and recieving messages.
|
|
||||||
*/
|
|
||||||
public interface Channel {
|
|
||||||
/**
|
|
||||||
* Registers a handler for a specific message type transmitted over this channel.
|
|
||||||
*
|
|
||||||
* @param messageType The message type being recieved.
|
|
||||||
* @param handler A handler instance to handle the message.
|
|
||||||
*/
|
|
||||||
<T extends Message> Channel listenFor(Class<T> messageType, Message.Handler<T> handler);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Registers a handler for a specific message type transmitted over this channel.
|
|
||||||
*
|
|
||||||
* @param messageType The message type being recieved.
|
|
||||||
*/
|
|
||||||
<T extends Message & Message.Handler<T>> Channel listenFor(Class<T> messageType);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets the minecraft server
|
|
||||||
*/
|
|
||||||
<T> T getServer();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sends a message over this channel. By default targets all other clients listening on this channel.
|
|
||||||
*
|
|
||||||
* @param message The message to send.
|
|
||||||
*/
|
|
||||||
default Channel send(Message message) {
|
|
||||||
return send(message, Target.CLIENTS);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sends a message over this channel.
|
|
||||||
*
|
|
||||||
* @param message The message to send.
|
|
||||||
* @param target Recipients that must handle this message (clients, server, or both)
|
|
||||||
*/
|
|
||||||
Channel send(Message message, Target target);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sends a message back. Use this if you're a server.
|
|
||||||
*
|
|
||||||
* @param message The message to send.
|
|
||||||
* @param recipient Recipient that must handle this message
|
|
||||||
*/
|
|
||||||
Channel respond(Message message, UUID recipient);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sends a message back to all clients. Use this if you're a server.
|
|
||||||
*
|
|
||||||
* @param message The message to send.
|
|
||||||
*/
|
|
||||||
Channel broadcast(Message message);
|
|
||||||
}
|
|
|
@ -1,28 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Jumping Castle main interface.
|
|
||||||
* <p>
|
|
||||||
*{@code
|
|
||||||
* JumpingCastle.listen("My Channel").consume(MyMessage.class, (msg, channel) -> {
|
|
||||||
* ...
|
|
||||||
* });
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
public interface JumpingCastle {
|
|
||||||
/**
|
|
||||||
* Gets or creates a new channel indexed by the given identifier.
|
|
||||||
*
|
|
||||||
* @param channelName The channel name
|
|
||||||
*
|
|
||||||
* @return An instance of IChannel.
|
|
||||||
*/
|
|
||||||
static Channel subscribeTo(String channelName, Client clientHandler) {
|
|
||||||
return null;// TODO: JumpingFabric
|
|
||||||
}
|
|
||||||
|
|
||||||
@FunctionalInterface
|
|
||||||
public interface Client {
|
|
||||||
void connectionEstablished();
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,45 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
import com.minelittlepony.jumpingcastle.api.payload.Serializable;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A message for communicating over a channel.
|
|
||||||
* Fields marked with @Expose are automatically serialized to the output packet stream
|
|
||||||
* and will be made available on the far end of the pipe.
|
|
||||||
*
|
|
||||||
* Override the read and write methods to customise this behaviour.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
public interface Message extends Serializable<Message> {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets a unique identifier to represent a packet over channel communications.
|
|
||||||
*/
|
|
||||||
static long identifier(Class<? extends Message> cls) {
|
|
||||||
return cls.getCanonicalName().hashCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Gets a unique identifier to represent this packet over channel communications.
|
|
||||||
*/
|
|
||||||
default long identifier() {
|
|
||||||
return identifier(getClass());
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Handler interface for incoming messages.
|
|
||||||
*
|
|
||||||
* @param <T> The type of message to handle.
|
|
||||||
*/
|
|
||||||
@FunctionalInterface
|
|
||||||
public interface Handler<T extends Message> {
|
|
||||||
/**
|
|
||||||
* Called when a new message is received.
|
|
||||||
*
|
|
||||||
* @param message The message received.
|
|
||||||
*
|
|
||||||
* @param channel The channel used to deliver the message.
|
|
||||||
*/
|
|
||||||
void onPayload(T message, Channel channel);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,7 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
import java.util.UUID;
|
|
||||||
|
|
||||||
public interface Server {
|
|
||||||
void stopTrackingPlayer(UUID playerId);
|
|
||||||
}
|
|
|
@ -1,43 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Targeting method to control who receives a message when sent.
|
|
||||||
* Senders choose whether a message is received on other clients, just the server, or both.
|
|
||||||
*/
|
|
||||||
public enum Target {
|
|
||||||
/**
|
|
||||||
* Message is ignored by the server and forwarded to connected clients.
|
|
||||||
*/
|
|
||||||
CLIENTS(true, false),
|
|
||||||
/**
|
|
||||||
* Only the server should process this message. Clients ignore it.
|
|
||||||
*/
|
|
||||||
SERVER(false, true),
|
|
||||||
/**
|
|
||||||
* The server should process this message and forward it to all available clients.
|
|
||||||
*/
|
|
||||||
SERVER_AND_CLIENTS(true, true);
|
|
||||||
|
|
||||||
private final boolean clients;
|
|
||||||
|
|
||||||
private final boolean servers;
|
|
||||||
|
|
||||||
Target(boolean clients, boolean servers) {
|
|
||||||
this.clients = clients;
|
|
||||||
this.servers = servers;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* True if messages with this targeting must be processed by the client.
|
|
||||||
*/
|
|
||||||
public boolean isClients() {
|
|
||||||
return clients;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* True if messages with this targeting must be processed by the server.
|
|
||||||
*/
|
|
||||||
public boolean isServers() {
|
|
||||||
return servers;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,63 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api.payload;
|
|
||||||
|
|
||||||
import javax.annotation.Nullable;
|
|
||||||
|
|
||||||
import io.netty.buffer.ByteBuf;
|
|
||||||
import io.netty.buffer.Unpooled;
|
|
||||||
|
|
||||||
public interface BinaryPayload {
|
|
||||||
|
|
||||||
@Nullable
|
|
||||||
static BinaryPayload of(Object buffer) {
|
|
||||||
if (buffer instanceof ByteBuf) {
|
|
||||||
return ByteBufBinaryPayload.of((ByteBuf)buffer);
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
static BinaryPayload create() {
|
|
||||||
return of(Unpooled.buffer());
|
|
||||||
}
|
|
||||||
|
|
||||||
<T> T buff();
|
|
||||||
|
|
||||||
byte[] bytes();
|
|
||||||
|
|
||||||
byte[] readToEnd();
|
|
||||||
|
|
||||||
long readLong();
|
|
||||||
|
|
||||||
BinaryPayload writeLong(long l);
|
|
||||||
|
|
||||||
int readInt();
|
|
||||||
|
|
||||||
BinaryPayload writeInt(int b);
|
|
||||||
|
|
||||||
byte readByte();
|
|
||||||
|
|
||||||
BinaryPayload writeByte(byte b);
|
|
||||||
|
|
||||||
String readString();
|
|
||||||
|
|
||||||
BinaryPayload writeString(String s);
|
|
||||||
|
|
||||||
byte[] readBytes(int len);
|
|
||||||
|
|
||||||
BinaryPayload writeBytes(byte[] bytes);
|
|
||||||
|
|
||||||
BinaryPayload reverse();
|
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
default <T extends Serializable<? super T>> T readBinary(Class<T> type) {
|
|
||||||
try {
|
|
||||||
return (T)type.newInstance().read(this);
|
|
||||||
} catch (InstantiationException | IllegalAccessException e) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
default <T extends Serializable<T>> BinaryPayload writeBinary(T message) {
|
|
||||||
message.write(this);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,89 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api.payload;
|
|
||||||
|
|
||||||
import java.nio.charset.StandardCharsets;
|
|
||||||
|
|
||||||
import io.netty.buffer.ByteBuf;
|
|
||||||
|
|
||||||
interface ByteBufBinaryPayload extends BinaryPayload {
|
|
||||||
|
|
||||||
static BinaryPayload of(ByteBuf buff) {
|
|
||||||
return (ByteBufBinaryPayload)(() -> buff);
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
ByteBuf buff();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default String readString() {
|
|
||||||
return buff().readCharSequence(readInt(), StandardCharsets.UTF_8).toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default int readInt() {
|
|
||||||
return buff().readInt();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload writeInt(int b) {
|
|
||||||
buff().writeInt(b);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default byte readByte() {
|
|
||||||
return buff().readByte();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload writeByte(byte b) {
|
|
||||||
buff().writeByte(b);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
default byte[] bytes() {
|
|
||||||
return buff().array();
|
|
||||||
}
|
|
||||||
|
|
||||||
default byte[] readToEnd() {
|
|
||||||
byte[] bytes = new byte[buff().writerIndex() - buff().readerIndex()];
|
|
||||||
buff().readBytes(bytes);
|
|
||||||
return bytes;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default long readLong() {
|
|
||||||
return buff().readLong();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload writeLong(long l) {
|
|
||||||
buff().writeLong(l);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload reverse() {
|
|
||||||
buff().readerIndex(0);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default byte[] readBytes(int len) {
|
|
||||||
byte[] data = new byte[len];
|
|
||||||
buff().readBytes(data);
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload writeBytes(byte[] bytes) {
|
|
||||||
buff().writeBytes(bytes);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
default BinaryPayload writeString(String s) {
|
|
||||||
buff().writeInt(s.getBytes(StandardCharsets.UTF_8).length);
|
|
||||||
buff().writeCharSequence(s, StandardCharsets.UTF_8);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,19 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api.payload;
|
|
||||||
|
|
||||||
import com.google.gson.Gson;
|
|
||||||
import com.google.gson.GsonBuilder;
|
|
||||||
|
|
||||||
public class JsonSerializer {
|
|
||||||
private static final Gson READER_GSON = new GsonBuilder()
|
|
||||||
.excludeFieldsWithoutExposeAnnotation()
|
|
||||||
.create();
|
|
||||||
|
|
||||||
public static <T> T read(BinaryPayload payload, Class<T> type) {
|
|
||||||
return (T)READER_GSON.fromJson(payload.readString(), type);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static <T> void write(BinaryPayload payload, T object) {
|
|
||||||
payload.writeString(READER_GSON.toJson(object));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,19 +0,0 @@
|
||||||
package com.minelittlepony.jumpingcastle.api.payload;
|
|
||||||
|
|
||||||
public interface Serializable<T extends Serializable<T>> {
|
|
||||||
/**
|
|
||||||
* Reads the contents of this message from a networking payload.
|
|
||||||
*/
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
default T read(BinaryPayload payload) {
|
|
||||||
return (T)JsonSerializer.read(payload, getClass());
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Writes the contents of this message to a networking payload.
|
|
||||||
*/
|
|
||||||
default void write(BinaryPayload payload) {
|
|
||||||
JsonSerializer.write(payload, this);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -16,7 +16,7 @@ import net.minecraft.world.World;
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
public class CustomDrops {
|
public class CustomDrops {
|
||||||
// TODO: loot table
|
// XXX: loot table
|
||||||
public void addAuxiliaryDrops(World world, BlockState state, BlockPos pos, List<ItemStack> drops, int fortune) {
|
public void addAuxiliaryDrops(World world, BlockState state, BlockPos pos, List<ItemStack> drops, int fortune) {
|
||||||
Block block = state.getBlock();
|
Block block = state.getBlock();
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,7 @@ import net.minecraft.util.Identifier;
|
||||||
import net.minecraft.util.registry.Registry;
|
import net.minecraft.util.registry.Registry;
|
||||||
|
|
||||||
public final class TreeType {
|
public final class TreeType {
|
||||||
// TODO: move to datapack
|
// XXX: move to datapack
|
||||||
private static final Set<TreeType> REGISTRY = new HashSet<>();
|
private static final Set<TreeType> REGISTRY = new HashSet<>();
|
||||||
|
|
||||||
public static final TreeType NONE = new TreeType("none", new Weighted<Supplier<ItemStack>>());
|
public static final TreeType NONE = new TreeType("none", new Weighted<Supplier<ItemStack>>());
|
||||||
|
|
|
@ -8,8 +8,6 @@ import org.apache.logging.log4j.LogManager;
|
||||||
import org.apache.logging.log4j.Logger;
|
import org.apache.logging.log4j.Logger;
|
||||||
|
|
||||||
import com.minelittlepony.common.util.GamePaths;
|
import com.minelittlepony.common.util.GamePaths;
|
||||||
import com.minelittlepony.jumpingcastle.api.Channel;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.JumpingCastle;
|
|
||||||
import com.minelittlepony.unicopia.ability.Abilities;
|
import com.minelittlepony.unicopia.ability.Abilities;
|
||||||
import com.minelittlepony.unicopia.advancement.BOHDeathCriterion;
|
import com.minelittlepony.unicopia.advancement.BOHDeathCriterion;
|
||||||
import com.minelittlepony.unicopia.block.UBlocks;
|
import com.minelittlepony.unicopia.block.UBlocks;
|
||||||
|
@ -17,39 +15,28 @@ import com.minelittlepony.unicopia.command.Commands;
|
||||||
import com.minelittlepony.unicopia.container.UContainers;
|
import com.minelittlepony.unicopia.container.UContainers;
|
||||||
import com.minelittlepony.unicopia.enchanting.Pages;
|
import com.minelittlepony.unicopia.enchanting.Pages;
|
||||||
import com.minelittlepony.unicopia.enchanting.recipe.AffineIngredients;
|
import com.minelittlepony.unicopia.enchanting.recipe.AffineIngredients;
|
||||||
|
import com.minelittlepony.unicopia.enchanting.recipe.URecipes;
|
||||||
import com.minelittlepony.unicopia.item.UItems;
|
import com.minelittlepony.unicopia.item.UItems;
|
||||||
import com.minelittlepony.unicopia.mixin.CriterionsRegistry;
|
import com.minelittlepony.unicopia.mixin.CriterionsRegistry;
|
||||||
import com.minelittlepony.unicopia.network.MsgPlayerAbility;
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
import com.minelittlepony.unicopia.network.MsgPlayerCapabilities;
|
|
||||||
import com.minelittlepony.unicopia.network.MsgRequestCapabilities;
|
|
||||||
import com.minelittlepony.unicopia.structure.UStructures;
|
import com.minelittlepony.unicopia.structure.UStructures;
|
||||||
|
|
||||||
public class Unicopia implements ModInitializer {
|
public class Unicopia implements ModInitializer {
|
||||||
public static final String MODID = "unicopia";
|
public static final String MODID = "unicopia";
|
||||||
|
|
||||||
public static final Logger LOGGER = LogManager.getLogger();
|
public static final Logger LOGGER = LogManager.getLogger();
|
||||||
|
|
||||||
private static Channel channel;
|
|
||||||
|
|
||||||
public static Channel getConnection() {
|
|
||||||
return channel;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onInitialize() {
|
public void onInitialize() {
|
||||||
Config.init(GamePaths.getConfigDirectory());
|
Config.init(GamePaths.getConfigDirectory());
|
||||||
|
|
||||||
channel = JumpingCastle.subscribeTo(MODID, () -> {})
|
Channel.bootstrap();
|
||||||
.listenFor(MsgRequestCapabilities.class)
|
|
||||||
.listenFor(MsgPlayerCapabilities.class)
|
|
||||||
.listenFor(MsgPlayerAbility.class);
|
|
||||||
|
|
||||||
UTags.bootstrap();
|
UTags.bootstrap();
|
||||||
Commands.bootstrap();
|
Commands.bootstrap();
|
||||||
UBlocks.bootstrap();
|
UBlocks.bootstrap();
|
||||||
UItems.bootstrap();
|
UItems.bootstrap();
|
||||||
UContainers.bootstrap();
|
UContainers.bootstrap();
|
||||||
UStructures.bootstrap();
|
UStructures.bootstrap();
|
||||||
|
URecipes.bootstrap();
|
||||||
Abilities.getInstance().init();
|
Abilities.getInstance().init();
|
||||||
|
|
||||||
CriterionsRegistry.register(BOHDeathCriterion.INSTANCE);
|
CriterionsRegistry.register(BOHDeathCriterion.INSTANCE);
|
||||||
|
|
|
@ -50,7 +50,7 @@ public class UnicornCastingAbility implements Ability<Ability.Hit> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void apply(Pony player, Hit data) {
|
public void apply(Pony player, Hit data) {
|
||||||
// TODO: A way for the player to select which effect they want
|
// XXX: A way for the player to select which effect they want
|
||||||
if (player.getEffect() instanceof ShieldSpell) {
|
if (player.getEffect() instanceof ShieldSpell) {
|
||||||
player.setEffect(null);
|
player.setEffect(null);
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -6,11 +6,9 @@ import javax.annotation.Nonnull;
|
||||||
import javax.annotation.Nullable;
|
import javax.annotation.Nullable;
|
||||||
|
|
||||||
import com.minelittlepony.common.event.ClientReadyCallback;
|
import com.minelittlepony.common.event.ClientReadyCallback;
|
||||||
import com.minelittlepony.jumpingcastle.api.Target;
|
|
||||||
import com.minelittlepony.unicopia.Config;
|
import com.minelittlepony.unicopia.Config;
|
||||||
import com.minelittlepony.unicopia.InteractionManager;
|
import com.minelittlepony.unicopia.InteractionManager;
|
||||||
import com.minelittlepony.unicopia.Race;
|
import com.minelittlepony.unicopia.Race;
|
||||||
import com.minelittlepony.unicopia.Unicopia;
|
|
||||||
import com.minelittlepony.unicopia.ability.Abilities;
|
import com.minelittlepony.unicopia.ability.Abilities;
|
||||||
import com.minelittlepony.unicopia.block.UBlocks;
|
import com.minelittlepony.unicopia.block.UBlocks;
|
||||||
import com.minelittlepony.unicopia.container.SpellbookResultSlot;
|
import com.minelittlepony.unicopia.container.SpellbookResultSlot;
|
||||||
|
@ -19,6 +17,7 @@ import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
import com.minelittlepony.unicopia.item.UItems;
|
import com.minelittlepony.unicopia.item.UItems;
|
||||||
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
||||||
import com.minelittlepony.unicopia.mixin.client.DefaultTexturesRegistry;
|
import com.minelittlepony.unicopia.mixin.client.DefaultTexturesRegistry;
|
||||||
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
import com.minelittlepony.unicopia.network.MsgRequestCapabilities;
|
import com.minelittlepony.unicopia.network.MsgRequestCapabilities;
|
||||||
import com.minelittlepony.unicopia.util.dummy.DummyClientPlayerEntity;
|
import com.minelittlepony.unicopia.util.dummy.DummyClientPlayerEntity;
|
||||||
import com.mojang.authlib.GameProfile;
|
import com.mojang.authlib.GameProfile;
|
||||||
|
@ -84,7 +83,7 @@ public class UnicopiaClient extends InteractionManager implements ClientModIniti
|
||||||
if (newRace != clientPlayerRace) {
|
if (newRace != clientPlayerRace) {
|
||||||
clientPlayerRace = newRace;
|
clientPlayerRace = newRace;
|
||||||
|
|
||||||
Unicopia.getConnection().send(new MsgRequestCapabilities(player, clientPlayerRace), Target.SERVER);
|
Channel.REQUEST_CAPABILITIES.send(new MsgRequestCapabilities(player, clientPlayerRace));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,7 @@ import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
import net.minecraft.client.MinecraftClient;
|
import net.minecraft.client.MinecraftClient;
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
// TODO: forge events
|
// XXX: hud render events
|
||||||
class HudHooks {
|
class HudHooks {
|
||||||
public static void beforePreRenderHud() {
|
public static void beforePreRenderHud() {
|
||||||
MinecraftClient client = MinecraftClient.getInstance();
|
MinecraftClient client = MinecraftClient.getInstance();
|
||||||
|
|
|
@ -5,6 +5,7 @@ import javax.annotation.Nonnull;
|
||||||
import com.minelittlepony.unicopia.AwaitTickQueue;
|
import com.minelittlepony.unicopia.AwaitTickQueue;
|
||||||
import com.minelittlepony.unicopia.EquinePredicates;
|
import com.minelittlepony.unicopia.EquinePredicates;
|
||||||
import com.minelittlepony.unicopia.enchanting.IPageUnlockListener;
|
import com.minelittlepony.unicopia.enchanting.IPageUnlockListener;
|
||||||
|
import com.minelittlepony.unicopia.enchanting.recipe.URecipes;
|
||||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
||||||
|
|
||||||
|
@ -16,7 +17,6 @@ import net.minecraft.inventory.Inventory;
|
||||||
import net.minecraft.item.ItemStack;
|
import net.minecraft.item.ItemStack;
|
||||||
import net.minecraft.particle.ParticleTypes;
|
import net.minecraft.particle.ParticleTypes;
|
||||||
import net.minecraft.recipe.Recipe;
|
import net.minecraft.recipe.Recipe;
|
||||||
import net.minecraft.recipe.RecipeType;
|
|
||||||
import net.minecraft.sound.SoundEvents;
|
import net.minecraft.sound.SoundEvents;
|
||||||
import net.minecraft.util.Identifier;
|
import net.minecraft.util.Identifier;
|
||||||
import net.minecraft.util.PacketByteBuf;
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
@ -73,8 +73,7 @@ public class SpellBookContainer extends Container {
|
||||||
ItemStack current = craftResult.getInvStack(0);
|
ItemStack current = craftResult.getInvStack(0);
|
||||||
|
|
||||||
if (!current.isEmpty()) {
|
if (!current.isEmpty()) {
|
||||||
// TODO: URecipeType.SPELL_BOOK
|
ItemStack crafted = player.world.getRecipeManager().getFirstMatch(URecipes.SPELL_BOOK, craftMatrix, worldObj)
|
||||||
ItemStack crafted = player.world.getRecipeManager().getFirstMatch(RecipeType.CRAFTING, craftMatrix, worldObj)
|
|
||||||
.map(Recipe::getOutput)
|
.map(Recipe::getOutput)
|
||||||
.orElse(ItemStack.EMPTY);
|
.orElse(ItemStack.EMPTY);
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package com.minelittlepony.unicopia.container;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.enchanting.IPageUnlockListener;
|
import com.minelittlepony.unicopia.enchanting.IPageUnlockListener;
|
||||||
import com.minelittlepony.unicopia.enchanting.SpellCraftingEvent;
|
import com.minelittlepony.unicopia.enchanting.SpellCraftingEvent;
|
||||||
|
import com.minelittlepony.unicopia.enchanting.recipe.URecipes;
|
||||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
import com.minelittlepony.unicopia.item.MagicGemItem;
|
import com.minelittlepony.unicopia.item.MagicGemItem;
|
||||||
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
||||||
|
@ -12,7 +13,6 @@ import net.minecraft.entity.player.PlayerEntity;
|
||||||
import net.minecraft.inventory.Inventory;
|
import net.minecraft.inventory.Inventory;
|
||||||
import net.minecraft.item.ItemStack;
|
import net.minecraft.item.ItemStack;
|
||||||
import net.minecraft.item.MusicDiscItem;
|
import net.minecraft.item.MusicDiscItem;
|
||||||
import net.minecraft.recipe.RecipeType;
|
|
||||||
import net.minecraft.util.DefaultedList;
|
import net.minecraft.util.DefaultedList;
|
||||||
import net.minecraft.util.Identifier;
|
import net.minecraft.util.Identifier;
|
||||||
|
|
||||||
|
@ -49,8 +49,7 @@ public class SpellbookResultSlot extends SpellBookContainer.SpellbookSlot {
|
||||||
ItemStack current = craftMatrix.getCraftResultMatrix().getInvStack(0);
|
ItemStack current = craftMatrix.getCraftResultMatrix().getInvStack(0);
|
||||||
craftMatrix.getCraftResultMatrix().setInvStack(0, stack);
|
craftMatrix.getCraftResultMatrix().setInvStack(0, stack);
|
||||||
|
|
||||||
// TODO: URecipeType.SPELL_BOOK
|
DefaultedList<ItemStack> remaining = player.world.getRecipeManager().getRemainingStacks(URecipes.SPELL_BOOK, craftMatrix, player.world);
|
||||||
DefaultedList<ItemStack> remaining = player.world.getRecipeManager().getRemainingStacks(RecipeType.CRAFTING, craftMatrix, player.world);
|
|
||||||
|
|
||||||
craftMatrix.getCraftResultMatrix().setInvStack(0, current);
|
craftMatrix.getCraftResultMatrix().setInvStack(0, current);
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
package com.minelittlepony.unicopia.ducks;
|
package com.minelittlepony.unicopia.ducks;
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
// TODO: 1.16 Use the vanilla BlockTag once mojang adds it
|
// XXX: 1.16 Use the vanilla BlockTag once mojang adds it
|
||||||
public interface Climbable {
|
public interface Climbable {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,29 +2,18 @@ package com.minelittlepony.unicopia.enchanting.recipe;
|
||||||
|
|
||||||
import com.google.gson.JsonObject;
|
import com.google.gson.JsonObject;
|
||||||
|
|
||||||
import net.minecraft.inventory.CraftingInventory;
|
|
||||||
import net.minecraft.item.ItemStack;
|
import net.minecraft.item.ItemStack;
|
||||||
import net.minecraft.recipe.Recipe;
|
|
||||||
import net.minecraft.recipe.RecipeSerializer;
|
import net.minecraft.recipe.RecipeSerializer;
|
||||||
import net.minecraft.recipe.RecipeType;
|
import net.minecraft.recipe.RecipeType;
|
||||||
import net.minecraft.util.DefaultedList;
|
import net.minecraft.util.DefaultedList;
|
||||||
import net.minecraft.util.Identifier;
|
import net.minecraft.util.Identifier;
|
||||||
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
|
||||||
public class SpecialRecipe extends AbstractSpecialRecipe {
|
public class SpecialRecipe extends AbstractSpecialRecipe {
|
||||||
|
|
||||||
private final SpellIngredient output;
|
private final SpellIngredient output;
|
||||||
|
|
||||||
public static Recipe<CraftingInventory> deserialize(JsonObject json) {
|
|
||||||
return new SpecialRecipe(null,
|
|
||||||
SpellIngredient.single(json.get("input").getAsJsonObject()),
|
|
||||||
SpellIngredient.single(json.get("output").getAsJsonObject()),
|
|
||||||
SpellIngredient.multiple(json)
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
public SpecialRecipe(Identifier id, SpellIngredient input, SpellIngredient output, DefaultedList<SpellIngredient> ingredients) {
|
public SpecialRecipe(Identifier id, SpellIngredient input, SpellIngredient output, DefaultedList<SpellIngredient> ingredients) {
|
||||||
super(id, input, ingredients);
|
super(id, input, ingredients);
|
||||||
|
|
||||||
this.output = output;
|
this.output = output;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -35,13 +24,45 @@ public class SpecialRecipe extends AbstractSpecialRecipe {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RecipeSerializer<?> getSerializer() {
|
public RecipeSerializer<?> getSerializer() {
|
||||||
// TODO Auto-generated method stub
|
return URecipes.SPECIAL_SERIALIZER;
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RecipeType<?> getType() {
|
public RecipeType<?> getType() {
|
||||||
// TODO Auto-generated method stub
|
return URecipes.SPELL_BOOK;
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static class Serializer implements RecipeSerializer<SpecialRecipe> {
|
||||||
|
@Override
|
||||||
|
public SpecialRecipe read(Identifier id, JsonObject json) {
|
||||||
|
return new SpecialRecipe(id,
|
||||||
|
SpellIngredient.single(json.get("input").getAsJsonObject()),
|
||||||
|
SpellIngredient.single(json.get("output").getAsJsonObject()),
|
||||||
|
SpellIngredient.multiple(json)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public SpecialRecipe read(Identifier id, PacketByteBuf buf) {
|
||||||
|
SpellIngredient input = SpellIngredient.SERIALIZER.read(buf);
|
||||||
|
SpellIngredient output = SpellIngredient.SERIALIZER.read(buf);
|
||||||
|
int length = buf.readInt();
|
||||||
|
DefaultedList<SpellIngredient> ingredients = DefaultedList.copyOf(SpellIngredient.EMPTY);
|
||||||
|
while (ingredients.size() < length) {
|
||||||
|
ingredients.add(SpellIngredient.SERIALIZER.read(buf));
|
||||||
|
}
|
||||||
|
|
||||||
|
return new SpecialRecipe(id, input, output, ingredients);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void write(PacketByteBuf buf, SpecialRecipe recipe) {
|
||||||
|
recipe.getSpellItem().write(buf);
|
||||||
|
recipe.output.write(buf);
|
||||||
|
DefaultedList<SpellIngredient> ingredients = recipe.getSpellIngredients();
|
||||||
|
buf.writeInt(ingredients.size());
|
||||||
|
ingredients.forEach(i -> i.write(buf));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -2,6 +2,7 @@ package com.minelittlepony.unicopia.enchanting.recipe;
|
||||||
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
|
|
||||||
import com.google.gson.JsonElement;
|
import com.google.gson.JsonElement;
|
||||||
|
@ -20,6 +21,7 @@ public interface SpellIngredient {
|
||||||
map.put("single", SingleSpellIngredient.SERIALIZER);
|
map.put("single", SingleSpellIngredient.SERIALIZER);
|
||||||
map.put("affine", AffineIngredient.SERIALIZER);
|
map.put("affine", AffineIngredient.SERIALIZER);
|
||||||
});
|
});
|
||||||
|
Map<Serializer<? extends SpellIngredient>, String> IDS = SERIALIZERS.entrySet().stream().collect(Collectors.toMap(Map.Entry::getValue, Map.Entry::getKey));
|
||||||
|
|
||||||
Serializer<SpellIngredient> SERIALIZER = new Serializer<SpellIngredient>() {
|
Serializer<SpellIngredient> SERIALIZER = new Serializer<SpellIngredient>() {
|
||||||
@Override
|
@Override
|
||||||
|
@ -40,7 +42,7 @@ public interface SpellIngredient {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void write(PacketByteBuf buff, SpellIngredient recipe) {
|
public void write(PacketByteBuf buff, SpellIngredient recipe) {
|
||||||
buff.writeByte(recipe instanceof SingleSpellIngredient ? 0 : 1);
|
buff.writeString(IDS.get(recipe.getSerializer()));
|
||||||
recipe.write(buff);
|
recipe.write(buff);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -45,16 +45,15 @@ public class SpellRecipe extends AbstractSpecialRecipe {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RecipeSerializer<?> getSerializer() {
|
public RecipeSerializer<?> getSerializer() {
|
||||||
return null;
|
return URecipes.SPELL_SERIALIZER;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RecipeType<?> getType() {
|
public RecipeType<?> getType() {
|
||||||
return null;
|
return URecipes.SPELL_BOOK;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class Serializer implements RecipeSerializer<SpellRecipe> {
|
public static class Serializer implements RecipeSerializer<SpellRecipe> {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SpellRecipe read(Identifier id, JsonObject json) {
|
public SpellRecipe read(Identifier id, JsonObject json) {
|
||||||
JsonObject resultJson = json.get("result").getAsJsonObject();
|
JsonObject resultJson = json.get("result").getAsJsonObject();
|
||||||
|
@ -93,4 +92,5 @@ public class SpellRecipe extends AbstractSpecialRecipe {
|
||||||
ingredients.forEach(i -> i.write(buff));
|
ingredients.forEach(i -> i.write(buff));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,30 @@
|
||||||
|
package com.minelittlepony.unicopia.enchanting.recipe;
|
||||||
|
|
||||||
|
import net.minecraft.recipe.Recipe;
|
||||||
|
import net.minecraft.recipe.RecipeSerializer;
|
||||||
|
import net.minecraft.recipe.RecipeType;
|
||||||
|
import net.minecraft.util.Identifier;
|
||||||
|
import net.minecraft.util.registry.Registry;
|
||||||
|
|
||||||
|
public interface URecipes {
|
||||||
|
|
||||||
|
RecipeType<SpellRecipe> SPELL_BOOK = register("spell_book");
|
||||||
|
|
||||||
|
RecipeSerializer<SpecialRecipe> SPECIAL_SERIALIZER = register("special_spell", new SpecialRecipe.Serializer());
|
||||||
|
RecipeSerializer<SpellRecipe> SPELL_SERIALIZER = register("spell", new SpellRecipe.Serializer());
|
||||||
|
|
||||||
|
static <T extends Recipe<?>> RecipeType<T> register(final String id) {
|
||||||
|
return Registry.register(Registry.RECIPE_TYPE, new Identifier("unicopia", id), new RecipeType<T>() {
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
static <S extends RecipeSerializer<T>, T extends Recipe<?>> S register(String id, S serializer) {
|
||||||
|
return Registry.register(Registry.RECIPE_SERIALIZER, new Identifier("unicopia", id), serializer);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void bootstrap() {}
|
||||||
|
}
|
|
@ -1,18 +1,17 @@
|
||||||
package com.minelittlepony.unicopia.entity;
|
package com.minelittlepony.unicopia.entity;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.Race;
|
import com.minelittlepony.unicopia.Race;
|
||||||
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
|
import com.minelittlepony.unicopia.network.MsgSpawnRainbow;
|
||||||
|
|
||||||
import net.minecraft.client.MinecraftClient;
|
|
||||||
import net.minecraft.client.network.packet.EntitySpawnGlobalS2CPacket;
|
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
|
import net.minecraft.entity.EntityDimensions;
|
||||||
|
import net.minecraft.entity.EntityPose;
|
||||||
import net.minecraft.entity.EntityType;
|
import net.minecraft.entity.EntityType;
|
||||||
import net.minecraft.entity.LightningEntity;
|
|
||||||
import net.minecraft.entity.SpawnType;
|
import net.minecraft.entity.SpawnType;
|
||||||
import net.minecraft.entity.mob.MobEntity;
|
import net.minecraft.entity.mob.MobEntity;
|
||||||
import net.minecraft.nbt.CompoundTag;
|
import net.minecraft.nbt.CompoundTag;
|
||||||
import net.minecraft.network.NetworkThreadUtils;
|
|
||||||
import net.minecraft.network.Packet;
|
import net.minecraft.network.Packet;
|
||||||
import net.minecraft.network.listener.ClientPlayPacketListener;
|
|
||||||
import net.minecraft.sound.SoundCategory;
|
import net.minecraft.sound.SoundCategory;
|
||||||
import net.minecraft.util.math.Box;
|
import net.minecraft.util.math.Box;
|
||||||
import net.minecraft.util.math.MathHelper;
|
import net.minecraft.util.math.MathHelper;
|
||||||
|
@ -26,7 +25,7 @@ public class RainbowEntity extends Entity implements InAnimate {
|
||||||
|
|
||||||
private int ticksAlive;
|
private int ticksAlive;
|
||||||
|
|
||||||
private double radius;
|
private final double radius;
|
||||||
|
|
||||||
public static final int RAINBOW_MAX_SIZE = 180;
|
public static final int RAINBOW_MAX_SIZE = 180;
|
||||||
public static final int RAINBOW_MIN_SIZE = 50;
|
public static final int RAINBOW_MIN_SIZE = 50;
|
||||||
|
@ -49,8 +48,7 @@ public class RainbowEntity extends Entity implements InAnimate {
|
||||||
|
|
||||||
ignoreCameraFrustum = true;
|
ignoreCameraFrustum = true;
|
||||||
|
|
||||||
//width = (float)radius;
|
calculateDimensions();
|
||||||
//height = width;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -69,6 +67,11 @@ public class RainbowEntity extends Entity implements InAnimate {
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public EntityDimensions getDimensions(EntityPose pose) {
|
||||||
|
return EntityDimensions.changing((float)getRadius(), (float)getRadius());
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public SoundCategory getSoundCategory() {
|
public SoundCategory getSoundCategory() {
|
||||||
return SoundCategory.WEATHER;
|
return SoundCategory.WEATHER;
|
||||||
|
@ -119,7 +122,7 @@ public class RainbowEntity extends Entity implements InAnimate {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Packet<?> createSpawnPacket() {
|
public Packet<?> createSpawnPacket() {
|
||||||
return new SpawnPacket(this);
|
return Channel.SPAWN_RAINBOW.toPacket(new MsgSpawnRainbow(this));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class Spawner extends MobEntity {
|
public static class Spawner extends MobEntity {
|
||||||
|
@ -159,27 +162,4 @@ public class RainbowEntity extends Entity implements InAnimate {
|
||||||
world.spawnEntity(rainbow);
|
world.spawnEntity(rainbow);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static class SpawnPacket extends EntitySpawnGlobalS2CPacket {
|
|
||||||
public SpawnPacket(RainbowEntity entity) {
|
|
||||||
super(entity);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void apply(ClientPlayPacketListener listener) {
|
|
||||||
// TODO: Packet needs to be registered, and handling separated
|
|
||||||
MinecraftClient client = MinecraftClient.getInstance();
|
|
||||||
|
|
||||||
NetworkThreadUtils.forceMainThread(this, listener, client);
|
|
||||||
double x = getX();
|
|
||||||
double y = getY();
|
|
||||||
double z = getZ();
|
|
||||||
LightningEntity entity = new LightningEntity(client.world, x, y, z, false);
|
|
||||||
entity.updateTrackedPosition(x, y, z);
|
|
||||||
entity.yaw = 0;
|
|
||||||
entity.pitch = 0;
|
|
||||||
entity.setEntityId(getId());
|
|
||||||
client.world.addLightning(entity);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,15 +1,13 @@
|
||||||
package com.minelittlepony.unicopia.entity.player;
|
package com.minelittlepony.unicopia.entity.player;
|
||||||
|
|
||||||
import javax.annotation.Nonnull;
|
|
||||||
import javax.annotation.Nullable;
|
import javax.annotation.Nullable;
|
||||||
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Target;
|
|
||||||
import com.minelittlepony.unicopia.Unicopia;
|
|
||||||
import com.minelittlepony.unicopia.ability.AbilityReceiver;
|
import com.minelittlepony.unicopia.ability.AbilityReceiver;
|
||||||
import com.minelittlepony.unicopia.ability.Ability;
|
import com.minelittlepony.unicopia.ability.Ability;
|
||||||
import com.minelittlepony.unicopia.ability.Abilities;
|
import com.minelittlepony.unicopia.ability.Abilities;
|
||||||
import com.minelittlepony.unicopia.entity.Updatable;
|
import com.minelittlepony.unicopia.entity.Updatable;
|
||||||
import com.minelittlepony.unicopia.network.MsgPlayerAbility;
|
import com.minelittlepony.unicopia.network.MsgPlayerAbility;
|
||||||
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
import com.minelittlepony.unicopia.util.NbtSerialisable;
|
import com.minelittlepony.unicopia.util.NbtSerialisable;
|
||||||
|
|
||||||
import net.minecraft.nbt.CompoundTag;
|
import net.minecraft.nbt.CompoundTag;
|
||||||
|
@ -112,7 +110,11 @@ class AbilityDelegate implements AbilityReceiver, Updatable, NbtSerialisable {
|
||||||
cooldown = ability.getCooldownTime(player);
|
cooldown = ability.getCooldownTime(player);
|
||||||
|
|
||||||
if (player.isClientPlayer()) {
|
if (player.isClientPlayer()) {
|
||||||
if (!activateAbility(ability)) {
|
Ability.IData data = ability.tryActivate(player);
|
||||||
|
|
||||||
|
if (data != null) {
|
||||||
|
Channel.PLAYER_ABILITY.send(new MsgPlayerAbility(ability, data));
|
||||||
|
} else {
|
||||||
cooldown = 0;
|
cooldown = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -150,18 +152,4 @@ class AbilityDelegate implements AbilityReceiver, Updatable, NbtSerialisable {
|
||||||
.ifPresent(p -> activeAbility = p);
|
.ifPresent(p -> activeAbility = p);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Attempts to activate the current stored ability.
|
|
||||||
* Returns true if the ability suceeded, otherwise false.
|
|
||||||
*/
|
|
||||||
protected boolean activateAbility(@Nonnull Ability<?> ability) {
|
|
||||||
Ability.IData data = ability.tryActivate(player);
|
|
||||||
|
|
||||||
if (data != null) {
|
|
||||||
Unicopia.getConnection().send(new MsgPlayerAbility(player.getOwner(), ability, data), Target.SERVER);
|
|
||||||
}
|
|
||||||
|
|
||||||
return data != null;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,6 +15,7 @@ import com.minelittlepony.unicopia.util.NbtSerialisable;
|
||||||
import com.minelittlepony.unicopia.util.MutableVector;
|
import com.minelittlepony.unicopia.util.MutableVector;
|
||||||
|
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
|
import net.minecraft.entity.EntityPose;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
import net.minecraft.nbt.CompoundTag;
|
import net.minecraft.nbt.CompoundTag;
|
||||||
import net.minecraft.sound.SoundCategory;
|
import net.minecraft.sound.SoundCategory;
|
||||||
|
@ -41,6 +42,8 @@ public class GravityDelegate implements Updatable, FlightControl, NbtSerialisabl
|
||||||
|
|
||||||
private float gravity = 0;
|
private float gravity = 0;
|
||||||
|
|
||||||
|
private float eyeHeight;
|
||||||
|
|
||||||
public GravityDelegate(Pony player) {
|
public GravityDelegate(Pony player) {
|
||||||
this.player = player;
|
this.player = player;
|
||||||
}
|
}
|
||||||
|
@ -65,6 +68,10 @@ public class GravityDelegate implements Updatable, FlightControl, NbtSerialisabl
|
||||||
return Math.sqrt(getHorizontalMotion(player.getOwner())) > 0.4F;
|
return Math.sqrt(getHorizontalMotion(player.getOwner())) > 0.4F;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public float getEyeHeight() {
|
||||||
|
return eyeHeight;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public float getTargetEyeHeight(Pony player) {
|
public float getTargetEyeHeight(Pony player) {
|
||||||
if (player.hasEffect()) {
|
if (player.hasEffect()) {
|
||||||
|
@ -81,7 +88,8 @@ public class GravityDelegate implements Updatable, FlightControl, NbtSerialisabl
|
||||||
return 0.5F;
|
return 0.5F;
|
||||||
}
|
}
|
||||||
|
|
||||||
return player.getOwner().getStandingEyeHeight();
|
EntityPose pose = player.getOwner().getPose();
|
||||||
|
return player.getOwner().getActiveEyeHeight(pose, player.getOwner().getDimensions(pose));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -163,7 +171,8 @@ public class GravityDelegate implements Updatable, FlightControl, NbtSerialisabl
|
||||||
}
|
}
|
||||||
|
|
||||||
float bodyHeight = getTargetBodyHeight(player);
|
float bodyHeight = getTargetBodyHeight(player);
|
||||||
float eyeHeight = getTargetEyeHeight(player);
|
eyeHeight = 0;
|
||||||
|
eyeHeight = getTargetEyeHeight(player);
|
||||||
|
|
||||||
if (gravity < 0) {
|
if (gravity < 0) {
|
||||||
eyeHeight = bodyHeight - eyeHeight;
|
eyeHeight = bodyHeight - eyeHeight;
|
||||||
|
@ -176,8 +185,6 @@ public class GravityDelegate implements Updatable, FlightControl, NbtSerialisabl
|
||||||
|
|
||||||
|
|
||||||
((MixinEntity)entity).setSize(entity.getWidth(), bodyHeight);
|
((MixinEntity)entity).setSize(entity.getWidth(), bodyHeight);
|
||||||
// TODO: Change eye height
|
|
||||||
//entity.eyeHeight = eyeHeight;
|
|
||||||
|
|
||||||
if (gravity < 0) {
|
if (gravity < 0) {
|
||||||
if (entity.isSneaking()) {
|
if (entity.isSneaking()) {
|
||||||
|
|
|
@ -6,6 +6,7 @@ import com.minelittlepony.unicopia.Race;
|
||||||
import com.minelittlepony.unicopia.container.HeavyInventory;
|
import com.minelittlepony.unicopia.container.HeavyInventory;
|
||||||
import com.minelittlepony.unicopia.mixin.Walker;
|
import com.minelittlepony.unicopia.mixin.Walker;
|
||||||
|
|
||||||
|
import net.minecraft.entity.attribute.ClampedEntityAttribute;
|
||||||
import net.minecraft.entity.attribute.EntityAttribute;
|
import net.minecraft.entity.attribute.EntityAttribute;
|
||||||
import net.minecraft.entity.attribute.EntityAttributeInstance;
|
import net.minecraft.entity.attribute.EntityAttributeInstance;
|
||||||
import net.minecraft.entity.attribute.EntityAttributeModifier;
|
import net.minecraft.entity.attribute.EntityAttributeModifier;
|
||||||
|
@ -13,14 +14,16 @@ import net.minecraft.entity.attribute.EntityAttributeModifier.Operation;
|
||||||
import net.minecraft.entity.attribute.EntityAttributes;
|
import net.minecraft.entity.attribute.EntityAttributes;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
|
|
||||||
public class PlayerAttributes {
|
class PlayerAttributes {
|
||||||
|
|
||||||
|
static final EntityAttribute EXTENDED_REACH_DISTANCE = new ClampedEntityAttribute(null, "player.reachDistance", 0, 0, 10);
|
||||||
|
|
||||||
private static final EntityAttributeModifier EARTH_PONY_STRENGTH =
|
private static final EntityAttributeModifier EARTH_PONY_STRENGTH =
|
||||||
new EntityAttributeModifier(UUID.fromString("777a5505-521e-480b-b9d5-6ea54f259564"), "Earth Pony Strength", 0.6, Operation.MULTIPLY_TOTAL);
|
new EntityAttributeModifier(UUID.fromString("777a5505-521e-480b-b9d5-6ea54f259564"), "Earth Pony Strength", 0.6, Operation.MULTIPLY_TOTAL);
|
||||||
private static final EntityAttributeModifier PEGASUS_SPEED =
|
private static final EntityAttributeModifier PEGASUS_SPEED =
|
||||||
new EntityAttributeModifier(UUID.fromString("9e2699fc-3b8d-4f71-9d2d-fb92ee19b4f7"), "Pegasus Speed", 0.2, Operation.MULTIPLY_TOTAL);
|
new EntityAttributeModifier(UUID.fromString("9e2699fc-3b8d-4f71-9d2d-fb92ee19b4f7"), "Pegasus Speed", 0.2, Operation.MULTIPLY_TOTAL);
|
||||||
//private static final EntityAttributeModifier PEGASUS_REACH =
|
private static final EntityAttributeModifier PEGASUS_REACH =
|
||||||
// new EntityAttributeModifier(UUID.fromString("707b50a8-03e8-40f4-8553-ecf67025fd6d"), "Pegasus Reach", 1.5, Operation.ADDITION);
|
new EntityAttributeModifier(UUID.fromString("707b50a8-03e8-40f4-8553-ecf67025fd6d"), "Pegasus Reach", 1.5, Operation.ADDITION);
|
||||||
|
|
||||||
private double loadStrength = 0;
|
private double loadStrength = 0;
|
||||||
|
|
||||||
|
@ -29,14 +32,15 @@ public class PlayerAttributes {
|
||||||
|
|
||||||
((Walker)entity.abilities).setWalkSpeed(0.1F - (float)(loadStrength / 100000));
|
((Walker)entity.abilities).setWalkSpeed(0.1F - (float)(loadStrength / 100000));
|
||||||
|
|
||||||
applyAttribute(entity, EntityAttributes.ATTACK_DAMAGE, EARTH_PONY_STRENGTH, race.canUseEarth());
|
toggleAttribute(entity, EntityAttributes.ATTACK_DAMAGE, EARTH_PONY_STRENGTH, race.canUseEarth());
|
||||||
applyAttribute(entity, EntityAttributes.KNOCKBACK_RESISTANCE, EARTH_PONY_STRENGTH, race.canUseEarth());
|
toggleAttribute(entity, EntityAttributes.KNOCKBACK_RESISTANCE, EARTH_PONY_STRENGTH, race.canUseEarth());
|
||||||
applyAttribute(entity, EntityAttributes.MOVEMENT_SPEED, PEGASUS_SPEED, race.canFly());
|
toggleAttribute(entity, EntityAttributes.MOVEMENT_SPEED, PEGASUS_SPEED, race.canFly());
|
||||||
applyAttribute(entity, EntityAttributes.ATTACK_SPEED, PEGASUS_SPEED, race.canFly());
|
toggleAttribute(entity, EntityAttributes.ATTACK_SPEED, PEGASUS_SPEED, race.canFly());
|
||||||
// applyAttribute(entity, PlayerEntity.REACH_DISTANCE, PEGASUS_REACH, race.canFly());
|
toggleAttribute(entity, EXTENDED_REACH_DISTANCE, PEGASUS_REACH, race.canFly());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void applyAttribute(PlayerEntity entity, EntityAttribute attribute, EntityAttributeModifier modifier, boolean enable) {
|
private void toggleAttribute(PlayerEntity entity, EntityAttribute attribute, EntityAttributeModifier modifier, boolean enable) {
|
||||||
|
|
||||||
EntityAttributeInstance instance = entity.getAttributeInstance(attribute);
|
EntityAttributeInstance instance = entity.getAttributeInstance(attribute);
|
||||||
|
|
||||||
if (enable) {
|
if (enable) {
|
||||||
|
|
|
@ -4,7 +4,6 @@ import javax.annotation.Nullable;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.Race;
|
import com.minelittlepony.unicopia.Race;
|
||||||
import com.minelittlepony.unicopia.UTags;
|
import com.minelittlepony.unicopia.UTags;
|
||||||
import com.minelittlepony.unicopia.Unicopia;
|
|
||||||
import com.minelittlepony.unicopia.ability.AbilityReceiver;
|
import com.minelittlepony.unicopia.ability.AbilityReceiver;
|
||||||
import com.minelittlepony.unicopia.enchanting.PageOwner;
|
import com.minelittlepony.unicopia.enchanting.PageOwner;
|
||||||
import com.minelittlepony.unicopia.entity.FlightControl;
|
import com.minelittlepony.unicopia.entity.FlightControl;
|
||||||
|
@ -16,6 +15,7 @@ import com.minelittlepony.unicopia.magic.HeldMagicEffect;
|
||||||
import com.minelittlepony.unicopia.magic.MagicEffect;
|
import com.minelittlepony.unicopia.magic.MagicEffect;
|
||||||
import com.minelittlepony.unicopia.magic.MagicalItem;
|
import com.minelittlepony.unicopia.magic.MagicalItem;
|
||||||
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
import com.minelittlepony.unicopia.magic.spell.SpellRegistry;
|
||||||
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
import com.minelittlepony.unicopia.network.EffectSync;
|
import com.minelittlepony.unicopia.network.EffectSync;
|
||||||
import com.minelittlepony.unicopia.network.MsgPlayerCapabilities;
|
import com.minelittlepony.unicopia.network.MsgPlayerCapabilities;
|
||||||
import com.minelittlepony.unicopia.util.BasicEasingInterpolator;
|
import com.minelittlepony.unicopia.util.BasicEasingInterpolator;
|
||||||
|
@ -85,6 +85,8 @@ public class PlayerImpl implements Pony {
|
||||||
player.getDataTracker().startTracking(ENERGY, 0F);
|
player.getDataTracker().startTracking(ENERGY, 0F);
|
||||||
player.getDataTracker().startTracking(EFFECT, new CompoundTag());
|
player.getDataTracker().startTracking(EFFECT, new CompoundTag());
|
||||||
player.getDataTracker().startTracking(HELD_EFFECT, new CompoundTag());
|
player.getDataTracker().startTracking(HELD_EFFECT, new CompoundTag());
|
||||||
|
|
||||||
|
player.getAttributes().register(PlayerAttributes.EXTENDED_REACH_DISTANCE);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -169,11 +171,7 @@ public class PlayerImpl implements Pony {
|
||||||
dirty = false;
|
dirty = false;
|
||||||
|
|
||||||
if (!getWorld().isClient()) {
|
if (!getWorld().isClient()) {
|
||||||
if (full) {
|
Channel.BROADCAST_CAPABILITIES.send(new MsgPlayerCapabilities(full, this));
|
||||||
Unicopia.getConnection().broadcast(new MsgPlayerCapabilities(this));
|
|
||||||
} else {
|
|
||||||
Unicopia.getConnection().broadcast(new MsgPlayerCapabilities(getSpecies(), getOwner()));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -199,6 +197,11 @@ public class PlayerImpl implements Pony {
|
||||||
return gravity;
|
return gravity;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public float getExtendedReach() {
|
||||||
|
return (float)entity.getAttributeInstance(PlayerAttributes.EXTENDED_REACH_DISTANCE).getValue();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public FlightControl getFlight() {
|
public FlightControl getFlight() {
|
||||||
return gravity;
|
return gravity;
|
||||||
|
|
|
@ -70,6 +70,12 @@ public interface Pony extends Caster<PlayerEntity>, RaceContainer<PlayerEntity>,
|
||||||
*/
|
*/
|
||||||
void setExertion(float exertion);
|
void setExertion(float exertion);
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
float getExtendedReach();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds player tiredness.
|
* Adds player tiredness.
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -55,7 +55,7 @@ public class ShieldSpell extends AbstractSpell.RangedAreaSpell implements Attach
|
||||||
particlEffect
|
particlEffect
|
||||||
.ifMissing(source, () -> {
|
.ifMissing(source, () -> {
|
||||||
source.addParticle(UParticles.SPHERE, source.getOriginVector(), Vec3d.ZERO);
|
source.addParticle(UParticles.SPHERE, source.getOriginVector(), Vec3d.ZERO);
|
||||||
return null; // TODO: Attachables
|
return null; // XXX: Attachables
|
||||||
}) // 1, getTint(), 10
|
}) // 1, getTint(), 10
|
||||||
.ifPresent(p -> p.setAttribute(0, radius));
|
.ifPresent(p -> p.setAttribute(0, radius));
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,6 +13,8 @@ import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
import com.minelittlepony.unicopia.entity.player.PlayerImpl;
|
import com.minelittlepony.unicopia.entity.player.PlayerImpl;
|
||||||
import com.mojang.datafixers.util.Either;
|
import com.mojang.datafixers.util.Either;
|
||||||
|
|
||||||
|
import net.minecraft.entity.EntityDimensions;
|
||||||
|
import net.minecraft.entity.EntityPose;
|
||||||
import net.minecraft.entity.ItemEntity;
|
import net.minecraft.entity.ItemEntity;
|
||||||
import net.minecraft.entity.LivingEntity;
|
import net.minecraft.entity.LivingEntity;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
|
@ -58,7 +60,17 @@ public abstract class MixinPlayerEntity extends LivingEntity implements PonyCont
|
||||||
|
|
||||||
@Inject(method = "setGameMode(Lnet/minecraft/world/GameMode;)V",
|
@Inject(method = "setGameMode(Lnet/minecraft/world/GameMode;)V",
|
||||||
at = @At("RETURN"))
|
at = @At("RETURN"))
|
||||||
public void setGameMode(GameMode mode, CallbackInfo info) {
|
private void onSetGameMode(GameMode mode, CallbackInfo info) {
|
||||||
get().setSpecies(get().getSpecies());
|
get().setSpecies(get().getSpecies());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Inject(method = "getActiveEyeHeight(Lnet/minecraft/entity/EntityPose;Lnet/minecraft/entity/EntityDimensions;)F",
|
||||||
|
at = @At("RETURN"),
|
||||||
|
cancellable = true)
|
||||||
|
private void onGetActiveEyeHeight(EntityPose pose, EntityDimensions dimensions, CallbackInfoReturnable<Float> info) {
|
||||||
|
float h = get().getGravity().getEyeHeight();
|
||||||
|
if (h != 0) {
|
||||||
|
info.setReturnValue(h);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,86 @@
|
||||||
|
package com.minelittlepony.unicopia.network;
|
||||||
|
|
||||||
|
import java.util.function.Function;
|
||||||
|
|
||||||
|
import io.netty.buffer.Unpooled;
|
||||||
|
import net.fabricmc.fabric.api.network.ClientSidePacketRegistry;
|
||||||
|
import net.fabricmc.fabric.api.network.PacketContext;
|
||||||
|
import net.fabricmc.fabric.api.network.ServerSidePacketRegistry;
|
||||||
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
|
import net.minecraft.util.Identifier;
|
||||||
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
|
||||||
|
public interface Channel {
|
||||||
|
|
||||||
|
SPacketType<MsgPlayerAbility> PLAYER_ABILITY = clientToServer(new Identifier("unicopia", "player_ability"), MsgPlayerAbility::new);
|
||||||
|
|
||||||
|
SPacketType<MsgRequestCapabilities> REQUEST_CAPABILITIES = clientToServer(new Identifier("unicopia", "request_capabilities"), MsgRequestCapabilities::new);
|
||||||
|
CPacketType<MsgPlayerCapabilities> PLAYER_CAPABILITIES = serverToClient(new Identifier("unicopia", "player_capabilities"), MsgPlayerCapabilities::new);
|
||||||
|
|
||||||
|
SPacketType<MsgPlayerCapabilities> BROADCAST_CAPABILITIES = broadcast(PLAYER_CAPABILITIES, MsgPlayerCapabilities::new);
|
||||||
|
|
||||||
|
CPacketType<MsgSpawnRainbow> SPAWN_RAINBOW = serverToClient(new Identifier("unicopia", "rainbow_entity"), MsgSpawnRainbow::new);
|
||||||
|
|
||||||
|
static void bootstrap() { }
|
||||||
|
|
||||||
|
static <T extends Packet> SPacketType<T> clientToServer(Identifier id, Function<PacketByteBuf, T> factory) {
|
||||||
|
ServerSidePacketRegistry.INSTANCE.register(id, (context, buffer) -> factory.apply(buffer).handle(context));
|
||||||
|
return () -> id;
|
||||||
|
}
|
||||||
|
|
||||||
|
static <T extends Packet> SPacketType<T> broadcast(CPacketType<T> redirect, Function<PacketByteBuf, T> factory) {
|
||||||
|
Identifier id = new Identifier(redirect.getId().getNamespace(), "broadcast_" + redirect.getId().getPath());
|
||||||
|
ServerSidePacketRegistry.INSTANCE.register(id, (context, buffer) -> {
|
||||||
|
PlayerEntity sender = context.getPlayer();
|
||||||
|
T p = factory.apply(buffer);
|
||||||
|
p.handle(context);
|
||||||
|
sender.world.getPlayers().forEach(player -> {
|
||||||
|
if (player != null && player != sender) {
|
||||||
|
redirect.send(player, p);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
return () -> id;
|
||||||
|
}
|
||||||
|
|
||||||
|
static <T extends Packet> CPacketType<T> serverToClient(Identifier id, Function<PacketByteBuf, T> factory) {
|
||||||
|
ClientSidePacketRegistry.INSTANCE.register(id, (context, buffer) -> factory.apply(buffer).handle(context));
|
||||||
|
return () -> id;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface CPacketType<T extends Packet> {
|
||||||
|
Identifier getId();
|
||||||
|
|
||||||
|
default void send(PlayerEntity recipient, T packet) {
|
||||||
|
ServerSidePacketRegistry.INSTANCE.sendToPlayer(recipient, getId(), packet.toBuffer());
|
||||||
|
}
|
||||||
|
|
||||||
|
default net.minecraft.network.Packet<?> toPacket(T packet) {
|
||||||
|
return ServerSidePacketRegistry.INSTANCE.toPacket(getId(), packet.toBuffer());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
interface SPacketType<T extends Packet> {
|
||||||
|
Identifier getId();
|
||||||
|
|
||||||
|
default void send(T packet) {
|
||||||
|
ClientSidePacketRegistry.INSTANCE.sendToServer(getId(), packet.toBuffer());
|
||||||
|
}
|
||||||
|
|
||||||
|
default net.minecraft.network.Packet<?> toPacket(T packet) {
|
||||||
|
return ClientSidePacketRegistry.INSTANCE.toPacket(getId(), packet.toBuffer());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
interface Packet {
|
||||||
|
void handle(PacketContext context);
|
||||||
|
|
||||||
|
void toBuffer(PacketByteBuf buffer);
|
||||||
|
|
||||||
|
default PacketByteBuf toBuffer() {
|
||||||
|
PacketByteBuf buf = new PacketByteBuf(Unpooled.buffer());
|
||||||
|
toBuffer(buf);
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,43 +1,36 @@
|
||||||
package com.minelittlepony.unicopia.network;
|
package com.minelittlepony.unicopia.network;
|
||||||
|
|
||||||
import java.util.UUID;
|
|
||||||
|
|
||||||
import com.google.gson.Gson;
|
import com.google.gson.Gson;
|
||||||
import com.google.gson.GsonBuilder;
|
import com.google.gson.GsonBuilder;
|
||||||
import com.google.gson.annotations.Expose;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Channel;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Message;
|
|
||||||
import com.minelittlepony.unicopia.ability.Ability;
|
import com.minelittlepony.unicopia.ability.Ability;
|
||||||
import com.minelittlepony.unicopia.ability.Abilities;
|
import com.minelittlepony.unicopia.ability.Abilities;
|
||||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
|
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.fabricmc.fabric.api.network.PacketContext;
|
||||||
import net.minecraft.server.MinecraftServer;
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
|
||||||
public class MsgPlayerAbility implements Message, Message.Handler<MsgPlayerAbility> {
|
public class MsgPlayerAbility implements Channel.Packet {
|
||||||
|
|
||||||
private static final Gson gson = new GsonBuilder()
|
private static final Gson gson = new GsonBuilder()
|
||||||
.excludeFieldsWithoutExposeAnnotation()
|
.excludeFieldsWithoutExposeAnnotation()
|
||||||
.create();
|
.create();
|
||||||
|
|
||||||
@Expose
|
private final String powerIdentifier;
|
||||||
private UUID senderId;
|
|
||||||
|
|
||||||
@Expose
|
private final String abilityJson;
|
||||||
private String powerIdentifier;
|
|
||||||
|
|
||||||
@Expose
|
public MsgPlayerAbility(Ability<?> power, Ability.IData data) {
|
||||||
private String abilityJson;
|
|
||||||
|
|
||||||
public MsgPlayerAbility(PlayerEntity player, Ability<?> power, Ability.IData data) {
|
|
||||||
senderId = player.getUuid();
|
|
||||||
powerIdentifier = power.getKeyName();
|
powerIdentifier = power.getKeyName();
|
||||||
abilityJson = gson.toJson(data, power.getPackageType());
|
abilityJson = gson.toJson(data, power.getPackageType());
|
||||||
}
|
}
|
||||||
|
|
||||||
private <T extends Ability.IData> void apply(Ability<T> power, Channel channel) {
|
public MsgPlayerAbility(PacketByteBuf buffer) {
|
||||||
MinecraftServer server = channel.getServer();
|
powerIdentifier = buffer.readString();
|
||||||
Pony player = Pony.of(server.getPlayerManager().getPlayer(senderId));
|
abilityJson = buffer.readString();
|
||||||
|
}
|
||||||
|
|
||||||
|
private <T extends Ability.IData> void apply(Ability<T> power, PacketContext context) {
|
||||||
|
Pony player = Pony.of(context.getPlayer());
|
||||||
if (player == null) {
|
if (player == null) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -48,7 +41,13 @@ public class MsgPlayerAbility implements Message, Message.Handler<MsgPlayerAbili
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onPayload(MsgPlayerAbility message, Channel channel) {
|
public void toBuffer(PacketByteBuf buffer) {
|
||||||
Abilities.getInstance().getPowerFromName(powerIdentifier).ifPresent(power -> apply(power, channel));
|
buffer.writeString(powerIdentifier);
|
||||||
|
buffer.writeString(abilityJson);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void handle(PacketContext context) {
|
||||||
|
Abilities.getInstance().getPowerFromName(powerIdentifier).ifPresent(power -> apply(power, context));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,77 +1,60 @@
|
||||||
package com.minelittlepony.unicopia.network;
|
package com.minelittlepony.unicopia.network;
|
||||||
|
|
||||||
import java.io.ByteArrayInputStream;
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.DataInputStream;
|
|
||||||
import java.io.DataOutputStream;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.UUID;
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
import com.google.gson.annotations.Expose;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Channel;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Message;
|
|
||||||
import com.minelittlepony.unicopia.Race;
|
import com.minelittlepony.unicopia.Race;
|
||||||
import com.minelittlepony.unicopia.Unicopia;
|
|
||||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
|
|
||||||
|
import io.netty.buffer.ByteBufInputStream;
|
||||||
|
import io.netty.buffer.ByteBufOutputStream;
|
||||||
|
import net.fabricmc.fabric.api.network.PacketContext;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
import net.minecraft.server.MinecraftServer;
|
import net.minecraft.util.PacketByteBuf;
|
||||||
import net.minecraft.nbt.CompoundTag;
|
import net.minecraft.nbt.CompoundTag;
|
||||||
import net.minecraft.nbt.NbtIo;
|
import net.minecraft.nbt.NbtIo;
|
||||||
|
|
||||||
public class MsgPlayerCapabilities implements Message, Message.Handler<MsgPlayerCapabilities> {
|
public class MsgPlayerCapabilities implements Channel.Packet {
|
||||||
@Expose
|
|
||||||
Race newRace;
|
|
||||||
|
|
||||||
@Expose
|
private final Race newRace;
|
||||||
UUID senderId;
|
|
||||||
|
|
||||||
@Expose
|
private final CompoundTag compoundTag;
|
||||||
byte[] compoundTag;
|
|
||||||
|
public MsgPlayerCapabilities(PacketByteBuf buffer) {
|
||||||
|
newRace = Race.values()[buffer.readInt()];
|
||||||
|
try (InputStream in = new ByteBufInputStream(buffer)) {
|
||||||
|
compoundTag = NbtIo.readCompressed(in);
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public MsgPlayerCapabilities(Race race, PlayerEntity player) {
|
public MsgPlayerCapabilities(Race race, PlayerEntity player) {
|
||||||
newRace = race;
|
newRace = race;
|
||||||
senderId = player.getUuid();
|
compoundTag = new CompoundTag();
|
||||||
compoundTag = new byte[0];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public MsgPlayerCapabilities(Pony player) {
|
public MsgPlayerCapabilities(boolean full, Pony player) {
|
||||||
newRace = player.getSpecies();
|
newRace = player.getSpecies();
|
||||||
senderId = player.getOwner().getUuid();
|
compoundTag = full ? player.toNBT() : new CompoundTag();
|
||||||
|
}
|
||||||
|
|
||||||
try (ByteArrayOutputStream bytes = new ByteArrayOutputStream()) {
|
@Override
|
||||||
CompoundTag nbt = player.toNBT();
|
public void toBuffer(PacketByteBuf buffer) {
|
||||||
|
buffer.writeInt(newRace.ordinal());
|
||||||
NbtIo.write(nbt, new DataOutputStream(bytes));
|
try (OutputStream out = new ByteBufOutputStream(buffer)) {
|
||||||
|
NbtIo.writeCompressed(compoundTag, out);
|
||||||
compoundTag = bytes.toByteArray();
|
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onPayload(MsgPlayerCapabilities message, Channel channel) {
|
public void handle(PacketContext context) {
|
||||||
|
Pony player = Pony.of(context.getPlayer());
|
||||||
MinecraftServer server = channel.getServer();
|
if (compoundTag.isEmpty()) {
|
||||||
|
player.setSpecies(newRace);
|
||||||
PlayerEntity self = server.getPlayerManager().getPlayer(senderId);
|
|
||||||
|
|
||||||
if (self == null) {
|
|
||||||
Unicopia.LOGGER.warn("[Unicopia] [CLIENT] [MsgPlayerCapabilities] Player with id %s was not found!\n", senderId.toString());
|
|
||||||
} else {
|
} else {
|
||||||
Pony player = Pony.of(self);
|
player.fromNBT(compoundTag);
|
||||||
|
|
||||||
if (compoundTag.length > 0) {
|
|
||||||
try (ByteArrayInputStream input = new ByteArrayInputStream(compoundTag)) {
|
|
||||||
CompoundTag nbt = NbtIo.read(new DataInputStream(input));
|
|
||||||
|
|
||||||
player.fromNBT(nbt);
|
|
||||||
} catch (IOException e) {
|
|
||||||
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
player.setSpecies(newRace);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,40 +1,38 @@
|
||||||
package com.minelittlepony.unicopia.network;
|
package com.minelittlepony.unicopia.network;
|
||||||
|
|
||||||
import java.util.UUID;
|
|
||||||
|
|
||||||
import com.google.gson.annotations.Expose;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Channel;
|
|
||||||
import com.minelittlepony.jumpingcastle.api.Message;
|
|
||||||
import com.minelittlepony.unicopia.Race;
|
import com.minelittlepony.unicopia.Race;
|
||||||
import com.minelittlepony.unicopia.Unicopia;
|
|
||||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||||
|
|
||||||
|
import net.fabricmc.fabric.api.network.PacketContext;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
import net.minecraft.server.MinecraftServer;
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
|
||||||
public class MsgRequestCapabilities implements Message, Message.Handler<MsgRequestCapabilities> {
|
public class MsgRequestCapabilities implements Channel.Packet {
|
||||||
@Expose
|
|
||||||
public UUID senderId;
|
|
||||||
|
|
||||||
@Expose
|
private final Race race;
|
||||||
public Race race;
|
|
||||||
|
public MsgRequestCapabilities(PacketByteBuf buffer) {
|
||||||
|
race = Race.values()[buffer.readInt()];
|
||||||
|
}
|
||||||
|
|
||||||
public MsgRequestCapabilities(PlayerEntity player, Race preferredRace) {
|
public MsgRequestCapabilities(PlayerEntity player, Race preferredRace) {
|
||||||
senderId = player.getGameProfile().getId();
|
|
||||||
race = preferredRace;
|
race = preferredRace;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onPayload(MsgRequestCapabilities message, Channel channel) {
|
public void toBuffer(PacketByteBuf buffer) {
|
||||||
MinecraftServer server = channel.getServer();
|
buffer.writeInt(race.ordinal());
|
||||||
|
}
|
||||||
|
|
||||||
Unicopia.LOGGER.warn("[Unicopia] [SERVER] [MsgRequestCapabilities] Sending capabilities to player %s\n", senderId.toString());
|
@Override
|
||||||
Pony player = Pony.of(server.getPlayerManager().getPlayer(senderId));
|
public void handle(PacketContext context) {
|
||||||
|
Pony player = Pony.of(context.getPlayer());
|
||||||
|
|
||||||
if (player.getSpecies().isDefault()) {
|
if (player.getSpecies().isDefault()) {
|
||||||
player.setSpecies(message.race);
|
player.setSpecies(race);
|
||||||
}
|
}
|
||||||
|
|
||||||
channel.respond(new MsgPlayerCapabilities(player), senderId);
|
Channel.PLAYER_CAPABILITIES.send(context.getPlayer(), new MsgPlayerCapabilities(true, player));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,52 @@
|
||||||
|
package com.minelittlepony.unicopia.network;
|
||||||
|
|
||||||
|
import com.minelittlepony.unicopia.entity.RainbowEntity;
|
||||||
|
import com.minelittlepony.unicopia.entity.UEntities;
|
||||||
|
import net.fabricmc.fabric.api.network.PacketContext;
|
||||||
|
import net.minecraft.client.MinecraftClient;
|
||||||
|
import net.minecraft.entity.Entity;
|
||||||
|
import net.minecraft.util.PacketByteBuf;
|
||||||
|
|
||||||
|
public class MsgSpawnRainbow implements Channel.Packet {
|
||||||
|
|
||||||
|
private final int id;
|
||||||
|
|
||||||
|
private final double x;
|
||||||
|
private final double y;
|
||||||
|
private final double z;
|
||||||
|
|
||||||
|
public MsgSpawnRainbow(Entity entity) {
|
||||||
|
id = entity.getEntityId();
|
||||||
|
x = entity.getX();
|
||||||
|
y = entity.getY();
|
||||||
|
z = entity.getZ();
|
||||||
|
}
|
||||||
|
|
||||||
|
public MsgSpawnRainbow(PacketByteBuf buffer) {
|
||||||
|
id = buffer.readVarInt();
|
||||||
|
x = buffer.readDouble();
|
||||||
|
y = buffer.readDouble();
|
||||||
|
z = buffer.readDouble();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void toBuffer(PacketByteBuf buffer) {
|
||||||
|
buffer.writeVarInt(id);
|
||||||
|
buffer.writeDouble(x);
|
||||||
|
buffer.writeDouble(y);
|
||||||
|
buffer.writeDouble(z);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void handle(PacketContext context) {
|
||||||
|
MinecraftClient client = MinecraftClient.getInstance();
|
||||||
|
|
||||||
|
RainbowEntity entity = UEntities.RAINBOW.create(client.world);
|
||||||
|
entity.setPos(x, y, z);
|
||||||
|
entity.updateTrackedPosition(x, y, z);
|
||||||
|
entity.yaw = 0;
|
||||||
|
entity.pitch = 0;
|
||||||
|
entity.setEntityId(id);
|
||||||
|
client.world.addEntity(id, entity);
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue