/* * Decompiled with CFR 0.152. */ package com.vinlanx.explosionoverhaul; import com.vinlanx.explosionoverhaul.Config; import com.vinlanx.explosionoverhaul.ExplosionOverhaul; import java.util.HashSet; import java.util.Set; import net.minecraft.core.BlockPos; import net.minecraft.core.Position; import net.minecraft.core.Vec3i; import net.minecraft.core.particles.ParticleOptions; import net.minecraft.core.particles.ParticleTypes; import net.minecraft.server.level.ServerLevel; import net.minecraft.util.Mth; import net.minecraft.util.RandomSource; import net.minecraft.world.entity.item.FallingBlockEntity; import net.minecraft.world.level.BlockGetter; import net.minecraft.world.level.Level; import net.minecraft.world.level.block.Block; import net.minecraft.world.level.block.Blocks; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.phys.Vec3; public class CraterDeformer { public static Set getCraterBlocks(ServerLevel level, Vec3 explosionPos, float power) { double multiplier = (Double)Config.COMMON.craterSizeMultiplier.get(); double baseRadius = CraterDeformer.calculateRadius(power); double finalRadius = baseRadius * multiplier; if (finalRadius <= 0.0) { return new HashSet(); } HashSet blocksToDestroy = new HashSet(); if (power >= 40.0f) { double coreRatio = (Double)Config.COMMON.craterCoreRatio.get(); double coreRadius = finalRadius * coreRatio; int searchRadius = (int)Math.ceil(finalRadius); BlockPos centerPos = BlockPos.m_274446_((Position)explosionPos); RandomSource random = level.m_213780_(); for (int x = -searchRadius; x <= searchRadius; ++x) { for (int y = -searchRadius; y <= searchRadius; ++y) { for (int z = -searchRadius; z <= searchRadius; ++z) { double noise; BlockPos currentPos = centerPos.m_7918_(x, y, z); double distanceToCenter = Math.sqrt(currentPos.m_123331_((Vec3i)centerPos)); if (!(distanceToCenter <= coreRadius * (noise = 1.0 - random.m_188500_() * 0.3)) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); float resistance = state.m_60800_((BlockGetter)level, currentPos); if (state.m_60795_() || resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; blocksToDestroy.add(currentPos); } } } int numberOfRays = (int)Math.max(200.0, Math.min(25000.0, finalRadius * 75.0)); float rayEnergy = (float)((double)(power * 4.0f) * multiplier); double goldenRatio = (1.0 + Math.sqrt(5.0)) / 2.0; double angleIncrement = Math.PI * 2 * goldenRatio; double stepIncrement = 0.4; block3: for (int i = 0; i < numberOfRays; ++i) { double t = (double)i / (double)numberOfRays; double inclination = Math.acos(1.0 - 2.0 * t); double azimuth = angleIncrement * (double)i; Vec3 rayDirection = new Vec3(Math.cos(azimuth) * Math.sin(inclination), Math.sin(azimuth) * Math.sin(inclination), Math.cos(inclination)).m_82541_(); float currentEnergy = rayEnergy * (0.75f + level.m_213780_().m_188501_() * 0.5f); BlockPos lastPos = null; for (double step = coreRadius * 0.8; step < finalRadius; step += 0.4) { BlockPos currentPos = BlockPos.m_274446_((Position)explosionPos.m_82549_(rayDirection.m_82490_(step))); if (currentPos.equals(lastPos) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; lastPos = currentPos; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); if (state.m_60795_() || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; float resistance = state.m_60800_((BlockGetter)level, currentPos); if (resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block) || !((currentEnergy -= resistance + 0.3f) > 0.0f)) continue block3; blocksToDestroy.add(currentPos); } } } else { int numberOfRays = (int)Math.max(200.0, Math.min(75000.0, finalRadius * 150.0)); float rayEnergy = (float)((double)(power * 7.5f) * multiplier); double goldenRatio = (1.0 + Math.sqrt(5.0)) / 2.0; double angleIncrement = Math.PI * 2 * goldenRatio; double stepIncrement = 0.4; RandomSource random = level.m_213780_(); block5: for (int i = 0; i < numberOfRays; ++i) { double t = (double)i / (double)numberOfRays; double inclination = Math.acos(1.0 - 2.0 * t); double azimuth = angleIncrement * (double)i; Vec3 rayDirection = new Vec3(Math.cos(azimuth) * Math.sin(inclination), Math.sin(azimuth) * Math.sin(inclination), Math.cos(inclination)).m_82541_(); float currentEnergy = rayEnergy * (0.75f + random.m_188501_() * 0.5f); BlockPos lastPos = null; for (double step = 0.0; step < finalRadius; step += 0.4) { BlockPos currentPos = BlockPos.m_274446_((Position)explosionPos.m_82549_(rayDirection.m_82490_(step))); if (currentPos.equals(lastPos) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; lastPos = currentPos; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); if (state.m_60795_() || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; float resistance = state.m_60800_((BlockGetter)level, currentPos); if (resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block) || !((currentEnergy -= resistance + 0.3f) > 0.0f)) continue block5; blocksToDestroy.add(currentPos); } } } return blocksToDestroy; } public static float calculateRadius(float power) { float baseRadius = power <= 4.0f ? Mth.m_14179_((float)(power / 4.0f), (float)2.0f, (float)6.0f) : (power <= 50.0f ? Mth.m_14179_((float)((power - 4.0f) / 46.0f), (float)6.0f, (float)60.0f) : 60.0f + (power - 50.0f) * 1.5f); return baseRadius * 0.5f; } private static float calculateMaxResistance(float power) { float maxRes = power <= 4.0f ? 10.0f : (power <= 10.0f ? 10.0f + (power - 4.0f) * 10.0f / 6.0f : (power <= 25.0f ? 20.0f + (power - 10.0f) * 10.0f / 15.0f : (power <= 40.0f ? 30.0f + (power - 25.0f) * 10.0f / 15.0f : (power <= 70.0f ? 40.0f + (power - 40.0f) * 10.0f / 30.0f : Float.MAX_VALUE)))); return maxRes; } public static void apply(ServerLevel level, Vec3 explosionPos, float power) { if (power >= 40.0f) { CraterDeformer.applyLargeExplosionLogic(level, explosionPos, power); } else { CraterDeformer.applySmallExplosionLogic(level, explosionPos, power); } } private static void applyLargeExplosionLogic(ServerLevel level, Vec3 explosionPos, float power) { RandomSource random = level.m_213780_(); double multiplier = (Double)Config.COMMON.craterSizeMultiplier.get(); double baseRadius = CraterDeformer.calculateRadius(power); double finalRadius = baseRadius * multiplier; if (finalRadius <= 0.0) { return; } HashSet blocksToDestroy = new HashSet(); HashSet blocksToLaunch = new HashSet(); double coreRatio = (Double)Config.COMMON.craterCoreRatio.get(); double coreRadius = finalRadius * coreRatio; int searchRadius = (int)Math.ceil(finalRadius); BlockPos centerPos = BlockPos.m_274446_((Position)explosionPos); for (int x = -searchRadius; x <= searchRadius; ++x) { for (int y = -searchRadius; y <= searchRadius; ++y) { for (int z = -searchRadius; z <= searchRadius; ++z) { double noise; BlockPos currentPos = centerPos.m_7918_(x, y, z); double distanceToCenter = Math.sqrt(currentPos.m_123331_((Vec3i)centerPos)); if (!(distanceToCenter <= coreRadius * (noise = 1.0 - random.m_188500_() * 0.3)) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); float resistance = state.m_60800_((BlockGetter)level, currentPos); if (state.m_60795_() || resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; blocksToDestroy.add(currentPos); if (!(distanceToCenter < coreRadius * 0.4)) continue; blocksToLaunch.add(currentPos); } } } int numberOfRays = (int)Math.max(200.0, Math.min(25000.0, finalRadius * 75.0)); float rayEnergy = (float)((double)(power * 4.0f) * multiplier); double goldenRatio = (1.0 + Math.sqrt(5.0)) / 2.0; double angleIncrement = Math.PI * 2 * goldenRatio; double stepIncrement = 0.4; block3: for (int i = 0; i < numberOfRays; ++i) { double t = (double)i / (double)numberOfRays; double inclination = Math.acos(1.0 - 2.0 * t); double azimuth = angleIncrement * (double)i; Vec3 rayDirection = new Vec3(Math.cos(azimuth) * Math.sin(inclination), Math.sin(azimuth) * Math.sin(inclination), Math.cos(inclination)).m_82541_(); float currentEnergy = rayEnergy * (0.75f + random.m_188501_() * 0.5f); BlockPos lastPos = null; for (double step = coreRadius * 0.8; step < finalRadius; step += 0.4) { BlockPos currentPos = BlockPos.m_274446_((Position)explosionPos.m_82549_(rayDirection.m_82490_(step))); if (currentPos.equals(lastPos) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; lastPos = currentPos; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); if (state.m_60795_() || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; float resistance = state.m_60800_((BlockGetter)level, currentPos); if (resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block) || !((currentEnergy -= resistance + 0.3f) > 0.0f)) continue block3; blocksToDestroy.add(currentPos); } } CraterDeformer.finalizeExplosion(level, explosionPos, power, blocksToDestroy, blocksToLaunch); } private static void applySmallExplosionLogic(ServerLevel level, Vec3 explosionPos, float power) { RandomSource random = level.m_213780_(); double multiplier = (Double)Config.COMMON.craterSizeMultiplier.get(); double baseRadius = CraterDeformer.calculateRadius(power); double finalRadius = baseRadius * multiplier; if (finalRadius <= 0.0) { return; } int numberOfRays = (int)Math.max(200.0, Math.min(75000.0, finalRadius * 150.0)); float rayEnergy = (float)((double)(power * 7.5f) * multiplier); HashSet blocksToDestroy = new HashSet(); HashSet blocksToLaunch = new HashSet(); double goldenRatio = (1.0 + Math.sqrt(5.0)) / 2.0; double angleIncrement = Math.PI * 2 * goldenRatio; double stepIncrement = 0.4; block0: for (int i = 0; i < numberOfRays; ++i) { double t = (double)i / (double)numberOfRays; double inclination = Math.acos(1.0 - 2.0 * t); double azimuth = angleIncrement * (double)i; Vec3 rayDirection = new Vec3(Math.cos(azimuth) * Math.sin(inclination), Math.sin(azimuth) * Math.sin(inclination), Math.cos(inclination)).m_82541_(); float currentEnergy = rayEnergy * (0.75f + random.m_188501_() * 0.5f); BlockPos lastPos = null; for (double step = 0.0; step < finalRadius; step += 0.4) { BlockPos currentPos = BlockPos.m_274446_((Position)explosionPos.m_82549_(rayDirection.m_82490_(step))); if (currentPos.equals(lastPos) || !level.m_46749_(currentPos) || level.m_151570_(currentPos)) continue; lastPos = currentPos; BlockState state = level.m_8055_(currentPos); Block block = state.m_60734_(); if (state.m_60795_() || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block)) continue; float resistance = state.m_60800_((BlockGetter)level, currentPos); if (resistance < 0.0f || resistance > CraterDeformer.calculateMaxResistance(power) || block == Blocks.f_50722_ || ExplosionOverhaul.isBlockBlacklisted(block) || !((currentEnergy -= resistance + 0.3f) > 0.0f)) continue block0; blocksToDestroy.add(currentPos); if (!(step < finalRadius * 0.3)) continue; blocksToLaunch.add(currentPos); } } CraterDeformer.finalizeExplosion(level, explosionPos, power, blocksToDestroy, blocksToLaunch); } private static void finalizeExplosion(ServerLevel level, Vec3 explosionPos, float power, Set blocksToDestroy, Set blocksToLaunch) { boolean allowFallingBlocks; RandomSource random = level.m_213780_(); level.m_8767_((ParticleOptions)ParticleTypes.f_123812_, explosionPos.f_82479_, explosionPos.f_82480_, explosionPos.f_82481_, 1, 0.0, 0.0, 0.0, 0.0); boolean bl = allowFallingBlocks = power <= 20.0f && (Boolean)Config.COMMON.enableFallingBlocks.get() != false; if (allowFallingBlocks) { for (BlockPos posToLaunch : blocksToLaunch) { if (!(random.m_188500_() < 0.35)) continue; FallingBlockEntity falling = FallingBlockEntity.m_201971_((Level)level, (BlockPos)posToLaunch, (BlockState)level.m_8055_(posToLaunch)); falling.m_6034_((double)posToLaunch.m_123341_() + 0.5, (double)posToLaunch.m_123342_() + 0.5, (double)posToLaunch.m_123343_() + 0.5); Vec3 motionDir = Vec3.m_82512_((Vec3i)posToLaunch).m_82546_(explosionPos).m_82541_(); double powerMul = 0.5 + random.m_188500_() * 0.8; falling.m_20334_(motionDir.f_82479_ * powerMul + (random.m_188500_() - 0.5) * 0.4, motionDir.f_82480_ * powerMul + 0.5 + random.m_188500_() * 0.4, motionDir.f_82481_ * powerMul + (random.m_188500_() - 0.5) * 0.4); } } for (BlockPos posToDestroy : blocksToDestroy) { level.m_7731_(posToDestroy, Blocks.f_50016_.m_49966_(), 3); } } }