mirror of
https://github.com/BentoBoxWorld/Limits.git
synced 2025-02-18 05:11:30 +01:00
WIP try to use EntityBreedEvent to track breeding
This commit is contained in:
parent
328a1a13f7
commit
14c38869df
2
pom.xml
2
pom.xml
@ -57,7 +57,7 @@
|
|||||||
<!-- Non-minecraft related dependencies -->
|
<!-- Non-minecraft related dependencies -->
|
||||||
<powermock.version>2.0.9</powermock.version>
|
<powermock.version>2.0.9</powermock.version>
|
||||||
<!-- More visible way how to change dependency versions -->
|
<!-- More visible way how to change dependency versions -->
|
||||||
<spigot.version>1.17.1-R0.1-SNAPSHOT</spigot.version>
|
<spigot.version>1.16.1-R0.1-SNAPSHOT</spigot.version>
|
||||||
<bentobox.version>1.18.0-SNAPSHOT</bentobox.version>
|
<bentobox.version>1.18.0-SNAPSHOT</bentobox.version>
|
||||||
<!-- Revision variable removes warning about dynamic version -->
|
<!-- Revision variable removes warning about dynamic version -->
|
||||||
<revision>${build.version}-SNAPSHOT</revision>
|
<revision>${build.version}-SNAPSHOT</revision>
|
||||||
|
@ -27,6 +27,7 @@ import org.bukkit.event.EventPriority;
|
|||||||
import org.bukkit.event.Listener;
|
import org.bukkit.event.Listener;
|
||||||
import org.bukkit.event.entity.CreatureSpawnEvent;
|
import org.bukkit.event.entity.CreatureSpawnEvent;
|
||||||
import org.bukkit.event.entity.CreatureSpawnEvent.SpawnReason;
|
import org.bukkit.event.entity.CreatureSpawnEvent.SpawnReason;
|
||||||
|
import org.bukkit.event.entity.EntityBreedEvent;
|
||||||
import org.bukkit.event.hanging.HangingPlaceEvent;
|
import org.bukkit.event.hanging.HangingPlaceEvent;
|
||||||
import org.bukkit.event.vehicle.VehicleCreateEvent;
|
import org.bukkit.event.vehicle.VehicleCreateEvent;
|
||||||
|
|
||||||
@ -43,17 +44,7 @@ public class EntityLimitListener implements Listener {
|
|||||||
private static final String MOD_BYPASS = "mod.bypass";
|
private static final String MOD_BYPASS = "mod.bypass";
|
||||||
private final Limits addon;
|
private final Limits addon;
|
||||||
private final List<UUID> justSpawned = new ArrayList<>();
|
private final List<UUID> justSpawned = new ArrayList<>();
|
||||||
private static final List<BlockFace> CARDINALS;
|
private static final List<BlockFace> CARDINALS = List.of(BlockFace.UP, BlockFace.NORTH, BlockFace.SOUTH, BlockFace.EAST, BlockFace.WEST, BlockFace.DOWN);
|
||||||
static {
|
|
||||||
List<BlockFace> cardinals = new ArrayList<>();
|
|
||||||
cardinals.add(BlockFace.UP);
|
|
||||||
cardinals.add(BlockFace.NORTH);
|
|
||||||
cardinals.add(BlockFace.SOUTH);
|
|
||||||
cardinals.add(BlockFace.EAST);
|
|
||||||
cardinals.add(BlockFace.WEST);
|
|
||||||
cardinals.add(BlockFace.DOWN);
|
|
||||||
CARDINALS = Collections.unmodifiableList(cardinals);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Handles entity and natural limitations
|
* Handles entity and natural limitations
|
||||||
@ -71,46 +62,34 @@ public class EntityLimitListener implements Listener {
|
|||||||
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
|
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
|
||||||
public void onMinecart(VehicleCreateEvent e) {
|
public void onMinecart(VehicleCreateEvent e) {
|
||||||
// Return if not in a known world
|
// Return if not in a known world
|
||||||
|
|
||||||
if (!addon.inGameModeWorld(e.getVehicle().getWorld())) {
|
if (!addon.inGameModeWorld(e.getVehicle().getWorld())) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
// Debounce
|
||||||
if (justSpawned.contains(e.getVehicle().getUniqueId())) {
|
if (justSpawned.contains(e.getVehicle().getUniqueId())) {
|
||||||
justSpawned.remove(e.getVehicle().getUniqueId());
|
justSpawned.remove(e.getVehicle().getUniqueId());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// If someone in that area has the bypass permission, allow the spawning
|
|
||||||
for (Entity entity : Objects.requireNonNull(e.getVehicle().getLocation().getWorld()).getNearbyEntities(e.getVehicle().getLocation(), 5, 5, 5)) {
|
|
||||||
if (entity instanceof Player) {
|
|
||||||
Player player = (Player)entity;
|
|
||||||
boolean bypass = (player.isOp() || player.hasPermission(addon.getPlugin().getIWM().getPermissionPrefix(e.getVehicle().getWorld()) + MOD_BYPASS));
|
|
||||||
// Check island
|
// Check island
|
||||||
addon.getIslands().getProtectedIslandAt(e.getVehicle().getLocation()).ifPresent(island -> {
|
addon.getIslands().getProtectedIslandAt(e.getVehicle().getLocation())
|
||||||
// Ignore spawn
|
// Ignore spawn
|
||||||
if (island.isSpawn()) {
|
.filter(i -> !i.isSpawn())
|
||||||
return;
|
.ifPresent(island -> {
|
||||||
}
|
|
||||||
// Check if the player is at the limit
|
// Check if the player is at the limit
|
||||||
AtLimitResult res;
|
AtLimitResult res = atLimit(island, e.getVehicle());
|
||||||
if (!bypass && (res = atLimit(island, e.getVehicle())).hit()) {
|
if (res.hit()) {
|
||||||
e.setCancelled(true);
|
e.setCancelled(true);
|
||||||
for (Entity ent : e.getVehicle().getLocation().getWorld().getNearbyEntities(e.getVehicle().getLocation(), 5, 5, 5)) {
|
this.tellPlayers(e.getVehicle().getLocation(), e.getVehicle(), SpawnReason.MOUNT, res);
|
||||||
if (ent instanceof Player) {
|
|
||||||
((Player) ent).updateInventory();
|
|
||||||
if (res.getTypelimit() != null) {
|
|
||||||
User.getInstance(ent).notify("entity-limits.hit-limit", "[entity]",
|
|
||||||
Util.prettifyText(e.getVehicle().getType().toString()),
|
|
||||||
TextVariables.NUMBER, String.valueOf(res.getTypelimit().getValue()));
|
|
||||||
} else {
|
|
||||||
User.getInstance(ent).notify("entity-limits.hit-limit", "[entity]",
|
|
||||||
res.getGrouplimit().getKey().getName() + " (" + res.getGrouplimit().getKey().getTypes().stream().map(x -> Util.prettifyText(x.toString())).collect(Collectors.joining(", ")) + ")",
|
|
||||||
TextVariables.NUMBER, String.valueOf(res.getGrouplimit().getValue()));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@EventHandler(priority = EventPriority.LOW, ignoreCancelled = true)
|
||||||
|
public void onBreed(final EntityBreedEvent e) {
|
||||||
|
if (e.getBreeder() != null && e.getBreeder() instanceof Player p &&
|
||||||
|
!(p.isOp() || p.hasPermission(addon.getPlugin().getIWM().getPermissionPrefix(e.getEntity().getWorld()) + MOD_BYPASS))) {
|
||||||
|
checkLimit(e, e.getEntity(), SpawnReason.BREEDING, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -124,53 +103,20 @@ public class EntityLimitListener implements Listener {
|
|||||||
justSpawned.remove(e.getEntity().getUniqueId());
|
justSpawned.remove(e.getEntity().getUniqueId());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
boolean bypass = false;
|
if (e.getSpawnReason().equals(SpawnReason.SHOULDER_ENTITY)) {
|
||||||
// Check why it was spawned
|
|
||||||
switch (e.getSpawnReason()) {
|
|
||||||
// These reasons are due to a player being involved (usually) so there may be a bypass
|
|
||||||
case BREEDING:
|
|
||||||
case BUILD_IRONGOLEM:
|
|
||||||
case BUILD_SNOWMAN:
|
|
||||||
case BUILD_WITHER:
|
|
||||||
case CURED:
|
|
||||||
case EGG:
|
|
||||||
case SPAWNER_EGG:
|
|
||||||
bypass = checkByPass(e.getLocation());
|
|
||||||
break;
|
|
||||||
case SHOULDER_ENTITY:
|
|
||||||
// Special case - do nothing - jumping around spawns parrots as they drop off player's shoulder
|
// Special case - do nothing - jumping around spawns parrots as they drop off player's shoulder
|
||||||
return;
|
return;
|
||||||
default:
|
|
||||||
// Other natural reasons
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
// Some checks can be done async, some not
|
// Some checks can be done async, some not
|
||||||
switch (e.getSpawnReason()) {
|
if (e.getSpawnReason().equals(SpawnReason.BUILD_SNOWMAN) || e.getSpawnReason().equals(SpawnReason.BUILD_IRONGOLEM)) {
|
||||||
case BUILD_SNOWMAN:
|
checkLimit(e, e.getEntity(), e.getSpawnReason(), addon.getSettings().isAsyncGolums());
|
||||||
case BUILD_IRONGOLEM:
|
} else {
|
||||||
checkLimit(e, e.getEntity(), e.getSpawnReason(), bypass, addon.getSettings().isAsyncGolums());
|
|
||||||
default:
|
|
||||||
// Check limit sync
|
// Check limit sync
|
||||||
checkLimit(e, e.getEntity(), e.getSpawnReason(), bypass, false);
|
checkLimit(e, e.getEntity(), e.getSpawnReason(), false);
|
||||||
break;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean checkByPass(Location l) {
|
|
||||||
// If someone in that area has the bypass permission, allow the spawning
|
|
||||||
for (Entity entity : Objects.requireNonNull(l.getWorld()).getNearbyEntities(l, 5, 5, 5)) {
|
|
||||||
if (entity instanceof Player) {
|
|
||||||
Player player = (Player)entity;
|
|
||||||
if (player.isOp() || player.hasPermission(addon.getPlugin().getIWM().getPermissionPrefix(l.getWorld()) + MOD_BYPASS)) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* handles paintings and item frames
|
* handles paintings and item frames
|
||||||
* @param e - event
|
* @param e - event
|
||||||
@ -205,22 +151,22 @@ public class EntityLimitListener implements Listener {
|
|||||||
/**
|
/**
|
||||||
* Check if a creature is allowed to spawn or not
|
* Check if a creature is allowed to spawn or not
|
||||||
* @param e - CreatureSpawnEvent
|
* @param e - CreatureSpawnEvent
|
||||||
* @param bypass - true if the player involved can bypass the checks
|
|
||||||
* @param async - true if check can be done async, false if not
|
* @param async - true if check can be done async, false if not
|
||||||
*/
|
*/
|
||||||
private void checkLimit(Cancellable c, LivingEntity e, SpawnReason reason, boolean bypass, boolean async) {
|
private void checkLimit(Cancellable c, LivingEntity e, SpawnReason reason, boolean async) {
|
||||||
|
BentoBox.getInstance().logDebug("Event = " + c.toString() + " " + e + " " + reason + " ");
|
||||||
Location l = e.getLocation();
|
Location l = e.getLocation();
|
||||||
if (async) {
|
if (async) {
|
||||||
c.setCancelled(true);
|
c.setCancelled(true);
|
||||||
}
|
}
|
||||||
processIsland(c, e, l, reason, bypass, async);
|
processIsland(c, e, l, reason, async);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void processIsland(Cancellable c, LivingEntity e, Location l, SpawnReason reason, boolean bypass, boolean async) {
|
private void processIsland(Cancellable c, LivingEntity e, Location l, SpawnReason reason, boolean async) {
|
||||||
addon.getIslands().getIslandAt(e.getLocation()).ifPresent(island -> {
|
addon.getIslands().getIslandAt(e.getLocation()).ifPresent(island -> {
|
||||||
// Check if creature is allowed to spawn or not
|
// Check if creature is allowed to spawn or not
|
||||||
AtLimitResult res = atLimit(island, e);
|
AtLimitResult res = atLimit(island, e);
|
||||||
if (bypass || island.isSpawn() || !res.hit()) {
|
if (island.isSpawn() || !res.hit()) {
|
||||||
// Allowed
|
// Allowed
|
||||||
if (async) {
|
if (async) {
|
||||||
Bukkit.getScheduler().runTask(BentoBox.getInstance(), () -> {
|
Bukkit.getScheduler().runTask(BentoBox.getInstance(), () -> {
|
||||||
@ -234,7 +180,7 @@ public class EntityLimitListener implements Listener {
|
|||||||
c.setCancelled(true);
|
c.setCancelled(true);
|
||||||
}
|
}
|
||||||
// If the reason is anything but because of a spawner then tell players within range
|
// If the reason is anything but because of a spawner then tell players within range
|
||||||
tellPlayers(c, l, e, reason, res);
|
tellPlayers(l, e, reason, res);
|
||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
@ -378,28 +324,37 @@ public class EntityLimitListener implements Listener {
|
|||||||
return Tag.WITHER_SUMMON_BASE_BLOCKS.isTagged(body.getType());
|
return Tag.WITHER_SUMMON_BASE_BLOCKS.isTagged(body.getType());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void tellPlayers(Cancellable e, Location l, LivingEntity entity, SpawnReason reason, AtLimitResult res) {
|
/**
|
||||||
if (!reason.equals(SpawnReason.SPAWNER) && !reason.equals(SpawnReason.NATURAL)
|
* Tell players within a 5 x 5 x 5 radius that the spawning was denied. Informing happens 1 tick after event
|
||||||
&& !reason.equals(SpawnReason.INFECTION) && !reason.equals(SpawnReason.NETHER_PORTAL)
|
* @param l location
|
||||||
&& !reason.equals(SpawnReason.REINFORCEMENTS) && !reason.equals(SpawnReason.SLIME_SPLIT)) {
|
* @param entity entity spawned
|
||||||
|
* @param reason reason - some reasons are not reported
|
||||||
|
* @param res at limit result
|
||||||
|
*/
|
||||||
|
private void tellPlayers(Location l, Entity entity, SpawnReason reason, AtLimitResult res) {
|
||||||
|
if (reason.equals(SpawnReason.SPAWNER) || reason.equals(SpawnReason.NATURAL)
|
||||||
|
|| reason.equals(SpawnReason.INFECTION) || reason.equals(SpawnReason.NETHER_PORTAL)
|
||||||
|
|| reason.equals(SpawnReason.REINFORCEMENTS) || reason.equals(SpawnReason.SLIME_SPLIT)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
World w = l.getWorld();
|
World w = l.getWorld();
|
||||||
if (w == null) return;
|
if (w == null) return;
|
||||||
Bukkit.getScheduler().runTask(addon.getPlugin(), () -> {
|
Bukkit.getScheduler().runTask(addon.getPlugin(), () -> {
|
||||||
for (Entity ent : w.getNearbyEntities(l, 5, 5, 5)) {
|
for (Entity ent : w.getNearbyEntities(l, 5, 5, 5)) {
|
||||||
if (ent instanceof Player) {
|
if (ent instanceof Player p) {
|
||||||
|
p.updateInventory();
|
||||||
if (res.getTypelimit() != null) {
|
if (res.getTypelimit() != null) {
|
||||||
User.getInstance(ent).notify("entity-limits.hit-limit", "[entity]",
|
User.getInstance(p).notify("entity-limits.hit-limit", "[entity]",
|
||||||
Util.prettifyText(entity.getType().toString()),
|
Util.prettifyText(entity.getType().toString()),
|
||||||
TextVariables.NUMBER, String.valueOf(res.getTypelimit().getValue()));
|
TextVariables.NUMBER, String.valueOf(res.getTypelimit().getValue()));
|
||||||
} else {
|
} else {
|
||||||
User.getInstance(ent).notify("entity-limits.hit-limit", "[entity]",
|
User.getInstance(p).notify("entity-limits.hit-limit", "[entity]",
|
||||||
res.getGrouplimit().getKey().getName() + " (" + res.getGrouplimit().getKey().getTypes().stream().map(x -> Util.prettifyText(x.toString())).collect(Collectors.joining(", ")) + ")",
|
res.getGrouplimit().getKey().getName() + " (" + res.getGrouplimit().getKey().getTypes().stream().map(x -> Util.prettifyText(x.toString())).collect(Collectors.joining(", ")) + ")",
|
||||||
TextVariables.NUMBER, String.valueOf(res.getGrouplimit().getValue()));
|
TextVariables.NUMBER, String.valueOf(res.getGrouplimit().getValue()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
name: Limits
|
name: Limits
|
||||||
main: world.bentobox.limits.Limits
|
main: world.bentobox.limits.Limits
|
||||||
version: ${version}${build.number}
|
version: ${version}${build.number}
|
||||||
api-version: 1.18
|
api-version: 1.16.5
|
||||||
|
|
||||||
authors: tastybento
|
authors: tastybento
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user