diff --git a/patches/minecraft/net/minecraft/entity/Entity.java.patch b/patches/minecraft/net/minecraft/entity/Entity.java.patch index e0e69e3ef4..da3f54f010 100644 --- a/patches/minecraft/net/minecraft/entity/Entity.java.patch +++ b/patches/minecraft/net/minecraft/entity/Entity.java.patch @@ -129,7 +129,7 @@ this.field_70126_B -= 360.0F; } -+ if (!this.field_70170_p.field_72995_K) this.field_70170_p.func_212866_a_((int) Math.floor(this.field_70165_t) >> 4, (int) Math.floor(this.field_70161_v) >> 4); // Forge - ensure target chunk is loaded. ++ if (!this.field_70170_p.field_72995_K && this.func_70089_S()) this.field_70170_p.func_212866_a_((int) Math.floor(this.field_70165_t) >> 4, (int) Math.floor(this.field_70161_v) >> 4); // Forge - ensure target chunk is loaded. this.func_70107_b(this.field_70165_t, this.field_70163_u, this.field_70161_v); this.func_70101_b(p_70080_7_, p_70080_8_); } diff --git a/patches/minecraft/net/minecraft/network/play/ServerPlayNetHandler.java.patch b/patches/minecraft/net/minecraft/network/play/ServerPlayNetHandler.java.patch index b5b0f08ef9..5368101d4d 100644 --- a/patches/minecraft/net/minecraft/network/play/ServerPlayNetHandler.java.patch +++ b/patches/minecraft/net/minecraft/network/play/ServerPlayNetHandler.java.patch @@ -1,17 +1,14 @@ --- a/net/minecraft/network/play/ServerPlayNetHandler.java +++ b/net/minecraft/network/play/ServerPlayNetHandler.java -@@ -180,8 +180,10 @@ +@@ -180,6 +180,7 @@ public void func_73660_a() { this.func_184342_d(); -+ if (this.field_147369_b.func_70089_S()) { //Don't tick players while they are dead/respawning. ++ if (this.field_147369_b.func_70089_S()) //Don't tick players while they are dead/respawning. this.field_147369_b.func_71127_g(); this.field_147369_b.func_70080_a(this.field_184349_l, this.field_184350_m, this.field_184351_n, this.field_147369_b.field_70177_z, this.field_147369_b.field_70125_A); -+ } ++this.field_147368_e; - this.field_184348_G = this.field_184347_F; - if (this.field_184344_B) { -@@ -337,9 +339,11 @@ +@@ -337,9 +338,11 @@ } entity.func_70080_a(d3, d4, d5, f, f1); @@ -23,7 +20,7 @@ this.field_147371_a.func_179290_a(new SMoveVehiclePacket(entity)); return; } -@@ -839,7 +843,9 @@ +@@ -839,7 +842,9 @@ Direction direction = blockraytraceresult.func_216354_b(); this.field_147369_b.func_143004_u(); if (blockpos.func_177956_o() < this.field_147367_d.func_71207_Z() - 1 || direction != Direction.UP && blockpos.func_177956_o() < this.field_147367_d.func_71207_Z()) { @@ -34,7 +31,7 @@ this.field_147369_b.field_71134_c.func_219441_a(this.field_147369_b, serverworld, itemstack, hand, blockraytraceresult); } } else { -@@ -959,7 +965,9 @@ +@@ -959,7 +964,9 @@ if (s.startsWith("/")) { this.func_147361_d(s); } else { @@ -45,7 +42,7 @@ this.field_147367_d.func_184103_al().func_148544_a(itextcomponent, false); } -@@ -1057,6 +1065,7 @@ +@@ -1057,6 +1064,7 @@ this.field_147369_b.func_190775_a(entity, hand); } else if (p_147340_1_.func_149565_c() == CUseEntityPacket.Action.INTERACT_AT) { Hand hand1 = p_147340_1_.func_186994_b(); @@ -53,7 +50,7 @@ entity.func_184199_a(this.field_147369_b, p_147340_1_.func_179712_b(), hand1); } else if (p_147340_1_.func_149565_c() == CUseEntityPacket.Action.ATTACK) { if (entity instanceof ItemEntity || entity instanceof ExperienceOrbEntity || entity instanceof AbstractArrowEntity || entity == this.field_147369_b) { -@@ -1087,7 +1096,7 @@ +@@ -1087,7 +1095,7 @@ return; } @@ -62,7 +59,7 @@ if (this.field_147367_d.func_71199_h()) { this.field_147369_b.func_71033_a(GameType.SPECTATOR); this.field_147369_b.func_71121_q().func_82736_K().func_223585_a(GameRules.field_223613_p).func_223570_a(false, this.field_147367_d); -@@ -1264,6 +1273,8 @@ +@@ -1264,6 +1272,8 @@ } public void func_147349_a(CCustomPayloadPacket p_147349_1_) { diff --git a/patches/minecraft/net/minecraft/server/management/PlayerList.java.patch b/patches/minecraft/net/minecraft/server/management/PlayerList.java.patch index cb91edb52f..d21b367998 100644 --- a/patches/minecraft/net/minecraft/server/management/PlayerList.java.patch +++ b/patches/minecraft/net/minecraft/server/management/PlayerList.java.patch @@ -1,6 +1,14 @@ --- a/net/minecraft/server/management/PlayerList.java +++ b/net/minecraft/server/management/PlayerList.java -@@ -110,6 +110,14 @@ +@@ -94,6 +94,7 @@ + private GameType field_72410_m; + private boolean field_72407_n; + private int field_72408_o; ++ private final List playersView = java.util.Collections.unmodifiableList(field_72404_b); + + public PlayerList(MinecraftServer p_i50688_1_, int p_i50688_2_) { + this.field_72400_f = p_i50688_1_; +@@ -110,6 +111,14 @@ playerprofilecache.func_152649_a(gameprofile); CompoundNBT compoundnbt = this.func_72380_a(p_72355_2_); ServerWorld serverworld = this.field_72400_f.func_71218_a(p_72355_2_.field_71093_bK); @@ -15,7 +23,16 @@ p_72355_2_.func_70029_a(serverworld); p_72355_2_.field_71134_c.func_73080_a((ServerWorld)p_72355_2_.field_70170_p); String s1 = "local"; -@@ -163,8 +171,9 @@ +@@ -142,7 +151,7 @@ + + this.func_148539_a(itextcomponent.func_211708_a(TextFormatting.YELLOW)); + serverplaynethandler.func_147364_a(p_72355_2_.field_70165_t, p_72355_2_.field_70163_u, p_72355_2_.field_70161_v, p_72355_2_.field_70177_z, p_72355_2_.field_70125_A); +- this.field_72404_b.add(p_72355_2_); ++ this.addPlayer(p_72355_2_); + this.field_177454_f.put(p_72355_2_.func_110124_au(), p_72355_2_); + this.func_148540_a(new SPlayerListItemPacket(SPlayerListItemPacket.Action.ADD_PLAYER, p_72355_2_)); + +@@ -163,8 +172,9 @@ if (compoundnbt != null && compoundnbt.func_150297_b("RootVehicle", 10)) { CompoundNBT compoundnbt1 = compoundnbt.func_74775_l("RootVehicle"); @@ -26,7 +43,7 @@ }); if (entity1 != null) { UUID uuid = compoundnbt1.func_186857_a("Attach"); -@@ -191,6 +200,7 @@ +@@ -191,6 +201,7 @@ } p_72355_2_.func_71116_b(); @@ -34,7 +51,7 @@ } protected void func_96456_a(ServerScoreboard p_96456_1_, ServerPlayerEntity p_96456_2_) { -@@ -252,6 +262,7 @@ +@@ -252,6 +263,7 @@ compoundnbt1 = compoundnbt; p_72380_1_.func_70020_e(compoundnbt); field_148546_d.debug("loading single player"); @@ -42,7 +59,7 @@ } else { compoundnbt1 = this.field_72412_k.func_75752_b(p_72380_1_); } -@@ -260,6 +271,7 @@ +@@ -260,6 +272,7 @@ } protected void func_72391_b(ServerPlayerEntity p_72391_1_) { @@ -50,7 +67,7 @@ this.field_72412_k.func_75753_a(p_72391_1_); ServerStatisticsManager serverstatisticsmanager = this.field_148547_k.get(p_72391_1_.func_110124_au()); if (serverstatisticsmanager != null) { -@@ -274,6 +286,7 @@ +@@ -274,6 +287,7 @@ } public void func_72367_e(ServerPlayerEntity p_72367_1_) { @@ -58,10 +75,23 @@ ServerWorld serverworld = p_72367_1_.func_71121_q(); p_72367_1_.func_195066_a(Stats.field_75947_j); this.func_72391_b(p_72367_1_); -@@ -364,10 +377,18 @@ +@@ -295,7 +309,7 @@ + p_72367_1_.func_213319_R(); + serverworld.func_217434_e(p_72367_1_); + p_72367_1_.func_192039_O().func_192745_a(); +- this.field_72404_b.remove(p_72367_1_); ++ this.removePlayer(p_72367_1_); + this.field_72400_f.func_201300_aS().func_201382_b(p_72367_1_); + UUID uuid = p_72367_1_.func_110124_au(); + ServerPlayerEntity serverplayerentity = this.field_177454_f.get(uuid); +@@ -364,10 +378,18 @@ } public ServerPlayerEntity func_72368_a(ServerPlayerEntity p_72368_1_, DimensionType p_72368_2_, boolean p_72368_3_) { +- this.field_72404_b.remove(p_72368_1_); +- p_72368_1_.func_71121_q().func_217434_e(p_72368_1_); +- BlockPos blockpos = p_72368_1_.func_180470_cg(); +- boolean flag = p_72368_1_.func_82245_bX(); + ServerWorld world = field_72400_f.func_71218_a(p_72368_2_); + if (world == null) + p_72368_2_ = p_72368_1_.getSpawnDimension(); @@ -70,17 +100,14 @@ + if (field_72400_f.func_71218_a(p_72368_2_) == null) + p_72368_2_ = DimensionType.field_223227_a_; + - this.field_72404_b.remove(p_72368_1_); -- p_72368_1_.func_71121_q().func_217434_e(p_72368_1_); -- BlockPos blockpos = p_72368_1_.func_180470_cg(); -- boolean flag = p_72368_1_.func_82245_bX(); ++ this.removePlayer(p_72368_1_); + p_72368_1_.func_71121_q().removePlayer(p_72368_1_, true); // Forge: keep data until copyFrom called + BlockPos blockpos = p_72368_1_.getBedLocation(p_72368_2_); + boolean flag = p_72368_1_.isSpawnForced(p_72368_2_); p_72368_1_.field_71093_bK = p_72368_2_; PlayerInteractionManager playerinteractionmanager; if (this.field_72400_f.func_71242_L()) { -@@ -379,6 +400,8 @@ +@@ -379,6 +401,8 @@ ServerPlayerEntity serverplayerentity = new ServerPlayerEntity(this.field_72400_f, this.field_72400_f.func_71218_a(p_72368_1_.field_71093_bK), p_72368_1_.func_146103_bH(), playerinteractionmanager); serverplayerentity.field_71135_a = p_72368_1_.field_71135_a; serverplayerentity.func_193104_a(p_72368_1_, p_72368_3_); @@ -89,7 +116,7 @@ serverplayerentity.func_145769_d(p_72368_1_.func_145782_y()); serverplayerentity.func_184819_a(p_72368_1_.func_184591_cq()); -@@ -393,7 +416,7 @@ +@@ -393,7 +417,7 @@ if (optional.isPresent()) { Vec3d vec3d = optional.get(); serverplayerentity.func_70012_b(vec3d.field_72450_a, vec3d.field_72448_b, vec3d.field_72449_c, 0.0F, 0.0F); @@ -98,7 +125,12 @@ } else { serverplayerentity.field_71135_a.func_147359_a(new SChangeGameStatePacket(0, 0.0F)); } -@@ -417,6 +440,7 @@ +@@ -413,10 +437,11 @@ + this.func_72354_b(serverplayerentity, serverworld); + this.func_187243_f(serverplayerentity); + serverworld.func_217433_d(serverplayerentity); +- this.field_72404_b.add(serverplayerentity); ++ this.addPlayer(serverplayerentity); this.field_177454_f.put(serverplayerentity.func_110124_au(), serverplayerentity); serverplayerentity.func_71116_b(); serverplayerentity.func_70606_j(serverplayerentity.func_110143_aJ()); @@ -106,3 +138,25 @@ return serverplayerentity; } +@@ -736,7 +761,7 @@ + } + + public List func_181057_v() { +- return this.field_72404_b; ++ return this.playersView; //Unmodifiable view, we don't want people removing things without us knowing. + } + + @Nullable +@@ -766,4 +791,12 @@ + public boolean func_206257_x() { + return this.field_72407_n; + } ++ ++ public boolean addPlayer(ServerPlayerEntity player) { ++ return net.minecraftforge.common.DimensionManager.rebuildPlayerMap(this, this.field_72404_b.add(player)); ++ } ++ ++ public boolean removePlayer(ServerPlayerEntity player) { ++ return net.minecraftforge.common.DimensionManager.rebuildPlayerMap(this, this.field_72404_b.remove(player)); ++ } + } diff --git a/src/main/java/net/minecraftforge/common/DimensionManager.java b/src/main/java/net/minecraftforge/common/DimensionManager.java index 64c2acbc46..a8310b3038 100644 --- a/src/main/java/net/minecraftforge/common/DimensionManager.java +++ b/src/main/java/net/minecraftforge/common/DimensionManager.java @@ -23,8 +23,10 @@ import java.io.IOException; import java.util.ArrayList; import java.util.Collections; import java.util.HashMap; +import java.util.HashSet; import java.util.List; import java.util.Map; +import java.util.Set; import java.util.concurrent.ConcurrentMap; import java.util.stream.Collectors; @@ -45,6 +47,7 @@ import net.minecraft.nbt.CompoundNBT; import net.minecraft.nbt.ListNBT; import net.minecraft.network.PacketBuffer; import net.minecraft.server.MinecraftServer; +import net.minecraft.server.management.PlayerList; import net.minecraft.util.ResourceLocation; import net.minecraft.util.math.ChunkPos; import net.minecraft.util.registry.MutableRegistry; @@ -80,6 +83,7 @@ public class DimensionManager private static final ConcurrentMap weakWorldMap = new MapMaker().weakKeys().weakValues().makeMap(); private static final Multiset leakedWorlds = HashMultiset.create(); private static final Map savedEntries = new HashMap<>(); + private static volatile Set playerWorlds = new HashSet<>(); /** * Registers a real unique dimension, Should be called on server init, or when the dimension is created. @@ -144,7 +148,7 @@ public class DimensionManager /** * Retrieves the world from the server allowing for null return, and optionally resetting it's unload timer. * - * @param server The server that controlls this world. + * @param server The server that controls this world. * @param dim Dimension to load. * @param resetUnloadDelay True to reset the unload timer, which is a delay that is used to prevent constant world loading/unloading cycle. * @param forceLoad True to attempt to load the dimension if the server has it unloaded. @@ -222,7 +226,8 @@ public class DimensionManager return world.getDimension().getType() != DimensionType.OVERWORLD && world.getPlayers().isEmpty() && world.getForcedChunks().isEmpty() - && !getData(world.getDimension().getType()).keepLoaded; + && !getData(world.getDimension().getType()).keepLoaded + && !playerWorlds.contains(world); } /** @@ -484,4 +489,10 @@ public class DimensionManager @Override public void statusChanged(ChunkPos p_219508_1_, ChunkStatus p_219508_2_) { } @Override public void stop() { } } + + public static boolean rebuildPlayerMap(PlayerList players, boolean changed) + { + playerWorlds = players.getPlayers().stream().map(e -> e.world).collect(Collectors.toSet()); + return changed; + } } diff --git a/src/main/java/net/minecraftforge/common/ForgeInternalHandler.java b/src/main/java/net/minecraftforge/common/ForgeInternalHandler.java index 75269dc4b9..6f2acb3ad9 100644 --- a/src/main/java/net/minecraftforge/common/ForgeInternalHandler.java +++ b/src/main/java/net/minecraftforge/common/ForgeInternalHandler.java @@ -21,12 +21,14 @@ package net.minecraftforge.common; import net.minecraft.entity.Entity; import net.minecraft.entity.item.ItemEntity; +import net.minecraft.entity.player.ServerPlayerEntity; import net.minecraft.item.Item; import net.minecraft.item.ItemStack; import net.minecraft.world.server.ServerWorld; import net.minecraftforge.client.CloudRenderer; import net.minecraftforge.common.util.FakePlayerFactory; import net.minecraftforge.event.entity.EntityJoinWorldEvent; +import net.minecraftforge.event.entity.player.PlayerEvent; import net.minecraftforge.event.world.ChunkEvent; import net.minecraftforge.event.world.WorldEvent; import net.minecraftforge.eventbus.api.EventPriority; @@ -46,18 +48,16 @@ public class ForgeInternalHandler { ItemStack stack = ((ItemEntity)entity).getItem(); Item item = stack.getItem(); -/* if (item.hasCustomEntity(stack)) { Entity newEntity = item.createEntity(event.getWorld(), entity, stack); if (newEntity != null) { - entity.setDead(); + entity.remove(); event.setCanceled(true); - event.getWorld().spawnEntity(newEntity); + event.getWorld().addEntity(newEntity); } } -*/ } } @@ -88,5 +88,18 @@ public class ForgeInternalHandler if (!event.getWorld().isRemote()) FarmlandWaterManager.removeTickets(event.getChunk()); } + + @SubscribeEvent + public void playerChangeDimension(PlayerEvent.PlayerChangedDimensionEvent event) + { + if (event.getPlayer() instanceof ServerPlayerEntity) + DimensionManager.rebuildPlayerMap(((ServerPlayerEntity)event.getPlayer()).server.getPlayerList(), true); + } + + @SubscribeEvent + public void playerLogin(PlayerEvent.PlayerLoggedInEvent event) + { + UsernameCache.setUsername(event.getPlayer().getUniqueID(), event.getPlayer().getGameProfile().getName()); + } } diff --git a/src/main/java/net/minecraftforge/common/ForgeMod.java b/src/main/java/net/minecraftforge/common/ForgeMod.java index 8f6b45ac20..cb16ec7bf8 100644 --- a/src/main/java/net/minecraftforge/common/ForgeMod.java +++ b/src/main/java/net/minecraftforge/common/ForgeMod.java @@ -49,7 +49,6 @@ import net.minecraftforge.common.data.ForgeItemTagsProvider; import net.minecraftforge.common.data.ForgeRecipeProvider; import net.minecraftforge.common.model.animation.CapabilityAnimation; import net.minecraftforge.energy.CapabilityEnergy; -import net.minecraftforge.event.entity.player.PlayerEvent; import net.minecraftforge.fml.event.lifecycle.GatherDataEvent; import net.minecraftforge.fluids.capability.CapabilityFluidHandler; import net.minecraftforge.items.CapabilityItemHandler; @@ -93,7 +92,6 @@ public class ForgeMod implements WorldPersistenceHooks.WorldPersistenceHook modEventBus.addListener(this::preInit); modEventBus.addListener(this::gatherData); MinecraftForge.EVENT_BUS.addListener(this::serverStarting); - MinecraftForge.EVENT_BUS.addListener(this::playerLogin); MinecraftForge.EVENT_BUS.addListener(this::serverStopping); ModLoadingContext.get().registerConfig(ModConfig.Type.CLIENT, ForgeConfig.clientSpec); ModLoadingContext.get().registerConfig(ModConfig.Type.SERVER, ForgeConfig.serverSpec); @@ -103,12 +101,6 @@ public class ForgeMod implements WorldPersistenceHooks.WorldPersistenceHook StartupMessageManager.addModMessage("Forge version "+ForgeVersion.getVersion()); } - public void playerLogin(PlayerEvent.PlayerLoggedInEvent event) - { - UsernameCache.setUsername(event.getPlayer().getUniqueID(), event.getPlayer().getGameProfile().getName()); - } - - public void preInit(FMLCommonSetupEvent evt) { CapabilityItemHandler.register();