Skip to content

Commit

Permalink
chore: refactor mob spawning checks and improve spatial query
Browse files Browse the repository at this point in the history
  • Loading branch information
Elenterius committed Dec 5, 2023
1 parent b1309ef commit eb763b2
Show file tree
Hide file tree
Showing 19 changed files with 287 additions and 115 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,11 @@
import com.github.elenterius.biomancy.network.ModNetworkHandler;
import com.github.elenterius.biomancy.tribute.Tribute;
import com.github.elenterius.biomancy.util.SoundUtil;
import com.github.elenterius.biomancy.util.shape.Shape;
import com.github.elenterius.biomancy.world.PrimordialEcosystem;
import com.github.elenterius.biomancy.world.mound.MoundGenerator;
import com.github.elenterius.biomancy.world.mound.MoundShape;
import com.github.elenterius.biomancy.world.spatial.SpatialShapeManager;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import com.google.common.math.IntMath;
import net.minecraft.core.BlockPos;
import net.minecraft.core.particles.ParticleOptions;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,11 @@
import com.github.elenterius.biomancy.util.EnhancedIntegerProperty;
import com.github.elenterius.biomancy.util.LevelUtil;
import com.github.elenterius.biomancy.util.random.CellularNoise;
import com.github.elenterius.biomancy.util.shape.Shape;
import com.github.elenterius.biomancy.world.PrimordialEcosystem;
import com.github.elenterius.biomancy.world.mound.MoundChamber;
import com.github.elenterius.biomancy.world.mound.MoundShape;
import com.github.elenterius.biomancy.world.spatial.SpatialShapeManager;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import net.minecraft.core.BlockPos;
import net.minecraft.core.Direction;
import net.minecraft.core.particles.ItemParticleOption;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,47 +1,47 @@
package com.github.elenterius.biomancy.event;

import com.github.elenterius.biomancy.BiomancyMod;
import com.github.elenterius.biomancy.world.mound.MoundShape;
import com.github.elenterius.biomancy.world.MobSpawnFilter;
import com.github.elenterius.biomancy.world.spatial.SpatialShapeManager;
import net.minecraft.core.BlockPos;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.world.entity.Mob;
import net.minecraft.world.entity.MobSpawnType;
import net.minecraftforge.event.entity.living.LivingSpawnEvent;
import net.minecraftforge.eventbus.api.Event;
import net.minecraftforge.eventbus.api.EventPriority;
import net.minecraftforge.eventbus.api.SubscribeEvent;
import net.minecraftforge.fml.common.Mod;

import java.util.Set;
import java.util.function.Predicate;

