public void shoot(Player player) { boolean shot = ammoTracker.shootBullet(player.getUniqueId()); if (!shot) return; startTracking(player); shootBullet(player); GamePlayer gamePlayer = main.getGameManager().getGamePlayer(player); int points = stopTracking(player); if (gamePlayer != null) gamePlayer.awardPoints(points); } public void shootBullet(Player player) { Game game = main.getGameManager().getPlayerGame(player); Location eyeLocation = player.getEyeLocation(); Vector direction = eyeLocation.getDirection().normalize(); float spread = getSpread(); double particleRange = getParticleRange(); double gunRange = getRange(); // add some randomness to the direction float randomX = ThreadLocalRandom.current().nextFloat() * spread * 2 - spread; float randomY = ThreadLocalRandom.current().nextFloat() * spread * 2 - spread; float randomZ = ThreadLocalRandom.current().nextFloat() * spread * 2 - spread; direction.add(new Vector(randomX, randomY, randomZ)).normalize().multiply(0.3); direction.normalize().multiply(1.0f); playSound(player, player.getEyeLocation(), SoundType.SHOOT); RayTraceResult result; double distance = particleRange; if (game == null) result = eyeLocation.getWorld().rayTrace(eyeLocation, direction, gunRange, FluidCollisionMode.NEVER, true, 0.5, (entity) -> entity instanceof Zombie); else result = game.rayTrace(eyeLocation, direction, gunRange, 0.5); if (result == null) { main.getParticleRenderer().render(new ParticleRenderer.ParticleLineData(eyeLocation, direction, particleRange, 1, getBulletParticle(), game, getParticleLineRenderer())); return; } Vector hitPosition = result.getHitPosition(); distance = Math.min(distance, hitPosition.distance(eyeLocation.toVector())); main.getParticleRenderer().render(new ParticleRenderer.ParticleLineData(eyeLocation, direction, distance, 1, getBulletParticle(), game, getParticleLineRenderer())); BodyPart bodyPart = BodyPart.rayTrace(result); Entity hitEntity = result.getHitEntity(); if (bodyPart == null || hitEntity == null) { return; } if (hitEntity instanceof Player) return; LivingEntity target = (LivingEntity) hitEntity; double gunDamage = getDamage(player, target); if (game != null && game.getDropManagement().isDropActive(MobDrop.INSTA_KILL)) gunDamage = 30000; // max health defined in server if (bodyPart == BodyPart.HEAD) { target.damage(gunDamage * getHeadshotMultiplier(), player); ParticleDisplayer.displayParticle(game, result.getHitPosition().toLocation(target.getWorld()), Particle.BLOCK_CRACK, 7, Material.REDSTONE_BLOCK.createBlockData()); track(player, getPointsPerHeadshot()); } else { target.damage(gunDamage, player); track(player, getPointsPerShot()); } target.setVelocity(ZERO); target.setNoDamageTicks(0); }