mirror of
https://github.com/Sollace/Unicopia.git
synced 2024-11-27 15:17:59 +01:00
Fixed compatibility with synatra connector
This commit is contained in:
parent
b3a46b0035
commit
253ff329c7
17 changed files with 88 additions and 96 deletions
|
@ -42,8 +42,8 @@ public record Race (
|
||||||
boolean canInteractWithClouds
|
boolean canInteractWithClouds
|
||||||
) implements Affine {
|
) implements Affine {
|
||||||
public static final String DEFAULT_ID = "unicopia:unset";
|
public static final String DEFAULT_ID = "unicopia:unset";
|
||||||
public static final Registry<Race> REGISTRY = RegistryUtils.createDefaulted(Unicopia.id("race"), DEFAULT_ID);
|
public static final Registry<Race> REGISTRY = RegistryUtils.createSynced(Unicopia.id("race"), DEFAULT_ID);
|
||||||
public static final Registry<Race> COMMAND_REGISTRY = RegistryUtils.createDefaulted(Unicopia.id("race/grantable"), DEFAULT_ID);
|
public static final Registry<Race> COMMAND_REGISTRY = RegistryUtils.createSynced(Unicopia.id("race/grantable"), DEFAULT_ID);
|
||||||
public static final RegistryKey<? extends Registry<Race>> REGISTRY_KEY = REGISTRY.getKey();
|
public static final RegistryKey<? extends Registry<Race>> REGISTRY_KEY = REGISTRY.getKey();
|
||||||
private static final DynamicCommandExceptionType UNKNOWN_RACE_EXCEPTION = new DynamicCommandExceptionType(id -> Text.translatable("commands.race.fail", id));
|
private static final DynamicCommandExceptionType UNKNOWN_RACE_EXCEPTION = new DynamicCommandExceptionType(id -> Text.translatable("commands.race.fail", id));
|
||||||
private static final Function<Race, Composite> COMPOSITES = Util.memoize(race -> new Composite(race, null, null));
|
private static final Function<Race, Composite> COMPOSITES = Util.memoize(race -> new Composite(race, null, null));
|
||||||
|
|
|
@ -18,7 +18,7 @@ import net.minecraft.network.codec.PacketCodecs;
|
||||||
import net.minecraft.registry.Registry;
|
import net.minecraft.registry.Registry;
|
||||||
|
|
||||||
public interface Abilities {
|
public interface Abilities {
|
||||||
Registry<Ability<?>> REGISTRY = RegistryUtils.createSimple(Unicopia.id("abilities"));
|
Registry<Ability<?>> REGISTRY = RegistryUtils.createSynced(Unicopia.id("abilities"));
|
||||||
PacketCodec<RegistryByteBuf, Ability<?>> PACKET_CODEC = PacketCodecs.registryValue(REGISTRY.getKey());
|
PacketCodec<RegistryByteBuf, Ability<?>> PACKET_CODEC = PacketCodecs.registryValue(REGISTRY.getKey());
|
||||||
Map<AbilitySlot, Set<Ability<?>>> BY_SLOT = new EnumMap<>(AbilitySlot.class);
|
Map<AbilitySlot, Set<Ability<?>>> BY_SLOT = new EnumMap<>(AbilitySlot.class);
|
||||||
BiFunction<AbilitySlot, Race.Composite, List<Ability<?>>> BY_SLOT_AND_COMPOSITE_RACE = Util.memoize((slot, race) -> {
|
BiFunction<AbilitySlot, Race.Composite, List<Ability<?>>> BY_SLOT_AND_COMPOSITE_RACE = Util.memoize((slot, race) -> {
|
||||||
|
|
|
@ -149,16 +149,14 @@ class MultiSpellSlot implements SpellSlots, NbtSerialisable {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void read(ByteBuf buffer, WrapperLookup lookup) {
|
public void read(RegistryByteBuf buffer, WrapperLookup lookup) {
|
||||||
byte contentType = buffer.readByte();
|
byte contentType = buffer.readByte();
|
||||||
if (contentType == 1) {
|
if (contentType == 1) {
|
||||||
readTrackedNbt(PacketCodecs.NBT_COMPOUND.decode(buffer), lookup);
|
readTrackedNbt(PacketCodecs.NBT_COMPOUND.decode(buffer), lookup);
|
||||||
} else {
|
} else {
|
||||||
T spell = this.spell.get();
|
T spell = this.spell.get();
|
||||||
if (spell != null) {
|
if (spell != null) {
|
||||||
spell.getDataTracker().load(MsgTrackedValues.TrackerEntries.PACKET_CODEC.decode(
|
spell.getDataTracker().load(MsgTrackedValues.TrackerEntries.PACKET_CODEC.decode(buffer), buffer.getRegistryManager());
|
||||||
buffer instanceof RegistryByteBuf r ? r : new RegistryByteBuf(buffer, owner.asEntity().getRegistryManager())
|
|
||||||
), lookup);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -44,13 +44,14 @@ import net.minecraft.server.command.ServerCommandSource;
|
||||||
|
|
||||||
public final class SpellType<T extends Spell> implements Affine, SpellPredicate<T> {
|
public final class SpellType<T extends Spell> implements Affine, SpellPredicate<T> {
|
||||||
public static final Identifier EMPTY_ID = Unicopia.id("none");
|
public static final Identifier EMPTY_ID = Unicopia.id("none");
|
||||||
public static final SpellType<?> EMPTY_KEY = builder(t -> null).affinity(Affinity.NEUTRAL).color(0xFFFFFF).unobtainable().build(EMPTY_ID);
|
|
||||||
|
|
||||||
public static final Registry<SpellType<?>> REGISTRY = RegistryUtils.createSimple(Unicopia.id("spells"));
|
public static final Registry<SpellType<?>> REGISTRY = RegistryUtils.createSynced(Unicopia.id("spells"), EMPTY_ID.toString());
|
||||||
public static final RegistryKey<? extends Registry<SpellType<?>>> REGISTRY_KEY = REGISTRY.getKey();
|
public static final RegistryKey<? extends Registry<SpellType<?>>> REGISTRY_KEY = REGISTRY.getKey();
|
||||||
public static final Codec<SpellType<?>> CODEC = REGISTRY.getCodec();
|
public static final Codec<SpellType<?>> CODEC = REGISTRY.getCodec();
|
||||||
public static final PacketCodec<RegistryByteBuf, SpellType<?>> PACKET_CODEC = PacketCodecs.registryValue(REGISTRY_KEY);
|
public static final PacketCodec<RegistryByteBuf, SpellType<?>> PACKET_CODEC = PacketCodecs.registryValue(REGISTRY_KEY);
|
||||||
|
|
||||||
|
public static final SpellType<?> EMPTY_KEY = register(EMPTY_ID.getPath(), builder(t -> null).affinity(Affinity.NEUTRAL).color(0xFFFFFF).unobtainable());
|
||||||
|
|
||||||
private static final DynamicCommandExceptionType UNKNOWN_SPELL_TYPE_EXCEPTION = new DynamicCommandExceptionType(id -> Text.translatable("spell_type.unknown", id));
|
private static final DynamicCommandExceptionType UNKNOWN_SPELL_TYPE_EXCEPTION = new DynamicCommandExceptionType(id -> Text.translatable("spell_type.unknown", id));
|
||||||
|
|
||||||
public static final SpellType<PlacementControlSpell> PLACE_CONTROL_SPELL = register("place_controller", SpellType.<PlacementControlSpell>builder(PlacementControlSpell::new).affinity(Affinity.NEUTRAL).unobtainable().stackable().shape(GemstoneItem.Shape.DONUT));
|
public static final SpellType<PlacementControlSpell> PLACE_CONTROL_SPELL = register("place_controller", SpellType.<PlacementControlSpell>builder(PlacementControlSpell::new).affinity(Affinity.NEUTRAL).unobtainable().stackable().shape(GemstoneItem.Shape.DONUT));
|
||||||
|
|
|
@ -15,7 +15,7 @@ import net.minecraft.util.Util;
|
||||||
|
|
||||||
public record AfflictionType<T extends Affliction>(Identifier id, MapCodec<T> codec, PacketCodec<? super RegistryByteBuf, T> packetCodec) {
|
public record AfflictionType<T extends Affliction>(Identifier id, MapCodec<T> codec, PacketCodec<? super RegistryByteBuf, T> packetCodec) {
|
||||||
public static final String DEFAULT_ID = "unicopia:apply_status_effect";
|
public static final String DEFAULT_ID = "unicopia:apply_status_effect";
|
||||||
public static final Registry<AfflictionType<?>> REGISTRY = RegistryUtils.createDefaulted(Unicopia.id("affliction_type"), DEFAULT_ID);
|
public static final Registry<AfflictionType<?>> REGISTRY = RegistryUtils.createSynced(Unicopia.id("affliction_type"), DEFAULT_ID);
|
||||||
public static final Codec<Affliction> CODEC = CodecUtils.apply(REGISTRY.getCodec()
|
public static final Codec<Affliction> CODEC = CodecUtils.apply(REGISTRY.getCodec()
|
||||||
.dispatch("type", Affliction::getType, AfflictionType::codec), elementCodec -> Codec
|
.dispatch("type", Affliction::getType, AfflictionType::codec), elementCodec -> Codec
|
||||||
.withAlternative(elementCodec, Codec.list(elementCodec), afflictions -> {
|
.withAlternative(elementCodec, Codec.list(elementCodec), afflictions -> {
|
||||||
|
|
|
@ -10,7 +10,7 @@ import net.minecraft.fluid.Fluids;
|
||||||
import net.minecraft.registry.tag.FluidTags;
|
import net.minecraft.registry.tag.FluidTags;
|
||||||
|
|
||||||
@Pseudo
|
@Pseudo
|
||||||
@Mixin(targets = "net.minecraftforge.common.extensions.IForgeBoat")
|
@Mixin(targets = "net.neoforged.neoforge.common.extensions.IAbstractBoatExtension")
|
||||||
interface MixinIForgeBoat {
|
interface MixinIForgeBoat {
|
||||||
@ModifyVariable(
|
@ModifyVariable(
|
||||||
method = "canBoatInFluid(Lnet/minecraft/fluid/FluidState;)Z",
|
method = "canBoatInFluid(Lnet/minecraft/fluid/FluidState;)Z",
|
||||||
|
|
|
@ -0,0 +1,15 @@
|
||||||
|
package com.minelittlepony.unicopia.mixin.forgified;
|
||||||
|
|
||||||
|
import java.util.function.Consumer;
|
||||||
|
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.Pseudo;
|
||||||
|
|
||||||
|
import net.minecraft.network.listener.ClientCommonPacketListener;
|
||||||
|
import net.minecraft.network.packet.Packet;
|
||||||
|
|
||||||
|
@Pseudo
|
||||||
|
@Mixin(targets = "net.neoforged.neoforge.network.bundle.PacketAndPayloadAcceptor")
|
||||||
|
interface MixinPacketAndPayloadAcceptor<L extends ClientCommonPacketListener> extends Consumer<Packet<? extends L>> {
|
||||||
|
|
||||||
|
}
|
|
@ -6,13 +6,13 @@ import org.spongepowered.asm.mixin.Final;
|
||||||
import org.spongepowered.asm.mixin.Mixin;
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
import org.spongepowered.asm.mixin.Shadow;
|
import org.spongepowered.asm.mixin.Shadow;
|
||||||
import org.spongepowered.asm.mixin.injection.At;
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Coerce;
|
||||||
import org.spongepowered.asm.mixin.injection.Inject;
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.network.track.Trackable;
|
import com.minelittlepony.unicopia.network.track.Trackable;
|
||||||
|
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
import net.minecraft.network.listener.ClientPlayPacketListener;
|
|
||||||
import net.minecraft.network.packet.Packet;
|
import net.minecraft.network.packet.Packet;
|
||||||
import net.minecraft.server.network.EntityTrackerEntry;
|
import net.minecraft.server.network.EntityTrackerEntry;
|
||||||
import net.minecraft.server.network.ServerPlayerEntity;
|
import net.minecraft.server.network.ServerPlayerEntity;
|
||||||
|
@ -29,8 +29,12 @@ abstract class MixinEntityTrackerEntry {
|
||||||
Trackable.of(entity).getDataTrackers().tick(this::sendSyncPacket);
|
Trackable.of(entity).getDataTrackers().tick(this::sendSyncPacket);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Inject(method = "sendPackets", at = @At("RETURN"))
|
@SuppressWarnings("unchecked")
|
||||||
private void unicopia_onSendPackets(ServerPlayerEntity player, Consumer<Packet<ClientPlayPacketListener>> sender, CallbackInfo info) {
|
@Inject(method = "sendPackets", at = @At("RETURN"), require = 0)
|
||||||
Trackable.of(entity).getDataTrackers().sendInitial(player, sender);
|
private void unicopia_onSendPackets(ServerPlayerEntity player, @Coerce Object sender, CallbackInfo info) {
|
||||||
|
// NEO: Consumer<Packet<ClientPlayPacketListener>> replaced with PacketAndPayloadAcceptor<ClientPlayPacketListener>
|
||||||
|
if (sender instanceof Consumer s) {
|
||||||
|
Trackable.of(entity).getDataTrackers().sendInitial(player, s);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,10 +42,14 @@ abstract class MixinServerPlayerEntity extends PlayerEntity implements ScreenHan
|
||||||
get().copyFrom(((Equine.Container<Pony>)oldPlayer).get(), alive);
|
get().copyFrom(((Equine.Container<Pony>)oldPlayer).get(), alive);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Inject(method = "trySleep(Lnet/minecraft/util/math/BlockPos;)Lcom/mojang/datafixers/util/Either;", at = @At(
|
@Inject(method = {
|
||||||
|
"trySleep(Lnet/minecraft/util/math/BlockPos;)Lcom/mojang/datafixers/util/Either;",
|
||||||
|
// NEO: https://github.com/neoforged/NeoForge/blob/62eb61a8e0c726faa30eaa3f4998ba1101368ee4/patches/net/minecraft/server/level/ServerPlayer.java.patch#L77
|
||||||
|
"lambda$0()Lcom/mojang/datafixers/util/Either;"
|
||||||
|
}, at = @At(
|
||||||
value = "FIELD",
|
value = "FIELD",
|
||||||
target = "net/minecraft/entity/player/PlayerEntity$SleepFailureReason.NOT_POSSIBLE_NOW:Lnet/minecraft/entity/player/PlayerEntity$SleepFailureReason;"
|
target = "net/minecraft/entity/player/PlayerEntity$SleepFailureReason.NOT_POSSIBLE_NOW:Lnet/minecraft/entity/player/PlayerEntity$SleepFailureReason;"
|
||||||
), cancellable = true)
|
), cancellable = true, require = 0)
|
||||||
private void onTrySleep(BlockPos pos, CallbackInfoReturnable<Either<PlayerEntity.SleepFailureReason, Unit>> info) {
|
private void onTrySleep(BlockPos pos, CallbackInfoReturnable<Either<PlayerEntity.SleepFailureReason, Unit>> info) {
|
||||||
if (get().getSpecies().isNocturnal() && get().asWorld().getGameRules().getBoolean(UGameRules.DO_NOCTURNAL_BAT_PONIES)) {
|
if (get().getSpecies().isNocturnal() && get().asWorld().getGameRules().getBoolean(UGameRules.DO_NOCTURNAL_BAT_PONIES)) {
|
||||||
((PlayerEntity)this).sendMessage(Text.translatable("block.unicopia.bed.no_sleep.nocturnal"), true);
|
((PlayerEntity)this).sendMessage(Text.translatable("block.unicopia.bed.no_sleep.nocturnal"), true);
|
||||||
|
|
|
@ -9,13 +9,14 @@ import java.util.Optional;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.util.Untyped;
|
import com.minelittlepony.unicopia.util.Untyped;
|
||||||
|
|
||||||
import io.netty.buffer.ByteBuf;
|
import io.netty.buffer.Unpooled;
|
||||||
import it.unimi.dsi.fastutil.ints.IntOpenHashSet;
|
import it.unimi.dsi.fastutil.ints.IntOpenHashSet;
|
||||||
import it.unimi.dsi.fastutil.ints.IntSet;
|
import it.unimi.dsi.fastutil.ints.IntSet;
|
||||||
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
|
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
|
||||||
import net.minecraft.network.RegistryByteBuf;
|
import net.minecraft.network.RegistryByteBuf;
|
||||||
import net.minecraft.network.codec.PacketCodec;
|
import net.minecraft.network.codec.PacketCodec;
|
||||||
import net.minecraft.network.codec.PacketCodecs;
|
import net.minecraft.network.codec.PacketCodecs;
|
||||||
|
import net.minecraft.registry.DynamicRegistryManager;
|
||||||
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
||||||
|
|
||||||
public class DataTracker {
|
public class DataTracker {
|
||||||
|
@ -86,7 +87,7 @@ public class DataTracker {
|
||||||
return getInitialPairs(lookup);
|
return getInitialPairs(lookup);
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<Integer, ByteBuf> updates = writePersistentObjects(lookup, false);
|
Map<Integer, byte[]> updates = writePersistentObjects(lookup, false);
|
||||||
|
|
||||||
if (dirtyIndices.isEmpty() && updates.isEmpty()) {
|
if (dirtyIndices.isEmpty() && updates.isEmpty()) {
|
||||||
return Optional.empty();
|
return Optional.empty();
|
||||||
|
@ -98,21 +99,21 @@ public class DataTracker {
|
||||||
for (int i : toSend) {
|
for (int i : toSend) {
|
||||||
pairs.add(codecs.get(i));
|
pairs.add(codecs.get(i));
|
||||||
}
|
}
|
||||||
return Optional.of(new MsgTrackedValues.TrackerEntries(id, false, pairs, Untyped.cast(updates)));
|
return Optional.of(new MsgTrackedValues.TrackerEntries(id, false, pairs, updates));
|
||||||
}
|
}
|
||||||
|
|
||||||
private Map<Integer, ByteBuf> writePersistentObjects(WrapperLookup lookup, boolean initial) {
|
private Map<Integer, byte[]> writePersistentObjects(WrapperLookup lookup, boolean initial) {
|
||||||
Map<Integer, ByteBuf> updates = new HashMap<>();
|
Map<Integer, byte[]> updates = new HashMap<>();
|
||||||
for (int i = 0; i < persistentObjects.size(); i++) {
|
for (int i = 0; i < persistentObjects.size(); i++) {
|
||||||
TrackableObject<?> o = persistentObjects.get(i);
|
TrackableObject<?> o = persistentObjects.get(i);
|
||||||
TrackableObject.Status status = initial ? TrackableObject.Status.NEW : o.getStatus();
|
TrackableObject.Status status = initial ? TrackableObject.Status.NEW : o.getStatus();
|
||||||
int id = i;
|
int id = i;
|
||||||
o.write(status, lookup).ifPresent(data -> updates.put(id, data));
|
o.write(status, lookup).ifPresent(data -> updates.put(id, data.copy().array()));
|
||||||
}
|
}
|
||||||
return updates;
|
return updates;
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized void load(MsgTrackedValues.TrackerEntries values, WrapperLookup lookup) {
|
public synchronized void load(MsgTrackedValues.TrackerEntries values, DynamicRegistryManager lookup) {
|
||||||
if (values.wipe()) {
|
if (values.wipe()) {
|
||||||
codecs.clear();
|
codecs.clear();
|
||||||
codecs.addAll(values.values());
|
codecs.addAll(values.values());
|
||||||
|
@ -129,7 +130,7 @@ public class DataTracker {
|
||||||
for (var entry : values.objects().entrySet()) {
|
for (var entry : values.objects().entrySet()) {
|
||||||
TrackableObject<?> o = persistentObjects.get(entry.getKey());
|
TrackableObject<?> o = persistentObjects.get(entry.getKey());
|
||||||
if (o != null) {
|
if (o != null) {
|
||||||
o.read(entry.getValue(), lookup);
|
o.read(new RegistryByteBuf(Unpooled.wrappedBuffer(entry.getValue()), lookup), lookup);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,16 +6,17 @@ import java.util.function.Consumer;
|
||||||
import java.util.function.Supplier;
|
import java.util.function.Supplier;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.network.Channel;
|
import com.minelittlepony.unicopia.network.Channel;
|
||||||
|
|
||||||
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
|
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
import net.minecraft.network.listener.ClientPlayPacketListener;
|
import net.minecraft.network.listener.ClientPlayPacketListener;
|
||||||
import net.minecraft.network.packet.Packet;
|
import net.minecraft.network.packet.Packet;
|
||||||
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
import net.minecraft.registry.DynamicRegistryManager;
|
||||||
import net.minecraft.server.network.ServerPlayerEntity;
|
import net.minecraft.server.network.ServerPlayerEntity;
|
||||||
|
|
||||||
public class DataTrackerManager {
|
public class DataTrackerManager {
|
||||||
private final Entity entity;
|
private final Entity entity;
|
||||||
private final WrapperLookup lookup;
|
private final DynamicRegistryManager lookup;
|
||||||
final boolean isClient;
|
final boolean isClient;
|
||||||
private final List<DataTracker> trackers = new ObjectArrayList<>();
|
private final List<DataTracker> trackers = new ObjectArrayList<>();
|
||||||
private final List<ObjectTracker<?>> objectTrackers = new ObjectArrayList<>();
|
private final List<ObjectTracker<?>> objectTrackers = new ObjectArrayList<>();
|
||||||
|
@ -44,13 +45,11 @@ public class DataTrackerManager {
|
||||||
packetEmitters.add((sender, initial) -> {
|
packetEmitters.add((sender, initial) -> {
|
||||||
var update = initial ? tracker.getInitialPairs(lookup) : tracker.getDirtyPairs(lookup);
|
var update = initial ? tracker.getInitialPairs(lookup) : tracker.getDirtyPairs(lookup);
|
||||||
if (update.isPresent()) {
|
if (update.isPresent()) {
|
||||||
try (var payload = new MsgTrackedValues(
|
sender.accept(Channel.SERVER_TRACKED_ENTITY_DATA.toPacket(new MsgTrackedValues(
|
||||||
entity.getId(),
|
entity.getId(),
|
||||||
Optional.empty(),
|
Optional.empty(),
|
||||||
update
|
update
|
||||||
)) {
|
)));
|
||||||
sender.accept(Channel.SERVER_TRACKED_ENTITY_DATA.toPacket(payload));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return tracker;
|
return tracker;
|
||||||
|
@ -62,13 +61,11 @@ public class DataTrackerManager {
|
||||||
packetEmitters.add((sender, initial) -> {
|
packetEmitters.add((sender, initial) -> {
|
||||||
var update = initial ? tracker.getInitialPairs(lookup) : tracker.getDirtyPairs(lookup);
|
var update = initial ? tracker.getInitialPairs(lookup) : tracker.getDirtyPairs(lookup);
|
||||||
if (update.isPresent()) {
|
if (update.isPresent()) {
|
||||||
try (var payload = new MsgTrackedValues(
|
sender.accept(Channel.SERVER_TRACKED_ENTITY_DATA.toPacket(new MsgTrackedValues(
|
||||||
entity.getId(),
|
entity.getId(),
|
||||||
update,
|
update,
|
||||||
Optional.empty()
|
Optional.empty()
|
||||||
)) {
|
)));
|
||||||
sender.accept(Channel.SERVER_TRACKED_ENTITY_DATA.toPacket(payload));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return tracker;
|
return tracker;
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
package com.minelittlepony.unicopia.network.track;
|
package com.minelittlepony.unicopia.network.track;
|
||||||
|
|
||||||
import java.io.Closeable;
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.HashSet;
|
import java.util.HashSet;
|
||||||
|
@ -10,10 +9,8 @@ import java.util.Optional;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.util.serialization.PacketCodecUtils;
|
|
||||||
import com.sollace.fabwork.api.packets.Handled;
|
import com.sollace.fabwork.api.packets.Handled;
|
||||||
|
|
||||||
import io.netty.buffer.ByteBuf;
|
|
||||||
import net.minecraft.entity.Entity;
|
import net.minecraft.entity.Entity;
|
||||||
import net.minecraft.entity.player.PlayerEntity;
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
import net.minecraft.network.RegistryByteBuf;
|
import net.minecraft.network.RegistryByteBuf;
|
||||||
|
@ -25,7 +22,7 @@ public record MsgTrackedValues(
|
||||||
int owner,
|
int owner,
|
||||||
Optional<TrackerObjects> updatedObjects,
|
Optional<TrackerObjects> updatedObjects,
|
||||||
Optional<TrackerEntries> updatedTrackers
|
Optional<TrackerEntries> updatedTrackers
|
||||||
) implements Handled<PlayerEntity>, AutoCloseable {
|
) implements Handled<PlayerEntity> {
|
||||||
public static final PacketCodec<RegistryByteBuf, MsgTrackedValues> PACKET_CODEC = PacketCodec.tuple(
|
public static final PacketCodec<RegistryByteBuf, MsgTrackedValues> PACKET_CODEC = PacketCodec.tuple(
|
||||||
PacketCodecs.INTEGER, MsgTrackedValues::owner,
|
PacketCodecs.INTEGER, MsgTrackedValues::owner,
|
||||||
PacketCodecs.optional(TrackerObjects.PACKET_CODEC), MsgTrackedValues::updatedObjects,
|
PacketCodecs.optional(TrackerObjects.PACKET_CODEC), MsgTrackedValues::updatedObjects,
|
||||||
|
@ -35,54 +32,28 @@ public record MsgTrackedValues(
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void handle(PlayerEntity sender) {
|
public void handle(PlayerEntity sender) {
|
||||||
try (this) {
|
Entity entity = sender.getWorld().getEntityById(owner);
|
||||||
Entity entity = sender.getWorld().getEntityById(owner);
|
if (entity instanceof Trackable trackable) {
|
||||||
if (entity instanceof Trackable trackable) {
|
trackable.getDataTrackers().load(this);
|
||||||
trackable.getDataTrackers().load(this);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public record TrackerObjects(int id, Set<UUID> removedValues, Map<UUID, ByteBuf> values) implements Closeable {
|
public record TrackerObjects(int id, Set<UUID> removedValues, Map<UUID, byte[]> values) {
|
||||||
public static final PacketCodec<RegistryByteBuf, TrackerObjects> PACKET_CODEC = PacketCodec.tuple(
|
public static final PacketCodec<RegistryByteBuf, TrackerObjects> PACKET_CODEC = PacketCodec.tuple(
|
||||||
PacketCodecs.INTEGER, TrackerObjects::id,
|
PacketCodecs.INTEGER, TrackerObjects::id,
|
||||||
Uuids.PACKET_CODEC.collect(PacketCodecs.toCollection(HashSet::new)), TrackerObjects::removedValues,
|
Uuids.PACKET_CODEC.collect(PacketCodecs.toCollection(HashSet::new)), TrackerObjects::removedValues,
|
||||||
PacketCodecs.map(HashMap::new, Uuids.PACKET_CODEC, PacketCodecUtils.REGISTRY_BUFFER), TrackerObjects::values,
|
PacketCodecs.map(HashMap::new, Uuids.PACKET_CODEC, PacketCodecs.BYTE_ARRAY), TrackerObjects::values,
|
||||||
TrackerObjects::new
|
TrackerObjects::new
|
||||||
);
|
);
|
||||||
|
|
||||||
@Override
|
|
||||||
public void close() {
|
|
||||||
values.values().forEach(buf -> {
|
|
||||||
if (buf.refCnt() > 0) {
|
|
||||||
buf.release();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public record TrackerEntries(int id, boolean wipe, List<DataTracker.Pair<?>> values, Map<Integer, ByteBuf> objects) implements Closeable {
|
public record TrackerEntries(int id, boolean wipe, List<DataTracker.Pair<?>> values, Map<Integer, byte[]> objects) {
|
||||||
public static final PacketCodec<RegistryByteBuf, TrackerEntries> PACKET_CODEC = PacketCodec.tuple(
|
public static final PacketCodec<RegistryByteBuf, TrackerEntries> PACKET_CODEC = PacketCodec.tuple(
|
||||||
PacketCodecs.INTEGER, TrackerEntries::id,
|
PacketCodecs.INTEGER, TrackerEntries::id,
|
||||||
PacketCodecs.BOOL, TrackerEntries::wipe,
|
PacketCodecs.BOOL, TrackerEntries::wipe,
|
||||||
DataTracker.Pair.PACKET_CODEC.collect(PacketCodecs.toCollection(ArrayList::new)), TrackerEntries::values,
|
DataTracker.Pair.PACKET_CODEC.collect(PacketCodecs.toCollection(ArrayList::new)), TrackerEntries::values,
|
||||||
PacketCodecs.map(HashMap::new, PacketCodecs.INTEGER, PacketCodecUtils.REGISTRY_BUFFER), TrackerEntries::objects,
|
PacketCodecs.map(HashMap::new, PacketCodecs.INTEGER, PacketCodecs.BYTE_ARRAY), TrackerEntries::objects,
|
||||||
TrackerEntries::new
|
TrackerEntries::new
|
||||||
);
|
);
|
||||||
|
|
||||||
@Override
|
|
||||||
public void close() {
|
|
||||||
objects.values().forEach(buf -> {
|
|
||||||
if (buf.refCnt() > 0) {
|
|
||||||
buf.release();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void close() {
|
|
||||||
updatedObjects.ifPresent(TrackerObjects::close);
|
|
||||||
updatedObjects.ifPresent(TrackerObjects::close);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,8 +12,10 @@ import java.util.function.Supplier;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
import com.minelittlepony.unicopia.network.track.TrackableObject.Status;
|
import com.minelittlepony.unicopia.network.track.TrackableObject.Status;
|
||||||
import io.netty.buffer.ByteBuf;
|
import io.netty.buffer.Unpooled;
|
||||||
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
||||||
|
import net.minecraft.network.RegistryByteBuf;
|
||||||
|
import net.minecraft.registry.DynamicRegistryManager;
|
||||||
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
||||||
|
|
||||||
public class ObjectTracker<T extends TrackableObject<T>> {
|
public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
|
@ -89,10 +91,10 @@ public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
return Optional.empty();
|
return Optional.empty();
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<UUID, ByteBuf> updates = new HashMap<>();
|
Map<UUID, byte[]> updates = new HashMap<>();
|
||||||
quickAccess.entrySet().forEach(object -> {
|
quickAccess.entrySet().forEach(object -> {
|
||||||
object.getValue().write(Status.NEW, lookup).ifPresent(data -> {
|
object.getValue().write(Status.NEW, lookup).ifPresent(data -> {
|
||||||
updates.put(object.getKey(), data);
|
updates.put(object.getKey(), data.copy().array());
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -101,7 +103,7 @@ public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
|
|
||||||
synchronized Optional<MsgTrackedValues.TrackerObjects> getDirtyPairs(WrapperLookup lookup) {
|
synchronized Optional<MsgTrackedValues.TrackerObjects> getDirtyPairs(WrapperLookup lookup) {
|
||||||
if (!trackedObjects.isEmpty()) {
|
if (!trackedObjects.isEmpty()) {
|
||||||
Map<UUID, ByteBuf> updates = new HashMap<>();
|
Map<UUID, byte[]> updates = new HashMap<>();
|
||||||
Set<UUID> removedTrackableObjects = new HashSet<>();
|
Set<UUID> removedTrackableObjects = new HashSet<>();
|
||||||
trackedObjects.entrySet().removeIf(object -> {
|
trackedObjects.entrySet().removeIf(object -> {
|
||||||
TrackableObject.Status status = object.getValue().getStatus();
|
TrackableObject.Status status = object.getValue().getStatus();
|
||||||
|
@ -110,7 +112,7 @@ public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
object.getValue().write(status, lookup).ifPresent(data -> {
|
object.getValue().write(status, lookup).ifPresent(data -> {
|
||||||
updates.put(object.getKey(), data);
|
updates.put(object.getKey(), data.copy().array());
|
||||||
});
|
});
|
||||||
return false;
|
return false;
|
||||||
});
|
});
|
||||||
|
@ -124,7 +126,7 @@ public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
return Optional.empty();
|
return Optional.empty();
|
||||||
}
|
}
|
||||||
|
|
||||||
synchronized void load(MsgTrackedValues.TrackerObjects objects, WrapperLookup lookup) {
|
synchronized void load(MsgTrackedValues.TrackerObjects objects, DynamicRegistryManager lookup) {
|
||||||
objects.removedValues().forEach(removedId -> {
|
objects.removedValues().forEach(removedId -> {
|
||||||
T o = trackedObjects.remove(removedId);
|
T o = trackedObjects.remove(removedId);
|
||||||
if (o != null) {
|
if (o != null) {
|
||||||
|
@ -137,7 +139,8 @@ public class ObjectTracker<T extends TrackableObject<T>> {
|
||||||
o = constructor.get();
|
o = constructor.get();
|
||||||
trackedObjects.put(id, o);
|
trackedObjects.put(id, o);
|
||||||
}
|
}
|
||||||
o.read(data, lookup);
|
|
||||||
|
o.read(new RegistryByteBuf(Unpooled.wrappedBuffer(data), lookup), lookup);
|
||||||
});
|
});
|
||||||
quickAccess = Map.copyOf(trackedObjects);
|
quickAccess = Map.copyOf(trackedObjects);
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,13 +5,14 @@ import java.util.Optional;
|
||||||
import io.netty.buffer.ByteBuf;
|
import io.netty.buffer.ByteBuf;
|
||||||
import io.netty.buffer.Unpooled;
|
import io.netty.buffer.Unpooled;
|
||||||
import net.minecraft.nbt.NbtCompound;
|
import net.minecraft.nbt.NbtCompound;
|
||||||
|
import net.minecraft.network.RegistryByteBuf;
|
||||||
import net.minecraft.network.codec.PacketCodecs;
|
import net.minecraft.network.codec.PacketCodecs;
|
||||||
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
import net.minecraft.registry.RegistryWrapper.WrapperLookup;
|
||||||
|
|
||||||
public interface TrackableObject<T extends TrackableObject<T>> {
|
public interface TrackableObject<T extends TrackableObject<T>> {
|
||||||
Status getStatus();
|
Status getStatus();
|
||||||
|
|
||||||
default void read(ByteBuf buffer, WrapperLookup lookup) {
|
default void read(RegistryByteBuf buffer, WrapperLookup lookup) {
|
||||||
readTrackedNbt(PacketCodecs.NBT_COMPOUND.decode(buffer), lookup);
|
readTrackedNbt(PacketCodecs.NBT_COMPOUND.decode(buffer), lookup);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,6 +8,7 @@ import com.google.common.base.Predicates;
|
||||||
import com.mojang.serialization.Lifecycle;
|
import com.mojang.serialization.Lifecycle;
|
||||||
|
|
||||||
import net.fabricmc.fabric.api.event.registry.FabricRegistryBuilder;
|
import net.fabricmc.fabric.api.event.registry.FabricRegistryBuilder;
|
||||||
|
import net.fabricmc.fabric.api.event.registry.RegistryAttribute;
|
||||||
import net.minecraft.registry.tag.TagKey;
|
import net.minecraft.registry.tag.TagKey;
|
||||||
import net.minecraft.util.Identifier;
|
import net.minecraft.util.Identifier;
|
||||||
import net.minecraft.util.Util;
|
import net.minecraft.util.Util;
|
||||||
|
@ -22,8 +23,16 @@ public interface RegistryUtils {
|
||||||
return FabricRegistryBuilder.from(new SimpleRegistry<T>(RegistryKey.ofRegistry(id), Lifecycle.stable())).buildAndRegister();
|
return FabricRegistryBuilder.from(new SimpleRegistry<T>(RegistryKey.ofRegistry(id), Lifecycle.stable())).buildAndRegister();
|
||||||
}
|
}
|
||||||
|
|
||||||
static <T> Registry<T> createDefaulted(Identifier id, String def) {
|
static <T> Registry<T> createSynced(Identifier id) {
|
||||||
return FabricRegistryBuilder.from(new SimpleDefaultedRegistry<T>(def, RegistryKey.ofRegistry(id), Lifecycle.stable(), false)).buildAndRegister();
|
return FabricRegistryBuilder.from(new SimpleRegistry<T>(RegistryKey.ofRegistry(id), Lifecycle.stable()))
|
||||||
|
.attribute(RegistryAttribute.SYNCED)
|
||||||
|
.buildAndRegister();
|
||||||
|
}
|
||||||
|
|
||||||
|
static <T> Registry<T> createSynced(Identifier id, String def) {
|
||||||
|
return FabricRegistryBuilder.from(new SimpleDefaultedRegistry<T>(def, RegistryKey.ofRegistry(id), Lifecycle.stable(), false))
|
||||||
|
.attribute(RegistryAttribute.SYNCED)
|
||||||
|
.buildAndRegister();
|
||||||
}
|
}
|
||||||
|
|
||||||
static <T> RegistryEntryList<T> entriesForTag(World world, TagKey<T> key) {
|
static <T> RegistryEntryList<T> entriesForTag(World world, TagKey<T> key) {
|
||||||
|
|
|
@ -9,9 +9,7 @@ import java.util.function.Function;
|
||||||
import java.util.function.IntFunction;
|
import java.util.function.IntFunction;
|
||||||
|
|
||||||
import io.netty.buffer.ByteBuf;
|
import io.netty.buffer.ByteBuf;
|
||||||
import io.netty.buffer.Unpooled;
|
|
||||||
import net.minecraft.network.PacketByteBuf;
|
import net.minecraft.network.PacketByteBuf;
|
||||||
import net.minecraft.network.RegistryByteBuf;
|
|
||||||
import net.minecraft.network.codec.PacketCodec;
|
import net.minecraft.network.codec.PacketCodec;
|
||||||
import net.minecraft.network.codec.PacketCodecs;
|
import net.minecraft.network.codec.PacketCodecs;
|
||||||
import net.minecraft.registry.RegistryKey;
|
import net.minecraft.registry.RegistryKey;
|
||||||
|
@ -21,17 +19,6 @@ import net.minecraft.util.math.BlockPos;
|
||||||
import net.minecraft.util.math.Vec3d;
|
import net.minecraft.util.math.Vec3d;
|
||||||
|
|
||||||
public interface PacketCodecUtils {
|
public interface PacketCodecUtils {
|
||||||
PacketCodec<RegistryByteBuf, ByteBuf> REGISTRY_BUFFER = PacketCodec.of((bytes, buffer) -> {
|
|
||||||
int length = bytes.readableBytes();
|
|
||||||
buffer.writeInt(length);
|
|
||||||
if (length > 0) {
|
|
||||||
buffer.writeBytes(bytes, 0, length);
|
|
||||||
}
|
|
||||||
}, buffer -> {
|
|
||||||
int length = buffer.readInt();
|
|
||||||
return new RegistryByteBuf(length > 0 ? buffer.readBytes(length) : Unpooled.EMPTY_BUFFER, buffer.getRegistryManager());
|
|
||||||
});
|
|
||||||
|
|
||||||
PacketCodec<PacketByteBuf, RegistryKey<?>> REGISTRY_KEY = PacketCodec.tuple(
|
PacketCodec<PacketByteBuf, RegistryKey<?>> REGISTRY_KEY = PacketCodec.tuple(
|
||||||
Identifier.PACKET_CODEC, RegistryKey::getRegistry,
|
Identifier.PACKET_CODEC, RegistryKey::getRegistry,
|
||||||
Identifier.PACKET_CODEC, RegistryKey::getValue,
|
Identifier.PACKET_CODEC, RegistryKey::getValue,
|
||||||
|
|
|
@ -85,7 +85,8 @@
|
||||||
"seasons.MixinFertilizableUtil",
|
"seasons.MixinFertilizableUtil",
|
||||||
"ad_astra.MixinApiHelper",
|
"ad_astra.MixinApiHelper",
|
||||||
"ad_astra.MixinOxygenApi",
|
"ad_astra.MixinOxygenApi",
|
||||||
"forgified.MixinIForgeBoat"
|
"forgified.MixinIForgeBoat",
|
||||||
|
"forgified.MixinPacketAndPayloadAcceptor"
|
||||||
],
|
],
|
||||||
"client": [
|
"client": [
|
||||||
"client.MixinAnimalModel",
|
"client.MixinAnimalModel",
|
||||||
|
|
Loading…
Reference in a new issue