@Mod.EventBusSubscriber(modid = BiomancyMod.MOD_ID, bus = Mod.EventBusSubscriber.Bus.FORGE)
public final class MobSpawnHandler {

private static final Set<MobSpawnType> NATURAL_SPAWN_TYPE = Set.of(
MobSpawnType.EVENT,
MobSpawnType.NATURAL,
MobSpawnType.CHUNK_GENERATION,
MobSpawnType.PATROL
);

private MobSpawnHandler() {}

@SubscribeEvent(priority = EventPriority.HIGH)
public static void onCheckSpawn(LivingSpawnEvent.CheckSpawn event) {
if (event.isCanceled()) return;

boolean isNaturalSpawn = NATURAL_SPAWN_TYPE.contains(event.getSpawnReason());
if (event.getLevel() instanceof ServerLevel serverLevel) {
MobSpawnType spawnReason = event.getSpawnReason();

if (isNaturalSpawn && event.getLevel() instanceof ServerLevel serverLevel) {
BlockPos pos = new BlockPos(event.getX(), event.getY(), event.getZ());
//Mob entity = event.getEntity();
//TODO: check unnatural spawns as well??
if (MobSpawnFilter.isNaturalSpawn(spawnReason)) {
Mob mob = event.getEntity();
double x = event.getX();
double y = event.getY();
double z = event.getZ();

//TODO: implement check with BoundingBox of entity
if (SpatialShapeManager.getClosestShape(serverLevel, pos) instanceof MoundShape) {
//TODO: chamber level mob spawn prevention? --> e.g. spawning chamber for creepers
//MoundChamber chamber = moundShape.getChamberAt(pos.getX(), pos.getY(), pos.getZ());
Predicate<Shape> denySpawnPredicate = shape -> shape instanceof MobSpawnFilter mobSpawnFilter && !mobSpawnFilter.isMobAllowedToSpawn(mob, spawnReason, serverLevel, x, y, z);
boolean denySpawn = SpatialShapeManager.getAnyShape(serverLevel, mob, denySpawnPredicate) != null;

event.setResult(Event.Result.DENY);
if (denySpawn) {
//TODO: chamber specific mob spawn filters? --> e.g. chamber only allows creepers spawns
//MoundChamber chamber = moundShape.getChamberAt(pos.getX(), pos.getY(), pos.getZ());
event.setResult(Event.Result.DENY);
}
}
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package com.github.elenterius.biomancy.world;

import net.minecraft.world.entity.Mob;
import net.minecraft.world.entity.MobSpawnType;
import net.minecraft.world.level.LevelAccessor;

import java.util.Set;

public interface MobSpawnFilter {

Set<MobSpawnType> NATURAL_SPAWN_REASON = Set.of(
MobSpawnType.EVENT,
MobSpawnType.NATURAL,
MobSpawnType.CHUNK_GENERATION,
MobSpawnType.PATROL
);

static boolean isNaturalSpawn(MobSpawnType spawnReason) {
return NATURAL_SPAWN_REASON.contains(spawnReason);
}

/**
* At the moment only checks natural mob spawns
*/
boolean isMobAllowedToSpawn(Mob mob, MobSpawnType spawnReason, LevelAccessor level, double x, double y, double z);

}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.github.elenterius.biomancy.world.mound;

import com.github.elenterius.biomancy.util.shape.OctantEllipsoidShape;
import com.github.elenterius.biomancy.util.shape.SphereShape;
import com.github.elenterius.biomancy.world.spatial.geometry.OctantEllipsoidShape;
import com.github.elenterius.biomancy.world.spatial.geometry.SphereShape;
import net.minecraft.util.random.SimpleWeightedRandomList;

import java.util.function.Consumer;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.github.elenterius.biomancy.world.mound;

import com.github.elenterius.biomancy.util.serialization.NBTSerializer;
import com.github.elenterius.biomancy.util.shape.Shape;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import net.minecraft.world.phys.AABB;
import net.minecraft.world.phys.Vec3;

Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package com.github.elenterius.biomancy.world.mound;

import com.github.elenterius.biomancy.util.TemperatureUtil;
import com.github.elenterius.biomancy.util.shape.Shape;
import com.github.elenterius.biomancy.util.shape.SphereShape;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import com.github.elenterius.biomancy.world.spatial.geometry.SphereShape;
import com.mojang.math.Vector3d;
import net.minecraft.core.BlockPos;
import net.minecraft.util.Mth;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,18 +1,22 @@
package com.github.elenterius.biomancy.world.mound;

import com.github.elenterius.biomancy.util.serialization.NBTSerializer;
import com.github.elenterius.biomancy.util.shape.Shape;
import com.github.elenterius.biomancy.util.shape.ShapeHierarchy;
import com.github.elenterius.biomancy.world.MobSpawnFilter;
import com.github.elenterius.biomancy.world.spatial.geometry.Shape;
import com.github.elenterius.biomancy.world.spatial.geometry.ShapeHierarchy;
import com.github.elenterius.biomancy.world.spatial.type.ShapeSerializers;
import net.minecraft.core.BlockPos;
import net.minecraft.nbt.CompoundTag;
import net.minecraft.world.entity.Mob;
import net.minecraft.world.entity.MobSpawnType;
import net.minecraft.world.level.LevelAccessor;
import net.minecraft.world.phys.AABB;
import net.minecraft.world.phys.Vec3;
import org.jetbrains.annotations.Nullable;

import java.util.List;

public class MoundShape implements Shape {
public class MoundShape implements Shape, MobSpawnFilter {
private final ProcGenValues procGenValues;
BlockPos origin;
ShapeHierarchy<Shape> boundingShapes;
Expand Down Expand Up @@ -68,6 +72,11 @@ public NBTSerializer<Shape> getNBTSerializer() {
return ShapeSerializers.MOUND_SERIALIZER;
}

@Override
public boolean isMobAllowedToSpawn(Mob mob, MobSpawnType spawnReason, LevelAccessor level, double x, double y, double z) {
return false;
}

public record ProcGenValues(long seed, int maxBuildHeight, int seaLevel, float biomeTemperature, float biomeHumidity) {
public void writeTo(CompoundTag tag) {
tag.putLong("Seed", seed);
Expand Down

This file was deleted.

Loading

0 comments on commit eb763b2

Please sign in to comment.