Complete phase 9 ambience polish
This commit is contained in:
@@ -36,6 +36,7 @@ import net.minecraft.world.entity.animal.Squid;
|
|||||||
import net.minecraft.world.entity.animal.Bee;
|
import net.minecraft.world.entity.animal.Bee;
|
||||||
import net.minecraft.world.entity.monster.Monster;
|
import net.minecraft.world.entity.monster.Monster;
|
||||||
import net.minecraft.world.entity.MobSpawnType;
|
import net.minecraft.world.entity.MobSpawnType;
|
||||||
|
import net.minecraft.world.entity.item.ItemEntity;
|
||||||
import net.minecraft.world.item.Items;
|
import net.minecraft.world.item.Items;
|
||||||
import net.minecraft.world.level.biome.Biome;
|
import net.minecraft.world.level.biome.Biome;
|
||||||
import net.minecraft.world.level.biome.Biomes;
|
import net.minecraft.world.level.biome.Biomes;
|
||||||
@@ -616,6 +617,10 @@ public class LivingWorldMod {
|
|||||||
Math.max(movement.y, 0.12),
|
Math.max(movement.y, 0.12),
|
||||||
movement.z + (random.nextDouble() - 0.5) * 0.35);
|
movement.z + (random.nextDouble() - 0.5) * 0.35);
|
||||||
}
|
}
|
||||||
|
if (bootstrap.isStormIncoming(coord) && random.nextInt(8) == 0) {
|
||||||
|
playAmbientSound(player, Holder.direct(SoundEvents.WEATHER_RAIN),
|
||||||
|
0.08f, 0.75f);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -651,6 +656,7 @@ public class LivingWorldMod {
|
|||||||
double tidalPushZ = Math.sin(windAngle) * tidalCurrentMag * TIDAL_CURRENT_STRENGTH;
|
double tidalPushZ = Math.sin(windAngle) * tidalCurrentMag * TIDAL_CURRENT_STRENGTH;
|
||||||
boolean hasTidalCurrent = Math.abs(tidalCurrentMag) > 0.1;
|
boolean hasTidalCurrent = Math.abs(tidalCurrentMag) > 0.1;
|
||||||
|
|
||||||
|
Set<UUID> processedItems = new HashSet<>();
|
||||||
for (ServerPlayer player : minecraftServer.getPlayerList().getPlayers()) {
|
for (ServerPlayer player : minecraftServer.getPlayerList().getPlayers()) {
|
||||||
if (!(player.level() instanceof ServerLevel level)) continue;
|
if (!(player.level() instanceof ServerLevel level)) continue;
|
||||||
BlockPos pos = player.blockPosition();
|
BlockPos pos = player.blockPosition();
|
||||||
@@ -694,6 +700,31 @@ public class LivingWorldMod {
|
|||||||
var mm = mob.getDeltaMovement();
|
var mm = mob.getDeltaMovement();
|
||||||
mob.setDeltaMovement(mm.x + mobFlow.x * mobForce, mm.y, mm.z + mobFlow.z * mobForce);
|
mob.setDeltaMovement(mm.x + mobFlow.x * mobForce, mm.y, mm.z + mobFlow.z * mobForce);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var nearbyItems = entityLevel.getEntitiesOfClass(
|
||||||
|
ItemEntity.class, player.getBoundingBox().inflate(48));
|
||||||
|
for (ItemEntity item : nearbyItems) {
|
||||||
|
if (!processedItems.add(item.getUUID())) continue;
|
||||||
|
var itemFluid = entityLevel.getFluidState(item.blockPosition());
|
||||||
|
if (!itemFluid.is(FluidTags.WATER)) continue;
|
||||||
|
var movement = item.getDeltaMovement();
|
||||||
|
if (!itemFluid.isSource()) {
|
||||||
|
var itemFlow = itemFluid.getFlow(entityLevel, item.blockPosition());
|
||||||
|
double force = CURRENT_STRENGTH * (itemFluid.getAmount() / 8.0) * 0.8;
|
||||||
|
item.setDeltaMovement(movement.x + itemFlow.x * force,
|
||||||
|
movement.y, movement.z + itemFlow.z * force);
|
||||||
|
} else if (hasTidalCurrent) {
|
||||||
|
RegionCoordinate itemCoord = RegionCoordinate.fromBlock(
|
||||||
|
entityLevel.dimension().location().toString(),
|
||||||
|
item.blockPosition().getX(), item.blockPosition().getZ(),
|
||||||
|
LivingWorldConstants.DEFAULT_REGION_SIZE_CHUNKS);
|
||||||
|
Double elevation = bootstrap.getRegionElevation(itemCoord);
|
||||||
|
if (elevation != null && elevation <= seaLevel + 6) {
|
||||||
|
item.setDeltaMovement(movement.x + tidalPushX,
|
||||||
|
movement.y, movement.z + tidalPushZ);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -710,14 +741,16 @@ public class LivingWorldMod {
|
|||||||
RegionCoordinate coord = new RegionCoordinate(dimId, regionX, regionZ);
|
RegionCoordinate coord = new RegionCoordinate(dimId, regionX, regionZ);
|
||||||
|
|
||||||
// Volcanic ambience — highest priority when eruption is active
|
// Volcanic ambience — highest priority when eruption is active
|
||||||
String volcanoPhase = bootstrap.getVolcanoPhaseAt(coord);
|
String volcanoPhase = bootstrap.getNearbyVolcanoPhase(coord, 3);
|
||||||
if (volcanoPhase != null) {
|
if (volcanoPhase != null) {
|
||||||
if ("ERUPTING".equals(volcanoPhase) && random.nextInt(4) == 0) {
|
if ("ERUPTING".equals(volcanoPhase) && random.nextInt(3) == 0) {
|
||||||
playAmbientSound(player, Holder.direct(SoundEvents.FIRE_AMBIENT), 0.55f, 0.8f + random.nextFloat() * 0.4f);
|
playAmbientSound(player, SoundEvents.AMBIENT_BASALT_DELTAS_MOOD,
|
||||||
|
0.45f, 0.55f + random.nextFloat() * 0.25f);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if ("BUILDING".equals(volcanoPhase) && random.nextInt(20) == 0) {
|
if ("BUILDING".equals(volcanoPhase) && random.nextInt(10) == 0) {
|
||||||
playAmbientSound(player, SoundEvents.AMBIENT_BASALT_DELTAS_MOOD, 0.25f, 0.7f + random.nextFloat() * 0.2f);
|
playAmbientSound(player, SoundEvents.AMBIENT_BASALT_DELTAS_MOOD,
|
||||||
|
0.22f, 0.75f + random.nextFloat() * 0.15f);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1489,6 +1489,33 @@ public final class LivingWorldBootstrap {
|
|||||||
return phase != null ? phase.name() : null;
|
return phase != null ? phase.name() : null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Returns the strongest volcanic phase within the requested region radius. */
|
||||||
|
public String getNearbyVolcanoPhase(RegionCoordinate coord, int radius) {
|
||||||
|
if (coord == null) return null;
|
||||||
|
VolcanoPhase strongest = null;
|
||||||
|
for (RegionCoordinate volcanic : volcanicRegions) {
|
||||||
|
if (!volcanic.dimensionId().equals(coord.dimensionId())) continue;
|
||||||
|
if (Math.abs(volcanic.x() - coord.x()) > radius
|
||||||
|
|| Math.abs(volcanic.z() - coord.z()) > radius) continue;
|
||||||
|
VolcanoPhase phase = volcanoPhase.get(volcanic);
|
||||||
|
if (phase == VolcanoPhase.ERUPTING) return phase.name();
|
||||||
|
if (phase == VolcanoPhase.BUILDING) strongest = phase;
|
||||||
|
}
|
||||||
|
return strongest != null ? strongest.name() : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isStormIncoming(RegionCoordinate coord) {
|
||||||
|
if (coord == null || isClimateEventActive(coord, ClimateEventType.LIGHTNING_STORM)
|
||||||
|
|| isClimateEventActive(coord, ClimateEventType.BLIZZARD)
|
||||||
|
|| isClimateEventActive(coord, ClimateEventType.SANDSTORM)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return getRegionalWeather(coord)
|
||||||
|
.map(atmosphere -> atmosphere.getThunderLevel() >= 0.25
|
||||||
|
&& atmosphere.getThunderLevel() < 0.55)
|
||||||
|
.orElse(false);
|
||||||
|
}
|
||||||
|
|
||||||
/** Marks a region as oceanic so it can host submarine volcanoes. */
|
/** Marks a region as oceanic so it can host submarine volcanoes. */
|
||||||
public void markOceanicRegion(RegionCoordinate coord) {
|
public void markOceanicRegion(RegionCoordinate coord) {
|
||||||
if (coord != null) oceanicRegions.add(coord);
|
if (coord != null) oceanicRegions.add(coord);
|
||||||
|
|||||||
Reference in New Issue
Block a user