more patches

This commit is contained in:
Jake Potrebic 2021-06-13 12:29:58 -07:00 committed by MiniDigger | Martin
parent 123a41d132
commit 27a8d6da9a
32 changed files with 825 additions and 1168 deletions

View File

@ -5,7 +5,7 @@ Subject: [PATCH] Expose the internal current tick
diff --git a/src/main/java/org/bukkit/Bukkit.java b/src/main/java/org/bukkit/Bukkit.java diff --git a/src/main/java/org/bukkit/Bukkit.java b/src/main/java/org/bukkit/Bukkit.java
index e3304fcc8c4fd176abd3fb7d4b47e5ccb7bdd37f..49bf621a2c0e5e9641b334a42b2769944c991d5d 100644 index 7dd3fc9301de9a88313179088f6b5ce4c1362f06..02f91b446697b1c637fda3b65b48ec8cf38de66d 100644
--- a/src/main/java/org/bukkit/Bukkit.java --- a/src/main/java/org/bukkit/Bukkit.java
+++ b/src/main/java/org/bukkit/Bukkit.java +++ b/src/main/java/org/bukkit/Bukkit.java
@@ -1835,6 +1835,10 @@ public final class Bukkit { @@ -1835,6 +1835,10 @@ public final class Bukkit {
@ -20,7 +20,7 @@ index e3304fcc8c4fd176abd3fb7d4b47e5ccb7bdd37f..49bf621a2c0e5e9641b334a42b276994
@NotNull @NotNull
diff --git a/src/main/java/org/bukkit/Server.java b/src/main/java/org/bukkit/Server.java diff --git a/src/main/java/org/bukkit/Server.java b/src/main/java/org/bukkit/Server.java
index 989a732e5ef2053deede245d65fbf99cdf117c5e..e448ae78304974f7664b7ef18568a547833ece9f 100644 index 139a96d01e3a7e2e298592ce5d485dfc21c9c6c7..b038a82ffc298abb5129b6ec20538df5d0b6f595 100644
--- a/src/main/java/org/bukkit/Server.java --- a/src/main/java/org/bukkit/Server.java
+++ b/src/main/java/org/bukkit/Server.java +++ b/src/main/java/org/bukkit/Server.java
@@ -1609,5 +1609,12 @@ public interface Server extends PluginMessageRecipient, net.kyori.adventure.audi @@ -1609,5 +1609,12 @@ public interface Server extends PluginMessageRecipient, net.kyori.adventure.audi

View File

@ -5,7 +5,7 @@ Subject: [PATCH] PlayerDeathEvent#shouldDropExperience
diff --git a/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java b/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java diff --git a/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java b/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java
index 7b78afe9281681cb9262fa044c1069a6121358eb..46917615ac4734bf5fa4ddea497132466eb5cc35 100644 index 8c46eaebf004823c1c31eb2c7304181487cb1332..3d45d2e41aad6992b40a22030f2a63baeec78757 100644
--- a/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java --- a/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java
+++ b/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java +++ b/src/main/java/org/bukkit/event/entity/PlayerDeathEvent.java
@@ -1,6 +1,8 @@ @@ -1,6 +1,8 @@

View File

@ -5,7 +5,7 @@ Subject: [PATCH] Add effect to block break naturally
diff --git a/src/main/java/org/bukkit/block/Block.java b/src/main/java/org/bukkit/block/Block.java diff --git a/src/main/java/org/bukkit/block/Block.java b/src/main/java/org/bukkit/block/Block.java
index d4ba9c2b858204825d47fd6e91dab8c003df085a..f8c599718143fe638de422fd4625f353ee6c54ae 100644 index 5e2aa4fb8cf8130df21d3172dd94e857317f7653..e1cc36fbe808973227c0e8ca7166453235c90279 100644
--- a/src/main/java/org/bukkit/block/Block.java --- a/src/main/java/org/bukkit/block/Block.java
+++ b/src/main/java/org/bukkit/block/Block.java +++ b/src/main/java/org/bukkit/block/Block.java
@@ -469,6 +469,18 @@ public interface Block extends Metadatable { @@ -469,6 +469,18 @@ public interface Block extends Metadatable {

View File

@ -5,7 +5,7 @@ Subject: [PATCH] World view distance api
diff --git a/src/main/java/org/bukkit/World.java b/src/main/java/org/bukkit/World.java diff --git a/src/main/java/org/bukkit/World.java b/src/main/java/org/bukkit/World.java
index 7bf85151efddcbd561afb0fb2d423aa97ac176c1..61dfb057d94d89477d11b9e8d4be7c16032e25a9 100644 index 6fe2875f95bb600606d66e2f7113d325d10a9b9c..cd96c851d00185e7ee3ec6682b166fc1d06b6a73 100644
--- a/src/main/java/org/bukkit/World.java --- a/src/main/java/org/bukkit/World.java
+++ b/src/main/java/org/bukkit/World.java +++ b/src/main/java/org/bukkit/World.java
@@ -3447,6 +3447,34 @@ public interface World extends PluginMessageRecipient, Metadatable, net.kyori.ad @@ -3447,6 +3447,34 @@ public interface World extends PluginMessageRecipient, Metadatable, net.kyori.ad

View File

@ -9,6 +9,8 @@ extra array with List.toArray() with is a costly and unneccessary
operation. This patch will reduce the load of plugins which for example operation. This patch will reduce the load of plugins which for example
implement custom moblimits and depend on Chunk.getEntities(). implement custom moblimits and depend on Chunk.getEntities().
1.17: needs to be reworked, entities not in chunk anymore?
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftChunk.java b/src/main/java/org/bukkit/craftbukkit/CraftChunk.java diff --git a/src/main/java/org/bukkit/craftbukkit/CraftChunk.java b/src/main/java/org/bukkit/craftbukkit/CraftChunk.java
index 74bad15034d9d55fb70931f38868f812160c6305..0f45f4b2486e910d11fd94b260bcd68e49eae31e 100644 index 74bad15034d9d55fb70931f38868f812160c6305..0f45f4b2486e910d11fd94b260bcd68e49eae31e 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftChunk.java --- a/src/main/java/org/bukkit/craftbukkit/CraftChunk.java

View File

@ -1,89 +0,0 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Byteflux <byte@byteflux.net>
Date: Wed, 2 Mar 2016 02:17:54 -0600
Subject: [PATCH] Generator Settings
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index 6aec502eb529d4090306e12e837117cde7e114eb..290e49cf0077909ad7ab8127c01ef93cf7b70b51 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -570,4 +570,9 @@ public class PaperWorldConfig {
private void perPlayerMobSpawns() {
perPlayerMobSpawns = getBoolean("per-player-mob-spawns", false);
}
+
+ public boolean generateFlatBedrock;
+ private void generatorSettings() {
+ generateFlatBedrock = getBoolean("generator-settings.flat-bedrock", false);
+ }
}
diff --git a/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java b/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
index e6303cdb433ee2b6782e2a0bd6b03e4f6ecb18ba..36c7ab3919d8818af96d50170aeb431051c5aabf 100644
--- a/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
+++ b/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
@@ -25,6 +25,18 @@ import org.apache.logging.log4j.LogManager;
public interface ChunkAccess extends BlockGetter, FeatureAccess {
+ // Paper start
+ default boolean generateFlatBedrock() {
+ if (this instanceof ProtoChunk) {
+ return ((ProtoChunk)this).world.paperConfig.generateFlatBedrock;
+ } else if (this instanceof LevelChunk) {
+ return ((LevelChunk)this).world.paperConfig.generateFlatBedrock;
+ } else {
+ return false;
+ }
+ }
+ // Paper end
+
BlockState getType(final int x, final int y, final int z); // Paper
@Nullable
BlockState setBlockState(BlockPos pos, BlockState state, boolean moved);
diff --git a/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java b/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
index 87fd585141ad9818fca0b697cb4c87248fe7ce11..5a94464b9628b74eefa1c1d8514cf267f4c8a11d 100644
--- a/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
+++ b/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
@@ -64,7 +64,7 @@ public class ProtoChunk implements ChunkAccess {
private long inhabitedTime;
private final Map<GenerationStep.Carving, BitSet> carvingMasks;
private volatile boolean isLightCorrect;
- private final Level world; // Paper - Anti-Xray - Add world
+ final Level world; // Paper - Anti-Xray - Add world // Paper - private -> default
// Paper start - Anti-Xray - Add world
@Deprecated public ProtoChunk(ChunkPos pos, UpgradeData upgradeData) { this(pos, upgradeData, null); } // Notice for updates: Please make sure this constructor isn't used anywhere
diff --git a/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java b/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
index b38a9c87fc996bd3107c38f6446a687fd093c617..04adec255e4650ead8d80bee32a681c98686fb95 100644
--- a/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
+++ b/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
@@ -408,8 +408,8 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
int i = chunk.getPos().getMinBlockX();
int j = chunk.getPos().getMinBlockZ();
NoiseGeneratorSettings generatorsettingbase = (NoiseGeneratorSettings) this.settings.get();
- int k = generatorsettingbase.getBedrockFloorPosition();
- int l = this.height - 1 - generatorsettingbase.getBedrockRoofPosition();
+ int k = generatorsettingbase.getBedrockFloorPosition(); final int floorHeight = k; // Paper
+ int l = this.height - 1 - generatorsettingbase.getBedrockRoofPosition(); final int roofHeight = l; // Paper
boolean flag = true;
boolean flag1 = l + 4 >= 0 && l < this.height;
boolean flag2 = k + 4 >= 0 && k < this.height;
@@ -423,7 +423,7 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
if (flag1) {
for (i1 = 0; i1 < 5; ++i1) {
- if (i1 <= random.nextInt(5)) {
+ if (i1 <= (chunk.generateFlatBedrock() ? roofHeight : random.nextInt(5))) { // Paper - Configurable flat bedrock roof
chunk.setBlockState(blockposition_mutableblockposition.set(blockposition.getX(), l - i1, blockposition.getZ()), Blocks.BEDROCK.defaultBlockState(), false);
}
}
@@ -431,7 +431,7 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
if (flag2) {
for (i1 = 4; i1 >= 0; --i1) {
- if (i1 <= random.nextInt(5)) {
+ if (i1 <= (chunk.generateFlatBedrock() ? floorHeight : random.nextInt(5))) { // Paper - Configurable flat bedrock floor
chunk.setBlockState(blockposition_mutableblockposition.set(blockposition.getX(), k + i1, blockposition.getZ()), Blocks.BEDROCK.defaultBlockState(), false);
}
}

View File

@ -1,20 +0,0 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Callahan <mr.callahhh@gmail.com>
Date: Mon, 13 Jan 2020 23:47:28 -0600
Subject: [PATCH] Prevent sync chunk loads when villagers try to find beds
diff --git a/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java b/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
index 5151c794985a135d3bd794bbafdf524ab9f670de..9a582fb4b96b2d0406cc86e473e8bf8c4e488e37 100644
--- a/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
+++ b/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
@@ -46,7 +46,8 @@ public class SleepInBed extends Behavior<LivingEntity> {
}
}
- BlockState iblockdata = world.getBlockState(globalpos.getBlockPosition());
+ BlockState iblockdata = world.getTypeIfLoaded(globalpos.getBlockPosition()); // Paper
+ if (iblockdata == null) { return false; } // Paper
return globalpos.getBlockPosition().a((Position) entity.position(), 2.0D) && iblockdata.getBlock().is((Tag) BlockTags.BEDS) && !(Boolean) iblockdata.getValue(BedBlock.OCCUPIED);
}

View File

@ -1,62 +0,0 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Spottedleaf <Spottedleaf@users.noreply.github.com>
Date: Fri, 27 Dec 2019 09:42:26 -0800
Subject: [PATCH] Guard against serializing mismatching chunk coordinate
Should help if something dumb happens
diff --git a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
index be67dc16bf70e4517efd213ca9002f116f60b57c..6c28a611b9b79c3322ab07883972c07b3bfc3073 100644
--- a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
+++ b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
@@ -67,6 +67,13 @@ public class ChunkSerializer {
private static final Logger LOGGER = LogManager.getLogger();
+ // Paper start - guard against serializing mismatching coordinates
+ // TODO Note: This needs to be re-checked each update
+ public static ChunkPos getChunkCoordinate(CompoundTag chunkData) {
+ CompoundTag levelData = chunkData.getCompound("Level");
+ return new ChunkPos(levelData.getInt("xPos"), levelData.getInt("zPos"));
+ }
+ // Paper end
// Paper start
public static final class InProgressChunkHolder {
@@ -92,8 +99,8 @@ public class ChunkSerializer {
// Paper end
ChunkGenerator chunkgenerator = worldserver.getChunkSource().getGenerator();
BiomeSource worldchunkmanager = chunkgenerator.getBiomeSource();
- CompoundTag nbttagcompound1 = nbttagcompound.getCompound("Level");
- ChunkPos chunkcoordintpair1 = new ChunkPos(nbttagcompound1.getInt("xPos"), nbttagcompound1.getInt("zPos"));
+ CompoundTag nbttagcompound1 = nbttagcompound.getCompound("Level"); // Paper - diff on change, see ChunkRegionLoader#getChunkCoordinate
+ ChunkPos chunkcoordintpair1 = new ChunkPos(nbttagcompound1.getInt("xPos"), nbttagcompound1.getInt("zPos")); // Paper - diff on change, see ChunkRegionLoader#getChunkCoordinate
if (!Objects.equals(chunkcoordintpair, chunkcoordintpair1)) {
ChunkSerializer.LOGGER.error("Chunk file at {} is in the wrong location; relocating. (Expected {}, got {})", chunkcoordintpair, chunkcoordintpair, chunkcoordintpair1);
diff --git a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
index 684442b7175e30b6d4cafb2f7d2d4c10517cc33d..1af804c5c6fb2b20ea3f020610763c1d7dcee110 100644
--- a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
+++ b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
@@ -13,6 +13,7 @@ import net.minecraft.SharedConstants;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.nbt.NbtUtils;
import net.minecraft.resources.ResourceKey;
+import net.minecraft.server.level.ChunkMap;
import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.util.datafix.DataFixTypes;
@@ -119,6 +120,13 @@ public class ChunkStorage implements AutoCloseable {
public void write(ChunkPos chunkcoordintpair, CompoundTag nbttagcompound) throws IOException { write(chunkcoordintpair, nbttagcompound); } // Paper OBFHELPER
public void write(ChunkPos chunkcoordintpair, CompoundTag nbttagcompound) throws IOException { // Paper - OBFHELPER - (Switched around for safety)
+ // Paper start
+ if (!chunkcoordintpair.equals(ChunkSerializer.getChunkCoordinate(nbttagcompound))) {
+ String world = (this instanceof ChunkMap) ? ((ChunkMap)this).level.getWorld().getName() : null;
+ throw new IllegalArgumentException("Chunk coordinate and serialized data do not have matching coordinates, trying to serialize coordinate " + chunkcoordintpair.toString()
+ + " but compound says coordinate is " + ChunkSerializer.getChunkCoordinate(nbttagcompound).toString() + (world == null ? " for an unknown world" : (" for world: " + world)));
+ }
+ // Paper end
this.regionFileCache.write(chunkcoordintpair, nbttagcompound);
if (this.legacyStructureHandler != null) {
synchronized (this.persistentDataLock) { // Paper - Async chunk loading

View File

@ -0,0 +1,165 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Byteflux <byte@byteflux.net>
Date: Wed, 2 Mar 2016 02:17:54 -0600
Subject: [PATCH] Generator Settings
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index 4c177a383b277debe8a7c02a70d029d862e6b048..0c336a794d21d5084b9ea39308379b2ffb4a4330 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -416,5 +416,10 @@ public class PaperWorldConfig {
private void disableRelativeProjectileVelocity() {
disableRelativeProjectileVelocity = getBoolean("game-mechanics.disable-relative-projectile-velocity", false);
}
+
+ public boolean generateFlatBedrock;
+ private void generatorSettings() {
+ generateFlatBedrock = getBoolean("generator-settings.flat-bedrock", false);
+ }
}
diff --git a/src/main/java/net/minecraft/server/level/ChunkMap.java b/src/main/java/net/minecraft/server/level/ChunkMap.java
index dd7de2c3db10d9d606d47c52eba40e71034fc11a..5473b22d21ea981f245f4826c4d47295890f88ef 100644
--- a/src/main/java/net/minecraft/server/level/ChunkMap.java
+++ b/src/main/java/net/minecraft/server/level/ChunkMap.java
@@ -678,7 +678,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
}
this.markPositionReplaceable(pos);
- return Either.left(new ProtoChunk(pos, UpgradeData.EMPTY, this.level));
+ return Either.left(new ProtoChunk(pos, UpgradeData.EMPTY, this.level, this.level)); // Paper - add level
// Paper start - Async chunk io
};
CompletableFuture<Either<ChunkAccess, ChunkHolder.ChunkLoadingFailure>> ret = new CompletableFuture<>();
diff --git a/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java b/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
index 974ab04b08bbd3c27a394b37c1af112be5f28f43..c0075d226331f32e470dae5bf1ce8d79e8b263dc 100644
--- a/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
+++ b/src/main/java/net/minecraft/world/level/chunk/ChunkAccess.java
@@ -29,6 +29,18 @@ public interface ChunkAccess extends BlockGetter, FeatureAccess {
return GameEventDispatcher.NOOP;
}
+ // Paper start
+ default boolean generateFlatBedrock() {
+ if (this instanceof ProtoChunk) {
+ return ((ProtoChunk)this).level.paperConfig.generateFlatBedrock;
+ } else if (this instanceof LevelChunk) {
+ return ((LevelChunk)this).level.paperConfig.generateFlatBedrock;
+ } else {
+ return false;
+ }
+ }
+ // Paper end
+
BlockState getType(final int x, final int y, final int z); // Paper
@Nullable
BlockState setBlockState(BlockPos pos, BlockState state, boolean moved);
diff --git a/src/main/java/net/minecraft/world/level/chunk/ImposterProtoChunk.java b/src/main/java/net/minecraft/world/level/chunk/ImposterProtoChunk.java
index 452b513e8b89d865a396066adaf4feb1140e1c62..8245c5834ec69beb8e3b95fb3900601009a9273f 100644
--- a/src/main/java/net/minecraft/world/level/chunk/ImposterProtoChunk.java
+++ b/src/main/java/net/minecraft/world/level/chunk/ImposterProtoChunk.java
@@ -25,7 +25,7 @@ public class ImposterProtoChunk extends ProtoChunk {
private final LevelChunk wrapped;
public ImposterProtoChunk(LevelChunk wrapped) {
- super(wrapped.getPos(), UpgradeData.EMPTY, wrapped);
+ super(wrapped.getPos(), UpgradeData.EMPTY, wrapped, wrapped.level); // Paper - add level
this.wrapped = wrapped;
}
diff --git a/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java b/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
index da36e6d40ad3e8b7cdbe09ef911d1e5b8c28670f..245998e2cea32cf15ee2659639c647f449704ec0 100644
--- a/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
+++ b/src/main/java/net/minecraft/world/level/chunk/ProtoChunk.java
@@ -63,16 +63,24 @@ public class ProtoChunk implements ChunkAccess {
private long inhabitedTime;
private final Map<GenerationStep.Carving, BitSet> carvingMasks = new Object2ObjectArrayMap<>();
private volatile boolean isLightCorrect;
+ final net.minecraft.world.level.Level level; // Paper - Add level
- public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, LevelHeightAccessor world) {
+ // Paper start - add level
+ @Deprecated public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, LevelHeightAccessor world) { this(pos, upgradeData, world, null); }
+ public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, LevelHeightAccessor world, net.minecraft.server.level.ServerLevel level) {
+ // Paper end
this(pos, upgradeData, (LevelChunkSection[])null, new ProtoTickList<>((block) -> {
return block == null || block.defaultBlockState().isAir();
}, pos, world), new ProtoTickList<>((fluid) -> {
return fluid == null || fluid == Fluids.EMPTY;
- }, pos, world), world);
+ }, pos, world), world, level); // Paper - add level
}
- public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, @Nullable LevelChunkSection[] levelChunkSections, ProtoTickList<Block> blockTickScheduler, ProtoTickList<Fluid> fluidTickScheduler, LevelHeightAccessor world) {
+ // Paper start - add level
+ @Deprecated public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, @Nullable LevelChunkSection[] levelChunkSections, ProtoTickList<Block> blockTickScheduler, ProtoTickList<Fluid> fluidTickScheduler, LevelHeightAccessor world) { this(pos, upgradeData, levelChunkSections, blockTickScheduler, fluidTickScheduler, world, null); }
+ public ProtoChunk(ChunkPos pos, UpgradeData upgradeData, @Nullable LevelChunkSection[] levelChunkSections, ProtoTickList<Block> blockTickScheduler, ProtoTickList<Fluid> fluidTickScheduler, LevelHeightAccessor world, net.minecraft.server.level.ServerLevel level) {
+ this.level = level;
+ // Paper end
this.chunkPos = pos;
this.upgradeData = upgradeData;
this.blockTicks = blockTickScheduler;
diff --git a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
index fc320450878279a6aa48019fbde35bb183f5f06e..3cb35f2f47ba841915ac2825d30cc4c3274ce3c4 100644
--- a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
+++ b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
@@ -210,7 +210,7 @@ public class ChunkSerializer {
// CraftBukkit end
});
} else {
- ProtoChunk protochunk = new ProtoChunk(pos, chunkconverter, achunksection, protochunkticklist, protochunkticklist1, world);
+ ProtoChunk protochunk = new ProtoChunk(pos, chunkconverter, achunksection, protochunkticklist, protochunkticklist1, world, world); // Paper - add level
protochunk.setBiomes(biomestorage);
object = protochunk;
diff --git a/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java b/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
index a0a3cf7655eca5c2b181476b0842d9e8c19dbffd..db0abd275be2df7a4fdeb1d7179bff4d61bab052 100644
--- a/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
+++ b/src/main/java/net/minecraft/world/level/levelgen/NoiseBasedChunkGenerator.java
@@ -270,8 +270,8 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
int j = chunk.getPos().getMinBlockZ();
NoiseGeneratorSettings noiseGeneratorSettings = this.settings.get();
int k = noiseGeneratorSettings.noiseSettings().minY();
- int l = k + noiseGeneratorSettings.getBedrockFloorPosition();
- int m = this.height - 1 + k - noiseGeneratorSettings.getBedrockRoofPosition();
+ int l = k + noiseGeneratorSettings.getBedrockFloorPosition(); final int floorHeight = k; // Paper
+ int m = this.height - 1 + k - noiseGeneratorSettings.getBedrockRoofPosition(); final int roofHeight = l; // Paper
int n = 5;
int o = chunk.getMinBuildHeight();
int p = chunk.getMaxBuildHeight();
@@ -281,7 +281,7 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
for(BlockPos blockPos : BlockPos.betweenClosed(i, 0, j, i + 15, 0, j + 15)) {
if (bl) {
for(int q = 0; q < 5; ++q) {
- if (q <= random.nextInt(5)) {
+ if (q <= (chunk.generateFlatBedrock() ? roofHeight : random.nextInt(5))) { // Paper - Configurable flat bedrock roof
chunk.setBlockState(mutableBlockPos.set(blockPos.getX(), m - q, blockPos.getZ()), Blocks.BEDROCK.defaultBlockState(), false);
}
}
@@ -289,7 +289,7 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
if (bl2) {
for(int r = 4; r >= 0; --r) {
- if (r <= random.nextInt(5)) {
+ if (r <= (chunk.generateFlatBedrock() ? roofHeight : random.nextInt(5))) { // Paper - Configurable flat bedrock floor
chunk.setBlockState(mutableBlockPos.set(blockPos.getX(), l + r, blockPos.getZ()), Blocks.BEDROCK.defaultBlockState(), false);
}
}
@@ -309,14 +309,14 @@ public final class NoiseBasedChunkGenerator extends ChunkGenerator {
if (l <= 0) {
return CompletableFuture.completedFuture(chunk);
} else {
- int m = chunk.getSectionIndex(l * this.cellHeight - 1 + i);
+ int mStart = chunk.getSectionIndex(l * this.cellHeight - 1 + i); // Paper - decompile fix
int n = chunk.getSectionIndex(i);
return CompletableFuture.supplyAsync(() -> {
Set<LevelChunkSection> set = Sets.newHashSet();
ChunkAccess var16;
try {
- for(int m = m; m >= n; --m) {
+ for(int m = mStart; m >= n; --m) { // Paper - decompile fix
LevelChunkSection levelChunkSection = chunk.getOrCreateSection(m);
levelChunkSection.acquire();
set.add(levelChunkSection);

View File

@ -9,15 +9,15 @@ We can use an entity valid check since this method is invoked for
each inventory iteraction (thanks to CB) and on player tick (vanilla). each inventory iteraction (thanks to CB) and on player tick (vanilla).
diff --git a/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java b/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java diff --git a/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java b/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java
index 7246b3a84415e303591adb08d81362201deebfce..e0237e821b2c31ba68168fddf1c1a4ebfcf10ca7 100644 index 9da2f9334ea98ecba328c7b0d022321d6194529b..0d145f075798dde27beef80022cd7c0f582f8253 100644
--- a/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java --- a/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java
+++ b/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java +++ b/src/main/java/net/minecraft/world/inventory/HorseInventoryMenu.java
@@ -85,7 +85,7 @@ public class HorseInventoryMenu extends AbstractContainerMenu { @@ -95,7 +95,7 @@ public class HorseInventoryMenu extends AbstractContainerMenu {
@Override @Override
public boolean stillValid(Player player) { public boolean stillValid(Player player) {
- return this.horseContainer.stillValid(player) && this.horse.isAlive() && this.horse.distanceTo((Entity) player) < 8.0F; - return !this.horse.hasInventoryChanged(this.horseContainer) && this.horseContainer.stillValid(player) && this.horse.isAlive() && this.horse.distanceTo((Entity) player) < 8.0F;
+ return this.horseContainer.stillValid(player) && (this.horse.isAlive() && this.horse.valid) && this.horse.distanceTo((Entity) player) < 8.0F; // Paper - Fix MC-161754 + return !this.horse.hasInventoryChanged(this.horseContainer) && this.horseContainer.stillValid(player) && (this.horse.isAlive() && this.horse.valid) && this.horse.distanceTo((Entity) player) < 8.0F; // Paper - Fix MC-161754
} }
@Override private boolean hasChest(AbstractHorse entityhorseabstract) {

View File

@ -6,10 +6,10 @@ Subject: [PATCH] Fix spawning of hanging entities that are not ItemFrames and
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
index 52444619a4bae80a12bf296fbe07fa811adf806e..fb74bdcf4c2935b56e92717cc5a1504fbc853d0a 100644 index 4841591539fdd5a01f9ded0ee510991602c266a4..f1cbcdb1e409f8544125dde5f24bff5b07cb5082 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java --- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
@@ -1868,7 +1868,12 @@ public class CraftWorld implements World { @@ -1881,7 +1881,12 @@ public class CraftWorld implements World {
height = 9; height = 9;
} }
@ -22,4 +22,4 @@ index 52444619a4bae80a12bf296fbe07fa811adf806e..fb74bdcf4c2935b56e92717cc5a1504f
+ // Paper end + // Paper end
final BlockPos pos = new BlockPos(x, y, z); final BlockPos pos = new BlockPos(x, y, z);
for (BlockFace dir : faces) { for (BlockFace dir : faces) {
net.minecraft.world.level.block.state.BlockState nmsBlock = world.getBlockState(pos.relative(CraftBlock.blockFaceToNotch(dir))); net.minecraft.world.level.block.state.BlockState nmsBlock = this.world.getBlockState(pos.relative(CraftBlock.blockFaceToNotch(dir)));

View File

@ -5,10 +5,10 @@ Subject: [PATCH] Expose the internal current tick
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftServer.java b/src/main/java/org/bukkit/craftbukkit/CraftServer.java diff --git a/src/main/java/org/bukkit/craftbukkit/CraftServer.java b/src/main/java/org/bukkit/craftbukkit/CraftServer.java
index 96a3a4d89df858d4e46a36f110dd9ad3a2061433..3c0ba80bbba19f3725013e118cecdbac5612deec 100644 index 58d7fec472dd8c8d7775eb6d931be29871102054..9730c701b734eb3491bc1fa5d9bb81ddfefc910a 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftServer.java --- a/src/main/java/org/bukkit/craftbukkit/CraftServer.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftServer.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftServer.java
@@ -2363,5 +2363,10 @@ public final class CraftServer implements Server { @@ -2364,5 +2364,10 @@ public final class CraftServer implements Server {
} }
return new com.destroystokyo.paper.profile.CraftPlayerProfile(uuid, name); return new com.destroystokyo.paper.profile.CraftPlayerProfile(uuid, name);
} }

View File

@ -5,23 +5,23 @@ Subject: [PATCH] Fix stuck in sneak when changing worlds (MC-10657)
diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java
index b0eed4e18fc183856613c05f378576eb19985c46..2ef273e3b917803f3e2ac3c6a22d92a15b9eb71a 100644 index 679f1e3ef4c19ab466cf2d06c47b1018aabaa7bf..8da35a7dde494b059e542d049d7ee039deb5833d 100644
--- a/src/main/java/net/minecraft/server/level/ServerPlayer.java --- a/src/main/java/net/minecraft/server/level/ServerPlayer.java
+++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java +++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java
@@ -1070,6 +1070,8 @@ public class ServerPlayer extends Player implements ContainerListener { @@ -1101,6 +1101,8 @@ public class ServerPlayer extends Player {
this.lastSentHealth = -1.0F; this.lastSentHealth = -1.0F;
this.lastSentFood = -1; this.lastSentFood = -1;
+ setShiftKeyDown(false); // Paper - fix MC-10657 + setShiftKeyDown(false); // Paper - fix MC-10657
+ +
// CraftBukkit start // CraftBukkit start
PlayerChangedWorldEvent changeEvent = new PlayerChangedWorldEvent(this.getBukkitEntity(), worldserver1.getWorld()); PlayerChangedWorldEvent changeEvent = new PlayerChangedWorldEvent(this.getBukkitEntity(), worldserver1.getWorld());
this.level.getCraftServer().getPluginManager().callEvent(changeEvent); this.level.getCraftServer().getPluginManager().callEvent(changeEvent);
diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java
index e6eebb8f6f48cc55fc8fb114c959b8fbec4b8472..dfdde9722bc0d83916779014b7718eef2c01b3db 100644 index 6f9bd5da1504af296e7ee2a69d8afdd3bc4cfd5e..bcc946d2747443c34ee8ac2485a5ab41773c93af 100644
--- a/src/main/java/net/minecraft/server/players/PlayerList.java --- a/src/main/java/net/minecraft/server/players/PlayerList.java
+++ b/src/main/java/net/minecraft/server/players/PlayerList.java +++ b/src/main/java/net/minecraft/server/players/PlayerList.java
@@ -842,6 +842,8 @@ public abstract class PlayerList { @@ -820,6 +820,8 @@ public abstract class PlayerList {
entityplayer.connection.send(new ClientboundUpdateMobEffectPacket(entityplayer.getId(), mobEffect)); entityplayer.connection.send(new ClientboundUpdateMobEffectPacket(entityplayer.getId(), mobEffect));
} }

View File

@ -5,10 +5,10 @@ Subject: [PATCH] Add option to disable pillager patrols
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index 290e49cf0077909ad7ab8127c01ef93cf7b70b51..e726b6213cf2e8f5b326f05c0438b8f1ee2b73c5 100644 index 0c336a794d21d5084b9ea39308379b2ffb4a4330..f46731897f4234b27dafa49a5f652535a99d2992 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java --- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java +++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -575,4 +575,9 @@ public class PaperWorldConfig { @@ -421,5 +421,10 @@ public class PaperWorldConfig {
private void generatorSettings() { private void generatorSettings() {
generateFlatBedrock = getBoolean("generator-settings.flat-bedrock", false); generateFlatBedrock = getBoolean("generator-settings.flat-bedrock", false);
} }
@ -18,8 +18,9 @@ index 290e49cf0077909ad7ab8127c01ef93cf7b70b51..e726b6213cf2e8f5b326f05c0438b8f1
+ disablePillagerPatrols = getBoolean("game-mechanics.disable-pillager-patrols", disablePillagerPatrols); + disablePillagerPatrols = getBoolean("game-mechanics.disable-pillager-patrols", disablePillagerPatrols);
+ } + }
} }
diff --git a/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java b/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java diff --git a/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java b/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java
index caadd1a0fa6c4c446f84629088890a09e29622d9..48efe133d294bb1b17e8ac8b44eea8a29f15845f 100644 index e0a376617f6b6232591942da0bc9d7b1ee58c2e7..744b58d59a5f34ed3bd6f2d4a0f876acfa6a7135 100644
--- a/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java --- a/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java
+++ b/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java +++ b/src/main/java/net/minecraft/world/level/levelgen/PatrolSpawner.java
@@ -26,6 +26,7 @@ public class PatrolSpawner implements CustomSpawner { @@ -26,6 +26,7 @@ public class PatrolSpawner implements CustomSpawner {

View File

@ -7,10 +7,10 @@ Fixes an AssertionError when setting the player's item in hand to null or a new
Fixes GH-2718 Fixes GH-2718
diff --git a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java diff --git a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
index e45690b6197335ed1c07fa04c39b311b401724d7..2b79413bb8a592a7b7093e11d3a0cce895286c8f 100644 index 377e224acb06bfd5f769b5f75b7f52129394b494..9240064a17e7ac2492fe157b759d1f724105cd0e 100644
--- a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java --- a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
+++ b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java +++ b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
@@ -1706,6 +1706,10 @@ public class ServerGamePacketListenerImpl implements ServerGamePacketListener { @@ -1741,6 +1741,10 @@ public class ServerGamePacketListenerImpl implements ServerPlayerConnection, Ser
this.player.getBukkitEntity().updateInventory(); // SPIGOT-2524 this.player.getBukkitEntity().updateInventory(); // SPIGOT-2524
return; return;
} }
@ -21,15 +21,3 @@ index e45690b6197335ed1c07fa04c39b311b401724d7..2b79413bb8a592a7b7093e11d3a0cce8
InteractionResult enuminteractionresult = this.player.gameMode.useItem(this.player, worldserver, itemstack, enumhand); InteractionResult enuminteractionresult = this.player.gameMode.useItem(this.player, worldserver, itemstack, enumhand);
if (enuminteractionresult.shouldSwing()) { if (enuminteractionresult.shouldSwing()) {
diff --git a/src/main/java/net/minecraft/world/entity/LivingEntity.java b/src/main/java/net/minecraft/world/entity/LivingEntity.java
index f8917123547615dd624e3e428ec1bf6450c7b7d8..b49d4772932a58852b3195f5f56ff93dbcabf766 100644
--- a/src/main/java/net/minecraft/world/entity/LivingEntity.java
+++ b/src/main/java/net/minecraft/world/entity/LivingEntity.java
@@ -2153,6 +2153,7 @@ public abstract class LivingEntity extends Entity {
return predicate.test(this.getMainHandItem().getItem()) || predicate.test(this.getOffhandItem().getItem());
}
+ public final ItemStack getItemInHand(InteractionHand enumhand) { return this.getItemInHand(enumhand); } // Paper - OBFHELPER
public ItemStack getItemInHand(InteractionHand hand) {
if (hand == InteractionHand.MAIN_HAND) {
return this.getItemBySlot(EquipmentSlot.MAINHAND);

View File

@ -0,0 +1,20 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Callahan <mr.callahhh@gmail.com>
Date: Mon, 13 Jan 2020 23:47:28 -0600
Subject: [PATCH] Prevent sync chunk loads when villagers try to find beds
diff --git a/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java b/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
index 455774a211c679367c6e7845a11159ad84ca07e2..673b6e60731d440cc02b1e86bfba50e6ebeb0da9 100644
--- a/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
+++ b/src/main/java/net/minecraft/world/entity/ai/behavior/SleepInBed.java
@@ -41,7 +41,8 @@ public class SleepInBed extends Behavior<LivingEntity> {
}
}
- BlockState blockState = world.getBlockState(globalPos.pos());
+ BlockState blockState = world.getTypeIfLoaded(globalPos.pos()); // Paper
+ if (blockState == null) { return false; } // Paper
return globalPos.pos().closerThan(entity.position(), 2.0D) && blockState.is(BlockTags.BEDS) && !blockState.getValue(BedBlock.OCCUPIED);
}
}

View File

@ -5,10 +5,10 @@ Subject: [PATCH] MC-145656 Fix Follow Range Initial Target
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index e726b6213cf2e8f5b326f05c0438b8f1ee2b73c5..edda2121f8c1046478beaa77030ebb36d403b334 100644 index f46731897f4234b27dafa49a5f652535a99d2992..8190c30346c0fd2d86fb7cbcfc7ce17333e05146 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java --- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java +++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -580,4 +580,9 @@ public class PaperWorldConfig { @@ -426,5 +426,10 @@ public class PaperWorldConfig {
private void pillagerSettings() { private void pillagerSettings() {
disablePillagerPatrols = getBoolean("game-mechanics.disable-pillager-patrols", disablePillagerPatrols); disablePillagerPatrols = getBoolean("game-mechanics.disable-pillager-patrols", disablePillagerPatrols);
} }
@ -18,41 +18,33 @@ index e726b6213cf2e8f5b326f05c0438b8f1ee2b73c5..edda2121f8c1046478beaa77030ebb36
+ entitiesTargetWithFollowRange = getBoolean("entities-target-with-follow-range", entitiesTargetWithFollowRange); + entitiesTargetWithFollowRange = getBoolean("entities-target-with-follow-range", entitiesTargetWithFollowRange);
+ } + }
} }
diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java b/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java b/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java
index 7bba2ac71a3cd34a06ec865a3c1828b10decd644..93845edab0e1b0e2ad300cad051b0182cadd46e5 100644 index 6cbd2fc4a7041f957966e5b09616e70aae63c0d4..b5bbcb9fa6de4c919e4d4fabbab483054d81574e 100644
--- a/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java --- a/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java
+++ b/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java +++ b/src/main/java/net/minecraft/world/entity/ai/goal/target/NearestAttackableTargetGoal.java
@@ -32,6 +32,7 @@ public class NearestAttackableTargetGoal<T extends LivingEntity> extends TargetG @@ -32,6 +32,7 @@ public class NearestAttackableTargetGoal<T extends LivingEntity> extends TargetG
this.randomInterval = reciprocalChance; this.randomInterval = reciprocalChance;
this.setFlags(EnumSet.of(Goal.Flag.TARGET)); this.setFlags(EnumSet.of(Goal.Flag.TARGET));
this.targetConditions = (new TargetingConditions()).range(this.getFollowDistance()).selector(targetPredicate); this.targetConditions = TargetingConditions.forCombat().range(this.getFollowDistance()).selector(targetPredicate);
+ if (mob.level.paperConfig.entitiesTargetWithFollowRange) this.targetConditions.useFollowRange(); // Paper + if (mob.level.paperConfig.entitiesTargetWithFollowRange) this.targetConditions.useFollowRange(); // Paper
} }
@Override @Override
diff --git a/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java b/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java diff --git a/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java b/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java
index 1714507fa744b2767e8a66cdb5db7f43c21f5c56..e1a0104a3b52990a83e7732491029d8a20976dc3 100644 index e45434b844c98c322e1432c2382c1ccb8c3e57a7..3ee691d4caccbc1b3e0f52decb41d436ac0d08ec 100644
--- a/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java --- a/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java
+++ b/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java +++ b/src/main/java/net/minecraft/world/entity/ai/targeting/TargetingConditions.java
@@ -4,6 +4,8 @@ import java.util.function.Predicate; @@ -75,7 +75,7 @@ public class TargetingConditions {
import javax.annotation.Nullable;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.Mob;
+import net.minecraft.world.entity.ai.attributes.AttributeInstance;
+import net.minecraft.world.entity.ai.attributes.Attributes;
public class TargetingConditions {
@@ -82,7 +84,7 @@ public class TargetingConditions {
if (this.range > 0.0D) { if (this.range > 0.0D) {
double d0 = this.testInvisible ? targetEntity.getVisibilityPercent(baseEntity) : 1.0D; double d = this.testInvisible ? targetEntity.getVisibilityPercent(baseEntity) : 1.0D;
- double d1 = Math.max(this.range * d0, 2.0D); - double e = Math.max(this.range * d, 2.0D);
+ double d1 = Math.max((useFollowRange ? getFollowRange(baseEntity) : this.range) * d0, 2.0D); // Paper + double e = Math.max((this.useFollowRange ? this.getFollowRange(baseEntity) : this.range) * d, 2.0D); // Paper
double d2 = baseEntity.distanceToSqr(targetEntity.getX(), targetEntity.getY(), targetEntity.getZ()); double f = baseEntity.distanceToSqr(targetEntity.getX(), targetEntity.getY(), targetEntity.getZ());
if (f > e * e) {
if (d2 > d1 * d1) { return false;
@@ -98,4 +100,18 @@ public class TargetingConditions { @@ -90,4 +90,18 @@ public class TargetingConditions {
return true; return true;
} }
} }
@ -66,7 +58,7 @@ index 1714507fa744b2767e8a66cdb5db7f43c21f5c56..e1a0104a3b52990a83e7732491029d8a
+ } + }
+ +
+ private double getFollowRange(LivingEntity entityliving) { + private double getFollowRange(LivingEntity entityliving) {
+ AttributeInstance attributeinstance = entityliving.getAttribute(Attributes.FOLLOW_RANGE); + net.minecraft.world.entity.ai.attributes.AttributeInstance attributeinstance = entityliving.getAttribute(net.minecraft.world.entity.ai.attributes.Attributes.FOLLOW_RANGE);
+ return attributeinstance == null ? 16.0D : attributeinstance.getValue(); + return attributeinstance == null ? 16.0D : attributeinstance.getValue();
+ } + }
+ // Paper end + // Paper end

View File

@ -13,10 +13,10 @@ Subject: [PATCH] Optimize Hoppers
* Remove Streams from Item Suck In and restore restore 1.12 AABB checks which is simpler and no voxel allocations (was doing TWO Item Suck ins) * Remove Streams from Item Suck In and restore restore 1.12 AABB checks which is simpler and no voxel allocations (was doing TWO Item Suck ins)
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index edda2121f8c1046478beaa77030ebb36d403b334..7fbd501d70dccf869a4454e2789a5d68f2e15754 100644 index 8190c30346c0fd2d86fb7cbcfc7ce17333e05146..041efecbfcd54384d15ebf771cdfa0e711483997 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java --- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java +++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -585,4 +585,13 @@ public class PaperWorldConfig { @@ -431,5 +431,14 @@ public class PaperWorldConfig {
private void entitiesTargetWithFollowRange() { private void entitiesTargetWithFollowRange() {
entitiesTargetWithFollowRange = getBoolean("entities-target-with-follow-range", entitiesTargetWithFollowRange); entitiesTargetWithFollowRange = getBoolean("entities-target-with-follow-range", entitiesTargetWithFollowRange);
} }
@ -30,31 +30,24 @@ index edda2121f8c1046478beaa77030ebb36d403b334..7fbd501d70dccf869a4454e2789a5d68
+ log("Hopper Move Item Events: " + (disableHopperMoveEvents ? "disabled" : "enabled")); + log("Hopper Move Item Events: " + (disableHopperMoveEvents ? "disabled" : "enabled"));
+ } + }
} }
diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java
index 753e6f609189c589514739bea80007bace3c89d2..7038897b8fb4c18ca97b95a3b24c30b40b62b005 100644 index f00839eab02277bf10b742c88fadc4aa9e89e7e0..312be2221e1acc44aaf6936533b0eb968f796dc6 100644
--- a/src/main/java/net/minecraft/server/MinecraftServer.java --- a/src/main/java/net/minecraft/server/MinecraftServer.java
+++ b/src/main/java/net/minecraft/server/MinecraftServer.java +++ b/src/main/java/net/minecraft/server/MinecraftServer.java
@@ -131,6 +131,7 @@ import net.minecraft.world.level.LevelSettings; @@ -1422,6 +1422,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
import net.minecraft.world.level.biome.BiomeManager;
import net.minecraft.world.level.biome.BiomeSource;
import net.minecraft.world.level.block.Block;
+import net.minecraft.world.level.block.entity.HopperBlockEntity;
import net.minecraft.world.level.border.WorldBorder;
import net.minecraft.world.level.chunk.ChunkGenerator;
import net.minecraft.world.level.dimension.DimensionType;
@@ -1360,6 +1361,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
while (iterator.hasNext()) { while (iterator.hasNext()) {
ServerLevel worldserver = (ServerLevel) iterator.next(); ServerLevel worldserver = (ServerLevel) iterator.next();
worldserver.hasPhysicsEvent = org.bukkit.event.block.BlockPhysicsEvent.getHandlerList().getRegisteredListeners().length > 0; // Paper worldserver.hasPhysicsEvent = org.bukkit.event.block.BlockPhysicsEvent.getHandlerList().getRegisteredListeners().length > 0; // Paper
+ HopperBlockEntity.skipHopperEvents = worldserver.paperConfig.disableHopperMoveEvents || org.bukkit.event.inventory.InventoryMoveItemEvent.getHandlerList().getRegisteredListeners().length == 0; // Paper + net.minecraft.world.level.block.entity.HopperBlockEntity.skipHopperEvents = worldserver.paperConfig.disableHopperMoveEvents || org.bukkit.event.inventory.InventoryMoveItemEvent.getHandlerList().getRegisteredListeners().length == 0; // Paper
this.profiler.push(() -> { this.profiler.push(() -> {
return worldserver + " " + worldserver.dimension().location(); return worldserver + " " + worldserver.dimension().location();
diff --git a/src/main/java/net/minecraft/world/item/ItemStack.java b/src/main/java/net/minecraft/world/item/ItemStack.java diff --git a/src/main/java/net/minecraft/world/item/ItemStack.java b/src/main/java/net/minecraft/world/item/ItemStack.java
index 02bfa4fb8055e60a84e878ffbf18303c0ee25b1d..ac996d581925c8f92832009945c766962e5b51c5 100644 index dd4deb08eb3ed15a156269a11d3d43abfd61fe5b..10f55ba189d12c46e0ef38b0b96a29894b4fba93 100644
--- a/src/main/java/net/minecraft/world/item/ItemStack.java --- a/src/main/java/net/minecraft/world/item/ItemStack.java
+++ b/src/main/java/net/minecraft/world/item/ItemStack.java +++ b/src/main/java/net/minecraft/world/item/ItemStack.java
@@ -538,11 +538,12 @@ public final class ItemStack { @@ -601,11 +601,12 @@ public final class ItemStack {
return this.getItem().interactLivingEntity(this, user, entity, hand); return this.getItem().interactLivingEntity(this, user, entity, hand);
} }
@ -70,89 +63,75 @@ index 02bfa4fb8055e60a84e878ffbf18303c0ee25b1d..ac996d581925c8f92832009945c76696
itemstack.setPopTime(this.getPopTime()); itemstack.setPopTime(this.getPopTime());
if (this.tag != null) { if (this.tag != null) {
diff --git a/src/main/java/net/minecraft/world/level/Level.java b/src/main/java/net/minecraft/world/level/Level.java
index 3e2cd6c7a34c1a792d7346019a8b039d1f4a7c04..6b79f8cd9258af47afa6efa7b1f97c3780be58b0 100644
--- a/src/main/java/net/minecraft/world/level/Level.java
+++ b/src/main/java/net/minecraft/world/level/Level.java
@@ -1162,8 +1162,8 @@ public abstract class Level implements LevelAccessor, AutoCloseable {
return list;
}
- @Override
- public <T extends Entity> List<T> getEntitiesOfClass(Class<? extends T> entityClass, AABB box, @Nullable Predicate<? super T> predicate) {
+ public <T extends Entity> List<T> getEntities(Class<? extends T> oclass, AABB axisalignedbb, @Nullable Predicate<? super T> predicate) { return getEntitiesOfClass(oclass, axisalignedbb, predicate); } // Paper - OBFHELPER
+ @Override public <T extends Entity> List<T> getEntitiesOfClass(Class<? extends T> entityClass, AABB box, @Nullable Predicate<? super T> predicate) {
this.getProfiler().incrementCounter("getEntities");
int i = Mth.floor((box.minX - 2.0D) / 16.0D);
int j = Mth.ceil((box.maxX + 2.0D) / 16.0D);
diff --git a/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java diff --git a/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java
index 84012c2d12817e657b046bc168cc8eddebcd3831..05fa76c02ce61e26891ad995fe89e925ea086557 100644 index 8a079ee3ed243fd19b1dd7eed2de1dd33785faa1..c3a07ccccd5cc38552363c82398f432c8d624288 100644
--- a/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java --- a/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java
+++ b/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java +++ b/src/main/java/net/minecraft/world/level/block/entity/BlockEntity.java
@@ -77,6 +77,7 @@ public abstract class BlockEntity implements net.minecraft.server.KeyedObject { @@ -63,6 +63,7 @@ public abstract class BlockEntity implements net.minecraft.server.KeyedObject {
public void setCurrentChunk(LevelChunk chunk) { getMinecraftKey(); // Try to load if it doesn't exists.
this.currentChunk = chunk != null ? new java.lang.ref.WeakReference<>(chunk) : null; return tileEntityKeyString;
} }
+ static boolean IGNORE_TILE_UPDATES = false; + static boolean IGNORE_TILE_UPDATES = false;
// Paper end // Paper end
@Nullable @Nullable
@@ -155,6 +156,7 @@ public abstract class BlockEntity implements net.minecraft.server.KeyedObject { @@ -145,6 +146,7 @@ public abstract class BlockEntity implements net.minecraft.server.KeyedObject {
public void setChanged() { public void setChanged() {
if (this.level != null) { if (this.level != null) {
+ if (IGNORE_TILE_UPDATES) return; // Paper + if (IGNORE_TILE_UPDATES) return; // Paper
this.blockState = this.level.getBlockState(this.worldPosition); BlockEntity.setChanged(this.level, this.worldPosition, this.blockState);
this.level.blockEntityChanged(this.worldPosition, this); }
if (!this.blockState.isAir()) {
diff --git a/src/main/java/net/minecraft/world/level/block/entity/Hopper.java b/src/main/java/net/minecraft/world/level/block/entity/Hopper.java diff --git a/src/main/java/net/minecraft/world/level/block/entity/Hopper.java b/src/main/java/net/minecraft/world/level/block/entity/Hopper.java
index f8e4a42bed265822666141683e36e6696694925b..fc8bb72f7d677f65db505016ad6a4cd6146de29f 100644 index a05acf709735b40ca86f978508c63a86065fd405..c1754df6a60ff93d75a28145b9dc4e9174241a21 100644
--- a/src/main/java/net/minecraft/world/level/block/entity/Hopper.java --- a/src/main/java/net/minecraft/world/level/block/entity/Hopper.java
+++ b/src/main/java/net/minecraft/world/level/block/entity/Hopper.java +++ b/src/main/java/net/minecraft/world/level/block/entity/Hopper.java
@@ -1,6 +1,7 @@ @@ -14,6 +14,10 @@ public interface Hopper extends Container {
package net.minecraft.world.level.block.entity; return SUCK;
import javax.annotation.Nullable;
+import net.minecraft.core.BlockPos;
import net.minecraft.world.Container;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.block.Block;
@@ -17,12 +18,13 @@ public interface Hopper extends Container {
return Hopper.SUCK;
} }
- @Nullable + net.minecraft.world.level.Level getLevel();
+ //@Nullable // Paper - it's annoying +
Level getLevel(); + default net.minecraft.core.BlockPos getBlockPosition() { return new net.minecraft.core.BlockPos(getLevelX(), getLevelY(), getLevelZ()); } // Paper
+ default BlockPos getBlockPosition() { return new BlockPos(getX(), getY(), getZ()); } // Paper +
double getLevelX();
- double getLevelX(); double getLevelY();
+ double getLevelX(); default double getX() { return this.getLevelX(); } // Paper - OBFHELPER
- double getLevelY();
+ double getLevelY(); default double getY() { return this.getLevelY(); } // Paper - OBFHELPER
- double getLevelZ();
+ double getLevelZ(); default double getZ() { return this.getLevelZ(); } // Paper - OBFHELPER
}
diff --git a/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java diff --git a/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java
index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f7639dab54b 100644 index 0ec16d554c2b51a64614c73783505c7b06ff02c7..86c0a477883102e4aebdab7ac28bf9f2ab2f7c48 100644
--- a/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java --- a/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java
+++ b/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java +++ b/src/main/java/net/minecraft/world/level/block/entity/HopperBlockEntity.java
@@ -193,6 +193,160 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen @@ -3,7 +3,6 @@ package net.minecraft.world.level.block.entity;
import java.util.Iterator;
import java.util.List;
import java.util.function.BooleanSupplier;
-import java.util.stream.Collectors;
import java.util.stream.IntStream;
import javax.annotation.Nullable;
import net.minecraft.core.BlockPos;
@@ -33,7 +32,6 @@ import net.minecraft.world.level.block.state.BlockState;
import net.minecraft.world.phys.AABB;
import net.minecraft.world.phys.shapes.BooleanOp;
import net.minecraft.world.phys.shapes.Shapes;
-import org.bukkit.Bukkit;
import org.bukkit.craftbukkit.entity.CraftHumanEntity;
import org.bukkit.craftbukkit.inventory.CraftItemStack;
import org.bukkit.entity.HumanEntity;
@@ -192,6 +190,159 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
return false; return false;
} }
+ // Paper start - Optimize Hoppers + // Paper start - Optimize Hoppers
+ private static boolean skipPullModeEventFire = false; + private static boolean skipPullModeEventFire = false;
+ private static boolean skipPushModeEventFire = false; + private static boolean skipPushModeEventFire = false;
+ public static boolean skipHopperEvents = false; + public static boolean skipHopperEvents = false;
+ +
+ private boolean hopperPush(Container iinventory, Direction enumdirection) { + private static boolean hopperPush(Level level, BlockPos pos, Container iinventory, Direction enumdirection, HopperBlockEntity hopper) {
+ skipPushModeEventFire = skipHopperEvents; + skipPushModeEventFire = skipHopperEvents;
+ boolean foundItem = false; + boolean foundItem = false;
+ for (int i = 0; i < this.getContainerSize(); ++i) { + for (int i = 0; i < iinventory.getContainerSize(); ++i) {
+ ItemStack item = this.getItem(i); + ItemStack item = iinventory.getItem(i);
+ if (!item.isEmpty()) { + if (!item.isEmpty()) {
+ foundItem = true; + foundItem = true;
+ ItemStack origItemStack = item; + ItemStack origItemStack = item;
@ -165,13 +144,13 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ // We only need to fire the event once to give protection plugins a chance to cancel this event + // We only need to fire the event once to give protection plugins a chance to cancel this event
+ // Because nothing uses getItem, every event call should end up the same result. + // Because nothing uses getItem, every event call should end up the same result.
+ if (!skipPushModeEventFire) { + if (!skipPushModeEventFire) {
+ itemstack = callPushMoveEvent(iinventory, itemstack); + itemstack = callPushMoveEvent(iinventory, itemstack, hopper);
+ if (itemstack == null) { // cancelled + if (itemstack == null) { // cancelled
+ origItemStack.setCount(origCount); + origItemStack.setCount(origCount);
+ return false; + return false;
+ } + }
+ } + }
+ final ItemStack itemstack2 = addItem(this, iinventory, itemstack, enumdirection); + final ItemStack itemstack2 = addItem(hopper, iinventory, itemstack, enumdirection);
+ final int remaining = itemstack2.getCount(); + final int remaining = itemstack2.getCount();
+ if (remaining != moved) { + if (remaining != moved) {
+ origItemStack = origItemStack.cloneItemStack(true); + origItemStack = origItemStack.cloneItemStack(true);
@ -179,7 +158,7 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ if (!origItemStack.isEmpty()) { + if (!origItemStack.isEmpty()) {
+ origItemStack.setCount(origCount - moved + remaining); + origItemStack.setCount(origCount - moved + remaining);
+ } + }
+ this.setItem(i, origItemStack); + hopper.setItem(i, origItemStack);
+ iinventory.setChanged(); + iinventory.setChanged();
+ return true; + return true;
+ } + }
@ -187,7 +166,7 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ } + }
+ } + }
+ if (foundItem && level.paperConfig.cooldownHopperWhenFull) { // Inventory was full - cooldown + if (foundItem && level.paperConfig.cooldownHopperWhenFull) { // Inventory was full - cooldown
+ this.setCooldown(level.spigotConfig.hopperTransfer); + hopper.setCooldown(level.spigotConfig.hopperTransfer);
+ } + }
+ return false; + return false;
+ } + }
@ -233,16 +212,16 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ return false; + return false;
+ } + }
+ +
+ private ItemStack callPushMoveEvent(Container iinventory, ItemStack itemstack) { + private static ItemStack callPushMoveEvent(Container iinventory, ItemStack itemstack, HopperBlockEntity hopper) {
+ Inventory destinationInventory = getInventory(iinventory); + Inventory destinationInventory = getInventory(iinventory);
+ InventoryMoveItemEvent event = new InventoryMoveItemEvent(this.getOwner(false).getInventory(), + InventoryMoveItemEvent event = new InventoryMoveItemEvent(hopper.getOwner(false).getInventory(),
+ CraftItemStack.asCraftMirror(itemstack), destinationInventory, true); + CraftItemStack.asCraftMirror(itemstack), destinationInventory, true);
+ boolean result = event.callEvent(); + boolean result = event.callEvent();
+ if (!event.calledGetItem && !event.calledSetItem) { + if (!event.calledGetItem && !event.calledSetItem) {
+ skipPushModeEventFire = true; + skipPushModeEventFire = true;
+ } + }
+ if (!result) { + if (!result) {
+ cooldownHopper(this); + cooldownHopper(hopper);
+ return null; + return null;
+ } + }
+ +
@ -296,58 +275,18 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ } + }
+ } + }
+ // Paper end + // Paper end
+
private boolean ejectItems() {
Container iinventory = this.getAttachedContainer();
@@ -204,27 +358,28 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen private static boolean a(Level world, BlockPos blockposition, BlockState iblockdata, Container iinventory, HopperBlockEntity hopper) { // CraftBukkit
if (this.isFullContainer(iinventory, enumdirection)) { Container iinventory1 = HopperBlockEntity.getAttachedContainer(world, blockposition, iblockdata);
@@ -204,6 +355,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
if (HopperBlockEntity.isFullContainer(iinventory1, enumdirection)) {
return false; return false;
} else { } else {
- for (int i = 0; i < this.getContainerSize(); ++i) { + return hopperPush(world, blockposition, iinventory, enumdirection, hopper); /* // Paper - disable rest
+ return hopperPush(iinventory, enumdirection); /* // Paper - disable rest for (int i = 0; i < iinventory.getContainerSize(); ++i) {
+ for (int i = 0; i < this.getSize(); ++i) { if (!iinventory.getItem(i).isEmpty()) {
if (!this.getItem(i).isEmpty()) { ItemStack itemstack = iinventory.getItem(i).copy();
- ItemStack itemstack = this.getItem(i).copy(); @@ -241,7 +393,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
+ ItemStack itemstack = this.getItem(i).cloneItemStack();
// ItemStack itemstack1 = addItem(this, iinventory, this.splitStack(i, 1), enumdirection);
// CraftBukkit start - Call event when pushing items into other inventories
- CraftItemStack oitemstack = CraftItemStack.asCraftMirror(this.removeItem(i, level.spigotConfig.hopperAmount)); // Spigot
+ CraftItemStack oitemstack = CraftItemStack.asCraftMirror(this.splitStack(i, world.spigotConfig.hopperAmount)); // Spigot
Inventory destinationInventory;
// Have to special case large chests as they work oddly
- if (iinventory instanceof CompoundContainer) {
- destinationInventory = new org.bukkit.craftbukkit.inventory.CraftInventoryDoubleChest((CompoundContainer) iinventory);
+ if (iinventory instanceof InventoryLargeChest) {
+ destinationInventory = new org.bukkit.craftbukkit.inventory.CraftInventoryDoubleChest((InventoryLargeChest) iinventory);
} else {
destinationInventory = iinventory.getOwner().getInventory();
}
InventoryMoveItemEvent event = new InventoryMoveItemEvent(this.getOwner().getInventory(), oitemstack.clone(), destinationInventory, true);
- this.getLevel().getCraftServer().getPluginManager().callEvent(event);
+ this.getWorld().getServer().getPluginManager().callEvent(event);
if (event.isCancelled()) {
this.setItem(i, itemstack);
- this.setCooldown(level.spigotConfig.hopperTransfer); // Spigot
+ this.setCooldown(world.spigotConfig.hopperTransfer); // Spigot
return false;
}
int origCount = event.getItem().getAmount(); // Spigot
@@ -232,16 +387,16 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
// CraftBukkit end
if (itemstack1.isEmpty()) {
- iinventory.setChanged();
+ iinventory.update();
return true;
}
- itemstack.shrink(origCount - itemstack1.getCount()); // Spigot
+ itemstack.subtract(origCount - itemstack1.getCount()); // Spigot
this.setItem(i, itemstack);
} }
} }
@ -356,13 +295,25 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
} }
} }
} }
@@ -250,18 +405,54 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen @@ -251,27 +403,68 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
return inventory instanceof WorldlyContainer ? IntStream.of(((WorldlyContainer) inventory).getSlotsForFace(side)) : IntStream.range(0, inventory.getContainerSize());
} }
- private boolean isFullContainer(Container inv, Direction enumdirection) { private static boolean isFullContainer(Container inventory, Direction direction) {
- return getSlots(inv, enumdirection).allMatch((i) -> { - return HopperBlockEntity.getSlots(inventory, direction).allMatch((i) -> {
- ItemStack itemstack = inv.getItem(i); - ItemStack itemstack = inventory.getItem(i);
-
- return itemstack.getCount() >= itemstack.getMaxStackSize();
- });
+ return allMatch(inventory, direction, STACK_SIZE_TEST); // Paper - no streams
}
private static boolean isEmptyContainer(Container inv, Direction facing) {
- return HopperBlockEntity.getSlots(inv, facing).allMatch((i) -> {
- return inv.getItem(i).isEmpty();
- });
+ // Paper start
+ return allMatch(inv, facing, IS_EMPTY_TEST);
+ }
+ private static boolean allMatch(Container iinventory, Direction enumdirection, java.util.function.BiPredicate<ItemStack, Integer> test) { + private static boolean allMatch(Container iinventory, Direction enumdirection, java.util.function.BiPredicate<ItemStack, Integer> test) {
+ if (iinventory instanceof WorldlyContainer) { + if (iinventory instanceof WorldlyContainer) {
+ for (int i : ((WorldlyContainer) iinventory).getSlotsForFace(enumdirection)) { + for (int i : ((WorldlyContainer) iinventory).getSlotsForFace(enumdirection)) {
@ -379,10 +330,8 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ } + }
+ } + }
+ return true; + return true;
+ } }
- return itemstack.getCount() >= itemstack.getMaxStackSize();
- });
+ private static boolean anyMatch(Container iinventory, Direction enumdirection, java.util.function.BiPredicate<ItemStack, Integer> test) { + private static boolean anyMatch(Container iinventory, Direction enumdirection, java.util.function.BiPredicate<ItemStack, Integer> test) {
+ if (iinventory instanceof WorldlyContainer) { + if (iinventory instanceof WorldlyContainer) {
+ for (int i : ((WorldlyContainer) iinventory).getSlotsForFace(enumdirection)) { + for (int i : ((WorldlyContainer) iinventory).getSlotsForFace(enumdirection)) {
@ -402,111 +351,53 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ } + }
+ private static final java.util.function.BiPredicate<ItemStack, Integer> STACK_SIZE_TEST = (itemstack, i) -> itemstack.getCount() >= itemstack.getMaxStackSize(); + private static final java.util.function.BiPredicate<ItemStack, Integer> STACK_SIZE_TEST = (itemstack, i) -> itemstack.getCount() >= itemstack.getMaxStackSize();
+ private static final java.util.function.BiPredicate<ItemStack, Integer> IS_EMPTY_TEST = (itemstack, i) -> itemstack.isEmpty(); + private static final java.util.function.BiPredicate<ItemStack, Integer> IS_EMPTY_TEST = (itemstack, i) -> itemstack.isEmpty();
+
+ // Paper end + // Paper end
+ +
+ private boolean isFullContainer(Container inv, Direction enumdirection) { public static boolean suckInItems(Level world, Hopper hopper) {
+ // Paper start - no streams Container iinventory = HopperBlockEntity.getSourceContainer(world, hopper);
+ return allMatch(inv, enumdirection, STACK_SIZE_TEST);
+ // Paper end
}
private static boolean isEmptyContainer(Container inv, Direction facing) {
- return getSlots(inv, facing).allMatch((i) -> {
- return inv.getItem(i).isEmpty();
- });
+ return allMatch(inv, facing, IS_EMPTY_TEST);
}
public static boolean suckInItems(Hopper hopper) {
@@ -270,9 +461,17 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
if (iinventory != null) { if (iinventory != null) {
Direction enumdirection = Direction.DOWN; Direction enumdirection = Direction.DOWN;
- return isEmptyContainer(iinventory, enumdirection) ? false : getSlots(iinventory, enumdirection).anyMatch((i) -> { - return HopperBlockEntity.isEmptyContainer(iinventory, enumdirection) ? false : HopperBlockEntity.getSlots(iinventory, enumdirection).anyMatch((i) -> {
- return tryTakeInItemFromSlot(hopper, iinventory, i, enumdirection); - return HopperBlockEntity.a(hopper, iinventory, i, enumdirection, world); // Spigot
+ // Paper start - optimize hoppers and remove streams + // Paper start - optimize hoppers and remove streams
+ skipPullModeEventFire = skipHopperEvents; + skipPullModeEventFire = skipHopperEvents;
+ return !isEmptyContainer(iinventory, enumdirection) && anyMatch(iinventory, enumdirection, (item, i) -> { + return !HopperBlockEntity.isEmptyContainer(iinventory, enumdirection) && anyMatch(iinventory, enumdirection, (item, i) -> {
+ // Logic copied from below to avoid extra getItem calls + // Logic copied from below to avoid extra getItem calls
+ if (!item.isEmpty() && canTakeItem(iinventory, item, i, enumdirection)) { + if (!item.isEmpty() && canTakeItemFromContainer(iinventory, item, i, enumdirection)) {
+ return hopperPull(hopper, iinventory, item, i); + return hopperPull(hopper, iinventory, item, i);
+ } else { + } else {
+ return false; + return false;
+ } + }
+ // Paper end
}); });
+ // Paper end
} else { } else {
Iterator iterator = getItemsAtAndAbove(hopper).iterator(); Iterator iterator = HopperBlockEntity.getItemsAtAndAbove(world, hopper).iterator();
@@ -290,10 +483,12 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
@@ -290,47 +489,48 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
} }
} }
- private static boolean tryTakeInItemFromSlot(Hopper hopper, Container inventory, int slot, Direction side) { + // Paper - method unused as logic is inlined above
+ private static boolean tryTakeInItemFromSlot(Hopper hopper, Container inventory, int slot, Direction side) {// Paper - method unused as logic is inlined above private static boolean a(Hopper ihopper, Container iinventory, int i, Direction enumdirection, Level world) { // Spigot
ItemStack itemstack = inventory.getItem(slot); ItemStack itemstack = iinventory.getItem(i);
- if (!itemstack.isEmpty() && canTakeItemFromContainer(inventory, itemstack, slot, side)) { - if (!itemstack.isEmpty() && HopperBlockEntity.canTakeItemFromContainer(iinventory, itemstack, i, enumdirection)) {
- ItemStack itemstack1 = itemstack.copy(); + if (!itemstack.isEmpty() && HopperBlockEntity.canTakeItemFromContainer(iinventory, itemstack, i, enumdirection)) { // If this logic changes, update above. this is left inused incase reflective plugins
+ if (!itemstack.isEmpty() && canTakeItemFromContainer(inventory, itemstack, slot, side)) { // If this logic changes, update above. this is left inused incase reflective plugins + return hopperPull(ihopper, iinventory, itemstack, i); /* // Paper - disable rest
+ return hopperPull(hopper, inventory, itemstack, slot); /* // Paper - disable rest ItemStack itemstack1 = itemstack.copy();
+ ItemStack itemstack1 = itemstack.cloneItemStack();
// ItemStack itemstack2 = addItem(iinventory, ihopper, iinventory.splitStack(i, 1), (EnumDirection) null); // ItemStack itemstack2 = addItem(iinventory, ihopper, iinventory.splitStack(i, 1), (EnumDirection) null);
// CraftBukkit start - Call event on collection of items from inventories into the hopper // CraftBukkit start - Call event on collection of items from inventories into the hopper
- CraftItemStack oitemstack = CraftItemStack.asCraftMirror(inventory.removeItem(slot, hopper.getLevel().spigotConfig.hopperAmount)); // Spigot @@ -330,7 +525,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
+ CraftItemStack oitemstack = CraftItemStack.asCraftMirror(iinventory.splitStack(i, ihopper.getWorld().spigotConfig.hopperAmount)); // Spigot
Inventory sourceInventory;
// Have to special case large chests as they work oddly
- if (inventory instanceof CompoundContainer) {
- sourceInventory = new org.bukkit.craftbukkit.inventory.CraftInventoryDoubleChest((CompoundContainer) inventory);
+ if (iinventory instanceof InventoryLargeChest) {
+ sourceInventory = new org.bukkit.craftbukkit.inventory.CraftInventoryDoubleChest((InventoryLargeChest) iinventory);
} else {
- sourceInventory = inventory.getOwner().getInventory();
+ sourceInventory = iinventory.getOwner().getInventory();
} }
- InventoryMoveItemEvent event = new InventoryMoveItemEvent(sourceInventory, oitemstack.clone(), hopper.getOwner().getInventory(), false); itemstack1.shrink(origCount - itemstack2.getCount()); // Spigot
+ InventoryMoveItemEvent event = new InventoryMoveItemEvent(sourceInventory, oitemstack.clone(), ihopper.getOwner().getInventory(), false); - iinventory.setItem(i, itemstack1);
- hopper.getLevel().getCraftServer().getPluginManager().callEvent(event);
+ ihopper.getWorld().getServer().getPluginManager().callEvent(event);
if (event.isCancelled()) {
- inventory.setItem(slot, itemstack1);
+ iinventory.setItem(i, itemstack1);
- if (hopper instanceof HopperBlockEntity) {
- ((HopperBlockEntity) hopper).setCooldown(hopper.getLevel().spigotConfig.hopperTransfer); // Spigot
- } else if (hopper instanceof MinecartHopper) {
- ((MinecartHopper) hopper).setCooldown(hopper.getLevel().spigotConfig.hopperTransfer / 2); // Spigot
+ if (ihopper instanceof TileEntityHopper) {
+ ((TileEntityHopper) ihopper).setCooldown(ihopper.getWorld().spigotConfig.hopperTransfer); // Spigot
+ } else if (ihopper instanceof EntityMinecartHopper) {
+ ((EntityMinecartHopper) ihopper).setCooldown(ihopper.getWorld().spigotConfig.hopperTransfer / 2); // Spigot
}
return false;
}
int origCount = event.getItem().getAmount(); // Spigot
- ItemStack itemstack2 = addItem(inventory, hopper, CraftItemStack.asNMSCopy(event.getItem()), null);
+ ItemStack itemstack2 = addItem(iinventory, ihopper, CraftItemStack.asNMSCopy(event.getItem()), null);
// CraftBukkit end
if (itemstack2.isEmpty()) {
- inventory.setChanged();
+ iinventory.update();
return true;
}
- itemstack1.shrink(origCount - itemstack2.getCount()); // Spigot
- inventory.setItem(slot, itemstack1);
+ itemstack1.subtract(origCount - itemstack2.getCount()); // Spigot
+ iinventory.setItem(i, itemstack1);*/ // Paper - end commenting out replaced block for Hopper Optimizations + iinventory.setItem(i, itemstack1);*/ // Paper - end commenting out replaced block for Hopper Optimizations
} }
return false; return false;
@@ -339,7 +539,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen @@ -339,7 +534,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
public static boolean addItem(Container inventory, ItemEntity itemEntity) { public static boolean addItem(Container inventory, ItemEntity itemEntity) {
boolean flag = false; boolean flag = false;
// CraftBukkit start // CraftBukkit start
@ -515,15 +406,7 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
itemEntity.level.getCraftServer().getPluginManager().callEvent(event); itemEntity.level.getCraftServer().getPluginManager().callEvent(event);
if (event.isCancelled()) { if (event.isCancelled()) {
return false; return false;
@@ -381,6 +581,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen @@ -393,7 +588,9 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
return !inventory.canPlaceItem(slot, stack) ? false : !(inventory instanceof WorldlyContainer) || ((WorldlyContainer) inventory).canPlaceItemThroughFace(slot, stack, side);
}
+ private static boolean canTakeItem(Container iinventory, ItemStack itemstack, int i, Direction enumdirection) { return canTakeItemFromContainer(iinventory, itemstack, i, enumdirection); } // Paper - OBFHELPER
private static boolean canTakeItemFromContainer(Container inv, ItemStack stack, int slot, Direction facing) {
return !(inv instanceof WorldlyContainer) || ((WorldlyContainer) inv).canTakeItemThroughFace(slot, stack, facing);
}
@@ -393,7 +594,9 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
boolean flag1 = to.isEmpty(); boolean flag1 = to.isEmpty();
if (itemstack1.isEmpty()) { if (itemstack1.isEmpty()) {
@ -532,59 +415,53 @@ index 04b0f0de43dfd95e82d402068da8a97bdb86f758..70718fcbaa6f671061479957b7608f76
+ IGNORE_TILE_UPDATES = false; // Paper + IGNORE_TILE_UPDATES = false; // Paper
stack = ItemStack.EMPTY; stack = ItemStack.EMPTY;
flag = true; flag = true;
} else if (canMergeItems(itemstack1, stack)) { } else if (HopperBlockEntity.canMergeItems(itemstack1, stack)) {
@@ -444,20 +647,26 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen @@ -444,18 +641,23 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
} }
public static List<ItemEntity> getItemsAtAndAbove(Hopper ihopper) { public static List<ItemEntity> getItemsAtAndAbove(Level world, Hopper hopper) {
- return (List) ihopper.getSuckShape().toAabbs().stream().flatMap((axisalignedbb) -> { - return (List) hopper.getSuckShape().toAabbs().stream().flatMap((axisalignedbb) -> {
- return ihopper.getLevel().getEntitiesOfClass(ItemEntity.class, axisalignedbb.move(ihopper.getLevelX() - 0.5D, ihopper.getLevelY() - 0.5D, ihopper.getLevelZ() - 0.5D), EntitySelector.ENTITY_STILL_ALIVE).stream(); - return world.getEntitiesOfClass(ItemEntity.class, axisalignedbb.move(hopper.getLevelX() - 0.5D, hopper.getLevelY() - 0.5D, hopper.getLevelZ() - 0.5D), EntitySelector.ENTITY_STILL_ALIVE).stream();
- }).collect(Collectors.toList()); - }).collect(Collectors.toList());
+ // Paper start - Optimize item suck in. remove streams, restore 1.12 checks. Seriously checking the bowl?! + // Paper start - Optimize item suck in. remove streams, restore 1.12 checks. Seriously checking the bowl?!
+ Level world = ihopper.getLevel(); + double d0 = hopper.getLevelX();
+ double d0 = ihopper.getX(); + double d1 = hopper.getLevelY();
+ double d1 = ihopper.getY(); + double d2 = hopper.getLevelZ();
+ double d2 = ihopper.getZ();
+ AABB bb = new AABB(d0 - 0.5D, d1, d2 - 0.5D, d0 + 0.5D, d1 + 1.5D, d2 + 0.5D); + AABB bb = new AABB(d0 - 0.5D, d1, d2 - 0.5D, d0 + 0.5D, d1 + 1.5D, d2 + 0.5D);
+ return world.getEntities(ItemEntity.class, bb, Entity::isAlive); + return world.getEntitiesOfClass(ItemEntity.class, bb, Entity::isAlive);
+ // Paper end + // Paper end
} }
@Nullable @Nullable
public static Container getContainerAt(Level world, BlockPos blockposition) { public static Container getContainerAt(Level world, BlockPos pos) {
- return getContainerAt(world, (double) blockposition.getX() + 0.5D, (double) blockposition.getY() + 0.5D, (double) blockposition.getZ() + 0.5D); - return HopperBlockEntity.getContainerAt(world, (double) pos.getX() + 0.5D, (double) pos.getY() + 0.5D, (double) pos.getZ() + 0.5D);
+ return a(world, (double) blockposition.getX() + 0.5D, (double) blockposition.getY() + 0.5D, (double) blockposition.getZ() + 0.5D, true); // Paper + return HopperBlockEntity.getContainerAt(world, (double) pos.getX() + 0.5D, (double) pos.getY() + 0.5D, (double) pos.getZ() + 0.5D, true); // Paper
} }
+ public static Container getContainerAt(Level world, double x, double y, double z) { return getContainerAt(world, x, y, z, false); } // Paper - overload to default false
@Nullable @Nullable
- public static Container getContainerAt(Level world, double x, double y, double z) { - private static Container getContainerAt(Level world, double x, double y, double z) {
+ public static Container getContainerAt(Level world, double x, double y, double z) { return a(world, x, y, z, false); } // Paper - overload to default false + private static Container getContainerAt(Level world, double x, double y, double z, boolean optimizeEntities) {
+ public static Container a(Level world, double d0, double d1, double d2, boolean optimizeEntities) { // Paper
Object object = null; Object object = null;
- BlockPos blockposition = new BlockPos(x, y, z); BlockPos blockposition = new BlockPos(x, y, z);
+ BlockPos blockposition = new BlockPos(d0, d1, d2);
if ( !world.hasChunkAt( blockposition ) ) return null; // Spigot if ( !world.hasChunkAt( blockposition ) ) return null; // Spigot
BlockState iblockdata = world.getBlockState(blockposition); @@ -475,7 +677,7 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
Block block = iblockdata.getBlock();
@@ -475,8 +684,8 @@ public class HopperBlockEntity extends RandomizableContainerBlockEntity implemen
} }
} }
- if (object == null) { - if (object == null) {
- List<Entity> list = world.getEntities((Entity) null, new AABB(x - 0.5D, y - 0.5D, z - 0.5D, x + 0.5D, y + 0.5D, z + 0.5D), EntitySelector.CONTAINER_ENTITY_SELECTOR);
+ if (object == null && (!optimizeEntities || !org.bukkit.craftbukkit.util.CraftMagicNumbers.getMaterial(block).isOccluding())) { // Paper + if (object == null && (!optimizeEntities || !org.bukkit.craftbukkit.util.CraftMagicNumbers.getMaterial(block).isOccluding())) { // Paper
+ List<Entity> list = world.getEntities((Entity) null, new AABB(d0 - 0.5D, d1 - 0.5D, d2 - 0.5D, d0 + 0.5D, d1 + 0.5D, d2 + 0.5D), EntitySelector.CONTAINER_ENTITY_SELECTOR); List<Entity> list = world.getEntities((Entity) null, new AABB(x - 0.5D, y - 0.5D, z - 0.5D, x + 0.5D, y + 0.5D, z + 0.5D), EntitySelector.CONTAINER_ENTITY_SELECTOR);
if (!list.isEmpty()) { if (!list.isEmpty()) {
object = (Container) list.get(world.random.nextInt(list.size()));
diff --git a/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java diff --git a/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java
index 5ad419941ff1113ef29b9a4593f44d8f35ba8424..4525032232b5a89de13c6a46dc489a07428e3f21 100644 index f23fff80d07ac7d06715efe67cb49ebbe704967b..ed3518fe7c841d9e1a9c97626acaa3d765a6d76f 100644
--- a/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java --- a/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java
+++ b/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java +++ b/src/main/java/net/minecraft/world/level/block/entity/RandomizableContainerBlockEntity.java
@@ -97,12 +97,19 @@ public abstract class RandomizableContainerBlockEntity extends BaseContainerBloc @@ -95,12 +95,19 @@ public abstract class RandomizableContainerBlockEntity extends BaseContainerBloc
@Override @Override
public boolean isEmpty() { public boolean isEmpty() {
this.unpackLootTable((Player) null); this.unpackLootTable((Player)null);
- return this.getItems().stream().allMatch(ItemStack::isEmpty); - return this.getItems().stream().allMatch(ItemStack::isEmpty);
+ // Paper start + // Paper start
+ for (ItemStack itemStack : this.getItems()) { + for (ItemStack itemStack : this.getItems()) {
@ -598,8 +475,8 @@ index 5ad419941ff1113ef29b9a4593f44d8f35ba8424..4525032232b5a89de13c6a46dc489a07
@Override @Override
public ItemStack getItem(int slot) { public ItemStack getItem(int slot) {
- this.unpackLootTable((Player) null); - this.unpackLootTable((Player)null);
+ if (slot == 0) this.unpackLootTable((Player) null); // Paper + if (slot == 0) this.unpackLootTable((Player) null); // Paper
return (ItemStack) this.getItems().get(slot); return this.getItems().get(slot);
} }

View File

@ -5,10 +5,10 @@ Subject: [PATCH] PlayerDeathEvent#shouldDropExperience
diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java
index 2ef273e3b917803f3e2ac3c6a22d92a15b9eb71a..7f4e81ee3339e90b8525541dccf6dea187853cf7 100644 index 8da35a7dde494b059e542d049d7ee039deb5833d..4fef4c0240be90ddcb9640f5719e292d2d5dbdf8 100644
--- a/src/main/java/net/minecraft/server/level/ServerPlayer.java --- a/src/main/java/net/minecraft/server/level/ServerPlayer.java
+++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java +++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java
@@ -819,7 +819,7 @@ public class ServerPlayer extends Player implements ContainerListener { @@ -849,7 +849,7 @@ public class ServerPlayer extends Player {
this.tellNeutralMobsThatIDied(); this.tellNeutralMobsThatIDied();
} }
// SPIGOT-5478 must be called manually now // SPIGOT-5478 must be called manually now
@ -16,4 +16,4 @@ index 2ef273e3b917803f3e2ac3c6a22d92a15b9eb71a..7f4e81ee3339e90b8525541dccf6dea1
+ if (event.shouldDropExperience()) this.dropExperience(); // Paper - tie to event + if (event.shouldDropExperience()) this.dropExperience(); // Paper - tie to event
// we clean the player's inventory after the EntityDeathEvent is called so plugins can get the exact state of the inventory. // we clean the player's inventory after the EntityDeathEvent is called so plugins can get the exact state of the inventory.
if (!event.getKeepInventory()) { if (!event.getKeepInventory()) {
// Paper start - replace logic this.getInventory().clearContent();

View File

@ -5,10 +5,10 @@ Subject: [PATCH] Prevent bees loading chunks checking hive position
diff --git a/src/main/java/net/minecraft/world/entity/animal/Bee.java b/src/main/java/net/minecraft/world/entity/animal/Bee.java diff --git a/src/main/java/net/minecraft/world/entity/animal/Bee.java b/src/main/java/net/minecraft/world/entity/animal/Bee.java
index 32ee38142a3053091ab7b3fb3d608d268b07d4e3..edd6d63f715acef1a77eba0cf46ff8267228f4c6 100644 index 488dd4693dbbc303f0fc6d98667b822304b06c9f..f3ba4b26553915917c79f013ed9dd7c87d9f65a4 100644
--- a/src/main/java/net/minecraft/world/entity/animal/Bee.java --- a/src/main/java/net/minecraft/world/entity/animal/Bee.java
+++ b/src/main/java/net/minecraft/world/entity/animal/Bee.java +++ b/src/main/java/net/minecraft/world/entity/animal/Bee.java
@@ -442,6 +442,7 @@ public class Bee extends Animal implements NeutralMob, FlyingAnimal { @@ -495,6 +495,7 @@ public class Bee extends Animal implements NeutralMob, FlyingAnimal {
if (!this.hasHive()) { if (!this.hasHive()) {
return false; return false;
} else { } else {

View File

@ -13,20 +13,20 @@ This of course is undesirable, so just return the loaded side as "primary"
and treat it as a single chest if the other sides are unloaded and treat it as a single chest if the other sides are unloaded
diff --git a/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java b/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java diff --git a/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java b/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java
index a4f16b2093c867e9fd1c2e07b67c49c3c5ec7506..df20b3616929657d2e8061159ed97f500b33d192 100644 index ff2a7b08fe70adaecdaa508baadcfe40416519e0..7082bb0b28b6a046e3925f69e18b7c319871128f 100644
--- a/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java --- a/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java
+++ b/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java +++ b/src/main/java/net/minecraft/world/level/block/DoubleBlockCombiner.java
@@ -29,7 +29,12 @@ public class DoubleBlockCombiner { @@ -25,7 +25,12 @@ public class DoubleBlockCombiner {
return new DoubleBlockCombiner.NeighborCombineResult.Single<>(s0); return new DoubleBlockCombiner.NeighborCombineResult.Single<>(blockEntity);
} else { } else {
BlockPos blockposition1 = pos.relative((Direction) function1.apply(state)); BlockPos blockPos = pos.relative(function.apply(state));
- BlockState iblockdata1 = world.getBlockState(blockposition1); - BlockState blockState = world.getBlockState(blockPos);
+ // Paper start + // Paper start
+ BlockState iblockdata1 = world.getTypeIfLoaded(blockposition1); + BlockState blockState = world.getTypeIfLoaded(blockPos);
+ if (iblockdata1 == null) { + if (blockState == null) {
+ return new DoubleBlockCombiner.NeighborCombineResult.Single<>(s0); + return new DoubleBlockCombiner.NeighborCombineResult.Single<>(blockEntity);
+ } + }
+ // Paper end + // Paper end
if (blockState.is(state.getBlock())) {
if (iblockdata1.is(state.getBlock())) { DoubleBlockCombiner.BlockType blockType2 = typeMapper.apply(blockState);
DoubleBlockCombiner.BlockType doubleblockfinder_blocktype1 = (DoubleBlockCombiner.BlockType) typeMapper.apply(iblockdata1); if (blockType2 != DoubleBlockCombiner.BlockType.SINGLE && blockType != blockType2 && blockState.getValue(directionProperty) == state.getValue(directionProperty)) {

View File

@ -0,0 +1,54 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Spottedleaf <Spottedleaf@users.noreply.github.com>
Date: Fri, 27 Dec 2019 09:42:26 -0800
Subject: [PATCH] Guard against serializing mismatching chunk coordinate
Should help if something dumb happens
diff --git a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
index 3cb35f2f47ba841915ac2825d30cc4c3274ce3c4..7c04aef3eac54981ca1e34cb87d97104c3c9685b 100644
--- a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
+++ b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkSerializer.java
@@ -69,6 +69,13 @@ public class ChunkSerializer {
public ChunkSerializer() {}
+ // Paper start - guard against serializing mismatching coordinates
+ // TODO Note: This needs to be re-checked each update
+ public static ChunkPos getChunkCoordinate(CompoundTag chunkData) {
+ CompoundTag levelData = chunkData.getCompound("Level");
+ return new ChunkPos(levelData.getInt("xPos"), levelData.getInt("zPos"));
+ }
+ // Paper end
// Paper start
public static final class InProgressChunkHolder {
@@ -95,8 +102,8 @@ public class ChunkSerializer {
// Paper end
ChunkGenerator chunkgenerator = world.getChunkSource().getGenerator();
BiomeSource worldchunkmanager = chunkgenerator.getBiomeSource();
- CompoundTag nbttagcompound1 = nbt.getCompound("Level");
- ChunkPos chunkcoordintpair1 = new ChunkPos(nbttagcompound1.getInt("xPos"), nbttagcompound1.getInt("zPos"));
+ CompoundTag nbttagcompound1 = nbt.getCompound("Level"); // Paper - diff on change, see ChunkSerializer#getChunkCoordinate
+ ChunkPos chunkcoordintpair1 = new ChunkPos(nbttagcompound1.getInt("xPos"), nbttagcompound1.getInt("zPos")); // Paper - diff on change, see ChunkSerializer#getChunkCoordinate
if (!Objects.equals(pos, chunkcoordintpair1)) {
ChunkSerializer.LOGGER.error("Chunk file at {} is in the wrong location; relocating. (Expected {}, got {})", pos, pos, chunkcoordintpair1);
diff --git a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
index 6f13c7adce7d4b3d170045ea5ef2a841d34ae7b0..176610b31f66b890afe61f4de46c412382bb8d22 100644
--- a/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
+++ b/src/main/java/net/minecraft/world/level/chunk/storage/ChunkStorage.java
@@ -117,6 +117,13 @@ public class ChunkStorage implements AutoCloseable {
// Paper start - async chunk io
public void write(ChunkPos chunkPos, CompoundTag nbt) throws IOException {
+ // Paper start
+ if (!chunkPos.equals(ChunkSerializer.getChunkCoordinate(nbt))) {
+ String world = (this instanceof net.minecraft.server.level.ChunkMap) ? ((net.minecraft.server.level.ChunkMap)this).level.getWorld().getName() : null;
+ throw new IllegalArgumentException("Chunk coordinate and serialized data do not have matching coordinates, trying to serialize coordinate " + chunkPos.toString()
+ + " but compound says coordinate is " + ChunkSerializer.getChunkCoordinate(nbt).toString() + (world == null ? " for an unknown world" : (" for world: " + world)));
+ }
+ // Paper end
this.regionFileCache.write(chunkPos, nbt);
// Paper end - Async chunk loading
if (this.legacyStructureHandler != null) {

View File

@ -6,39 +6,21 @@ Subject: [PATCH] Optimise IEntityAccess#getPlayerByUUID
Use the world entity map instead of iterating over all players Use the world entity map instead of iterating over all players
diff --git a/src/main/java/net/minecraft/server/level/ServerLevel.java b/src/main/java/net/minecraft/server/level/ServerLevel.java diff --git a/src/main/java/net/minecraft/server/level/ServerLevel.java b/src/main/java/net/minecraft/server/level/ServerLevel.java
index 01f879a8dd0e1ffec380e02072567330152eaceb..40d7dbc4f1deda88d4a539b89d84b595217051b6 100644 index 736521c0925339dc74c2648641932104a947708e..eabf8fa6e8802ebea8dbe124363bb085849af5d9 100644
--- a/src/main/java/net/minecraft/server/level/ServerLevel.java --- a/src/main/java/net/minecraft/server/level/ServerLevel.java
+++ b/src/main/java/net/minecraft/server/level/ServerLevel.java +++ b/src/main/java/net/minecraft/server/level/ServerLevel.java
@@ -283,6 +283,15 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl @@ -281,6 +281,14 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
} public final com.destroystokyo.paper.io.chunk.ChunkTaskManager asyncChunkTaskManager;
// Paper end // Paper end
+ // Paper start - optimise getPlayerByUUID + // Paper start - optimise getPlayerByUUID
+ @Nullable + @Nullable
+ @Override + @Override
+ public Player getPlayerByUUID(UUID uuid) { + public Player getPlayerByUUID(UUID uuid) {
+ Entity player = this.entitiesByUuid.get(uuid); + return this.getServer().getPlayerList().getPlayer(uuid);
+ return (player instanceof Player) ? (Player)player : null;
+ } + }
+ // Paper end + // Paper end
+ +
// Add env and gen to constructor, WorldData -> WorldDataServer // Add env and gen to constructor, WorldData -> WorldDataServer
public ServerLevel(MinecraftServer minecraftserver, Executor executor, LevelStorageSource.LevelStorageAccess convertable_conversionsession, ServerLevelData iworlddataserver, ResourceKey<net.minecraft.world.level.Level> resourcekey, DimensionType dimensionmanager, ChunkProgressListener worldloadlistener, ChunkGenerator chunkgenerator, boolean flag, long i, List<CustomSpawner> list, boolean flag1, org.bukkit.World.Environment env, org.bukkit.generator.ChunkGenerator gen) { public ServerLevel(MinecraftServer minecraftserver, Executor executor, LevelStorageSource.LevelStorageAccess convertable_conversionsession, ServerLevelData iworlddataserver, ResourceKey<net.minecraft.world.level.Level> resourcekey, DimensionType dimensionmanager, ChunkProgressListener worldloadlistener, ChunkGenerator chunkgenerator, boolean flag, long i, List<CustomSpawner> list, boolean flag1, org.bukkit.World.Environment env, org.bukkit.generator.ChunkGenerator gen) {
super(iworlddataserver, resourcekey, dimensionmanager, minecraftserver::getProfiler, false, flag, i, gen, env, executor); // Paper pass executor // Objects.requireNonNull(minecraftserver); // CraftBukkit - decompile error
diff --git a/src/main/java/net/minecraft/world/level/EntityGetter.java b/src/main/java/net/minecraft/world/level/EntityGetter.java
index 6a5430fe54a5c8ad119a0f3842961825a54d8d7a..b9606465ace8b320eafbbad3d60c01b87a859c44 100644
--- a/src/main/java/net/minecraft/world/level/EntityGetter.java
+++ b/src/main/java/net/minecraft/world/level/EntityGetter.java
@@ -277,6 +277,12 @@ public interface EntityGetter {
@Nullable
default Player getPlayerByUUID(UUID uuid) {
+ // Paper start - allow WorldServer to override
+ return this.getPlayerByUUID(uuid);
+ }
+ @Nullable
+ default Player getPlayerByUUID(UUID uuid) {
+ // Paper end
for (int i = 0; i < this.players().size(); ++i) {
Player entityhuman = (Player) this.players().get(i);

View File

@ -15,15 +15,15 @@ This patch resolves the conflict by offsetting checking an item's
move method from Spigot's entity activation range check. move method from Spigot's entity activation range check.
diff --git a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java diff --git a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
index 96b8102773cbee2c3fe2711008ba1487084d67b0..9311f9f411d09d4460f0be8235957fab9e195b7a 100644 index 82ffe3624943d2e931e2cc2f85ede94f369bd06b..9ee1dc89dd4c6b9453e1f6f92208d454877d23c9 100644
--- a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java --- a/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
+++ b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java +++ b/src/main/java/net/minecraft/world/entity/item/ItemEntity.java
@@ -115,7 +115,7 @@ public class ItemEntity extends Entity { @@ -135,7 +135,7 @@ public class ItemEntity extends Entity {
} }
} }
- if (!this.onGround || getHorizontalDistanceSqr(this.getDeltaMovement()) > 9.999999747378752E-6D || (this.tickCount + this.getId()) % 4 == 0) { - if (!this.onGround || this.getDeltaMovement().horizontalDistanceSqr() > 9.999999747378752E-6D || (this.tickCount + this.getId()) % 4 == 0) {
+ if (!this.onGround || getHorizontalDistanceSqr(this.getDeltaMovement()) > 9.999999747378752E-6D || this.tickCount % 4 == 0) { // Paper - Ensure checking item movement is always offset from Spigot's entity activation range check + if (!this.onGround || this.getDeltaMovement().horizontalDistanceSqr() > 9.999999747378752E-6D || this.tickCount % 4 == 0) { // Paper - Ensure checking item movement is always offset from Spigot's entity activation range check
this.move(MoverType.SELF, this.getDeltaMovement()); this.move(MoverType.SELF, this.getDeltaMovement());
float f1 = 0.98F; float f1 = 0.98F;

View File

@ -7,19 +7,10 @@ When the server is lagging, players will wait longer when eating.
Change to also use a time check instead if it passes. Change to also use a time check instead if it passes.
diff --git a/src/main/java/net/minecraft/world/entity/LivingEntity.java b/src/main/java/net/minecraft/world/entity/LivingEntity.java diff --git a/src/main/java/net/minecraft/world/entity/LivingEntity.java b/src/main/java/net/minecraft/world/entity/LivingEntity.java
index b49d4772932a58852b3195f5f56ff93dbcabf766..016fcc4ae20e1e48728a848be28633e624ae49a7 100644 index 5def2e0379373b126a1b2281b0859b39443fc4ac..f48435dc344fb48feb48e2a141b394829058c5c4 100644
--- a/src/main/java/net/minecraft/world/entity/LivingEntity.java --- a/src/main/java/net/minecraft/world/entity/LivingEntity.java
+++ b/src/main/java/net/minecraft/world/entity/LivingEntity.java +++ b/src/main/java/net/minecraft/world/entity/LivingEntity.java
@@ -211,7 +211,7 @@ public abstract class LivingEntity extends Entity { @@ -3492,6 +3492,11 @@ public abstract class LivingEntity extends Entity {
private int noJumpDelay;
private float absorptionAmount;
public ItemStack useItem; // Paper - public
- protected int useItemRemaining;
+ protected int useItemRemaining; protected final int getEatTimeTicks() { return this.useItemRemaining; } protected final void setEatTimeTicks(int value) { this.useItemRemaining = value; } // Paper - OBFHELPER
protected int fallFlyTicks;
private BlockPos lastPos;
private Optional<BlockPos> lastClimbablePos;
@@ -3148,6 +3148,11 @@ public abstract class LivingEntity extends Entity {
return ((Byte) this.entityData.get(LivingEntity.DATA_LIVING_ENTITY_FLAGS) & 2) > 0 ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND; return ((Byte) this.entityData.get(LivingEntity.DATA_LIVING_ENTITY_FLAGS) & 2) > 0 ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND;
} }
@ -31,21 +22,22 @@ index b49d4772932a58852b3195f5f56ff93dbcabf766..016fcc4ae20e1e48728a848be28633e6
private void updatingUsingItem() { private void updatingUsingItem() {
if (this.isUsingItem()) { if (this.isUsingItem()) {
if (ItemStack.isSameIgnoreDurability(this.getItemInHand(this.getUsedItemHand()), this.useItem)) { if (ItemStack.isSameIgnoreDurability(this.getItemInHand(this.getUsedItemHand()), this.useItem)) {
@@ -3157,7 +3162,12 @@ public abstract class LivingEntity extends Entity { @@ -3509,8 +3514,12 @@ public abstract class LivingEntity extends Entity {
this.triggerItemUseEffects(this.useItem, 5); if (this.shouldTriggerItemUseEffects()) {
} this.triggerItemUseEffects(stack, 5);
}
-
- if (--this.useItemRemaining == 0 && !this.level.isClientSide && !stack.useOnRelease()) {
+ // Paper start - lag compensate eating
+ // we add 1 to the expected time to avoid lag compensating when we should not
+ boolean shouldLagCompensate = this.useItem.getItem().isEdible() && this.eatStartTime != -1 && (System.nanoTime() - this.eatStartTime) > ((1 + this.totalEatTimeTicks) * 50 * (1000 * 1000));
+ if ((--this.useItemRemaining == 0 || shouldLagCompensate) && !this.level.isClientSide && !this.useItem.useOnRelease()) {
+ this.useItemRemaining = 0;
+ // Paper end
this.completeUsingItem();
}
- if (--this.useItemRemaining == 0 && !this.level.isClientSide && !this.useItem.useOnRelease()) { @@ -3556,7 +3565,10 @@ public abstract class LivingEntity extends Entity {
+ // Paper start - lag compensate eating
+ // we add 1 to the expected time to avoid lag compensating when we should not
+ boolean shouldLagCompensate = this.useItem.getItem().isEdible() && this.eatStartTime != -1 && (System.nanoTime() - this.eatStartTime) > ((1 + this.totalEatTimeTicks) * 50 * (1000 * 1000));
+ if ((--this.useItemRemaining == 0 || shouldLagCompensate) && !this.level.isClientSide && !this.useItem.useOnRelease()) {
+ this.setEatTimeTicks(0);
+ // Paper end
this.completeUsingItem();
}
} else {
@@ -3207,7 +3217,10 @@ public abstract class LivingEntity extends Entity {
if (!itemstack.isEmpty() && !this.isUsingItem() || forceUpdate) { // Paper use override flag if (!itemstack.isEmpty() && !this.isUsingItem() || forceUpdate) { // Paper use override flag
this.useItem = itemstack; this.useItem = itemstack;
@ -57,7 +49,7 @@ index b49d4772932a58852b3195f5f56ff93dbcabf766..016fcc4ae20e1e48728a848be28633e6
if (!this.level.isClientSide) { if (!this.level.isClientSide) {
this.setLivingEntityFlag(1, true); this.setLivingEntityFlag(1, true);
this.setLivingEntityFlag(2, enumhand == InteractionHand.OFF_HAND); this.setLivingEntityFlag(2, enumhand == InteractionHand.OFF_HAND);
@@ -3231,7 +3244,10 @@ public abstract class LivingEntity extends Entity { @@ -3580,7 +3592,10 @@ public abstract class LivingEntity extends Entity {
} }
} else if (!this.isUsingItem() && !this.useItem.isEmpty()) { } else if (!this.isUsingItem() && !this.useItem.isEmpty()) {
this.useItem = ItemStack.EMPTY; this.useItem = ItemStack.EMPTY;
@ -69,7 +61,7 @@ index b49d4772932a58852b3195f5f56ff93dbcabf766..016fcc4ae20e1e48728a848be28633e6
} }
} }
@@ -3359,7 +3375,10 @@ public abstract class LivingEntity extends Entity { @@ -3706,7 +3721,10 @@ public abstract class LivingEntity extends Entity {
} }
this.useItem = ItemStack.EMPTY; this.useItem = ItemStack.EMPTY;

View File

@ -5,15 +5,15 @@ Subject: [PATCH] Optimize call to getFluid for explosions
diff --git a/src/main/java/net/minecraft/world/level/Explosion.java b/src/main/java/net/minecraft/world/level/Explosion.java diff --git a/src/main/java/net/minecraft/world/level/Explosion.java b/src/main/java/net/minecraft/world/level/Explosion.java
index 45a75f7be308678336e192828becf6cf5c9047bc..667a6d645034c67639c01b8221591877bcb87b35 100644 index edc0845ae735a9cf3e0f1a3a2b7eabf726d62744..cdf214fca3b0055efa56702470d9d2f890a8aead 100644
--- a/src/main/java/net/minecraft/world/level/Explosion.java --- a/src/main/java/net/minecraft/world/level/Explosion.java
+++ b/src/main/java/net/minecraft/world/level/Explosion.java +++ b/src/main/java/net/minecraft/world/level/Explosion.java
@@ -151,7 +151,7 @@ public class Explosion { @@ -174,7 +174,7 @@ public class Explosion {
for (float f1 = 0.3F; f > 0.0F; f -= 0.22500001F) { for (float f1 = 0.3F; f > 0.0F; f -= 0.22500001F) {
BlockPos blockposition = new BlockPos(d4, d5, d6); BlockPos blockposition = new BlockPos(d4, d5, d6);
BlockState iblockdata = this.level.getBlockState(blockposition); BlockState iblockdata = this.level.getBlockState(blockposition);
- FluidState fluid = this.level.getFluidState(blockposition); - FluidState fluid = this.level.getFluidState(blockposition);
+ FluidState fluid = iblockdata.getFluidState(); // Paper + FluidState fluid = iblockdata.getFluidState(); // Paper
Optional<Float> optional = this.damageCalculator.a(this, this.level, blockposition, iblockdata, fluid);
if (optional.isPresent()) { if (!this.level.isInWorldBounds(blockposition)) {
break;

View File

@ -9,10 +9,10 @@ dispensed. The resulting item would have size == 0 and therefore
be convertered to air, hence why the effects disappeared. be convertered to air, hence why the effects disappeared.
diff --git a/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java b/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java diff --git a/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java b/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java
index 67a894a185a3d4a53b3c7f90174b2604dff18257..67d140dff483bfc654a0390e0cdcd13aa658a62d 100644 index b665d4293b746b221d469a7b029c1c7f17df6188..92623ae25249d63efb92be8bd6c95228f9155ad2 100644
--- a/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java --- a/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java
+++ b/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java +++ b/src/main/java/net/minecraft/core/dispenser/DispenseItemBehavior.java
@@ -425,7 +425,7 @@ public interface DispenseItemBehavior { @@ -431,7 +431,7 @@ public interface DispenseItemBehavior {
} }
itemstack1 = CraftItemStack.asNMSCopy(event.getItem()); itemstack1 = CraftItemStack.asNMSCopy(event.getItem());

View File

@ -5,10 +5,10 @@ Subject: [PATCH] Add effect to block break naturally
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
index 5bff313dbbb3049105874846d995883e827fbc00..05f0833f762436bf8f5f5875c7e3cfed1da11e1c 100644 index 0a9ed9992a2fc97472a06591a5d129a767ce21af..ca95a6b1b156b37f839c6479733e5184691af66c 100644
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java --- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java +++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
@@ -630,6 +630,13 @@ public class CraftBlock implements Block { @@ -632,6 +632,13 @@ public class CraftBlock implements Block {
@Override @Override
public boolean breakNaturally(ItemStack item) { public boolean breakNaturally(ItemStack item) {
@ -22,10 +22,10 @@ index 5bff313dbbb3049105874846d995883e827fbc00..05f0833f762436bf8f5f5875c7e3cfed
// Order matters here, need to drop before setting to air so skulls can get their data // Order matters here, need to drop before setting to air so skulls can get their data
net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS(); net.minecraft.world.level.block.state.BlockState iblockdata = this.getNMS();
net.minecraft.world.level.block.Block block = iblockdata.getBlock(); net.minecraft.world.level.block.Block block = iblockdata.getBlock();
@@ -639,6 +646,7 @@ public class CraftBlock implements Block { @@ -641,6 +648,7 @@ public class CraftBlock implements Block {
// Modelled off EntityHuman#hasBlock // Modelled off EntityHuman#hasBlock
if (block != Blocks.AIR && (item == null || !iblockdata.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(iblockdata))) { if (block != Blocks.AIR && (item == null || !iblockdata.requiresCorrectToolForDrops() || nmsItem.isCorrectToolForDrops(iblockdata))) {
net.minecraft.world.level.block.Block.dropResources(iblockdata, world.getLevel(), position, world.getBlockEntity(position), null, nmsItem); net.minecraft.world.level.block.Block.dropResources(iblockdata, this.world.getMinecraftWorld(), position, this.world.getBlockEntity(position), null, nmsItem);
+ if (triggerEffect) world.levelEvent(org.bukkit.Effect.STEP_SOUND.getId(), position, net.minecraft.world.level.block.Block.getId(block.defaultBlockState())); // Paper + if (triggerEffect) world.levelEvent(org.bukkit.Effect.STEP_SOUND.getId(), position, net.minecraft.world.level.block.Block.getId(block.defaultBlockState())); // Paper
result = true; result = true;
} }

View File

@ -14,111 +14,120 @@ Adds flying monsters to control ghast and phantoms
Adds villagers as separate config Adds villagers as separate config
diff --git a/src/main/java/net/minecraft/server/level/ServerLevel.java b/src/main/java/net/minecraft/server/level/ServerLevel.java diff --git a/src/main/java/net/minecraft/server/level/ServerLevel.java b/src/main/java/net/minecraft/server/level/ServerLevel.java
index 40d7dbc4f1deda88d4a539b89d84b595217051b6..bf1bb1530037ebcacc8d5a491789909bddb8b697 100644 index eabf8fa6e8802ebea8dbe124363bb085849af5d9..67b9daee8d7e55fdf2015e6616f393f176b1ca96 100644
--- a/src/main/java/net/minecraft/server/level/ServerLevel.java --- a/src/main/java/net/minecraft/server/level/ServerLevel.java
+++ b/src/main/java/net/minecraft/server/level/ServerLevel.java +++ b/src/main/java/net/minecraft/server/level/ServerLevel.java
@@ -855,17 +855,17 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl @@ -2,7 +2,6 @@ package net.minecraft.server.level;
++TimingHistory.entityTicks; // Paper - timings
// Spigot start
co.aikar.timings.Timing timer; // Paper
- if (!org.spigotmc.ActivationRange.checkIfActive(entity)) {
- entity.tickCount++;
- timer = entity.getType().inactiveTickTimer.startTiming(); try { // Paper - timings
+ /*if (!org.spigotmc.ActivationRange.checkIfActive(entity)) { // Paper - comment out - EAR 2, reimplement below
+ entity.ticksLived++;
+ timer = entity.getEntityType().inactiveTickTimer.startTiming(); try { // Paper - timings
entity.inactiveTick();
} finally { timer.stopTiming(); } // Paper
return;
- }
+ }*/ // Paper - comment out EAR 2
// Spigot end
// Paper start- timings
- TimingHistory.activatedEntityTicks++;
- timer = entity.getVehicle() != null ? entity.getType().passengerTickTimer.startTiming() : entity.getType().tickTimer.startTiming();
+ final boolean isActive = org.spigotmc.ActivationRange.checkIfActive(entity);
+ timer = isActive ? entity.getType().tickTimer.startTiming() : entity.getType().inactiveTickTimer.startTiming(); // Paper
try {
// Paper end - timings
entity.setPosAndOldPos(entity.getX(), entity.getY(), entity.getZ());
@@ -879,12 +879,16 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
return Registry.ENTITY_TYPE.getKey(entity.getType()).toString();
});
gameprofilerfiller.incrementCounter("tickNonPassenger");
+ if (isActive) { // Paper - EAR 2
+ TimingHistory.activatedEntityTicks++; // Paper
entity.tick();
entity.postTick(); // CraftBukkit
+ } else { entity.inactiveTick(); } // Paper - EAR 2
gameprofilerfiller.pop();
}
this.updateChunkPos(entity); import com.google.common.annotations.VisibleForTesting;
+ } finally { timer.stopTiming(); } // Paper - timings import co.aikar.timings.TimingHistory; // Paper
if (entity.inChunk) { -import co.aikar.timings.Timings; // Paper
Iterator iterator = entity.getPassengers().iterator(); import com.google.common.collect.Lists;
import com.mojang.datafixers.DataFixer;
@@ -894,7 +898,7 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
this.tickPassenger(entity, entity1); @@ -11,7 +10,6 @@ import it.unimi.dsi.fastutil.longs.LongSet;
} import it.unimi.dsi.fastutil.longs.LongSets;
} import it.unimi.dsi.fastutil.objects.Object2IntMap.Entry;
- } finally { timer.stopTiming(); } // Paper - timings import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap;
+ //} finally { timer.stopTiming(); } // Paper - timings - move up -import it.unimi.dsi.fastutil.objects.Object2IntMap;
import it.unimi.dsi.fastutil.objects.ObjectIterator;
import it.unimi.dsi.fastutil.objects.ObjectLinkedOpenHashSet;
import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet;
@@ -123,7 +121,6 @@ import net.minecraft.world.level.chunk.LevelChunkSection;
import net.minecraft.world.level.chunk.storage.EntityStorage;
import net.minecraft.world.level.dimension.DimensionType;
import net.minecraft.world.level.dimension.end.EndDragonFight;
-import net.minecraft.world.level.entity.EntityAccess;
import net.minecraft.world.level.entity.EntityPersistentStorage;
import net.minecraft.world.level.entity.EntityTickList;
import net.minecraft.world.level.entity.EntityTypeTest;
@@ -888,17 +885,17 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
++TimingHistory.entityTicks; // Paper - timings
// Spigot start
co.aikar.timings.Timing timer; // Paper
- if (!org.spigotmc.ActivationRange.checkIfActive(entity)) {
+ /*if (!org.spigotmc.ActivationRange.checkIfActive(entity)) { // Paper - comment out - EAR 2, reimplement below
entity.tickCount++;
timer = entity.getType().inactiveTickTimer.startTiming(); try { // Paper - timings
entity.inactiveTick();
} finally { timer.stopTiming(); } // Paper
return;
- }
+ }*/ // Paper - comment out EAR 2
// Spigot end
// Paper start- timings
- TimingHistory.activatedEntityTicks++;
- timer = entity.getVehicle() != null ? entity.getType().passengerTickTimer.startTiming() : entity.getType().tickTimer.startTiming();
+ final boolean isActive = org.spigotmc.ActivationRange.checkIfActive(entity);
+ timer = isActive ? entity.getType().tickTimer.startTiming() : entity.getType().inactiveTickTimer.startTiming(); // Paper
try {
// Paper end - timings
entity.isInLava();
@@ -909,9 +906,13 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
return Registry.ENTITY_TYPE.getKey(entity.getType()).toString();
});
gameprofilerfiller.incrementCounter("tickNonPassenger");
+ if (isActive) { // Paper - EAR 2
+ TimingHistory.activatedEntityTicks++;
entity.tick();
entity.postTick(); // CraftBukkit
+ } else { entity.inactiveTick(); } // Paper - EAR 2
this.getProfiler().pop();
+ } finally { timer.stopTiming(); } // Paper - timings
Iterator iterator = entity.getPassengers().iterator();
while (iterator.hasNext()) {
@@ -920,13 +921,18 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
this.tickPassenger(entity, entity1);
} }
- } finally { timer.stopTiming(); } // Paper - timings
+ // } finally { timer.stopTiming(); } // Paper - timings - move up
} }
@@ -902,6 +906,11 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
public void tickPassenger(Entity vehicle, Entity passenger) { private void tickPassenger(Entity vehicle, Entity passenger) {
if (!passenger.removed && passenger.getVehicle() == vehicle) { if (!passenger.isRemoved() && passenger.getVehicle() == vehicle) {
if (passenger instanceof Player || this.getChunkSource().isEntityTickingChunk(passenger)) { if (passenger instanceof Player || this.entityTickList.contains(passenger)) {
+ // Paper - EAR 2 + // Paper - EAR 2
+ final boolean isActive = org.spigotmc.ActivationRange.checkIfActive(passenger); + final boolean isActive = org.spigotmc.ActivationRange.checkIfActive(passenger);
+ co.aikar.timings.Timing timer = isActive ? passenger.getType().passengerTickTimer.startTiming() : passenger.getType().passengerInactiveTickTimer.startTiming(); // Paper + co.aikar.timings.Timing timer = isActive ? passenger.getType().passengerTickTimer.startTiming() : passenger.getType().passengerInactiveTickTimer.startTiming(); // Paper
+ try { + try {
+ // Paper end + // Paper end
passenger.setPosAndOldPos(passenger.getX(), passenger.getY(), passenger.getZ()); passenger.setOldPosAndRot();
passenger.yRotO = passenger.yRot; ++passenger.tickCount;
passenger.xRotO = passenger.xRot; ProfilerFiller gameprofilerfiller = this.getProfiler();
@@ -913,8 +922,17 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl @@ -935,8 +941,17 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
return Registry.ENTITY_TYPE.getKey(passenger.getType()).toString(); return Registry.ENTITY_TYPE.getKey(passenger.getType()).toString();
}); });
gameprofilerfiller.incrementCounter("tickPassenger"); gameprofilerfiller.incrementCounter("tickPassenger");
+ // Paper start - EAR 2 + // Paper start - EAR 2
+ if (isActive) { + if (isActive) {
passenger.rideTick(); passenger.rideTick();
passenger.postTick(); // CraftBukkit passenger.postTick(); // CraftBukkit
+ } else { + } else {
+ passenger.setDeltaMovement(Vec3.ZERO); + passenger.setDeltaMovement(Vec3.ZERO);
+ passenger.inactiveTick(); + passenger.inactiveTick();
+ // copied from inside of if (isPassenger()) of passengerTick, but that ifPassenger is unnecessary + // copied from inside of if (isPassenger()) of passengerTick, but that ifPassenger is unnecessary
+ vehicle.syncPositionOf(passenger); + vehicle.positionRider(passenger);
+ } + }
+ // Paper end - EAR 2 + // Paper end - EAR 2
gameprofilerfiller.pop(); gameprofilerfiller.pop();
Iterator iterator = passenger.getPassengers().iterator();
@@ -946,6 +961,7 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl
this.tickPassenger(passenger, entity2);
} }
@@ -927,7 +945,7 @@ public class ServerLevel extends net.minecraft.world.level.Level implements Worl + } finally { timer.stopTiming(); }// Paper - EAR2 timings
this.tickPassenger(passenger, entity2);
}
- }
+ } } finally { timer.stopTiming(); } // Paper - EAR2 timings
} }
} else { } else {
passenger.stopRiding();
diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java
index af86c370c6f834514115a8e40659f5e1aaabec75..c6881a9a5da2caed77dea30e4906d2dd99a624c1 100644 index a5159198003e43ce272ae73941d2be47d50eedc9..fffeba61e9af5c69876921b48241edb881af2a64 100644
--- a/src/main/java/net/minecraft/world/entity/Entity.java --- a/src/main/java/net/minecraft/world/entity/Entity.java
+++ b/src/main/java/net/minecraft/world/entity/Entity.java +++ b/src/main/java/net/minecraft/world/entity/Entity.java
@@ -67,6 +67,7 @@ import net.minecraft.world.entity.animal.AbstractFish; @@ -275,7 +275,7 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource, n
import net.minecraft.world.entity.animal.Animal;
import net.minecraft.world.entity.item.ItemEntity;
import net.minecraft.world.entity.player.Player;
+import net.minecraft.world.entity.vehicle.AbstractMinecart;
import net.minecraft.world.entity.vehicle.Boat;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.enchantment.EnchantmentHelper;
@@ -250,7 +251,7 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s
public boolean noCulling; public boolean noCulling;
public boolean hasImpulse; public boolean hasImpulse;
public int portalCooldown; public int portalCooldown;
@ -127,7 +136,7 @@ index af86c370c6f834514115a8e40659f5e1aaabec75..c6881a9a5da2caed77dea30e4906d2dd
protected int portalTime; protected int portalTime;
protected BlockPos portalEntrancePos; protected BlockPos portalEntrancePos;
private boolean invulnerable; private boolean invulnerable;
@@ -274,6 +275,7 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s @@ -305,6 +305,7 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource, n
public final org.spigotmc.ActivationRange.ActivationType activationType = org.spigotmc.ActivationRange.initializeEntityActivationType(this); public final org.spigotmc.ActivationRange.ActivationType activationType = org.spigotmc.ActivationRange.initializeEntityActivationType(this);
public final boolean defaultActivationState; public final boolean defaultActivationState;
public long activatedTick = Integer.MIN_VALUE; public long activatedTick = Integer.MIN_VALUE;
@ -135,51 +144,35 @@ index af86c370c6f834514115a8e40659f5e1aaabec75..c6881a9a5da2caed77dea30e4906d2dd
public boolean spawnedViaMobSpawner; // Paper - Yes this name is similar to above, upstream took the better one public boolean spawnedViaMobSpawner; // Paper - Yes this name is similar to above, upstream took the better one
protected int numCollisions = 0; // Paper protected int numCollisions = 0; // Paper
public void inactiveTick() { } public void inactiveTick() { }
@@ -664,6 +666,7 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s @@ -746,6 +747,7 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource, n
this.setLocationFromBoundingbox();
} else { } else {
if (type == MoverType.PISTON) { this.wasOnFire = this.isOnFire();
if (movementType == MoverType.PISTON) {
+ this.activatedTick = MinecraftServer.currentTick + 20; // Paper + this.activatedTick = MinecraftServer.currentTick + 20; // Paper
movement = this.limitPistonMovement(movement); movement = this.limitPistonMovement(movement);
if (movement.equals(Vec3.ZERO)) { if (movement.equals(Vec3.ZERO)) {
return; return;
@@ -676,6 +679,13 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s @@ -758,6 +760,13 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource, n
this.stuckSpeedMultiplier = Vec3.ZERO; this.stuckSpeedMultiplier = Vec3.ZERO;
this.setDeltaMovement(Vec3.ZERO); this.setDeltaMovement(Vec3.ZERO);
} }
+ // Paper start - ignore movement changes while inactive. + // Paper start - ignore movement changes while inactive.
+ if (isTemporarilyActive && !(this instanceof ItemEntity || this instanceof AbstractMinecart) && movement == getDeltaMovement() && type == MoverType.SELF) { + if (isTemporarilyActive && !(this instanceof ItemEntity || this instanceof net.minecraft.world.entity.vehicle.AbstractMinecart) && movement == getDeltaMovement() && movementType == MoverType.SELF) {
+ setDeltaMovement(Vec3.ZERO); + setDeltaMovement(Vec3.ZERO);
+ this.level.getProfiler().pop(); + this.level.getProfiler().pop();
+ return; + return;
+ } + }
+ // Paper end + // Paper end
movement = this.maybeBackOffFromEdge(movement, type); movement = this.maybeBackOffFromEdge(movement, movementType);
Vec3 vec3d1 = this.collide(movement); Vec3 vec3d1 = this.collide(movement);
@@ -2011,6 +2021,7 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s
}
}
+ public void syncPositionOf(Entity entity) { positionRider(entity); } // Paper - OBFHELPER
public void positionRider(Entity passenger) {
this.positionRider(passenger, Entity::setPos);
}
@@ -2821,6 +2832,7 @@ public abstract class Entity implements Nameable, CommandSource, net.minecraft.s
return this.stringUUID;
}
+ public final boolean isPushedByWater() { return this.isPushedByFluid(); } // Paper - OBFHELPER - the below is not an obfhelper, don't use it!
public boolean isPushedByFluid() {
// Paper start
return this.pushedByWater();
diff --git a/src/main/java/net/minecraft/world/entity/LivingEntity.java b/src/main/java/net/minecraft/world/entity/LivingEntity.java diff --git a/src/main/java/net/minecraft/world/entity/LivingEntity.java b/src/main/java/net/minecraft/world/entity/LivingEntity.java
index 016fcc4ae20e1e48728a848be28633e624ae49a7..b84dab1043c56e2deb58aec8639226f98db165d1 100644 index f48435dc344fb48feb48e2a141b394829058c5c4..bd1cc5e6fea4b9a171718c1249f652782b7ce13e 100644
--- a/src/main/java/net/minecraft/world/entity/LivingEntity.java --- a/src/main/java/net/minecraft/world/entity/LivingEntity.java
+++ b/src/main/java/net/minecraft/world/entity/LivingEntity.java +++ b/src/main/java/net/minecraft/world/entity/LivingEntity.java
@@ -189,7 +189,7 @@ public abstract class LivingEntity extends Entity { @@ -219,7 +219,7 @@ public abstract class LivingEntity extends Entity {
protected float rotOffs; protected float rotOffs;
protected int deathScore;protected int getKillCount() { return this.deathScore; } // Paper - OBFHELPER protected int deathScore;
public float lastHurt; public float lastHurt;
- protected boolean jumping; - protected boolean jumping;
+ public boolean jumping; // Paper protected -> public + public boolean jumping; // Paper protected -> public
@ -187,10 +180,10 @@ index 016fcc4ae20e1e48728a848be28633e624ae49a7..b84dab1043c56e2deb58aec8639226f9
public float yya; public float yya;
public float zza; public float zza;
diff --git a/src/main/java/net/minecraft/world/entity/Mob.java b/src/main/java/net/minecraft/world/entity/Mob.java diff --git a/src/main/java/net/minecraft/world/entity/Mob.java b/src/main/java/net/minecraft/world/entity/Mob.java
index 29a2eeee9f2011ed6fcc44f19041f616decfdb38..40ab66f888f30a5506e3aa96a4b32485452e8978 100644 index 32e8ae0d2a0f78af671a632c4d1be58a0b38a392..79e10f41b2993a02c4218551b06673f1848325a3 100644
--- a/src/main/java/net/minecraft/world/entity/Mob.java --- a/src/main/java/net/minecraft/world/entity/Mob.java
+++ b/src/main/java/net/minecraft/world/entity/Mob.java +++ b/src/main/java/net/minecraft/world/entity/Mob.java
@@ -113,7 +113,7 @@ public abstract class Mob extends LivingEntity { @@ -117,7 +117,7 @@ public abstract class Mob extends LivingEntity {
public ResourceLocation lootTable; public ResourceLocation lootTable;
public long lootTableSeed; public long lootTableSeed;
@Nullable @Nullable
@ -199,7 +192,7 @@ index 29a2eeee9f2011ed6fcc44f19041f616decfdb38..40ab66f888f30a5506e3aa96a4b32485
private int delayedLeashHolderId; private int delayedLeashHolderId;
@Nullable @Nullable
private CompoundTag leashInfoTag; private CompoundTag leashInfoTag;
@@ -194,6 +194,19 @@ public abstract class Mob extends LivingEntity { @@ -198,6 +198,19 @@ public abstract class Mob extends LivingEntity {
return this.lookControl; return this.lookControl;
} }
@ -231,51 +224,29 @@ index 920ae9af8985705a0ada7da5b7085a1ed8ca7f27..7c82d453388a27b69207d051dec316fc
protected PathfinderMob(EntityType<? extends PathfinderMob> type, Level world) { protected PathfinderMob(EntityType<? extends PathfinderMob> type, Level world) {
super(type, world); super(type, world);
diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/Goal.java b/src/main/java/net/minecraft/world/entity/ai/goal/Goal.java
index d44a5b7f6cf62d5e9acacad25d47cb0d44761cfa..558dd72c47930f6993952467f83b5a54ead95d92 100644
--- a/src/main/java/net/minecraft/world/entity/ai/goal/Goal.java
+++ b/src/main/java/net/minecraft/world/entity/ai/goal/Goal.java
@@ -20,7 +20,10 @@ public abstract class Goal {
public void start() {}
- public void stop() {}
+ public void stop() {
+ onTaskReset(); // Paper
+ }
+ public void onTaskReset() {} // Paper
public void tick() {}
diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java b/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java b/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java
index 9066db5c9a76cfb9665bef77b36172f1ea6ba931..9bd2ee05a0de6678ad8933a8ffbe0ae66bd073b4 100644 index 70e5b4446a8485b5995a0ba26af3a86d9b79bcc7..f29ace7b6a27a602102d37d43a6dd0571f218dfe 100644
--- a/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java --- a/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java
+++ b/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java +++ b/src/main/java/net/minecraft/world/entity/ai/goal/GoalSelector.java
@@ -26,10 +26,11 @@ public class GoalSelector { @@ -31,6 +31,7 @@ public class GoalSelector {
}
};
private final Map<Goal.Flag, WrappedGoal> lockedFlags = new EnumMap(Goal.Flag.class);
- private final Set<WrappedGoal> availableGoals = Sets.newLinkedHashSet();
+ private final Set<WrappedGoal> availableGoals = Sets.newLinkedHashSet(); private Set<WrappedGoal> getTasks() { return availableGoals; }// Paper - OBFHELPER
private final Supplier<ProfilerFiller> profiler;
private final EnumSet<Goal.Flag> disabledFlags = EnumSet.noneOf(Goal.Flag.class); private final EnumSet<Goal.Flag> disabledFlags = EnumSet.noneOf(Goal.Flag.class);
- private int newGoalRate = 3; private int tickCount;
+ private int newGoalRate = 3;private int getTickRate() { return newGoalRate; } // Paper - OBFHELPER private int newGoalRate = 3;
+ private int curRate;private int getCurRate() { return curRate; } private void incRate() { this.curRate++; } // Paper TODO + private int curRate;
public GoalSelector(Supplier<ProfilerFiller> profiler) { public GoalSelector(Supplier<ProfilerFiller> profiler) {
this.profiler = profiler; this.profiler = profiler;
@@ -39,6 +40,21 @@ public class GoalSelector { @@ -45,6 +46,20 @@ public class GoalSelector {
this.availableGoals.add(new WrappedGoal(priority, goal)); this.availableGoals.clear();
} }
+ // Paper start + // Paper start
+ public boolean inactiveTick() { + public boolean inactiveTick() {
+ incRate(); + this.curRate++;
+ return getCurRate() % getTickRate() == 0; + return this.curRate % this.newGoalRate == 0;
+ } + }
+ public boolean hasTasks() { + public boolean hasTasks() {
+ for (WrappedGoal task : getTasks()) { + for (WrappedGoal task : this.availableGoals) {
+ if (task.isRunning()) { + if (task.isRunning()) {
+ return true; + return true;
+ } + }
@ -283,26 +254,19 @@ index 9066db5c9a76cfb9665bef77b36172f1ea6ba931..9bd2ee05a0de6678ad8933a8ffbe0ae6
+ return false; + return false;
+ } + }
+ // Paper end + // Paper end
+
public void removeGoal(Goal goal) { public void removeGoal(Goal goal) {
this.availableGoals.stream().filter((pathfindergoalwrapped) -> { this.availableGoals.stream().filter((wrappedGoal) -> {
return pathfindergoalwrapped.getGoal() == goal; return wrappedGoal.getGoal() == goal;
diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java b/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java b/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
index c8680e795deeb68e0662eac7c760a103d1c767b4..e83cb412d8549b86d0348a2aa37c79201a5930be 100644 index 065d0752db0e3ae2a89d707aaa2145807f50ecad..c93805ae832d049ea13ca495b778ed52381b1f78 100644
--- a/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java --- a/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
+++ b/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java +++ b/src/main/java/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
@@ -9,12 +9,12 @@ import net.minecraft.world.level.LevelReader; @@ -14,7 +14,7 @@ public abstract class MoveToBlockGoal extends Goal {
public abstract class MoveToBlockGoal extends Goal {
- protected final PathfinderMob mob;
+ protected final PathfinderMob mob;public PathfinderMob getEntity() { return mob; } // Paper - OBFHELPER
public final double speedModifier;
protected int nextStartTick; protected int nextStartTick;
protected int tryTicks; protected int tryTicks;
private int maxStayTicks; private int maxStayTicks;
- protected BlockPos blockPos;public final BlockPos getTargetPosition() { return this.blockPos; } // Paper - OBFHELPER - protected BlockPos blockPos = BlockPos.ZERO; public final BlockPos getTargetPosition() { return this.blockPos; } // Paper - OBFHELPER
+ protected BlockPos blockPos; public final BlockPos getTargetPosition() { return this.blockPos; } public void setTargetPosition(BlockPos pos) { this.blockPos = pos; getEntity().movingTarget = pos != BlockPos.ZERO ? pos : null; } // Paper - OBFHELPER + protected BlockPos blockPos = BlockPos.ZERO; public final BlockPos getTargetPosition() { return this.blockPos; } public void setTargetPosition(BlockPos pos) { this.blockPos = pos; mob.movingTarget = pos != BlockPos.ZERO ? pos : null; } // Paper - OBFHELPER
private boolean reachedTarget; private boolean reachedTarget;
private final int searchRange; private final int searchRange;
private final int verticalSearchRange; private final int verticalSearchRange;
@ -312,85 +276,44 @@ index c8680e795deeb68e0662eac7c760a103d1c767b4..e83cb412d8549b86d0348a2aa37c7920
} }
+ // Paper start - activation range improvements + // Paper start - activation range improvements
+ @Override + @Override
+ public void onTaskReset() { + public void stop() {
+ super.onTaskReset(); + super.stop();
+ setTargetPosition(BlockPos.ZERO); + setTargetPosition(BlockPos.ZERO);
+ } + }
+ // Paper end + // Paper end
public MoveToBlockGoal(PathfinderMob mob, double speed, int range, int maxYDifference) { public MoveToBlockGoal(PathfinderMob mob, double speed, int range, int maxYDifference) {
this.blockPos = BlockPos.ZERO; this.mob = mob;
@@ -111,6 +118,7 @@ public abstract class MoveToBlockGoal extends Goal { @@ -109,6 +116,7 @@ public abstract class MoveToBlockGoal extends Goal {
blockposition_mutableblockposition.setWithOffset((Vec3i) blockposition, i1, k - 1, j1); mutableBlockPos.setWithOffset(blockPos, m, k - 1, n);
if (this.mob.isWithinRestriction((BlockPos) blockposition_mutableblockposition) && this.isValidTarget(this.mob.level, blockposition_mutableblockposition)) { if (this.mob.isWithinRestriction(mutableBlockPos) && this.isValidTarget(this.mob.level, mutableBlockPos)) {
this.blockPos = blockposition_mutableblockposition; this.blockPos = mutableBlockPos;
+ setTargetPosition(blockposition_mutableblockposition.immutable()); // Paper + setTargetPosition(mutableBlockPos.immutable()); // Paper
return true; return true;
} }
} }
diff --git a/src/main/java/net/minecraft/world/entity/ai/goal/WrappedGoal.java b/src/main/java/net/minecraft/world/entity/ai/goal/WrappedGoal.java
index 9921adf9292e0eff77515841d1b109a07b489367..81b4618a7979ee8dd25e1749c084de9262318ef4 100644
--- a/src/main/java/net/minecraft/world/entity/ai/goal/WrappedGoal.java
+++ b/src/main/java/net/minecraft/world/entity/ai/goal/WrappedGoal.java
@@ -64,6 +64,7 @@ public class WrappedGoal extends Goal {
return this.goal.getFlags();
}
+ public boolean isRunning() { return this.isRunning(); } // Paper - OBFHELPER
public boolean isRunning() {
return this.isRunning;
}
diff --git a/src/main/java/net/minecraft/world/entity/animal/horse/Llama.java b/src/main/java/net/minecraft/world/entity/animal/horse/Llama.java
index 5a7310bb48c1b8a72ad3c5d82c44fff8800995a2..a24af0600ad3e7d189581aa06a8e998f6a12e0fc 100644
--- a/src/main/java/net/minecraft/world/entity/animal/horse/Llama.java
+++ b/src/main/java/net/minecraft/world/entity/animal/horse/Llama.java
@@ -454,6 +454,7 @@ public class Llama extends AbstractChestedHorse implements RangedAttackMob {
return this.caravanTail != null;
}
+ public final boolean inCaravan() { return this.inCaravan(); } // Paper - OBFHELPER
public boolean inCaravan() {
return this.caravanHead != null;
}
diff --git a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
index ae8f850baa14a4f4277da5b6fdb1e5ccb44c4f35..9eee68a5a84e121698d26bd54212a72c75e16251 100644
--- a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
+++ b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
@@ -70,10 +70,12 @@ public abstract class AbstractVillager extends AgableMob implements Npc, Merchan
return super.finalizeSpawn(world, difficulty, spawnReason, (SpawnGroupData) entityData, entityTag);
}
+ public final int getUnhappy() { return getUnhappyCounter(); } // Paper - OBFHELPER
public int getUnhappyCounter() {
return (Integer) this.entityData.get(AbstractVillager.DATA_UNHAPPY_COUNTER);
}
+ public final void setUnhappy(int i) { setUnhappyCounter(i); } // Paper - OBFHELPER
public void setUnhappyCounter(int ticks) {
this.entityData.set(AbstractVillager.DATA_UNHAPPY_COUNTER, ticks);
}
diff --git a/src/main/java/net/minecraft/world/entity/npc/Villager.java b/src/main/java/net/minecraft/world/entity/npc/Villager.java diff --git a/src/main/java/net/minecraft/world/entity/npc/Villager.java b/src/main/java/net/minecraft/world/entity/npc/Villager.java
index eed6265dc8275921a18fc5f4970ba131ba782132..4aa34320ef7d6c62ccb17734bfa61d406190b919 100644 index 6a9e2105b2d9a4ee83c0a2516d5ef26dc3b99053..a35ce224b11b44567814207c3821d0cd4cdd9ec1 100644
--- a/src/main/java/net/minecraft/world/entity/npc/Villager.java --- a/src/main/java/net/minecraft/world/entity/npc/Villager.java
+++ b/src/main/java/net/minecraft/world/entity/npc/Villager.java +++ b/src/main/java/net/minecraft/world/entity/npc/Villager.java
@@ -212,17 +212,29 @@ public class Villager extends AbstractVillager implements ReputationEventHandler @@ -227,17 +227,29 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
@Override @Override
public void inactiveTick() { public void inactiveTick() {
// SPIGOT-3874, SPIGOT-3894, SPIGOT-3846, SPIGOT-5286 :( // SPIGOT-3874, SPIGOT-3894, SPIGOT-3846, SPIGOT-5286 :(
- if (level.spigotConfig.tickInactiveVillagers && this.isEffectiveAi()) { - if (level.spigotConfig.tickInactiveVillagers && this.isEffectiveAi()) {
- this.customServerAiStep(); - this.customServerAiStep();
+ // Paper start + // Paper start
+ if (this.getUnhappy() > 0) { + if (this.getUnhappyCounter() > 0) {
+ this.setUnhappy(this.getUnhappy() - 1); + this.setUnhappyCounter(this.getUnhappyCounter() - 1);
} + }
+ if (this.isEffectiveAi()) { + if (this.isEffectiveAi()) {
+ if (level.spigotConfig.tickInactiveVillagers) { + if (level.spigotConfig.tickInactiveVillagers) {
+ this.customServerAiStep(); + this.customServerAiStep();
+ } else { + } else {
+ this.mobTick(true); + this.mobTick(true);
+ } + }
+ } }
+ doReputationTick(); + maybeDecayGossip();
+ // Paper end + // Paper end
+ +
super.inactiveTick(); super.inactiveTick();
@ -407,7 +330,7 @@ index eed6265dc8275921a18fc5f4970ba131ba782132..4aa34320ef7d6c62ccb17734bfa61d40
this.level.getProfiler().pop(); this.level.getProfiler().pop();
if (this.assignProfessionWhenSpawned) { if (this.assignProfessionWhenSpawned) {
this.assignProfessionWhenSpawned = false; this.assignProfessionWhenSpawned = false;
@@ -246,7 +258,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler @@ -261,7 +273,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
this.lastTradedPlayer = null; this.lastTradedPlayer = null;
} }
@ -416,7 +339,7 @@ index eed6265dc8275921a18fc5f4970ba131ba782132..4aa34320ef7d6c62ccb17734bfa61d40
Raid raid = ((ServerLevel) this.level).getRaidAt(this.blockPosition()); Raid raid = ((ServerLevel) this.level).getRaidAt(this.blockPosition());
if (raid != null && raid.isActive() && !raid.isOver()) { if (raid != null && raid.isActive() && !raid.isOver()) {
@@ -257,6 +269,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler @@ -272,6 +284,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
if (this.getVillagerData().getProfession() == VillagerProfession.NONE && this.isTrading()) { if (this.getVillagerData().getProfession() == VillagerProfession.NONE && this.isTrading()) {
this.stopTrading(); this.stopTrading();
} }
@ -424,19 +347,11 @@ index eed6265dc8275921a18fc5f4970ba131ba782132..4aa34320ef7d6c62ccb17734bfa61d40
super.customServerAiStep(); super.customServerAiStep();
} }
@@ -900,6 +913,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
}
}
+ private void doReputationTick() { maybeDecayGossip(); } // Paper - OBFHELPER
private void maybeDecayGossip() {
long i = this.level.getGameTime();
diff --git a/src/main/java/net/minecraft/world/level/Level.java b/src/main/java/net/minecraft/world/level/Level.java diff --git a/src/main/java/net/minecraft/world/level/Level.java b/src/main/java/net/minecraft/world/level/Level.java
index 6b79f8cd9258af47afa6efa7b1f97c3780be58b0..1d536d77518a70bdc1a23924aea99df1042b3cd5 100644 index 9891e40972c1dc6bebe8ccec2bf82123dcdd7e94..ddcde88a8c8b748b4dc2583b4dfd0fb8ea9e201e 100644
--- a/src/main/java/net/minecraft/world/level/Level.java --- a/src/main/java/net/minecraft/world/level/Level.java
+++ b/src/main/java/net/minecraft/world/level/Level.java +++ b/src/main/java/net/minecraft/world/level/Level.java
@@ -142,6 +142,12 @@ public abstract class Level implements LevelAccessor, AutoCloseable { @@ -153,6 +153,12 @@ public abstract class Level implements LevelAccessor, AutoCloseable {
public long ticksPerWaterSpawns; public long ticksPerWaterSpawns;
public long ticksPerWaterAmbientSpawns; public long ticksPerWaterAmbientSpawns;
public long ticksPerAmbientSpawns; public long ticksPerAmbientSpawns;
@ -450,17 +365,16 @@ index 6b79f8cd9258af47afa6efa7b1f97c3780be58b0..1d536d77518a70bdc1a23924aea99df1
public final org.spigotmc.SpigotWorldConfig spigotConfig; // Spigot public final org.spigotmc.SpigotWorldConfig spigotConfig; // Spigot
diff --git a/src/main/java/org/spigotmc/ActivationRange.java b/src/main/java/org/spigotmc/ActivationRange.java diff --git a/src/main/java/org/spigotmc/ActivationRange.java b/src/main/java/org/spigotmc/ActivationRange.java
index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3e4ac3eaf 100644 index 84ce3d38d5decb4a2f9fae78e0ef5d715860dc7d..2ab585a018290996e7fa9ca6f3ad7d734cd7beaa 100644
--- a/src/main/java/org/spigotmc/ActivationRange.java --- a/src/main/java/org/spigotmc/ActivationRange.java
+++ b/src/main/java/org/spigotmc/ActivationRange.java +++ b/src/main/java/org/spigotmc/ActivationRange.java
@@ -1,41 +1,55 @@ @@ -1,39 +1,51 @@
package org.spigotmc; package org.spigotmc;
import java.util.Collection; -import java.util.Collection;
+import net.minecraft.core.BlockPos; +import net.minecraft.core.BlockPos;
import net.minecraft.server.MinecraftServer; import net.minecraft.server.MinecraftServer;
+import net.minecraft.server.level.ServerChunkCache; +import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.util.Mth;
import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.Entity;
+import net.minecraft.world.entity.FlyingMob; +import net.minecraft.world.entity.FlyingMob;
import net.minecraft.world.entity.LightningBolt; import net.minecraft.world.entity.LightningBolt;
@ -478,7 +392,6 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
import net.minecraft.world.entity.boss.enderdragon.EndCrystal; import net.minecraft.world.entity.boss.enderdragon.EndCrystal;
import net.minecraft.world.entity.boss.enderdragon.EnderDragon; import net.minecraft.world.entity.boss.enderdragon.EnderDragon;
import net.minecraft.world.entity.boss.wither.WitherBoss; import net.minecraft.world.entity.boss.wither.WitherBoss;
+import net.minecraft.world.entity.item.FallingBlockEntity;
import net.minecraft.world.entity.item.PrimedTnt; import net.minecraft.world.entity.item.PrimedTnt;
import net.minecraft.world.entity.monster.Creeper; import net.minecraft.world.entity.monster.Creeper;
-import net.minecraft.world.entity.monster.Monster; -import net.minecraft.world.entity.monster.Monster;
@ -497,7 +410,6 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
+import co.aikar.timings.MinecraftTimings; +import co.aikar.timings.MinecraftTimings;
+import net.minecraft.world.entity.schedule.Activity; +import net.minecraft.world.entity.schedule.Activity;
import net.minecraft.world.level.Level; import net.minecraft.world.level.Level;
import net.minecraft.world.level.chunk.LevelChunk;
import net.minecraft.world.phys.AABB; import net.minecraft.world.phys.AABB;
-import co.aikar.timings.MinecraftTimings; -import co.aikar.timings.MinecraftTimings;
@ -512,7 +424,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
MONSTER, MONSTER,
ANIMAL, ANIMAL,
RAIDER, RAIDER,
@@ -43,6 +57,43 @@ public class ActivationRange @@ -41,6 +53,43 @@ public class ActivationRange
AABB boundingBox = new AABB( 0, 0, 0, 0, 0, 0 ); AABB boundingBox = new AABB( 0, 0, 0, 0, 0, 0 );
} }
@ -556,7 +468,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
static AABB maxBB = new AABB( 0, 0, 0, 0, 0, 0 ); static AABB maxBB = new AABB( 0, 0, 0, 0, 0, 0 );
@@ -55,10 +106,13 @@ public class ActivationRange @@ -53,10 +102,13 @@ public class ActivationRange
*/ */
public static ActivationType initializeEntityActivationType(Entity entity) public static ActivationType initializeEntityActivationType(Entity entity)
{ {
@ -571,7 +483,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
{ {
return ActivationType.MONSTER; return ActivationType.MONSTER;
} else if ( entity instanceof PathfinderMob || entity instanceof AmbientCreature ) } else if ( entity instanceof PathfinderMob || entity instanceof AmbientCreature )
@@ -79,10 +133,14 @@ public class ActivationRange @@ -77,10 +129,14 @@ public class ActivationRange
*/ */
public static boolean initializeEntityActivationState(Entity entity, SpigotWorldConfig config) public static boolean initializeEntityActivationState(Entity entity, SpigotWorldConfig config)
{ {
@ -590,16 +502,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
|| entity instanceof Player || entity instanceof Player
|| entity instanceof ThrowableProjectile || entity instanceof ThrowableProjectile
|| entity instanceof EnderDragon || entity instanceof EnderDragon
@@ -91,7 +149,7 @@ public class ActivationRange @@ -113,10 +169,25 @@ public class ActivationRange
|| entity instanceof AbstractHurtingProjectile
|| entity instanceof LightningBolt
|| entity instanceof PrimedTnt
- || entity instanceof EntityFallingBlock // Paper - Always tick falling blocks
+ || entity instanceof FallingBlockEntity // Paper - Always tick falling blocks
|| entity instanceof EndCrystal
|| entity instanceof FireworkRocketEntity
|| entity instanceof ThrownTrident )
@@ -115,10 +173,25 @@ public class ActivationRange
final int raiderActivationRange = world.spigotConfig.raiderActivationRange; final int raiderActivationRange = world.spigotConfig.raiderActivationRange;
final int animalActivationRange = world.spigotConfig.animalActivationRange; final int animalActivationRange = world.spigotConfig.animalActivationRange;
final int monsterActivationRange = world.spigotConfig.monsterActivationRange; final int monsterActivationRange = world.spigotConfig.monsterActivationRange;
@ -625,7 +528,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
maxRange = Math.min( ( world.spigotConfig.viewDistance << 4 ) - 8, maxRange ); maxRange = Math.min( ( world.spigotConfig.viewDistance << 4 ) - 8, maxRange );
for ( Player player : world.players() ) for ( Player player : world.players() )
@@ -130,6 +203,11 @@ public class ActivationRange @@ -128,6 +199,11 @@ public class ActivationRange
ActivationType.RAIDER.boundingBox = player.getBoundingBox().inflate( raiderActivationRange, 256, raiderActivationRange ); ActivationType.RAIDER.boundingBox = player.getBoundingBox().inflate( raiderActivationRange, 256, raiderActivationRange );
ActivationType.ANIMAL.boundingBox = player.getBoundingBox().inflate( animalActivationRange, 256, animalActivationRange ); ActivationType.ANIMAL.boundingBox = player.getBoundingBox().inflate( animalActivationRange, 256, animalActivationRange );
ActivationType.MONSTER.boundingBox = player.getBoundingBox().inflate( monsterActivationRange, 256, monsterActivationRange ); ActivationType.MONSTER.boundingBox = player.getBoundingBox().inflate( monsterActivationRange, 256, monsterActivationRange );
@ -635,46 +538,9 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
+ ActivationType.VILLAGER.boundingBox = player.getBoundingBox().inflate( villagerActivationRange, 256, waterActivationRange ); + ActivationType.VILLAGER.boundingBox = player.getBoundingBox().inflate( villagerActivationRange, 256, waterActivationRange );
+ // Paper end + // Paper end
int i = Mth.floor( maxBB.minX / 16.0D ); world.getEntities().get(maxBB, ActivationRange::activateEntity);
int j = Mth.floor( maxBB.maxX / 16.0D ); }
@@ -140,7 +218,7 @@ public class ActivationRange @@ -162,56 +238,105 @@ public class ActivationRange
{
for ( int j1 = k; j1 <= l; ++j1 )
{
- LevelChunk chunk = (LevelChunk) world.getChunkIfLoadedImmediately( i1, j1 );
+ LevelChunk chunk = chunkProvider.getChunkAtIfLoadedMainThreadNoCache( i1, j1 ); // Paper
if ( chunk != null )
{
activateChunkEntities( chunk );
@@ -158,19 +236,15 @@ public class ActivationRange
*/
private static void activateChunkEntities(LevelChunk chunk)
{
- for ( java.util.List<Entity> slice : chunk.entitySlices )
- {
- for ( Entity entity : (Collection<Entity>) slice )
+ // Paper start
+ Entity[] rawData = chunk.entities.getRawData();
+ for (int i = 0; i < chunk.entities.size(); i++) {
+ Entity entity = rawData[i];
+ //for ( Entity entity : (Collection<Entity>) slice )
+ // Paper end
{
- if ( MinecraftServer.currentTick > entity.activatedTick )
- {
- if ( entity.defaultActivationState )
- {
- entity.activatedTick = MinecraftServer.currentTick;
- continue;
- }
- if ( entity.activationType.boundingBox.intersects( entity.getBoundingBox() ) )
- {
+ if (MinecraftServer.currentTick > entity.activatedTick) {
+ if (entity.defaultActivationState || entity.activationType.boundingBox.intersects(entity.getBoundingBox())) { // Paper
entity.activatedTick = MinecraftServer.currentTick;
}
}
@@ -185,56 +259,105 @@ public class ActivationRange
* @param entity * @param entity
* @return * @return
*/ */
@ -694,7 +560,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
+ // Paper end + // Paper end
// quick checks. // quick checks.
- if ( entity.wasTouchingWater || entity.remainingFireTicks > 0 ) - if ( entity.wasTouchingWater || entity.remainingFireTicks > 0 )
+ if ( (entity.activationType != ActivationType.WATER && entity.wasTouchingWater && entity.isPushedByWater()) ) // Paper + if ( (entity.activationType != ActivationType.WATER && entity.wasTouchingWater && entity.isPushedByFluid()) ) // Paper
{ {
- return true; - return true;
+ return 100; // Paper + return 100; // Paper
@ -780,7 +646,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
if (entity instanceof Creeper && ((Creeper) entity).isIgnited()) { // isExplosive if (entity instanceof Creeper && ((Creeper) entity).isIgnited()) { // isExplosive
- return true; - return true;
+ return 20; // Paper + return 20; // Paper
} + }
+ // Paper start + // Paper start
+ if (entity instanceof Mob && ((Mob) entity).targetSelector.hasTasks() ) { + if (entity instanceof Mob && ((Mob) entity).targetSelector.hasTasks() ) {
+ return 0; + return 0;
@ -788,7 +654,7 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
+ if (entity instanceof Pillager) { + if (entity instanceof Pillager) {
+ Pillager pillager = (Pillager) entity; + Pillager pillager = (Pillager) entity;
+ // TODO:? + // TODO:?
+ } }
+ // Paper end + // Paper end
} }
- return false; - return false;
@ -796,8 +662,8 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
} }
/** /**
@@ -249,8 +372,19 @@ public class ActivationRange @@ -226,8 +351,19 @@ public class ActivationRange
if ( !entity.inChunk || entity instanceof FireworkRocketEntity ) { if ( entity instanceof FireworkRocketEntity ) {
return true; return true;
} }
+ // Paper start - special case always immunities + // Paper start - special case always immunities
@ -817,11 +683,11 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
// Should this entity tick? // Should this entity tick?
if ( !isActive ) if ( !isActive )
@@ -258,15 +392,19 @@ public class ActivationRange @@ -235,15 +371,19 @@ public class ActivationRange
if ( ( MinecraftServer.currentTick - entity.activatedTick - 1 ) % 20 == 0 ) if ( ( MinecraftServer.currentTick - entity.activatedTick - 1 ) % 20 == 0 )
{ {
// Check immunities every 20 ticks. // Check immunities every 20 ticks.
- if ( checkEntityImmunities( entity ) ) - if ( ActivationRange.checkEntityImmunities( entity ) )
- { - {
- // Triggered some sort of immunity, give 20 full ticks before we check again. - // Triggered some sort of immunity, give 20 full ticks before we check again.
- entity.activatedTick = MinecraftServer.currentTick + 20; - entity.activatedTick = MinecraftServer.currentTick + 20;
@ -837,13 +703,13 @@ index 61f180a7c95d83bb88c7df4910c498d9bdf6785a..8cbafad53d20366a36493f22160c4fa3
+ +
} }
// Add a little performance juice to active entities. Skip 1/4 if not immune. // Add a little performance juice to active entities. Skip 1/4 if not immune.
- } else if ( !entity.defaultActivationState && entity.tickCount % 4 == 0 && !checkEntityImmunities( entity ) ) - } else if ( !entity.defaultActivationState && entity.tickCount % 4 == 0 && !ActivationRange.checkEntityImmunities( entity ) )
+ } else if (entity.tickCount % 4 == 0 && checkEntityImmunities( entity) < 0 ) // Paper + } else if ( entity.tickCount % 4 == 0 && ActivationRange.checkEntityImmunities( entity ) < 0 ) // Paper
{ {
isActive = false; isActive = false;
} }
diff --git a/src/main/java/org/spigotmc/SpigotWorldConfig.java b/src/main/java/org/spigotmc/SpigotWorldConfig.java diff --git a/src/main/java/org/spigotmc/SpigotWorldConfig.java b/src/main/java/org/spigotmc/SpigotWorldConfig.java
index 34ee684901906fc2ef5f0d09680d2686b813e52b..6b015c1f26facb4e82d75b252164dec05731ca6c 100644 index 8e6eae7cc27f66faede9a3dc74571e1814df3652..308de0757c219c1e5fa8bde182343c4095301cde 100644
--- a/src/main/java/org/spigotmc/SpigotWorldConfig.java --- a/src/main/java/org/spigotmc/SpigotWorldConfig.java
+++ b/src/main/java/org/spigotmc/SpigotWorldConfig.java +++ b/src/main/java/org/spigotmc/SpigotWorldConfig.java
@@ -180,13 +180,59 @@ public class SpigotWorldConfig @@ -180,13 +180,59 @@ public class SpigotWorldConfig
@ -873,36 +739,36 @@ index 34ee684901906fc2ef5f0d09680d2686b813e52b..6b015c1f26facb4e82d75b252164dec0
public boolean tickInactiveVillagers = true; public boolean tickInactiveVillagers = true;
private void activationRange() private void activationRange()
{ {
+ boolean hasAnimalsConfig = config.getInt("entity-activation-range.animals", animalActivationRange) != animalActivationRange; // Paper + boolean hasAnimalsConfig = config.getInt("entity-activation-range.animals", this.animalActivationRange) != this.animalActivationRange; // Paper
animalActivationRange = getInt( "entity-activation-range.animals", animalActivationRange ); this.animalActivationRange = this.getInt( "entity-activation-range.animals", this.animalActivationRange );
monsterActivationRange = getInt( "entity-activation-range.monsters", monsterActivationRange ); this.monsterActivationRange = this.getInt( "entity-activation-range.monsters", this.monsterActivationRange );
raiderActivationRange = getInt( "entity-activation-range.raiders", raiderActivationRange ); this.raiderActivationRange = this.getInt( "entity-activation-range.raiders", this.raiderActivationRange );
miscActivationRange = getInt( "entity-activation-range.misc", miscActivationRange ); this.miscActivationRange = this.getInt( "entity-activation-range.misc", this.miscActivationRange );
+ // Paper start + // Paper start
+ waterActivationRange = getInt( "entity-activation-range.water", waterActivationRange ); + this.waterActivationRange = this.getInt( "entity-activation-range.water", this.waterActivationRange );
+ villagerActivationRange = getInt( "entity-activation-range.villagers", hasAnimalsConfig ? animalActivationRange : villagerActivationRange ); + this.villagerActivationRange = this.getInt( "entity-activation-range.villagers", hasAnimalsConfig ? this.animalActivationRange : this.villagerActivationRange );
+ flyingMonsterActivationRange = getInt( "entity-activation-range.flying-monsters", flyingMonsterActivationRange ); + this.flyingMonsterActivationRange = this.getInt( "entity-activation-range.flying-monsters", this.flyingMonsterActivationRange );
+ +
+ wakeUpInactiveAnimals = getInt("entity-activation-range.wake-up-inactive.animals-max-per-tick", wakeUpInactiveAnimals); + this.wakeUpInactiveAnimals = this.getInt("entity-activation-range.wake-up-inactive.animals-max-per-tick", this.wakeUpInactiveAnimals);
+ wakeUpInactiveAnimalsEvery = getInt("entity-activation-range.wake-up-inactive.animals-every", wakeUpInactiveAnimalsEvery); + this.wakeUpInactiveAnimalsEvery = this.getInt("entity-activation-range.wake-up-inactive.animals-every", this.wakeUpInactiveAnimalsEvery);
+ wakeUpInactiveAnimalsFor = getInt("entity-activation-range.wake-up-inactive.animals-for", wakeUpInactiveAnimalsFor); + this.wakeUpInactiveAnimalsFor = this.getInt("entity-activation-range.wake-up-inactive.animals-for", this.wakeUpInactiveAnimalsFor);
+ +
+ wakeUpInactiveMonsters = getInt("entity-activation-range.wake-up-inactive.monsters-max-per-tick", wakeUpInactiveMonsters); + this.wakeUpInactiveMonsters = this.getInt("entity-activation-range.wake-up-inactive.monsters-max-per-tick", this.wakeUpInactiveMonsters);
+ wakeUpInactiveMonstersEvery = getInt("entity-activation-range.wake-up-inactive.monsters-every", wakeUpInactiveMonstersEvery); + this.wakeUpInactiveMonstersEvery = this.getInt("entity-activation-range.wake-up-inactive.monsters-every", this.wakeUpInactiveMonstersEvery);
+ wakeUpInactiveMonstersFor = getInt("entity-activation-range.wake-up-inactive.monsters-for", wakeUpInactiveMonstersFor); + this.wakeUpInactiveMonstersFor = this.getInt("entity-activation-range.wake-up-inactive.monsters-for", this.wakeUpInactiveMonstersFor);
+ +
+ wakeUpInactiveVillagers = getInt("entity-activation-range.wake-up-inactive.villagers-max-per-tick", wakeUpInactiveVillagers); + this.wakeUpInactiveVillagers = this.getInt("entity-activation-range.wake-up-inactive.villagers-max-per-tick", this.wakeUpInactiveVillagers);
+ wakeUpInactiveVillagersEvery = getInt("entity-activation-range.wake-up-inactive.villagers-every", wakeUpInactiveVillagersEvery); + this.wakeUpInactiveVillagersEvery = this.getInt("entity-activation-range.wake-up-inactive.villagers-every", this.wakeUpInactiveVillagersEvery);
+ wakeUpInactiveVillagersFor = getInt("entity-activation-range.wake-up-inactive.villagers-for", wakeUpInactiveVillagersFor); + this.wakeUpInactiveVillagersFor = this.getInt("entity-activation-range.wake-up-inactive.villagers-for", this.wakeUpInactiveVillagersFor);
+ +
+ wakeUpInactiveFlying = getInt("entity-activation-range.wake-up-inactive.flying-monsters-max-per-tick", wakeUpInactiveFlying); + this.wakeUpInactiveFlying = this.getInt("entity-activation-range.wake-up-inactive.flying-monsters-max-per-tick", this.wakeUpInactiveFlying);
+ wakeUpInactiveFlyingEvery = getInt("entity-activation-range.wake-up-inactive.flying-monsters-every", wakeUpInactiveFlyingEvery); + this.wakeUpInactiveFlyingEvery = this.getInt("entity-activation-range.wake-up-inactive.flying-monsters-every", this.wakeUpInactiveFlyingEvery);
+ wakeUpInactiveFlyingFor = getInt("entity-activation-range.wake-up-inactive.flying-monsters-for", wakeUpInactiveFlyingFor); + this.wakeUpInactiveFlyingFor = this.getInt("entity-activation-range.wake-up-inactive.flying-monsters-for", this.wakeUpInactiveFlyingFor);
+ +
+ villagersWorkImmunityAfter = getInt( "entity-activation-range.villagers-work-immunity-after", villagersWorkImmunityAfter ); + this.villagersWorkImmunityAfter = this.getInt( "entity-activation-range.villagers-work-immunity-after", this.villagersWorkImmunityAfter );
+ villagersWorkImmunityFor = getInt( "entity-activation-range.villagers-work-immunity-for", villagersWorkImmunityFor ); + this.villagersWorkImmunityFor = this.getInt( "entity-activation-range.villagers-work-immunity-for", this.villagersWorkImmunityFor );
+ villagersActiveForPanic = getBoolean( "entity-activation-range.villagers-active-for-panic", villagersActiveForPanic ); + this.villagersActiveForPanic = this.getBoolean( "entity-activation-range.villagers-active-for-panic", this.villagersActiveForPanic );
+ // Paper end + // Paper end
tickInactiveVillagers = getBoolean( "entity-activation-range.tick-inactive-villagers", tickInactiveVillagers ); this.tickInactiveVillagers = this.getBoolean( "entity-activation-range.tick-inactive-villagers", this.tickInactiveVillagers );
log( "Entity Activation Range: An " + animalActivationRange + " / Mo " + monsterActivationRange + " / Ra " + raiderActivationRange + " / Mi " + miscActivationRange + " / Tiv " + tickInactiveVillagers ); this.log( "Entity Activation Range: An " + this.animalActivationRange + " / Mo " + this.monsterActivationRange + " / Ra " + this.raiderActivationRange + " / Mi " + this.miscActivationRange + " / Tiv " + this.tickInactiveVillagers );
} }

View File

@ -14,12 +14,12 @@ light engine on shutdown...
The queue size only puts a cap on max loss, doesn't solve that problem. The queue size only puts a cap on max loss, doesn't solve that problem.
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index 6c8e9d498c9a30a1aa88494ba09c3cae012a8fa1..cd248eb6be663e8be33f2c3c6b06b77b6d5753a4 100644 index 041efecbfcd54384d15ebf771cdfa0e711483997..e29566cad2647da4d9288e912188b57f00e8dd0c 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java --- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java +++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -620,4 +620,9 @@ public class PaperWorldConfig { @@ -440,5 +440,10 @@ public class PaperWorldConfig {
private void zombieVillagerInfectionChance() { disableHopperMoveEvents = getBoolean("hopper.disable-move-event", disableHopperMoveEvents);
zombieVillagerInfectionChance = getDouble("zombie-villager-infection-chance", zombieVillagerInfectionChance); log("Hopper Move Item Events: " + (disableHopperMoveEvents ? "disabled" : "enabled"));
} }
+ +
+ public int lightQueueSize = 20; + public int lightQueueSize = 20;
@ -27,11 +27,12 @@ index 6c8e9d498c9a30a1aa88494ba09c3cae012a8fa1..cd248eb6be663e8be33f2c3c6b06b77b
+ lightQueueSize = getInt("light-queue-size", lightQueueSize); + lightQueueSize = getInt("light-queue-size", lightQueueSize);
+ } + }
} }
diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java
index e33189dc8375a3034910087654607fb531061636..11c6e8ce10c53dcb639145fbda32c5426eb6b3d9 100644 index 312be2221e1acc44aaf6936533b0eb968f796dc6..494a3afaaa0e3496d30e8d97edbab62b21610dfe 100644
--- a/src/main/java/net/minecraft/server/MinecraftServer.java --- a/src/main/java/net/minecraft/server/MinecraftServer.java
+++ b/src/main/java/net/minecraft/server/MinecraftServer.java +++ b/src/main/java/net/minecraft/server/MinecraftServer.java
@@ -775,7 +775,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa @@ -832,7 +832,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
this.executeModerately(); this.executeModerately();
// CraftBukkit end // CraftBukkit end
if (worldserver.getWorld().getKeepSpawnInMemory()) worldloadlistener.stop(); // Paper if (worldserver.getWorld().getKeepSpawnInMemory()) worldloadlistener.stop(); // Paper

View File

@ -7,32 +7,20 @@ This lets you run /paper fixlight <chunkRadius> (max 5) to automatically
fix all light data in the chunks. fix all light data in the chunks.
diff --git a/src/main/java/com/destroystokyo/paper/PaperCommand.java b/src/main/java/com/destroystokyo/paper/PaperCommand.java diff --git a/src/main/java/com/destroystokyo/paper/PaperCommand.java b/src/main/java/com/destroystokyo/paper/PaperCommand.java
index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9c2d04789 100644 index 71ffa66973d8994e2a480435ac1ada3fe61600a4..7b5afc5d34b78e6404c1a5c6bb823d9589471f13 100644
--- a/src/main/java/com/destroystokyo/paper/PaperCommand.java --- a/src/main/java/com/destroystokyo/paper/PaperCommand.java
+++ b/src/main/java/com/destroystokyo/paper/PaperCommand.java +++ b/src/main/java/com/destroystokyo/paper/PaperCommand.java
@@ -11,16 +11,20 @@ import com.google.common.collect.Maps; @@ -10,7 +10,8 @@ import net.minecraft.server.MinecraftServer;
import com.google.gson.JsonObject;
import com.google.gson.internal.Streams;
import com.google.gson.stream.JsonWriter;
+import net.minecraft.core.BlockPos;
+import net.minecraft.network.protocol.game.ClientboundLightUpdatePacket;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.server.MCUtil;
import net.minecraft.server.MinecraftServer;
import net.minecraft.server.level.ChunkHolder; import net.minecraft.server.level.ChunkHolder;
import net.minecraft.server.level.ServerChunkCache; import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerLevel;
-import net.minecraft.world.entity.Entity;
+import net.minecraft.server.level.ServerPlayer; +import net.minecraft.server.level.ServerPlayer;
+import net.minecraft.server.level.ThreadedLevelLightEngine; +import net.minecraft.server.level.ThreadedLevelLightEngine;
import net.minecraft.world.entity.Entity;
import net.minecraft.world.entity.EntityType; import net.minecraft.world.entity.EntityType;
import net.minecraft.world.level.ChunkPos; import net.minecraft.world.level.ChunkPos;
-import net.minecraft.server.MCUtil; import net.minecraft.resources.ResourceLocation;
+import net.minecraft.world.level.chunk.LevelChunk; @@ -25,15 +26,18 @@ import org.bukkit.command.Command;
import org.apache.commons.lang3.tuple.MutablePair;
import org.apache.commons.lang3.tuple.Pair;
import org.bukkit.Bukkit;
@@ -31,6 +35,7 @@ import org.bukkit.command.Command;
import org.bukkit.command.CommandSender; import org.bukkit.command.CommandSender;
import org.bukkit.craftbukkit.CraftServer; import org.bukkit.craftbukkit.CraftServer;
import org.bukkit.craftbukkit.CraftWorld; import org.bukkit.craftbukkit.CraftWorld;
@ -40,8 +28,6 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import java.io.File; import java.io.File;
@@ -39,10 +44,12 @@ import java.io.PrintStream;
import java.io.StringWriter;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
+import java.util.ArrayDeque; +import java.util.ArrayDeque;
@ -53,18 +39,18 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Locale; import java.util.Locale;
@@ -52,7 +59,7 @@ import java.util.stream.Collectors; @@ -43,7 +47,7 @@ import java.util.stream.Collectors;
public class PaperCommand extends Command { public class PaperCommand extends Command {
private static final String BASE_PERM = "bukkit.command.paper."; private static final String BASE_PERM = "bukkit.command.paper.";
- private static final ImmutableSet<String> SUBCOMMANDS = ImmutableSet.<String>builder().add("heap", "entity", "reload", "version", "debug", "chunkinfo", "dumpwaiting", "syncloadinfo").build(); - private static final ImmutableSet<String> SUBCOMMANDS = ImmutableSet.<String>builder().add("heap", "entity", "reload", "version", "debug", "chunkinfo").build();
+ private static final ImmutableSet<String> SUBCOMMANDS = ImmutableSet.<String>builder().add("heap", "entity", "reload", "version", "debug", "chunkinfo", "dumpwaiting", "syncloadinfo", "fixlight").build(); + private static final ImmutableSet<String> SUBCOMMANDS = ImmutableSet.<String>builder().add("heap", "entity", "reload", "version", "debug", "chunkinfo", "fixlight").build();
public PaperCommand(String name) { public PaperCommand(String name) {
super(name); super(name);
@@ -173,6 +180,9 @@ public class PaperCommand extends Command { @@ -158,6 +162,9 @@ public class PaperCommand extends Command {
case "syncloadinfo": case "chunkinfo":
this.doSyncLoadInfo(sender, args); doChunkInfo(sender, args);
break; break;
+ case "fixlight": + case "fixlight":
+ this.doFixLight(sender, args); + this.doFixLight(sender, args);
@ -72,10 +58,10 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
case "ver": case "ver":
if (!testPermission(sender, "version")) break; // "ver" needs a special check because it's an alias. All other commands are checked up before the switch statement (because they are present in the SUBCOMMANDS set) if (!testPermission(sender, "version")) break; // "ver" needs a special check because it's an alias. All other commands are checked up before the switch statement (because they are present in the SUBCOMMANDS set)
case "version": case "version":
@@ -190,6 +200,77 @@ public class PaperCommand extends Command { @@ -413,4 +420,74 @@ public class PaperCommand extends Command {
return true;
}
Command.broadcastCommandMessage(sender, ChatColor.GREEN + "Paper config reload complete.");
}
+ private void doFixLight(CommandSender sender, String[] args) { + private void doFixLight(CommandSender sender, String[] args) {
+ if (!(sender instanceof Player)) { + if (!(sender instanceof Player)) {
+ sender.sendMessage("Only players can use this command"); + sender.sendMessage("Only players can use this command");
@ -97,7 +83,7 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
+ ServerLevel world = (ServerLevel) handle.level; + ServerLevel world = (ServerLevel) handle.level;
+ ThreadedLevelLightEngine lightengine = world.getChunkSource().getLightEngine(); + ThreadedLevelLightEngine lightengine = world.getChunkSource().getLightEngine();
+ +
+ BlockPos center = MCUtil.toBlockPosition(player.getLocation()); + net.minecraft.core.BlockPos center = MCUtil.toBlockPosition(player.getLocation());
+ Deque<ChunkPos> queue = new ArrayDeque<>(MCUtil.getSpiralOutChunks(center, radius)); + Deque<ChunkPos> queue = new ArrayDeque<>(MCUtil.getSpiralOutChunks(center, radius));
+ updateLight(sender, world, lightengine, queue); + updateLight(sender, world, lightengine, queue);
+ } + }
@ -114,7 +100,7 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
+ updateLight(sender, world, lightengine, queue); + updateLight(sender, world, lightengine, queue);
+ return; + return;
+ } + }
+ LevelChunk chunk = (LevelChunk) either.left().orElse(null); + net.minecraft.world.level.chunk.LevelChunk chunk = (net.minecraft.world.level.chunk.LevelChunk) either.left().orElse(null);
+ if (chunk == null) { + if (chunk == null) {
+ updateLight(sender, world, lightengine, queue); + updateLight(sender, world, lightengine, queue);
+ return; + return;
@ -126,7 +112,7 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
+ for (int y = 0; y < world.getHeight(); y++) { + for (int y = 0; y < world.getHeight(); y++) {
+ for (int x = 0; x < 16; x++) { + for (int x = 0; x < 16; x++) {
+ for (int z = 0; z < 16; z++) { + for (int z = 0; z < 16; z++) {
+ BlockPos pos = new BlockPos(cx + x, y, cz + z); + net.minecraft.core.BlockPos pos = new net.minecraft.core.BlockPos(cx + x, y, cz + z);
+ lightengine.checkBlock(pos); + lightengine.checkBlock(pos);
+ } + }
+ } + }
@ -136,7 +122,7 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
+ if (visibleChunk != null) { + if (visibleChunk != null) {
+ world.getChunkSource().chunkMap.addLightTask(visibleChunk, () -> { + world.getChunkSource().chunkMap.addLightTask(visibleChunk, () -> {
+ MinecraftServer.getServer().processQueue.add(() -> { + MinecraftServer.getServer().processQueue.add(() -> {
+ visibleChunk.sendPacketToTrackedPlayers(new ClientboundLightUpdatePacket(chunk.getPos(), lightengine, true), false); + visibleChunk.broadcast(new net.minecraft.network.protocol.game.ClientboundLightUpdatePacket(chunk.getPos(), lightengine, null, null, true), false);
+ updateLight(sender, world, lightengine, queue); + updateLight(sender, world, lightengine, queue);
+ }); + });
+ }); + });
@ -146,37 +132,48 @@ index ff718bc7f521575e6a670e17fcf59a2d30841705..528c860fc0c04431e0ebb2ae6bc96bf9
+ lightengine.setTaskPerBatch(world.paperConfig.lightQueueSize); + lightengine.setTaskPerBatch(world.paperConfig.lightQueueSize);
+ }, MinecraftServer.getServer()); + }, MinecraftServer.getServer());
+ } + }
+ }
private void doSyncLoadInfo(CommandSender sender, String[] args) {
if (!SyncLoadFinder.ENABLED) {
sender.sendMessage(ChatColor.RED + "This command requires the server startup flag '-Dpaper.debug-sync-loads=true' to be set.");
diff --git a/src/main/java/net/minecraft/server/level/ChunkHolder.java b/src/main/java/net/minecraft/server/level/ChunkHolder.java diff --git a/src/main/java/net/minecraft/server/level/ChunkHolder.java b/src/main/java/net/minecraft/server/level/ChunkHolder.java
index 9ebcfca10071cc42d4f1df02c25de5042c065f38..d907872d80f840b343419f49a6708082da6f921b 100644 index 56e292e6550b19d0cae9ebad369da730ca1cabd8..3653ec6f93d627092e63cede51f4db2e12b10613 100644
--- a/src/main/java/net/minecraft/server/level/ChunkHolder.java --- a/src/main/java/net/minecraft/server/level/ChunkHolder.java
+++ b/src/main/java/net/minecraft/server/level/ChunkHolder.java +++ b/src/main/java/net/minecraft/server/level/ChunkHolder.java
@@ -349,6 +349,7 @@ public class ChunkHolder { @@ -312,7 +312,7 @@ public class ChunkHolder {
} }
+ public void sendPacketToTrackedPlayers(Packet<?> packet, boolean flag) { broadcast(packet, flag); } // Paper - OBFHELPER - private void broadcast(Packet<?> packet, boolean onlyOnWatchDistanceEdge) {
private void broadcast(Packet<?> packet, boolean onlyOnWatchDistanceEdge) { + public void broadcast(Packet<?> packet, boolean onlyOnWatchDistanceEdge) { // Paper - private -> public
// Paper start - per player view distance this.playerProvider.getPlayers(this.pos, onlyOnWatchDistanceEdge).forEach((entityplayer) -> {
// there can be potential desync with player's last mapped section and the view distance map, so use the entityplayer.connection.send(packet);
});
diff --git a/src/main/java/net/minecraft/server/level/ChunkMap.java b/src/main/java/net/minecraft/server/level/ChunkMap.java diff --git a/src/main/java/net/minecraft/server/level/ChunkMap.java b/src/main/java/net/minecraft/server/level/ChunkMap.java
index 6b51a082cf42bc3ffc550614e385d3956c5f2efb..67f748d5955453ba4873b0c9bb741b5bfe52d655 100644 index 5473b22d21ea981f245f4826c4d47295890f88ef..480c361c919bbfbebacf9ac94418eac5ed38e233 100644
--- a/src/main/java/net/minecraft/server/level/ChunkMap.java --- a/src/main/java/net/minecraft/server/level/ChunkMap.java
+++ b/src/main/java/net/minecraft/server/level/ChunkMap.java +++ b/src/main/java/net/minecraft/server/level/ChunkMap.java
@@ -344,11 +344,12 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -123,6 +123,12 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
ProcessorHandle<Runnable> mailbox = ProcessorHandle.of("main", mainThreadExecutor::tell); private final ChunkTaskPriorityQueueSorter queueSorter;
private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> worldgenMailbox;
private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mainThreadMailbox;
+ // Paper start
+ final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mailboxLight;
+ public void addLightTask(ChunkHolder playerchunk, Runnable run) {
+ this.mailboxLight.tell(ChunkTaskPriorityQueueSorter.message(playerchunk, run));
+ }
+ // Paper end
public final ChunkProgressListener progressListener;
private final ChunkStatusUpdateListener chunkStatusListener;
public final ChunkMap.ChunkDistanceManager distanceManager;
@@ -199,11 +205,12 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
this.progressListener = worldGenerationProgressListener; this.progressListener = worldGenerationProgressListener;
- ProcessorMailbox<Runnable> threadedmailbox1 = ProcessorMailbox.create(workerExecutor, "light"); this.chunkStatusListener = chunkStatusChangeListener;
+ ProcessorMailbox<Runnable> lightthreaded; ProcessorMailbox<Runnable> threadedmailbox1 = lightthreaded = ProcessorMailbox.create(workerExecutor, "light"); // Paper - ProcessorMailbox<Runnable> threadedmailbox1 = ProcessorMailbox.create(executor, "light");
+ ProcessorMailbox<Runnable> lightthreaded; ProcessorMailbox<Runnable> threadedmailbox1 = lightthreaded = ProcessorMailbox.create(executor, "light"); // Paper
this.queueSorter = new ChunkTaskPriorityQueueSorter(ImmutableList.of(threadedmailbox, mailbox, threadedmailbox1), workerExecutor, Integer.MAX_VALUE); this.queueSorter = new ChunkTaskPriorityQueueSorter(ImmutableList.of(threadedmailbox, mailbox, threadedmailbox1), executor, Integer.MAX_VALUE);
this.worldgenMailbox = this.queueSorter.getProcessor(threadedmailbox, false); this.worldgenMailbox = this.queueSorter.getProcessor(threadedmailbox, false);
this.mainThreadMailbox = this.queueSorter.getProcessor(mailbox, false); this.mainThreadMailbox = this.queueSorter.getProcessor(mailbox, false);
+ this.mailboxLight = this.queueSorter.getProcessor(lightthreaded, false);// Paper + this.mailboxLight = this.queueSorter.getProcessor(lightthreaded, false);// Paper
this.lightEngine = new ThreadedLevelLightEngine(chunkProvider, this, this.level.dimensionType().hasSkyLight(), threadedmailbox1, this.queueSorter.getProcessor(threadedmailbox1, false)); this.lightEngine = new ThreadedLevelLightEngine(chunkProvider, this, this.level.dimensionType().hasSkyLight(), threadedmailbox1, this.queueSorter.getProcessor(threadedmailbox1, false));
this.distanceManager = new ChunkMap.ChunkDistanceManager(workerExecutor, mainThreadExecutor); this.distanceManager.chunkMap = this; // Paper this.distanceManager = new ChunkMap.ChunkDistanceManager(executor, mainThreadExecutor);
this.overworldDataStorage = supplier; this.overworldDataStorage = persistentStateManagerFactory;

View File

@ -9,26 +9,26 @@ Per-Player is absent due to difficulty of maintaining
the diff required to make it happen. the diff required to make it happen.
diff --git a/src/main/java/co/aikar/timings/TimingsExport.java b/src/main/java/co/aikar/timings/TimingsExport.java diff --git a/src/main/java/co/aikar/timings/TimingsExport.java b/src/main/java/co/aikar/timings/TimingsExport.java
index 5bcf9cefc29eb20e2cfbfb49e2b2662ec394a87e..a696474b4bd0e32a26dadfbc1257580ee596f0c0 100644 index f27fadc15cb7f5c782e45885ec6a5a69963beade..2ff4d4921e2076abf415bd3c8f5173ecd6222168 100644
--- a/src/main/java/co/aikar/timings/TimingsExport.java --- a/src/main/java/co/aikar/timings/TimingsExport.java
+++ b/src/main/java/co/aikar/timings/TimingsExport.java +++ b/src/main/java/co/aikar/timings/TimingsExport.java
@@ -156,7 +156,8 @@ public class TimingsExport extends Thread { @@ -152,7 +152,8 @@ public class TimingsExport extends Thread {
pair("gamerules", toObjectMapper(world.getWorld().getGameRules(), rule -> { pair("gamerules", toObjectMapper(world.getWorld().getGameRules(), rule -> {
return pair(rule, world.getWorld().getGameRuleValue(rule)); return pair(rule, world.getWorld().getGameRuleValue(rule));
})), })),
- pair("ticking-distance", world.getChunkProvider().playerChunkMap.getEffectiveViewDistance()) - pair("ticking-distance", world.getChunkSource().chunkMap.getEffectiveViewDistance())
+ pair("ticking-distance", world.getChunkProvider().playerChunkMap.getEffectiveViewDistance()), + pair("ticking-distance", world.getChunkSource().chunkMap.getEffectiveViewDistance()),
+ pair("notick-viewdistance", world.getChunkProvider().playerChunkMap.getEffectiveNoTickViewDistance()) + pair("notick-viewdistance", world.getChunkSource().chunkMap.getEffectiveNoTickViewDistance())
)); ));
})); }));
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
index 46ac6d91422423f1e03b86d3efa3241f2599000d..6463d3e4837d032a35654a035f42b8a805e0e286 100644 index e29566cad2647da4d9288e912188b57f00e8dd0c..3cd8895adecd345c3bdfb8b5e3e9fdf0ef9097db 100644
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java --- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java +++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
@@ -632,4 +632,9 @@ public class PaperWorldConfig { @@ -445,5 +445,10 @@ public class PaperWorldConfig {
phantomIgnoreCreative = getBoolean("phantoms-do-not-spawn-on-creative-players", phantomIgnoreCreative); private void lightQueueSize() {
phantomOnlyAttackInsomniacs = getBoolean("phantoms-only-attack-insomniacs", phantomOnlyAttackInsomniacs); lightQueueSize = getInt("light-queue-size", lightQueueSize);
} }
+ +
+ public int noTickViewDistance; + public int noTickViewDistance;
@ -36,11 +36,12 @@ index 46ac6d91422423f1e03b86d3efa3241f2599000d..6463d3e4837d032a35654a035f42b8a8
+ this.noTickViewDistance = this.getInt("viewdistances.no-tick-view-distance", -1); + this.noTickViewDistance = this.getInt("viewdistances.no-tick-view-distance", -1);
+ } + }
} }
diff --git a/src/main/java/net/minecraft/server/MCUtil.java b/src/main/java/net/minecraft/server/MCUtil.java diff --git a/src/main/java/net/minecraft/server/MCUtil.java b/src/main/java/net/minecraft/server/MCUtil.java
index 9abef8550a89df5e15ac28de1a5549d064f29122..d18497a33dc53f6b465e659967bf8c98731c46c0 100644 index bb0a07a280c7d4885165e9d6488e7741aaa7b47c..9c88426ab1275ee5fb6e28be8b213533dc4ab859 100644
--- a/src/main/java/net/minecraft/server/MCUtil.java --- a/src/main/java/net/minecraft/server/MCUtil.java
+++ b/src/main/java/net/minecraft/server/MCUtil.java +++ b/src/main/java/net/minecraft/server/MCUtil.java
@@ -638,7 +638,8 @@ public final class MCUtil { @@ -636,7 +636,8 @@ public final class MCUtil {
}); });
worldData.addProperty("name", world.getWorld().getName()); worldData.addProperty("name", world.getWorld().getName());
@ -51,13 +52,13 @@ index 9abef8550a89df5e15ac28de1a5549d064f29122..d18497a33dc53f6b465e659967bf8c98
worldData.addProperty("keep-spawn-loaded-range", world.paperConfig.keepLoadedRange); worldData.addProperty("keep-spawn-loaded-range", world.paperConfig.keepLoadedRange);
worldData.addProperty("visible-chunk-count", visibleChunks.size()); worldData.addProperty("visible-chunk-count", visibleChunks.size());
diff --git a/src/main/java/net/minecraft/server/level/ChunkHolder.java b/src/main/java/net/minecraft/server/level/ChunkHolder.java diff --git a/src/main/java/net/minecraft/server/level/ChunkHolder.java b/src/main/java/net/minecraft/server/level/ChunkHolder.java
index 0147798c0285f64b8d767dfb2709d92f66ac72ef..9ebcfca10071cc42d4f1df02c25de5042c065f38 100644 index 3653ec6f93d627092e63cede51f4db2e12b10613..995d7977233f0d7683c00a75c3833f9a1eba7f92 100644
--- a/src/main/java/net/minecraft/server/level/ChunkHolder.java --- a/src/main/java/net/minecraft/server/level/ChunkHolder.java
+++ b/src/main/java/net/minecraft/server/level/ChunkHolder.java +++ b/src/main/java/net/minecraft/server/level/ChunkHolder.java
@@ -81,6 +81,18 @@ public class ChunkHolder { @@ -75,6 +75,17 @@ public class ChunkHolder {
}
// Paper end - optimise isOutsideOfRange
boolean isUpdateQueued = false; // Paper
private final ChunkMap chunkMap; // Paper
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ public final LevelChunk getSendingChunk() { + public final LevelChunk getSendingChunk() {
+ // it's important that we use getChunkAtIfLoadedImmediately to mirror the chunk sending logic used + // it's important that we use getChunkAtIfLoadedImmediately to mirror the chunk sending logic used
@ -69,32 +70,31 @@ index 0147798c0285f64b8d767dfb2709d92f66ac72ef..9ebcfca10071cc42d4f1df02c25de504
+ return null; + return null;
+ } + }
+ // Paper end - no-tick view distance + // Paper end - no-tick view distance
+
public ChunkHolder(ChunkPos pos, int level, LevelLightEngine lightingProvider, ChunkHolder.LevelChangeListener levelUpdateListener, ChunkHolder.PlayerProvider playersWatchingChunkProvider) { public ChunkHolder(ChunkPos pos, int level, LevelHeightAccessor world, LevelLightEngine lightingProvider, ChunkHolder.LevelChangeListener levelUpdateListener, ChunkHolder.PlayerProvider playersWatchingChunkProvider) {
this.futures = new AtomicReferenceArray(ChunkHolder.CHUNK_STATUSES.size()); this.futures = new AtomicReferenceArray(ChunkHolder.CHUNK_STATUSES.size());
this.fullChunkFuture = ChunkHolder.UNLOADED_LEVEL_CHUNK_FUTURE; @@ -207,7 +218,7 @@ public class ChunkHolder {
@@ -240,7 +252,7 @@ public class ChunkHolder {
} }
public void blockChanged(BlockPos blockposition) { public void blockChanged(BlockPos pos) {
- LevelChunk chunk = this.getTickingChunk(); - LevelChunk chunk = this.getTickingChunk();
+ LevelChunk chunk = this.getSendingChunk(); // Paper - no-tick view distance + LevelChunk chunk = this.getSendingChunk(); // Paper - no-tick view distance
if (chunk != null) { if (chunk != null) {
byte b0 = (byte) SectionPos.blockToSectionCoord(blockposition.getY()); int i = this.levelHeightAccessor.getSectionIndex(pos.getY());
@@ -256,7 +268,7 @@ public class ChunkHolder { @@ -223,7 +234,7 @@ public class ChunkHolder {
} }
public void sectionLightChanged(LightLayer type, int y) { public void sectionLightChanged(LightLayer lightType, int y) {
- LevelChunk chunk = this.getTickingChunk(); - LevelChunk chunk = this.getTickingChunk();
+ LevelChunk chunk = this.getSendingChunk(); // Paper - no-tick view distance + LevelChunk chunk = this.getSendingChunk(); // Paper - no-tick view distance
if (chunk != null) { if (chunk != null) {
chunk.setUnsaved(true); chunk.setUnsaved(true);
@@ -338,9 +350,48 @@ public class ChunkHolder { @@ -313,9 +324,48 @@ public class ChunkHolder {
} }
private void broadcast(Packet<?> packet, boolean onlyOnWatchDistanceEdge) { public void broadcast(Packet<?> packet, boolean onlyOnWatchDistanceEdge) { // Paper - private -> public
- this.playerProvider.getPlayers(this.pos, onlyOnWatchDistanceEdge).forEach((entityplayer) -> { - this.playerProvider.getPlayers(this.pos, onlyOnWatchDistanceEdge).forEach((entityplayer) -> {
- entityplayer.connection.send(packet); - entityplayer.connection.send(packet);
- }); - });
@ -119,8 +119,8 @@ index 0147798c0285f64b8d767dfb2709d92f66ac72ef..9ebcfca10071cc42d4f1df02c25de504
+ int viewDistance = viewDistanceMap.getLastViewDistance(player); + int viewDistance = viewDistanceMap.getLastViewDistance(player);
+ long lastPosition = viewDistanceMap.getLastCoordinate(player); + long lastPosition = viewDistanceMap.getLastCoordinate(player);
+ +
+ int distX = Math.abs(MCUtil.getCoordinateX(lastPosition) - this.pos.x); + int distX = Math.abs(net.minecraft.server.MCUtil.getCoordinateX(lastPosition) - this.pos.x);
+ int distZ = Math.abs(MCUtil.getCoordinateZ(lastPosition) - this.pos.z); + int distZ = Math.abs(net.minecraft.server.MCUtil.getCoordinateZ(lastPosition) - this.pos.z);
+ +
+ if (Math.max(distX, distZ) == viewDistance) { + if (Math.max(distX, distZ) == viewDistance) {
+ player.connection.send(packet); + player.connection.send(packet);
@ -144,43 +144,22 @@ index 0147798c0285f64b8d767dfb2709d92f66ac72ef..9ebcfca10071cc42d4f1df02c25de504
public CompletableFuture<Either<ChunkAccess, ChunkHolder.ChunkLoadingFailure>> getOrScheduleFuture(ChunkStatus targetStatus, ChunkMap chunkStorage) { public CompletableFuture<Either<ChunkAccess, ChunkHolder.ChunkLoadingFailure>> getOrScheduleFuture(ChunkStatus targetStatus, ChunkMap chunkStorage) {
diff --git a/src/main/java/net/minecraft/server/level/ChunkMap.java b/src/main/java/net/minecraft/server/level/ChunkMap.java diff --git a/src/main/java/net/minecraft/server/level/ChunkMap.java b/src/main/java/net/minecraft/server/level/ChunkMap.java
index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d3956c5f2efb 100644 index 480c361c919bbfbebacf9ac94418eac5ed38e233..fdf5d8ede4b01e399272ddebfbd49258b166f00b 100644
--- a/src/main/java/net/minecraft/server/level/ChunkMap.java --- a/src/main/java/net/minecraft/server/level/ChunkMap.java
+++ b/src/main/java/net/minecraft/server/level/ChunkMap.java +++ b/src/main/java/net/minecraft/server/level/ChunkMap.java
@@ -57,12 +57,14 @@ import net.minecraft.network.protocol.Packet; @@ -122,7 +122,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
import net.minecraft.network.protocol.game.ClientboundLevelChunkPacket;
import net.minecraft.network.protocol.game.ClientboundLightUpdatePacket;
import net.minecraft.network.protocol.game.ClientboundSetChunkCacheCenterPacket;
+import net.minecraft.network.protocol.game.ClientboundSetChunkCacheRadiusPacket;
import net.minecraft.network.protocol.game.ClientboundSetEntityLinkPacket;
import net.minecraft.network.protocol.game.ClientboundSetPassengersPacket;
import net.minecraft.network.protocol.game.DebugPackets;
import net.minecraft.server.MCUtil;
import net.minecraft.server.MinecraftServer;
import net.minecraft.server.level.progress.ChunkProgressListener;
+import net.minecraft.server.network.ServerGamePacketListenerImpl;
import net.minecraft.util.CsvOutput;
import net.minecraft.util.Mth;
import net.minecraft.util.profiling.ProfilerFiller;
@@ -144,7 +146,13 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
private boolean modified; private boolean modified;
private final ChunkTaskPriorityQueueSorter queueSorter; private final ChunkTaskPriorityQueueSorter queueSorter;
private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> worldgenMailbox; private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> worldgenMailbox;
- private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mainThreadMailbox; - private final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mainThreadMailbox;
+ public final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mainThreadMailbox; // Paper - private -> public + public final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mainThreadMailbox; // Paper - private -> public
+ // Paper start // Paper start
+ final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mailboxLight; final ProcessorHandle<ChunkTaskPriorityQueueSorter.Message<Runnable>> mailboxLight;
+ public void addLightTask(ChunkHolder playerchunk, Runnable run) { public void addLightTask(ChunkHolder playerchunk, Runnable run) {
+ this.mailboxLight.tell(ChunkTaskPriorityQueueSorter.message(playerchunk, run)); @@ -164,21 +164,68 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
+ }
+ // Paper end // Paper start - distance maps
public final ChunkProgressListener progressListener; private final com.destroystokyo.paper.util.misc.PooledLinkedHashSets<ServerPlayer> pooledLinkedPlayerHashSets = new com.destroystokyo.paper.util.misc.PooledLinkedHashSets<>();
public final ChunkMap.ChunkDistanceManager distanceManager; public final DistanceManager getChunkDistanceManager() { return this.distanceManager; } // Paper - OBFHELPER
private final AtomicInteger tickingGenerated;
@@ -219,6 +227,22 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
public final com.destroystokyo.paper.util.misc.PlayerAreaMap playerMobSpawnMap; // this map is absent from updateMaps since it's controlled at the start of the chunkproviderserver tick
public final com.destroystokyo.paper.util.misc.PlayerAreaMap playerChunkTickRangeMap;
// Paper end - optimise PlayerChunkMap#isOutsideRange
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ int noTickViewDistance; + int noTickViewDistance;
+ public final int getRawNoTickViewDistance() { + public final int getRawNoTickViewDistance() {
@ -200,15 +179,13 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
void addPlayerToDistanceMaps(ServerPlayer player) { void addPlayerToDistanceMaps(ServerPlayer player) {
int chunkX = MCUtil.getChunkCoordinate(player.getX()); int chunkX = MCUtil.getChunkCoordinate(player.getX());
@@ -235,6 +259,19 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider int chunkZ = MCUtil.getChunkCoordinate(player.getZ());
// Paper start - optimise PlayerChunkMap#isOutsideRange // Note: players need to be explicitly added to distance maps before they can be updated
this.playerChunkTickRangeMap.add(player, chunkX, chunkZ, DistanceManager.MOB_SPAWN_RANGE);
// Paper end - optimise PlayerChunkMap#isOutsideRange
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ int effectiveTickViewDistance = this.getEffectiveViewDistance(); + int effectiveTickViewDistance = this.getEffectiveViewDistance();
+ int effectiveNoTickViewDistance = Math.max(this.getEffectiveNoTickViewDistance(), effectiveTickViewDistance); + int effectiveNoTickViewDistance = Math.max(this.getEffectiveNoTickViewDistance(), effectiveTickViewDistance);
+ +
+ if (!this.cannotLoadChunks(player)) { + if (!this.skipPlayer(player)) {
+ this.playerViewDistanceTickMap.add(player, chunkX, chunkZ, effectiveTickViewDistance); + this.playerViewDistanceTickMap.add(player, chunkX, chunkZ, effectiveTickViewDistance);
+ this.playerViewDistanceNoTickMap.add(player, chunkX, chunkZ, effectiveNoTickViewDistance + 2); // clients need chunk 1 neighbour, and we need another 1 for sending those extra neighbours (as we require neighbours to send) + this.playerViewDistanceNoTickMap.add(player, chunkX, chunkZ, effectiveNoTickViewDistance + 2); // clients need chunk 1 neighbour, and we need another 1 for sending those extra neighbours (as we require neighbours to send)
+ } + }
@ -220,10 +197,7 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
} }
void removePlayerFromDistanceMaps(ServerPlayer player) { void removePlayerFromDistanceMaps(ServerPlayer player) {
@@ -247,6 +284,11 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
this.playerMobSpawnMap.remove(player);
this.playerChunkTickRangeMap.remove(player);
// Paper end - optimise PlayerChunkMap#isOutsideRange
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ this.playerViewDistanceBroadcastMap.remove(player); + this.playerViewDistanceBroadcastMap.remove(player);
+ this.playerViewDistanceTickMap.remove(player); + this.playerViewDistanceTickMap.remove(player);
@ -232,15 +206,14 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
} }
void updateMaps(ServerPlayer player) { void updateMaps(ServerPlayer player) {
@@ -264,6 +306,19 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider int chunkX = MCUtil.getChunkCoordinate(player.getX());
// Paper start - optimise PlayerChunkMap#isOutsideRange int chunkZ = MCUtil.getChunkCoordinate(player.getZ());
this.playerChunkTickRangeMap.update(player, chunkX, chunkZ, DistanceManager.MOB_SPAWN_RANGE); // Note: players need to be explicitly added to distance maps before they can be updated
// Paper end - optimise PlayerChunkMap#isOutsideRange
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ int effectiveTickViewDistance = this.getEffectiveViewDistance(); + int effectiveTickViewDistance = this.getEffectiveViewDistance();
+ int effectiveNoTickViewDistance = Math.max(this.getEffectiveNoTickViewDistance(), effectiveTickViewDistance); + int effectiveNoTickViewDistance = Math.max(this.getEffectiveNoTickViewDistance(), effectiveTickViewDistance);
+ +
+ if (!this.cannotLoadChunks(player)) { + if (!this.skipPlayer(player)) {
+ this.playerViewDistanceTickMap.update(player, chunkX, chunkZ, effectiveTickViewDistance); + this.playerViewDistanceTickMap.update(player, chunkX, chunkZ, effectiveTickViewDistance);
+ this.playerViewDistanceNoTickMap.update(player, chunkX, chunkZ, effectiveNoTickViewDistance + 2); // clients need chunk 1 neighbour, and we need another 1 for sending those extra neighbours (as we require neighbours to send) + this.playerViewDistanceNoTickMap.update(player, chunkX, chunkZ, effectiveNoTickViewDistance + 2); // clients need chunk 1 neighbour, and we need another 1 for sending those extra neighbours (as we require neighbours to send)
+ } + }
@ -252,10 +225,10 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
} }
// Paper end // Paper end
@@ -371,6 +426,45 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -216,6 +263,45 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
} this.overworldDataStorage = persistentStateManagerFactory;
}); this.poiManager = new PoiManager(new File(this.storageFolder, "poi"), dataFixer, dsync, world);
// Paper end - optimise PlayerChunkMap#isOutsideRange this.setViewDistance(viewDistance);
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ this.setNoTickViewDistance(this.level.paperConfig.noTickViewDistance); + this.setNoTickViewDistance(this.level.paperConfig.noTickViewDistance);
+ this.playerViewDistanceTickMap = new com.destroystokyo.paper.util.misc.PlayerAreaMap(this.pooledLinkedPlayerHashSets, + this.playerViewDistanceTickMap = new com.destroystokyo.paper.util.misc.PlayerAreaMap(this.pooledLinkedPlayerHashSets,
@ -297,10 +270,10 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+ // Paper end - no-tick view distance + // Paper end - no-tick view distance
} }
public void updatePlayerMobTypeMap(Entity entity) { private static double euclideanDistanceSquared(ChunkPos pos, Entity entity) {
@@ -1199,15 +1293,11 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -863,14 +949,10 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
completablefuture1.thenAcceptAsync((either) -> { completablefuture1.thenAcceptAsync((either) -> {
either.mapLeft((chunk) -> { either.ifLeft((chunk) -> {
this.tickingGenerated.getAndIncrement(); this.tickingGenerated.getAndIncrement();
- Packet<?>[] apacket = new Packet[2]; - Packet<?>[] apacket = new Packet[2];
- -
@ -308,7 +281,6 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
- this.playerLoadedChunk(entityplayer, apacket, chunk); - this.playerLoadedChunk(entityplayer, apacket, chunk);
- }); - });
+ // Paper - no-tick view distance - moved to Chunk neighbour update + // Paper - no-tick view distance - moved to Chunk neighbour update
return Either.left(chunk);
}); });
}, (runnable) -> { }, (runnable) -> {
- this.mainThreadMailbox.tell(ChunkTaskPriorityQueueSorter.message(holder, runnable)); - this.mainThreadMailbox.tell(ChunkTaskPriorityQueueSorter.message(holder, runnable));
@ -316,7 +288,7 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
}); });
return completablefuture1; return completablefuture1;
} }
@@ -1302,32 +1392,38 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -962,28 +1044,35 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
} }
} }
@ -341,7 +313,7 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+ } + }
- this.getPlayers(chunkcoordintpair, false).forEach((entityplayer) -> { - this.getPlayers(chunkcoordintpair, false).forEach((entityplayer) -> {
- int l = checkerboardDistance(chunkcoordintpair, entityplayer, true); - int l = ChunkMap.checkerboardDistance(chunkcoordintpair, entityplayer, true);
- boolean flag = l <= k; - boolean flag = l <= k;
- boolean flag1 = l <= this.viewDistance; - boolean flag1 = l <= this.viewDistance;
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
@ -356,21 +328,17 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+ +
+ if (this.level != null && this.level.players != null) { // this can be called from constructor, where these aren't set + if (this.level != null && this.level.players != null) { // this can be called from constructor, where these aren't set
+ for (ServerPlayer player : this.level.players) { + for (ServerPlayer player : this.level.players) {
+ ServerGamePacketListenerImpl connection = player.connection; + net.minecraft.server.network.ServerGamePacketListenerImpl connection = player.connection;
+ if (connection != null) { + if (connection != null) {
+ // moved in from PlayerList + // moved in from PlayerList
+ connection.send(new ClientboundSetChunkCacheRadiusPacket(loadViewDistance)); + connection.send(new net.minecraft.network.protocol.game.ClientboundSetChunkCacheRadiusPacket(loadViewDistance));
+ } + }
+ this.updateMaps(player); + this.updateMaps(player);
+ // Paper end - no-tick view distance
} }
} }
-
}
+ // Paper end - no-tick view distance
protected void updateChunkTracking(ServerPlayer player, ChunkPos pos, Packet<?>[] packets, boolean withinMaxWatchDistance, boolean withinViewDistance) { @@ -995,7 +1084,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
if (player.level == this.level) {
@@ -1335,7 +1431,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
ChunkHolder playerchunk = this.getVisibleChunkIfPresent(pos.toLong()); ChunkHolder playerchunk = this.getVisibleChunkIfPresent(pos.toLong());
if (playerchunk != null) { if (playerchunk != null) {
@ -379,15 +347,7 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
if (chunk != null) { if (chunk != null) {
this.playerLoadedChunk(player, packets, chunk); this.playerLoadedChunk(player, packets, chunk);
@@ -1596,6 +1692,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1202,13 +1291,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
}
// Paper end - optimise isOutsideOfRange
+ private boolean cannotLoadChunks(ServerPlayer entityplayer) { return this.skipPlayer(entityplayer); } // Paper - OBFHELPER
private boolean skipPlayer(ServerPlayer player) {
return player.isSpectator() && !this.level.getGameRules().getBoolean(GameRules.RULE_SPECTATORSGENERATECHUNKS);
}
@@ -1623,13 +1720,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
this.removePlayerFromDistanceMaps(player); // Paper - distance maps this.removePlayerFromDistanceMaps(player); // Paper - distance maps
} }
@ -402,16 +362,16 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
} }
@@ -1637,7 +1728,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1216,7 +1299,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
SectionPos sectionposition = SectionPos.of((Entity) entityplayer); SectionPos sectionposition = SectionPos.of((Entity) player);
entityplayer.setLastSectionPos(sectionposition); player.setLastSectionPos(sectionposition);
- entityplayer.connection.send(new ClientboundSetChunkCacheCenterPacket(sectionposition.x(), sectionposition.z())); - player.connection.send(new ClientboundSetChunkCacheCenterPacket(sectionposition.x(), sectionposition.z()));
+ // Paper - distance map handles this now + // player.connection.send(new ClientboundSetChunkCacheCenterPacket(sectionposition.x(), sectionposition.z())); // Paper - distance map handles this now
return sectionposition; return sectionposition;
} }
@@ -1682,6 +1773,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1271,6 +1354,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
int k1; int k1;
int l1; int l1;
@ -419,65 +379,26 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
if (Math.abs(i1 - i) <= this.viewDistance * 2 && Math.abs(j1 - j) <= this.viewDistance * 2) { if (Math.abs(i1 - i) <= this.viewDistance * 2 && Math.abs(j1 - j) <= this.viewDistance * 2) {
k1 = Math.min(i, i1) - this.viewDistance; k1 = Math.min(i, i1) - this.viewDistance;
l1 = Math.min(j, j1) - this.viewDistance; l1 = Math.min(j, j1) - this.viewDistance;
@@ -1690,36 +1782,36 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1309,6 +1393,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
for (int k2 = k1; k2 <= i2; ++k2) {
for (int l2 = l1; l2 <= j2; ++l2) {
- ChunkPos chunkcoordintpair = new ChunkPos(k2, l2);
- boolean flag3 = checkerboardDistance(chunkcoordintpair, i1, j1) <= this.viewDistance;
- boolean flag4 = checkerboardDistance(chunkcoordintpair, i, j) <= this.viewDistance;
+ ChunkCoordIntPair chunkcoordintpair = new ChunkCoordIntPair(k2, l2);
+ boolean flag3 = a(chunkcoordintpair, i1, j1) <= this.viewDistance;
+ boolean flag4 = a(chunkcoordintpair, i, j) <= this.viewDistance;
- this.updateChunkTracking(player, chunkcoordintpair, new Packet[2], flag3, flag4);
+ this.sendChunk(entityplayer, chunkcoordintpair, new Packet[2], flag3, flag4);
} }
} }
} else { }
- ChunkPos chunkcoordintpair1; + */ // Paper end - replaced by distance map
+ ChunkCoordIntPair chunkcoordintpair1;
boolean flag5;
boolean flag6;
for (k1 = i1 - this.viewDistance; k1 <= i1 + this.viewDistance; ++k1) {
for (l1 = j1 - this.viewDistance; l1 <= j1 + this.viewDistance; ++l1) {
- chunkcoordintpair1 = new ChunkPos(k1, l1);
+ chunkcoordintpair1 = new ChunkCoordIntPair(k1, l1);
flag5 = true;
flag6 = false;
- this.updateChunkTracking(player, chunkcoordintpair1, new Packet[2], true, false);
+ this.sendChunk(entityplayer, chunkcoordintpair1, new Packet[2], true, false);
}
}
for (k1 = i - this.viewDistance; k1 <= i + this.viewDistance; ++k1) {
for (l1 = j - this.viewDistance; l1 <= j + this.viewDistance; ++l1) {
- chunkcoordintpair1 = new ChunkPos(k1, l1);
+ chunkcoordintpair1 = new ChunkCoordIntPair(k1, l1);
flag5 = false;
flag6 = true;
- this.updateChunkTracking(player, chunkcoordintpair1, new Packet[2], false, true);
+ this.sendChunk(entityplayer, chunkcoordintpair1, new Packet[2], false, true);
}
}
- }
+ }*/ // Paper end - replaced by distance map
this.updateMaps(player); // Paper - distance maps this.updateMaps(player); // Paper - distance maps
@@ -1727,11 +1819,46 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1316,11 +1401,46 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
@Override @Override
public Stream<ServerPlayer> getPlayers(ChunkPos chunkPos, boolean onlyOnWatchDistanceEdge) { public Stream<ServerPlayer> getPlayers(ChunkPos chunkPos, boolean onlyOnWatchDistanceEdge) {
- return this.playerMap.a(chunkPos.toLong()).filter((entityplayer) -> { - return this.playerMap.getPlayers(chunkPos.toLong()).filter((entityplayer) -> {
- int i = b(chunkcoordintpair, entityplayer, true); - int i = ChunkMap.checkerboardDistance(chunkPos, entityplayer, true);
+ // Paper start - per player view distance + // Paper start - per player view distance
+ // there can be potential desync with player's last mapped section and the view distance map, so use the + // there can be potential desync with player's last mapped section and the view distance map, so use the
+ // view distance map here. + // view distance map here.
+ com.destroystokyo.paper.util.misc.PooledLinkedHashSets.PooledObjectLinkedOpenHashSet<ServerPlayer> inRange = this.playerViewDistanceBroadcastMap.getObjectsInRange(chunkPos); + com.destroystokyo.paper.util.misc.PooledLinkedHashSets.PooledObjectLinkedOpenHashSet<ServerPlayer> inRange = this.playerViewDistanceBroadcastMap.getObjectsInRange(chunkPos);
- return i > this.viewDistance ? false : !flag || i == this.viewDistance; - return i > this.viewDistance ? false : !onlyOnWatchDistanceEdge || i == this.viewDistance;
- }); - });
+ if (inRange == null) { + if (inRange == null) {
+ return Stream.empty(); + return Stream.empty();
@ -516,15 +437,15 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+ // Paper end - per player view distance + // Paper end - per player view distance
} }
public void addEntity(Entity entity) { // Paper - protected -> public protected void addEntity(Entity entity) {
@@ -1889,7 +2016,48 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider @@ -1442,7 +1562,48 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider
} }
- private final void sendChunk(ServerPlayer entityplayer, Packet<?>[] apacket, LevelChunk chunk) { this.playerLoadedChunk(entityplayer, apacket, chunk); } // Paper - OBFHELPER - private void playerLoadedChunk(ServerPlayer player, Packet<?>[] packets, LevelChunk chunk) {
+ // Paper start + // Paper start
+ private static int getLightMask(final LevelChunk chunk) { + private static int getLightMask(final LevelChunk chunk) {
+ final ChunkSection[] chunkSections = chunk.getSections(); + final net.minecraft.world.level.chunk.LevelChunkSection[] chunkSections = chunk.getSections();
+ int mask = 0; + int mask = 0;
+ +
+ for (int i = 0; i < chunkSections.length; ++i) { + for (int i = 0; i < chunkSections.length; ++i) {
@ -535,7 +456,7 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+Sections go from 0..16. Now whenever a section is not empty, it can potentially change lighting for the section itself, the section below and the section above, hence the bitmask 111b, which is 7d. +Sections go from 0..16. Now whenever a section is not empty, it can potentially change lighting for the section itself, the section below and the section above, hence the bitmask 111b, which is 7d.
+ +
+ */ + */
+ mask |= (ChunkSection.isEmpty(chunkSections[i]) ? 0 : 7) << i; + mask |= (net.minecraft.world.level.chunk.LevelChunkSection.isEmpty(chunkSections[i]) ? 0 : 7) << i;
+ } + }
+ +
+ return mask; + return mask;
@ -563,24 +484,15 @@ index 56ca469bf930bcced88efdafc78f464c756a5be9..6b51a082cf42bc3ffc550614e385d395
+ } + }
+ // Paper end + // Paper end
+ +
+ public final void sendChunk(ServerPlayer entityplayer, Packet<?>[] apacket, LevelChunk chunk) { this.playerLoadedChunk(entityplayer, apacket, chunk); } // Paper - OBFHELPER + public void playerLoadedChunk(ServerPlayer player, Packet<?>[] packets, LevelChunk chunk) { // Paper - private -> public
private void playerLoadedChunk(ServerPlayer player, Packet<?>[] packets, LevelChunk chunk) {
if (packets[0] == null) { if (packets[0] == null) {
packets[0] = new ClientboundLevelChunkPacket(chunk, 65535, chunk.world.chunkPacketBlockController.shouldModify(player, chunk, 65535)); // Paper - Anti-Xray - Bypass packets[0] = new ClientboundLevelChunkPacket(chunk);
@@ -2075,7 +2243,7 @@ public class ChunkMap extends ChunkStorage implements ChunkHolder.PlayerProvider packets[1] = new ClientboundLightUpdatePacket(chunk.getPos(), this.lightEngine, (BitSet) null, (BitSet) null, true);
ChunkPos chunkcoordintpair = new ChunkPos(this.entity.xChunk, this.entity.zChunk);
ChunkHolder playerchunk = ChunkMap.this.getVisibleChunkIfPresent(chunkcoordintpair.toLong());
- if (playerchunk != null && playerchunk.getTickingChunk() != null) {
+ if (playerchunk != null && playerchunk.getSendingChunk() != null) { // Paper - no-tick view distance
flag1 = ChunkMap.checkerboardDistance(chunkcoordintpair, player, false) <= ChunkMap.this.viewDistance;
}
}
diff --git a/src/main/java/net/minecraft/server/level/DistanceManager.java b/src/main/java/net/minecraft/server/level/DistanceManager.java diff --git a/src/main/java/net/minecraft/server/level/DistanceManager.java b/src/main/java/net/minecraft/server/level/DistanceManager.java
index 91c672531087430c47365657a3219ab5980d3467..c9b4025f6c3d1be7bca2ff7337dd86e37d21b53e 100644 index 45c7ebe67019cdbe88b6617a95d5c40d3a68286c..38eebda226e007c8910e04f502ce218cdfe1d456 100644
--- a/src/main/java/net/minecraft/server/level/DistanceManager.java --- a/src/main/java/net/minecraft/server/level/DistanceManager.java
+++ b/src/main/java/net/minecraft/server/level/DistanceManager.java +++ b/src/main/java/net/minecraft/server/level/DistanceManager.java
@@ -269,8 +269,8 @@ public abstract class DistanceManager { @@ -275,8 +275,8 @@ public abstract class DistanceManager {
return s; return s;
} }
@ -591,7 +503,7 @@ index 91c672531087430c47365657a3219ab5980d3467..c9b4025f6c3d1be7bca2ff7337dd86e3
} }
public int getNaturalSpawnChunkCount() { public int getNaturalSpawnChunkCount() {
@@ -388,7 +388,7 @@ public abstract class DistanceManager { @@ -503,7 +503,7 @@ public abstract class DistanceManager {
private void onLevelChange(long pos, int distance, boolean oldWithinViewDistance, boolean withinViewDistance) { private void onLevelChange(long pos, int distance, boolean oldWithinViewDistance, boolean withinViewDistance) {
if (oldWithinViewDistance != withinViewDistance) { if (oldWithinViewDistance != withinViewDistance) {
@ -601,23 +513,22 @@ index 91c672531087430c47365657a3219ab5980d3467..c9b4025f6c3d1be7bca2ff7337dd86e3
if (withinViewDistance) { if (withinViewDistance) {
DistanceManager.this.ticketThrottlerInput.tell(ChunkTaskPriorityQueueSorter.message(() -> { DistanceManager.this.ticketThrottlerInput.tell(ChunkTaskPriorityQueueSorter.message(() -> {
diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java diff --git a/src/main/java/net/minecraft/server/level/ServerPlayer.java b/src/main/java/net/minecraft/server/level/ServerPlayer.java
index 95f1f4727a8e2000931e6f36b862e3ad28334a69..8e4cef60b760be385df81a74834d026f856a78c5 100644 index 4fef4c0240be90ddcb9640f5719e292d2d5dbdf8..bffc897cb88a54c36432c98264f3416051aeab17 100644
--- a/src/main/java/net/minecraft/server/level/ServerPlayer.java --- a/src/main/java/net/minecraft/server/level/ServerPlayer.java
+++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java +++ b/src/main/java/net/minecraft/server/level/ServerPlayer.java
@@ -249,6 +249,8 @@ public class ServerPlayer extends Player implements ContainerListener { @@ -241,6 +241,7 @@ public class ServerPlayer extends Player {
public PlayerNaturallySpawnCreaturesEvent playerNaturallySpawnedEvent; // Paper
double lastEntitySpawnRadiusSquared; // Paper - optimise isOutsideRange, this field is in blocks
public final com.destroystokyo.paper.util.misc.PooledLinkedHashSets.PooledObjectLinkedOpenHashSet<ServerPlayer> cachedSingleHashSet; // Paper
+ boolean needsChunkCenterUpdate; // Paper - no-tick view distance + boolean needsChunkCenterUpdate; // Paper - no-tick view distance
+
public ServerPlayer(MinecraftServer server, ServerLevel world, GameProfile profile, ServerPlayerGameMode interactionManager) { public ServerPlayer(MinecraftServer server, ServerLevel world, GameProfile profile) {
super(world, world.getSpawn(), world.getSharedSpawnAngle(), profile); super(world, world.getSharedSpawnPos(), world.getSharedSpawnAngle(), profile);
this.respawnDimension = Level.OVERWORLD;
diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java
index ffc8c9ee8b1768dd809189858ee45658fb9bf1c5..8e00747c1a717836d12a43aa48d667bf801167b0 100644 index bcc946d2747443c34ee8ac2485a5ab41773c93af..2730923bd0bf3b0f928765b9e09e2299fa9a393d 100644
--- a/src/main/java/net/minecraft/server/players/PlayerList.java --- a/src/main/java/net/minecraft/server/players/PlayerList.java
+++ b/src/main/java/net/minecraft/server/players/PlayerList.java +++ b/src/main/java/net/minecraft/server/players/PlayerList.java
@@ -250,7 +250,7 @@ public abstract class PlayerList { @@ -241,7 +241,7 @@ public abstract class PlayerList {
boolean flag1 = gamerules.getBoolean(GameRules.RULE_REDUCEDDEBUGINFO); boolean flag1 = gamerules.getBoolean(GameRules.RULE_REDUCEDDEBUGINFO);
// Spigot - view distance // Spigot - view distance
@ -626,16 +537,16 @@ index ffc8c9ee8b1768dd809189858ee45658fb9bf1c5..8e00747c1a717836d12a43aa48d667bf
player.getBukkitEntity().sendSupportedChannels(); // CraftBukkit player.getBukkitEntity().sendSupportedChannels(); // CraftBukkit
playerconnection.send(new ClientboundCustomPayloadPacket(ClientboundCustomPayloadPacket.BRAND, (new FriendlyByteBuf(Unpooled.buffer())).writeUtf(this.getServer().getServerModName()))); playerconnection.send(new ClientboundCustomPayloadPacket(ClientboundCustomPayloadPacket.BRAND, (new FriendlyByteBuf(Unpooled.buffer())).writeUtf(this.getServer().getServerModName())));
playerconnection.send(new ClientboundChangeDifficultyPacket(worlddata.getDifficulty(), worlddata.isDifficultyLocked())); playerconnection.send(new ClientboundChangeDifficultyPacket(worlddata.getDifficulty(), worlddata.isDifficultyLocked()));
@@ -904,7 +904,7 @@ public abstract class PlayerList { @@ -789,7 +789,7 @@ public abstract class PlayerList {
// CraftBukkit start // CraftBukkit start
LevelData worlddata = worldserver1.getLevelData(); LevelData worlddata = worldserver1.getLevelData();
entityplayer1.connection.send(new ClientboundRespawnPacket(worldserver1.dimensionType(), worldserver1.dimension(), BiomeManager.obfuscateSeed(worldserver1.getSeed()), entityplayer1.gameMode.getGameModeForPlayer(), entityplayer1.gameMode.getPreviousGameModeForPlayer(), worldserver1.isDebug(), worldserver1.isFlat(), flag)); entityplayer1.connection.send(new ClientboundRespawnPacket(worldserver1.dimensionType(), worldserver1.dimension(), BiomeManager.obfuscateSeed(worldserver1.getSeed()), entityplayer1.gameMode.getGameModeForPlayer(), entityplayer1.gameMode.getPreviousGameModeForPlayer(), worldserver1.isDebug(), worldserver1.isFlat(), flag));
- entityplayer1.connection.send(new ClientboundSetChunkCacheRadiusPacket(worldserver1.spigotConfig.viewDistance)); // Spigot - entityplayer1.connection.send(new ClientboundSetChunkCacheRadiusPacket(worldserver1.spigotConfig.viewDistance)); // Spigot
+ entityplayer1.connection.send(new ClientboundSetChunkCacheRadiusPacket(worldserver1.getChunkSource().chunkMap.getLoadViewDistance())); // Spigot // Paper - no-tick view distance + entityplayer1.connection.send(new ClientboundSetChunkCacheRadiusPacket(worldserver1.getChunkSource().chunkMap.getLoadViewDistance())); // Spigot // Paper - no-tick view distance
entityplayer1.setLevel(worldserver1); entityplayer1.setLevel(worldserver1);
entityplayer1.removed = false; entityplayer1.unsetRemoved();
entityplayer1.connection.teleport(new Location(worldserver1.getWorld(), entityplayer1.getX(), entityplayer1.getY(), entityplayer1.getZ(), entityplayer1.yRot, entityplayer1.xRot)); entityplayer1.connection.teleport(new Location(worldserver1.getWorld(), entityplayer1.getX(), entityplayer1.getY(), entityplayer1.getZ(), entityplayer1.getYRot(), entityplayer1.getXRot()));
@@ -1372,7 +1372,7 @@ public abstract class PlayerList { @@ -1273,7 +1273,7 @@ public abstract class PlayerList {
public void setViewDistance(int viewDistance) { public void setViewDistance(int viewDistance) {
this.viewDistance = viewDistance; this.viewDistance = viewDistance;
@ -645,10 +556,10 @@ index ffc8c9ee8b1768dd809189858ee45658fb9bf1c5..8e00747c1a717836d12a43aa48d667bf
while (iterator.hasNext()) { while (iterator.hasNext()) {
diff --git a/src/main/java/net/minecraft/world/level/Level.java b/src/main/java/net/minecraft/world/level/Level.java diff --git a/src/main/java/net/minecraft/world/level/Level.java b/src/main/java/net/minecraft/world/level/Level.java
index 5860e7866724abd35bde2a5710d9c92799e5de67..67ab681a9c9157a420de5fd872bde1fc0de24561 100644 index ddcde88a8c8b748b4dc2583b4dfd0fb8ea9e201e..07e81fa1119bba4981e34e70b9e67f43280f8071 100644
--- a/src/main/java/net/minecraft/world/level/Level.java --- a/src/main/java/net/minecraft/world/level/Level.java
+++ b/src/main/java/net/minecraft/world/level/Level.java +++ b/src/main/java/net/minecraft/world/level/Level.java
@@ -525,8 +525,13 @@ public abstract class Level implements LevelAccessor, AutoCloseable { @@ -521,8 +521,13 @@ public abstract class Level implements LevelAccessor, AutoCloseable {
this.setBlocksDirty(blockposition, iblockdata1, iblockdata2); this.setBlocksDirty(blockposition, iblockdata1, iblockdata2);
} }
@ -664,30 +575,26 @@ index 5860e7866724abd35bde2a5710d9c92799e5de67..67ab681a9c9157a420de5fd872bde1fc
if ((i & 1) != 0) { if ((i & 1) != 0) {
diff --git a/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java b/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java diff --git a/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java b/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java
index 8a14bdda4a408ec1e2b51efeb35467835f62b42c..dbea2a4370ccf24a5084cdabeecbc81f206e910a 100644 index 521f199e495f3bec232cc9ca36e51e0392afe737..922026da8c234427e0322443004d3c32993adfce 100644
--- a/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java --- a/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java
+++ b/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java +++ b/src/main/java/net/minecraft/world/level/chunk/LevelChunk.java
@@ -27,9 +27,14 @@ import net.minecraft.core.BlockPos; @@ -33,7 +33,10 @@ import net.minecraft.core.Registry;
import net.minecraft.core.Registry; import net.minecraft.core.SectionPos;
import net.minecraft.nbt.CompoundTag; import net.minecraft.nbt.CompoundTag;
import net.minecraft.server.MinecraftServer; import net.minecraft.network.FriendlyByteBuf;
+import net.minecraft.network.protocol.Packet; +import net.minecraft.network.protocol.Packet;
import net.minecraft.server.level.ChunkHolder; import net.minecraft.server.level.ChunkHolder;
+import net.minecraft.server.level.ChunkMap; +import net.minecraft.server.level.ChunkMap;
+import net.minecraft.server.level.ChunkTaskPriorityQueueSorter; +import net.minecraft.server.level.ChunkTaskPriorityQueueSorter;
import net.minecraft.server.level.ServerChunkCache; import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerLevel; import net.minecraft.server.level.ServerLevel;
+import net.minecraft.server.level.ServerPlayer; import net.minecraft.util.profiling.ProfilerFiller;
+import net.minecraft.server.level.TicketType; @@ -227,7 +230,51 @@ public class LevelChunk implements ChunkAccess {
import net.minecraft.util.Mth;
import net.minecraft.world.Container;
import net.minecraft.world.entity.Entity;
@@ -242,7 +247,51 @@ public class LevelChunk implements ChunkAccess {
} }
protected void onNeighbourChange(final long bitsetBefore, final long bitsetAfter) { protected void onNeighbourChange(final long bitsetBefore, final long bitsetAfter) {
+ // Paper start - no-tick view distance + // Paper start - no-tick view distance
+ ServerChunkCache chunkProviderServer = ((ServerLevel)this.world).getChunkSource(); + ServerChunkCache chunkProviderServer = ((ServerLevel)this.level).getChunkSource();
+ ChunkMap chunkMap = chunkProviderServer.chunkMap; + ChunkMap chunkMap = chunkProviderServer.chunkMap;
+ // this code handles the addition of ticking tickets - the distance map handles the removal + // this code handles the addition of ticking tickets - the distance map handles the removal
+ if (!areNeighboursLoaded(bitsetBefore, 2) && areNeighboursLoaded(bitsetAfter, 2)) { + if (!areNeighboursLoaded(bitsetBefore, 2) && areNeighboursLoaded(bitsetAfter, 2)) {
@ -696,7 +603,7 @@ index 8a14bdda4a408ec1e2b51efeb35467835f62b42c..dbea2a4370ccf24a5084cdabeecbc81f
+ chunkProviderServer.mainThreadProcessor.execute(() -> { + chunkProviderServer.mainThreadProcessor.execute(() -> {
+ // double check that this condition still holds. + // double check that this condition still holds.
+ if (LevelChunk.this.areNeighboursLoaded(2) && chunkMap.playerViewDistanceTickMap.getObjectsInRange(LevelChunk.this.coordinateKey) != null) { + if (LevelChunk.this.areNeighboursLoaded(2) && chunkMap.playerViewDistanceTickMap.getObjectsInRange(LevelChunk.this.coordinateKey) != null) {
+ chunkProviderServer.addTicketAtLevel(TicketType.PLAYER, LevelChunk.this.chunkPos, 31, LevelChunk.this.chunkPos); // 31 -> entity ticking, TODO check on update + chunkProviderServer.addTicketAtLevel(net.minecraft.server.level.TicketType.PLAYER, LevelChunk.this.chunkPos, 31, LevelChunk.this.chunkPos); // 31 -> entity ticking, TODO check on update
+ } + }
+ }); + });
+ } + }
@ -711,7 +618,7 @@ index 8a14bdda4a408ec1e2b51efeb35467835f62b42c..dbea2a4370ccf24a5084cdabeecbc81f
+ if (!LevelChunk.this.areNeighboursLoaded(1)) { + if (!LevelChunk.this.areNeighboursLoaded(1)) {
+ return; + return;
+ } + }
+ com.destroystokyo.paper.util.misc.PooledLinkedHashSets.PooledObjectLinkedOpenHashSet<ServerPlayer> inRange = chunkMap.playerViewDistanceBroadcastMap.getObjectsInRange(LevelChunk.this.coordinateKey); + com.destroystokyo.paper.util.misc.PooledLinkedHashSets.PooledObjectLinkedOpenHashSet<net.minecraft.server.level.ServerPlayer> inRange = chunkMap.playerViewDistanceBroadcastMap.getObjectsInRange(LevelChunk.this.coordinateKey);
+ if (inRange == null) { + if (inRange == null) {
+ return; + return;
+ } + }
@ -721,11 +628,11 @@ index 8a14bdda4a408ec1e2b51efeb35467835f62b42c..dbea2a4370ccf24a5084cdabeecbc81f
+ Packet[] chunkPackets = new Packet[2]; + Packet[] chunkPackets = new Packet[2];
+ for (int index = 0, len = backingSet.length; index < len; ++index) { + for (int index = 0, len = backingSet.length; index < len; ++index) {
+ Object temp = backingSet[index]; + Object temp = backingSet[index];
+ if (!(temp instanceof ServerPlayer)) { + if (!(temp instanceof net.minecraft.server.level.ServerPlayer)) {
+ continue; + continue;
+ } + }
+ ServerPlayer player = (ServerPlayer)temp; + net.minecraft.server.level.ServerPlayer player = (net.minecraft.server.level.ServerPlayer)temp;
+ chunkMap.sendChunk(player, chunkPackets, LevelChunk.this); + chunkMap.playerLoadedChunk(player, chunkPackets, LevelChunk.this);
+ } + }
+ }))); + })));
+ } + }
@ -734,28 +641,20 @@ index 8a14bdda4a408ec1e2b51efeb35467835f62b42c..dbea2a4370ccf24a5084cdabeecbc81f
} }
public final boolean isAnyNeighborsLoaded() { public final boolean isAnyNeighborsLoaded() {
@@ -1131,7 +1180,7 @@ public class LevelChunk implements ChunkAccess { @@ -1005,7 +1052,7 @@ public class LevelChunk implements ChunkAccess {
BlockState iblockdata = this.getBlockState(blockposition); BlockState iblockdata = this.getBlockState(blockposition);
BlockState iblockdata1 = Block.updateFromNeighbourShapes(iblockdata, (LevelAccessor) this.world, blockposition); BlockState iblockdata1 = Block.updateFromNeighbourShapes(iblockdata, (LevelAccessor) this.level, blockposition);
- this.world.setBlock(blockposition, iblockdata1, 20); - this.level.setBlock(blockposition, iblockdata1, 20);
+ this.world.setBlock(blockposition, iblockdata1, 20 | 2); // Paper - We send chunks before they're ticking ready, so we need to notify here + this.level.setBlock(blockposition, iblockdata1, 20 | 2); // Paper - We send chunks before they're ticking ready, so we need to notify here
} }
this.postProcessing[i].clear(); this.postProcessing[i].clear();
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
index 1a839242e359fa32f32d0e571c6e918ac39642e9..4fc44390f432ef13c9952aa22bbb29bc8bf47975 100644 index f1cbcdb1e409f8544125dde5f24bff5b07cb5082..1d22119b962840dff789a0619fd2188958f924d0 100644
--- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java --- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
+++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java +++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
@@ -31,6 +31,7 @@ import net.minecraft.network.protocol.game.ClientboundLevelEventPacket; @@ -2540,10 +2540,39 @@ public class CraftWorld implements World {
import net.minecraft.network.protocol.game.ClientboundSetTimePacket;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.server.level.ChunkHolder;
+import net.minecraft.server.level.ChunkMap;
import net.minecraft.server.level.DistanceManager;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.server.level.Ticket;
@@ -2532,10 +2533,39 @@ public class CraftWorld implements World {
// Spigot start // Spigot start
@Override @Override
public int getViewDistance() { public int getViewDistance() {
@ -770,7 +669,7 @@ index 1a839242e359fa32f32d0e571c6e918ac39642e9..4fc44390f432ef13c9952aa22bbb29bc
+ if (viewDistance < 2 || viewDistance > 32) { + if (viewDistance < 2 || viewDistance > 32) {
+ throw new IllegalArgumentException("View distance " + viewDistance + " is out of range of [2, 32]"); + throw new IllegalArgumentException("View distance " + viewDistance + " is out of range of [2, 32]");
+ } + }
+ ChunkMap chunkMap = getHandle().getChunkSource().chunkMap; + net.minecraft.server.level.ChunkMap chunkMap = getHandle().getChunkSource().chunkMap;
+ if (viewDistance != chunkMap.getEffectiveViewDistance()) { + if (viewDistance != chunkMap.getEffectiveViewDistance()) {
+ chunkMap.setViewDistance(viewDistance); + chunkMap.setViewDistance(viewDistance);
+ } + }
@ -786,7 +685,7 @@ index 1a839242e359fa32f32d0e571c6e918ac39642e9..4fc44390f432ef13c9952aa22bbb29bc
+ if ((viewDistance < 2 || viewDistance > 32) && viewDistance != -1) { + if ((viewDistance < 2 || viewDistance > 32) && viewDistance != -1) {
+ throw new IllegalArgumentException("View distance " + viewDistance + " is out of range of [2, 32]"); + throw new IllegalArgumentException("View distance " + viewDistance + " is out of range of [2, 32]");
+ } + }
+ ChunkMap chunkMap = getHandle().getChunkSource().chunkMap; + net.minecraft.server.level.ChunkMap chunkMap = getHandle().getChunkSource().chunkMap;
+ if (viewDistance != chunkMap.getRawNoTickViewDistance()) { + if (viewDistance != chunkMap.getRawNoTickViewDistance()) {
+ chunkMap.setNoTickViewDistance(viewDistance); + chunkMap.setNoTickViewDistance(viewDistance);
+ } + }
@ -797,23 +696,15 @@ index 1a839242e359fa32f32d0e571c6e918ac39642e9..4fc44390f432ef13c9952aa22bbb29bc
private final org.bukkit.World.Spigot spigot = new org.bukkit.World.Spigot() private final org.bukkit.World.Spigot spigot = new org.bukkit.World.Spigot()
{ {
diff --git a/src/main/java/org/spigotmc/ActivationRange.java b/src/main/java/org/spigotmc/ActivationRange.java diff --git a/src/main/java/org/spigotmc/ActivationRange.java b/src/main/java/org/spigotmc/ActivationRange.java
index 8cbafad53d20366a36493f22160c4fa3e4ac3eaf..20d5da61fc0594e86c68ea8fb5ebe5517f27f126 100644 index 2ab585a018290996e7fa9ca6f3ad7d734cd7beaa..a08583863f9fa08016bdfc7949a273eaa4429927 100644
--- a/src/main/java/org/spigotmc/ActivationRange.java --- a/src/main/java/org/spigotmc/ActivationRange.java
+++ b/src/main/java/org/spigotmc/ActivationRange.java +++ b/src/main/java/org/spigotmc/ActivationRange.java
@@ -4,6 +4,7 @@ import java.util.Collection; @@ -188,7 +188,7 @@ public class ActivationRange
import net.minecraft.core.BlockPos;
import net.minecraft.server.MinecraftServer;
import net.minecraft.server.level.ServerChunkCache;
+import net.minecraft.server.level.ServerLevel;
import net.minecraft.util.Mth;
import net.minecraft.world.entity.Entity;
import net.minecraft.world.entity.FlyingMob;
@@ -192,7 +193,7 @@ public class ActivationRange
maxRange = Math.max( maxRange, waterActivationRange ); maxRange = Math.max( maxRange, waterActivationRange );
maxRange = Math.max( maxRange, villagerActivationRange ); maxRange = Math.max( maxRange, villagerActivationRange );
// Paper end // Paper end
- maxRange = Math.min( ( world.spigotConfig.viewDistance << 4 ) - 8, maxRange ); - maxRange = Math.min( ( world.spigotConfig.viewDistance << 4 ) - 8, maxRange );
+ maxRange = Math.min( ( ((ServerLevel)world).getChunkSource().chunkMap.getEffectiveViewDistance() << 4 ) - 8, maxRange ); // Paper - no-tick view distance + maxRange = Math.min( ( ((net.minecraft.server.level.ServerLevel)world).getChunkSource().chunkMap.getEffectiveViewDistance() << 4 ) - 8, maxRange ); // Paper - no-tick view distance
for ( Player player : world.players() ) for ( Player player : world.players() )
{ {