package de.flo56958.minetinker.modifiers.types; import de.flo56958.minetinker.MineTinker; import de.flo56958.minetinker.data.ToolType; import de.flo56958.minetinker.events.MTEntityDamageByEntityEvent; import de.flo56958.minetinker.events.MTProjectileHitEvent; import de.flo56958.minetinker.modifiers.Modifier; import de.flo56958.minetinker.utils.ChatWriter; import de.flo56958.minetinker.utils.ConfigurationManager; import de.flo56958.minetinker.utils.LanguageManager; import org.bukkit.Color; import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.Sound; import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.entity.*; import org.bukkit.event.EventHandler; import org.bukkit.event.Listener; import org.bukkit.event.entity.EntityDamageEvent; import org.bukkit.inventory.ItemStack; import org.bukkit.potion.PotionEffect; import org.bukkit.potion.PotionEffectType; import org.bukkit.util.Vector; import java.io.File; import java.util.Arrays; import java.util.HashMap; import java.util.List; import java.util.Map; public class Ender extends Modifier implements Listener { private static Ender instance; private boolean hasSound; private boolean hasParticles; private boolean giveNauseaOnUse; private int nauseaDuration; private boolean giveBlindnessOnUse; private int blindnessDuration; private Ender() { super(MineTinker.getPlugin()); customModelData = 10_009; } public static Ender instance() { synchronized (Ender.class) { if (instance == null) { instance = new Ender(); } } return instance; } @Override public String getKey() { return "Ender"; } @Override public List<ToolType> getAllowedTools() { return Arrays.asList(ToolType.BOW, ToolType.CROSSBOW, ToolType.TRIDENT); } @Override public void reload() { FileConfiguration config = getConfig(); config.options().copyDefaults(true); config.addDefault("Allowed", true); config.addDefault("Color", "%DARK_GREEN%"); config.addDefault("MaxLevel", 2); config.addDefault("SlotCost", 2); config.addDefault("Sound", true); //#Enderman-Teleport-Sound config.addDefault("Particles", true); config.addDefault("GiveNauseaOnUse", true); config.addDefault("NauseaDuration", 5); //seconds config.addDefault("GiveBlindnessOnUse", true); config.addDefault("BlindnessDuration", 3); //seconds config.addDefault("EnchantCost", 10); config.addDefault("Enchantable", false); config.addDefault("Recipe.Enabled", true); config.addDefault("Recipe.Top", "PPP"); config.addDefault("Recipe.Middle", "PEP"); config.addDefault("Recipe.Bottom", "PPP"); Map<String, String> recipeMaterials = new HashMap<>(); recipeMaterials.put("P", Material.ENDER_PEARL.name()); recipeMaterials.put("E", Material.ENDER_EYE.name()); config.addDefault("Recipe.Materials", recipeMaterials); ConfigurationManager.saveConfig(config); ConfigurationManager.loadConfig("Modifiers" + File.separator, getFileName()); init(Material.ENDER_EYE); this.hasSound = config.getBoolean("Sound", true); this.hasParticles = config.getBoolean("Particles", true); this.giveNauseaOnUse = config.getBoolean("GiveNauseaOnUse", true); this.nauseaDuration = config.getInt("NauseaDuration", 5) * 20; this.giveBlindnessOnUse = config.getBoolean("GiveBlindnessOnUse", true); this.blindnessDuration = config.getInt("BlindnessDuration", 3) * 20; } /** * The Effect for the ProjectileHitEvent * * @param event the Event */ @EventHandler public void effect(MTProjectileHitEvent event) { Player player = event.getPlayer(); ItemStack tool = event.getTool(); if (!player.hasPermission("minetinker.modifiers.ender.use")) { return; } if (!modManager.hasMod(tool, this)) { return; } if (!player.isSneaking()) { return; } Location loc = event.getEvent().getEntity().getLocation().clone(); //Location of the Arrow Location oldLoc = player.getLocation(); player.teleport(new Location(loc.getWorld(), loc.getX(), loc.getY(), loc.getZ(), player.getLocation().getYaw(), player.getLocation().getPitch()).add(0, 1, 0)); if (this.hasSound) { player.getWorld().playSound(player.getLocation(), Sound.ENTITY_ENDERMAN_TELEPORT, 1.0F, 0.3F); } spawnParticles(player, oldLoc); if (this.giveNauseaOnUse) { player.removePotionEffect(PotionEffectType.CONFUSION); player.addPotionEffect(new PotionEffect(PotionEffectType.CONFUSION, this.nauseaDuration, 0, false, false)); } if (this.giveBlindnessOnUse) { player.removePotionEffect(PotionEffectType.BLINDNESS); player.addPotionEffect(new PotionEffect(PotionEffectType.BLINDNESS, this.blindnessDuration, 0, false, false)); } ChatWriter.logModifier(player, event, this, tool, String.format("Location: (%s: %d/%d/%d -> %d/%d/%d)", loc.getWorld().getName(), oldLoc.getBlockX(), oldLoc.getBlockY(), oldLoc.getBlockZ(), loc.getBlockX(), loc.getBlockY(), loc.getBlockZ())); } /** * The Effect for the EntityDamageByEntityEvent * * @param event */ @EventHandler(ignoreCancelled = true) public void effect(MTEntityDamageByEntityEvent event) { Player player = event.getPlayer(); Entity entity = event.getEvent().getEntity(); if (!player.isSneaking()) { return; } //The Damage cause was not the arrow and therefore Ender should not be triggered if (!event.getEvent().getCause().equals(EntityDamageEvent.DamageCause.PROJECTILE)) { return; } if (player.equals(event.getEvent().getEntity())) { return; } if (!player.hasPermission("minetinker.modifiers.ender.use")) { return; } ItemStack tool = event.getTool(); if (!modManager.hasMod(tool, this)) { return; //No check needed, as Ender can only be applied on the Bow } if (modManager.getModLevel(tool, this) < 2) { return; } if (entity instanceof Player) { //Save Players from getting teleported if (entity.hasPermission("minetinker.modifiers.ender.prohibittp")) { ChatWriter.sendActionBar(player, LanguageManager.getString("Modifier.Ender.TeleportationProhibited", player)); ChatWriter.logModifier(player, event, this, tool, "Teleport denied"); return; } } Location loc = entity.getLocation().clone(); Location oldLoc = player.getLocation(); entity.teleport(oldLoc); spawnParticles(player, loc); player.teleport(loc); if (this.hasSound) { player.getWorld().playSound(player.getLocation(), Sound.ENTITY_ENDERMAN_TELEPORT, 1.0F, 0.3F); //Sound at Players position player.getWorld().playSound(event.getEvent().getEntity().getLocation(), Sound.ENTITY_ENDERMAN_TELEPORT, 1.0F, 0.3F); //Sound at Entity's position } if (this.giveNauseaOnUse) { player.removePotionEffect(PotionEffectType.CONFUSION); player.addPotionEffect(new PotionEffect(PotionEffectType.CONFUSION, this.nauseaDuration, 0, false, false)); if (entity instanceof LivingEntity) { ((LivingEntity) entity).removePotionEffect(PotionEffectType.CONFUSION); ((LivingEntity) entity).addPotionEffect(new PotionEffect(PotionEffectType.CONFUSION, this.nauseaDuration, 0, false, false)); } } if (this.giveBlindnessOnUse) { player.removePotionEffect(PotionEffectType.BLINDNESS); player.addPotionEffect(new PotionEffect(PotionEffectType.BLINDNESS, this.blindnessDuration, 0, false, false)); if (entity instanceof LivingEntity) { ((LivingEntity) entity).removePotionEffect(PotionEffectType.BLINDNESS); ((LivingEntity) entity).addPotionEffect(new PotionEffect(PotionEffectType.BLINDNESS, this.blindnessDuration, 0, false, false)); } } ChatWriter.logModifier(player, event, this, tool, "Entity(" + entity.getType().toString() + ")", String.format("Location: (%s: %d/%d/%d <-> %d/%d/%d)", loc.getWorld().getName(), oldLoc.getBlockX(), oldLoc.getBlockY(), oldLoc.getBlockZ(), loc.getBlockX(), loc.getBlockY(), loc.getBlockZ())); } private void spawnParticles(Player player, Location oldLoc) { if (this.hasParticles) { AreaEffectCloud cloud = (AreaEffectCloud) player.getWorld().spawnEntity(player.getLocation(), EntityType.AREA_EFFECT_CLOUD); cloud.setVelocity(new Vector(0, 1, 0)); cloud.setRadius(0.5f); cloud.setDuration(5); cloud.setColor(Color.GREEN); cloud.getLocation().setYaw(90); AreaEffectCloud cloud2 = (AreaEffectCloud) player.getWorld().spawnEntity(oldLoc, EntityType.AREA_EFFECT_CLOUD); cloud2.setVelocity(new Vector(0, 1, 0)); cloud2.setRadius(0.5f); cloud2.setDuration(5); cloud2.setColor(Color.GREEN); cloud2.getLocation().setPitch(90); } } }