Committing to maintain remote branch

This commit is contained in:
jayoevans 2019-11-23 17:09:50 +10:00
parent c6d56bd9ce
commit 03844d5bab
16 changed files with 1815 additions and 973 deletions

View file

@ -14,38 +14,22 @@ import com.griefcraft.model.Protection;
import com.palmergames.bukkit.towny.Towny;
import com.palmergames.bukkit.towny.TownyMessaging;
import com.palmergames.bukkit.towny.TownySettings;
import com.palmergames.bukkit.towny.object.Coord;
import com.palmergames.bukkit.towny.object.PlayerCache;
import com.palmergames.bukkit.towny.object.*;
import com.palmergames.bukkit.towny.object.PlayerCache.TownBlockStatus;
import com.palmergames.bukkit.towny.object.TownyPermission;
import com.palmergames.bukkit.towny.object.TownyUniverse;
import com.palmergames.bukkit.towny.object.TownyWorld;
import com.palmergames.bukkit.towny.object.WorldCoord;
import com.palmergames.bukkit.towny.utils.PlayerCacheUtil;
import com.palmergames.bukkit.towny.war.flagwar.TownyWar;
import com.palmergames.bukkit.towny.war.flagwar.TownyWarConfig;
import com.projectkorra.projectkorra.ability.Ability;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.ability.AbilityHandlerManager;
import com.projectkorra.projectkorra.ability.AbilityManager;
import com.projectkorra.projectkorra.ability.api.AddonAbility;
import com.projectkorra.projectkorra.ability.CoreAbility;
import com.projectkorra.projectkorra.ability.legacy.EarthAbility;
import com.projectkorra.projectkorra.ability.bind.AbilityBindManager;
import com.projectkorra.projectkorra.ability.legacy.ElementalAbility;
import com.projectkorra.projectkorra.ability.legacy.FireAbility;
import com.projectkorra.projectkorra.ability.api.PassiveAbility;
import com.projectkorra.projectkorra.ability.legacy.WaterAbility;
import com.projectkorra.projectkorra.ability.info.AbilityInfo;
import com.projectkorra.projectkorra.ability.util.Collision;
import com.projectkorra.projectkorra.ability.util.CollisionInitializer;
import com.projectkorra.projectkorra.ability.util.CollisionManager;
import com.projectkorra.projectkorra.ability.util.ComboManager;
import com.projectkorra.projectkorra.ability.util.ComboManager.AbilityInformation;
import com.projectkorra.projectkorra.ability.util.MultiAbilityManager;
import com.projectkorra.projectkorra.ability.util.PassiveManager;
import com.projectkorra.projectkorra.airbending.AirBlast;
import com.projectkorra.projectkorra.airbending.AirShield;
import com.projectkorra.projectkorra.airbending.AirSpout;
import com.projectkorra.projectkorra.airbending.AirSuction;
import com.projectkorra.projectkorra.airbending.AirSwipe;
import com.projectkorra.projectkorra.airbending.*;
import com.projectkorra.projectkorra.configuration.ConfigManager;
import com.projectkorra.projectkorra.configuration.configs.properties.GeneralPropertiesConfig;
import com.projectkorra.projectkorra.earthbending.EarthBlast;
@ -55,18 +39,11 @@ import com.projectkorra.projectkorra.firebending.FireBlast;
import com.projectkorra.projectkorra.firebending.FireShield;
import com.projectkorra.projectkorra.firebending.combustion.Combustion;
import com.projectkorra.projectkorra.module.ModuleManager;
import com.projectkorra.projectkorra.object.Preset;
import com.projectkorra.projectkorra.player.BendingPlayer;
import com.projectkorra.projectkorra.player.BendingPlayerManager;
import com.projectkorra.projectkorra.storage.DBConnection;
import com.projectkorra.projectkorra.util.ActionBar;
import com.projectkorra.projectkorra.util.BlockCacheElement;
import com.projectkorra.projectkorra.util.ColoredParticle;
import com.projectkorra.projectkorra.util.MovementHandler;
import com.projectkorra.projectkorra.util.ParticleEffect;
import com.projectkorra.projectkorra.util.ReflectionHandler;
import com.projectkorra.projectkorra.util.*;
import com.projectkorra.projectkorra.util.ReflectionHandler.PackageType;
import com.projectkorra.projectkorra.util.TempArmor;
import com.projectkorra.projectkorra.util.TempArmorStand;
import com.projectkorra.projectkorra.util.TempBlock;
import com.projectkorra.projectkorra.waterbending.WaterManipulation;
import com.projectkorra.projectkorra.waterbending.WaterSpout;
import com.sk89q.worldedit.bukkit.BukkitAdapter;
@ -89,57 +66,27 @@ import net.md_5.bungee.api.chat.ClickEvent;
import net.md_5.bungee.api.chat.ComponentBuilder;
import net.md_5.bungee.api.chat.HoverEvent;
import net.md_5.bungee.api.chat.TextComponent;
import org.bukkit.Bukkit;
import org.bukkit.ChatColor;
import org.bukkit.Color;
import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.*;
import org.bukkit.block.Block;
import org.bukkit.block.BlockFace;
import org.bukkit.block.BlockState;
import org.bukkit.block.data.BlockData;
import org.bukkit.block.data.Levelled;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Entity;
import org.bukkit.entity.FallingBlock;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player;
import org.bukkit.entity.TNTPrimed;
import org.bukkit.entity.*;
import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.MainHand;
import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin;
import org.bukkit.scheduler.BukkitRunnable;
import org.bukkit.util.Vector;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.io.*;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.UUID;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
@SuppressWarnings("rawtypes")
@ -1109,7 +1056,7 @@ public class GeneralMethods {
}
public static boolean isRegionProtectedFromBuild(final Ability ability, final Location loc) {
return isRegionProtectedFromBuild(ability.getPlayer(), ability.getName(), loc);
return isRegionProtectedFromBuild(ability.getPlayer(), ability.getHandler().getName(), loc);
}
public static boolean isRegionProtectedFromBuild(final Player player, final Location loc) {
@ -1120,11 +1067,11 @@ public class GeneralMethods {
boolean isIgnite = false;
boolean isExplosive = false;
boolean isHarmless = false;
final AbilityInfo abilityInfo = ModuleManager.getModule(AbilityManager.class).getAbilityInfo(abilityName);
if (abilityInfo != null) {
isIgnite = abilityInfo.isIgniteAbility();
isExplosive = abilityInfo.isExplosiveAbility();
isHarmless = abilityInfo.isHarmlessAbility();
final AbilityHandler abilityHandler = ModuleManager.getModule(AbilityHandlerManager.class).getHandler(abilityName);
if (abilityHandler != null) {
isIgnite = abilityHandler.isIgniteAbility();
isExplosive = abilityHandler.isExplosiveAbility();
isHarmless = abilityHandler.isHarmlessAbility();
}
if (abilityName == null && ConfigManager.getConfig(GeneralPropertiesConfig.class).RegionProtection.AllowHarmlessAbilities) {
@ -1433,7 +1380,7 @@ public class GeneralMethods {
final String entry = abilityManager.getAddonPlugins().get(i);
final String[] split = entry.split("::");
if (Bukkit.getServer().getPluginManager().isPluginEnabled(split[0])) {
abilityManager.registerPluginAbilities((JavaPlugin) Bukkit.getServer().getPluginManager().getPlugin(split[0]), split[1]);
// abilityManager.registerPluginAbilities((JavaPlugin) Bukkit.getServer().getPluginManager().getPlugin(split[0]), split[1]);
} else {
abilityManager.getAddonPlugins().remove(i);
}
@ -1451,41 +1398,50 @@ public class GeneralMethods {
}
}
public static void removeUnusableAbilities(final String player) {
public static void removeUnusableAbilities(final String playerName) {
final BendingPlayer bPlayer = BendingPlayer.getBendingPlayer(player);
if (bPlayer == null) {
Player player = Bukkit.getPlayer(playerName);
if (player == null) {
return;
}
BendingPlayer bendingPlayer = ModuleManager.getModule(BendingPlayerManager.class).getBendingPlayer(player);
if (bendingPlayer == null) {
return;
}
// Remove all active instances of abilities that will become unusable.
// We need to do this prior to filtering binds in case the player has a MultiAbility running.
for (final CoreAbility coreAbility : CoreAbility.getAbilities()) {
final CoreAbility playerAbility = CoreAbility.getAbility(bPlayer.getPlayer(), coreAbility.getClass());
if (playerAbility != null) {
if (playerAbility instanceof PassiveAbility && PassiveManager.hasPassive(bPlayer.getPlayer(), playerAbility)) {
for (final AbilityHandler abilityHandler : ModuleManager.getModule(AbilityHandlerManager.class).getHandlers()) {
final Ability ability = ModuleManager.getModule(AbilityManager.class).getAbility(player, abilityHandler.getAbility());
if (ability != null) {
/*
if (abilityHandler instanceof PassiveAbility && PassiveManager.hasPassive(bPlayer.getPlayer(), playerAbility)) {
// The player will be able to keep using the given PassiveAbility.
continue;
} else if (bPlayer.canBend(playerAbility)) {
} else */
if (bendingPlayer.canBend(abilityHandler)) {
// The player will still be able to use this given Ability, do not end it.
continue;
}
playerAbility.remove();
ability.remove();
}
}
// Remove all bound abilities that will become unusable.
String[] currentAbilities = bPlayer.getAbilities();
String[] currentAbilities = bendingPlayer.getAbilities();
String[] finalAbilities = new String[9];
for (int i = 0; i < 9; i++) {
if (bPlayer.canBind(CoreAbility.getAbility(currentAbilities[i]))) {
if (bendingPlayer.canBind(ModuleManager.getModule(AbilityHandlerManager.class).getHandler(currentAbilities[i]))) {
// The player will still be able to use this given Ability, do not remove it from their binds.
finalAbilities[i] = currentAbilities[i];
}
}
bPlayer.setAbilities(finalAbilities);
ModuleManager.getModule(AbilityBindManager.class).setAbilities(player, finalAbilities);
}
public static Vector rotateVectorAroundVector(final Vector axis, final Vector rotator, final double degrees) {
@ -1606,11 +1562,11 @@ public class GeneralMethods {
writeToDebug("====================");
final ArrayList<String> stockAbils = new ArrayList<String>();
final ArrayList<String> unofficialAbils = new ArrayList<String>();
for (final CoreAbility ability : CoreAbility.getAbilities()) {
if (ability.getClass().getPackage().getName().startsWith("com.projectkorra")) {
stockAbils.add(ability.getName());
for (final AbilityHandler abilityHandler : ModuleManager.getModule(AbilityHandlerManager.class).getHandlers()) {
if (abilityHandler.getClass().getPackage().getName().startsWith("com.projectkorra")) {
stockAbils.add(abilityHandler.getName());
} else {
unofficialAbils.add(ability.getName());
unofficialAbils.add(abilityHandler.getName());
}
}
if (!stockAbils.isEmpty()) {
@ -1657,9 +1613,9 @@ public class GeneralMethods {
writeToDebug("");
writeToDebug("CoreAbility Debugger");
writeToDebug("====================");
for (final String line : CoreAbility.getDebugString().split("\\n")) {
writeToDebug(line);
}
// for (final String line : CoreAbility.getDebugString().split("\\n")) {
// writeToDebug(line);
// }
}
@ -1792,25 +1748,25 @@ public class GeneralMethods {
}
public static void stopBending() {
for (final CoreAbility ability : CoreAbility.getAbilities()) {
if (ability instanceof AddonAbility) {
((AddonAbility) ability).stop();
}
}
CoreAbility.removeAll();
EarthAbility.stopBending();
WaterAbility.stopBending();
FireAbility.stopBending();
TempBlock.removeAll();
TempArmor.revertAll();
TempArmorStand.removeAll();
MovementHandler.resetAll();
MultiAbilityManager.removeAll();
if (!INVINCIBLE.isEmpty()) {
INVINCIBLE.clear();
}
// for (final CoreAbility ability : CoreAbility.getAbilities()) {
// if (ability instanceof AddonAbility) {
// ((AddonAbility) ability).stop();
// }
// }
//
// CoreAbility.removeAll();
// EarthAbility.stopBending();
// WaterAbility.stopBending();
// FireAbility.stopBending();
//
// TempBlock.removeAll();
// TempArmor.revertAll();
// TempArmorStand.removeAll();
// MovementHandler.resetAll();
// MultiAbilityManager.removeAll();
// if (!INVINCIBLE.isEmpty()) {
// INVINCIBLE.clear();
// }
}
public static void stopPlugin() {

File diff suppressed because it is too large Load diff

View file

@ -65,7 +65,6 @@ public abstract class Ability<Handler extends AbilityHandler> {
private final Map<String, Object> attributeValues = new HashMap<>();
private boolean started;
private boolean removed;
private boolean hidden;
private int id;
private long startTime;
private long startTick;
@ -364,7 +363,7 @@ public abstract class Ability<Handler extends AbilityHandler> {
Validate.notNull(value, "value cannot be null");
Validate.notNull(modificationType, "modifierMethod cannot be null");
Validate.notNull(priority, "priority cannot be null");
Validate.isTrue(ATTRIBUTE_FIELDS.containsKey(this.getClass()) && ATTRIBUTE_FIELDS.get(this.getClass()).containsKey(attribute), "Attribute " + attribute + " is not a defined Attribute for " + this.getName());
Validate.isTrue(ATTRIBUTE_FIELDS.containsKey(this.getClass()) && ATTRIBUTE_FIELDS.get(this.getClass()).containsKey(attribute), "Attribute " + attribute + " is not a defined Attribute for " + getHandler().getName());
if (!this.attributeModifiers.containsKey(attribute)) {
this.attributeModifiers.put(attribute, new HashMap<>());
}
@ -378,7 +377,7 @@ public abstract class Ability<Handler extends AbilityHandler> {
public Ability setAttribute(final String attribute, final Object value) {
Validate.notNull(attribute, "attribute cannot be null");
Validate.notNull(value, "value cannot be null");
Validate.isTrue(ATTRIBUTE_FIELDS.containsKey(this.getClass()) && ATTRIBUTE_FIELDS.get(this.getClass()).containsKey(attribute), "Attribute " + attribute + " is not a defined Attribute for " + this.getName());
Validate.isTrue(ATTRIBUTE_FIELDS.containsKey(this.getClass()) && ATTRIBUTE_FIELDS.get(this.getClass()).containsKey(attribute), "Attribute " + attribute + " is not a defined Attribute for " + getHandler().getName());
this.attributeValues.put(attribute, value);
return this;
}
@ -465,18 +464,6 @@ public abstract class Ability<Handler extends AbilityHandler> {
public abstract void progress();
public abstract boolean isSneakAbility();
public abstract boolean isHarmlessAbility();
public abstract boolean isIgniteAbility();
public abstract boolean isExplosiveAbility();
public abstract long getCooldown();
public abstract String getName();
public abstract Location getLocation();
public static double getDefaultCollisionRadius() {

View file

@ -1,20 +1,42 @@
package com.projectkorra.projectkorra.ability;
import com.projectkorra.projectkorra.GeneralMethods;
import com.projectkorra.projectkorra.configuration.ConfigManager;
import com.projectkorra.projectkorra.configuration.configs.abilities.AbilityConfig;
import com.projectkorra.projectkorra.configuration.configs.properties.EarthPropertiesConfig;
import com.projectkorra.projectkorra.configuration.configs.properties.WaterPropertiesConfig;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.player.BendingPlayer;
import org.bukkit.Material;
import org.bukkit.World;
import org.bukkit.block.Block;
import org.bukkit.block.data.BlockData;
import org.bukkit.block.data.Waterlogged;
import org.bukkit.entity.Player;
import org.bukkit.event.Listener;
import org.bukkit.potion.PotionEffectType;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;
import java.util.stream.Stream;
public abstract class AbilityHandler<T extends Ability, U extends AbilityConfig> implements Listener {
private static final PotionEffectType[] POSITIVE_EFFECTS = { PotionEffectType.ABSORPTION, PotionEffectType.DAMAGE_RESISTANCE, PotionEffectType.FAST_DIGGING, PotionEffectType.FIRE_RESISTANCE, PotionEffectType.HEAL, PotionEffectType.HEALTH_BOOST, PotionEffectType.INCREASE_DAMAGE, PotionEffectType.JUMP, PotionEffectType.NIGHT_VISION, PotionEffectType.REGENERATION, PotionEffectType.SATURATION, PotionEffectType.SPEED, PotionEffectType.WATER_BREATHING };
private static final PotionEffectType[] NEUTRAL_EFFECTS = { PotionEffectType.INVISIBILITY };
private static final PotionEffectType[] NEGATIVE_EFFECTS = { PotionEffectType.POISON, PotionEffectType.BLINDNESS, PotionEffectType.CONFUSION, PotionEffectType.HARM, PotionEffectType.HUNGER, PotionEffectType.SLOW, PotionEffectType.SLOW_DIGGING, PotionEffectType.WEAKNESS, PotionEffectType.WITHER };
private static final Set<Material> TRANSPARENT = Stream.of(Material.values()).filter(GeneralMethods::isTransparent).collect(Collectors.toSet());
private final Class<T> abilityClass;
private final Class<U> configClass;
private boolean hidden;
public AbilityHandler(Class<T> abilityClass, Class<U> configClass) {
this.abilityClass = abilityClass;
this.configClass = configClass;
@ -22,9 +44,9 @@ public abstract class AbilityHandler<T extends Ability, U extends AbilityConfig>
public T newInstance(Player player) {
try {
Constructor<T> constructor = abilityClass.getDeclaredConstructor(Player.class);
Constructor<T> constructor = abilityClass.getDeclaredConstructor(AbilityHandler.class, Player.class);
return constructor.newInstance(player);
return constructor.newInstance(this, player);
} catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) {
throw new AbilityException(e);
}
@ -64,14 +86,197 @@ public abstract class AbilityHandler<T extends Ability, U extends AbilityConfig>
public abstract Element getElement();
public abstract String getDescription();
public String getDescription() {
return getConfig().Description;
}
public abstract String getInstructions();
public String getInstructions() {
return getConfig().Instructions;
}
/**
* @return true if this is a hidden ability.
*/
public boolean isHidden() {
return this.hidden;
}
public void setHidden(boolean hidden)
{
this.hidden = hidden;
}
// public boolean isTransparent(final Player player, final Block block) {
// return isTransparent(player, this.getName(), block);
// }
public static boolean isTransparent(final Player player, final Block block) {
return isTransparent(player, null, block);
}
public static boolean isTransparent(final Player player, final String abilityName, final Block block) {
return Arrays.asList(getTransparentMaterials()).contains(block.getType()) && !GeneralMethods.isRegionProtectedFromBuild(player, abilityName, block.getLocation());
}
public List<Material> getEarthbendableBlocks() {
return Arrays.asList(ConfigManager.getConfig(EarthPropertiesConfig.class).EarthBlocks);
}
public static Material[] getTransparentMaterials() {
return TRANSPARENT.toArray(new Material[TRANSPARENT.size()]);
}
public static HashSet<Material> getTransparentMaterialSet() {
return new HashSet<>(TRANSPARENT);
}
public static boolean isAir(final Material material) {
return material == Material.AIR || material == Material.CAVE_AIR || material == Material.VOID_AIR;
}
public static boolean isDay(final World world) {
final long time = world.getTime();
if (world.getEnvironment() == World.Environment.NETHER || world.getEnvironment() == World.Environment.THE_END) {
return true;
}
if (time >= 23500 || time <= 12500) {
return true;
}
return false;
}
public static boolean isEarth(final Block block) {
return block != null ? isEarth(block.getType()) : false;
}
public static boolean isEarth(final Material material) {
return Stream.of(ConfigManager.getConfig(EarthPropertiesConfig.class).EarthBlocks).anyMatch(material::equals);
}
public static boolean isFullMoon(final World world) {
final double days = Math.ceil(world.getFullTime() / 24000) + 1;
final double phase = days % 8;
return phase == 0;
}
public static boolean isIce(final Block block) {
return block != null ? isIce(block.getType()) : false;
}
public static boolean isIce(final Material material) {
return Stream.of(ConfigManager.getConfig(WaterPropertiesConfig.class).IceBlocks).anyMatch(material::equals);
}
public static boolean isLava(final Block block) {
return block != null ? isLava(block.getType()) : false;
}
public static boolean isLava(final Material material) {
return material == Material.LAVA;
}
public static boolean isSnow(final Block block) {
return block != null ? isSnow(block.getType()) : false;
}
public static boolean isSnow(final Material material) {
return Stream.of(ConfigManager.getConfig(WaterPropertiesConfig.class).SnowBlocks).anyMatch(material::equals);
}
public static boolean isMeltable(final Block block) {
if (isIce(block) || isSnow(block)) {
return true;
}
return false;
}
public static boolean isMetal(final Block block) {
return block != null ? isMetal(block.getType()) : false;
}
public static boolean isMetal(final Material material) {
return Stream.of(ConfigManager.getConfig(EarthPropertiesConfig.class).MetalBlocks).anyMatch(material::equals);
}
public static boolean isNegativeEffect(final PotionEffectType effect) {
for (final PotionEffectType effect2 : NEGATIVE_EFFECTS) {
if (effect2.equals(effect)) {
return true;
}
}
return false;
}
public static boolean isNeutralEffect(final PotionEffectType effect) {
for (final PotionEffectType effect2 : NEUTRAL_EFFECTS) {
if (effect2.equals(effect)) {
return true;
}
}
return false;
}
public static boolean isNight(final World world) {
if (world.getEnvironment() == World.Environment.NETHER || world.getEnvironment() == World.Environment.THE_END) {
return false;
}
final long time = world.getTime();
if (time >= 12950 && time <= 23050) {
return true;
}
return false;
}
public static boolean isPlant(final Block block) {
return block != null ? isPlant(block.getType()) : false;
}
public static boolean isPlant(final Material material) {
return Stream.of(ConfigManager.getConfig(WaterPropertiesConfig.class).PlantBlocks).anyMatch(material::equals);
}
public static boolean isPositiveEffect(final PotionEffectType effect) {
for (final PotionEffectType effect2 : POSITIVE_EFFECTS) {
if (effect2.equals(effect)) {
return true;
}
}
return false;
}
public static boolean isSand(final Block block) {
return block != null ? isSand(block.getType()) : false;
}
public static boolean isSand(final Material material) {
return Stream.of(ConfigManager.getConfig(EarthPropertiesConfig.class).SandBlocks).anyMatch(material::equals);
}
public static boolean isWater(final Block block) {
if (block == null) {
return false;
} else if (isWater(block.getType())) {
return true;
} else {
return isWater(block.getBlockData());
}
}
public static boolean isWater(final BlockData data) {
return (data instanceof Waterlogged) ? ((Waterlogged) data).isWaterlogged() : isWater(data.getMaterial());
}
public static boolean isWater(final Material material) {
return Stream.of(ConfigManager.getConfig(WaterPropertiesConfig.class).IceBlocks).anyMatch(material::equals);
}
}

View file

@ -0,0 +1,126 @@
package com.projectkorra.projectkorra.ability;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipe;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipeConfig;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipeHandler;
import com.projectkorra.projectkorra.ability.api.AddonAbility;
import com.projectkorra.projectkorra.ability.api.ComboAbility;
import com.projectkorra.projectkorra.ability.api.MultiAbility;
import com.projectkorra.projectkorra.ability.api.PassiveAbility;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.element.SubElement;
import com.projectkorra.projectkorra.module.Module;
import com.projectkorra.projectkorra.util.MultiKeyMap;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
public class AbilityHandlerManager extends Module {
private final ComboAbilityManager comboAbilityManager;
private final MultiAbilityManager multiAbilityManager;
private final PassiveAbilityManager passiveAbilityManager;
private final MultiKeyMap<String, AbilityHandler> handlerMap = new MultiKeyMap<>();
private AbilityHandlerManager() {
super("Ability Handler");
this.comboAbilityManager = module(ComboAbilityManager.class);
this.multiAbilityManager = module(MultiAbilityManager.class);
this.passiveAbilityManager = module(PassiveAbilityManager.class);
registerAbilities();
}
/**
* Scans and loads plugin CoreAbilities, and Addon CoreAbilities that are
* located in a Jar file inside of the /ProjectKorra/Abilities/ folder.
*/
public void registerAbilities() {
this.handlerMap.clear();
// registerPluginAbilities(getPlugin(), "com.projectkorra");
// registerAddonAbilities("Abilities");
registerAbility(new AirSwipeHandler(AirSwipe.class, AirSwipeConfig.class));
}
private <T extends AbilityHandler> void registerAbility(T abilityHandler) throws AbilityException {
if (abilityHandler == null) {
throw new AbilityException("abilityHandler is null");
}
String abilityName = abilityHandler.getName();
if (abilityName == null) {
throw new AbilityException("Ability " + abilityHandler.getClass().getName() + " has no name");
}
if (!abilityHandler.getConfig().Enabled) {
getPlugin().getLogger().info(abilityName + " is disabled");
return;
}
if (abilityHandler instanceof AddonAbility) {
((AddonAbility) abilityHandler).load();
}
if (abilityHandler instanceof ComboAbility) {
ComboAbility comboAbility = (ComboAbility) abilityHandler;
if (comboAbility.getCombination() == null || comboAbility.getCombination().size() < 2) {
getPlugin().getLogger().info(abilityName + " has no combination");
return;
}
this.comboAbilityManager.registerAbility(abilityHandler);
return;
}
if (abilityHandler instanceof MultiAbility) {
this.multiAbilityManager.registerAbility(abilityHandler);
return;
}
if (abilityHandler instanceof PassiveAbility) {
PassiveAbility passiveAbility = (PassiveAbility) abilityHandler;
abilityHandler.setHidden(true);
this.passiveAbilityManager.registerAbility(abilityHandler);
return;
}
this.handlerMap.put(abilityName, abilityHandler);
}
public AbilityHandler getHandler(String abilityName) {
return this.handlerMap.get(abilityName);
}
public AbilityHandler getHandler(Class<? extends AbilityHandler> handlerClass) {
return this.handlerMap.get(handlerClass);
}
public List<AbilityHandler> getHandlers(Element element) {
return this.handlerMap.values().stream()
.filter(ability ->
{
if (ability.getElement().equals(element)) {
return true;
}
if (ability.getElement() instanceof SubElement) {
return ((SubElement) ability.getElement()).getParent().equals(element);
}
return false;
})
.collect(Collectors.toList());
}
public List<AbilityHandler> getHandlers() {
return new ArrayList<>(this.handlerMap.values());
}
}

View file

@ -2,14 +2,15 @@ package com.projectkorra.projectkorra.ability;
import co.aikar.timings.lib.MCTiming;
import com.projectkorra.projectkorra.ProjectKorra;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipe;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipeConfig;
import com.projectkorra.projectkorra.ability.abilities.air.airswipe.AirSwipeHandler;
import com.projectkorra.projectkorra.ability.api.AddonAbility;
import com.projectkorra.projectkorra.ability.api.ComboAbility;
import com.projectkorra.projectkorra.ability.api.MultiAbility;
import com.projectkorra.projectkorra.ability.api.PassiveAbility;
import com.projectkorra.projectkorra.airbending.passive.AirSaturation;
import com.projectkorra.projectkorra.configuration.ConfigManager;
import com.projectkorra.projectkorra.configuration.configs.abilities.AbilityConfig;
import com.projectkorra.projectkorra.configuration.configs.abilities.air.AirSaturationConfig;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.element.SubElement;
import com.projectkorra.projectkorra.event.AbilityProgressEvent;
@ -31,7 +32,7 @@ public class AbilityManager extends Module {
private final MultiAbilityManager multiAbilityManager;
private final PassiveAbilityManager passiveAbilityManager;
private final MultiKeyMap<String, AbilityHandler> handlerMap = new MultiKeyMap<>();
// private final MultiKeyMap<String, AbilityHandler> handlerMap = new MultiKeyMap<>();
private final Set<Ability> abilities = new HashSet<>();
private final Map<UUID, Map<Class<? extends Ability>, LinkedList<Ability>>> abilityMap = new HashMap<>();
@ -74,7 +75,7 @@ public class AbilityManager extends Module {
try {
ability.tryModifyAttributes();
try (MCTiming abilityTiming = ProjectKorra.timing(ability.getName()).startTiming()) {
try (MCTiming abilityTiming = ProjectKorra.timing(ability.getHandler().getName()).startTiming()) {
ability.progress();
}
@ -84,7 +85,7 @@ public class AbilityManager extends Module {
getPlugin().getLogger().severe(ability.toString());
try {
ability.getPlayer().sendMessage(ChatColor.YELLOW + "[" + new SimpleDateFormat("dd-MM-yyyy HH:mm:ss").format(new Date()) + "] " + ChatColor.RED + "There was an error running " + ability.getName() + ". please notify the server owner describing exactly what you were doing at this moment");
ability.getPlayer().sendMessage(ChatColor.YELLOW + "[" + new SimpleDateFormat("dd-MM-yyyy HH:mm:ss").format(new Date()) + "] " + ChatColor.RED + "There was an error running " + ability.getHandler().getName() + ". please notify the server owner describing exactly what you were doing at this moment");
} catch (final Exception me) {
Bukkit.getLogger().severe("unable to notify ability user of error");
}
@ -97,22 +98,6 @@ public class AbilityManager extends Module {
}
}
}, 1L, 1L);
registerAbilities();
}
/**
* Scans and loads plugin CoreAbilities, and Addon CoreAbilities that are
* located in a Jar file inside of the /ProjectKorra/Abilities/ folder.
*/
public void registerAbilities() {
this.abilities.clear();
this.abilityMap.clear();
// registerPluginAbilities(getPlugin(), "com.projectkorra");
// registerAddonAbilities("Abilities");
registerAbility(new AirSaturation.AirSaturationHandler(AirSaturation.class, AirSaturationConfig.class));
}
// /**
@ -168,62 +153,6 @@ public class AbilityManager extends Module {
// }
// }
private <T extends AbilityHandler> void registerAbility(T abilityHandler) throws AbilityException {
if (abilityHandler == null) {
throw new AbilityException("abilityHandler is null");
}
String abilityName = abilityHandler.getName();
if (abilityName == null) {
throw new AbilityException("Ability " + abilityHandler.getClass().getName() + " has no name");
}
if (!abilityHandler.getConfig().Enabled) {
getPlugin().getLogger().info(abilityName + " is disabled");
return;
}
if (abilityHandler instanceof AddonAbility) {
((AddonAbility) abilityHandler).load();
}
if (abilityHandler instanceof ComboAbility) {
ComboAbility comboAbility = (ComboAbility) abilityHandler;
if (comboAbility.getCombination() == null || comboAbility.getCombination().size() < 2) {
getPlugin().getLogger().info(abilityName + " has no combination");
return;
}
this.comboAbilityManager.registerAbility(abilityHandler);
return;
}
if (abilityHandler instanceof MultiAbility) {
this.multiAbilityManager.registerAbility(abilityHandler);
return;
}
if (abilityHandler instanceof PassiveAbility) {
PassiveAbility passiveAbility = (PassiveAbility) abilityHandler;
// TODO Set Hidden Ability
this.passiveAbilityManager.registerAbility(abilityHandler);
return;
}
this.handlerMap.put(abilityName, abilityHandler);
}
private AbilityConfig getAbilityConfig(Class<? extends Ability> abilityClass) throws AbilityException {
try {
return ConfigManager.getConfig(((Class<? extends AbilityConfig>) ((ParameterizedType) abilityClass.getGenericSuperclass()).getActualTypeArguments()[1]));
} catch (Exception e) {
throw new AbilityException(e);
}
}
public void startAbility(Ability ability) {
if (ability.isStarted()) {
return;
@ -292,18 +221,6 @@ public class AbilityManager extends Module {
return abilities.get(abilities).stream().map(ability::cast).collect(Collectors.toList());
}
public AbilityHandler getHandler(String abilityName) {
return this.handlerMap.get(abilityName);
}
public AbilityHandler getHandler(Class<? extends AbilityHandler> handlerClass) {
return this.handlerMap.get(handlerClass);
}
public List<AbilityHandler> getHandlers() {
return new ArrayList<>(this.handlerMap.values());
}
public <T extends Ability> LinkedList<T> getAbilities(Class<T> abilityClass) {
LinkedList<T> abilities = new LinkedList<>();
@ -318,23 +235,6 @@ public class AbilityManager extends Module {
return new ArrayList<>(this.abilities);
}
public List<AbilityHandler> getHandlers(Element element) {
return this.handlerMap.values().stream()
.filter(ability ->
{
if (ability.getElement().equals(element)) {
return true;
}
if (ability.getElement() instanceof SubElement) {
return ((SubElement) ability.getElement()).getParent().equals(element);
}
return false;
})
.collect(Collectors.toList());
}
/**
* {@link AbilityManager} keeps track of plugins that have registered abilities to use
* for bending reload purposes <br>

View file

@ -0,0 +1,300 @@
package com.projectkorra.projectkorra.ability.abilities.air.airswipe;
import com.projectkorra.projectkorra.GeneralMethods;
import com.projectkorra.projectkorra.ProjectKorra;
import com.projectkorra.projectkorra.ability.Ability;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.ability.AbilityManager;
import com.projectkorra.projectkorra.ability.api.air.AirAbilityHandler;
import com.projectkorra.projectkorra.ability.util.Collision;
import com.projectkorra.projectkorra.attribute.Attribute;
import com.projectkorra.projectkorra.command.Commands;
import com.projectkorra.projectkorra.earthbending.lava.LavaFlow;
import com.projectkorra.projectkorra.module.ModuleManager;
import com.projectkorra.projectkorra.util.DamageHandler;
import com.projectkorra.projectkorra.util.TempBlock;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.block.Block;
import org.bukkit.block.data.Levelled;
import org.bukkit.entity.Entity;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player;
import org.bukkit.scheduler.BukkitRunnable;
import org.bukkit.util.Vector;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.concurrent.ConcurrentHashMap;
public class AirSwipe extends Ability<AirSwipeHandler> {
// Limiting the entities reduces the risk of crashing.
private static final int MAX_AFFECTABLE_ENTITIES = 10;
private boolean charging;
@Attribute("Arc")
private int arc;
private int particles;
@Attribute("ArcIncrement")
private int arcIncrement;
@Attribute(Attribute.CHARGE_DURATION)
private long maxChargeTime;
@Attribute(Attribute.COOLDOWN)
private long cooldown;
@Attribute(Attribute.DAMAGE)
private double damage;
@Attribute(Attribute.KNOCKBACK)
private double pushFactor;
@Attribute(Attribute.SPEED)
private double speed;
@Attribute(Attribute.RANGE)
private double range;
@Attribute(Attribute.RADIUS)
private double radius;
private double maxChargeFactor;
private Location origin;
private Random random;
private Map<Vector, Location> elements;
private ArrayList<Entity> affectedEntities;
public AirSwipe(AirSwipeHandler abilityHandler, Player player) {
super(abilityHandler, player);
if (this.manager.hasAbility(player, AirSwipe.class)) {
for (AirSwipe airSwipe : this.manager.getAbilities(player, AirSwipe.class)) {
if (airSwipe.charging) {
airSwipe.launch();
airSwipe.charging = false;
return;
}
}
}
this.charging = charging;
this.origin = GeneralMethods.getMainHandLocation(player);
this.particles = abilityHandler.getConfig().AnimationParticleAmount;
this.arc = abilityHandler.getConfig().Arc;
this.arcIncrement = abilityHandler.getConfig().StepSize;
this.maxChargeTime = abilityHandler.getConfig().MaxChargeTime;
this.cooldown = abilityHandler.getConfig().Cooldown;
this.damage = abilityHandler.getConfig().Damage;
this.pushFactor = abilityHandler.getConfig().PushFactor;
this.speed = abilityHandler.getConfig().Speed * (ProjectKorra.time_step / 1000.0);
this.range = abilityHandler.getConfig().Range;
this.radius = abilityHandler.getConfig().Radius;
this.maxChargeFactor = abilityHandler.getConfig().MaxChargeFactor;
this.random = new Random();
this.elements = new ConcurrentHashMap<>();
this.affectedEntities = new ArrayList<>();
if (this.bendingPlayer.isOnCooldown(abilityHandler) || player.getEyeLocation().getBlock().isLiquid()) {
this.remove();
return;
}
if (!this.bendingPlayer.canBend(abilityHandler)) {
this.remove();
return;
}
if (!charging) {
this.launch();
}
if (this.bendingPlayer.isAvatarState()) {
this.cooldown = abilityHandler.getConfig().AvatarState_Cooldown;
this.damage = abilityHandler.getConfig().AvatarState_Damage;
this.pushFactor = abilityHandler.getConfig().AvatarState_PushFactor;
this.range = abilityHandler.getConfig().AvatarState_Range;
this.radius = abilityHandler.getConfig().AvatarState_Radius;
}
this.start();
}
/**
* This method was used for the old collision detection system. Please see
* {@link Collision} for the new system.
*/
@Deprecated
public static boolean removeSwipesAroundPoint(final Location loc, final double radius) {
boolean removed = false;
for (final AirSwipe aswipe : ModuleManager.getModule(AbilityManager.class).getAbilities(AirSwipe.class)) {
for (final Vector vec : aswipe.elements.keySet()) {
final Location vectorLoc = aswipe.elements.get(vec);
if (vectorLoc != null && vectorLoc.getWorld().equals(loc.getWorld())) {
if (vectorLoc.distanceSquared(loc) <= radius * radius) {
aswipe.remove();
removed = true;
}
}
}
}
return removed;
}
private void advanceSwipe() {
this.affectedEntities.clear();
for (final Vector direction : this.elements.keySet()) {
Location location = this.elements.get(direction);
if (direction != null && location != null) {
location = location.clone().add(direction.clone().multiply(this.speed));
this.elements.put(direction, location);
if (location.distanceSquared(this.origin) > this.range * this.range || GeneralMethods.isRegionProtectedFromBuild(this, location)) {
this.elements.clear();
} else {
final Block block = location.getBlock();
if (!AbilityHandler.isTransparent(this.player, block)) {
this.remove();
return;
}
for (final Block testblock : GeneralMethods.getBlocksAroundPoint(location, this.radius)) {
if (testblock.getType() == Material.FIRE) {
testblock.setType(Material.AIR);
}
}
if (!AbilityHandler.isAir(block.getType())) {
if (block.getType().equals(Material.SNOW)) {
continue;
} else if (AbilityHandler.isPlant(block.getType())) {
block.breakNaturally();
} else {
this.elements.remove(direction);
}
if (AbilityHandler.isLava(block)) {
if (LavaFlow.isLavaFlowBlock(block)) {
LavaFlow.removeBlock(block); // TODO: Make more generic for future lava generating moves.
} else
if (block.getBlockData() instanceof Levelled && ((Levelled) block.getBlockData()).getLevel() == 0) {
new TempBlock(block, Material.OBSIDIAN);
} else {
new TempBlock(block, Material.COBBLESTONE);
}
}
} else {
AirAbilityHandler.playAirbendingParticles(location, this.particles, 0.2F, 0.2F, 0);
if (this.random.nextInt(4) == 0) {
AirAbilityHandler.playAirbendingSound(location);
}
this.affectPeople(location, direction);
}
}
}
}
if (this.elements.isEmpty()) {
this.remove();
}
}
private void affectPeople(final Location location, final Vector direction) {
final List<Entity> entities = GeneralMethods.getEntitiesAroundPoint(location, this.radius);
final Vector fDirection = direction.clone();
for (int i = 0; i < entities.size(); i++) {
final Entity entity = entities.get(i);
final AirSwipe abil = this;
new BukkitRunnable() {
@Override
public void run() {
if (GeneralMethods.isRegionProtectedFromBuild(AirSwipe.this, entity.getLocation())) {
return;
}
if (entity.getEntityId() != AirSwipe.this.player.getEntityId() && entity instanceof LivingEntity) {
if (entity instanceof Player) {
if (Commands.invincible.contains(((Player) entity).getName())) {
return;
}
}
if (entities.size() < MAX_AFFECTABLE_ENTITIES) {
GeneralMethods.setVelocity(entity, fDirection.multiply(AirSwipe.this.pushFactor));
}
if (!AirSwipe.this.affectedEntities.contains(entity)) {
if (AirSwipe.this.damage != 0) {
DamageHandler.damageEntity(entity, AirSwipe.this.damage, abil);
}
AirSwipe.this.affectedEntities.add(entity);
}
AirAbilityHandler.breakBreathbendingHold(entity);
AirSwipe.this.elements.remove(direction);
} else if (entity.getEntityId() != AirSwipe.this.player.getEntityId() && !(entity instanceof LivingEntity)) {
GeneralMethods.setVelocity(entity, fDirection.multiply(AirSwipe.this.pushFactor));
}
}
}.runTaskLater(ProjectKorra.plugin, i / MAX_AFFECTABLE_ENTITIES);
}
}
private void launch() {
this.bendingPlayer.addCooldown(getHandler(), this.cooldown);
this.origin = this.player.getEyeLocation();
for (double i = -this.arc; i <= this.arc; i += this.arcIncrement) {
final double angle = Math.toRadians(i);
final Vector direction = this.player.getEyeLocation().getDirection().clone();
double x, z, vx, vz;
x = direction.getX();
z = direction.getZ();
vx = x * Math.cos(angle) - z * Math.sin(angle);
vz = x * Math.sin(angle) + z * Math.cos(angle);
direction.setX(vx);
direction.setZ(vz);
this.elements.put(direction, this.origin);
}
}
@Override
public void progress() {
if (!this.bendingPlayer.canBendIgnoreBindsCooldowns(this.abilityHandler)) {
this.remove();
return;
}
if (this.player.isDead() || !this.player.isOnline()) {
this.remove();
return;
}
if (!this.charging) {
if (this.elements.isEmpty()) {
this.remove();
return;
}
this.advanceSwipe();
} else {
if (!this.player.isSneaking()) {
double factor = 1;
if (System.currentTimeMillis() >= this.getStartTime() + this.maxChargeTime) {
factor = this.maxChargeFactor;
} else {
factor = this.maxChargeFactor * (System.currentTimeMillis() - this.getStartTime()) / this.maxChargeTime;
}
this.charging = false;
this.launch();
factor = Math.max(1, factor);
this.damage *= factor;
this.pushFactor *= factor;
} else if (System.currentTimeMillis() >= this.getStartTime() + this.maxChargeTime) {
AirAbilityHandler.playAirbendingParticles(this.player.getEyeLocation(), this.particles);
}
}
}
@Override
public Location getLocation() {
return this.elements.size() != 0 ? this.elements.values().iterator().next() : null;
}
}

View file

@ -0,0 +1,39 @@
package com.projectkorra.projectkorra.ability.abilities.air.airswipe;
import com.projectkorra.projectkorra.configuration.configs.abilities.AbilityConfig;
public class AirSwipeConfig extends AbilityConfig {
public final long Cooldown = 1250;
public final int AnimationParticleAmount = 2;
public final int Arc = 16;
public final int StepSize = 4;
public final long MaxChargeTime = 2500;
public final double Damage = 2;
public final double PushFactor = .5;
public final double Speed = 25;
public final double Range = 15;
public final double Radius = 1.5;
public final double MaxChargeFactor = 3;
public final long AvatarState_Cooldown = 700;
public final double AvatarState_Damage = 3;
public final double AvatarState_PushFactor = 1.0;
public final double AvatarState_Range = 20;
public final double AvatarState_Radius = 2;
public AirSwipeConfig() {
super(true, "AirSwipe is the most commonly used damage ability in an airbender's arsenal. An arc of air will flow from you towards the direction you're facing, cutting and pushing back anything in its path. This ability will extinguish fires, cool lava, and cut things like grass, mushrooms, and flowers.", "\"\\n\" + \"(Uncharged) Simply left click to send an air swipe out that will damage targets that it comes into contact with.\" + \"\\n\" + \"(Charged) Hold sneak until particles appear, then release sneak to send a more powerful air swipe out that damages entity's that it comes into contact with.\"");
}
@Override
public String getName() {
return "AirSwipe";
}
@Override
public String[] getParents() {
return new String[] { "Abilities", "Air" };
}
}

View file

@ -0,0 +1,30 @@
package com.projectkorra.projectkorra.ability.abilities.air.airswipe;
import com.projectkorra.projectkorra.ability.api.air.AirAbilityHandler;
public class AirSwipeHandler extends AirAbilityHandler<AirSwipe, AirSwipeConfig> {
public AirSwipeHandler(Class<AirSwipe> abilityClass, Class<AirSwipeConfig> configClass) {
super(abilityClass, configClass);
}
@Override
public String getName() {
return "AirSwipe";
}
@Override
public boolean isSneakAbility() {
return true;
}
@Override
public boolean isHarmlessAbility() {
return false;
}
@Override
public long getCooldown() {
return getConfig().Cooldown;
}
}

View file

@ -0,0 +1,30 @@
package com.projectkorra.projectkorra.ability.abilities.chi;
import com.projectkorra.projectkorra.ability.Ability;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.configuration.configs.abilities.AbilityConfig;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.element.ElementManager;
import com.projectkorra.projectkorra.module.ModuleManager;
public abstract class ChiAbilityHandler<T extends Ability, U extends AbilityConfig> extends AbilityHandler<T, U> {
public ChiAbilityHandler(Class<T> abilityClass, Class<U> configClass) {
super(abilityClass, configClass);
}
@Override
public boolean isIgniteAbility() {
return false;
}
@Override
public boolean isExplosiveAbility() {
return false;
}
@Override
public Element getElement() {
return ModuleManager.getModule(ElementManager.class).getChi();
}
}

View file

@ -0,0 +1,160 @@
package com.projectkorra.projectkorra.ability.api.air;
import com.projectkorra.projectkorra.GeneralMethods;
import com.projectkorra.projectkorra.ability.Ability;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.ability.util.Collision;
import com.projectkorra.projectkorra.configuration.ConfigManager;
import com.projectkorra.projectkorra.configuration.configs.abilities.AbilityConfig;
import com.projectkorra.projectkorra.configuration.configs.properties.AirPropertiesConfig;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.element.ElementManager;
import com.projectkorra.projectkorra.module.ModuleManager;
import com.projectkorra.projectkorra.util.ParticleEffect;
import org.bukkit.Location;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import java.util.ArrayList;
import java.util.List;
public abstract class AirAbilityHandler<T extends Ability, U extends AbilityConfig> extends AbilityHandler<T, U> {
public AirAbilityHandler(Class<T> abilityClass, Class<U> configClass) {
super(abilityClass, configClass);
}
@Override
public boolean isIgniteAbility() {
return false;
}
@Override
public boolean isExplosiveAbility() {
return false;
}
@Override
public Element getElement() {
return ModuleManager.getModule(ElementManager.class).getAir();
}
// @Override
// public void handleCollision(final Collision collision) {
// super.handleCollision(collision);
// if (collision.isRemovingFirst()) {
// ParticleEffect.BLOCK_CRACK.display(collision.getLocationFirst(), 10, 1, 1, 1, 0.1, Material.WHITE_WOOL.createBlockData());
// }
// }
/**
* Breaks a breathbendng hold on an entity or one a player is inflicting on
* an entity.
*
* @param entity The entity to be acted upon
*/
public static void breakBreathbendingHold(final Entity entity) {
// if (Suffocate.isBreathbent(entity)) {
// Suffocate.breakSuffocate(entity);
// return;
// }
//
// if (entity instanceof Player) {
// final Player player = (Player) entity;
// if (Suffocate.isChannelingSphere(player)) {
// Suffocate.remove(player);
// }
// }
}
/**
* Gets the Air Particles from the config.
*
* @return Config specified ParticleEffect
*/
public static ParticleEffect getAirbendingParticles() {
return ConfigManager.getConfig(AirPropertiesConfig.class).Particles;
}
/**
* This method was used for the old collision detection system. Please see
* {@link Collision} for the new system.
* <p>
* Checks whether a location is within an AirShield.
*
* @param loc The location to check
* @return true If the location is inside an AirShield.
*/
@Deprecated
public static boolean isWithinAirShield(final Location loc) {
final List<String> list = new ArrayList<String>();
list.add("AirShield");
return GeneralMethods.blockAbilities(null, list, loc, 0);
}
/**
* Plays an integer amount of air particles in a location.
*
* @param loc The location to use
* @param amount The amount of particles
*/
public static void playAirbendingParticles(final Location loc, final int amount) {
playAirbendingParticles(loc, amount, Math.random(), Math.random(), Math.random());
}
/**
* Plays an integer amount of air particles in a location with a given
* xOffset, yOffset, and zOffset.
*
* @param loc The location to use
* @param amount The amount of particles
* @param xOffset The xOffset to use
* @param yOffset The yOffset to use
* @param zOffset The zOffset to use
*/
public static void playAirbendingParticles(final Location loc, final int amount, final double xOffset, final double yOffset, final double zOffset) {
getAirbendingParticles().display(loc, amount, xOffset, yOffset, zOffset);
}
/**
* Plays the Airbending Sound at a location if enabled in the config.
*
* @param loc The location to play the sound at
*/
public static void playAirbendingSound(final Location loc) {
AirPropertiesConfig air = ConfigManager.getConfig(AirPropertiesConfig.class);
if (air.PlaySound) {
loc.getWorld().playSound(loc, air.SoundType, air.SoundVolume, air.SoundPitch);
}
}
/**
* This method was used for the old collision detection system. Please see
* {@link Collision} for the new system.
* <p>
* Removes all air spouts in a location within a certain radius.
*
* @param loc The location to use
* @param radius The radius around the location to remove spouts in
* @param source The player causing the removal
*/
@Deprecated
public static void removeAirSpouts(final Location loc, final double radius, final Player source) {
// AirSpout.removeSpouts(loc, radius, source);
}
/**
* This method was used for the old collision detection system. Please see
* {@link Collision} for the new system.
* <p>
* Removes all air spouts in a location with a radius of 1.5.
*
* @param loc The location to use
* @param source The player causing the removal
*/
@Deprecated
public static void removeAirSpouts(final Location loc, final Player source) {
removeAirSpouts(loc, 1.5, source);
}
}

View file

@ -0,0 +1,4 @@
package com.projectkorra.projectkorra.ability.api.air;
public class FlightAbilityHandler {
}

View file

@ -0,0 +1,4 @@
package com.projectkorra.projectkorra.ability.api.air;
public class SpiritualAbilityHandler {
}

View file

@ -1,6 +1,7 @@
package com.projectkorra.projectkorra.ability.bind;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.ability.AbilityHandlerManager;
import com.projectkorra.projectkorra.ability.AbilityManager;
import com.projectkorra.projectkorra.ability.api.PlayerBindChangeEvent;
import com.projectkorra.projectkorra.configuration.ConfigManager;
@ -25,12 +26,14 @@ public class AbilityBindManager extends PlayerDatabaseModule<String[], AbilityBi
private final BendingPlayerManager bendingPlayerManager;
private final AbilityManager abilityManager;
private final AbilityHandlerManager abilityHandlerManager;
private AbilityBindManager() {
super("Ability Binds", new AbilityBindRepository());
this.bendingPlayerManager = ModuleManager.getModule(BendingPlayerManager.class);
this.abilityManager = ModuleManager.getModule(AbilityManager.class);
this.bendingPlayerManager = module(BendingPlayerManager.class);
this.abilityManager = module(AbilityManager.class);
this.abilityHandlerManager = module(AbilityHandlerManager.class);
runAsync(() -> {
try {
@ -183,7 +186,7 @@ public class AbilityBindManager extends PlayerDatabaseModule<String[], AbilityBi
return;
}
AbilityHandler abilityHandler = this.abilityManager.getHandler(abilityName);
AbilityHandler abilityHandler = this.abilityHandlerManager.getHandler(abilityName);
if (abilityHandler == null) {
ActionBar.sendActionBar(abilityName, player);

View file

@ -81,7 +81,11 @@ public abstract class Module implements Listener {
getPlugin().getLogger().log(level, String.format(LOG_FORMAT, getName(), message));
}
public ProjectKorra getPlugin() {
public final ProjectKorra getPlugin() {
return JavaPlugin.getPlugin(ProjectKorra.class);
}
public final <T extends Module> T module(Class<T> moduleClass) {
return ModuleManager.getModule(moduleClass);
}
}

View file

@ -1,23 +1,28 @@
package com.projectkorra.projectkorra.player;
import com.projectkorra.projectkorra.GeneralMethods;
import com.projectkorra.projectkorra.ability.Ability;
import com.projectkorra.projectkorra.ability.AbilityHandler;
import com.projectkorra.projectkorra.ability.AbilityManager;
import com.projectkorra.projectkorra.ability.PassiveAbilityManager;
import com.projectkorra.projectkorra.ability.legacy.ChiAbility;
import com.projectkorra.projectkorra.ability.abilities.chi.ChiAbilityHandler;
import com.projectkorra.projectkorra.ability.api.AvatarAbility;
import com.projectkorra.projectkorra.ability.bind.AbilityBindManager;
import com.projectkorra.projectkorra.ability.info.AbilityInfo;
import com.projectkorra.projectkorra.ability.api.AvatarAbilityInfo;
import com.projectkorra.projectkorra.command.Commands;
import com.projectkorra.projectkorra.configuration.ConfigManager;
import com.projectkorra.projectkorra.configuration.configs.properties.GeneralPropertiesConfig;
import com.projectkorra.projectkorra.cooldown.CooldownManager;
import com.projectkorra.projectkorra.element.Element;
import com.projectkorra.projectkorra.element.ElementManager;
import com.projectkorra.projectkorra.element.SubElement;
import com.projectkorra.projectkorra.module.ModuleManager;
import org.bukkit.GameMode;
import org.bukkit.Location;
import org.bukkit.entity.Player;
import java.util.HashSet;
import java.util.Set;
import java.util.UUID;
import java.util.stream.Stream;
public class BendingPlayer {
@ -36,7 +41,7 @@ public class BendingPlayer {
private final Set<Element> toggledElements;
private ChiAbility stance;
private ChiAbilityHandler stance;
private boolean bendingPermanentlyRemoved;
private boolean toggled;
private boolean tremorSense;
@ -153,18 +158,74 @@ public class BendingPlayer {
return this.abilityBindManager.getAbilities(this.player);
}
public boolean canBind(AbilityInfo abilityInfo) {
if (abilityInfo == null || !this.player.isOnline()) {
public boolean canBend(AbilityHandler abilityHandler) {
return canBend(abilityHandler, false, false);
}
public boolean canBendIgnoreBinds(AbilityHandler abilityHandler) {
return canBend(abilityHandler, true, false);
}
public boolean canBendIgnoreCooldowns(AbilityHandler abilityHandler) {
return canBend(abilityHandler, false, true);
}
public boolean canBendIgnoreBindsCooldowns(AbilityHandler abilityHandler) {
return canBend(abilityHandler, true, true);
}
private boolean canBend(AbilityHandler abilityHandler, boolean ignoreBinds, boolean ignoreCooldowns) {
if (abilityHandler == null) {
return false;
}
if (!this.player.hasPermission("bending.ability." + abilityInfo.getName())) {
final Location playerLoc = this.player.getLocation();
if (!this.player.isOnline() || this.player.isDead()) {
return false;
} else if (!this.canBind(abilityHandler)) {
return false;
// } else if (ability.getPlayer() != null && ability.getLocation() != null && !ability.getLocation().getWorld().equals(this.player.getWorld())) {
// return false;
} else if (!ignoreCooldowns && this.isOnCooldown(abilityHandler.getName())) {
return false;
} else if (!ignoreBinds && (!abilityHandler.getName().equals(this.getBoundAbility()))) {
return false;
} else if (Stream.of(ConfigManager.getConfig(GeneralPropertiesConfig.class).DisabledWorlds).anyMatch(this.player.getWorld().getName()::equalsIgnoreCase)) {
return false;
} else if (Commands.isToggledForAll || !this.isToggled() || !this.isElementToggled(abilityHandler.getElement())) {
return false;
} else if (this.player.getGameMode() == GameMode.SPECTATOR) {
return false;
}
Element element = abilityInfo.getElement();
if (!ignoreCooldowns && isOnCooldown(abilityHandler.getName())) {
if (getCooldown(abilityHandler.getName()) + ConfigManager.getConfig(GeneralPropertiesConfig.class).GlobalCooldown >= System.currentTimeMillis()) {
return false;
}
}
if (!hasElement(element) && !(abilityInfo instanceof AvatarAbilityInfo && !((AvatarAbilityInfo) abilityInfo).requireAvatar())) {
if (this.isChiBlocked() || this.isParalyzed() || (this.isBloodbent() && !abilityHandler.getName().equalsIgnoreCase("AvatarState")) || this.isControlledByMetalClips()) {
return false;
} else if (GeneralMethods.isRegionProtectedFromBuild(this.player, abilityHandler.getName(), playerLoc)) {
return false;
}
return true;
}
public boolean canBind(AbilityHandler abilityHandler) {
if (abilityHandler == null || !this.player.isOnline()) {
return false;
}
if (!this.player.hasPermission("bending.ability." + abilityHandler.getName())) {
return false;
}
Element element = abilityHandler.getElement();
if (!hasElement(element) && !(abilityHandler instanceof AvatarAbility && !((AvatarAbility) abilityHandler).requireAvatar())) {
return false;
}
@ -177,7 +238,7 @@ public class BendingPlayer {
return true;
}
public long getCooldown(Ability ability) {
public long getCooldown(AbilityHandler ability) {
return getCooldown(ability.getName());
}
@ -185,15 +246,16 @@ public class BendingPlayer {
return this.cooldownManager.getCooldown(this.player, abilityName);
}
public void addCooldown(Ability ability) {
public void addCooldown(AbilityHandler ability) {
addCooldown(ability, ability.getCooldown());
}
public void addCooldown(Ability ability, long duration) {
// TODO Move this method into AbilityHandler, which calls BendingPlayer#addCooldown(String, Long)
public void addCooldown(AbilityHandler ability, long duration) {
addCooldown(ability.getName(), duration);
}
public void addCooldown(Ability ability, long duration, boolean permanent) {
public void addCooldown(AbilityHandler ability, long duration, boolean permanent) {
addCooldown(ability.getName(), duration, permanent);
}
@ -205,7 +267,7 @@ public class BendingPlayer {
this.cooldownManager.addCooldown(this.player, abilityName, duration, permanent);
}
public boolean isOnCooldown(Ability ability) {
public boolean isOnCooldown(AbilityHandler ability) {
return isOnCooldown(ability.getName());
}
@ -213,7 +275,7 @@ public class BendingPlayer {
return this.cooldownManager.isOnCooldown(this.player, abilityName);
}
public void removeCooldown(Ability ability) {
public void removeCooldown(AbilityHandler ability) {
removeCooldown(ability.getName());
}
@ -241,11 +303,11 @@ public class BendingPlayer {
return !hasWeapon;
}
public ChiAbility getStance() {
public ChiAbilityHandler getStance() {
return this.stance;
}
public void setStance(ChiAbility stance) {
public void setStance(ChiAbilityHandler stance) {
this.stance = stance;
}
@ -282,6 +344,21 @@ public class BendingPlayer {
this.illumination = !this.illumination;
}
public boolean isAvatarState() {
return false;
// return this.abilityManager.hasAbility(this.player, AvatarState.class);
}
public boolean isBloodbent() {
return false;
// return BloodBending.isBloodbent(this.player);
}
public boolean isControlledByMetalClips() {
return false;
// return MetalClips.isControlled(this.player);
}
public boolean isChiBlocked() {
return this.chiBlocked;
}
@ -294,6 +371,10 @@ public class BendingPlayer {
this.chiBlocked = false;
}
public boolean isParalyzed() {
return this.player.hasMetadata("movement:stop");
}
public boolean canBeSlowed() {
return System.currentTimeMillis() > this.slowTime;
}