package com.hbm.items.weapon.grenade; import java.util.HashSet; import java.util.Set; import java.util.function.BiConsumer; import java.util.function.Consumer; import com.hbm.entity.effect.EntityFireLingering; import com.hbm.entity.grenade.EntityGrenadeUniversal; import com.hbm.entity.projectile.EntityBulletBaseMK4; import com.hbm.explosion.vanillant.ExplosionVNT; import com.hbm.explosion.vanillant.standard.BlockAllocatorStandard; import com.hbm.explosion.vanillant.standard.BlockMutatorFire; import com.hbm.explosion.vanillant.standard.BlockProcessorStandard; import com.hbm.explosion.vanillant.standard.EntityProcessorCrossSmooth; import com.hbm.explosion.vanillant.standard.ExplosionEffectTiny; import com.hbm.explosion.vanillant.standard.ExplosionEffectWeapon; import com.hbm.explosion.vanillant.standard.PlayerProcessorStandard; import com.hbm.handler.radiation.ChunkRadiationManager; import com.hbm.handler.threading.PacketThreading; import com.hbm.items.ItemEnumMulti; import com.hbm.items.weapon.grenade.ItemGrenadeShell.EnumGrenadeShell; import static com.hbm.items.weapon.grenade.ItemGrenadeShell.EnumGrenadeShell.*; import com.hbm.items.weapon.sedna.BulletConfig; import com.hbm.items.weapon.sedna.factory.Lego; import com.hbm.items.weapon.sedna.factory.XFactoryCatapult; import com.hbm.main.MainRegistry; import com.hbm.main.NTMSounds; import com.hbm.packet.toclient.AuxParticlePacketNT; import com.hbm.util.DamageResistanceHandler.DamageClass; import cpw.mods.fml.common.network.NetworkRegistry.TargetPoint; import net.minecraft.init.Blocks; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.util.MovingObjectPosition; import net.minecraft.world.World; import net.minecraftforge.common.util.ForgeDirection; public class ItemGrenadeFilling extends ItemEnumMulti { public static BulletConfig fragmentation; public static BulletConfig pellets; public ItemGrenadeFilling() { super(EnumGrenadeFilling.class, true, true); fragmentation = new BulletConfig().setLife(3).setThresholdNegation(5F).setRicochetAngle(90).setRicochetCount(2); pellets = new BulletConfig().setLife(100).setGrav(0.04).setVel(1.5F).setOnImpact(LAMBDA_TINY_EXPLODE); } public static enum EnumGrenadeFilling { POWDER(EXPLODE_POWDER, 0x424242, 0x939176, FRAG, STICK), // gunpowder HE(EXPLODE_HE, 0x595533, 0xA49D62, FRAG, STICK), // high explosive DEMO(EXPLODE_DEMO, 0x595533, 0xDD4029, FRAG, STICK), // demolition INC(EXPLODE_INC, 0x5A5A5A, 0xFF5F21, FRAG, STICK), // incendiary CLUSTER(EXPLODE_CLUSTER, 0x5A5A5A, 0xFFC711, FRAG, STICK, NUKE), // explosive pellets EMP(EXPLODE_EMP, 0x93A1AC, 0x00FFFF, TECH), // tesla PLASMA(EXPLODE_PLASMA, 0x655B2C, 0x4CFF00, TECH), // EMP but more oomph NUCLEAR(EXPLODE_NUKE, 0, 0xA49D62, NUKE), // nuka grenade NUCLEAR_DEMO(EXPLODE_NUKE_DEMO, 0, 0xDD4029, NUKE); // demolition nuka grenade public Consumer explode; public Set compatibleShells = new HashSet(); public int bodyColor; public int labelColor; private EnumGrenadeFilling(Consumer explode, int bodyColor, int labelColor, EnumGrenadeShell... compatibleShells) { this.explode = explode; for(EnumGrenadeShell shell : compatibleShells) this.compatibleShells.add(shell); this.bodyColor = bodyColor; this.labelColor = labelColor; } } public static Consumer EXPLODE_POWDER = (grenade) -> { standardExplode(grenade, 5F, 10F, 5F, 0F); }; public static Consumer EXPLODE_HE = (grenade) -> { standardExplode(grenade, 7.5F, 25F, 10F, 0.1F); }; public static Consumer EXPLODE_CLUSTER = (grenade) -> { standardExplode(grenade, 7.5F, 15F, 10F, 0.1F); int frags = 30; if(grenade.getShell() == EnumGrenadeShell.FRAG) frags *= 1.25; for(int i = 0; i < frags; i++) { EntityBulletBaseMK4 bullet = new EntityBulletBaseMK4(grenade.worldObj, pellets, 10F, 0F, grenade.worldObj.rand.nextFloat() * 2F * (float) Math.PI, (grenade.worldObj.rand.nextFloat() * 0.5F + 0.5F) * (float) Math.PI); bullet.setPosition(grenade.posX, grenade.posY + 0.05, grenade.posZ); bullet.motionX *= 0.5; bullet.motionY *= 0.75; bullet.motionZ *= 0.5; grenade.worldObj.spawnEntityInWorld(bullet); } }; public static Consumer EXPLODE_DEMO = (grenade) -> { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, 5F, grenade.getThrower()); vnt.setBlockAllocator(new BlockAllocatorStandard()); vnt.setBlockProcessor(new BlockProcessorStandard()); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(1, 10F)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.setSFX(new ExplosionEffectWeapon(10, 2.5F, 1F)); vnt.explode(); }; public static Consumer EXPLODE_INC = (grenade) -> { World world = grenade.worldObj; standardExplode(grenade, 3F, 10F); EntityFireLingering fire = new EntityFireLingering(world).setArea(6, 2).setDuration(200).setType(EntityFireLingering.TYPE_DIESEL); fire.setPosition(grenade.posX, grenade.posY, grenade.posZ); world.spawnEntityInWorld(fire); for(int dx = -2; dx <= 2; dx++) for(int dy = -2; dy <= 2; dy++) for(int dz = -2; dz <= 2; dz++) { int x = (int) Math.floor(grenade.posX) + dx; int y = (int) Math.floor(grenade.posY) + dy; int z = (int) Math.floor(grenade.posZ) + dz; if(world.getBlock(x, y, z).isAir(grenade.worldObj, x, y, z)) { for(ForgeDirection dir : ForgeDirection.VALID_DIRECTIONS) { if(world.getBlock(x + dir.offsetX, y + dir.offsetY, z + dir.offsetZ).isFlammable(world, x + dir.offsetX, y + dir.offsetY, z + dir.offsetZ, dir.getOpposite())) { world.setBlock(x, y, z, Blocks.fire); break; } } } } }; public static Consumer EXPLODE_EMP = (grenade) -> { explodeStandardEnergy(grenade, 30F, 3F, DamageClass.ELECTRIC, 0.5F, 0.5F, 1F, 3F); }; public static Consumer EXPLODE_PLASMA = (grenade) -> { explodeStandardEnergy(grenade, 50F, 5F, DamageClass.PLASMA, 0.5F, 1F, 0.5F, 4F); // TODO: unique effect because this sucks }; public static Consumer EXPLODE_NUKE = (grenade) -> { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, 10); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(2, 100).withRangeMod(1.5F)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.explode(); XFactoryCatapult.incrementRad(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, 1F); spawnMush(grenade); }; public static Consumer EXPLODE_NUKE_DEMO = (grenade) -> { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, 10); vnt.setBlockAllocator(new BlockAllocatorStandard(64)); vnt.setBlockProcessor(new BlockProcessorStandard().withBlockEffect(new BlockMutatorFire())); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(2, 50).withRangeMod(1.5F)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.explode(); XFactoryCatapult.incrementRad(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, 1.5F); spawnMush(grenade); }; public static void incrementRad(World world, double posX, double posY, double posZ, float mult) { for(int i = -2; i <= 2; i++) { for(int j = -2; j <= 2; j++) { if(Math.abs(i) + Math.abs(j) < 4) { ChunkRadiationManager.proxy.incrementRad(world, (int) Math.floor(posX + i * 16), (int) Math.floor(posY), (int) Math.floor(posZ + j * 16), 50F / (Math.abs(i) + Math.abs(j) + 1) * mult); } } } } public static void spawnMush(EntityGrenadeUniversal grenade) { grenade.worldObj.playSoundEffect(grenade.posX, grenade.posY, grenade.posZ, NTMSounds.GUN_MINI_NUKE_EXPLOSION, 15.0F, 1.0F); NBTTagCompound data = new NBTTagCompound(); data.setString("type", "muke"); data.setBoolean("balefire", MainRegistry.polaroidID == 11 || grenade.worldObj.rand.nextInt(100) == 0); PacketThreading.createAllAroundThreadedPacket(new AuxParticlePacketNT(data, grenade.posX, grenade.posY + 0.5, grenade.posZ), new TargetPoint(grenade.dimension, grenade.posX, grenade.posY, grenade.posZ, 250)); } public static void explodeStandardEnergy(EntityGrenadeUniversal grenade, float damage, float range, DamageClass damageClass, float r, float g, float b, float scale) { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, range, grenade.getThrower()); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(1, damage).setDamageClass(damageClass)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.explode(); grenade.worldObj.playSoundEffect(grenade.posX, grenade.posY, grenade.posZ, "hbm:entity.ufoBlast", 5.0F, 0.9F + grenade.worldObj.rand.nextFloat() * 0.2F); grenade.worldObj.playSoundEffect(grenade.posX, grenade.posY, grenade.posZ, NTMSounds.VANILLA_FIREWORKS_BANG, 5.0F, 0.5F); float yaw = grenade.worldObj.rand.nextFloat() * 180F; for(int i = 0; i < 3; i++) { NBTTagCompound data = new NBTTagCompound(); data.setString("type", "plasmablast"); data.setFloat("r", r); data.setFloat("g", g); data.setFloat("b", b); data.setFloat("pitch", -60F + 60F * i); data.setFloat("yaw", yaw); data.setFloat("scale", scale); PacketThreading.createAllAroundThreadedPacket(new AuxParticlePacketNT(data, grenade.posX, grenade.posY + 0.125, grenade.posZ), new TargetPoint(grenade.dimension, grenade.posX, grenade.posY, grenade.posZ, 100)); } } public static BiConsumer LAMBDA_TINY_EXPLODE = (bullet, mop) -> { if(bullet.ticksExisted < 2) return; Lego.tinyExplode(bullet, mop, 1.5F); bullet.setDead(); }; public static void standardExplode(EntityGrenadeUniversal grenade, float range, float damage) { standardExplode(grenade, range, damage, 0F, 0F); } public static void standardExplode(EntityGrenadeUniversal grenade, float range, float damage, float dt, float dr) { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, range, grenade.getThrower()); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(1, damage).setupPiercing(dt, dr)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.setSFX(new ExplosionEffectWeapon(10, 2.5F, 1F)); vnt.explode(); } public static void tinyExplode(EntityGrenadeUniversal grenade, float range, float damage) { tinyExplode(grenade, range, damage, 0F, 0F); } public static void tinyExplode(EntityGrenadeUniversal grenade, float range, float damage, float dt, float dr) { ExplosionVNT vnt = new ExplosionVNT(grenade.worldObj, grenade.posX, grenade.posY, grenade.posZ, range, grenade.getThrower()); vnt.setEntityProcessor(new EntityProcessorCrossSmooth(0.5, damage).setupPiercing(dt, dr).setKnockback(0.25D)); vnt.setPlayerProcessor(new PlayerProcessorStandard()); vnt.setSFX(new ExplosionEffectTiny()); vnt.explode(); } public static void standardFragmentation(EntityGrenadeUniversal grenade, float frags) { if(grenade.getShell() == EnumGrenadeShell.FRAG) frags *= 1.5; for(int i = 0; i < frags; i++) { EntityBulletBaseMK4 bullet = new EntityBulletBaseMK4(grenade.worldObj, fragmentation, 10F, 0F, grenade.worldObj.rand.nextFloat() * 2F * (float) Math.PI, (grenade.worldObj.rand.nextFloat() - 0.5F) * 2F * (float) Math.PI); bullet.setPosition(grenade.posX, grenade.posY + 0.05, grenade.posZ); grenade.worldObj.spawnEntityInWorld(bullet); } } }