mirror of
https://github.com/MinecraftForge/MinecraftForge
synced 2026-08-22 04:26:10 -04:00
Fix mod packets being processed after vanilla packets when received in the same tick.
This commit is contained in:
parent
62fa5b26a7
commit
813b53a9f6
3 changed files with 34 additions and 1 deletions
|
|
@ -15,6 +15,7 @@ import java.util.List;
|
|||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.Optional;
|
||||
import java.util.function.BiConsumer;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.regex.Matcher;
|
||||
|
|
@ -54,6 +55,7 @@ import net.minecraft.core.particles.ParticleTypes;
|
|||
import net.minecraft.core.registries.Registries;
|
||||
import net.minecraft.network.Connection;
|
||||
import net.minecraft.network.FriendlyByteBuf;
|
||||
import net.minecraft.network.PacketListener;
|
||||
import net.minecraft.network.RegistryFriendlyByteBuf;
|
||||
import net.minecraft.network.VarInt;
|
||||
import net.minecraft.network.chat.ClickEvent;
|
||||
|
|
@ -105,6 +107,7 @@ import net.minecraft.nbt.CompoundTag;
|
|||
import net.minecraft.nbt.ListTag;
|
||||
import net.minecraft.network.protocol.Packet;
|
||||
import net.minecraft.network.protocol.PacketFlow;
|
||||
import net.minecraft.network.protocol.PacketType;
|
||||
import net.minecraft.network.protocol.common.custom.CustomPacketPayload;
|
||||
import net.minecraft.network.protocol.common.custom.DiscardedPayload;
|
||||
import net.minecraft.network.syncher.EntityDataSerializer;
|
||||
|
|
@ -1308,4 +1311,32 @@ public final class ForgeHooks {
|
|||
|
||||
return Optional.of(ret);
|
||||
}
|
||||
|
||||
// This is similar to PacketUtils.ensureRunningOnSameThread, we can't use the normal LogicalSidedProvider.WORKQUEUE because it is processed after packets.
|
||||
// So any vanilla packets that are received after this packet, will be processed before our enqueued packet.
|
||||
public static <MSG> void enqueuePacket(BiConsumer<MSG, CustomPayloadEvent.Context> handler, MSG packet, CustomPayloadEvent.Context context) {
|
||||
var processor = LogicalSidedProvider.PACKETS.get(context.isClientSide());
|
||||
if (!processor.isSameThread())
|
||||
processor.scheduleIfPossible(context.getConnection().getPacketListener(), new DummyPacket<>(handler, packet, context));
|
||||
else
|
||||
handler.accept(packet, context);
|
||||
}
|
||||
|
||||
private static final record DummyPacket<MSG>(
|
||||
BiConsumer<MSG, CustomPayloadEvent.Context> handler,
|
||||
MSG packet,
|
||||
CustomPayloadEvent.Context context
|
||||
) implements Packet<PacketListener> {
|
||||
private static final PacketType<DummyPacket<?>> TYPE = new PacketType<>(PacketFlow.CLIENTBOUND, ResourceLocation.fromNamespaceAndPath("forge", "dummy_for_schedualing"));
|
||||
|
||||
@Override
|
||||
public PacketType<DummyPacket<?>> type() {
|
||||
return TYPE;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handle(PacketListener listener) {
|
||||
handler.accept(packet, context);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -6,6 +6,7 @@
|
|||
package net.minecraftforge.common.util;
|
||||
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.network.PacketProcessor;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import net.minecraft.server.TickTask;
|
||||
import net.minecraft.util.thread.BlockableEventLoop;
|
||||
|
|
@ -21,6 +22,7 @@ import org.jetbrains.annotations.ApiStatus;
|
|||
public class LogicalSidedProvider<T> {
|
||||
public static final LogicalSidedProvider<BlockableEventLoop<? super TickTask>> WORKQUEUE = new LogicalSidedProvider<>(Supplier::get, Supplier::get);
|
||||
public static final LogicalSidedProvider<Optional<Level>> CLIENTWORLD = new LogicalSidedProvider<>((c)-> Optional.of(c.get().level), (s)->Optional.empty());
|
||||
public static final LogicalSidedProvider<PacketProcessor> PACKETS = new LogicalSidedProvider<>(client -> client.get().packetProcessor(), server -> server.get().packetProcessor());
|
||||
|
||||
public T get(LogicalSide side) {
|
||||
return side == LogicalSide.CLIENT ? clientSide.apply(client) : serverSide.apply(server);
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ public interface SimpleFlow<BUF extends FriendlyByteBuf, BASE> extends SimplePro
|
|||
*/
|
||||
default <MSG extends BASE> SimpleFlow<BUF, BASE> addMain(Class<MSG> type, StreamCodec<BUF, MSG> codec, BiConsumer<MSG, CustomPayloadEvent.Context> handler) {
|
||||
return add(type, codec, (msg, ctx) -> {
|
||||
ctx.enqueueWork(() -> handler.accept(msg, ctx));
|
||||
net.minecraftforge.common.ForgeHooks.enqueuePacket(handler, msg, ctx);
|
||||
ctx.setPacketHandled(true);
|
||||
});
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue