From 329f91fff885e2092265806cc9a5c14ad04c8151 Mon Sep 17 00:00:00 2001 From: Sobki Date: Sat, 15 Oct 2016 10:02:57 +1000 Subject: [PATCH] Core 1.9.0 changes to Healing Waters. Updated /b who staff list. (#606) * Core 1.9.0 changes to Healing Waters. Updated /b who staff list. * More HealingWaters changes & updated staff * Updated HealingWaters description --- .../projectkorra/projectkorra/PKListener.java | 8 + .../projectkorra/command/WhoCommand.java | 4 +- .../configuration/ConfigManager.java | 8 +- .../waterbending/HealingWaters.java | 350 ++++++++++++------ .../waterbending/WaterbendingManager.java | 1 - 5 files changed, 252 insertions(+), 119 deletions(-) diff --git a/src/com/projectkorra/projectkorra/PKListener.java b/src/com/projectkorra/projectkorra/PKListener.java index b8200130..66bef11a 100644 --- a/src/com/projectkorra/projectkorra/PKListener.java +++ b/src/com/projectkorra/projectkorra/PKListener.java @@ -153,6 +153,7 @@ import com.projectkorra.projectkorra.util.PassiveHandler; import com.projectkorra.projectkorra.util.TempArmor; import com.projectkorra.projectkorra.util.TempBlock; import com.projectkorra.projectkorra.waterbending.Bloodbending; +import com.projectkorra.projectkorra.waterbending.HealingWaters; import com.projectkorra.projectkorra.waterbending.IceBlast; import com.projectkorra.projectkorra.waterbending.IceSpikeBlast; import com.projectkorra.projectkorra.waterbending.OctopusForm; @@ -1267,6 +1268,9 @@ public class PKListener implements Listener { else if (abil.equalsIgnoreCase("WaterArms")) { new WaterArms(player); } + if (abil.equalsIgnoreCase("HealingWaters")) { + new HealingWaters(player); + } } if (coreAbil instanceof EarthAbility && bPlayer.isElementToggled(Element.EARTH) == true) { @@ -1490,6 +1494,10 @@ public class PKListener implements Listener { else if (abil.equalsIgnoreCase("Torrent")) { new Torrent(player); } + if (abil.equalsIgnoreCase("HealingWaters")) { + HealingWaters instance = CoreAbility.getAbility(player, HealingWaters.class); + instance.click(); + } } if (coreAbil instanceof EarthAbility && bPlayer.isElementToggled(Element.EARTH) == true) { diff --git a/src/com/projectkorra/projectkorra/command/WhoCommand.java b/src/com/projectkorra/projectkorra/command/WhoCommand.java index 22121455..79506db6 100644 --- a/src/com/projectkorra/projectkorra/command/WhoCommand.java +++ b/src/com/projectkorra/projectkorra/command/WhoCommand.java @@ -59,13 +59,15 @@ public class WhoCommand extends PKCommand { staff.put("679a6396-6a31-4898-8130-044f34bef743", ChatColor.DARK_PURPLE + "ProjectKorra Developer"); // savior67 staff.put("1c30007f-f8ef-4b4e-aff0-787aa1bc09a3", ChatColor.DARK_PURPLE + "ProjectKorra Developer"); // Sorin staff.put("dd578a4f-d35e-4fed-94db-9d5a627ff962", ChatColor.DARK_PURPLE + "ProjectKorra Developer"); // Sobki - staff.put("ed8c05af-eb43-4b71-9be3-c2ccca6c849a", ChatColor.DARK_PURPLE + "ProjectKorra Developer"); // Matan + staff.put("9636d66a-bff8-48e4-993e-68f0e7891c3b", ChatColor.DARK_PURPLE + "ProjectKorra Developer"); // runefist staff.put("623df34e-9cd4-438d-b07c-1905e1fc46b6", ChatColor.GREEN + "ProjectKorra Concept Designer"); // Loony staff.put("3c484e61-7876-46c0-98c9-88c7834dc96c", ChatColor.GREEN + "ProjectKorra Concept Designer"); // SamuraiSnowman (Zmeduna) staff.put("3d5bc713-ab8b-4125-b5ba-a1c1c2400b2c", ChatColor.GOLD + "ProjectKorra Community Moderator"); // Gold staff.put("38217173-8a32-4ba7-9fe1-dd4fed031a74", ChatColor.GOLD + "ProjectKorra Community Moderator"); // Easte + + staff.put("f2868ba3-e2fc-4731-8e36-56de2f3e6471", ChatColor.BLUE + "ProjectKorra Graphic Designer"); // paliate } @Override diff --git a/src/com/projectkorra/projectkorra/configuration/ConfigManager.java b/src/com/projectkorra/projectkorra/configuration/ConfigManager.java index 1ff63681..1a6fd61c 100644 --- a/src/com/projectkorra/projectkorra/configuration/ConfigManager.java +++ b/src/com/projectkorra/projectkorra/configuration/ConfigManager.java @@ -250,7 +250,7 @@ public class ConfigManager { config.addDefault("Abilities.Water.Bloodbending.Description", "This ability was made illegal for a reason. With this ability selected, sneak while " + "targetting something and you will bloodbend that target. Bloodbent targets cannot move, " + "bend or attack. You are free to control their actions by looking elsewhere - they will " + "be forced to move in that direction. Additionally, clicking while bloodbending will " + "launch that target off in the direction you're looking. " + "People who are capable of bloodbending are immune to your technique, and you are immune to theirs."); config.addDefault("Abilities.Water.Bloodbending.DeathMessage", "{victim} was destroyed by {attacker}'s {ability}"); config.addDefault("Abilities.Water.Bloodbending.HorizontalVelocityDeath","{victim} experienced kinetic damage by {attacker}'s {ability}"); - config.addDefault("Abilities.Water.HealingWaters.Description", "To use, the bender must be at least partially submerged in water. " + "If the user is not sneaking, this ability will automatically begin " + "working provided the user has it selected. If the user is sneaking, " + "he/she is channeling the healing to their target in front of them. " + "In order for this channel to be successful, the user and the target must " + "be at least partially submerged in water."); + config.addDefault("Abilities.Water.HealingWaters.Description", "To use, the bender must be at least partially submerged in water. " + "Once in the water, hold shift to begin using the ability. " + "This will default to healing the user. To heal somebody else, left click while looking at them. " + "This will channel the healing to their target in front of them. " + "In order for this channel to be successful, the user must remain in water, while the target is in reach of the caster."); config.addDefault("Abilities.Water.IceBlast.Description", "This ability offers a powerful ice utility for Waterbenders. It can be used to fire an explosive burst of ice at an opponent, spraying ice and snow around it. To use, simply tap sneak (Default: Shift) while targeting a block of ice to select it as a source. From there, you can just left click to send the blast off at your opponent."); config.addDefault("Abilities.Water.IceBlast.DeathMessage", "{victim} was shattered by {attacker}'s {ability}"); config.addDefault("Abilities.Water.IceSpike.Description", "This ability has many functions. Clicking while targetting ice, or an entity over some ice, " + "will raise a spike of ice up, damaging and slowing the target. Tapping sneak (shift) while" + " selecting a water source will select that source that can then be fired with a click. Firing" + " this will launch a spike of ice at your target, dealing a bit of damage and slowing the target. " + "If you sneak (shift) while not selecting a source, many ice spikes will erupt from around you, " + "damaging and slowing those targets."); @@ -618,11 +618,13 @@ public class ConfigManager { config.addDefault("Abilities.Water.Bloodbending.CanBloodbendOtherBloodbenders", false); config.addDefault("Abilities.Water.HealingWaters.Enabled", true); - config.addDefault("Abilities.Water.HealingWaters.ShiftRequired", true); - config.addDefault("Abilities.Water.HealingWaters.Radius", 5); + config.addDefault("Abilities.Water.HealingWaters.Cooldown", 0); + config.addDefault("Abilities.Water.HealingWaters.Range", 5); config.addDefault("Abilities.Water.HealingWaters.Interval", 750); + config.addDefault("Abilities.Water.HealingWaters.ChargeTime", 1000); config.addDefault("Abilities.Water.HealingWaters.Power", 1); config.addDefault("Abilities.Water.HealingWaters.Duration", 70); + config.addDefault("Abilities.Water.HealingWaters.EnableParticles", true); config.addDefault("Abilities.Water.IceBlast.Enabled", true); config.addDefault("Abilities.Water.IceBlast.Damage", 3); diff --git a/src/com/projectkorra/projectkorra/waterbending/HealingWaters.java b/src/com/projectkorra/projectkorra/waterbending/HealingWaters.java index e8040cd6..5b7d7d4a 100644 --- a/src/com/projectkorra/projectkorra/waterbending/HealingWaters.java +++ b/src/com/projectkorra/projectkorra/waterbending/HealingWaters.java @@ -1,14 +1,5 @@ package com.projectkorra.projectkorra.waterbending; -import com.projectkorra.projectkorra.BendingPlayer; -import com.projectkorra.projectkorra.GeneralMethods; -import com.projectkorra.projectkorra.ability.AirAbility; -import com.projectkorra.projectkorra.ability.HealingAbility; -import com.projectkorra.projectkorra.ability.WaterAbility; -import com.projectkorra.projectkorra.chiblocking.Smokescreen; -import com.projectkorra.projectkorra.util.TempBlock; - -import org.bukkit.Bukkit; import org.bukkit.Location; import org.bukkit.block.Block; import org.bukkit.entity.Entity; @@ -16,56 +7,144 @@ import org.bukkit.entity.LivingEntity; import org.bukkit.entity.Player; import org.bukkit.potion.PotionEffect; import org.bukkit.potion.PotionEffectType; +import org.bukkit.util.Vector; + +import com.projectkorra.projectkorra.GeneralMethods; +import com.projectkorra.projectkorra.ability.AirAbility; +import com.projectkorra.projectkorra.ability.HealingAbility; +import com.projectkorra.projectkorra.ability.WaterAbility; +import com.projectkorra.projectkorra.chiblocking.Smokescreen; +import com.projectkorra.projectkorra.util.TempBlock; public class HealingWaters extends HealingAbility { - - private static long time = 0; + // Configurable Variables + + private long cooldown; + private double range; + private long interval; + private long chargeTime; + private int power; + private int duration; + private boolean enableParticles; + + // Instance related and predefined variables. + + private Player player; + private LivingEntity target; + private Location origin; + private Location location; + private long currTime; + private int pstage; + private int tstage1; + private int tstage2; + private boolean healing = false; + private boolean healingSelf = false; + private boolean charged = false; + private String hex; + public HealingWaters(Player player) { super(player); + + if (!bPlayer.canBend(this)) { + remove(); + return; + } + + setFields(); + this.player = player; + this.origin = player.getLocation().clone().add(player.getLocation().getDirection()).add(0, 1.5, 0); + this.location = origin.clone(); + this.currTime = System.currentTimeMillis(); + this.pstage = 0; + this.tstage1 = 0; + this.tstage2 = 18; + + start(); } - public static void heal() { - if (System.currentTimeMillis() - time >= getInterval()) { - time = System.currentTimeMillis(); - for (Player player : Bukkit.getServer().getOnlinePlayers()) { - BendingPlayer bPlayer = BendingPlayer.getBendingPlayer(player); - if (bPlayer != null && bPlayer.canBend(getAbility("HealingWaters"))) { - heal(player); - } - } - } - } - - private static void heal(Player player) { - if (inWater(player)) { - if ((getShiftRequired() == true && player.isSneaking()) || getShiftRequired() == false) { - Entity target = GeneralMethods.getTargetedEntity(player, getRadius()); - if (target == null || !(target instanceof LivingEntity)) { - giveHP(player); - } else { - giveHPToEntity((LivingEntity) target); - } - } else if (getShiftRequired() == true && !player.isSneaking()) { - return; - } - } - } - - private static void giveHPToEntity(LivingEntity le) { - if (!le.isDead() && le.getHealth() < le.getMaxHealth()) { - applyHealingToEntity(le); - } - for (PotionEffect effect : le.getActivePotionEffects()) { - if (WaterAbility.isNegativeEffect(effect.getType())) { - le.removePotionEffect(effect.getType()); - } - } + public void setFields() { + + cooldown = getConfig().getLong("Abilities.Water.HealingWaters.Cooldown"); + range = getConfig().getDouble("Abilities.Water.HealingWaters.Range"); + interval = getConfig().getLong("Abilities.Water.HealingWaters.Interval"); + chargeTime = getConfig().getLong("Abilities.Water.HealingWaters.ChargeTime"); + power = getConfig().getInt("Abilities.Water.HealingWaters.Power"); + duration = getConfig().getInt("Abilities.Water.HealingWaters.Duration"); + enableParticles = getConfig().getBoolean("Abilities.Water.HealingWaters.EnableParticles"); + hex = "00ffff"; } - private static void giveHP(Player player) { - if (!player.isDead() && player.getHealth() < 20) { + @Override + public void progress() { + + if (!bPlayer.canBend(this)) { + remove(); + return; + } + + if (!player.isSneaking()) { + remove(); + return; + } + + if (!inWater(player)) { + remove(); + return; + } + + // If ability is is charged, set charged = true. If not, play charging particles. + if (System.currentTimeMillis() >= startTime + chargeTime) { + if (!charged) { + this.charged = true; + } + } else { + GeneralMethods.displayColoredParticle(origin, hex); + } + + // If the ability is charged, try healing. + if (charged) { + + // Try to heal themselves/target with 'interval' millisecond intervals. + if (System.currentTimeMillis() - currTime >= interval) { + + heal(player); + currTime = System.currentTimeMillis(); + } + + // Display healing particles. + if (healing && enableParticles) { + if (healingSelf) { + displayHealingParticlesSelf(); + } else { + displayHealingParticlesOther(); + } + } + } + } + + public void click() { + Entity target = GeneralMethods.getTargetedEntity(player, range); + if (target != null && target instanceof LivingEntity) { + this.target = (LivingEntity) target; + } + } + + private void heal(Player player) { + Entity target = GeneralMethods.getTargetedEntity(player, range); + if (target != null && this.target != null && target instanceof LivingEntity && this.target.getEntityId() == target.getEntityId()) { + giveHP(this.target); + } else { + giveHP(player); + this.target = null; + } + } + + private void giveHP(Player player) { + if (!player.isDead() && player.getHealth() < player.getMaxHealth()) { applyHealing(player); + } else { + healing = false; } for (PotionEffect effect : player.getActivePotionEffects()) { @@ -77,75 +156,103 @@ public class HealingWaters extends HealingAbility { } } } - - private static boolean inWater(Entity entity) { - Block block = entity.getLocation().getBlock(); - return isWater(block) && !TempBlock.isTempBlock(block); - } - - private static void applyHealing(Player player) { - if (!GeneralMethods.isRegionProtectedFromBuild(player, "HealingWaters", player.getLocation())) { - if (player.getHealth() < player.getMaxHealth()) { - player.addPotionEffect(new PotionEffect(PotionEffectType.REGENERATION, getDuration(), getPower())); - AirAbility.breakBreathbendingHold(player); + + private void giveHP(LivingEntity livingEntity) { + if (!livingEntity.isDead() && livingEntity.getHealth() < livingEntity.getMaxHealth()) { + applyHealing(livingEntity); + } else { + healing = false; + } + + for (PotionEffect effect : livingEntity.getActivePotionEffects()) { + if (WaterAbility.isNegativeEffect(effect.getType())) { + livingEntity.removePotionEffect(effect.getType()); } } } - - private static void applyHealingToEntity(LivingEntity le) { - if (le.getHealth() < le.getMaxHealth()) { - le.addPotionEffect(new PotionEffect(PotionEffectType.REGENERATION, getDuration(), 1)); - AirAbility.breakBreathbendingHold(le); + + private void applyHealing(Player player) { + if (!GeneralMethods.isRegionProtectedFromBuild(player, "HealingWaters", player.getLocation())) { + player.addPotionEffect(new PotionEffect(PotionEffectType.REGENERATION, duration, power)); + AirAbility.breakBreathbendingHold(player); + healing = true; + healingSelf = true; + } + } + + private void applyHealing(LivingEntity livingEntity) { + if (livingEntity.getHealth() < livingEntity.getMaxHealth()) { + livingEntity.addPotionEffect(new PotionEffect(PotionEffectType.REGENERATION, duration, 1)); + AirAbility.breakBreathbendingHold(livingEntity); + this.target = livingEntity; + healing = true; + healingSelf = false; + } + } + + private boolean inWater(Player player) { + Block block = player.getLocation().getBlock(); + return isWater(block) && !TempBlock.isTempBlock(block); + } + + public void displayHealingParticlesSelf() { + + Location centre = player.getLocation().clone().add(0, 1, 0); + double increment = (2 * Math.PI) / 36; + double angle = pstage * increment; + double x = centre.getX() + (0.75 * Math.cos(angle)); + double z = centre.getZ() + (0.75 * Math.sin(angle)); + GeneralMethods.displayColoredParticle(new Location(centre.getWorld(), x, centre.getY(), z), hex); + + if (pstage >= 36) { + pstage = 0; + } + pstage++; + } + + public void displayHealingParticlesOther() { + + if (target != null) { + + Location centre = target.getLocation().clone().add(0, 1, 0); + double increment = (2 * Math.PI) / 36; + double angle1 = tstage1 * increment; + double angle2 = tstage2 * increment; + double x1 = centre.getX() + (0.75 * Math.cos(angle1)); + double z1 = centre.getZ() + (0.75 * Math.sin(angle1)); + double x2 = centre.getX() + (0.75 * Math.cos(angle2)); + double z2 = centre.getZ() + (0.75 * Math.sin(angle2)); + + GeneralMethods.displayColoredParticle(new Location(centre.getWorld(), x1, centre.getY() + (0.75 * Math.cos(angle1)), z1), hex); + GeneralMethods.displayColoredParticle(new Location(centre.getWorld(), x2, centre.getY() + (0.75 * -Math.cos(angle2)), z2), hex); + + if (tstage1 >= 36) { + tstage1 = 0; + } + tstage1++; + + if (tstage2 >= 36) { + tstage2 = 0; + } + tstage2++; + + double factor = 0.2; + + Location targetLoc = target.getLocation().clone().add(0, 1, 0); + double distance = origin.distance(targetLoc); + Vector vec = new Vector( + targetLoc.getX() - location.getX(), + targetLoc.getY() - location.getY(), + targetLoc.getZ() - location.getZ()).normalize(); + + if (origin.distance(location) < distance) { + location = location.clone().add(vec.clone().multiply(factor)); + GeneralMethods.displayColoredParticle(location, hex); + } + } } - public static long getTime() { - return time; - } - - public static void setTime(long time) { - HealingWaters.time = time; - } - - public static boolean getShiftRequired() { - return getConfig().getBoolean("Abilities.Water.HealingWaters.ShiftRequired"); - } - - public static double getRadius() { - return getConfig().getDouble("Abilities.Water.HealingWaters.Radius"); - } - - public static long getInterval() { - return getConfig().getLong("Abilities.Water.HealingWaters.Interval"); - } - - public static int getPower() { - return getConfig().getInt("Abilities.Water.HealingWaters.Power"); - } - - public static int getDuration() { - return getConfig().getInt("Abilities.Water.HealingWaters.Duration"); - } - - @Override - public String getName() { - return "HealingWaters"; - } - - @Override - public void progress() { - } - - @Override - public Location getLocation() { - return null; - } - - @Override - public long getCooldown() { - return 0; - } - @Override public boolean isSneakAbility() { return true; @@ -155,5 +262,20 @@ public class HealingWaters extends HealingAbility { public boolean isHarmlessAbility() { return true; } - -} + + @Override + public long getCooldown() { + return cooldown; + } + + @Override + public String getName() { + return "HealingWaters"; + } + + @Override + public Location getLocation() { + return location; + } + +} \ No newline at end of file diff --git a/src/com/projectkorra/projectkorra/waterbending/WaterbendingManager.java b/src/com/projectkorra/projectkorra/waterbending/WaterbendingManager.java index 9707ee88..1cf3c0db 100644 --- a/src/com/projectkorra/projectkorra/waterbending/WaterbendingManager.java +++ b/src/com/projectkorra/projectkorra/waterbending/WaterbendingManager.java @@ -14,7 +14,6 @@ public class WaterbendingManager implements Runnable { public void run() { WaterPassive.handlePassive(); PhaseChangeFreeze.handleFrozenBlocks(); - HealingWaters.heal(); Torrent.progressAllCleanup(); WaterArms.progressAllCleanup(); }