2013-03-06 18:31:48 +01:00
package com.gmail.nossr50.skills.salvage ;
2013-12-14 14:27:50 +01:00
import com.gmail.nossr50.config.Config ;
2013-03-06 18:31:48 +01:00
import com.gmail.nossr50.datatypes.player.McMMOPlayer ;
2018-12-29 14:24:55 +01:00
import com.gmail.nossr50.datatypes.skills.PrimarySkill ;
2013-03-06 18:31:48 +01:00
import com.gmail.nossr50.locale.LocaleLoader ;
2018-07-26 02:29:40 +02:00
import com.gmail.nossr50.mcMMO ;
2013-03-06 18:31:48 +01:00
import com.gmail.nossr50.skills.SkillManager ;
import com.gmail.nossr50.skills.salvage.Salvage.Tier ;
2013-12-14 14:27:50 +01:00
import com.gmail.nossr50.skills.salvage.salvageables.Salvageable ;
2018-04-02 18:59:00 +02:00
import com.gmail.nossr50.util.EventUtils ;
2013-03-06 18:31:48 +01:00
import com.gmail.nossr50.util.Misc ;
import com.gmail.nossr50.util.Permissions ;
2013-12-14 14:27:50 +01:00
import com.gmail.nossr50.util.StringUtils ;
import com.gmail.nossr50.util.skills.SkillUtils ;
2018-07-26 02:29:40 +02:00
import org.bukkit.Location ;
import org.bukkit.Material ;
import org.bukkit.Sound ;
import org.bukkit.enchantments.Enchantment ;
import org.bukkit.entity.Player ;
import org.bukkit.inventory.ItemStack ;
import org.bukkit.inventory.meta.EnchantmentStorageMeta ;
import java.util.Map ;
import java.util.Map.Entry ;
2013-03-06 18:31:48 +01:00
public class SalvageManager extends SkillManager {
private boolean placedAnvil ;
private int lastClick ;
public SalvageManager ( McMMOPlayer mcMMOPlayer ) {
2018-12-29 14:24:55 +01:00
super ( mcMMOPlayer , PrimarySkill . SALVAGE ) ;
2013-03-06 18:31:48 +01:00
}
/ * *
* Handles notifications for placing an anvil .
* /
2013-12-14 14:27:50 +01:00
public void placedAnvilCheck ( ) {
2013-03-06 18:31:48 +01:00
Player player = getPlayer ( ) ;
2013-12-14 14:27:50 +01:00
if ( getPlacedAnvil ( ) ) {
2013-03-06 18:31:48 +01:00
return ;
}
2013-12-14 14:27:50 +01:00
if ( Config . getInstance ( ) . getSalvageAnvilMessagesEnabled ( ) ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Listener.Anvil " ) ) ;
}
if ( Config . getInstance ( ) . getSalvageAnvilPlaceSoundsEnabled ( ) ) {
2018-07-26 02:29:40 +02:00
player . playSound ( player . getLocation ( ) , Sound . BLOCK_ANVIL_LAND , Misc . ANVIL_USE_VOLUME , Misc . ANVIL_USE_PITCH ) ;
2013-12-14 14:27:50 +01:00
}
2013-03-06 18:31:48 +01:00
2013-12-14 14:27:50 +01:00
togglePlacedAnvil ( ) ;
2013-03-06 18:31:48 +01:00
}
public void handleSalvage ( Location location , ItemStack item ) {
Player player = getPlayer ( ) ;
2013-12-14 14:27:50 +01:00
Salvageable salvageable = mcMMO . getSalvageableManager ( ) . getSalvageable ( item . getType ( ) ) ;
2018-05-10 05:54:35 +02:00
if ( item . getItemMeta ( ) . isUnbreakable ( ) ) {
player . sendMessage ( LocaleLoader . getString ( " Anvil.Unbreakable " ) ) ;
return ;
}
2013-12-14 14:27:50 +01:00
// Permissions checks on material and item types
if ( ! Permissions . salvageItemType ( player , salvageable . getSalvageItemType ( ) ) ) {
player . sendMessage ( LocaleLoader . getString ( " mcMMO.NoPermission " ) ) ;
return ;
}
if ( ! Permissions . salvageMaterialType ( player , salvageable . getSalvageMaterialType ( ) ) ) {
player . sendMessage ( LocaleLoader . getString ( " mcMMO.NoPermission " ) ) ;
return ;
}
int skillLevel = getSkillLevel ( ) ;
int minimumSalvageableLevel = salvageable . getMinimumLevel ( ) ;
// Level check
if ( skillLevel < minimumSalvageableLevel ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.Adept.Level " , minimumSalvageableLevel , StringUtils . getPrettyItemString ( item . getType ( ) ) ) ) ;
return ;
}
2013-03-06 18:31:48 +01:00
if ( item . getDurability ( ) ! = 0 & & ( getSkillLevel ( ) < Salvage . advancedSalvageUnlockLevel | | ! Permissions . advancedSalvage ( player ) ) ) {
2013-12-14 14:27:50 +01:00
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.Adept.Damaged " ) ) ;
2013-03-06 18:31:48 +01:00
return ;
}
2013-12-14 14:27:50 +01:00
int salvageableAmount = Salvage . calculateSalvageableAmount ( item . getDurability ( ) , salvageable . getMaximumDurability ( ) , salvageable . getMaximumQuantity ( ) ) ;
2013-03-06 18:31:48 +01:00
if ( salvageableAmount = = 0 ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.TooDamaged " ) ) ;
return ;
}
2015-11-04 22:31:30 +01:00
salvageableAmount = Math . max ( ( int ) ( salvageableAmount * getMaxSalvagePercentage ( ) ) , 1 ) ; // Always get at least something back, if you're capable of salvaging it.
2013-03-06 18:31:48 +01:00
2016-03-11 15:20:23 +01:00
player . getInventory ( ) . setItemInMainHand ( new ItemStack ( Material . AIR ) ) ;
2016-03-17 08:06:19 +01:00
location . add ( 0 . 5 , 1 , 0 . 5 ) ;
2013-03-06 18:31:48 +01:00
Map < Enchantment , Integer > enchants = item . getEnchantments ( ) ;
2018-04-02 18:59:00 +02:00
ItemStack enchantBook = null ;
2013-03-06 18:31:48 +01:00
if ( ! enchants . isEmpty ( ) ) {
2018-04-02 18:59:00 +02:00
enchantBook = arcaneSalvageCheck ( enchants ) ;
2013-03-06 18:31:48 +01:00
}
2018-07-27 01:53:29 +02:00
ItemStack salvageResults = new ItemStack ( salvageable . getSalvageMaterial ( ) , salvageableAmount ) ;
2018-04-02 18:59:00 +02:00
//Call event
if ( EventUtils . callSalvageCheckEvent ( player , item , salvageResults , enchantBook ) . isCancelled ( ) ) {
return ;
}
if ( enchantBook ! = null ) {
Misc . dropItem ( location , enchantBook ) ;
}
Misc . dropItems ( location , salvageResults , 1 ) ;
2013-12-14 14:27:50 +01:00
// BWONG BWONG BWONG - CLUNK!
if ( Config . getInstance ( ) . getSalvageAnvilUseSoundsEnabled ( ) ) {
2018-07-26 02:29:40 +02:00
player . playSound ( player . getLocation ( ) , Sound . BLOCK_ANVIL_USE , Misc . ANVIL_USE_VOLUME , Misc . ANVIL_USE_PITCH ) ;
player . playSound ( player . getLocation ( ) , Sound . ENTITY_ITEM_BREAK , 1 . 0F , 1 . 0F ) ;
2013-12-14 14:27:50 +01:00
}
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.Success " ) ) ;
}
2013-03-06 18:31:48 +01:00
2013-12-14 14:27:50 +01:00
public double getMaxSalvagePercentage ( ) {
return Math . min ( ( ( ( Salvage . salvageMaxPercentage / Salvage . salvageMaxPercentageLevel ) * getSkillLevel ( ) ) / 100 . 0D ) , Salvage . salvageMaxPercentage / 100 . 0D ) ;
2013-03-06 18:31:48 +01:00
}
/ * *
* Gets the Arcane Salvage rank
*
* @return the current Arcane Salvage rank
* /
public int getArcaneSalvageRank ( ) {
int skillLevel = getSkillLevel ( ) ;
for ( Tier tier : Tier . values ( ) ) {
if ( skillLevel > = tier . getLevel ( ) ) {
return tier . toNumerical ( ) ;
}
}
return 0 ;
}
public double getExtractFullEnchantChance ( ) {
int skillLevel = getSkillLevel ( ) ;
for ( Tier tier : Tier . values ( ) ) {
if ( skillLevel > = tier . getLevel ( ) ) {
return tier . getExtractFullEnchantChance ( ) ;
}
}
return 0 ;
}
public double getExtractPartialEnchantChance ( ) {
int skillLevel = getSkillLevel ( ) ;
for ( Tier tier : Tier . values ( ) ) {
if ( skillLevel > = tier . getLevel ( ) ) {
return tier . getExtractPartialEnchantChance ( ) ;
}
}
return 0 ;
}
private ItemStack arcaneSalvageCheck ( Map < Enchantment , Integer > enchants ) {
Player player = getPlayer ( ) ;
if ( getArcaneSalvageRank ( ) = = 0 | | ! Permissions . arcaneSalvage ( player ) ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.ArcaneFailed " ) ) ;
return null ;
}
ItemStack book = new ItemStack ( Material . ENCHANTED_BOOK ) ;
EnchantmentStorageMeta enchantMeta = ( EnchantmentStorageMeta ) book . getItemMeta ( ) ;
boolean downgraded = false ;
for ( Entry < Enchantment , Integer > enchant : enchants . entrySet ( ) ) {
int successChance = Misc . getRandom ( ) . nextInt ( activationChance ) ;
if ( ! Salvage . arcaneSalvageEnchantLoss | | getExtractFullEnchantChance ( ) > successChance ) {
enchantMeta . addStoredEnchant ( enchant . getKey ( ) , enchant . getValue ( ) , true ) ;
}
else if ( enchant . getValue ( ) > 1 & & Salvage . arcaneSalvageDowngrades & & getExtractPartialEnchantChance ( ) > successChance ) {
enchantMeta . addStoredEnchant ( enchant . getKey ( ) , enchant . getValue ( ) - 1 , true ) ;
downgraded = true ;
}
else {
downgraded = true ;
}
}
Map < Enchantment , Integer > newEnchants = enchantMeta . getStoredEnchants ( ) ;
if ( newEnchants . isEmpty ( ) ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.ArcaneFailed " ) ) ;
return null ;
}
if ( downgraded | | newEnchants . size ( ) < enchants . size ( ) ) {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.ArcanePartial " ) ) ;
}
else {
player . sendMessage ( LocaleLoader . getString ( " Salvage.Skills.ArcaneSuccess " ) ) ;
}
book . setItemMeta ( enchantMeta ) ;
return book ;
}
2013-12-14 14:27:50 +01:00
/ * *
* Check if the player has tried to use an Anvil before .
* @param actualize
*
* @return true if the player has confirmed using an Anvil
2013-03-06 18:31:48 +01:00
* /
2013-12-14 14:27:50 +01:00
public boolean checkConfirmation ( boolean actualize ) {
Player player = getPlayer ( ) ;
long lastUse = getLastAnvilUse ( ) ;
2013-03-06 18:31:48 +01:00
2013-12-14 14:27:50 +01:00
if ( ! SkillUtils . cooldownExpired ( lastUse , 3 ) | | ! Config . getInstance ( ) . getSalvageConfirmRequired ( ) ) {
return true ;
2013-03-06 18:31:48 +01:00
}
2013-12-14 14:27:50 +01:00
if ( ! actualize ) {
return false ;
}
actualizeLastAnvilUse ( ) ;
player . sendMessage ( LocaleLoader . getString ( " Skills.ConfirmOrCancel " , LocaleLoader . getString ( " Salvage.Pretty.Name " ) ) ) ;
return false ;
2013-03-06 18:31:48 +01:00
}
2013-12-14 14:27:50 +01:00
/ *
* Salvage Anvil Placement
* /
public boolean getPlacedAnvil ( ) {
return placedAnvil ;
}
public void togglePlacedAnvil ( ) {
placedAnvil = ! placedAnvil ;
2013-03-06 18:31:48 +01:00
}
/ *
* Salvage Anvil Usage
* /
2013-12-14 14:27:50 +01:00
public int getLastAnvilUse ( ) {
return lastClick ;
2013-03-06 18:31:48 +01:00
}
2013-12-14 14:27:50 +01:00
public void setLastAnvilUse ( int value ) {
lastClick = value ;
2013-03-06 18:31:48 +01:00
}
2013-12-14 14:27:50 +01:00
public void actualizeLastAnvilUse ( ) {
lastClick = ( int ) ( System . currentTimeMillis ( ) / Misc . TIME_CONVERSION_FACTOR ) ;
2013-03-06 18:31:48 +01:00
}
}