mirror of
https://github.com/PaperMC/Paper.git
synced 2024-12-28 23:38:25 +01:00
302 lines
15 KiB
Diff
302 lines
15 KiB
Diff
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
|
From: Aikar <aikar@aikar.co>
|
|
Date: Fri, 13 May 2016 01:38:06 -0400
|
|
Subject: [PATCH] Entity Activation Range 2.0
|
|
|
|
Optimizes performance of Activation Range
|
|
|
|
Adds many new configurations and a new wake up inactive system
|
|
|
|
Fixes and adds new Immunities to improve gameplay behavior
|
|
|
|
Adds water Mobs to activation range config and nerfs fish
|
|
Adds flying monsters to control ghast and phantoms
|
|
Adds villagers as separate config
|
|
|
|
|
|
diff --git a/net/minecraft/server/level/ServerLevel.java b/net/minecraft/server/level/ServerLevel.java
|
|
index 1d7e9492a474c99dff372d6b57f1f195e42d5114..aa5eed48871b5ab67d18213e532271241aae9182 100644
|
|
--- a/net/minecraft/server/level/ServerLevel.java
|
|
+++ b/net/minecraft/server/level/ServerLevel.java
|
|
@@ -963,10 +963,10 @@ public class ServerLevel extends Level implements ServerEntityGetter, WorldGenLe
|
|
profilerFiller.incrementCounter("tickNonPassenger");
|
|
// Spigot start
|
|
final boolean isActive = org.spigotmc.ActivationRange.checkIfActive(entity); // Paper - EAR 2
|
|
- if (isActive) {
|
|
+ if (isActive) { // Paper - EAR 2
|
|
entity.tick();
|
|
entity.postTick(); // CraftBukkit
|
|
- } else {entity.inactiveTick();} // Spigot end
|
|
+ } else {entity.inactiveTick();} // Paper - EAR 2
|
|
profilerFiller.pop();
|
|
|
|
for (Entity entity1 : entity.getPassengers()) {
|
|
diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java
|
|
index 0aed1e455dec32c3d53d8fb2f1047e1bf177f171..8c2441a6c7abc3a80426923c1ea42000283ee167 100644
|
|
--- a/net/minecraft/world/entity/Entity.java
|
|
+++ b/net/minecraft/world/entity/Entity.java
|
|
@@ -383,6 +383,8 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
|
|
// Spigot end
|
|
protected int numCollisions = 0; // Paper - Cap entity collisions
|
|
public boolean fromNetherPortal; // Paper - Add option to nerf pigmen from nether portals
|
|
+ public long activatedImmunityTick = Integer.MIN_VALUE; // Paper - EAR
|
|
+ public boolean isTemporarilyActive; // Paper - EAR
|
|
public boolean spawnedViaMobSpawner; // Paper - Yes this name is similar to above, upstream took the better one
|
|
// Paper start - Entity origin API
|
|
@javax.annotation.Nullable
|
|
@@ -959,6 +961,8 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
|
|
} else {
|
|
this.wasOnFire = this.isOnFire();
|
|
if (type == MoverType.PISTON) {
|
|
+ this.activatedTick = Math.max(this.activatedTick, MinecraftServer.currentTick + 20); // Paper - EAR 2
|
|
+ this.activatedImmunityTick = Math.max(this.activatedImmunityTick, MinecraftServer.currentTick + 20); // Paper - EAR 2
|
|
movement = this.limitPistonMovement(movement);
|
|
if (movement.equals(Vec3.ZERO)) {
|
|
return;
|
|
@@ -972,6 +976,13 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess
|
|
this.stuckSpeedMultiplier = Vec3.ZERO;
|
|
this.setDeltaMovement(Vec3.ZERO);
|
|
}
|
|
+ // Paper start - ignore movement changes while inactive.
|
|
+ if (isTemporarilyActive && !(this instanceof ItemEntity) && movement == getDeltaMovement() && type == MoverType.SELF) {
|
|
+ setDeltaMovement(Vec3.ZERO);
|
|
+ gameprofilerfiller.pop();
|
|
+ return;
|
|
+ }
|
|
+ // Paper end
|
|
|
|
movement = this.maybeBackOffFromEdge(movement, type);
|
|
Vec3 vec3 = this.collide(movement);
|
|
diff --git a/net/minecraft/world/entity/Mob.java b/net/minecraft/world/entity/Mob.java
|
|
index f7d69db61d1293510428ae275e8a50571dde5ddf..1ed07fd23985a6bf8cf8300f74c92b7531a79fc6 100644
|
|
--- a/net/minecraft/world/entity/Mob.java
|
|
+++ b/net/minecraft/world/entity/Mob.java
|
|
@@ -215,6 +215,19 @@ public abstract class Mob extends LivingEntity implements EquipmentUser, Leashab
|
|
return this.lookControl;
|
|
}
|
|
|
|
+ // Paper start
|
|
+ @Override
|
|
+ public void inactiveTick() {
|
|
+ super.inactiveTick();
|
|
+ if (this.goalSelector.inactiveTick()) {
|
|
+ this.goalSelector.tick();
|
|
+ }
|
|
+ if (this.targetSelector.inactiveTick()) {
|
|
+ this.targetSelector.tick();
|
|
+ }
|
|
+ }
|
|
+ // Paper end
|
|
+
|
|
public MoveControl getMoveControl() {
|
|
return this.getControlledVehicle() instanceof Mob mob ? mob.getMoveControl() : this.moveControl;
|
|
}
|
|
diff --git a/net/minecraft/world/entity/PathfinderMob.java b/net/minecraft/world/entity/PathfinderMob.java
|
|
index 0caf50ec50f056b83a20bbc6a2fe0144593aef39..af59a700755654eb68d6bf57d0712c4a2ac6c09b 100644
|
|
--- a/net/minecraft/world/entity/PathfinderMob.java
|
|
+++ b/net/minecraft/world/entity/PathfinderMob.java
|
|
@@ -17,6 +17,8 @@ public abstract class PathfinderMob extends Mob {
|
|
super(entityType, level);
|
|
}
|
|
|
|
+ public BlockPos movingTarget; public BlockPos getMovingTarget() { return movingTarget; } // Paper
|
|
+
|
|
public float getWalkTargetValue(BlockPos pos) {
|
|
return this.getWalkTargetValue(pos, this.level());
|
|
}
|
|
diff --git a/net/minecraft/world/entity/ai/goal/GoalSelector.java b/net/minecraft/world/entity/ai/goal/GoalSelector.java
|
|
index 88e7e245824b670652878e03a2142a13e97508fe..2730e76228b03b1ec52108f394c20fe003801b02 100644
|
|
--- a/net/minecraft/world/entity/ai/goal/GoalSelector.java
|
|
+++ b/net/minecraft/world/entity/ai/goal/GoalSelector.java
|
|
@@ -22,12 +22,12 @@ public class GoalSelector {
|
|
return false;
|
|
}
|
|
};
|
|
+ private int curRate; // Paper - EAR 2
|
|
private final Map<Goal.Flag, WrappedGoal> lockedFlags = new EnumMap<>(Goal.Flag.class);
|
|
private final Set<WrappedGoal> availableGoals = new ObjectLinkedOpenHashSet<>();
|
|
private static final Goal.Flag[] GOAL_FLAG_VALUES = Goal.Flag.values(); // Paper - remove streams from pathfindergoalselector
|
|
private final ca.spottedleaf.moonrise.common.set.OptimizedSmallEnumSet<net.minecraft.world.entity.ai.goal.Goal.Flag> goalTypes = new ca.spottedleaf.moonrise.common.set.OptimizedSmallEnumSet<>(Goal.Flag.class); // Paper - remove streams from pathfindergoalselector
|
|
|
|
-
|
|
public void addGoal(int priority, Goal goal) {
|
|
this.availableGoals.add(new WrappedGoal(priority, goal));
|
|
}
|
|
@@ -37,6 +37,22 @@ public class GoalSelector {
|
|
this.availableGoals.removeIf(wrappedGoal -> filter.test(wrappedGoal.getGoal()));
|
|
}
|
|
|
|
+ // Paper start - EAR 2
|
|
+ public boolean inactiveTick() {
|
|
+ this.curRate++;
|
|
+ return this.curRate % 3 == 0; // TODO newGoalRate was already unused in 1.20.4, check if this is correct
|
|
+ }
|
|
+
|
|
+ public boolean hasTasks() {
|
|
+ for (WrappedGoal task : this.availableGoals) {
|
|
+ if (task.isRunning()) {
|
|
+ return true;
|
|
+ }
|
|
+ }
|
|
+ return false;
|
|
+ }
|
|
+ // Paper end - EAR 2
|
|
+
|
|
public void removeGoal(Goal goal) {
|
|
for (WrappedGoal wrappedGoal : this.availableGoals) {
|
|
if (wrappedGoal.getGoal() == goal && wrappedGoal.isRunning()) {
|
|
diff --git a/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java b/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
|
|
index 789fea258d70e60d38271ebb31270562dc7eb3ab..d0ab3db7bbd2942db19f473474371b20ce822608 100644
|
|
--- a/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
|
|
+++ b/net/minecraft/world/entity/ai/goal/MoveToBlockGoal.java
|
|
@@ -23,6 +23,14 @@ public abstract class MoveToBlockGoal extends Goal {
|
|
public MoveToBlockGoal(PathfinderMob mob, double speedModifier, int searchRange) {
|
|
this(mob, speedModifier, searchRange, 1);
|
|
}
|
|
+ // Paper start - activation range improvements
|
|
+ @Override
|
|
+ public void stop() {
|
|
+ super.stop();
|
|
+ this.blockPos = BlockPos.ZERO;
|
|
+ this.mob.movingTarget = null;
|
|
+ }
|
|
+ // Paper end
|
|
|
|
public MoveToBlockGoal(PathfinderMob mob, double speedModifier, int searchRange, int verticalSearchRange) {
|
|
this.mob = mob;
|
|
@@ -113,6 +121,7 @@ public abstract class MoveToBlockGoal extends Goal {
|
|
mutableBlockPos.setWithOffset(blockPos, i4, i2 - 1, i5);
|
|
if (this.mob.isWithinRestriction(mutableBlockPos) && this.isValidTarget(this.mob.level(), mutableBlockPos)) {
|
|
this.blockPos = mutableBlockPos;
|
|
+ this.mob.movingTarget = mutableBlockPos == BlockPos.ZERO ? null : mutableBlockPos.immutable(); // Paper
|
|
return true;
|
|
}
|
|
}
|
|
diff --git a/net/minecraft/world/entity/npc/Villager.java b/net/minecraft/world/entity/npc/Villager.java
|
|
index 81a6d31d90dc139e4d99c2b8e609032e8b100b2d..0b73ad491eb6992e1d8fdd7e75264c9ce712a462 100644
|
|
--- a/net/minecraft/world/entity/npc/Villager.java
|
|
+++ b/net/minecraft/world/entity/npc/Villager.java
|
|
@@ -269,18 +269,33 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
|
|
@Override
|
|
public void inactiveTick() {
|
|
// SPIGOT-3874, SPIGOT-3894, SPIGOT-3846, SPIGOT-5286 :(
|
|
- if (this.level().spigotConfig.tickInactiveVillagers && this.isEffectiveAi()) {
|
|
- this.customServerAiStep((ServerLevel) this.level());
|
|
+ // Paper start
|
|
+ if (this.getUnhappyCounter() > 0) {
|
|
+ this.setUnhappyCounter(this.getUnhappyCounter() - 1);
|
|
}
|
|
+ if (this.isEffectiveAi()) {
|
|
+ if (this.level().spigotConfig.tickInactiveVillagers) {
|
|
+ this.customServerAiStep(this.level().getMinecraftWorld());
|
|
+ } else {
|
|
+ this.customServerAiStep(this.level().getMinecraftWorld(), true);
|
|
+ }
|
|
+ }
|
|
+ maybeDecayGossip();
|
|
+ // Paper end
|
|
super.inactiveTick();
|
|
}
|
|
// Spigot End
|
|
|
|
@Override
|
|
protected void customServerAiStep(ServerLevel level) {
|
|
+ // Paper start - EAR 2
|
|
+ this.customServerAiStep(level, false);
|
|
+ }
|
|
+ protected void customServerAiStep(ServerLevel level, final boolean inactive) {
|
|
+ // Paper end - EAR 2
|
|
ProfilerFiller profilerFiller = Profiler.get();
|
|
profilerFiller.push("villagerBrain");
|
|
- this.getBrain().tick(level, this);
|
|
+ if (!inactive) this.getBrain().tick(level, this); // Paper - EAR 2
|
|
profilerFiller.pop();
|
|
if (this.assignProfessionWhenSpawned) {
|
|
this.assignProfessionWhenSpawned = false;
|
|
@@ -304,7 +319,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
|
|
this.lastTradedPlayer = null;
|
|
}
|
|
|
|
- if (!this.isNoAi() && this.random.nextInt(100) == 0) {
|
|
+ if (!inactive && !this.isNoAi() && this.random.nextInt(100) == 0) { // Paper - EAR 2
|
|
Raid raidAt = level.getRaidAt(this.blockPosition());
|
|
if (raidAt != null && raidAt.isActive() && !raidAt.isOver()) {
|
|
level.broadcastEntityEvent(this, (byte)42);
|
|
@@ -314,6 +329,7 @@ public class Villager extends AbstractVillager implements ReputationEventHandler
|
|
if (this.getVillagerData().getProfession() == VillagerProfession.NONE && this.isTrading()) {
|
|
this.stopTrading();
|
|
}
|
|
+ if (inactive) return; // Paper - EAR 2
|
|
|
|
super.customServerAiStep(level);
|
|
}
|
|
diff --git a/net/minecraft/world/entity/vehicle/MinecartHopper.java b/net/minecraft/world/entity/vehicle/MinecartHopper.java
|
|
index c553cf0592dfa606dbbb1e6854d3377b9feb5efb..dec705ec57e4f63ef2ccaa87c5400c116aee9b35 100644
|
|
--- a/net/minecraft/world/entity/vehicle/MinecartHopper.java
|
|
+++ b/net/minecraft/world/entity/vehicle/MinecartHopper.java
|
|
@@ -47,6 +47,7 @@ public class MinecartHopper extends AbstractMinecartContainer implements Hopper
|
|
if (flag != this.isEnabled()) {
|
|
this.setEnabled(flag);
|
|
}
|
|
+ this.immunize(); // Paper
|
|
}
|
|
|
|
public boolean isEnabled() {
|
|
@@ -100,11 +101,13 @@ public class MinecartHopper extends AbstractMinecartContainer implements Hopper
|
|
|
|
public boolean suckInItems() {
|
|
if (HopperBlockEntity.suckInItems(this.level(), this)) {
|
|
+ this.immunize(); // Paper
|
|
return true;
|
|
} else {
|
|
for (ItemEntity itemEntity : this.level()
|
|
.getEntitiesOfClass(ItemEntity.class, this.getBoundingBox().inflate(0.25, 0.0, 0.25), EntitySelector.ENTITY_STILL_ALIVE)) {
|
|
if (HopperBlockEntity.addItem(this, itemEntity)) {
|
|
+ this.immunize(); // Paper
|
|
return true;
|
|
}
|
|
}
|
|
@@ -139,4 +142,11 @@ public class MinecartHopper extends AbstractMinecartContainer implements Hopper
|
|
public AbstractContainerMenu createMenu(int id, Inventory playerInventory) {
|
|
return new HopperMenu(id, playerInventory, this);
|
|
}
|
|
+
|
|
+ // Paper start
|
|
+ public void immunize() {
|
|
+ this.activatedImmunityTick = Math.max(this.activatedImmunityTick, net.minecraft.server.MinecraftServer.currentTick + 20);
|
|
+ }
|
|
+ // Paper end
|
|
+
|
|
}
|
|
diff --git a/net/minecraft/world/level/Level.java b/net/minecraft/world/level/Level.java
|
|
index e0239091729f6be138c037951fd5c138497ee358..051a86e8a723aeb86ffa06e3cd5fab102a808cde 100644
|
|
--- a/net/minecraft/world/level/Level.java
|
|
+++ b/net/minecraft/world/level/Level.java
|
|
@@ -153,6 +153,12 @@ public abstract class Level implements LevelAccessor, AutoCloseable {
|
|
public Map<BlockPos, BlockEntity> capturedTileEntities = new java.util.LinkedHashMap<>(); // Paper - Retain block place order when capturing blockstates
|
|
public List<net.minecraft.world.entity.item.ItemEntity> captureDrops;
|
|
public final it.unimi.dsi.fastutil.objects.Object2LongOpenHashMap<SpawnCategory> ticksPerSpawnCategory = new it.unimi.dsi.fastutil.objects.Object2LongOpenHashMap<>();
|
|
+ // Paper start
|
|
+ public int wakeupInactiveRemainingAnimals;
|
|
+ public int wakeupInactiveRemainingFlying;
|
|
+ public int wakeupInactiveRemainingMonsters;
|
|
+ public int wakeupInactiveRemainingVillagers;
|
|
+ // Paper end
|
|
public boolean populating;
|
|
public final org.spigotmc.SpigotWorldConfig spigotConfig; // Spigot
|
|
// Paper start - add paper world config
|
|
diff --git a/net/minecraft/world/level/block/piston/PistonMovingBlockEntity.java b/net/minecraft/world/level/block/piston/PistonMovingBlockEntity.java
|
|
index 754cfdcd5a28287aa3545aaffdce1e391cbefc1e..1e6e940fca9d96ef410c7bf05524bd9b24db4a79 100644
|
|
--- a/net/minecraft/world/level/block/piston/PistonMovingBlockEntity.java
|
|
+++ b/net/minecraft/world/level/block/piston/PistonMovingBlockEntity.java
|
|
@@ -149,6 +149,10 @@ public class PistonMovingBlockEntity extends BlockEntity {
|
|
}
|
|
|
|
entity.setDeltaMovement(d1, d2, d3);
|
|
+ // Paper - EAR items stuck in slime pushed by a piston
|
|
+ entity.activatedTick = Math.max(entity.activatedTick, net.minecraft.server.MinecraftServer.currentTick + 10);
|
|
+ entity.activatedImmunityTick = Math.max(entity.activatedImmunityTick, net.minecraft.server.MinecraftServer.currentTick + 10);
|
|
+ // Paper end
|
|
break;
|
|
}
|
|
}
|