2022-02-01 22:24:39 +01:00
|
|
|
package net.apunch.blacksmith;
|
|
|
|
|
2022-07-19 02:38:35 +02:00
|
|
|
import net.apunch.blacksmith.config.Settings;
|
2022-02-01 22:24:39 +01:00
|
|
|
import net.citizensnpcs.api.npc.NPC;
|
|
|
|
import org.bukkit.NamespacedKey;
|
|
|
|
import org.bukkit.enchantments.Enchantment;
|
|
|
|
import org.bukkit.entity.LivingEntity;
|
|
|
|
import org.bukkit.entity.Player;
|
|
|
|
import org.bukkit.inventory.ItemStack;
|
|
|
|
import org.bukkit.inventory.meta.Damageable;
|
|
|
|
import org.bukkit.inventory.meta.ItemMeta;
|
|
|
|
|
|
|
|
import java.util.Calendar;
|
|
|
|
import java.util.Objects;
|
|
|
|
import java.util.Random;
|
|
|
|
|
2022-07-19 02:38:35 +02:00
|
|
|
/**
|
|
|
|
* A representation of the session between a player and a blacksmith
|
|
|
|
*/
|
|
|
|
public class ReforgeSession implements Runnable {
|
|
|
|
|
2022-02-01 22:24:39 +01:00
|
|
|
private final BlacksmithTrait blacksmithTrait;
|
|
|
|
private final Player player;
|
|
|
|
private final NPC npc;
|
|
|
|
private final ItemStack itemToReforge;
|
|
|
|
private int taskId;
|
|
|
|
private final Settings config;
|
|
|
|
private static final String[] enchantments = new String[Enchantment.values().length];
|
|
|
|
|
2022-07-19 02:38:35 +02:00
|
|
|
/**
|
|
|
|
* Instantiates a new session
|
|
|
|
*
|
|
|
|
* @param blacksmithTrait <p>A reference to the blacksmith trait</p>
|
|
|
|
* @param player <p>The player initiating the session</p>
|
|
|
|
* @param npc <p>The Blacksmith NPC involved in the session</p>
|
|
|
|
* @param config <p>The config to use for the session</p>
|
|
|
|
*/
|
2022-02-01 22:24:39 +01:00
|
|
|
ReforgeSession(BlacksmithTrait blacksmithTrait, Player player, NPC npc, Settings config) {
|
|
|
|
this.blacksmithTrait = blacksmithTrait;
|
|
|
|
this.player = player;
|
|
|
|
this.npc = npc;
|
|
|
|
itemToReforge = player.getInventory().getItemInMainHand();
|
|
|
|
this.config = config;
|
|
|
|
|
|
|
|
int i = 0;
|
|
|
|
for (Enchantment enchantment : Enchantment.values()) {
|
|
|
|
enchantments[i++] = enchantment.getKey().asString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void run() {
|
|
|
|
player.sendMessage(reforgeItemInHand() ? config.getSuccessMessage() : config.getFailMessage());
|
|
|
|
if (npc.getEntity() instanceof Player) {
|
|
|
|
((Player) npc.getEntity()).getInventory().setItemInMainHand(null);
|
|
|
|
} else {
|
|
|
|
Objects.requireNonNull(((LivingEntity) npc.getEntity()).getEquipment()).setItemInMainHand(null);
|
|
|
|
}
|
|
|
|
if (!config.getDisableDelay()) {
|
|
|
|
if (config.getDropItem()) {
|
|
|
|
player.getWorld().dropItemNaturally(npc.getEntity().getLocation(), itemToReforge);
|
|
|
|
} else {
|
|
|
|
player.getInventory().addItem(itemToReforge);
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
player.getInventory().setItemInMainHand(itemToReforge);
|
|
|
|
}
|
|
|
|
blacksmithTrait.unsetSession();
|
|
|
|
// Start cool down
|
|
|
|
Calendar wait = Calendar.getInstance();
|
|
|
|
wait.add(Calendar.SECOND, config.getReforgeCoolDown());
|
|
|
|
blacksmithTrait.addCoolDown(player.getUniqueId(), wait);
|
|
|
|
}
|
|
|
|
|
|
|
|
private boolean reforgeItemInHand() {
|
|
|
|
Random random = new Random();
|
|
|
|
if (random.nextInt(100) < config.getFailChance()) {
|
|
|
|
for (Enchantment enchantment : itemToReforge.getEnchantments().keySet()) {
|
|
|
|
// Remove or downgrade enchantments
|
|
|
|
if (random.nextBoolean()) {
|
|
|
|
itemToReforge.removeEnchantment(enchantment);
|
|
|
|
} else {
|
|
|
|
if (itemToReforge.getEnchantmentLevel(enchantment) > 1) {
|
|
|
|
itemToReforge.removeEnchantment(enchantment);
|
|
|
|
itemToReforge.addEnchantment(enchantment, 1);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
// Damage the item
|
|
|
|
short reforgeDurability = BlacksmithPlugin.getDurability(itemToReforge);
|
|
|
|
short durability = (short) (reforgeDurability + reforgeDurability * random.nextInt(8));
|
|
|
|
short maxDurability = itemToReforge.getType().getMaxDurability();
|
|
|
|
if (durability <= 0) {
|
|
|
|
durability = (short) (maxDurability / 3);
|
|
|
|
} else if (reforgeDurability + durability > maxDurability) {
|
|
|
|
durability = (short) (maxDurability - random.nextInt(maxDurability - 25));
|
|
|
|
}
|
|
|
|
updateDamage(itemToReforge, maxDurability - durability);
|
|
|
|
return false;
|
|
|
|
} else {
|
|
|
|
updateDamage(itemToReforge, 0);
|
|
|
|
|
|
|
|
// Add random enchantments
|
|
|
|
int roll = random.nextInt(100);
|
|
|
|
if (roll < config.getExtraEnchantmentChance() && itemToReforge.getEnchantments().keySet().size() < config.getMaxEnchantments()) {
|
|
|
|
Enchantment enchantment = Enchantment.getByKey(NamespacedKey.fromString(enchantments[random.nextInt(enchantments.length)]));
|
|
|
|
if (Objects.requireNonNull(enchantment).canEnchantItem(itemToReforge)) {
|
2022-07-11 17:35:47 +02:00
|
|
|
int randomBound = enchantment.getMaxLevel() - enchantment.getStartLevel();
|
|
|
|
//A workaround for the random method's bound sometimes being negative
|
|
|
|
if (randomBound >= 0) {
|
2022-07-16 14:56:29 +02:00
|
|
|
itemToReforge.addEnchantment(enchantment, random.nextInt(randomBound) +
|
2022-07-11 17:35:47 +02:00
|
|
|
enchantment.getStartLevel());
|
|
|
|
}
|
2022-02-01 22:24:39 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
private void updateDamage(ItemStack item, int newDamage) {
|
|
|
|
ItemMeta meta = item.getItemMeta();
|
|
|
|
Damageable damageable = (Damageable) meta;
|
|
|
|
damageable.setDamage(newDamage);
|
|
|
|
item.setItemMeta(meta);
|
|
|
|
}
|
|
|
|
|
|
|
|
// Return if the session should end
|
2022-02-02 00:36:15 +01:00
|
|
|
boolean endSession() {
|
2022-02-01 22:24:39 +01:00
|
|
|
// Prevent player from switching items during session
|
2022-02-02 00:36:15 +01:00
|
|
|
ItemStack itemInHand = player.getInventory().getItemInMainHand();
|
|
|
|
if (!itemToReforge.equals(itemInHand)) {
|
2022-02-01 22:24:39 +01:00
|
|
|
player.sendMessage(config.getItemChangedMessage());
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
if (!BlacksmithPlugin.getInstance().doesPlayerHaveEnough(player)) {
|
|
|
|
player.sendMessage(config.getInsufficientFundsMessage());
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
boolean isRunning() {
|
|
|
|
return BlacksmithPlugin.getInstance().getServer().getScheduler().isQueued(taskId);
|
|
|
|
}
|
|
|
|
|
|
|
|
boolean isInSession(Player other) {
|
|
|
|
return player.getName().equals(other.getName());
|
|
|
|
}
|
|
|
|
|
|
|
|
void beginReforge() {
|
|
|
|
if (!config.getDisableCoolDown()) {
|
|
|
|
taskId = BlacksmithPlugin.getInstance().getServer().getScheduler().scheduleSyncDelayedTask(
|
|
|
|
BlacksmithPlugin.getInstance(), this, (new Random().nextInt(config.getMaxReforgeDelay()) +
|
|
|
|
config.getMinReforgeDelay()) * 20L);
|
|
|
|
} else {
|
|
|
|
taskId = BlacksmithPlugin.getInstance().getServer().getScheduler().scheduleSyncDelayedTask(
|
|
|
|
BlacksmithPlugin.getInstance(), this, 0);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public Player getPlayer() {
|
|
|
|
return player;
|
|
|
|
}
|
2022-07-19 02:38:35 +02:00
|
|
|
|
2022-02-01 22:24:39 +01:00
|
|
|
}
|